diff options
Diffstat (limited to 'ldap/c-sdk/libraries/libldap/pthreadtest.c')
-rw-r--r-- | ldap/c-sdk/libraries/libldap/pthreadtest.c | 1028 |
1 files changed, 0 insertions, 1028 deletions
diff --git a/ldap/c-sdk/libraries/libldap/pthreadtest.c b/ldap/c-sdk/libraries/libldap/pthreadtest.c deleted file mode 100644 index fa913f691..000000000 --- a/ldap/c-sdk/libraries/libldap/pthreadtest.c +++ /dev/null @@ -1,1028 +0,0 @@ -/* ***** BEGIN LICENSE BLOCK ***** - * Version: MPL 1.1/GPL 2.0/LGPL 2.1 - * - * The contents of this file are subject to the Mozilla Public License Version - * 1.1 (the "License"); you may not use this file except in compliance with - * the License. You may obtain a copy of the License at - * http://www.mozilla.org/MPL/ - * - * Software distributed under the License is distributed on an "AS IS" basis, - * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License - * for the specific language governing rights and limitations under the - * License. - * - * The Original Code is Mozilla Communicator client code, released - * March 31, 1998. - * - * The Initial Developer of the Original Code is - * Netscape Communications Corporation. - * Portions created by the Initial Developer are Copyright (C) 1998-1999 - * the Initial Developer. All Rights Reserved. - * - * Contributor(s): - * - * Alternatively, the contents of this file may be used under the terms of - * either of the GNU General Public License Version 2 or later (the "GPL"), - * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"), - * in which case the provisions of the GPL or the LGPL are applicable instead - * of those above. If you wish to allow use of your version of this file only - * under the terms of either the GPL or the LGPL, and not to allow others to - * use your version of this file under the terms of the MPL, indicate your - * decision by deleting the provisions above and replace them with the notice - * and other provisions required by the GPL or the LGPL. If you do not delete - * the provisions above, a recipient may use your version of this file under - * the terms of any one of the MPL, the GPL or the LGPL. - * - * ***** END LICENSE BLOCK ***** */ - -#include <stdio.h> -#include <stdlib.h> -#include <string.h> -#include <malloc.h> -#include <values.h> -#include <errno.h> -#include <pthread.h> -#include <synch.h> - -#include <ldap.h> - -/* Authentication and search information. */ -#define NAME "cn=Directory Manager" -#define PASSWORD "rtfm11111" -#define BASE "dc=example,dc=com" -#define SCOPE LDAP_SCOPE_SUBTREE - -static void *modify_thread(); -static void *add_thread(); -static void *delete_thread(); -static void *bind_thread(); -static void *compare_thread(); -static void *search_thread(); -static void *my_mutex_alloc(); -static void my_mutex_free(); -void *my_sema_alloc( void ); -void my_sema_free( void * ); -int my_sema_wait( void * ); -int my_sema_post( void * ); -static void set_ld_error(); -static int get_ld_error(); -static void set_errno(); -static int get_errno(); -static void tsd_setup(); -static void tsd_cleanup(); -static int get_random_id( void ); -static char *get_id_str( int id ); - -/* Linked list of LDAPMessage structs for search results. */ -typedef struct ldapmsgwrapper { - LDAPMessage *lmw_messagep; - struct ldapmsgwrapper *lmw_next; -} ldapmsgwrapper; - -LDAP *ld; -pthread_key_t key; -int maxid = MAXINT; -int maxops = 0; /* zero means no limit */ -int range_filters = 0; /* if non-zero use >= and >= filters */ - -main( int argc, char **argv ) - -{ - pthread_attr_t attr; - pthread_t *threadids; - void *status; - struct ldap_thread_fns tfns; - struct ldap_extra_thread_fns extrafns; - int rc, c, errflg, i, inited_attr; - int doadd, dodelete, domodify, docompare, dosearch, dobind; - int option_extthreads, option_restart; - int each_thread_count, thread_count; - extern int optind; - extern char *optarg; - - doadd = dodelete = domodify = docompare = dobind = dosearch = 0; - option_extthreads = option_restart = 0; - inited_attr = 0; - errflg = 0; - each_thread_count = 1; /* how many of each type of thread? */ - rc = LDAP_SUCCESS; /* optimistic */ - - while (( c = getopt( argc, argv, "abcdmrsERi:n:o:S:" )) != EOF ) { - switch( c ) { - case 'a': /* perform add operations */ - ++doadd; - break; - case 'b': /* perform bind operations */ - ++dobind; - break; - case 'c': /* perform compare operations */ - ++docompare; - break; - case 'd': /* perform delete operations */ - ++dodelete; - break; - case 'm': /* perform modify operations */ - ++domodify; - break; - case 'r': /* use range filters in searches */ - ++range_filters; - break; - case 's': /* perform search operations */ - ++dosearch; - break; - case 'E': /* use extended thread functions */ - ++option_extthreads; - break; - case 'R': /* turn on LDAP_OPT_RESTART */ - ++option_restart; - break; - case 'i': /* highest # used for entry names */ - maxid = atoi( optarg ); - break; - case 'n': /* # threads for each operation */ - if (( each_thread_count = atoi( optarg )) < 1 ) { - fprintf( stderr, "thread count must be > 0\n" ); - ++errflg; - } - break; - case 'o': /* operations to perform per thread */ - if (( maxops = atoi( optarg )) < 0 ) { - fprintf( stderr, - "operation limit must be >= 0\n" ); - ++errflg; - } - break; - case 'S': /* random number seed */ - if ( *optarg == 'r' ) { - int seed = (int)time( (time_t *)0 ); - srandom( seed ); - printf( "Random seed: %d\n", seed ); - } else { - srandom( atoi( optarg )); - } - break; - default: - ++errflg; - break; - } - } - - /* Check command-line syntax. */ - thread_count = each_thread_count * ( doadd + dodelete + domodify - + dobind + docompare + dosearch ); - if ( thread_count < 1 ) { - fprintf( stderr, - "Specify at least one of -a, -b, -c, -d, -m, or -s\n" ); - ++errflg; - } - - if ( errflg || argc - optind != 2 ) { - fprintf( stderr, "usage: %s [-abcdmrsER] [-i id] [-n thr]" - " [-o oplim] [-S sd] host port\n", argv[0] ); - fputs( "\nWhere:\n" - "\t\"id\" is the highest entry id (name) to use" - " (default is MAXINT)\n" - "\t\"thr\" is the number of threads for each operation" - " (default is 1)\n" - "\t\"oplim\" is the number of ops done by each thread" - " (default is infinite)\n" - "\t\"sd\" is a random() number seed (default is 1). Use" - " the letter r for\n" - "\t\tsd to seed random() using time of day.\n" - "\t\"host\" is the hostname of an LDAP directory server\n" - "\t\"port\" is the TCP port of the LDAP directory server\n" - , stderr ); - fputs( "\nAnd the single character options are:\n" - "\t-a\tstart thread(s) to perform add operations\n" - "\t-b\tstart thread(s) to perform bind operations\n" - "\t-c\tstart thread(s) to perform compare operations\n" - "\t-d\tstart thread(s) to perform delete operations\n" - "\t-m\tstart thread(s) to perform modify operations\n" - "\t-s\tstart thread(s) to perform search operations\n" - "\t-r\tuse range filters in searches\n" - "\t-E\tinstall LDAP_OPT_EXTRA_THREAD_FN_PTRS\n" - "\t-R\tturn on LDAP_OPT_RESTART\n", stderr ); - - return( LDAP_PARAM_ERROR ); - } - - /* Create a key. */ - if ( pthread_key_create( &key, free ) != 0 ) { - perror( "pthread_key_create" ); - } - tsd_setup(); - - /* Allocate space for thread ids */ - if (( threadids = (pthread_t *)calloc( thread_count, - sizeof( pthread_t ))) == NULL ) { - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - - - /* Initialize the LDAP session. */ - if (( ld = ldap_init( argv[optind], atoi( argv[optind+1] ))) == NULL ) { - perror( "ldap_init" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - - /* Set the function pointers for dealing with mutexes - and error information. */ - memset( &tfns, '\0', sizeof(struct ldap_thread_fns) ); - tfns.ltf_mutex_alloc = (void *(*)(void)) my_mutex_alloc; - tfns.ltf_mutex_free = (void (*)(void *)) my_mutex_free; - tfns.ltf_mutex_lock = (int (*)(void *)) pthread_mutex_lock; - tfns.ltf_mutex_unlock = (int (*)(void *)) pthread_mutex_unlock; - tfns.ltf_get_errno = get_errno; - tfns.ltf_set_errno = set_errno; - tfns.ltf_get_lderrno = get_ld_error; - tfns.ltf_set_lderrno = set_ld_error; - tfns.ltf_lderrno_arg = NULL; - - /* Set up this session to use those function pointers. */ - - rc = ldap_set_option( ld, LDAP_OPT_THREAD_FN_PTRS, (void *) &tfns ); - if ( rc < 0 ) { - rc = ldap_get_lderrno( ld, NULL, NULL ); - fprintf( stderr, - "ldap_set_option (LDAP_OPT_THREAD_FN_PTRS): %s\n", - ldap_err2string( rc ) ); - goto clean_up_and_return; - } - - if ( option_extthreads ) { - /* Set the function pointers for working with semaphores. */ - - memset( &extrafns, '\0', sizeof(struct ldap_extra_thread_fns) ); - extrafns.ltf_mutex_trylock = - (int (*)(void *)) pthread_mutex_trylock; - extrafns.ltf_sema_alloc = (void *(*)(void)) my_sema_alloc; - extrafns.ltf_sema_free = (void (*)(void *)) my_sema_free; - extrafns.ltf_sema_wait = (int (*)(void *)) my_sema_wait; - extrafns.ltf_sema_post = (int (*)(void *)) my_sema_post; - - /* Set up this session to use those function pointers. */ - - if ( ldap_set_option( ld, LDAP_OPT_EXTRA_THREAD_FN_PTRS, - (void *) &extrafns ) != 0 ) { - rc = ldap_get_lderrno( ld, NULL, NULL ); - ldap_perror( ld, "ldap_set_option" - " (LDAP_OPT_EXTRA_THREAD_FN_PTRS)" ); - goto clean_up_and_return; - } - } - - - if ( option_restart && ldap_set_option( ld, LDAP_OPT_RESTART, - LDAP_OPT_ON ) != 0 ) { - rc = ldap_get_lderrno( ld, NULL, NULL ); - ldap_perror( ld, "ldap_set_option(LDAP_OPT_RESTART)" ); - goto clean_up_and_return; - } - - /* Attempt to bind to the server. */ - rc = ldap_simple_bind_s( ld, NAME, PASSWORD ); - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "ldap_simple_bind_s: %s\n", - ldap_err2string( rc ) ); - goto clean_up_and_return; - } - - /* Initialize the attribute. */ - if ( pthread_attr_init( &attr ) != 0 ) { - perror( "pthread_attr_init" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++inited_attr; - - /* Specify that the threads are joinable. */ - pthread_attr_setdetachstate( &attr, PTHREAD_CREATE_JOINABLE ); - - /* Create all the requested threads */ - thread_count = 0; - if ( domodify ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - modify_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create modify_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - if ( doadd ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - add_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create add_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - if ( dodelete ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - delete_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create delete_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - if ( dobind ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - bind_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create bind_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - if ( docompare ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - compare_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create compare_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - if ( dosearch ) { - for ( i = 0; i < each_thread_count; ++i ) { - if ( pthread_create( &threadids[thread_count], &attr, - search_thread, get_id_str(thread_count) ) != 0 ) { - perror( "pthread_create search_thread" ); - rc = LDAP_LOCAL_ERROR; - goto clean_up_and_return; - } - ++thread_count; - } - } - - /* Wait until these threads exit. */ - for ( i = 0; i < thread_count; ++i ) { - pthread_join( threadids[i], &status ); - } - -clean_up_and_return: - if ( ld != NULL ) { - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - ldap_unbind( ld ); - } - if ( threadids != NULL ) { - free( threadids ); - } - if ( inited_attr ) { - pthread_attr_destroy( &attr ); - } - tsd_cleanup(); - - return( rc ); -} - - -static void * -modify_thread( char *id ) -{ - LDAPMessage *res; - LDAPMessage *e; - int i, modentry, num_entries, msgid, parse_rc, finished; - int rc, opcount; - LDAPMod mod; - LDAPMod *mods[2]; - char *vals[2]; - char *dn; - ldapmsgwrapper *list, *lmwp, *lastlmwp; - struct timeval zerotime; - void *voidrc = (void *)0; - - zerotime.tv_sec = zerotime.tv_usec = 0L; - - printf( "Starting modify_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - rc = ldap_search_ext( ld, BASE, SCOPE, "(objectclass=*)", - NULL, 0, NULL, NULL, NULL, LDAP_NO_LIMIT, &msgid ); - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: Modify thread: " - "ldap_search_ext: %s\n", id, ldap_err2string( rc ) ); - exit( 1 ); - } - list = lastlmwp = NULL; - finished = 0; - num_entries = 0; - while ( !finished ) { - rc = ldap_result( ld, msgid, LDAP_MSG_ONE, &zerotime, &res ); - switch ( rc ) { - case -1: - rc = ldap_get_lderrno( ld, NULL, NULL ); - fprintf( stderr, "ldap_result: %s\n", ldap_err2string( rc ) ); - exit( 1 ); - break; - case 0: - break; - /* Keep track of the number of entries found. */ - case LDAP_RES_SEARCH_ENTRY: - num_entries++; - if (( lmwp = (ldapmsgwrapper *) - malloc( sizeof( ldapmsgwrapper ))) == NULL ) { - fprintf( stderr, "Thread %s: Modify thread: Cannot malloc\n", id ); - exit( 1 ); - } - lmwp->lmw_messagep = res; - lmwp->lmw_next = NULL; - if ( lastlmwp == NULL ) { - list = lastlmwp = lmwp; - } else { - lastlmwp->lmw_next = lmwp; - } - lastlmwp = lmwp; - break; - case LDAP_RES_SEARCH_REFERENCE: - break; - case LDAP_RES_SEARCH_RESULT: - finished = 1; - parse_rc = ldap_parse_result( ld, res, &rc, NULL, NULL, NULL, NULL, 1 ); - if ( parse_rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: can't parse result code.\n", id ); - exit( 1 ); - } else { - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: ldap_search: %s\n", id, ldap_err2string( rc ) ); - } else { - printf( "Thread %s: Got %d results.\n", id, num_entries ); - } - } - break; - default: - break; - } - } - - mods[0] = &mod; - mods[1] = NULL; - vals[0] = "bar"; - vals[1] = NULL; - - for ( ;; ) { - modentry = random() % num_entries; - for ( i = 0, lmwp = list; lmwp != NULL && i < modentry; - i++, lmwp = lmwp->lmw_next ) { - /* NULL */ - } - - if ( lmwp == NULL ) { - fprintf( stderr, - "Thread %s: Modify thread could not find entry %d of %d\n", - id, modentry, num_entries ); - continue; - } - - e = lmwp->lmw_messagep; - printf( "Thread %s: Modify thread picked entry %d of %d\n", id, i, num_entries ); - dn = ldap_get_dn( ld, e ); - - mod.mod_op = LDAP_MOD_REPLACE; - mod.mod_type = "description"; - mod.mod_values = vals; - printf( "Thread %s: Modifying (%s)\n", id, dn ); - - rc = ldap_modify_ext_s( ld, dn, mods, NULL, NULL ); - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "ldap_modify_ext_s: %s\n", - ldap_err2string( rc ) ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_modify_ext_s" ); - voidrc = (void *)1; - goto modify_cleanup_and_return; - } - } - free( dn ); - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -modify_cleanup_and_return: - printf( "Thread %s: attempted %d modify operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -add_thread( char *id ) -{ - LDAPMod mod[4]; - LDAPMod *mods[5]; - char dn[BUFSIZ], name[40]; - char *cnvals[2], *snvals[2], *pwdvals[2], *ocvals[3]; - int i, rc, opcount; - void *voidrc = (void *)0; - - printf( "Starting add_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - for ( i = 0; i < 4; i++ ) { - mods[i] = &mod[i]; - } - - mods[4] = NULL; - - mod[0].mod_op = 0; - mod[0].mod_type = "cn"; - mod[0].mod_values = cnvals; - cnvals[1] = NULL; - mod[1].mod_op = 0; - mod[1].mod_type = "sn"; - mod[1].mod_values = snvals; - snvals[1] = NULL; - mod[2].mod_op = 0; - mod[2].mod_type = "objectclass"; - mod[2].mod_values = ocvals; - ocvals[0] = "top"; - ocvals[1] = "person"; - ocvals[2] = NULL; - mod[3].mod_op = 0; - mod[3].mod_type = "userPassword"; - mod[3].mod_values = pwdvals; - pwdvals[1] = NULL; - mods[4] = NULL; - - for ( ;; ) { - sprintf( name, "%d", get_random_id() ); - sprintf( dn, "cn=%s, " BASE, name ); - cnvals[0] = name; - snvals[0] = name; - pwdvals[0] = name; - - printf( "Thread %s: Adding entry (%s)\n", id, dn ); - rc = ldap_add_ext_s( ld, dn, mods, NULL, NULL ); - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "ldap_add_ext_s: %s\n", - ldap_err2string( rc ) ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_add_ext_s" ); - voidrc = (void *)1; - goto add_cleanup_and_return; - } - } - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -add_cleanup_and_return: - printf( "Thread %s: attempted %d add operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -delete_thread( char *id ) -{ - LDAPMessage *res; - char dn[BUFSIZ], name[40]; - int num_entries, msgid, rc, parse_rc, finished, opcount; - struct timeval zerotime; - void *voidrc = (void *)0; - - zerotime.tv_sec = zerotime.tv_usec = 0L; - - printf( "Starting delete_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - rc = ldap_search_ext( ld, BASE, SCOPE, "(objectclass=*)", - NULL, 0, NULL, NULL, NULL, LDAP_NO_LIMIT, &msgid ); - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: Delete thread: " - "ldap_search_ext: %s\n", id, ldap_err2string( rc ) ); - exit( 1 ); - } - - finished = 0; - num_entries = 0; - while ( !finished ) { - rc = ldap_result( ld, msgid, LDAP_MSG_ONE, &zerotime, &res ); - switch ( rc ) { - case -1: - rc = ldap_get_lderrno( ld, NULL, NULL ); - fprintf( stderr, "ldap_result: %s\n", ldap_err2string( rc ) ); - exit( 1 ); - break; - case 0: - break; - /* Keep track of the number of entries found. */ - case LDAP_RES_SEARCH_ENTRY: - num_entries++; - break; - case LDAP_RES_SEARCH_REFERENCE: - break; - case LDAP_RES_SEARCH_RESULT: - finished = 1; - parse_rc = ldap_parse_result( ld, res, &rc, NULL, NULL, NULL, NULL, 1 ); - if ( parse_rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: can't parse result code.\n", id ); - exit( 1 ); - } else { - if ( rc != LDAP_SUCCESS ) { - fprintf( stderr, "Thread %s error: ldap_search: %s\n", id, ldap_err2string( rc ) ); - } else { - printf( "Thread %s: Got %d results.\n", id, num_entries ); - } - } - break; - default: - break; - } - } - - for ( ;; ) { - sprintf( name, "%d", get_random_id() ); - sprintf( dn, "cn=%s, " BASE, name ); - printf( "Thread %s: Deleting entry (%s)\n", id, dn ); - - if (( rc = ldap_delete_ext_s( ld, dn, NULL, NULL )) - != LDAP_SUCCESS ) { - ldap_perror( ld, "ldap_delete_ext_s" ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_delete_ext_s" ); - voidrc = (void *)1; - goto delete_cleanup_and_return; - } - } - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -delete_cleanup_and_return: - printf( "Thread %s: attempted %d delete operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -bind_thread( char *id ) -{ - char dn[BUFSIZ], name[40]; - int rc, opcount; - void *voidrc = (void *)0; - - printf( "Starting bind_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - for ( ;; ) { - sprintf( name, "%d", get_random_id() ); - sprintf( dn, "cn=%s, " BASE, name ); - printf( "Thread %s: Binding as entry (%s)\n", id, dn ); - - if (( rc = ldap_simple_bind_s( ld, dn, name )) - != LDAP_SUCCESS ) { - ldap_perror( ld, "ldap_simple_bind_s" ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_simple_bind_s" ); - voidrc = (void *)1; - goto bind_cleanup_and_return; - } - } else { - printf( "Thread %s: bound as entry (%s)\n", id, dn ); - } - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -bind_cleanup_and_return: - printf( "Thread %s: attempted %d bind operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -compare_thread( char *id ) -{ - char dn[BUFSIZ], name[40], cmpval[40]; - int rc, randval, opcount; - struct berval bv; - void *voidrc = (void *)0; - - printf( "Starting compare_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - for ( ;; ) { - randval = get_random_id(); - sprintf( name, "%d", randval ); - sprintf( dn, "cn=%s, " BASE, name ); - sprintf( cmpval, "%d", randval + random() % 3 ); - bv.bv_val = cmpval; - bv.bv_len = strlen( cmpval ); - - printf( "Thread %s: Comparing cn in entry (%s) with %s\n", - id, dn, cmpval ); - - rc = ldap_compare_ext_s( ld, dn, "cn", &bv, NULL, NULL ); - switch ( rc ) { - case LDAP_COMPARE_TRUE: - printf( "Thread %s: entry (%s) contains cn %s\n", - id, dn, cmpval ); - break; - case LDAP_COMPARE_FALSE: - printf( "Thread %s: entry (%s) doesn't contain cn %s\n", - id, dn, cmpval ); - break; - default: - ldap_perror( ld, "ldap_compare_ext_s" ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_compare_ext_s" ); - voidrc = (void *)1; - goto compare_cleanup_and_return; - } - } - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -compare_cleanup_and_return: - printf( "Thread %s: attempted %d compare operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -search_thread( char *id ) -{ - LDAPMessage *res, *entry; - char *dn, filter[40]; - int rc, opcount; - void *voidrc = (void *)0; - - printf( "Starting search_thread %s.\n", id ); - opcount = 0; - tsd_setup(); - - for ( ;; ) { - if ( range_filters ) { - switch( get_random_id() % 3 ) { - case 0: - sprintf( filter, "(cn>=%d)", get_random_id()); - break; - case 1: - sprintf( filter, "(cn<=%d)", get_random_id()); - break; - case 2: - sprintf( filter, "(&(cn>=%d)(cn<=%d))", - get_random_id(), get_random_id() ); - break; - } - } else { - sprintf( filter, "cn=%d", get_random_id() ); - } - - printf( "Thread %s: Searching for entry (%s)\n", id, filter ); - - res = NULL; - if (( rc = ldap_search_ext_s( ld, BASE, SCOPE, filter, NULL, 0, - NULL, NULL, NULL, 0, &res )) != LDAP_SUCCESS ) { - ldap_perror( ld, "ldap_search_ext_s" ); - if ( rc == LDAP_SERVER_DOWN ) { - perror( "ldap_search_ext_s" ); - voidrc = (void *)1; - goto search_cleanup_and_return; - } - } - if ( res != NULL ) { - entry = ldap_first_entry( ld, res ); - if ( entry == NULL ) { - printf( "Thread %s: found no entries\n", id ); - } else { - dn = ldap_get_dn( ld, entry ); - printf( - "Thread %s: found entry (%s); %d total\n", - id, dn == NULL ? "(Null)" : dn, - ldap_count_entries( ld, res )); - ldap_memfree( dn ); - } - ldap_msgfree( res ); - } - - ++opcount; - if ( maxops != 0 && opcount >= maxops ) { - break; - } - } - -search_cleanup_and_return: - printf( "Thread %s: attempted %d search operations\n", id, opcount ); - set_ld_error( 0, NULL, NULL, NULL ); /* disposes of memory */ - tsd_cleanup(); - free( id ); - return voidrc; -} - - -static void * -my_mutex_alloc( void ) -{ - pthread_mutex_t *mutexp; - - if ( (mutexp = malloc( sizeof(pthread_mutex_t) )) != NULL ) { - pthread_mutex_init( mutexp, NULL ); - } - return( mutexp ); -} - - -void * -my_sema_alloc( void ) -{ - sema_t *semptr; - - if( (semptr = malloc( sizeof(sema_t) ) ) != NULL ) { - sema_init( semptr, 0, USYNC_THREAD, NULL ); - } - return ( semptr ); -} - - -static void -my_mutex_free( void *mutexp ) -{ - pthread_mutex_destroy( (pthread_mutex_t *) mutexp ); - free( mutexp ); -} - - -void -my_sema_free( void *semptr ) -{ - sema_destroy( (sema_t *) semptr ); - free( semptr ); -} - - -int -my_sema_wait( void *semptr ) -{ - if( semptr != NULL ) - return( sema_wait( (sema_t *) semptr ) ); - else - return( -1 ); -} - - -int -my_sema_post( void *semptr ) -{ - if( semptr != NULL ) - return( sema_post( (sema_t *) semptr ) ); - else - return( -1 ); -} - - -struct ldap_error { - int le_errno; - char *le_matched; - char *le_errmsg; -}; - - -static void -tsd_setup() -{ - void *tsd; - tsd = pthread_getspecific( key ); - if ( tsd != NULL ) { - fprintf( stderr, "tsd non-null!\n" ); - pthread_exit( NULL ); - } - - tsd = (void *) calloc( 1, sizeof(struct ldap_error) ); - pthread_setspecific( key, tsd ); -} - - -static void -tsd_cleanup() -{ - void *tsd; - - if (( tsd = pthread_getspecific( key )) != NULL ) { - pthread_setspecific( key, NULL ); - free( tsd ); - } -} - - -static void -set_ld_error( int err, char *matched, char *errmsg, void *dummy ) -{ - struct ldap_error *le; - - le = pthread_getspecific( key ); - - le->le_errno = err; - - if ( le->le_matched != NULL ) { - ldap_memfree( le->le_matched ); - } - le->le_matched = matched; - - if ( le->le_errmsg != NULL ) { - ldap_memfree( le->le_errmsg ); - } - le->le_errmsg = errmsg; -} - - -static int -get_ld_error( char **matchedp, char **errmsgp, void *dummy ) -{ - struct ldap_error *le; - - le = pthread_getspecific( key ); - if ( matchedp != NULL ) { - *matchedp = le->le_matched; - } - if ( errmsgp != NULL ) { - *errmsgp = le->le_errmsg; - } - return( le->le_errno ); -} - - -static void -set_errno( int err ) -{ - errno = err; -} - - -static int -get_errno( void ) -{ - return( errno ); -} - - -static int -get_random_id() -{ - return( random() % maxid ); -} - - -static char * -get_id_str( int id ) -{ - char idstr[ 10 ]; - - sprintf( idstr, "%d", id ); - return( strdup( idstr )); -} |