1 /* ldbm.c - ldap dbm compatibility routines */
3 /* Patched for Berkeley DB version 2.0; /KSp; 98/02/23
5 * - DB version 2.6.4b ; 1998/12/28, /KSp
6 * - DB_DBT_MALLOC ; 1998/03/22, /KSp
7 * - basic implementation; 1998/02/23, /KSp
18 #include <ac/string.h>
23 #if defined( LDBM_USE_DBHASH ) || defined( LDBM_USE_DBBTREE )
25 /*****************************************************************
27 * use berkeley db hash or btree package *
29 *****************************************************************/
31 #ifdef HAVE_BERKELEY_DB2
32 /*************************************************
34 * A malloc routine for use with DB_DBT_MALLOC *
36 *************************************************/
39 ldbm_malloc( size_t size )
41 return( calloc( 1, size ));
44 /* a dbEnv for BERKELEYv2 */
49 pthread_mutex_t dbEnvInit_mutex;
52 ldbm_db_errcall( char *prefix, char *message )
55 syslog( LOG_INFO, "ldbm_db_errcall(): %s %s", prefix, message );
63 ldbm_open( char *name, int rw, int mode, int dbcachesize )
67 #ifdef HAVE_BERKELEY_DB2
70 /* initialize an environment for the DB application */
71 pthread_mutex_lock( &dbEnvInit_mutex );
77 int envFlags = DB_CREATE | DB_THREAD;
80 if ( ( dir = strrchr( tmp, '/' )) ) {
91 memset( &dbEnv, 0, sizeof( dbEnv ));
93 dbEnv.db_errcall = ldbm_db_errcall;
94 dbEnv.db_errpfx = "==>";
96 if ( ( err = db_appinit( NULL, NULL, &dbEnv, envFlags )) ) {
99 if ( err < 0 ) sprintf( error, "%ld\n", (long) err );
100 else sprintf( error, "%s\n", strerror( err ));
103 "ldbm_open(): FATAL error in db_appinit(%s) : %s\n",
113 pthread_mutex_unlock( &dbEnvInit_mutex );
115 memset( &dbinfo, 0, sizeof( dbinfo ));
116 dbinfo.db_cachesize = dbcachesize;
117 dbinfo.db_pagesize = DEFAULT_DB_PAGE_SIZE;
118 dbinfo.db_malloc = ldbm_malloc;
120 (void) db_open( name, DB_TYPE, rw, mode, &dbEnv, &dbinfo, &ret );
127 if ( DB_TYPE == DB_HASH ) {
128 memset( (char *) &hinfo, '\0', sizeof(hinfo) );
129 hinfo.cachesize = dbcachesize;
131 } else if ( DB_TYPE == DB_BTREE ) {
132 memset( (char *) &binfo, '\0', sizeof(binfo) );
133 binfo.cachesize = dbcachesize;
139 ret = dbopen( name, rw, mode, DB_TYPE, info );
147 ldbm_close( LDBM ldbm )
149 #ifdef HAVE_BERKELEY_DB2
150 (*ldbm->close)( ldbm, 0 );
152 (*ldbm->close)( ldbm );
157 ldbm_sync( LDBM ldbm )
159 (*ldbm->sync)( ldbm, 0 );
163 ldbm_datum_free( LDBM ldbm, Datum data )
169 ldbm_datum_dup( LDBM ldbm, Datum data )
173 ldbm_datum_init( dup );
175 if ( data.dsize == 0 ) {
178 dup.dsize = data.dsize;
179 if ( dup.dptr = (char *) malloc( data.dsize ) )
180 memcpy( dup.dptr, data.dptr, data.dsize );
186 ldbm_fetch( LDBM ldbm, Datum key )
191 #ifdef HAVE_BERKELEY_DB2
192 ldbm_datum_init( data );
194 data.flags = DB_DBT_MALLOC;
196 if ( (rc = (*ldbm->get)( ldbm, NULL, &key, &data, 0 )) != 0 ) {
197 if ( data.dptr ) free( data.dptr );
199 if ( (rc = (*ldbm->get)( ldbm, &key, &data, 0 )) == 0 ) {
200 data = ldbm_datum_dup( ldbm, data );
211 ldbm_store( LDBM ldbm, Datum key, Datum data, int flags )
215 #ifdef HAVE_BERKELEY_DB2
216 rc = (*ldbm->put)( ldbm, NULL, &key, &data, flags & ~LDBM_SYNC );
219 rc = (*ldbm->put)( ldbm, &key, &data, flags & ~LDBM_SYNC );
222 if ( flags & LDBM_SYNC )
223 (*ldbm->sync)( ldbm, 0 );
228 ldbm_delete( LDBM ldbm, Datum key )
232 #ifdef HAVE_BERKELEY_DB2
233 rc = (*ldbm->del)( ldbm, NULL, &key, 0 );
236 rc = (*ldbm->del)( ldbm, &key, 0 );
238 (*ldbm->sync)( ldbm, 0 );
243 #ifdef HAVE_BERKELEY_DB2
244 ldbm_firstkey( LDBM ldbm, DBC **dbch )
246 ldbm_firstkey( LDBM ldbm )
252 #ifdef HAVE_BERKELEY_DB2
255 ldbm_datum_init( key );
256 ldbm_datum_init( data );
258 key.flags = data.flags = DB_DBT_MALLOC;
260 /* acquire a cursor for the DB */
262 # if defined( DB_VERSION_MAJOR ) && defined( DB_VERSION_MINOR ) && \
263 DB_VERSION_MAJOR == 2 && DB_VERSION_MINOR < 6
265 if ( (*ldbm->cursor)( ldbm, NULL, &dbci )) {
269 if ( (*ldbm->cursor)( ldbm, NULL, &dbci, 0 )) {
276 if ( (*dbci->c_get)( dbci, &key, &data, DB_NEXT ) == 0 ) {
277 if ( data.dptr ) free( data.dptr );
279 if ( (rc = (*ldbm->seq)( ldbm, &key, &data, R_FIRST )) == 0 ) {
280 key = ldbm_datum_dup( ldbm, key );
287 #ifdef HAVE_BERKELEY_DB2
295 #ifdef HAVE_BERKELEY_DB2
296 ldbm_nextkey( LDBM ldbm, Datum key, DBC *dbcp )
298 ldbm_nextkey( LDBM ldbm, Datum key )
304 #ifdef HAVE_BERKELEY_DB2
305 void *oldKey = key.dptr;
307 ldbm_datum_init( data );
309 data.flags = DB_DBT_MALLOC;
311 if ( (*dbcp->c_get)( dbcp, &key, &data, DB_NEXT ) == 0 ) {
312 if ( data.dptr ) free( data.dptr );
314 if ( (rc = (*ldbm->seq)( ldbm, &key, &data, R_NEXT )) == 0 ) {
315 key = ldbm_datum_dup( ldbm, key );
321 #ifdef HAVE_BERKELEY_DB2
322 if ( oldKey ) free( oldKey );
329 ldbm_errno( LDBM ldbm )
334 #elif defined( HAVE_GDBM )
336 #include <sys/stat.h>
338 /*****************************************************************
342 *****************************************************************/
345 ldbm_open( char *name, int rw, int mode, int dbcachesize )
350 if ( (db = gdbm_open( name, 0, rw | GDBM_FAST, mode, 0 )) == NULL ) {
353 if ( dbcachesize > 0 && stat( name, &st ) == 0 ) {
354 dbcachesize = (dbcachesize / st.st_blksize);
355 gdbm_setopt( db, GDBM_CACHESIZE, &dbcachesize, sizeof(int) );
362 ldbm_close( LDBM ldbm )
368 ldbm_sync( LDBM ldbm )
374 ldbm_datum_free( LDBM ldbm, Datum data )
380 ldbm_datum_dup( LDBM ldbm, Datum data )
384 if ( data.dsize == 0 ) {
390 dup.dsize = data.dsize;
391 if ( (dup.dptr = (char *) malloc( data.dsize )) != NULL )
392 memcpy( dup.dptr, data.dptr, data.dsize );
398 ldbm_fetch( LDBM ldbm, Datum key )
400 return( gdbm_fetch( ldbm, key ) );
404 ldbm_store( LDBM ldbm, Datum key, Datum data, int flags )
408 rc = gdbm_store( ldbm, key, data, flags & ~LDBM_SYNC );
409 if ( flags & LDBM_SYNC )
415 ldbm_delete( LDBM ldbm, Datum key )
419 rc = gdbm_delete( ldbm, key );
425 ldbm_firstkey( LDBM ldbm )
427 return( gdbm_firstkey( ldbm ) );
431 ldbm_nextkey( LDBM ldbm, Datum key )
433 return( gdbm_nextkey( ldbm, key ) );
437 ldbm_errno( LDBM ldbm )
439 return( (int) gdbm_errno );
442 #elif defined( HAVE_NDBM )
444 /*****************************************************************
446 * if no gdbm, fall back to using ndbm, the standard unix thing *
448 *****************************************************************/
452 ldbm_open( char *name, int rw, int mode, int dbcachesize )
454 return( dbm_open( name, rw, mode ) );
458 ldbm_close( LDBM ldbm )
465 ldbm_sync( LDBM ldbm )
471 ldbm_datum_free( LDBM ldbm, Datum data )
477 ldbm_datum_dup( LDBM ldbm, Datum data )
481 if ( data.dsize == 0 ) {
487 dup.dsize = data.dsize;
488 dup.dptr = (char *) malloc( data.dsize );
490 memcpy( dup.dptr, data.dptr, data.dsize );
496 ldbm_fetch( LDBM ldbm, Datum key )
498 return( ldbm_datum_dup( ldbm, dbm_fetch( ldbm, key ) ) );
502 ldbm_store( LDBM ldbm, Datum key, Datum data, int flags )
504 return( dbm_store( ldbm, key, data, flags ) );
508 ldbm_delete( LDBM ldbm, Datum key )
510 return( dbm_delete( ldbm, key ) );
514 ldbm_firstkey( LDBM ldbm )
516 return( dbm_firstkey( ldbm ) );
520 ldbm_nextkey( LDBM ldbm, Datum key )
522 return( dbm_nextkey( ldbm ) );
526 ldbm_errno( LDBM ldbm )
528 return( dbm_error( ldbm ) );