[Date Prev][Date Next] [Chronological] [Thread] [Top]

how to decode the BER encoded data using ber library



Hi,

I am using openldap-2.3.39 stable version. I am able to encode using the
etest.c in library/liblber directory. But I am not able to decode the
encoded data.

I am encoding the data and this data is written to a file in binary format. 
While decoding the data, this file is opened and the descriptor is passed as
the parameter to the function "ber_sockbuf_add_io". Then doing the
ber_get_next and then doing the ber_scanf.

If I have encoded one ber element its decoding. If I decode 2 elements
ber_get_next fails. I am not sure why this is happening.

This is what the output I get when I do ./dtest

[root@Linux liblber]# ./dtest
===fd1 = 3
ber_get_next
ber_get_next: Numerical result out of range
[root@Linux liblber]#


Kindly help me .....

With regards
ShashiKumar.



My program is as follows

-------------------------------------Etest.c-------------------------
#include "lber-int.h"
#include "portable.h"

#include <stdio.h>
#include <ac/stdlib.h>

#include <ac/socket.h>
#include <ac/string.h>
#include <ac/unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>

#ifdef HAVE_CONSOLE_H
#include <console.h>
#endif /* HAVE_CONSOLE_H */

#include "lber.h"

static void usage( const char *name )
{
        fprintf( stderr, "usage: %s fmtstring\n", name );
}

static char* getbuf( void ) {
        char *p;
        static char buf[1024];
        if ( fgets( buf, sizeof(buf), stdin ) == NULL ) return NULL;

        if ( (p = strchr( buf, '\n' )) != NULL ) *p = '\0';

        return buf;
}

int
main( int argc, char **argv )
{
        char    *s;
        char ch = 'i';
        int tag;
        char arr[20];
        int i;
        ber_len_t  count;

        int                     fd, fd1,rc;
        BerElement      *ber , *ber1;
        Sockbuf         *sb;
        /* enable debugging */
        int ival = -1;
ber_set_option( NULL, LBER_OPT_DEBUG_LEVEL, &ival );
        fd = fileno(stdout);

        sb = ber_sockbuf_alloc();
        ber_sockbuf_add_io( sb, &ber_sockbuf_io_fd,
LBER_SBIOD_LEVEL_PROVIDER, (void *)&fd );

        if( sb == NULL ) {
                perror( "ber_sockbuf_alloc_fd" );
                return( EXIT_FAILURE );
        }

        if ( (ber = ber_alloc_t( LBER_USE_DER )) == NULL ) {
                perror( "ber_alloc" );
                return( EXIT_FAILURE );
        }

        fprintf(stderr, "encode: start\n" );

        ber_printf( ber, "iii", 107,108,109);

        if ( ber_flush( sb, ber, 0 ) == -1 ) {
                perror( "ber_flush" );
                return( EXIT_FAILURE );
        }
        memcpy((void *)arr,(void *)ber->ber_buf,ber->ber_len);
        printf("ber_len = %d\n",ber->ber_len);
        fd1 = open("./abc",O_WRONLY|O_CREAT);
        printf("====fd = %d\n",fd1);
        write(fd1,ber->ber_buf,ber->ber_len);
        for(i = 0; i<ber->ber_len; i++)
                printf("0x%02x  ",ber->ber_buf[i]);
        printf("\n");
  	  ber_sockbuf_free( sb );
        ber_free( ber, 1 );
        return( EXIT_SUCCESS );
}


--------------------------dtest.c-------------------------------
#include "portable.h"

#include <stdio.h>

#include <ac/stdlib.h>
#include <ac/string.h>
#include <ac/socket.h>
#include <ac/unistd.h>
#include <ac/errno.h>

#ifdef HAVE_CONSOLE_H
#include <console.h>
#endif

#include <lber.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include<unistd.h>
#include "lber.h"

static void usage( const char *name )
{
        fprintf( stderr, "usage: %s fmt\n", name );
}

int
main( int argc, char **argv )
{
        char *s;

        ber_tag_t       tag;
        ber_len_t       len;

        BerElement      *ber;
        BerElement      *ber1;
        Sockbuf         *sb;
        int             fd,fd1;
                char buf[128];
                char buf1[128];
                char fmt[2];
                int a,b;
                fmt[0] = *s;
                fmt[1] = '\0';

        /* enable debugging */
        int ival = -1;
        ber_set_option( NULL, LBER_OPT_DEBUG_LEVEL, &ival );
/*
        if ( argc < 2 ) {
                usage( argv[0] );
                return( EXIT_FAILURE );
        }
*/
#ifdef HAVE_CONSOLE_H
        ccommand( &argv );
        cshow( stdout );
#endif

        sb = ber_sockbuf_alloc();
        fd1 = open("./abc",O_RDWR);
        printf("===fd1 = %d\n",fd1);
        ber_sockbuf_add_io( sb, &ber_sockbuf_io_fd,
LBER_SBIOD_LEVEL_TRANSPORT, void *)&fd1 );
        ber = ber_alloc_t(LBER_USE_DER);
        ber1 = ber_alloc_t(LBER_USE_DER);
        if( ber == NULL ) {
                perror( "ber_alloc_t" );
                return( EXIT_FAILURE );
        }

        for (;;) {
                tag = ber_get_next( sb, &len, ber);
                if( tag != LBER_ERROR ) break;

                if( errno == EWOULDBLOCK ) continue;
                if( errno == EAGAIN ) continue;

                perror( "ber_get_next" );
                return( EXIT_FAILURE );
        }

        printf("decode: message tag 0x%lx and length %ld\n",
                (unsigned long) tag, (long) len );
        ival = 0;
        for( ;;) {
                 len = sizeof(buf);
                //printf("decode: format %s\n", fmt );
                tag = ber_scanf( ber, "iii", &a, &b ,&buf[0]);
                if( tag == LBER_ERROR ) {
                        perror( "ber_scanf" );
                        return( EXIT_FAILURE );
                }
        }

        ber_sockbuf_free( sb );
        return( EXIT_SUCCESS );
}