diff options
55 files changed, 1281 insertions, 294 deletions
diff --git a/ldap/servers/plugins/chainingdb/cb_conn_stateless.c b/ldap/servers/plugins/chainingdb/cb_conn_stateless.c index a7df413b..adc87ff0 100644 --- a/ldap/servers/plugins/chainingdb/cb_conn_stateless.c +++ b/ldap/servers/plugins/chainingdb/cb_conn_stateless.c @@ -386,7 +386,7 @@ int cb_get_connection(cb_conn_pool * pool, LDAP ** lld, cb_outgoing_conn ** cc,s rc=ldap_get_lderrno( ld, NULL, NULL ); prerr=PR_GetError(); } - if ( ret == 0 ) free(plain); /* free plain only if it has been duplicated */ + if ( ret == 0 ) slapi_ch_free_string(&plain); /* free plain only if it has been duplicated */ if ( rc != LDAP_SUCCESS ) { if (cb_debug_on()) { diff --git a/ldap/servers/plugins/dna/dna.c b/ldap/servers/plugins/dna/dna.c index 24184914..e96d090e 100644 --- a/ldap/servers/plugins/dna/dna.c +++ b/ldap/servers/plugins/dna/dna.c @@ -680,7 +680,7 @@ dna_parse_config_entry(Slapi_Entry * e, int apply) value = slapi_entry_get_ndn(e); if (value) { - entry->dn = strdup(value); + entry->dn = slapi_ch_strdup(value); } slapi_log_error(SLAPI_LOG_CONFIG, DNA_PLUGIN_SUBSYSTEM, diff --git a/ldap/servers/plugins/pam_passthru/pam_ptimpl.c b/ldap/servers/plugins/pam_passthru/pam_ptimpl.c index 93aa9207..62f51ecd 100644 --- a/ldap/servers/plugins/pam_passthru/pam_ptimpl.c +++ b/ldap/servers/plugins/pam_passthru/pam_ptimpl.c @@ -77,7 +77,7 @@ static void delete_my_str_buf(MyStrBuf *buf) { if (buf->str != buf->fixbuf) { - slapi_ch_free_string(&buf->str); + slapi_ch_free_string(&(buf->str)); } } @@ -152,7 +152,7 @@ report_pam_error(char *str, int rc, pam_handle_t *pam_handle) /* returns a berval value as a null terminated string */ static char *strdupbv(struct berval *bv) { - char *str = malloc(bv->bv_len+1); + char *str = slapi_ch_malloc(bv->bv_len+1); memcpy(str, bv->bv_val, bv->bv_len); str[bv->bv_len] = 0; return str; @@ -164,10 +164,10 @@ free_pam_response(int nresp, struct pam_response *resp) int ii; for (ii = 0; ii < nresp; ++ii) { if (resp[ii].resp) { - free(resp[ii].resp); + slapi_ch_free((void **)&(resp[ii].resp)); } } - free(resp); + slapi_ch_free((void **)&resp); } /* @@ -190,7 +190,7 @@ pam_conv_func(int num_msg, const struct pam_message **msg, struct pam_response * } /* empty reply structure */ - reply = (struct pam_response *)calloc(num_msg, + reply = (struct pam_response *)slapi_ch_calloc(num_msg, sizeof(struct pam_response)); slapi_pblock_get( my_data->pb, SLAPI_BIND_CREDENTIALS, &creds ); /* the password */ for (ii = 0; ii < num_msg; ++ii) { @@ -206,7 +206,7 @@ pam_conv_func(int num_msg, const struct pam_message **msg, struct pam_response * reply[ii].resp = strdupbv(creds); #endif } else if (msg[ii]->msg_style == PAM_PROMPT_ECHO_ON) { /* assume username */ - reply[ii].resp = strdup(my_data->pam_identity); + reply[ii].resp = slapi_ch_strdup(my_data->pam_identity); } else if (msg[ii]->msg_style == PAM_ERROR_MSG) { slapi_log_error(SLAPI_LOG_FATAL, PAM_PASSTHRU_PLUGIN_SUBSYSTEM, "pam msg [%d] error [%s]\n", ii, msg[ii]->msg); diff --git a/ldap/servers/plugins/referint/referint.c b/ldap/servers/plugins/referint/referint.c index 286169c6..eee69957 100644 --- a/ldap/servers/plugins/referint/referint.c +++ b/ldap/servers/plugins/referint/referint.c @@ -444,13 +444,11 @@ int update_integrity(char **argv, char *origDN, char *newrDN, int logChanges){ if(dnParts != NULL){ for(x=0; dnParts[x] != NULL; x++) { - free(dnParts[x]); + slapi_ch_free_string(&dnParts[x]); } - free(dnParts); - } - if(newDN != NULL){ - slapi_ch_free((void**)&newDN); + slapi_ch_free((void **)&dnParts); } + slapi_ch_free_string(&newDN); } @@ -485,15 +483,12 @@ int update_integrity(char **argv, char *origDN, char *newrDN, int logChanges){ free_and_return: /* free filter and search_results_pb */ - if(filter != NULL) - { - free(filter); - } + slapi_ch_free_string(&filter); if(search_result_pb != NULL) { slapi_free_search_results_internal(search_result_pb); - free(search_result_pb); + slapi_pblock_destroy(search_result_pb); } return(rc); diff --git a/ldap/servers/plugins/replication/cl5_api.c b/ldap/servers/plugins/replication/cl5_api.c index d81e2a09..fda8f8af 100644 --- a/ldap/servers/plugins/replication/cl5_api.c +++ b/ldap/servers/plugins/replication/cl5_api.c @@ -1008,7 +1008,7 @@ int cl5Backup (const char *bkDir, Object **replicas) } /* copy db log files */ - rc = LOG_ARCHIVE(s_cl5Desc.dbEnv, &list, DB_ARCH_LOG, malloc); + rc = LOG_ARCHIVE(s_cl5Desc.dbEnv, &list, DB_ARCH_LOG, (void *)slapi_ch_malloc); if (rc != 0) { slapi_log_error(SLAPI_LOG_FATAL, repl_plugin_name_cl, @@ -1037,7 +1037,7 @@ int cl5Backup (const char *bkDir, Object **replicas) logFile ++; } - free(list); + slapi_ch_free((void **)&list); } /* now, copy the version file */ @@ -2535,7 +2535,7 @@ static int _cl5Entry2DBData (const CL5Entry *entry, char **data, PRUint32 *len) } /* allocate data buffer */ - (*data) = (char *) slapi_ch_malloc (size); + (*data) = slapi_ch_malloc (size); if ((*data) == NULL) { slapi_log_error(SLAPI_LOG_FATAL, repl_plugin_name_cl, @@ -3029,7 +3029,7 @@ static void _cl5ReadBerval (struct berval *bv, char** buff) bv->bv_len = length; if (bv->bv_len > 0) { - bv->bv_val = (char*)slapi_ch_malloc (bv->bv_len); + bv->bv_val = slapi_ch_malloc (bv->bv_len); memcpy (bv->bv_val, *buff, bv->bv_len); *buff += bv->bv_len; } @@ -3216,7 +3216,7 @@ static int _cl5CheckpointMain (void *param) char filename[MAXPATHLEN + 1]; /* find out which log files don't contain active txns */ - rc = LOG_ARCHIVE(s_cl5Desc.dbEnv, &list, 0, malloc); + rc = LOG_ARCHIVE(s_cl5Desc.dbEnv, &list, 0, (void *)slapi_ch_malloc); if (0 == rc && NULL != list) { /* zap 'em ! */ @@ -3982,6 +3982,16 @@ static void _cl5SetDBConfig (const CL5DBConfig *config) s_cl5Desc.dbConfig.fileMode = FILE_CREATE_MODE; } +/* + * a wrapper for slapi_ch_free; it's declared to set slapi_ch_free in BDB + * dbEnv->set_alloc(dbEnv, (void *)slapi_ch_malloc, (void *)slapi_ch_realloc, _cl5_api_free); + * + */ +void _cl5_api_free(void *ptr) +{ + slapi_ch_free(&ptr); +} + #define ONEG 1073741824 /* one giga bytes */ static void _cl5InitDBEnv(DB_ENV *dbEnv) { @@ -4011,7 +4021,7 @@ static void _cl5InitDBEnv(DB_ENV *dbEnv) dbEnv->set_errcall(dbEnv, _cl5DBLogPrint); } #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR >= 3300 - dbEnv->set_alloc(dbEnv, malloc, realloc, free); + dbEnv->set_alloc(dbEnv, (void *)slapi_ch_malloc, (void *)slapi_ch_realloc, _cl5_api_free); #endif } @@ -4393,7 +4403,7 @@ static int _cl5ReadRUV (const char *replGen, Object *obj, PRBool purge) { case 0: pos = data.data; rc = _cl5ReadBervals (&vals, &pos, data.size); - free (data.data); + slapi_ch_free (&(data.data)); if (rc != CL5_SUCCESS) return rc; @@ -4473,7 +4483,7 @@ static int _cl5WriteRUV (CL5DBFile *file, PRBool purge) #endif rc = file->db->put(file->db, txnid, &key, &data, DEFAULT_DB_OP_FLAGS); - slapi_ch_free ((void**)&data.data); + slapi_ch_free (&(data.data)); if ( rc == 0 ) { #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR < 4100 @@ -4748,7 +4758,7 @@ static int _cl5GetEntryCount (CL5DBFile *file) switch (rc) { case 0: file->entryCount = *(int*)data.data; - free (data.data); + slapi_ch_free (&(data.data)); /* delete the entry. the entry is re-added when file is successfully closed */ @@ -4765,7 +4775,7 @@ static int _cl5GetEntryCount (CL5DBFile *file) #elif 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR >= 3300 rc = file->db->stat(file->db, (void*)&stats, 0); #else - rc = file->db->stat(file->db, (void*)&stats, malloc, 0); + rc = file->db->stat(file->db, (void*)&stats, (void *)slapi_ch_malloc, 0); #endif if (rc != 0) { @@ -4784,7 +4794,7 @@ static int _cl5GetEntryCount (CL5DBFile *file) "_cl5GetEntryCount: %d changes for replica %s\n", file->entryCount, file->replName); - free (stats); + slapi_ch_free ((void **)&stats); return CL5_SUCCESS; default: slapi_log_error(SLAPI_LOG_FATAL, repl_plugin_name_cl, @@ -4950,7 +4960,7 @@ static int _cl5Operation2LDIF (const slapi_operation_parameters *op, const char } /* allocate buffer */ - buff = (char*)slapi_ch_malloc (len); + buff = slapi_ch_malloc (len); start = buff; if (buff == NULL) { @@ -5315,7 +5325,7 @@ static int _cl5WriteOperation(const char *replName, const char *replGen, rc = CL5_SUCCESS; done: if (data->data) - slapi_ch_free ((void**)&data->data); + slapi_ch_free (&(data->data)); slapi_ch_free((void**) &data); if (file_obj) @@ -5353,15 +5363,15 @@ static int _cl5GetFirstEntry (Object *obj, CL5Entry *entry, void **iterator, DB_ /* skip service entries */ if (cl5HelperEntry ((char*)key.data, NULL)) { - free (key.data); - free (data.data); + slapi_ch_free (&(key.data)); + slapi_ch_free (&(data.data)); continue; } /* format entry */ - free (key.data); + slapi_ch_free (&(key.data)); rc = cl5DBData2Entry (data.data, data.size, entry); - free (data.data); + slapi_ch_free (&(data.data)); if (rc != 0) { slapi_log_error(SLAPI_LOG_REPL, repl_plugin_name_cl, @@ -5397,8 +5407,8 @@ static int _cl5GetFirstEntry (Object *obj, CL5Entry *entry, void **iterator, DB_ /* successfully retrieved next entry but it was out of range */ if (rc == CL5_SUCCESS) { - free (key.data); - free (data.data); + slapi_ch_free (&(key.data)); + slapi_ch_free (&(data.data)); rc = CL5_NOTFOUND; goto done; } @@ -5429,15 +5439,15 @@ static int _cl5GetNextEntry (CL5Entry *entry, void *iterator) { if (cl5HelperEntry ((char*)key.data, NULL)) { - free (key.data); - free (data.data); + slapi_ch_free (&(key.data)); + slapi_ch_free (&(data.data)); continue; } - free (key.data); + slapi_ch_free (&(key.data)); /* format entry */ rc = cl5DBData2Entry (data.data, data.size, entry); - free (data.data); + slapi_ch_free (&(data.data)); if (rc != 0) { slapi_log_error(SLAPI_LOG_REPL, repl_plugin_name_cl, @@ -5558,8 +5568,7 @@ done:; if (obj) object_release (obj); - if (data.data) - free (data.data); + slapi_ch_free (&(data.data)); return rc; } @@ -6341,7 +6350,7 @@ static int _cl5NewDBFile (const char *replName, const char *replGen, CL5DBFile** } #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR < 3300 - rc = db->set_malloc(db, malloc); + rc = db->set_malloc(db, (void *)slapi_ch_malloc); if (0 != rc) { goto out; } diff --git a/ldap/servers/plugins/replication/repl5_agmt.c b/ldap/servers/plugins/replication/repl5_agmt.c index 60d3565b..a6314498 100644 --- a/ldap/servers/plugins/replication/repl5_agmt.c +++ b/ldap/servers/plugins/replication/repl5_agmt.c @@ -977,12 +977,12 @@ agmt_set_binddn_from_entry(Repl_Agmt *ra, const Slapi_Entry *e) if (NULL != sval) { const char *val = slapi_value_get_string(sval); - ra->binddn = strdup(val); + ra->binddn = slapi_ch_strdup(val); } } /* If no BindDN set, set to zero-length string */ if (ra->binddn == NULL) { - ra->binddn = strdup(""); + ra->binddn = slapi_ch_strdup(""); } PR_Unlock(ra->lock); prot_notify_agmt_changed(ra->protocol, ra->long_name); diff --git a/ldap/servers/plugins/replication/repl_controls.c b/ldap/servers/plugins/replication/repl_controls.c index 066c6c59..cfd980fd 100644 --- a/ldap/servers/plugins/replication/repl_controls.c +++ b/ldap/servers/plugins/replication/repl_controls.c @@ -254,7 +254,7 @@ decode_NSDS50ReplUpdateInfoControl(LDAPControl **controlsp, goto loser; } slapi_mods_add_modbvps(&modrdn_smods, op, type, embvals); - free( type ); + slapi_ch_free_string( &type ); ber_bvecfree( embvals ); } got_modrdn_mods = PR_TRUE; @@ -364,7 +364,7 @@ add_repl_control_mods( Slapi_PBlock *pb, Slapi_Mods *smods ) to end up in the entry. We need to remove the old ones. */ } - free( type ); + slapi_ch_free_string( &type ); ber_bvecfree( embvals ); } } diff --git a/ldap/servers/plugins/replication/repl_objset.c b/ldap/servers/plugins/replication/repl_objset.c index 300cfee0..48c36418 100644 --- a/ldap/servers/plugins/replication/repl_objset.c +++ b/ldap/servers/plugins/replication/repl_objset.c @@ -95,7 +95,7 @@ repl_objset_new(FNFree destructor) p->lock = PR_NewLock(); if (NULL == p->lock) { - free(p); p = NULL; + slapi_ch_free((void **)&p); } p->objects = llistNew(); p->destructor = destructor; @@ -196,7 +196,7 @@ repl_objset_destroy(Repl_Objset **o, time_t maxwait, FNFree panic_fn) /* Free the linked list */ llistDestroy(&(*o)->objects, (*o)->destructor); PR_DestroyLock((*o)->lock); - free(*o); *o = NULL; + slapi_ch_free((void **)o); } } @@ -270,9 +270,9 @@ removeObjectNolock(Repl_Objset *o, Repl_Objset_object *co) llistRemove(o->objects, co->key); /* Destroy the object */ o->destructor(&(co->data)); - free(co->key); + slapi_ch_free((void **)&(co->key)); /* Deallocate the container */ - free(co); + slapi_ch_free((void **)&co); } static Repl_Objset_object * @@ -287,9 +287,9 @@ removeCurrentObjectAndGetNextNolock (Repl_Objset *o, Repl_Objset_object *co, voi ro = llistRemoveCurrentAndGetNext (o->objects, &iterator); o->destructor(&(co->data)); - free(co->key); + slapi_ch_free((void **)&(co->key)); /* Deallocate the container */ - free(co); + slapi_ch_free((void **)&co); return ro; } diff --git a/ldap/servers/plugins/replication/replutil.c b/ldap/servers/plugins/replication/replutil.c index 5b292f52..8b457a11 100644 --- a/ldap/servers/plugins/replication/replutil.c +++ b/ldap/servers/plugins/replication/replutil.c @@ -170,7 +170,7 @@ entry_print( Slapi_Entry *e ) } puts( p ); fflush( stdout ); - free( p ); + slapi_ch_free_string( &p ); return; } @@ -198,8 +198,8 @@ int copyfile(char* source, char * destination, int overwrite, int mode) int return_value = -1; int bytes_to_write = 0; - /* malloc the buffer */ - buffer = (char*) malloc(64*1024); + /* allocate the buffer */ + buffer = slapi_ch_malloc(64*1024); if (NULL == buffer) { slapi_log_error(SLAPI_LOG_FATAL, repl_plugin_name, "copy file: memory allocation failed\n"); @@ -250,10 +250,7 @@ error: { close(dest_fd); } - if (NULL != buffer) - { - free(buffer); - } + slapi_ch_free_string(&buffer); return return_value; #endif } @@ -263,7 +260,7 @@ time_t age_str2time (const char *age) { char *maxage; - char unit; + char unit; time_t ageval; if (age == NULL || age[0] == '\0' || strcmp (age, "0") == 0) @@ -272,14 +269,11 @@ age_str2time (const char *age) } maxage = slapi_ch_strdup ( age ); - unit = maxage[ strlen( maxage ) - 1 ]; - maxage[ strlen( maxage ) - 1 ] = '\0'; - ageval = strntoul( maxage, strlen( maxage ), 10 ); - if ( maxage) - { - slapi_ch_free ( (void **) &maxage ); - } - switch ( unit ) + unit = maxage[ strlen( maxage ) - 1 ]; + maxage[ strlen( maxage ) - 1 ] = '\0'; + ageval = strntoul( maxage, strlen( maxage ), 10 ); + slapi_ch_free_string(&maxage); + switch ( unit ) { case 's': break; @@ -297,10 +291,10 @@ age_str2time (const char *age) break; default: slapi_log_error( SLAPI_LOG_PLUGIN, repl_plugin_name, - "age_str2time: unknown unit \"%c\" " + "age_str2time: unknown unit \"%c\" " "for maxiumum changelog age\n", unit ); ageval = -1; - } + } return ageval; } @@ -394,7 +388,7 @@ make_changes_string(LDAPMod **ldm, char **includeattrs) addlenstr( l, buf ); - free( buf ); + slapi_ch_free_string( &buf ); } addlenstr( l, "-\n" ); } @@ -635,7 +629,7 @@ LDAPControl* create_backend_control (Slapi_DN *sdn) control = (LDAPControl*)slapi_ch_malloc (sizeof (LDAPControl)); control->ldctl_oid = slapi_ch_strdup ("2.16.840.1.113730.3.4.14"); - control->ldctl_value.bv_val = strdup(be_name); + control->ldctl_value.bv_val = slapi_ch_strdup(be_name); control->ldctl_value.bv_len = strlen (be_name); control->ldctl_iscritical = 1; } diff --git a/ldap/servers/plugins/replication/urp.c b/ldap/servers/plugins/replication/urp.c index 9f03851c..d1d55c4d 100644 --- a/ldap/servers/plugins/replication/urp.c +++ b/ldap/servers/plugins/replication/urp.c @@ -343,7 +343,7 @@ urp_modrdn_operation( Slapi_PBlock *pb ) * Remember to turn this entry back to tombstone in post op. * We'll just borrow an obsolete pblock type here. */ - slapi_pblock_set (pb, SLAPI_URP_TOMBSTONE_UNIQUEID, strdup(op_uniqueid)); + slapi_pblock_set (pb, SLAPI_URP_TOMBSTONE_UNIQUEID, slapi_ch_strdup(op_uniqueid)); rc= slapi_setbit_int(rc,SLAPI_RTN_BIT_FETCH_TARGET_ENTRY); rc = 0; } diff --git a/ldap/servers/plugins/retrocl/retrocl_po.c b/ldap/servers/plugins/retrocl/retrocl_po.c index a069fd9f..e368ad98 100644 --- a/ldap/servers/plugins/retrocl/retrocl_po.c +++ b/ldap/servers/plugins/retrocl/retrocl_po.c @@ -133,7 +133,7 @@ static lenstr *make_changes_string(LDAPMod **ldm, const char **includeattrs) addlenstr( l, buf ); - free( buf ); + slapi_ch_free_string( &buf ); } addlenstr( l, "-\n" ); } @@ -219,7 +219,7 @@ write_replog_db( val.bv_val = format_genTime (curtime); val.bv_len = strlen( val.bv_val ); slapi_entry_add_values( e, attr_changetime, vals ); - free( val.bv_val ); + slapi_ch_free( (void **)&val.bv_val ); /* * Finish constructing the entry. How to do it depends on the type @@ -329,7 +329,7 @@ entry2reple( Slapi_Entry *e, Slapi_Entry *oe ) val.bv_val = p; val.bv_len = len - ( p - estr ); /* length + terminating \0 */ slapi_entry_add_values( e, attr_changes, vals ); - free( estr ); + slapi_ch_free_string( &estr ); return 0; } diff --git a/ldap/servers/plugins/rever/des.c b/ldap/servers/plugins/rever/des.c index 0966951b..d45d6716 100644 --- a/ldap/servers/plugins/rever/des.c +++ b/ldap/servers/plugins/rever/des.c @@ -431,7 +431,8 @@ static SVRCOREError cryptPassword(struct pk11ContextStore *store, char * clear, } /* store->crypt will hold the crypted password - it must be >= clear length */ - store->crypt = (unsigned char *)slapi_ch_calloc(sizeof(unsigned char), + /* store->crypt is freed in NSS; let's not use slapi_ch_calloc */ + store->crypt = (unsigned char *)calloc(sizeof(unsigned char), store->length+1); if (!store->crypt) { diff --git a/ldap/servers/plugins/roles/roles_cache.c b/ldap/servers/plugins/roles/roles_cache.c index 4d3c4037..60bf3631 100644 --- a/ldap/servers/plugins/roles/roles_cache.c +++ b/ldap/servers/plugins/roles/roles_cache.c @@ -272,7 +272,7 @@ int roles_cache_init() { slapi_log_error( SLAPI_LOG_FATAL, ROLES_PLUGIN_SUBSYSTEM, "roles_cache_init: slapi_vattrspi_regattr failed\n"); - free(vattr_handle); + slapi_ch_free((void **)&vattr_handle); PR_DestroyRWLock(global_lock); global_lock = NULL; return(-1); diff --git a/ldap/servers/plugins/roles/roles_plugin.c b/ldap/servers/plugins/roles/roles_plugin.c index 96f92756..046df3d6 100644 --- a/ldap/servers/plugins/roles/roles_plugin.c +++ b/ldap/servers/plugins/roles/roles_plugin.c @@ -246,7 +246,7 @@ int roles_sp_get_value(vattr_sp_handle *handle, if (rc == 0) { *free_flags = SLAPI_VIRTUALATTRS_RETURNED_COPIES; - *actual_type_name = strdup(NSROLEATTR); + *actual_type_name = slapi_ch_strdup(NSROLEATTR); if (type_name_disposition) { diff --git a/ldap/servers/plugins/shared/utils.c b/ldap/servers/plugins/shared/utils.c index 1010e8c9..028b530c 100644 --- a/ldap/servers/plugins/shared/utils.c +++ b/ldap/servers/plugins/shared/utils.c @@ -441,10 +441,10 @@ static Slapi_Mutex *cache_lock = NULL; DNLink *cacheInit() { DNLink *root; slapi_lock_mutex(cache_lock); - root = (DNLink *)malloc( sizeof(DNLink) ); + root = (DNLink *)slapi_ch_malloc( sizeof(DNLink) ); root->next = NULL; root->data = NULL; - root->dn = (char *)malloc(1); + root->dn = (char *)slapi_ch_malloc(1); root->dn[0] = 0; slapi_unlock_mutex(cache_lock); return root; @@ -457,7 +457,7 @@ DNLink *cacheAdd( DNLink *root, char *dn, void *data ) { slapi_lock_mutex(cache_lock); for( ; root->next; root = root->next ) { } - root->next = (DNLink *)malloc( sizeof(DNLink) ); + root->next = (DNLink *)slapi_ch_malloc( sizeof(DNLink) ); root = root->next; root->dn = dn; root->data = data; diff --git a/ldap/servers/plugins/syntaxes/string.c b/ldap/servers/plugins/syntaxes/string.c index 6a1d3c99..3142491b 100644 --- a/ldap/servers/plugins/syntaxes/string.c +++ b/ldap/servers/plugins/syntaxes/string.c @@ -357,6 +357,11 @@ string_values2keys( Slapi_PBlock *pb, Slapi_Value **bvals, Slapi_Value **bvlp; char *w, *c, *p; + if (NULL == bvals) { + *ivals = NULL; + return 0; + } + switch ( ftype ) { case LDAP_FILTER_EQUALITY: /* allocate a new array for the normalized values */ diff --git a/ldap/servers/plugins/views/views.c b/ldap/servers/plugins/views/views.c index 3735440f..1d1f2e82 100644 --- a/ldap/servers/plugins/views/views.c +++ b/ldap/servers/plugins/views/views.c @@ -542,7 +542,7 @@ static int views_cache_index() theCache.view_count++; - theCache.ppViewIndex = (viewEntry**)calloc(theCache.view_count, sizeof(viewEntry*)); + theCache.ppViewIndex = (viewEntry**)slapi_ch_calloc(theCache.view_count, sizeof(viewEntry*)); if(theCache.ppViewIndex) { /* copy over the views */ @@ -687,7 +687,7 @@ static void views_cache_discover_children(viewEntry *pView) /* make the space for them */ pView->child_count = child_count; - pView->pChildren = calloc(child_count, sizeof(viewEntry*)); + pView->pChildren = (void **)slapi_ch_calloc(child_count, sizeof(viewEntry*)); /* add them */ for(current = head; current != NULL; current = current->list.pNext) @@ -1211,7 +1211,7 @@ static int views_dn_views_cb (Slapi_Entry* e, void *callback_data) { pDn = slapi_entry_get_ndn(e); /* create the view */ - pView = calloc(1, sizeof(viewEntry)); + pView = (viewEntry *)slapi_ch_calloc(1, sizeof(viewEntry)); pView->pDn = slapi_ch_strdup(pDn); if(!slapi_entry_first_attr(e, &dnAttr)) @@ -1517,7 +1517,7 @@ static void views_update_views_cache( Slapi_Entry *e, char *dn, int modtype, Sla */ if(modtype == LDAP_CHANGETYPE_ADD) { - theView = calloc(1, sizeof(viewEntry)); + theView = (viewEntry *)slapi_ch_calloc(1, sizeof(viewEntry)); theView->pDn = slapi_ch_strdup(pDn); /* get the view filter, the entryid, and the parentid */ diff --git a/ldap/servers/slapd/add.c b/ldap/servers/slapd/add.c index 0e5c87cb..bdd6998d 100644 --- a/ldap/servers/slapd/add.c +++ b/ldap/servers/slapd/add.c @@ -158,7 +158,7 @@ do_add( Slapi_PBlock *pb ) ber_bvecfree( vals ); goto free_and_return; } - free( type ); + slapi_ch_free_string(&type); /* for now we just ignore attributes that client is not allowed to modify so not to break existing clients */ diff --git a/ldap/servers/slapd/attrsyntax.c b/ldap/servers/slapd/attrsyntax.c index 3cda3277..a85ec63c 100644 --- a/ldap/servers/slapd/attrsyntax.c +++ b/ldap/servers/slapd/attrsyntax.c @@ -695,9 +695,7 @@ slapi_attr_type2plugin( const char *type, void **pi ) if ( NULL != *pi ) { rc = 0; } - if ( tmp != NULL ) { - free( tmp ); - } + slapi_ch_free_string(&tmp); return( rc ); } diff --git a/ldap/servers/slapd/ava.c b/ldap/servers/slapd/ava.c index 1905e4cb..e1ffff1a 100644 --- a/ldap/servers/slapd/ava.c +++ b/ldap/servers/slapd/ava.c @@ -62,13 +62,13 @@ get_ava( if ( ber_scanf( ber, "{ao}", &type, &ava->ava_value ) == LBER_ERROR ) { - slapi_ch_free_string(&type); + slapi_ch_free_string( &type ); ava_done(ava); LDAPDebug( LDAP_DEBUG_ANY, " get_ava ber_scanf\n", 0, 0, 0 ); return( LDAP_PROTOCOL_ERROR ); } ava->ava_type = slapi_attr_syntax_normalize(type); - free( type ); + slapi_ch_free_string( &type ); return( 0 ); } diff --git a/ldap/servers/slapd/back-ldbm/ancestorid.c b/ldap/servers/slapd/back-ldbm/ancestorid.c index 0ac082b9..fb830770 100644 --- a/ldap/servers/slapd/back-ldbm/ancestorid.c +++ b/ldap/servers/slapd/back-ldbm/ancestorid.c @@ -373,7 +373,7 @@ static int ldbm_parentid(backend *be, DB_TXN *txn, ID id, ID *ppid) out: /* Free the entry value */ - if (data.data != NULL) free(data.data); + slapi_ch_free(&(data.data)); /* Release the id2entry file */ if (db != NULL) { diff --git a/ldap/servers/slapd/back-ldbm/cache.c b/ldap/servers/slapd/back-ldbm/cache.c index 45c252b3..90fc8149 100644 --- a/ldap/servers/slapd/back-ldbm/cache.c +++ b/ldap/servers/slapd/back-ldbm/cache.c @@ -423,7 +423,7 @@ int cache_init(struct cache *cache, size_t maxsize, long maxentries) #define CACHE_FULL(cache) \ (((cache)->c_cursize > (cache)->c_maxsize) || \ (((cache)->c_maxentries > 0) && \ - ((cache)->c_curentries > cache->c_maxentries))) + ((cache)->c_curentries > (cache)->c_maxentries))) /* clear out the cache to make room for new entries diff --git a/ldap/servers/slapd/back-ldbm/dblayer.c b/ldap/servers/slapd/back-ldbm/dblayer.c index 18c504d2..a51abf40 100644 --- a/ldap/servers/slapd/back-ldbm/dblayer.c +++ b/ldap/servers/slapd/back-ldbm/dblayer.c @@ -772,6 +772,11 @@ cleanup: } #endif +void dblayer_free(void *ptr) +{ + slapi_ch_free(&ptr); +} + static void dblayer_init_dbenv(DB_ENV *pEnv, dblayer_private *priv) { size_t mysize; @@ -797,7 +802,7 @@ static void dblayer_init_dbenv(DB_ENV *pEnv, dblayer_private *priv) pEnv->set_tx_max(pEnv, priv->dblayer_tx_max); #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR >= 3300 - pEnv->set_alloc(pEnv, malloc, realloc, free); + pEnv->set_alloc(pEnv, (void *)slapi_ch_malloc, (void *)slapi_ch_realloc, dblayer_free); /* * The log region is used to store filenames and so needs to be @@ -2063,7 +2068,7 @@ int dblayer_instance_start(backend *be, int mode) } #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR < 3300 - return_value = dbp->set_malloc(dbp, malloc); + return_value = dbp->set_malloc(dbp, (void *)slapi_ch_malloc); if (0 != return_value) { LDAPDebug(LDAP_DEBUG_ANY, "dbp->set_malloc failed %d\n", @@ -2762,7 +2767,7 @@ int dblayer_open_file(backend *be, char* indexname, int open_flag, struct attrin goto out; #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR < 3300 - return_value = dbp->set_malloc(dbp, malloc); + return_value = dbp->set_malloc(dbp, (void *)slapi_ch_malloc); if (0 != return_value) { goto out; } @@ -3727,7 +3732,7 @@ static int checkpoint_threadmain(void *param) /* find out which log files don't contain active txns */ DB_CHECKPOINT_LOCK(PR_TRUE, penv->dblayer_env_lock); return_value = LOG_ARCHIVE(penv->dblayer_DB_ENV, &list, - 0, malloc); + 0, (void *)slapi_ch_malloc); DB_CHECKPOINT_UNLOCK(PR_TRUE, penv->dblayer_env_lock); checkpoint_debug_message(debug_checkpointing, "Got list of logfiles not needed %d %p\n", @@ -3990,7 +3995,7 @@ int dblayer_memp_stat(struct ldbminfo *li, DB_MPOOL_STAT **gsp, env = priv->dblayer_env->dblayer_DB_ENV; PR_ASSERT(NULL != env); - return MEMP_STAT(env, gsp, fsp, 0, malloc); + return MEMP_STAT(env, gsp, fsp, 0, (void *)slapi_ch_malloc); } /* import wants this one */ @@ -4011,7 +4016,7 @@ int dblayer_memp_stat_instance(ldbm_instance *inst, DB_MPOOL_STAT **gsp, } PR_ASSERT(NULL != env); - return MEMP_STAT(env, gsp, fsp, 0, malloc); + return MEMP_STAT(env, gsp, fsp, 0, (void *)slapi_ch_malloc); } /* Helper functions for recovery */ @@ -4954,7 +4959,7 @@ int dblayer_backup(struct ldbminfo *li, char *dest_dir, Slapi_Task *task) /* get the list of logfiles currently existing */ if (priv->dblayer_enable_transactions) { return_value = LOG_ARCHIVE(priv->dblayer_env->dblayer_DB_ENV, - &listA, DB_ARCH_LOG, malloc); + &listA, DB_ARCH_LOG, (void *)slapi_ch_malloc); if ((return_value != 0) || (listA == NULL)) { LDAPDebug(LDAP_DEBUG_ANY, "BAD: can't get list of logs\n", 0, 0, 0); @@ -4990,9 +4995,7 @@ int dblayer_backup(struct ldbminfo *li, char *dest_dir, Slapi_Task *task) slapi_task_log_notice(task, "ERROR: Instance dir is empty\n"); } - if (listA) { - free(listA); - } + slapi_ch_free((void **)&listA); dblayer_txn_abort(li,&txn); return -1; } @@ -5005,9 +5008,7 @@ int dblayer_backup(struct ldbminfo *li, char *dest_dir, Slapi_Task *task) "ERROR: error copying directory (%s -> %s): err=%d", inst_dirp, dest_dir, return_value); } - if (listA) { - free(listA); - } + slapi_ch_free((void **)&listA); dblayer_txn_abort(li,&txn); if (inst_dirp != inst_dir) slapi_ch_free_string(&inst_dirp); @@ -5019,11 +5020,11 @@ int dblayer_backup(struct ldbminfo *li, char *dest_dir, Slapi_Task *task) if (priv->dblayer_enable_transactions) { /* now, get the list of logfiles that still exist */ return_value = LOG_ARCHIVE(priv->dblayer_env->dblayer_DB_ENV, - &listB, DB_ARCH_LOG, malloc); + &listB, DB_ARCH_LOG, (void *)slapi_ch_malloc); if ((return_value != 0) || (listB == NULL)) { LDAPDebug(LDAP_DEBUG_ANY, "ERROR: can't get list of logs\n", 0, 0, 0); - free(listA); + slapi_ch_free((void **)&listA); dblayer_txn_abort(li,&txn); return return_value; } @@ -5107,14 +5108,8 @@ int dblayer_backup(struct ldbminfo *li, char *dest_dir, Slapi_Task *task) slapi_ch_free((void **)&pathname2); } - if (listA) { - free(listA); - listA = NULL; - } - if (listB) { - free(listB); - listB = NULL; - } + slapi_ch_free((void **)&listA); + slapi_ch_free((void **)&listB); } } while (!ok); diff --git a/ldap/servers/slapd/back-ldbm/dbtest.c b/ldap/servers/slapd/back-ldbm/dbtest.c index 222d0ff6..703c3611 100644 --- a/ldap/servers/slapd/back-ldbm/dbtest.c +++ b/ldap/servers/slapd/back-ldbm/dbtest.c @@ -260,8 +260,8 @@ dbtest_traverse( DB *db, char *filename, unsigned int options, FILE *outfp ) fprintf( outfp, "\tdata: %s\n", (char *)data.data ); } } - free( key.data ); - free( data.data ); + slapi_ch_free( &(key.data) ); + slapi_ch_free( &(data.data) ); } dbc->c_close(dbc); } diff --git a/ldap/servers/slapd/back-ldbm/id2entry.c b/ldap/servers/slapd/back-ldbm/id2entry.c index 3fa60282..e951e5e9 100644 --- a/ldap/servers/slapd/back-ldbm/id2entry.c +++ b/ldap/servers/slapd/back-ldbm/id2entry.c @@ -103,7 +103,7 @@ id2entry_add_ext( backend *be, struct backentry *e, back_txn *txn, int encrypt /* store it */ rc = db->put( db, db_txn, &key, &data, 0); /* DBDB looks like we're freeing memory allocated by another DLL, which is bad */ - free( data.dptr ); + slapi_ch_free( &(data.dptr) ); dblayer_release_id2entry( be, db ); @@ -210,19 +210,30 @@ id2entry( backend *be, ID id, back_txn *txn, int *err ) } do { *err = db->get( db, db_txn, &key, &data, 0 ); - if ( 0 != *err && - DB_NOTFOUND != *err && DB_LOCK_DEADLOCK != *err ) + if ( (0 != *err) && + (DB_NOTFOUND != *err) && (DB_LOCK_DEADLOCK != *err) ) { - LDAPDebug( LDAP_DEBUG_ANY, "id2entry error %d\n", - *err, 0, 0 ); + LDAPDebug( LDAP_DEBUG_ANY, + "id2entry: libdb returned error %d (%s)\n", + *err, dblayer_strerror( *err ), 0 ); } } - while ( DB_LOCK_DEADLOCK == *err && txn == NULL ); + while ( (DB_LOCK_DEADLOCK == *err) && (txn == NULL) ); - if ( 0 != *err && DB_NOTFOUND != *err && DB_LOCK_DEADLOCK != *err ) + if ( (0 != *err) && (DB_NOTFOUND != *err) && (DB_LOCK_DEADLOCK != *err) ) { - LDAPDebug( LDAP_DEBUG_ANY, "id2entry get error %d\n", - *err, 0, 0 ); + if ( (ENOMEM == *err) && (data.dptr == NULL) ) + { + /* + * Now we are setting slapi_ch_malloc and its friends to libdb + * by ENV->set_alloc in dblayer.c. As long as the functions are + * used by libdb, it won't reach here. + */ + LDAPDebug( LDAP_DEBUG_ANY, + "malloc failed in libdb; terminating the server; OS error %d (%s)\n", + *err, slapd_system_strerror( *err ), 0 ); + exit (1); + } dblayer_release_id2entry( be, db ); return( NULL ); } @@ -274,7 +285,7 @@ id2entry( backend *be, ID id, back_txn *txn, int *err ) e = NULL; } - free( data.data ); + slapi_ch_free( &(data.data) ); dblayer_release_id2entry( be, db ); diff --git a/ldap/servers/slapd/back-ldbm/idl.c b/ldap/servers/slapd/back-ldbm/idl.c index abdfe5ea..be564467 100644 --- a/ldap/servers/slapd/back-ldbm/idl.c +++ b/ldap/servers/slapd/back-ldbm/idl.c @@ -141,7 +141,7 @@ int idl_old_release_private(struct attrinfo *a) PR_ASSERT(NULL != priv->idl_rwlock); PR_DestroyRWLock(priv->idl_rwlock); #endif - free( a->ai_idl ); + slapi_ch_free( (void **)&(a->ai_idl) ); } return 0; } @@ -909,12 +909,8 @@ idl_old_insert_key( idl_check_indirect (idl, i, tmp, tmp2, "idl_insert_key", "overflow", key, id); - if ( k2.dptr != NULL ) { - free( k2.dptr ); - } - if ( k3.dptr != NULL ) { - free( k3.dptr ); - } + slapi_ch_free( (void **)&(k2.dptr) ); + slapi_ch_free( (void **)&(k3.dptr) ); idl_free( tmp ); idl_free( tmp2 ); idl_free( idl ); @@ -998,12 +994,8 @@ idl_old_insert_key( } } - if ( k2.dptr != NULL ) { - free( k2.dptr ); - } - if ( k3.dptr != NULL ) { - free( k3.dptr ); - } + slapi_ch_free( (void **)&(k2.dptr) ); + slapi_ch_free( (void **)&(k3.dptr) ); idl_free( idl ); idl_free( tmp ); idl_unlock_list(a->ai_idl,key); @@ -1065,12 +1057,8 @@ idl_old_insert_key( break; } - if ( k2.dptr != NULL ) { - free( k2.dptr ); - } - if ( k3.dptr != NULL ) { - free( k3.dptr ); - } + slapi_ch_free( (void **)&(k2.dptr) ); + slapi_ch_free( (void **)&(k3.dptr) ); idl_free( tmp ); idl_free( idl ); idl_unlock_list(a->ai_idl,key); @@ -1166,7 +1154,7 @@ int idl_old_store_block( /* Now store the continuation block */ ret = idl_store(be,db,&cont_key,this_cont_block,txn); idl_free(this_cont_block); - free(cont_key.data); + slapi_ch_free(&(cont_key.data)); if ( ret != 0 && ret != DB_LOCK_DEADLOCK ) { LDAPDebug( LDAP_DEBUG_ANY, "idl_store_block(%s) 1 BAD %d %s\n",key->data, ret, dblayer_strerror( ret )); @@ -1490,9 +1478,7 @@ idl_old_delete_key( } LDAPDebug( LDAP_DEBUG_TRACE, "<= idl_delete_key(%s,%lu) %d idl_fetch_one(contkey)\n", contkey.dptr, (u_long)id, rc ); - if ( contkey.dptr != NULL ) { - free( contkey.dptr ); - } + slapi_ch_free( (void **)&(contkey.dptr) ); return( rc ); } @@ -1572,9 +1558,7 @@ idl_old_delete_key( } idl_free( idl ); idl_free( didl ); - if ( contkey.dptr != NULL ) { - free( contkey.dptr ); - } + slapi_ch_free( (void **)&(contkey.dptr) ); idl_unlock_list(a->ai_idl,key); if ( rc != 0 && rc != DB_LOCK_DEADLOCK ) { diff --git a/ldap/servers/slapd/back-ldbm/import-merge.c b/ldap/servers/slapd/back-ldbm/import-merge.c index b2d2074d..38b622c7 100644 --- a/ldap/servers/slapd/back-ldbm/import-merge.c +++ b/ldap/servers/slapd/back-ldbm/import-merge.c @@ -100,12 +100,12 @@ static int import_merge_get_next_thang(backend *be, DBC *cursor, DB *db, import_ thang->payload.idl = idl_fetch(be, db, key, NULL, NULL, &ret); PR_ASSERT(NULL != thang->payload.idl); } else { - free(value.data); - free(key->data); + slapi_ch_free(&(value.data)); + slapi_ch_free(&(key->data)); key->flags = DB_DBT_MALLOC; goto around; /* Just skip these */ } - free(value.data); + slapi_ch_free(&(value.data)); } else { if (DB_NOTFOUND == ret) { /* This means that we're at the end of the file */ @@ -189,7 +189,7 @@ static int import_merge_insert_input_queue(backend *be, import_merge_queue_entry (current_entry->file_referenced_list)[fileno] = 1; /* Because we merged the entries, we no longer need the * key, so free it */ - free(key->data); + slapi_ch_free(&(key->data)); goto done; } else { /* VLV case, we can see exact keys, this is not a bug ! */ @@ -573,7 +573,7 @@ static int import_merge_one_file(ImportWorkerInfo *worker, int passes, /* Write the vlv index */ ret = output_file->put(output_file, NULL, &key, &(thang.payload.vlv_data),0); - free(thang.payload.vlv_data.data); + slapi_ch_free(&(thang.payload.vlv_data.data)); thang.payload.vlv_data.data = NULL; } else { /* Write the IDL index */ @@ -583,7 +583,7 @@ static int import_merge_one_file(ImportWorkerInfo *worker, int passes, idl_free(thang.payload.idl); thang.payload.idl = NULL; } - free(key.data); + slapi_ch_free(&(key.data)); key.data = NULL; if (0 != ret) { /* Failed to write--- most obvious cause being out of diff --git a/ldap/servers/slapd/back-ldbm/import-threads.c b/ldap/servers/slapd/back-ldbm/import-threads.c index c6303d33..b827deac 100644 --- a/ldap/servers/slapd/back-ldbm/import-threads.c +++ b/ldap/servers/slapd/back-ldbm/import-threads.c @@ -734,7 +734,7 @@ void index_producer(void *param) } curr_entry++; temp_id = id_stored_to_internal((char *)key.data); - free(key.data); + slapi_ch_free(&(key.data)); /* call post-entry plugin */ plugin_call_entryfetch_plugins((char **) &data.dptr, &data.dsize); @@ -750,7 +750,7 @@ void index_producer(void *param) inst->inst_name, (u_long)temp_id, 0); continue; } - free(data.data); + slapi_ch_free(&(data.data)); /* generate uniqueid if necessary */ import_generate_uniqueid(job, e); diff --git a/ldap/servers/slapd/back-ldbm/import.c b/ldap/servers/slapd/back-ldbm/import.c index 2a2c6917..e7b1fdb4 100644 --- a/ldap/servers/slapd/back-ldbm/import.c +++ b/ldap/servers/slapd/back-ldbm/import.c @@ -135,7 +135,7 @@ static void import_fifo_destroy(ImportJob *job) job->fifo.item[i].entry = NULL; job->fifo.item[i].filename = NULL; } - free(job->fifo.item); + slapi_ch_free((void **)&job->fifo.item); job->fifo.item = NULL; } @@ -277,7 +277,7 @@ static int import_attr_callback(void *node, void *param) info->ai = a; if (NULL == info->name) { /* Memory allocation error */ - free(info); + FREE(info); return -1; } info->next = job->index_list; @@ -505,15 +505,15 @@ static double import_grok_db_stats(ldbm_instance *inst) inst->inst_cache_hits = current_cache_hits; if (mpstat) - free(mpstat); + slapi_ch_free((void **)&mpstat); if (mpfstat) { #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR + DB_VERSION_PATCH <= 3204 /* In DB 3.2.4 and earlier, we need to free each element */ DB_MPOOL_FSTAT **tfsp; for (tfsp = mpfstat; *tfsp; tfsp++) - free(*tfsp); + slapi_ch_free((void **)tfsp); #endif - free(mpfstat); + slapi_ch_free((void **)&mpfstat); } } return cache_hit_ratio; diff --git a/ldap/servers/slapd/back-ldbm/index.c b/ldap/servers/slapd/back-ldbm/index.c index d7dc0b79..62df834e 100644 --- a/ldap/servers/slapd/back-ldbm/index.c +++ b/ldap/servers/slapd/back-ldbm/index.c @@ -187,7 +187,7 @@ index_put_idl(index_buffer_bin *bin,backend *be, DB_TXN *txn,struct attrinfo *a) if (0 != ret) { goto error; } - slapi_ch_free((void**)&bin->key.data ); + slapi_ch_free( &(bin->key.data) ); idl_free(bin->value); /* If we're already at allids, store an allids block to prevent needless accumulation of blocks */ if (old_idl && ALLIDS(old_idl)) { @@ -262,13 +262,11 @@ index_buffer_terminate(void *h) idl_free(bin->value); bin->value = NULL; } - if (bin->key.data) { - free(bin->key.data); - } + slapi_ch_free(&(bin->key.data)); } - free(handle->bins); + slapi_ch_free((void **)&(handle->bins)); /* Now free the handle */ - free(handle); + slapi_ch_free((void **)&handle); return 0; } @@ -334,7 +332,7 @@ index_buffer_insert(void *h, DBT *key, ID id,backend *be, DB_TXN *txn,struct att retry: if (!(bin->key).data) { (bin->key).size = key->size; - (bin->key).data = malloc(key->size); + (bin->key).data = slapi_ch_malloc(key->size); if (NULL == bin->key.data) { return -1; } @@ -1018,7 +1016,7 @@ error: /* Means that we never allocated a new key */ ; } else { - free(saved_key); + slapi_ch_free(&saved_key); } } return ret; @@ -1248,7 +1246,7 @@ index_range_read( *err = dbc->c_get(dbc,&lowerkey,&data,DB_SET_RANGE); /* lowerkey, if allocated and needs freed */ DBT_FREE_PAYLOAD(data); if (old_lower_key_data != lowerkey.data) { - free(old_lower_key_data); + slapi_ch_free(&old_lower_key_data); } } /* If the seek above fails due to DB_NOTFOUND, this means that there are no keys @@ -2044,7 +2042,7 @@ valuearray_minus_valuearray( for (bcnt = 0; b[bcnt] != NULL; bcnt++); /* allocate return array as big as a */ - c = (Slapi_Value**)calloc(acnt+1, sizeof(Slapi_Value*)); + c = (Slapi_Value**)slapi_ch_calloc(acnt+1, sizeof(Slapi_Value*)); if (acnt == 0) return c; /* sort a */ diff --git a/ldap/servers/slapd/back-ldbm/instance.c b/ldap/servers/slapd/back-ldbm/instance.c index 1e02ac4d..ef19d89f 100644 --- a/ldap/servers/slapd/back-ldbm/instance.c +++ b/ldap/servers/slapd/back-ldbm/instance.c @@ -60,7 +60,7 @@ int ldbm_instance_create(backend *be, char *name) inst = (ldbm_instance *) slapi_ch_calloc(1, sizeof(ldbm_instance)); /* Record the name of this instance. */ - inst->inst_name = strdup(name); + inst->inst_name = slapi_ch_strdup(name); /* initialize the entry cache */ if (! cache_init(&(inst->inst_cache), DEFAULT_CACHE_SIZE, diff --git a/ldap/servers/slapd/back-ldbm/ldif2ldbm.c b/ldap/servers/slapd/back-ldbm/ldif2ldbm.c index 31c76224..626bddee 100644 --- a/ldap/servers/slapd/back-ldbm/ldif2ldbm.c +++ b/ldap/servers/slapd/back-ldbm/ldif2ldbm.c @@ -463,7 +463,7 @@ int update_subordinatecounts(backend *be, import_subcount_stuff *mothers, key.flags = DB_DBT_MALLOC; ret = dbc->c_get(dbc,&key,&data,DB_NEXT_NODUP); if (NULL != data.data) { - free(data.data); + slapi_ch_free(&(data.data)); data.data = NULL; } if (0 != ret) { @@ -471,7 +471,7 @@ int update_subordinatecounts(backend *be, import_subcount_stuff *mothers, ldbm_nasty(sourcefile,62,ret); } if (NULL != key.data) { - free(key.data); + slapi_ch_free(&(key.data)); key.data = NULL; } break; @@ -521,7 +521,7 @@ int update_subordinatecounts(backend *be, import_subcount_stuff *mothers, } } if (NULL != key.data) { - free(key.data); + slapi_ch_free(&(key.data)); key.data = NULL; } } @@ -985,8 +985,8 @@ ldbm_back_ldbm2ldif( Slapi_PBlock *pb ) keepgoing = 0; } else { lastid = id_stored_to_internal((char *)key.data); - free( key.data ); - free( data.data ); + slapi_ch_free( &(key.data) ); + slapi_ch_free( &(data.data) ); isfirst = 1; } } @@ -1089,7 +1089,7 @@ ldbm_back_ldbm2ldif( Slapi_PBlock *pb ) /* back to internal format */ temp_id = id_stored_to_internal((char *)key.data); - free(key.data); + slapi_ch_free(&(key.data)); } /* call post-entry plugin */ @@ -1097,7 +1097,7 @@ ldbm_back_ldbm2ldif( Slapi_PBlock *pb ) ep = backentry_alloc(); ep->ep_entry = slapi_str2entry( data.data, str2entry_options ); - free(data.data); + slapi_ch_free(&(data.data)); if ( (ep->ep_entry) != NULL ) { ep->ep_id = temp_id; @@ -1176,7 +1176,7 @@ ldbm_back_ldbm2ldif( Slapi_PBlock *pb ) } backentry_free( &ep ); - free( data.data ); + slapi_ch_free( &(data.data) ); } /* DB_NOTFOUND -> successful end */ if (return_value == DB_NOTFOUND) @@ -1383,8 +1383,8 @@ ldbm_back_ldbm2index(Slapi_PBlock *pb) isfirst = 0; /* neither a first nor a last */ } else if (rc == 0) { lastid = id_stored_to_internal((char *)key.data); - free(key.data); - free(data.data); + slapi_ch_free(&(key.data)); + slapi_ch_free(&(data.data)); isfirst = 1; } else { LDAPDebug(LDAP_DEBUG_ANY, @@ -1560,7 +1560,7 @@ ldbm_back_ldbm2index(Slapi_PBlock *pb) break; } temp_id = id_stored_to_internal((char *)key.data); - free(key.data); + slapi_ch_free(&(key.data)); } /* call post-entry plugin */ @@ -1568,7 +1568,7 @@ ldbm_back_ldbm2index(Slapi_PBlock *pb) ep = backentry_alloc(); ep->ep_entry = slapi_str2entry( data.data, 0 ); - free(data.data); + slapi_ch_free(&(data.data)); if ( ep->ep_entry != NULL ) { ep->ep_id = temp_id; diff --git a/ldap/servers/slapd/back-ldbm/monitor.c b/ldap/servers/slapd/back-ldbm/monitor.c index 8282d0d3..f13b7c38 100644 --- a/ldap/servers/slapd/back-ldbm/monitor.c +++ b/ldap/servers/slapd/back-ldbm/monitor.c @@ -218,9 +218,9 @@ int ldbm_back_monitor_instance_search(Slapi_PBlock *pb, Slapi_Entry *e, #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR + DB_VERSION_PATCH <= 3204 /* In DB 3.2.4 and earlier, we need to free each element */ for (i = 0; mpfstat[i]; i++) - free(mpfstat[i]); + slapi_ch_free((void **)&mpfstat[i]); #endif - free(mpfstat); + slapi_ch_free((void **)&mpfstat); *returncode = LDAP_SUCCESS; return SLAPI_DSE_CALLBACK_OK; @@ -275,16 +275,16 @@ int ldbm_back_monitor_search(Slapi_PBlock *pb, Slapi_Entry *e, sprintf(buf, "%u", mpstat->st_rw_evict); MSET("dbCacheRWEvict"); - free(mpstat); + slapi_ch_free((void **)&mpstat); if (mpfstat) { #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR + DB_VERSION_PATCH <= 3204 /* In DB 3.2.4 and earlier, we need to free each element */ int i; for (i = 0; mpfstat[i]; i++) - free(mpfstat[i]); + slapi_ch_free((void **)&mpfstat[i]); #endif - free(mpfstat); + slapi_ch_free((void **)&mpfstat); } *returncode = LDAP_SUCCESS; diff --git a/ldap/servers/slapd/back-ldbm/nextid.c b/ldap/servers/slapd/back-ldbm/nextid.c index a1cff1a8..6e8f6316 100644 --- a/ldap/servers/slapd/back-ldbm/nextid.c +++ b/ldap/servers/slapd/back-ldbm/nextid.c @@ -177,35 +177,26 @@ get_ids_from_disk(backend *be) /*Get the last key*/ DBC *dbc = NULL; - DBT key = {0}; /*For the nextid*/ + DBT key = {0}; /*For the nextid*/ DBT Value = {0}; + Value.flags = DB_DBT_MALLOC; key.flags = DB_DBT_MALLOC; return_value = id2entrydb->cursor(id2entrydb,NULL,&dbc,0); if (0 == return_value) { return_value = dbc->c_get(dbc,&key,&Value,DB_LAST); - if (0 == return_value) { + if ( (0 == return_value) && (NULL != key.dptr) ) { inst->inst_nextid = id_stored_to_internal(key.dptr) + 1; + } else { + inst->inst_nextid = 1; /* error case: set 1 */ } - if (NULL != key.data) { - free(key.data); - } - if (NULL != Value.data) { - free(Value.data); - } + slapi_ch_free(&(key.data)); + slapi_ch_free(&(Value.data)); dbc->c_close(dbc); + } else { + inst->inst_nextid = 1; /* when there is no id2entry, start from id 1 */ } - if ( (key.dptr == NULL) || (0 != return_value) ) { - inst->inst_nextid = 1; - /*close the cache*/ - dblayer_release_id2entry( be, id2entrydb ); - - /* unlock */ - PR_Unlock( inst->inst_nextid_mutex ); - return; - } - } /*close the cache*/ @@ -213,6 +204,8 @@ get_ids_from_disk(backend *be) /* unlock */ PR_Unlock( inst->inst_nextid_mutex ); + + return; } diff --git a/ldap/servers/slapd/back-ldbm/perfctrs.c b/ldap/servers/slapd/back-ldbm/perfctrs.c index 578c7528..5b7c68f0 100644 --- a/ldap/servers/slapd/back-ldbm/perfctrs.c +++ b/ldap/servers/slapd/back-ldbm/perfctrs.c @@ -91,7 +91,7 @@ char * string_concatenate(char *a, char* b) char *string = NULL; string_length = strlen(a) + strlen(b) + 1; - string = malloc(string_length); + string = slapi_ch_malloc(string_length); if (NULL == string) { return string; } @@ -188,7 +188,7 @@ void perfctrs_init(struct ldbminfo *li, perfctrs_private **ret_priv) /* * We need the perfctrs_private area on all platforms. */ - priv = calloc(1,sizeof(perfctrs_private)); + priv = (perfctrs_private *)slapi_ch_calloc(1,sizeof(perfctrs_private)); if (NULL == priv) { return; } @@ -210,7 +210,7 @@ void perfctrs_init(struct ldbminfo *li, perfctrs_private **ret_priv) /* * On other platforms, the performance counters reside in regular memory. */ - if ( NULL == ( priv->memory = calloc( 1, sizeof( performance_counters )))) { + if ( NULL == ( priv->memory = slapi_ch_calloc( 1, sizeof( performance_counters )))) { return; } #endif @@ -226,13 +226,13 @@ void perfctrs_terminate(perfctrs_private **priv, DB_ENV *db_env) DB_LOG_STAT *logstat = NULL; DB_LOCK_STAT *lockstat = NULL; - MEMP_STAT(db_env, &mpstat, NULL, DB_STAT_CLEAR, malloc); + MEMP_STAT(db_env, &mpstat, NULL, DB_STAT_CLEAR, (void *)slapi_ch_malloc); slapi_ch_free((void**)&mpstat); - TXN_STAT(db_env, &txnstat, DB_STAT_CLEAR, malloc); + TXN_STAT(db_env, &txnstat, DB_STAT_CLEAR, (void *)slapi_ch_malloc); slapi_ch_free((void**)&txnstat); - LOG_STAT(db_env, &logstat, DB_STAT_CLEAR, malloc); + LOG_STAT(db_env, &logstat, DB_STAT_CLEAR, (void *)slapi_ch_malloc); slapi_ch_free((void**)&logstat); - LOCK_STAT(db_env, &lockstat, DB_STAT_CLEAR, malloc); + LOCK_STAT(db_env, &lockstat, DB_STAT_CLEAR, (void *)slapi_ch_malloc); slapi_ch_free((void**)&lockstat); #if defined(_WIN32) if (NULL != (*priv)->memory) { @@ -246,12 +246,11 @@ void perfctrs_terminate(perfctrs_private **priv, DB_ENV *db_env) } #else if (NULL != (*priv)->memory) { - free((*priv)->memory); + slapi_ch_free(&(*priv)->memory); } #endif - free( (*priv) ); - (*priv) = NULL; + slapi_ch_free( (void **)priv ); } /* Wait while checking for perfctr update requests */ @@ -299,31 +298,30 @@ void perfctrs_update(perfctrs_private *priv, DB_ENV *db_env) if (dblayer_db_uses_logging(db_env)) { DB_LOG_STAT *logstat = NULL; - ret = LOG_STAT(db_env,&logstat,0,malloc); + ret = LOG_STAT(db_env,&logstat,0,(void *)slapi_ch_malloc); if (0 == ret) { perf->log_region_wait_rate = logstat->st_region_wait; perf->log_write_rate = 1024*1024*logstat->st_w_mbytes + logstat->st_w_bytes; perf->log_bytes_since_checkpoint = 1024*1024*logstat->st_wc_mbytes + logstat->st_wc_bytes; } - free(logstat); + slapi_ch_free((void **)&logstat); } if (dblayer_db_uses_transactions(db_env)) { DB_TXN_STAT *txnstat = NULL; - ret = TXN_STAT(db_env, &txnstat, 0, malloc); + ret = TXN_STAT(db_env, &txnstat, 0, (void *)slapi_ch_malloc); if (0 == ret) { perf->active_txns = txnstat->st_nactive; perf->commit_rate = txnstat->st_ncommits; perf->abort_rate = txnstat->st_naborts; perf->txn_region_wait_rate = txnstat->st_region_wait; } - if (txnstat) - free(txnstat); + slapi_ch_free((void **)&txnstat); } if (dblayer_db_uses_locking(db_env)) { DB_LOCK_STAT *lockstat = NULL; - ret = LOCK_STAT(db_env,&lockstat,0,malloc); + ret = LOCK_STAT(db_env,&lockstat,0,(void *)slapi_ch_malloc); if (0 == ret) { perf->lock_region_wait_rate = lockstat->st_region_wait; perf->deadlock_rate = lockstat->st_ndeadlocks; @@ -336,12 +334,12 @@ void perfctrs_update(perfctrs_private *priv, DB_ENV *db_env) perf->current_lock_objects = lockstat->st_nobjects; perf->max_lock_objects = lockstat->st_maxnobjects; } - free(lockstat); + slapi_ch_free((void **)&lockstat); } if (dblayer_db_uses_mpool(db_env)) { DB_MPOOL_STAT *mpstat = NULL; - ret = MEMP_STAT(db_env,&mpstat,NULL,0,malloc); + ret = MEMP_STAT(db_env,&mpstat,NULL,0,(void *)slapi_ch_malloc); if (0 == ret) { #define ONEG 1073741824 perf->cache_size_bytes = mpstat->st_gbytes * ONEG + mpstat->st_bytes; @@ -362,7 +360,7 @@ void perfctrs_update(perfctrs_private *priv, DB_ENV *db_env) perf->clean_pages = mpstat->st_page_clean; perf->page_trickle_rate = mpstat->st_page_trickle; perf->cache_region_wait_rate = mpstat->st_region_wait; - free(mpstat); + slapi_ch_free((void **)&mpstat); } } /* Place the stats in the shared memory region */ diff --git a/ldap/servers/slapd/back-ldbm/seq.c b/ldap/servers/slapd/back-ldbm/seq.c index 449bcf83..6e2fdfd8 100644 --- a/ldap/servers/slapd/back-ldbm/seq.c +++ b/ldap/servers/slapd/back-ldbm/seq.c @@ -184,7 +184,7 @@ ldbm_back_seq( Slapi_PBlock *pb ) return_value = dbc->c_get(dbc,&key,&data,DB_SET); if (0 == return_value) { - free(data.data); + slapi_ch_free(&(data.data)); return_value = dbc->c_get(dbc,&key,&data,DB_NEXT); } else @@ -198,7 +198,7 @@ ldbm_back_seq( Slapi_PBlock *pb ) return_value = dbc->c_get(dbc,&key,&data,DB_SET); if (0 == return_value ) { - free(data.data); + slapi_ch_free(&(data.data)); return_value = dbc->c_get(dbc,&key,&data,DB_PREV); } else @@ -216,7 +216,7 @@ ldbm_back_seq( Slapi_PBlock *pb ) return_value = dbc->c_get(dbc,&key,&data,DB_SET_RANGE); if (0 == return_value || DB_NOTFOUND == return_value) { - free(data.data); + slapi_ch_free(&(data.data)); return_value = dbc->c_get(dbc,&key,&data,DB_PREV); } } @@ -252,11 +252,11 @@ ldbm_back_seq( Slapi_PBlock *pb ) } else if ( err != 0 && err != DB_NOTFOUND ) { ldbm_nasty("ldbm_back_seq database error", 1650, err); } - free( data.data ); + slapi_ch_free( &(data.data) ); if ( key.data != little_buffer && key.data != &keystring ) { - free( key.data ); + slapi_ch_free( &(key.data) ); } - free( big_buffer ); + slapi_ch_free_string( &big_buffer ); } /* null idlist means there were no matching keys */ diff --git a/ldap/servers/slapd/back-ldbm/sort.c b/ldap/servers/slapd/back-ldbm/sort.c index b9f3e211..e9397a88 100644 --- a/ldap/servers/slapd/back-ldbm/sort.c +++ b/ldap/servers/slapd/back-ldbm/sort.c @@ -395,7 +395,7 @@ int parse_sort_spec(struct berval *sort_spec_ber, sort_spec **ps) } /* normalize */ type = slapi_attr_syntax_normalize(rtype); - free(rtype); + slapi_ch_free_string(&rtype); /* Now look for the next tag. */ diff --git a/ldap/servers/slapd/back-ldbm/vlv.c b/ldap/servers/slapd/back-ldbm/vlv.c index b8ba3f1a..3bb39aff 100644 --- a/ldap/servers/slapd/back-ldbm/vlv.c +++ b/ldap/servers/slapd/back-ldbm/vlv.c @@ -959,14 +959,14 @@ vlv_build_candidate_list_byvalue( struct vlvIndex* p, DBC *dbc, PRUint32 length, err= dbc->c_get(dbc,&key,&data,DB_SET_RANGE); if(err==0) { - free(data.data); + slapi_ch_free(&(data.data)); err= dbc->c_get(dbc,&key,&data,DB_GET_RECNO); if(err==0) { si= *((db_recno_t*)data.data); /* Records are numbered from one. */ si--; - free(data.data); + slapi_ch_free(&(data.data)); LDAPDebug( LDAP_DEBUG_TRACE, "<= vlv_build_candidate_list_byvalue: Found. Index=%lu\n",si,0,0); } else @@ -1029,7 +1029,7 @@ int vlv_build_idl(PRUint32 start, PRUint32 stop, DB *db, DBC *dbc, err = dbc->c_get(dbc, &key, &data, DB_SET_RECNO); while ((err == 0) && (recno <= stop+1)) { if (key.data != &recno) - free(key.data); + slapi_ch_free(&(key.data)); idl_append(idl, *(ID *)data.data); if (++recno <= stop+1) { err = dbc->c_get(dbc, &key, &data, DB_NEXT); @@ -1955,7 +1955,7 @@ static void replace_char(char *name, char c, char c2) /* similar to what the console GUI does */ char *create_vlv_search_tag(const char* dn) { - char *tmp2=strdup(dn); + char *tmp2=slapi_ch_strdup(dn); replace_char(tmp2,',',' '); replace_char(tmp2,'"','-'); diff --git a/ldap/servers/slapd/back-ldbm/vlv_srch.c b/ldap/servers/slapd/back-ldbm/vlv_srch.c index ace763d4..63c63485 100644 --- a/ldap/servers/slapd/back-ldbm/vlv_srch.c +++ b/ldap/servers/slapd/back-ldbm/vlv_srch.c @@ -673,8 +673,8 @@ vlvIndex_get_indexlength(struct vlvIndex* p, DB *db, back_txn *txn) err= dbc->c_get(dbc,&key,&data,DB_LAST); if(err==0) { - free(key.data); key.data= NULL; - free(data.data); data.data= NULL; + slapi_ch_free(&(key.data)); + slapi_ch_free(&(data.data)); err= dbc->c_get(dbc,&key,&data,DB_GET_RECNO); if(err==0) { @@ -682,7 +682,7 @@ vlvIndex_get_indexlength(struct vlvIndex* p, DB *db, back_txn *txn) p->vlv_indexlength_cached= 1; p->vlv_indexlength= *((db_recno_t*)data.data); PR_Unlock(p->vlv_indexlength_lock); - free(data.data); + slapi_ch_free(&(data.data)); } } dbc->c_close(dbc); diff --git a/ldap/servers/slapd/bind.c b/ldap/servers/slapd/bind.c index 72c84530..5ae89720 100644 --- a/ldap/servers/slapd/bind.c +++ b/ldap/servers/slapd/bind.c @@ -652,12 +652,8 @@ do_bind( Slapi_PBlock *pb ) if (be) slapi_be_Unlock(be); slapi_sdn_done(&sdn); - if ( saslmech != NULL ) { - free( saslmech ); - } - if ( cred.bv_val != NULL ) { - free( cred.bv_val ); - } + slapi_ch_free_string( &saslmech ); + slapi_ch_free( (void **)&cred.bv_val ); if ( bind_target_entry != NULL ) slapi_entry_free(bind_target_entry); } diff --git a/ldap/servers/slapd/ch_malloc.c b/ldap/servers/slapd/ch_malloc.c index df72a603..b2afbe0d 100644 --- a/ldap/servers/slapd/ch_malloc.c +++ b/ldap/servers/slapd/ch_malloc.c @@ -139,6 +139,7 @@ log_negative_alloc_msg( const char *op, const char *units, unsigned long size ) op, size, units, units ); } +#if !defined(MEMPOOL_EXPERIMENTAL) char * slapi_ch_malloc( unsigned long size @@ -300,6 +301,7 @@ slapi_ch_strdup ( const char* s1) #endif return newmem; } +#endif /* !MEMPOOL_EXPERIMENTAL */ struct berval* slapi_ch_bvdup (const struct berval* v) @@ -334,6 +336,7 @@ slapi_ch_bvecdup (struct berval** v) return newberval; } +#if !defined(MEMPOOL_EXPERIMENTAL) /* * Function: slapi_ch_free * @@ -368,6 +371,7 @@ slapi_ch_free(void **ptr) PR_DECREMENT_COUNTER(slapi_ch_counter_exist); return; } +#endif /* !MEMPOOL_EXPERIMENTAL */ /* just like slapi_ch_free, takes the address of the struct berval pointer */ @@ -414,6 +418,7 @@ slapi_ch_free_string(char **s) the operating system. But if this changes in the future, this function will have to change as well. */ +#if !defined(MEMPOOL_EXPERIMENTAL) char * slapi_ch_smprintf(const char *fmt, ...) { @@ -430,6 +435,7 @@ slapi_ch_smprintf(const char *fmt, ...) return p; } +#endif /* ========================= NT Specific Leak Checking Code ================================== */ diff --git a/ldap/servers/slapd/computed.c b/ldap/servers/slapd/computed.c index c82746f5..4a767ba9 100644 --- a/ldap/servers/slapd/computed.c +++ b/ldap/servers/slapd/computed.c @@ -139,7 +139,7 @@ int slapi_compute_add_evaluator(slapi_compute_callback_t function) PR_ASSERT(NULL != function); PR_ASSERT(NULL != compute_evaluators_lock); PR_RWLock_Wlock(compute_evaluators_lock); - new_eval = calloc(1,sizeof (compute_evaluator)); + new_eval = (compute_evaluator *)slapi_ch_calloc(1,sizeof (compute_evaluator)); if (NULL == new_eval) { rc = ENOMEM; } else { @@ -180,7 +180,7 @@ int compute_terminate() while (current != NULL) { compute_evaluator *asabird = current; current = current->next; - free(asabird); + slapi_ch_free((void **)&asabird); } PR_RWLock_Unlock(compute_evaluators_lock); /* Free the lock */ @@ -192,7 +192,7 @@ int compute_terminate() while (current != NULL) { compute_rewriter *asabird = current; current = current->next; - free(asabird); + slapi_ch_free((void **)&asabird); } PR_RWLock_Unlock(compute_rewriters_lock); PR_DestroyRWLock(compute_rewriters_lock); @@ -208,7 +208,7 @@ int slapi_compute_add_search_rewriter(slapi_search_rewrite_callback_t function) compute_rewriter *new_rewriter = NULL; PR_ASSERT(NULL != function); PR_ASSERT(NULL != compute_rewriters_lock); - new_rewriter = calloc(1,sizeof (compute_rewriter)); + new_rewriter = (compute_rewriter *)slapi_ch_calloc(1,sizeof (compute_rewriter)); if (NULL == new_rewriter) { rc = ENOMEM; } else { diff --git a/ldap/servers/slapd/connection.c b/ldap/servers/slapd/connection.c index 7d6e58d1..58495436 100644 --- a/ldap/servers/slapd/connection.c +++ b/ldap/servers/slapd/connection.c @@ -191,12 +191,12 @@ connection_cleanup(Connection *conn) conn->c_prfd= NULL; /* c_ci stays as it is */ conn->c_fdi= SLAPD_INVALID_SOCKET_INDEX; - conn->c_next= NULL; - conn->c_prev= NULL; + conn->c_next= NULL; + conn->c_prev= NULL; conn->c_extension= NULL; /* remove any SASL I/O from the connection */ sasl_io_cleanup(conn); - sasl_dispose((sasl_conn_t**)&conn->c_sasl_conn); + sasl_dispose((sasl_conn_t**)&conn->c_sasl_conn); /* free the connection socket buffer */ connection_free_private_buffer(conn); @@ -2310,7 +2310,7 @@ get_pb() pb = tmp->pb; /* Free the memory used by the pb found. */ - free ((char *) tmp); + slapi_ch_free ((void **)&tmp); return (pb); } @@ -2448,7 +2448,7 @@ op_copy_identity(Connection *conn, Operation *op) typelen= conn->c_authtype ? strlen (conn->c_authtype) : 0; slapi_sdn_done(&op->o_sdn); - slapi_ch_free((void **) &(op->o_authtype)); + slapi_ch_free_string(&(op->o_authtype)); if (dnlen <= 0 && typelen <= 0) { op->o_authtype = NULL; } else { diff --git a/ldap/servers/slapd/entry.c b/ldap/servers/slapd/entry.c index c7c1a74e..e3d2795e 100644 --- a/ldap/servers/slapd/entry.c +++ b/ldap/servers/slapd/entry.c @@ -1918,7 +1918,7 @@ slapi_entry_vattrcache_find_values_and_type_ex( const Slapi_Entry *e, *actual_type_name = (char**)slapi_ch_malloc(sizeof(*actual_type_name)); slapi_attr_get_type( tmp_attr, &vattr_type ); - **actual_type_name = strdup(vattr_type); + **actual_type_name = slapi_ch_strdup(vattr_type); } } @@ -1974,7 +1974,7 @@ slapi_entry_vattrcache_find_values_and_type( const Slapi_Entry *e, *results = valueset_dup(&(tmp_attr->a_present_values)); slapi_attr_get_type( tmp_attr, &vattr_type ); - *actual_type_name = strdup(vattr_type); + *actual_type_name = slapi_ch_strdup(vattr_type); } } diff --git a/ldap/servers/slapd/filter.c b/ldap/servers/slapd/filter.c index 867b37fd..14fee9ff 100644 --- a/ldap/servers/slapd/filter.c +++ b/ldap/servers/slapd/filter.c @@ -303,7 +303,7 @@ get_filter_internal( Connection *conn, BerElement *ber, } else { err = LDAP_SUCCESS; f->f_type = slapi_attr_syntax_normalize( type ); - free( type ); + slapi_ch_free_string( &type ); filter_compute_hash(f); *fstr = slapi_ch_smprintf( "(%s=*)", f->f_type ); } @@ -458,7 +458,7 @@ get_substring_filter( return( LDAP_PROTOCOL_ERROR ); } f->f_sub_type = slapi_attr_syntax_normalize( type ); - free( type ); + slapi_ch_free_string( &type ); f->f_sub_initial = NULL; f->f_sub_any = NULL; f->f_sub_final = NULL; @@ -477,7 +477,7 @@ get_substring_filter( } if ( val == NULL || *val == '\0' ) { if ( val != NULL ) { - free( val ); + slapi_ch_free_string( &val ); } return( LDAP_INVALID_SYNTAX ); } @@ -593,7 +593,7 @@ get_extensible_filter( BerElement *ber, mr_filter_t* mrf ) rc = LDAP_PROTOCOL_ERROR; } else { mrf->mrf_type = slapi_attr_syntax_normalize(type); - free (type); + slapi_ch_free_string (&type); } } gotelem++; @@ -642,7 +642,7 @@ parsing_error:; Slapi_Filter * slapi_filter_dup(Slapi_Filter *f) { - Slapi_Filter *out = 0; + Slapi_Filter *out = 0; struct slapi_filter *fl = 0; struct slapi_filter **outl = 0; struct slapi_filter *lastout = 0; @@ -651,7 +651,7 @@ slapi_filter_dup(Slapi_Filter *f) return NULL; } - out = (struct slapi_filter*)calloc(1, sizeof(struct slapi_filter)); + out = (struct slapi_filter*)slapi_ch_calloc(1, sizeof(struct slapi_filter)); if ( out == NULL ) { LDAPDebug(LDAP_DEBUG_ANY, "slapi_filter_dup: memory allocation error\n", 0, 0, 0 ); diff --git a/ldap/servers/slapd/filtercmp.c b/ldap/servers/slapd/filtercmp.c index 40b9178d..05916815 100644 --- a/ldap/servers/slapd/filtercmp.c +++ b/ldap/servers/slapd/filtercmp.c @@ -264,7 +264,7 @@ static int filter_compare_substrings(struct slapi_filter *f1, return 1; ret = 1; /* assume failure until done comparing */ if (count1 > 20) - tally = (int *)malloc(count1); + tally = (int *)slapi_ch_malloc(count1); else tally = buf; if (!tally) @@ -292,7 +292,7 @@ static int filter_compare_substrings(struct slapi_filter *f1, done: if ((count1 > 20) && tally) - free(tally); + slapi_ch_free((void **)&tally); return ret; } @@ -310,7 +310,7 @@ static int filter_compare_lists(struct slapi_filter *f1, return 1; ret = 1; if (count1 > 20) - tally = (int *)malloc(count1); + tally = (int *)slapi_ch_malloc(count1); else tally = buf; if (!tally) @@ -336,7 +336,7 @@ static int filter_compare_lists(struct slapi_filter *f1, done: if ((count1 > 20) && tally) - free(tally); + slapi_ch_free((void **)&tally); return ret; } diff --git a/ldap/servers/slapd/libglobs.c b/ldap/servers/slapd/libglobs.c index 6b896835..6a7c0178 100644 --- a/ldap/servers/slapd/libglobs.c +++ b/ldap/servers/slapd/libglobs.c @@ -585,6 +585,14 @@ static struct config_get_and_set { NULL, 0, (void **)&global_slapdFrontendConfig.outbound_ldap_io_timeout, CONFIG_INT, NULL} +#ifdef MEMPOOL_EXPERIMENTAL + ,{CONFIG_MEMPOOL_SWITCH_ATTRIBUTE, config_set_mempool_switch, + NULL, 0, + (void**)&global_slapdFrontendConfig.mempool_switch, CONFIG_ON_OFF, (ConfigGetFunc)config_get_mempool_switch}, + {CONFIG_MEMPOOL_MAXFREELIST_ATTRIBUTE, config_set_mempool_maxfreelist, + NULL, 0, + (void**)&global_slapdFrontendConfig.mempool_maxfreelist, CONFIG_INT, (ConfigGetFunc)config_get_mempool_maxfreelist} +#endif /* MEMPOOL_EXPERIMENTAL */ }; /* @@ -940,6 +948,19 @@ FrontendConfig_init () { cfg->auditlog_exptime = 1; cfg->auditlog_exptimeunit = slapi_ch_strdup("month"); +#ifdef MEMPOOL_EXPERIMENTAL + cfg->mempool_switch = LDAP_ON; + cfg->mempool_maxfreelist = 1024; + cfg->system_page_size = sysconf(_SC_PAGE_SIZE); /* not to get every time; no set, get only */ + { + long sc_size = cfg->system_page_size; + cfg->system_page_bits = 0; + while ((sc_size >>= 1) > 0) { + cfg->system_page_bits++; /* to calculate once; no set, get only */ + } + } +#endif /* MEMPOOL_EXPERIMENTAL */ + init_config_get_and_set(); } @@ -4840,6 +4861,79 @@ config_set_accesslogbuffering(const char *attrname, char *value, char *errorbuf, return retVal; } +#ifdef MEMPOOL_EXPERIMENTAL +int +config_set_mempool_switch( const char *attrname, char *value, char *errorbuf, int apply ) { + int retVal = LDAP_SUCCESS; + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + + retVal = config_set_onoff(attrname, + value, + &(slapdFrontendConfig->mempool_switch), + errorbuf, + apply); + + return retVal; +} + +int +config_get_mempool_switch() +{ + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + return slapdFrontendConfig->mempool_switch; +} + +int +config_set_mempool_maxfreelist( const char *attrname, char *value, char *errorbuf, int apply ) +{ + int retVal = LDAP_SUCCESS; + char *endp = NULL; + int maxfreelist; + + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + + if ( config_value_is_null( attrname, value, errorbuf, 0 )) { + return LDAP_OPERATIONS_ERROR; + } + errno = 0; + maxfreelist = strtol(value, &endp, 10); + if (0 != errno ) { + return LDAP_OPERATIONS_ERROR; + } + + if ( apply ) { + CFG_LOCK_WRITE(slapdFrontendConfig); + + slapdFrontendConfig->mempool_maxfreelist = maxfreelist; + + CFG_UNLOCK_WRITE(slapdFrontendConfig); + } + + return retVal; +} + +int +config_get_mempool_maxfreelist() +{ + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + return slapdFrontendConfig->mempool_maxfreelist; +} + +long +config_get_system_page_size() +{ + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + return slapdFrontendConfig->system_page_size; +} + +int +config_get_system_page_bits() +{ + slapdFrontendConfig_t *slapdFrontendConfig = getFrontendConfig(); + return slapdFrontendConfig->system_page_bits; +} +#endif /* MEMPOOL_EXPERIMENTAL */ + int config_set_csnlogging(const char *attrname, char *value, char *errorbuf, int apply) { diff --git a/ldap/servers/slapd/main.c b/ldap/servers/slapd/main.c index 61ead86f..3a328cd8 100644 --- a/ldap/servers/slapd/main.c +++ b/ldap/servers/slapd/main.c @@ -225,7 +225,7 @@ chown_dir_files(char *name, struct passwd *pw, PRBool strip_fn) char *log=NULL, *ptr=NULL; int rc=0; - log=strdup(name); + log=slapi_ch_strdup(name); if(strip_fn) { if((ptr=strrchr(log,'/'))==NULL) @@ -250,7 +250,7 @@ chown_dir_files(char *name, struct passwd *pw, PRBool strip_fn) } PR_CloseDir( dir ); } - free(log); + slapi_ch_free_string(&log); } /* Changes the owner of the files in the logs and @@ -621,6 +621,12 @@ write_start_pid_file() } #endif /* WIN32 */ +#ifdef MEMPOOL_EXPERIMENTAL +void _free_wrapper(void *ptr) +{ + slapi_ch_free(&ptr); +} +#endif int main( int argc, char **argv) @@ -635,6 +641,19 @@ main( int argc, char **argv) _main(); #endif #endif +#ifdef MEMPOOL_EXPERIMENTAL + /* to use LDAP C SDK lber functions seemlessly with slapi_ch_malloc funcs, + * setting the slapi_ch_malloc funcs to lber option here. */ + { + struct ldap_memalloc_fns memalloc_fns; + + memalloc_fns.ldapmem_malloc = (LDAP_MALLOC_CALLBACK *)slapi_ch_malloc; + memalloc_fns.ldapmem_calloc = (LDAP_CALLOC_CALLBACK *)slapi_ch_calloc; + memalloc_fns.ldapmem_realloc = (LDAP_REALLOC_CALLBACK *)slapi_ch_realloc; + memalloc_fns.ldapmem_free = (LDAP_FREE_CALLBACK *)_free_wrapper; + ldap_set_option( 0x1, LDAP_OPT_MEMALLOC_FN_PTRS, &memalloc_fns ); + } +#endif /* * Initialize NSPR very early. NSPR supports implicit initialization, * but it is not bulletproof -- so it is better to be explicit. diff --git a/ldap/servers/slapd/mempool.c b/ldap/servers/slapd/mempool.c new file mode 100644 index 00000000..56fd783d --- /dev/null +++ b/ldap/servers/slapd/mempool.c @@ -0,0 +1,842 @@ +/** BEGIN COPYRIGHT BLOCK + * This Program is free software; you can redistribute it and/or modify it under + * the terms of the GNU General Public License as published by the Free Software + * Foundation; version 2 of the License. + * + * This Program is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along with + * this Program; if not, write to the Free Software Foundation, Inc., 59 Temple + * Place, Suite 330, Boston, MA 02111-1307 USA. + * + * In addition, as a special exception, Red Hat, Inc. gives You the additional + * right to link the code of this Program with code not covered under the GNU + * General Public License ("Non-GPL Code") and to distribute linked combinations + * including the two, subject to the limitations in this paragraph. Non-GPL Code + * permitted under this exception must only link to the code of this Program + * through those well defined interfaces identified in the file named EXCEPTION + * found in the source code files (the "Approved Interfaces"). The files of + * Non-GPL Code may instantiate templates or use macros or inline functions from + * the Approved Interfaces without causing the resulting work to be covered by + * the GNU General Public License. Only Red Hat, Inc. may make changes or + * additions to the list of Approved Interfaces. You must obey the GNU General + * Public License in all respects for all of the Program code and other code used + * in conjunction with the Program except the Non-GPL Code covered by this + * exception. If you modify this file, you may extend this exception to your + * version of the file, but you are not obligated to do so. If you do not wish to + * provide this exception without modification, you must delete this exception + * statement from your version and license this file solely under the GPL without + * exception. + * + * Copyright (C) 2008 Red Hat, Inc. + * All rights reserved. + * END COPYRIGHT BLOCK **/ + +#ifdef MEMPOOL_EXPERIMENTAL + +#ifdef HAVE_CONFIG_H +# include <config.h> +#endif + +#include <slap.h> +#include <prcountr.h> + +struct mempool_object { + struct mempool_object *mempool_next; +}; + +typedef int (*mempool_cleanup_callback)(void *object); + +#ifdef SHARED_MEMPOOL +/* + * shared mempool among threads + * contention causes the performance degradation + * (Warning: SHARED_MEMPOOL code is obsolete) + */ +#define MEMPOOL_END NULL +static struct mempool { + const char *mempool_name; + struct mempool_object *mempool_head; + PRLock *mempool_mutex; + mempool_cleanup_callback mempool_cleanup_fn; + unsigned long mempool_count; +} mempool[] = { + {"2K", NULL, NULL, NULL, 0}, + {"4K", NULL, NULL, NULL, 0}, + {"8K", NULL, NULL, NULL, 0}, + {"16K", NULL, NULL, NULL, 0}, + {"32K", NULL, NULL, NULL, 0}, + {"64K", NULL, NULL, NULL, 0}, + {"128K", NULL, NULL, NULL, 0}, + {"256K", NULL, NULL, NULL, 0}, + {"512K", NULL, NULL, NULL, 0}, + {"1M", NULL, NULL, NULL, 0}, + {"2M", NULL, NULL, NULL, 0}, + {"4M", NULL, NULL, NULL, 0}, + {"8M", NULL, NULL, NULL, 0}, + {"16M", NULL, NULL, NULL, 0}, + {"32M", NULL, NULL, NULL, 0}, + {"64M", NULL, NULL, NULL, 0}, + {MEMPOOL_END, NULL, NULL, NULL, 0} +}; +#else +/* + * mempool per thread; no lock is needed + */ +#define MAX_MEMPOOL 16 +#define MEMPOOL_END 0 +struct mempool { + const char *mempool_name; + struct mempool_object *mempool_head; + mempool_cleanup_callback mempool_cleanup_fn; + unsigned long mempool_count; +}; + +char *mempool_names[] = +{ + "2K", "4K", "8K", "16K", + "32K", "64K", "128K", "256K", + "512K", "1M", "2M", "4M", + "8M", "16M", "32M", "64M" +}; +#endif + +static PRUintn mempool_index; /* thread private index used to store mempool + in NSPR ThreadPrivateIndex */ +static void mempool_destroy(); + +/* + * mempool_init creates NSPR thread private index, + * then allocates per-thread-private. + * mempool is initialized at the first mempool_return + */ +static void +mempool_init(struct mempool **my_mempool) +{ + int i; + if (NULL == my_mempool) { + return; + } +#ifdef SHARED_MEMPOOL + for (i = 0; MEMPOOL_END != mempool[i].mempool_name; i++) { + mempool[i].mempool_mutex = PR_NewLock(); + if (NULL == mempool[i].mempool_mutex) { + PRErrorCode ec = PR_GetError(); + slapi_log_error (SLAPI_LOG_FATAL, "mempool", "mempool_init: " + "failed to create mutex - (%d - %s); mempool(%s) is disabled", + ec, slapd_pr_strerror(ec), mempool[i].mempool_name); + rc = LDAP_OPERATIONS_ERROR; + } + } +#else + PR_NewThreadPrivateIndex (&mempool_index, mempool_destroy); + *my_mempool = (struct mempool *)slapi_ch_calloc(MAX_MEMPOOL, sizeof(struct mempool)); + for (i = 0; i < MAX_MEMPOOL; i++) { + (*my_mempool)[i].mempool_name = mempool_names[i]; + } +#endif +} + +/* + * mempool_destroy is a callback which is set to NSPR ThreadPrivateIndex + */ +static void +mempool_destroy() +{ + int i = 0; + struct mempool *my_mempool; +#ifdef SHARED_MEMPOOL + for (i = 0; MEMPOOL_END != mempool[i].mempool_name; i++) { + struct mempool_object *object = NULL; + if (NULL == mempool[i].mempool_mutex) { + /* mutex is NULL; this mempool is not enabled */ + continue; + } + object = mempool[i].mempool_head; + mempool[i].mempool_head = NULL; + while (NULL != object) { + struct mempool_object *next = object->mempool_next; + if (NULL != mempool[i].mempool_cleanup_fn) { + (mempool[i].mempool_cleanup_fn)((void *)object); + } + slapi_ch_free((void **)&object); + object = next; + } + PR_DestroyLock(mempool[i].mempool_mutex); + mempool[i].mempool_mutex = NULL; + } +#else + my_mempool = (struct mempool *)PR_GetThreadPrivate(mempool_index); + if (NULL == my_mempool || my_mempool[0].mempool_name != mempool_names[0]) { + /* mempool is not initialized */ + return; + } + for (i = 0; i < MAX_MEMPOOL; i++) { + struct mempool_object *object = my_mempool[i].mempool_head; + while (NULL != object) { + struct mempool_object *next = object->mempool_next; + if (NULL != my_mempool[i].mempool_cleanup_fn) { + (my_mempool[i].mempool_cleanup_fn)((void *)object); + } + slapi_ch_free((void **)&object); + object = next; + } + my_mempool[i].mempool_head = NULL; + my_mempool[i].mempool_count = 0; + } + slapi_ch_free((void **)&my_mempool); + PR_SetThreadPrivate (mempool_index, (void *)NULL); +#endif +} + +/* + * return memory to memory pool + * (Callback cleanup function was intented to release nested memory in the + * memory area. Initially, memory had its structure which could point + * other memory area. But the current code (#else) expects no structure. + * Thus, the cleanup callback is not needed) + * The current code (#else) uses the memory pool stored in the + * per-thread-private data. + */ +int +mempool_return(int type, void *object, mempool_cleanup_callback cleanup) +{ + PR_ASSERT(type >= 0 && type < MEMPOOL_END); + + if (!config_get_mempool_switch()) { + return LDAP_SUCCESS; /* memory pool: off */ + } +#ifdef SHARED_MEMPOOL + if (NULL == mempool[type].mempool_mutex) { + /* mutex is NULL; this mempool is not enabled */ + return LDAP_SUCCESS; + } + PR_Lock(mempool[type].mempool_mutex); + ((struct mempool_object *)object)->mempool_next = mempool[type].mempool_head; + mempool[type].mempool_head = (struct mempool_object *)object; + mempool[type].mempool_cleanup_fn = cleanup; + mempool[type].mempool_count++; + PR_Unlock(mempool[type].mempool_mutex); + return LDAP_SUCCESS; +#else + { + struct mempool *my_mempool; + int maxfreelist; + my_mempool = (struct mempool *)PR_GetThreadPrivate(mempool_index); + if (NULL == my_mempool || my_mempool[0].mempool_name != mempool_names[0]) { + /* mempool is not initialized */ + mempool_init(&my_mempool); + } + ((struct mempool_object *)object)->mempool_next = my_mempool[type].mempool_head; + maxfreelist = config_get_mempool_maxfreelist(); + if ((maxfreelist > 0) && (my_mempool[type].mempool_count > maxfreelist)) { + return LDAP_UNWILLING_TO_PERFORM; + } else { + my_mempool[type].mempool_head = (struct mempool_object *)object; + my_mempool[type].mempool_cleanup_fn = cleanup; + my_mempool[type].mempool_count++; + PR_SetThreadPrivate (mempool_index, (void *)my_mempool); + return LDAP_SUCCESS; + } + } +#endif +} + +/* + * get memory from memory pool + * The current code (#else) uses the memory pool stored in the + * per-thread-private data. + */ +void * +mempool_get(int type) +{ + struct mempool_object *object = NULL; + struct mempool *my_mempool; + PR_ASSERT(type >= 0 && type < MEMPOOL_END); + + if (!config_get_mempool_switch()) { + return NULL; /* memory pool: off */ + } +#ifdef SHARED_MEMPOOL + if (NULL == mempool[type].mempool_mutex) { + /* mutex is NULL; this mempool is not enabled */ + return NULL; + } + + PR_Lock(mempool[type].mempool_mutex); + object = mempool[type].mempool_head; + if (NULL != object) { + mempool[type].mempool_head = object->mempool_next; + mempool[type].mempool_count--; + object->mempool_next = NULL; + } + PR_Unlock(mempool[type].mempool_mutex); +#else + my_mempool = (struct mempool *)PR_GetThreadPrivate(mempool_index); + if (NULL == my_mempool || my_mempool[0].mempool_name != mempool_names[0]) { /* mempool is not initialized */ + return NULL; + } + + object = my_mempool[type].mempool_head; + if (NULL != object) { + my_mempool[type].mempool_head = object->mempool_next; + my_mempool[type].mempool_count--; + object->mempool_next = NULL; + PR_SetThreadPrivate (mempool_index, (void *)my_mempool); + } +#endif + return object; +} + +/***************************************************************************** + * The rest is slapi_ch_malloc and its friends, which are adjusted to mempool. + * The challenge is mempool_return needs to know the size of the memory, but + * free does not pass the info. To work around it, malloc allocates the extra + * space in front of the memory to be returned and store the size in the extra + * space. + * + * Also, to simplify the code, it allocates the smallest 2^n size which + * could store the requested size. We should make the granurality higher for + * the real use. + * + * Above 64MB, the functions call mmap directly. The reason + * why I chose mmap over mempool is in mempool, the memory stays until the + * server is shutdown even if the memory is never be requested. By using mmap, + * the memory is returned to the system and it's guaranteed to shrink the + * process size. + * + * In this implementation, it changes the behavior based on the requested + * size (+ size space -- unsigned long)* : + * 1B ~ 1KB: call system *alloc/free; but still it needs to store the size to + * support realloc. The function needs to know if the passed address + * is the real address or shifted for the size. + * 1KB + 1B ~ 64MB: use mempool + * 64MB + 1B ~ : call mmap + */ +#include <sys/mman.h> +static int slapi_ch_munmap_no_roundup(void **start, unsigned long len); +char *slapi_ch_mmap(unsigned long len); + +static int counters_created= 0; +PR_DEFINE_COUNTER(slapi_ch_counter_malloc); +PR_DEFINE_COUNTER(slapi_ch_counter_calloc); +PR_DEFINE_COUNTER(slapi_ch_counter_realloc); +PR_DEFINE_COUNTER(slapi_ch_counter_strdup); +PR_DEFINE_COUNTER(slapi_ch_counter_free); +PR_DEFINE_COUNTER(slapi_ch_counter_created); +PR_DEFINE_COUNTER(slapi_ch_counter_exist); + +#define OOM_PREALLOC_SIZE 65536 +static void *oom_emergency_area = NULL; +static PRLock *oom_emergency_lock = NULL; + +#define SLAPD_MODULE "memory allocator" + +static const char* const oom_advice = + "\nThe server has probably allocated all available virtual memory. To solve\n" + "this problem, make more virtual memory available to your server, or reduce\n" + "one or more of the following server configuration settings:\n" + " nsslapd-cachesize (Database Settings - Maximum entries in cache)\n" + " nsslapd-cachememsize (Database Settings - Memory available for cache)\n" + " nsslapd-dbcachesize (LDBM Plug-in Settings - Maximum cache size)\n" + " nsslapd-import-cachesize (LDBM Plug-in Settings - Import cache size).\n" + "Can't recover; calling exit(1).\n"; + +static void +create_counters() +{ + PR_CREATE_COUNTER(slapi_ch_counter_malloc,"slapi_ch","malloc",""); + PR_CREATE_COUNTER(slapi_ch_counter_calloc,"slapi_ch","calloc",""); + PR_CREATE_COUNTER(slapi_ch_counter_realloc,"slapi_ch","realloc",""); + PR_CREATE_COUNTER(slapi_ch_counter_strdup,"slapi_ch","strdup",""); + PR_CREATE_COUNTER(slapi_ch_counter_free,"slapi_ch","free",""); + PR_CREATE_COUNTER(slapi_ch_counter_created,"slapi_ch","created",""); + PR_CREATE_COUNTER(slapi_ch_counter_exist,"slapi_ch","exist",""); + + /* ensure that we have space to allow for shutdown calls to malloc() + * from should we run out of memory. + */ + if (oom_emergency_area == NULL) { + oom_emergency_area = malloc(OOM_PREALLOC_SIZE); + } + oom_emergency_lock = PR_NewLock(); +} + +static void +log_negative_alloc_msg( const char *op, const char *units, unsigned long size ) +{ + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "cannot %s %lu %s;\n" + "trying to allocate 0 or a negative number of %s is not portable and\n" + "gives different results on different platforms.\n", + op, size, units, units ); +} + +static char * +slapi_ch_malloc_core( unsigned long lsize ) +{ + char *newmem; + + if ( (newmem = (char *) malloc( lsize )) == NULL ) { + int oserr = errno; + + oom_occurred(); + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "malloc of %lu bytes failed; OS error %d (%s)%s\n", + lsize, oserr, slapd_system_strerror( oserr ), oom_advice ); + exit( 1 ); + } + *(unsigned long *)newmem = lsize; + newmem += sizeof(unsigned long); + + return newmem; +} + +char * +slapi_ch_malloc( unsigned long size ) +{ + char *newmem; + unsigned long lsize; + + if (size <= 0) { + log_negative_alloc_msg( "malloc", "bytes", size ); + return 0; + } + + lsize = size + sizeof(unsigned long); + if (lsize <= 1024) { + newmem = slapi_ch_malloc_core( lsize ); + } else if (lsize <= 67108864) { + /* return 2KB ~ 64MB memory to memory pool */ + unsigned long roundup = 1; + int n = 0; + while (1) { + roundup <<= 1; + n++; + if (roundup >= lsize) { + break; + } + } + PR_ASSERT(n >= 11 && n <= 26); + newmem = (char *)mempool_get(n-11); /* 11: 2^11 = 2K */ + if (NULL == newmem) { + newmem = slapi_ch_malloc_core( roundup ); + } + } else { + newmem = slapi_ch_mmap( size ); + } + + if(!counters_created) + { + create_counters(); + counters_created= 1; + } + PR_INCREMENT_COUNTER(slapi_ch_counter_malloc); + PR_INCREMENT_COUNTER(slapi_ch_counter_created); + PR_INCREMENT_COUNTER(slapi_ch_counter_exist); +#if defined(_WIN32) && defined(DEBUG) + if(recording) + { + add_memory_record(newmem,size); + } +#endif + + return( newmem ); +} + +static char * +slapi_ch_realloc_core( char *block, unsigned long lsize ) +{ + char *realblock; + char *newmem; + + realblock = block - sizeof(unsigned long); + if ( (newmem = (char *) realloc( realblock, lsize )) == NULL ) { + int oserr = errno; + + oom_occurred(); + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "realloc of %lu bytes failed; OS error %d (%s)%s\n", + lsize, oserr, slapd_system_strerror( oserr ), oom_advice ); + exit( 1 ); + } + *(unsigned long *)newmem = lsize; + newmem += sizeof(unsigned long); + + return newmem; +} + +char * +slapi_ch_realloc( char *block, unsigned long size ) +{ + char *newmem; + unsigned long lsize; + unsigned long origsize; + char *realblock; + char *realnewmem; + + if ( block == NULL ) { + return( slapi_ch_malloc( size ) ); + } + + if (size <= 0) { + log_negative_alloc_msg( "realloc", "bytes", size ); + return block; + } + + lsize = size + sizeof(unsigned long); + if (lsize <= 1024) { + newmem = slapi_ch_realloc_core( block, lsize ); + } else if (lsize <= 67108864) { + /* return 2KB ~ 64MB memory to memory pool */ + unsigned long roundup = 1; + int n = 0; + while (1) { + roundup <<= 1; + n++; + if (roundup >= lsize) { + break; + } + } + PR_ASSERT(n >= 11 && n <= 26); + newmem = (char *)mempool_get(n-11); /* 11: 2^11 = 2K */ + if (NULL == newmem) { + newmem = slapi_ch_realloc_core( block, roundup ); + } else { + realblock = block - sizeof(unsigned long); + origsize = *(unsigned long *)realblock - sizeof(unsigned long);; + memcpy(newmem, block, origsize); + slapi_ch_free_string(&block); + } + } else { + realblock = block - sizeof(unsigned long); + origsize = *(unsigned long *)realblock - sizeof(unsigned long);; + newmem = slapi_ch_mmap( size ); + memcpy(newmem, block, origsize); + realnewmem = newmem - sizeof(unsigned long); + *(unsigned long *)realnewmem = lsize; + slapi_ch_free_string(&block); + } + if(!counters_created) + { + create_counters(); + counters_created= 1; + } + PR_INCREMENT_COUNTER(slapi_ch_counter_realloc); +#if defined(_WIN32) && defined(DEBUG) + if(recording) + { + remove_memory_record(block); + add_memory_record(newmem,size); + } +#endif + + return( newmem ); +} + +static char * +slapi_ch_calloc_core( unsigned long lsize ) +{ + char *newmem; + + if ( (newmem = (char *) calloc( 1, lsize )) == NULL ) { + int oserr = errno; + + oom_occurred(); + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "calloc of %lu bytes failed; OS error %d (%s)%s\n", + lsize, oserr, slapd_system_strerror( oserr ), oom_advice ); + exit( 1 ); + } + *(unsigned long *)newmem = lsize; + newmem += sizeof(unsigned long); + + return newmem; +} + +char * +slapi_ch_calloc( unsigned long nelem, unsigned long size ) +{ + char *newmem; + unsigned long lsize; + + if (size <= 0) { + log_negative_alloc_msg( "calloc", "bytes", size ); + return 0; + } + + if (nelem <= 0) { + log_negative_alloc_msg( "calloc", "elements", nelem ); + return 0; + } + + lsize = nelem * size + sizeof(unsigned long); + if (lsize <= 1024) { + newmem = slapi_ch_calloc_core( lsize ); + } else if (lsize <= 67108864) { + /* return 2KB ~ 64MB memory to memory pool */ + unsigned long roundup = 1; + int n = 0; + while (1) { + roundup <<= 1; + n++; + if (roundup >= lsize) { + break; + } + } + PR_ASSERT(n >= 11 && n <= 26); + newmem = (char *)mempool_get(n-11); /* 11: 2^11 = 2K */ + if (NULL == newmem) { + newmem = slapi_ch_calloc_core( roundup ); + } else { + memset (newmem, 0, size * nelem); + } + } else { + unsigned long mysize = size * nelem; + newmem = slapi_ch_mmap( mysize ); + memset(newmem, 0, mysize); + } + if(!counters_created) + { + create_counters(); + counters_created= 1; + } + PR_INCREMENT_COUNTER(slapi_ch_counter_calloc); + PR_INCREMENT_COUNTER(slapi_ch_counter_created); + PR_INCREMENT_COUNTER(slapi_ch_counter_exist); +#if defined(_WIN32) && defined(DEBUG) + if(recording) + { + add_memory_record(newmem,size); + } +#endif + return( newmem ); +} + +char * +slapi_ch_strdup ( const char* s1 ) +{ + char* newmem; + unsigned long lsize; + + /* strdup pukes on NULL strings...bail out now */ + if(NULL == s1) + return NULL; + + lsize = strlen(s1) + sizeof(unsigned long) + 1; + newmem = slapi_ch_malloc( lsize ); + sprintf(newmem, "%s", s1); + + if(!counters_created) + { + create_counters(); + counters_created= 1; + } + PR_INCREMENT_COUNTER(slapi_ch_counter_strdup); + PR_INCREMENT_COUNTER(slapi_ch_counter_created); + PR_INCREMENT_COUNTER(slapi_ch_counter_exist); +#if defined(_WIN32) && defined(DEBUG) + if(recording) + { + add_memory_record(newmem,strlen(s1)+1); + } +#endif + return newmem; +} + +/* + * Function: slapi_ch_free + * + * Returns: nothing + * + * Description: frees the pointer, and then sets it to NULL to + * prevent free-memory writes. + * Note: pass in the address of the pointer you want to free. + * Note: you can pass in null pointers, it's cool. + * + * Implementation: get the size from the size space, and determine the behavior + * based upon the size: + * 1B ~ 1KB: call system free + * 1KB + 1B ~ 64MB: return memory to mempool + * 64MB + 1B ~ : call munmap + */ +void +slapi_ch_free(void **ptr) +{ + void *realptr; + unsigned long size; + + if (ptr==NULL || *ptr == NULL){ + return; + } + +#if defined(_WIN32) && defined(DEBUG) + if(recording) + { + remove_memory_record(*ptr); + } +#endif + realptr = (void *)((char *)*ptr - sizeof(unsigned long)); + size = *(unsigned long *)realptr; + if (size <= 1024) { + free (realptr); + } else if (size <= 67108864) { + /* return 2KB ~ 64MB memory to memory pool */ + unsigned long roundup = 1; + int n = 0; + int rc = LDAP_SUCCESS; + while (1) { + roundup <<= 1; + n++; + if (roundup >= size) { + break; + } + } + PR_ASSERT(n >= 11 && n <= 26); + rc = mempool_return(n-11, *ptr, (mempool_cleanup_callback)NULL); + if (LDAP_SUCCESS != rc) { + free (realptr); + } + } else { + slapi_ch_munmap_no_roundup( ptr, size ); + } + *ptr = NULL; + + if(!counters_created) + { + create_counters(); + counters_created= 1; + } + PR_INCREMENT_COUNTER(slapi_ch_counter_free); + PR_DECREMENT_COUNTER(slapi_ch_counter_exist); + return; +} + +char * +slapi_ch_mmap(unsigned long len) +{ + char *newmem; + long sc_page_size = config_get_system_page_size(); + int sc_page_bits = config_get_system_page_bits(); + unsigned long roundup = (len&(sc_page_size-1))?(((len>>sc_page_bits)+1)<<sc_page_bits):len; + if ( (newmem = (char *)mmap(NULL, roundup, PROT_READ | PROT_WRITE, + MAP_PRIVATE | MAP_ANONYMOUS, -1, 0/*ignored */)) == MAP_FAILED ) { + int oserr = errno; + + oom_occurred(); + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "mmap of %lu bytes failed; OS error %d (%s)%s\n", + roundup, oserr, slapd_system_strerror( oserr ), oom_advice ); + exit( 1 ); + } + *(unsigned long *)newmem = roundup; + newmem += sizeof(unsigned long); + return( newmem ); +} + +int +slapi_ch_munmap(void **start, unsigned long len) +{ + long sc_page_size = config_get_system_page_size(); + int sc_page_bits = config_get_system_page_bits(); + unsigned long roundup = (len&(sc_page_size-1))?(((len>>sc_page_bits)+1)<<sc_page_bits):len; + void *realstart = *start - sizeof(unsigned long); + int rc = munmap(realstart, roundup); + if (0 != rc) { + int oserr = errno; + + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "munmap of %lu bytes failed; OS error %d (%s)\n", + roundup, oserr, slapd_system_strerror( oserr ) ); + /* Leaked. This should not happen */ + } + *start = NULL; + return rc; +} + +static char * +slapi_ch_mmap_no_roundup( unsigned long size) +{ + char *newmem; + unsigned long mysize; + + if ( (newmem = (char *)mmap(NULL, size + sizeof(unsigned long), + PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, + -1, 0/*ignored */)) == MAP_FAILED ) { + int oserr = errno; + + oom_occurred(); + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "mmap of %lu bytes failed; OS error %d (%s)%s\n", + size + sizeof(unsigned long), oserr, + slapd_system_strerror( oserr ), oom_advice ); + exit( 1 ); + } + *(unsigned long *)newmem = size; + newmem += sizeof(unsigned long); + + return newmem; +} + +static int +slapi_ch_munmap_no_roundup(void **start, unsigned long len) +{ + void *realstart = *start - sizeof(unsigned long); + int reallen = len + sizeof(unsigned long); + int rc = munmap(realstart, reallen); + if (0 != rc) { + int oserr = errno; + + slapi_log_error( SLAPI_LOG_FATAL, SLAPD_MODULE, + "munmap of %lu bytes failed; OS error %d (%s)\n", + len, oserr, slapd_system_strerror( oserr ) ); + /* Leaked. This should not happen */ + } + *start = NULL; + return rc; +} + +/* + This function is just like PR_smprintf. It works like sprintf + except that it allocates enough memory to hold the result + string and returns that allocated memory to the caller. The + caller must use slapi_ch_free_string to free the memory. + It should only be used in those situations that will eventually free + the memory using slapi_ch_free_string e.g. allocating a string + that will be freed as part of pblock cleanup, or passed in to create + a Slapi_DN, or things of that nature. If you have control of the + flow such that the memory will be allocated and freed in the same + scope, better to just use PR_smprintf and PR_smprintf_free instead + because it is likely faster. +*/ +/* + This implementation is the same as PR_smprintf. + The above comment does not apply to this function for now. + see [150809] for more details. + WARNING - with this fix, this means we are now mixing PR_Malloc with + slapi_ch_free. Which is ok for now - they both use malloc/free from + the operating system. But if this changes in the future, this + function will have to change as well. +*/ +char * +slapi_ch_smprintf(const char *fmt, ...) +{ + char *p = NULL, *q = NULL; + va_list ap; + + if (NULL == fmt) { + return NULL; + } + + va_start(ap, fmt); + p = PR_vsmprintf(fmt, ap); + va_end(ap); + + q = slapi_ch_strdup (p); /* ugly ...; hope there's any better way */ + free(p); + + return q; +} +#endif /* MEMPOOL_EXPERIMENTAL */ diff --git a/ldap/servers/slapd/operation.c b/ldap/servers/slapd/operation.c index 39dffdbc..ed8cbd88 100644 --- a/ldap/servers/slapd/operation.c +++ b/ldap/servers/slapd/operation.c @@ -170,7 +170,7 @@ operation_free( Slapi_Operation **op, Connection *conn ) factory_destroy_extension(get_operation_object_type(),*op,conn,&((*op)->o_extension)); slapi_sdn_done(&(*op)->o_sdn); slapi_sdn_free(&(*op)->o_target_spec); - free( (*op)->o_authtype ); + slapi_ch_free_string( &(*op)->o_authtype ); if ( (*op)->o_searchattrs != NULL ) { cool_charray_free( (*op)->o_searchattrs ); } diff --git a/ldap/servers/slapd/proto-slap.h b/ldap/servers/slapd/proto-slap.h index eb0d0380..881667e6 100644 --- a/ldap/servers/slapd/proto-slap.h +++ b/ldap/servers/slapd/proto-slap.h @@ -346,6 +346,11 @@ int config_set_maxdescriptors( const char *attrname, char *value, char *errorbuf int config_set_localuser( const char *attrname, char *value, char *errorbuf, int apply ); #endif /* !_WIN32 */ +#ifdef MEMPOOL_EXPERIMENTAL +int config_set_mempool_switch( const char *attrname, char *value, char *errorbuf, int apply ); +int config_set_mempool_maxfreelist( const char *attrname, char *value, char *errorbuf, int apply ); +#endif /* MEMPOOL_EXPERIMENTAL */ + int config_get_SSLclientAuth(); int config_get_ssl_check_hostname(); char *config_get_SSL3ciphers(); @@ -451,6 +456,13 @@ int config_get_hash_filters(); int config_get_rewrite_rfc1274(); int config_get_outbound_ldap_io_timeout(void); int config_get_csnlogging(); +#ifdef MEMPOOL_EXPERIMENTAL +int config_get_mempool_switch(); +int config_get_mempool_maxfreelist(); +long config_get_system_page_size(); +int config_get_system_page_bits(); +#endif + int is_abspath(const char *); char* rel2abspath( char * ); char* rel2abspath_ext( char *, char * ); diff --git a/ldap/servers/slapd/rwlock.c b/ldap/servers/slapd/rwlock.c index abd55ef1..e210145d 100644 --- a/ldap/servers/slapd/rwlock.c +++ b/ldap/servers/slapd/rwlock.c @@ -193,23 +193,21 @@ rwl_new() { rwl *rp; - if (( rp = (rwl *)malloc( sizeof( rwl ))) == NULL ) { - return NULL; - } + rp = (rwl *)slapi_ch_malloc( sizeof( rwl )); if (( rp->rwl_readers_mutex = PR_NewLock()) == NULL ) { - free( rp ); + slapi_ch_free( (void **)&rp ); return NULL; } if (( rp->rwl_writers_mutex = PR_NewLock()) == NULL ) { PR_DestroyLock( rp->rwl_readers_mutex ); - free( rp ); + slapi_ch_free( (void **)&rp ); return NULL; } if (( rp->rwl_writer_waiting_cv = PR_NewCondVar( rp->rwl_readers_mutex )) == NULL ) { PR_DestroyLock( rp->rwl_readers_mutex ); PR_DestroyLock( rp->rwl_writers_mutex ); - free( rp ); + slapi_ch_free( (void **)&rp ); } rp->rwl_num_readers = rp->rwl_writer_waiting = 0; @@ -254,6 +252,6 @@ rwl_free( rwl **rh ) PR_DestroyCondVar( rp->rwl_writer_waiting_cv ); } memset( rp, '\0', sizeof( rwl )); - free( rp ); + slapi_ch_free( (void **)&rp ); *rh = NULL; } diff --git a/ldap/servers/slapd/slap.h b/ldap/servers/slapd/slap.h index dea64a2f..abccf3ad 100644 --- a/ldap/servers/slapd/slap.h +++ b/ldap/servers/slapd/slap.h @@ -1769,6 +1769,11 @@ typedef struct _slapdEntryPoints { #define CONFIG_HASH_FILTERS_ATTRIBUTE "nsslapd-hash-filters" #define CONFIG_OUTBOUND_LDAP_IO_TIMEOUT_ATTRIBUTE "nsslapd-outbound-ldap-io-timeout" +#ifdef MEMPOOL_EXPERIMENTAL +#define CONFIG_MEMPOOL_SWITCH_ATTRIBUTE "nsslapd-mempool" +#define CONFIG_MEMPOOL_MAXFREELIST_ATTRIBUTE "nsslapd-mempool-maxfreelist" +#endif /* MEMPOOL_EXPERIMENTAL */ + /* flag used to indicate that the change to the config parameter should be saved */ #define CONFIG_APPLY 1 @@ -1960,6 +1965,12 @@ typedef struct _slapdFrontendConfig { #ifndef _WIN32 struct passwd *localuserinfo; /* userinfo of localuser */ #endif /* _WIN32 */ +#ifdef MEMPOOL_EXPERIMENTAL + int mempool_switch; /* switch to turn memory pool on/off */ + int mempool_maxfreelist; /* max free list length per memory pool item */ + long system_page_size; /* system page size */ + int system_page_bits; /* bit count to shift the system page size */ +#endif /* MEMPOOL_EXPERIMENTAL */ } slapdFrontendConfig_t; #define SLAPD_FULL 0 diff --git a/ldap/servers/slapd/slapi2nspr.c b/ldap/servers/slapd/slapi2nspr.c index d5d583dc..ebe2e451 100644 --- a/ldap/servers/slapd/slapi2nspr.c +++ b/ldap/servers/slapd/slapi2nspr.c @@ -214,6 +214,12 @@ slapi_notify_condvar( Slapi_CondVar *cvar, int notify_all ) return( prrc == PR_SUCCESS ? 1 : 0 ); } +#ifdef MEMPOOL_EXPERIMENTAL +void _free_wrapper(void *ptr) +{ + slapi_ch_free(&ptr); +} +#endif /* * Function: slapi_ldap_init() @@ -239,18 +245,40 @@ slapi_ldap_init( char *ldaphost, int ldapport, int secure, int shared ) * Note that ldapssl_init() uses libprldap implicitly. */ +#ifdef MEMPOOL_EXPERIMENTAL + { + /* + * slapi_ch_malloc functions need to be set to LDAP C SDK + */ + struct ldap_memalloc_fns memalloc_fns; + memalloc_fns.ldapmem_malloc = (LDAP_MALLOC_CALLBACK *)slapi_ch_malloc; + memalloc_fns.ldapmem_calloc = (LDAP_CALLOC_CALLBACK *)slapi_ch_calloc; + memalloc_fns.ldapmem_realloc = (LDAP_REALLOC_CALLBACK *)slapi_ch_realloc; + memalloc_fns.ldapmem_free = (LDAP_FREE_CALLBACK *)_free_wrapper; + } + /* + * MEMPOOL_EXPERIMENTAL: + * These LDAP C SDK init function needs to be revisited. + * In ldap_init called via ldapssl_init and prldap_init initializes + * options and set default values including memalloc_fns, then it + * initializes as sasl client by calling sasl_client_init. In + * sasl_client_init, it creates mechlist using the malloc function + * available at the moment which could mismatch the malloc/free functions + * set later. + */ +#endif if ( secure ) { ld = ldapssl_init( ldaphost, ldapport, secure ); } else { ld = prldap_init( ldaphost, ldapport, shared ); } - /* Update snmp interaction table */ - if ( ld == NULL) { - set_snmp_interaction_row( ldaphost, ldapport, -1); - } else { - set_snmp_interaction_row( ldaphost, ldapport, 0); - } + /* Update snmp interaction table */ + if ( ld == NULL) { + set_snmp_interaction_row( ldaphost, ldapport, -1); + } else { + set_snmp_interaction_row( ldaphost, ldapport, 0); + } if ( ld != NULL ) { /* diff --git a/ldap/servers/slapd/tools/pwenc.c b/ldap/servers/slapd/tools/pwenc.c index d18622eb..dba107a3 100644 --- a/ldap/servers/slapd/tools/pwenc.c +++ b/ldap/servers/slapd/tools/pwenc.c @@ -105,7 +105,7 @@ decode( char *orig ) if ( NULL == orig ) { return NULL; } - r = calloc( 1, strlen( orig ) + 2 ); + r = slapi_ch_calloc( 1, strlen( orig ) + 2 ); strcpy( r, orig ); if ( heflag ) { @@ -282,7 +282,7 @@ main( argc, argv ) } puts( enc ); - free( enc ); + slapi_ch_free_string( &enc ); } else { /* compare passwords */ if (( rc = (*(cmppwsp->pws_cmp))( decode( argv[ optind ]), cmp )) == 0 ) { printf( "%s: password ok.\n", name ); |