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

ldapurl (ITS#317)



This is a multi-part message in MIME format.
--------------02712D2DB7C762155228EECD
Content-Type: text/plain; charset=us-ascii
Content-Transfer-Encoding: 7bit

ldapurl  source (LDAP client for searchin LDAP URLs)

--
Aaron Stromas    | "Tick-tick-tick!!!... ja, Pantani is weg..."
Oracle Corp      |                             BRTN commentator
+1 703.708.68.21 |                              L'Alpe d'Huez
                                            1995 Tour de France



--------------02712D2DB7C762155228EECD
Content-Type: text/plain; charset=us-ascii;
 name="ldapurl.c"
Content-Transfer-Encoding: 7bit
Content-Disposition: inline;
 filename="ldapurl.c"

/*  ldapurl.c - LDAP client for searchin LDAP URLs  */

#include "portable.h"

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

#include <ac/ctype.h>
#include <ac/signal.h>
#include <ac/socket.h>
#include <ac/string.h>
#include <ac/time.h>
#include <ac/unistd.h>

#include <lber.h>
#include <ldap.h>
#include <ldif.h>

#include "ldapconfig.h"

#define DEFSEP	"="	/* default separator between attribute names and values */
#ifdef HAVE_KERBEROS
#define OPTIONS        "ABLKRknuvD:F:d:f:h:l:p:w:z:"
#else /* HAVE_KERBEROS */
#define OPTIONS        "ABLRnuvD:F:d:f:h:l:p:w:z:"
#endif /* HAVE_KERBEROS */

typedef struct URL2ID_t {	/* associates URL with LDAP message id */
    char *url;
    int id;
    struct URL2ID_t *next;
} url2id_t;


static int search LDAP_P((
        LDAP *ld,
	char *url,
	int attrsonly ));
	
static void print_entry LDAP_P((
	LDAP *ld,
	LDAPMessage *result,
	int attrsonly ));

static int write_ldif_value LDAP_P((
    char *type,
    char *value,
    unsigned long len ));;

static void enqueue LDAP_P((
	char *url,
	int msgid ));

char *dequeue LDAP_P((
    int msgid ));

static void
usage( s )
char *s;
{
    fprintf( stderr, "usage: %s [options] url [url ...\nwhere:\n", s );
    fprintf( stderr, "    url\tRFC-1959 compliant LDAP URL");
    fprintf( stderr, "options:\n" );
    fprintf( stderr, "    -A\t\tretrieve attribute names only (no values)\n" );
    fprintf( stderr, "    -B\t\tdo not suppress printing of non-ASCII values\n" );
    fprintf( stderr, "    -L\t\tprint entries in LDIF format (-B is implied)\n" );
#ifdef LDAP_REFERRALS
    fprintf( stderr, "    -R\t\tdo not automatically follow referrals\n" );
#endif /* LDAP_REFERRALS */    
    fprintf( stderr, "    -n\t\tshow what would be done but don't actually search\n" );
    fprintf( stderr, "    -u\t\tinclude User Friendly entry names in the output\n" );
    fprintf( stderr, "    -v\t\trun in verbose mode (diagnostics to standard output\n" );
    fprintf( stderr, "    -D binddn\tbind dn\n" );
    fprintf( stderr, "    -F sep\tprint `sep' instead of `=' between attribute names and values\n" );
    fprintf( stderr, "    -S attr\tsort the results by attribute `attr'\n" );
    fprintf( stderr, "    -d level\tset LDAP debugging level to `level'\n" );
    fprintf( stderr, "    -f file\tread LDAP URLs from file `file'\n" );
    fprintf( stderr, "    -h host\tldap server\n" );
    fprintf( stderr, "    -l time lim\ttime limit (in seconds) for search\n" );
    fprintf( stderr, "    -p port\tport on ldap server\n");
    fprintf( stderr, "    -s deref\tone of never, always, search or find (alias dereferencing)\n" );
    fprintf( stderr, "    -w passwd\tbind password (for simple authentication)\n" );
    fprintf( stderr, "    -z size lim\tsize limit (in entries) for search\n" );
    exit( 1 );
}


static char	*ldaphost = NULL;
static char	buffer[BUFSIZ];
static int	ldapport = 0;
static char	*sep = DEFSEP;
static char	*binddn = NULL;
static char	*passwd = NULL;
static int	allow_binary, ldif, includeufn, nosearch, verbose;


int
main( argc, argv)
    int argc;
    char **argv;
{
    int	attrsonly = 0, debug = 0;
    int	deref = -1, sizelimit = -1, timelimit = -1;
    int authmethod = LDAP_AUTH_NONE;
    char *infile = NULL;
    FILE *fp = NULL;
    char *url;
    LDAP *ld;
    int i, rc;
    LDAPMessage *result, *entry;
    BerElement		*ber;
    struct berval	**bvals;
    
#ifdef LDAP_REFERRALS
    int ldap_options = LDAP_OPT_REFERRALS;
#else /* LDAP_REFERRALS */    
    int ldap_options = 0;
#endif /* LDAP_REFERRALS */    

    while ((i = getopt(argc, argv, OPTIONS)) != EOF) {
        switch(i) {

            case 'A': ++attrsonly;		/* retrieve attributes only -- no values */
                      break;

            case 'B': ++allow_binary;		/* allow binary values to be printed */
                      break;

#ifdef HAVE_KERBEROS
            case 'K': if (authmethod != LDAP_AUTH_NONE) {	/* use kerberos bind, 1st part only */
                          fprintf(stderr, "authentication should be one of -K, -k or -w");
                          exit(1);
                      }
                      authmethod = LDAP_AUTH_KRBV41;
                      break;
#endif

            case 'L': ++ldif;			/* print values in LDIF format */
                      break;

            case 'R':				/* print values in LDIF format */
#ifdef LDAP_REFERRALS
                      ldap_options &= ~LDAP_OPT_REFERRALS;
#else /* LDAP_REFERRALS */    
                      fprintf( stderr, "compile with -DLDAP_REFERRALS for referral support\n" );
#endif /* LDAP_REFERRALS */    
                      break;

#ifdef HAVE_KERBEROS
            case 'k': if (authmethod != LDAP_AUTH_NONE) {	 /* use Kerberos bind */
                          fprintf(stderr, "authentication should be one of -K, -k or -w");
                          exit(1);
                      }
                      authmethod = LDAP_AUTH_KRBV4;
                      break;
#endif

            case 'n': ++nosearch;		/* don't do any searches */
                      break;

            case 'u': ++includeufn;		/* include UFN */
                      break;

            case 'v': ++verbose;		/* verbose mode */
                      break;

            case 'D': binddn = strdup(optarg);	/* bind DN */
                      break;

            case 'F': sep = strdup(optarg);	/* field separator */
                      break;

            case 'd': 
#ifdef LDAP_DEBUG
                      debug |= atoi( optarg );		/* debug level */
                      lber_debug = ldap_debug = debug;
#else
                      fprintf(stderr, "compile with -DLDAP_DEBUG for debugging\n");
#endif            
                      break;

            case 'f': infile = strdup( optarg );	/* input file */
                      break;

            case 'h': ldaphost = strdup( optarg );	/* LDAP server */
                      break;

            case 'l': timelimit = atoi( optarg );	/* time limit */
                      break;

            case 'p': ldapport = atoi( optarg );	/* LDAP port */
                      break;

            case 'w': if (authmethod != LDAP_AUTH_NONE) { /* bind password */
                          fprintf(stderr, "authentication should be one of -K, -k or -w");
                          exit(1);
                      }
                      passwd = strdup( optarg );
                      authmethod = LDAP_AUTH_SIMPLE;
                      break;

            case 'z': sizelimit = atoi( optarg );	/* size limit */
                      break;

            default: usage( argv[0] );
        }
    }    

    if (argc - optind < 1 && infile == NULL)
        usage(argv[0]);

    if (infile != NULL) {
        if (infile[0] == '1' && infile[1] == '\0') {
            fp = stdin;
        } else if ((fp = fopen(infile, "r")) == NULL) {
            perror(infile);
            exit(1);
        }
        url = buffer;
    }

#ifdef SIGPIPE
    (void) SIGNAL(SIGPIPE, SIG_IGN);
#endif
        
    if (verbose)
        printf("ldap_init(%s, %s)\n", ldaphost, ldapport);
            
    if ((ld = ldap_init(ldaphost, ldapport)) == NULL) {
        perror("ldap_init");
        exit(1);
    }

    if (deref != -1)
        ld->ld_deref = deref;
    if (timelimit != -1)
        ld->ld_timelimit = timelimit;
    if (sizelimit != -1)
        ld->ld_sizelimit = sizelimit;
    ld->ld_options = ldap_options;    

    if (authmethod == LDAP_AUTH_NONE)
        authmethod = LDAP_AUTH_SIMPLE;

    if (ldap_bind_s(ld, binddn, passwd, authmethod) != LDAP_SUCCESS) {
        ldap_perror(ld, "ldap_bind");
        exit(1);
    }

    
    while (1) {
        if (fp) {
            if (fgets(buffer, sizeof(buffer), fp) == NULL)
                break;
            buffer[strlen(url)-1] = '\0';    
            url = strdup(buffer);
        } else {
            if (optind == argc)
                break;
            url = strdup(argv[optind++]);
        }
        search(ld, url, attrsonly);
    }
}

static int
search(ld, url, attrsonly)
    LDAP *ld;
    char *url;
    int attrsonly;
{
    int first = 1;
    LDAPMessage *result, *entry;
    BerElement		*ber;
    struct berval	**bvals;
    int rc, id;
    
    if ((id = ldap_url_search(ld, url, attrsonly)) == -1) {
        sprintf(buffer, "ldap_url_search(%s)", url);
        ldap_perror(ld, buffer);
        return (ld->ld_errno);
    }
    enqueue(url, id);

    while ((rc = ldap_result(ld, LDAP_RES_ANY, 0, NULL, &result)) == LDAP_RES_SEARCH_ENTRY) {
        entry = ldap_first_entry(ld, result);

        if (entry == NULL)
	    continue;

        if (first)
            first = 0;
        else
            putchar('\n');

        print_entry(ld, entry, attrsonly);

        ldap_msgfree(result);
    }        

    if (rc == -1) {
        ldap_perror(ld, "ldap_result");
        return (rc);
    }

    if ((rc = ldap_result2error(ld, result, 0)) != LDAP_SUCCESS)
        ldap_perror(ld, "ldap_result");

    ldap_msgfree(result);
    return(rc);
}

static void
print_entry(ld, result, attrsonly)
    LDAP *ld;
    LDAPMessage *result;
    int attrsonly;
{
    char		*a, *dn, *ufn;
    int			i, j, notascii;
    BerElement		*ber;
    struct berval	**bvals;
    FILE		*fp;


    printf("\nURL: %s\n", dequeue(result->lm_msgid));
    dn = ldap_get_dn(ld, result);
    if (ldif) 
        write_ldif_value("dn", dn, strlen(dn));
    else
        printf("%s\n", dn);
    if (includeufn) {
        ufn = ldap_dn2ufn(dn);
    }
    free(dn);

    for (a = ldap_first_attribute(ld, result, &ber); a; a = ldap_next_attribute(ld, result, ber)) {
        if (attrsonly) {
            if (ldif)
                write_ldif_value(a, "", 0);
            else
                printf("%s\n", a);
        } else if ((bvals = ldap_get_values_len(ld, result, a)) != NULL) {
            for (i = 0; bvals[i] != NULL; i++) {
                notascii = 0;
                if (!allow_binary)
                    for (j = 0; (unsigned long) j < bvals[i]->bv_len; ++j)
                        if (!isascii(bvals[i]->bv_val[j])) {
                            notascii = 1;
                            break;
                        }

                if (ldif)
                    write_ldif_value(a, bvals[i]->bv_val, bvals[i]->bv_len);
                else
                    printf("%s%s%s\n", a, sep, notascii ? "Not ASCII" : bvals[i]->bv_val);
            }
            ber_bvecfree(bvals);
        }
    }
}

static int
write_ldif_value(type, value, len)
    char *type;
    char *value;
    unsigned long len;
{
    char *ldif;

    if ((ldif = ldif_type_and_value(type, value, (int) len)) == NULL)
        return(-1);

    fputs(ldif, stdout);
    free(ldif);
    return(0);
}

static url2id_t *url_list = NULL;
static int searches = 0;

static void
enqueue(url, msgid)
	char *url;
	int msgid;
{
     url2id_t *p;


    if ((p = (url2id_t *) calloc(1, sizeof(url2id_t))) == NULL) {
        perror("calloc");
        exit(1);
    }

    p->next = url_list;
    p->url = url;
    p->id = msgid;
    url_list = p;

    searches++;
}

char *
dequeue(msgid)
	int msgid;
{
    url2id_t *p = url_list;

    while (p)
	if (p->id == msgid)
	    return p->url;
	else
	    ++p;
    return NULL;
}

--------------02712D2DB7C762155228EECD--