Back to index

openldap  2.4.31
Defines | Functions | Variables
proto-bdb.h File Reference
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Defines

#define BDB_SYMBOL(x)   LDAP_CONCAT(bdb_,x)
#define BDB_UCTYPE   "BDB"
#define bdb_attr_mask   BDB_SYMBOL(attr_mask)
#define bdb_attr_flush   BDB_SYMBOL(attr_flush)
#define bdb_attr_slot   BDB_SYMBOL(attr_slot)
#define bdb_attr_index_config   BDB_SYMBOL(attr_index_config)
#define bdb_attr_index_destroy   BDB_SYMBOL(attr_index_destroy)
#define bdb_attr_index_free   BDB_SYMBOL(attr_index_free)
#define bdb_attr_index_unparse   BDB_SYMBOL(attr_index_unparse)
#define bdb_attr_info_free   BDB_SYMBOL(attr_info_free)
#define bdb_back_init_cf   BDB_SYMBOL(back_init_cf)
#define bdb_db_cache   BDB_SYMBOL(db_cache)
#define bdb_db_findsize   BDB_SYMBOL(db_findsize)
#define bdb_dn2entry   BDB_SYMBOL(dn2entry)
#define bdb_dn2id   BDB_SYMBOL(dn2id)
#define bdb_dn2id_add   BDB_SYMBOL(dn2id_add)
#define bdb_dn2id_delete   BDB_SYMBOL(dn2id_delete)
#define bdb_dn2id_children   BDB_SYMBOL(dn2id_children)
#define bdb_dn2idl   BDB_SYMBOL(dn2idl)
#define bdb_errcall   BDB_SYMBOL(errcall)
#define bdb_filter_candidates   BDB_SYMBOL(filter_candidates)
#define bdb_id2entry   BDB_SYMBOL(id2entry)
#define bdb_id2entry_add   BDB_SYMBOL(id2entry_add)
#define bdb_id2entry_update   BDB_SYMBOL(id2entry_update)
#define bdb_id2entry_delete   BDB_SYMBOL(id2entry_delete)
#define bdb_entry_free   BDB_SYMBOL(entry_free)
#define bdb_entry_return   BDB_SYMBOL(entry_return)
#define bdb_entry_release   BDB_SYMBOL(entry_release)
#define bdb_entry_get   BDB_SYMBOL(entry_get)
#define bdb_idl_cache_get   BDB_SYMBOL(idl_cache_get)
#define bdb_idl_cache_put   BDB_SYMBOL(idl_cache_put)
#define bdb_idl_cache_del   BDB_SYMBOL(idl_cache_del)
#define bdb_idl_cache_add_id   BDB_SYMBOL(idl_cache_add_id)
#define bdb_idl_cache_del_id   BDB_SYMBOL(idl_cache_del_id)
#define bdb_idl_first   BDB_SYMBOL(idl_first)
#define bdb_idl_next   BDB_SYMBOL(idl_next)
#define bdb_idl_search   BDB_SYMBOL(idl_search)
#define bdb_idl_insert   BDB_SYMBOL(idl_insert)
#define bdb_idl_delete   BDB_SYMBOL(idl_delete)
#define bdb_idl_intersection   BDB_SYMBOL(idl_intersection)
#define bdb_idl_union   BDB_SYMBOL(idl_union)
#define bdb_idl_sort   BDB_SYMBOL(idl_sort)
#define bdb_idl_append   BDB_SYMBOL(idl_append)
#define bdb_idl_append_one   BDB_SYMBOL(idl_append_one)
#define bdb_idl_fetch_key   BDB_SYMBOL(idl_fetch_key)
#define bdb_idl_insert_key   BDB_SYMBOL(idl_insert_key)
#define bdb_idl_delete_key   BDB_SYMBOL(idl_delete_key)
#define bdb_index_mask   BDB_SYMBOL(index_mask)
#define bdb_index_param   BDB_SYMBOL(index_param)
#define bdb_index_values   BDB_SYMBOL(index_values)
#define bdb_index_entry   BDB_SYMBOL(index_entry)
#define bdb_index_recset   BDB_SYMBOL(index_recset)
#define bdb_index_recrun   BDB_SYMBOL(index_recrun)
#define bdb_index_entry_add(op, t, e)   bdb_index_entry((op),(t),SLAP_INDEX_ADD_OP,(e))
#define bdb_index_entry_del(op, t, e)   bdb_index_entry((op),(t),SLAP_INDEX_DELETE_OP,(e))
#define bdb_key_read   BDB_SYMBOL(key_read)
#define bdb_key_change   BDB_SYMBOL(key_change)
#define bdb_next_id   BDB_SYMBOL(next_id)
#define bdb_last_id   BDB_SYMBOL(last_id)
#define bdb_modify_internal   BDB_SYMBOL(modify_internal)
#define bdb_monitor_db_init   BDB_SYMBOL(monitor_db_init)
#define bdb_monitor_db_open   BDB_SYMBOL(monitor_db_open)
#define bdb_monitor_db_close   BDB_SYMBOL(monitor_db_close)
#define bdb_monitor_db_destroy   BDB_SYMBOL(monitor_db_destroy)
#define bdb_cache_entry_db_unlock   BDB_SYMBOL(cache_entry_db_unlock)
#define bdb_cache_return_entry_rw   BDB_SYMBOL(cache_return_entry_rw)
#define bdb_cache_entryinfo_lock(e)   ldap_pvt_thread_mutex_lock( &(e)->bei_kids_mutex )
#define bdb_cache_entryinfo_unlock(e)   ldap_pvt_thread_mutex_unlock( &(e)->bei_kids_mutex )
#define bdb_cache_entryinfo_trylock(e)   ldap_pvt_thread_mutex_trylock( &(e)->bei_kids_mutex )
#define bdb_cache_return_entry_r(bdb, e, l)   bdb_cache_return_entry_rw((bdb), (e), 0, (l))
#define bdb_cache_return_entry_w(bdb, e, l)   bdb_cache_return_entry_rw((bdb), (e), 1, (l))
#define bdb_unlocked_cache_return_entry_rw(a, b, c)   ((void)0)
#define bdb_unlocked_cache_return_entry_r(c, e)   bdb_unlocked_cache_return_entry_rw((c), (e), 0)
#define bdb_unlocked_cache_return_entry_w(c, e)   bdb_unlocked_cache_return_entry_rw((c), (e), 1)
#define bdb_cache_add   BDB_SYMBOL(cache_add)
#define bdb_cache_children   BDB_SYMBOL(cache_children)
#define bdb_cache_delete   BDB_SYMBOL(cache_delete)
#define bdb_cache_delete_cleanup   BDB_SYMBOL(cache_delete_cleanup)
#define bdb_cache_find_id   BDB_SYMBOL(cache_find_id)
#define bdb_cache_find_ndn   BDB_SYMBOL(cache_find_ndn)
#define bdb_cache_find_parent   BDB_SYMBOL(cache_find_parent)
#define bdb_cache_modify   BDB_SYMBOL(cache_modify)
#define bdb_cache_modrdn   BDB_SYMBOL(cache_modrdn)
#define bdb_cache_release_all   BDB_SYMBOL(cache_release_all)
#define bdb_cache_delete_entry   BDB_SYMBOL(cache_delete_entry)
#define bdb_cache_deref   BDB_SYMBOL(cache_deref)
#define ID_LOCKED   1
#define ID_NOCACHE   2
#define ID_NOENTRY   4
#define ID_CHKPURGE   8
#define bdb_cache_entry_db_relock   BDB_SYMBOL(cache_entry_db_relock)
#define bdb_reader_get   BDB_SYMBOL(reader_get)
#define bdb_reader_flush   BDB_SYMBOL(reader_flush)
#define bdb_trans_backoff   BDB_SYMBOL(trans_backoff)
#define bdb_back_initialize   BDB_SYMBOL(back_initialize)
#define bdb_db_config   BDB_SYMBOL(db_config)
#define bdb_add   BDB_SYMBOL(add)
#define bdb_bind   BDB_SYMBOL(bind)
#define bdb_compare   BDB_SYMBOL(compare)
#define bdb_delete   BDB_SYMBOL(delete)
#define bdb_modify   BDB_SYMBOL(modify)
#define bdb_modrdn   BDB_SYMBOL(modrdn)
#define bdb_search   BDB_SYMBOL(search)
#define bdb_extended   BDB_SYMBOL(extended)
#define bdb_referrals   BDB_SYMBOL(referrals)
#define bdb_operational   BDB_SYMBOL(operational)
#define bdb_hasSubordinates   BDB_SYMBOL(hasSubordinates)
#define bdb_tool_entry_open   BDB_SYMBOL(tool_entry_open)
#define bdb_tool_entry_close   BDB_SYMBOL(tool_entry_close)
#define bdb_tool_entry_first_x   BDB_SYMBOL(tool_entry_first_x)
#define bdb_tool_entry_next   BDB_SYMBOL(tool_entry_next)
#define bdb_tool_entry_get   BDB_SYMBOL(tool_entry_get)
#define bdb_tool_entry_put   BDB_SYMBOL(tool_entry_put)
#define bdb_tool_entry_reindex   BDB_SYMBOL(tool_entry_reindex)
#define bdb_tool_dn2id_get   BDB_SYMBOL(tool_dn2id_get)
#define bdb_tool_entry_modify   BDB_SYMBOL(tool_entry_modify)
#define bdb_tool_idl_add   BDB_SYMBOL(tool_idl_add)

Functions

AttrInfobdb_attr_mask (struct bdb_info *bdb, AttributeDescription *desc)
void bdb_attr_flush (struct bdb_info *bdb)
int bdb_attr_slot (struct bdb_info *bdb, AttributeDescription *desc, int *insert)
int bdb_attr_index_config LDAP_P ((struct bdb_info *bdb, const char *fname, int lineno, int argc, char **argv, struct config_reply_s *cr))
void bdb_attr_index_unparse LDAP_P ((struct bdb_info *bdb, BerVarray *bva))
void bdb_attr_index_destroy LDAP_P ((struct bdb_info *bdb))
void bdb_attr_index_free LDAP_P ((struct bdb_info *bdb, AttributeDescription *ad))
void bdb_attr_info_free (AttrInfo *ai)
int bdb_back_init_cf (BackendInfo *bi)
int bdb_db_cache (Backend *be, struct berval *name, DB **db)
int bdb_db_findsize (struct bdb_info *bdb, struct berval *name)
int bdb_dn2entry LDAP_P ((Operation *op, DB_TXN *tid, struct berval *dn, EntryInfo **e, int matched, DB_LOCK *lock))
int bdb_dn2id (Operation *op, struct berval *dn, EntryInfo *ei, DB_TXN *txn, DBC **cursor)
int bdb_dn2id_add (Operation *op, DB_TXN *tid, EntryInfo *eip, Entry *e)
int bdb_dn2id_delete (Operation *op, DB_TXN *tid, EntryInfo *eip, Entry *e)
int bdb_dn2id_children (Operation *op, DB_TXN *tid, Entry *e)
int bdb_dn2idl (Operation *op, DB_TXN *txn, struct berval *ndn, EntryInfo *ei, ID *ids, ID *stack)
void bdb_errcall (const char *pfx, char *msg)
int bdb_filter_candidates (Operation *op, DB_TXN *txn, Filter *f, ID *ids, ID *tmp, ID *stack)
int bdb_id2entry_add (BackendDB *be, DB_TXN *tid, Entry *e)
int bdb_id2entry_update (BackendDB *be, DB_TXN *tid, Entry *e)
int bdb_id2entry_delete (BackendDB *be, DB_TXN *tid, Entry *e)
int bdb_id2entry (BackendDB *be, DB_TXN *tid, ID id, Entry **e)
void bdb_entry_free (Entry *e)
int bdb_entry_return (Entry *e)
int bdb_idl_cache_get (struct bdb_info *bdb, DB *db, DBT *key, ID *ids)
void bdb_idl_cache_put (struct bdb_info *bdb, DB *db, DBT *key, ID *ids, int rc)
void bdb_idl_cache_del (struct bdb_info *bdb, DB *db, DBT *key)
void bdb_idl_cache_add_id (struct bdb_info *bdb, DB *db, DBT *key, ID id)
void bdb_idl_cache_del_id (struct bdb_info *bdb, DB *db, DBT *key, ID id)
unsigned bdb_idl_search (ID *ids, ID id)
int bdb_idl_fetch_key (BackendDB *be, DB *db, DB_TXN *txn, DBT *key, ID *ids, DBC **saved_cursor, int get_flag)
int bdb_idl_insert (ID *ids, ID id)
int bdb_idl_delete (ID *ids, ID id)
int bdb_idl_insert_key (BackendDB *be, DB *db, DB_TXN *txn, DBT *key, ID id)
int bdb_idl_delete_key (BackendDB *be, DB *db, DB_TXN *txn, DBT *key, ID id)
int bdb_idl_intersection (ID *a, ID *b)
int bdb_idl_union (ID *a, ID *b)
ID bdb_idl_first (ID *ids, ID *cursor)
ID bdb_idl_next (ID *ids, ID *cursor)
void bdb_idl_sort (ID *ids, ID *tmp)
int bdb_idl_append (ID *a, ID *b)
int bdb_idl_append_one (ID *ids, ID id)
AttrInfo *bdb_index_mask LDAP_P ((Backend *be, AttributeDescription *desc, struct berval *name))
int bdb_index_param LDAP_P ((Backend *be, AttributeDescription *desc, int ftype, DB **db, slap_mask_t *mask, struct berval *prefix))
int bdb_index_values LDAP_P ((Operation *op, DB_TXN *txn, AttributeDescription *desc, BerVarray vals, ID id, int opid))
int bdb_index_recset LDAP_P ((struct bdb_info *bdb, Attribute *a, AttributeType *type, struct berval *tags, IndexRec *ir))
int bdb_index_recrun LDAP_P ((Operation *op, struct bdb_info *bdb, IndexRec *ir, ID id, int base))
int bdb_index_entry LDAP_P ((Operation *op, DB_TXN *t, int r, Entry *e))
int bdb_key_read (Backend *be, DB *db, DB_TXN *txn, struct berval *k, ID *ids, DBC **saved_cursor, int get_flags)
int bdb_key_change (Backend *be, DB *db, DB_TXN *txn, struct berval *k, ID id, int op)
int bdb_next_id (BackendDB *be, ID *id)
int bdb_last_id (BackendDB *be, DB_TXN *tid)
int bdb_modify_internal (Operation *op, DB_TXN *tid, Modifications *modlist, Entry *e, const char **text, char *textbuf, size_t textlen)
int bdb_monitor_db_init (BackendDB *be)
int bdb_monitor_db_open (BackendDB *be)
int bdb_monitor_db_close (BackendDB *be)
int bdb_monitor_db_destroy (BackendDB *be)
void bdb_cache_return_entry_rw (struct bdb_info *bdb, Entry *e, int rw, DB_LOCK *lock)
int bdb_cache_children (Operation *op, DB_TXN *txn, Entry *e)
int bdb_cache_add (struct bdb_info *bdb, EntryInfo *pei, Entry *e, struct berval *nrdn, DB_TXN *txn, DB_LOCK *lock)
int bdb_cache_modrdn (struct bdb_info *bdb, Entry *e, struct berval *nrdn, Entry *new, EntryInfo *ein, DB_TXN *txn, DB_LOCK *lock)
int bdb_cache_modify (struct bdb_info *bdb, Entry *e, Attribute *newAttrs, DB_TXN *txn, DB_LOCK *lock)
int bdb_cache_find_ndn (Operation *op, DB_TXN *txn, struct berval *ndn, EntryInfo **res)
int bdb_cache_find_id (Operation *op, DB_TXN *tid, ID id, EntryInfo **eip, int flag, DB_LOCK *lock)
int bdb_cache_find_parent (Operation *op, DB_TXN *txn, ID id, EntryInfo **res)
int bdb_cache_delete (struct bdb_info *bdb, Entry *e, DB_TXN *txn, DB_LOCK *lock)
void bdb_cache_delete_cleanup (Cache *cache, EntryInfo *ei)
void bdb_cache_release_all (Cache *cache)
void bdb_cache_deref (EntryInfo *ei)
int bdb_cache_entry_db_relock (struct bdb_info *bdb, DB_TXN *txn, EntryInfo *ei, int rw, int tryOnly, DB_LOCK *lock)
int bdb_cache_entry_db_unlock (struct bdb_info *bdb, DB_LOCK *lock)
int bdb_reader_get (Operation *op, DB_ENV *env, DB_TXN **txn)
void bdb_reader_flush (DB_ENV *env)
void bdb_trans_backoff (int num_retries)
int bdb_tool_idl_add (BackendDB *be, DB *db, DB_TXN *txn, DBT *key, ID id)

Variables

BI_entry_release_rw bdb_entry_release
BI_entry_get_rw bdb_entry_get
BI_init bdb_back_initialize
BI_db_config bdb_db_config
BI_op_add bdb_add
BI_op_bind bdb_bind
BI_op_compare bdb_compare
BI_op_delete bdb_delete
BI_op_modify bdb_modify
BI_op_modrdn bdb_modrdn
BI_op_search bdb_search
BI_op_extended bdb_extended
BI_chk_referrals bdb_referrals
BI_operational bdb_operational
BI_has_subordinates bdb_hasSubordinates
BI_tool_entry_open bdb_tool_entry_open
BI_tool_entry_close bdb_tool_entry_close
BI_tool_entry_first_x bdb_tool_entry_first_x
BI_tool_entry_next bdb_tool_entry_next
BI_tool_entry_get bdb_tool_entry_get
BI_tool_entry_put bdb_tool_entry_put
BI_tool_entry_reindex bdb_tool_entry_reindex
BI_tool_dn2id_get bdb_tool_dn2id_get
BI_tool_entry_modify bdb_tool_entry_modify

Define Documentation

#define bdb_add   BDB_SYMBOL(add)

Definition at line 622 of file proto-bdb.h.

#define bdb_attr_flush   BDB_SYMBOL(attr_flush)

Definition at line 34 of file proto-bdb.h.

#define bdb_attr_index_config   BDB_SYMBOL(attr_index_config)

Definition at line 36 of file proto-bdb.h.

#define bdb_attr_index_destroy   BDB_SYMBOL(attr_index_destroy)

Definition at line 37 of file proto-bdb.h.

#define bdb_attr_index_free   BDB_SYMBOL(attr_index_free)

Definition at line 38 of file proto-bdb.h.

#define bdb_attr_index_unparse   BDB_SYMBOL(attr_index_unparse)

Definition at line 39 of file proto-bdb.h.

#define bdb_attr_info_free   BDB_SYMBOL(attr_info_free)

Definition at line 40 of file proto-bdb.h.

#define bdb_attr_mask   BDB_SYMBOL(attr_mask)

Definition at line 33 of file proto-bdb.h.

#define bdb_attr_slot   BDB_SYMBOL(attr_slot)

Definition at line 35 of file proto-bdb.h.

#define bdb_back_init_cf   BDB_SYMBOL(back_init_cf)

Definition at line 65 of file proto-bdb.h.

#define bdb_back_initialize   BDB_SYMBOL(back_initialize)

Definition at line 620 of file proto-bdb.h.

#define bdb_bind   BDB_SYMBOL(bind)

Definition at line 623 of file proto-bdb.h.

#define bdb_cache_add   BDB_SYMBOL(cache_add)

Definition at line 501 of file proto-bdb.h.

#define bdb_cache_children   BDB_SYMBOL(cache_children)

Definition at line 502 of file proto-bdb.h.

#define bdb_cache_delete   BDB_SYMBOL(cache_delete)

Definition at line 503 of file proto-bdb.h.

#define bdb_cache_delete_cleanup   BDB_SYMBOL(cache_delete_cleanup)

Definition at line 504 of file proto-bdb.h.

#define bdb_cache_delete_entry   BDB_SYMBOL(cache_delete_entry)

Definition at line 511 of file proto-bdb.h.

#define bdb_cache_deref   BDB_SYMBOL(cache_deref)

Definition at line 512 of file proto-bdb.h.

#define bdb_cache_entry_db_relock   BDB_SYMBOL(cache_entry_db_relock)

Definition at line 590 of file proto-bdb.h.

#define bdb_cache_entry_db_unlock   BDB_SYMBOL(cache_entry_db_unlock)

Definition at line 472 of file proto-bdb.h.

#define bdb_cache_entryinfo_lock (   e)    ldap_pvt_thread_mutex_lock( &(e)->bei_kids_mutex )

Definition at line 475 of file proto-bdb.h.

#define bdb_cache_entryinfo_trylock (   e)    ldap_pvt_thread_mutex_trylock( &(e)->bei_kids_mutex )

Definition at line 479 of file proto-bdb.h.

#define bdb_cache_entryinfo_unlock (   e)    ldap_pvt_thread_mutex_unlock( &(e)->bei_kids_mutex )

Definition at line 477 of file proto-bdb.h.

#define bdb_cache_find_id   BDB_SYMBOL(cache_find_id)

Definition at line 505 of file proto-bdb.h.

#define bdb_cache_find_ndn   BDB_SYMBOL(cache_find_ndn)

Definition at line 506 of file proto-bdb.h.

#define bdb_cache_find_parent   BDB_SYMBOL(cache_find_parent)

Definition at line 507 of file proto-bdb.h.

#define bdb_cache_modify   BDB_SYMBOL(cache_modify)

Definition at line 508 of file proto-bdb.h.

#define bdb_cache_modrdn   BDB_SYMBOL(cache_modrdn)

Definition at line 509 of file proto-bdb.h.

#define bdb_cache_release_all   BDB_SYMBOL(cache_release_all)

Definition at line 510 of file proto-bdb.h.

#define bdb_cache_return_entry_r (   bdb,
  e,
  l 
)    bdb_cache_return_entry_rw((bdb), (e), 0, (l))

Definition at line 487 of file proto-bdb.h.

#define bdb_cache_return_entry_rw   BDB_SYMBOL(cache_return_entry_rw)

Definition at line 473 of file proto-bdb.h.

#define bdb_cache_return_entry_w (   bdb,
  e,
  l 
)    bdb_cache_return_entry_rw((bdb), (e), 1, (l))

Definition at line 489 of file proto-bdb.h.

#define bdb_compare   BDB_SYMBOL(compare)

Definition at line 624 of file proto-bdb.h.

#define bdb_db_cache   BDB_SYMBOL(db_cache)

Definition at line 72 of file proto-bdb.h.

#define bdb_db_config   BDB_SYMBOL(db_config)

Definition at line 621 of file proto-bdb.h.

#define bdb_db_findsize   BDB_SYMBOL(db_findsize)

Definition at line 73 of file proto-bdb.h.

#define bdb_delete   BDB_SYMBOL(delete)

Definition at line 625 of file proto-bdb.h.

#define bdb_dn2entry   BDB_SYMBOL(dn2entry)

Definition at line 89 of file proto-bdb.h.

#define bdb_dn2id   BDB_SYMBOL(dn2id)

Definition at line 98 of file proto-bdb.h.

#define bdb_dn2id_add   BDB_SYMBOL(dn2id_add)

Definition at line 99 of file proto-bdb.h.

#define bdb_dn2id_children   BDB_SYMBOL(dn2id_children)

Definition at line 101 of file proto-bdb.h.

#define bdb_dn2id_delete   BDB_SYMBOL(dn2id_delete)

Definition at line 100 of file proto-bdb.h.

#define bdb_dn2idl   BDB_SYMBOL(dn2idl)

Definition at line 102 of file proto-bdb.h.

Definition at line 221 of file proto-bdb.h.

#define bdb_entry_get   BDB_SYMBOL(entry_get)

Definition at line 224 of file proto-bdb.h.

#define bdb_entry_release   BDB_SYMBOL(entry_release)

Definition at line 223 of file proto-bdb.h.

#define bdb_entry_return   BDB_SYMBOL(entry_return)

Definition at line 222 of file proto-bdb.h.

#define bdb_errcall   BDB_SYMBOL(errcall)

Definition at line 159 of file proto-bdb.h.

#define bdb_extended   BDB_SYMBOL(extended)

Definition at line 629 of file proto-bdb.h.

#define bdb_filter_candidates   BDB_SYMBOL(filter_candidates)

Definition at line 179 of file proto-bdb.h.

#define bdb_hasSubordinates   BDB_SYMBOL(hasSubordinates)

Definition at line 632 of file proto-bdb.h.

#define bdb_id2entry   BDB_SYMBOL(id2entry)

Definition at line 192 of file proto-bdb.h.

#define bdb_id2entry_add   BDB_SYMBOL(id2entry_add)

Definition at line 193 of file proto-bdb.h.

#define bdb_id2entry_delete   BDB_SYMBOL(id2entry_delete)

Definition at line 195 of file proto-bdb.h.

#define bdb_id2entry_update   BDB_SYMBOL(id2entry_update)

Definition at line 194 of file proto-bdb.h.

#define bdb_idl_append   BDB_SYMBOL(idl_append)

Definition at line 288 of file proto-bdb.h.

#define bdb_idl_append_one   BDB_SYMBOL(idl_append_one)

Definition at line 289 of file proto-bdb.h.

#define bdb_idl_cache_add_id   BDB_SYMBOL(idl_cache_add_id)

Definition at line 243 of file proto-bdb.h.

#define bdb_idl_cache_del   BDB_SYMBOL(idl_cache_del)

Definition at line 242 of file proto-bdb.h.

#define bdb_idl_cache_del_id   BDB_SYMBOL(idl_cache_del_id)

Definition at line 244 of file proto-bdb.h.

#define bdb_idl_cache_get   BDB_SYMBOL(idl_cache_get)

Definition at line 240 of file proto-bdb.h.

#define bdb_idl_cache_put   BDB_SYMBOL(idl_cache_put)

Definition at line 241 of file proto-bdb.h.

#define bdb_idl_delete   BDB_SYMBOL(idl_delete)

Definition at line 284 of file proto-bdb.h.

#define bdb_idl_delete_key   BDB_SYMBOL(idl_delete_key)

Definition at line 293 of file proto-bdb.h.

#define bdb_idl_fetch_key   BDB_SYMBOL(idl_fetch_key)

Definition at line 291 of file proto-bdb.h.

#define bdb_idl_first   BDB_SYMBOL(idl_first)

Definition at line 280 of file proto-bdb.h.

#define bdb_idl_insert   BDB_SYMBOL(idl_insert)

Definition at line 283 of file proto-bdb.h.

#define bdb_idl_insert_key   BDB_SYMBOL(idl_insert_key)

Definition at line 292 of file proto-bdb.h.

#define bdb_idl_intersection   BDB_SYMBOL(idl_intersection)

Definition at line 285 of file proto-bdb.h.

#define bdb_idl_next   BDB_SYMBOL(idl_next)

Definition at line 281 of file proto-bdb.h.

#define bdb_idl_search   BDB_SYMBOL(idl_search)

Definition at line 282 of file proto-bdb.h.

#define bdb_idl_sort   BDB_SYMBOL(idl_sort)

Definition at line 287 of file proto-bdb.h.

#define bdb_idl_union   BDB_SYMBOL(idl_union)

Definition at line 286 of file proto-bdb.h.

#define bdb_index_entry   BDB_SYMBOL(index_entry)

Definition at line 347 of file proto-bdb.h.

#define bdb_index_entry_add (   op,
  t,
  e 
)    bdb_index_entry((op),(t),SLAP_INDEX_ADD_OP,(e))

Definition at line 393 of file proto-bdb.h.

#define bdb_index_entry_del (   op,
  t,
  e 
)    bdb_index_entry((op),(t),SLAP_INDEX_DELETE_OP,(e))

Definition at line 395 of file proto-bdb.h.

#define bdb_index_mask   BDB_SYMBOL(index_mask)

Definition at line 344 of file proto-bdb.h.

#define bdb_index_param   BDB_SYMBOL(index_param)

Definition at line 345 of file proto-bdb.h.

#define bdb_index_recrun   BDB_SYMBOL(index_recrun)

Definition at line 349 of file proto-bdb.h.

#define bdb_index_recset   BDB_SYMBOL(index_recset)

Definition at line 348 of file proto-bdb.h.

#define bdb_index_values   BDB_SYMBOL(index_values)

Definition at line 346 of file proto-bdb.h.

#define bdb_key_change   BDB_SYMBOL(key_change)

Definition at line 402 of file proto-bdb.h.

#define bdb_key_read   BDB_SYMBOL(key_read)

Definition at line 401 of file proto-bdb.h.

#define bdb_last_id   BDB_SYMBOL(last_id)

Definition at line 427 of file proto-bdb.h.

#define bdb_modify   BDB_SYMBOL(modify)

Definition at line 626 of file proto-bdb.h.

#define bdb_modify_internal   BDB_SYMBOL(modify_internal)

Definition at line 435 of file proto-bdb.h.

#define bdb_modrdn   BDB_SYMBOL(modrdn)

Definition at line 627 of file proto-bdb.h.

#define bdb_monitor_db_close   BDB_SYMBOL(monitor_db_close)

Definition at line 452 of file proto-bdb.h.

#define bdb_monitor_db_destroy   BDB_SYMBOL(monitor_db_destroy)

Definition at line 453 of file proto-bdb.h.

#define bdb_monitor_db_init   BDB_SYMBOL(monitor_db_init)

Definition at line 450 of file proto-bdb.h.

#define bdb_monitor_db_open   BDB_SYMBOL(monitor_db_open)

Definition at line 451 of file proto-bdb.h.

#define bdb_next_id   BDB_SYMBOL(next_id)

Definition at line 426 of file proto-bdb.h.

#define bdb_operational   BDB_SYMBOL(operational)

Definition at line 631 of file proto-bdb.h.

#define bdb_reader_flush   BDB_SYMBOL(reader_flush)

Definition at line 604 of file proto-bdb.h.

#define bdb_reader_get   BDB_SYMBOL(reader_get)

Definition at line 603 of file proto-bdb.h.

Definition at line 630 of file proto-bdb.h.

#define bdb_search   BDB_SYMBOL(search)

Definition at line 628 of file proto-bdb.h.

#define BDB_SYMBOL (   x)    LDAP_CONCAT(bdb_,x)

Definition at line 25 of file proto-bdb.h.

#define bdb_tool_dn2id_get   BDB_SYMBOL(tool_dn2id_get)

Definition at line 640 of file proto-bdb.h.

#define bdb_tool_entry_close   BDB_SYMBOL(tool_entry_close)

Definition at line 634 of file proto-bdb.h.

#define bdb_tool_entry_first_x   BDB_SYMBOL(tool_entry_first_x)

Definition at line 635 of file proto-bdb.h.

#define bdb_tool_entry_get   BDB_SYMBOL(tool_entry_get)

Definition at line 637 of file proto-bdb.h.

#define bdb_tool_entry_modify   BDB_SYMBOL(tool_entry_modify)

Definition at line 641 of file proto-bdb.h.

#define bdb_tool_entry_next   BDB_SYMBOL(tool_entry_next)

Definition at line 636 of file proto-bdb.h.

#define bdb_tool_entry_open   BDB_SYMBOL(tool_entry_open)

Definition at line 633 of file proto-bdb.h.

#define bdb_tool_entry_put   BDB_SYMBOL(tool_entry_put)

Definition at line 638 of file proto-bdb.h.

#define bdb_tool_entry_reindex   BDB_SYMBOL(tool_entry_reindex)

Definition at line 639 of file proto-bdb.h.

#define bdb_tool_idl_add   BDB_SYMBOL(tool_idl_add)

Definition at line 642 of file proto-bdb.h.

#define bdb_trans_backoff   BDB_SYMBOL(trans_backoff)

Definition at line 611 of file proto-bdb.h.

#define BDB_UCTYPE   "BDB"

Definition at line 26 of file proto-bdb.h.

Definition at line 496 of file proto-bdb.h.

#define bdb_unlocked_cache_return_entry_rw (   a,
  b,
  c 
)    ((void)0)

Definition at line 494 of file proto-bdb.h.

Definition at line 498 of file proto-bdb.h.

#define ID_CHKPURGE   8

Definition at line 553 of file proto-bdb.h.

#define ID_LOCKED   1

Definition at line 550 of file proto-bdb.h.

#define ID_NOCACHE   2

Definition at line 551 of file proto-bdb.h.

#define ID_NOENTRY   4

Definition at line 552 of file proto-bdb.h.


Function Documentation

void bdb_attr_flush ( struct bdb_info bdb)

Definition at line 427 of file attr.c.

{
       int i;

       for ( i=0; i<bdb->bi_nattrs; i++ ) {
              if ( bdb->bi_attrs[i]->ai_indexmask & BDB_INDEX_DELETING ) {
                     int j;
                     bdb_attr_info_free( bdb->bi_attrs[i] );
                     bdb->bi_nattrs--;
                     for (j=i; j<bdb->bi_nattrs; j++)
                            bdb->bi_attrs[j] = bdb->bi_attrs[j+1];
                     i--;
              }
       }
}

Definition at line 395 of file attr.c.

{
#ifdef LDAP_COMP_MATCH
       free( ai->ai_cr );
#endif
       free( ai );
}
AttrInfo* bdb_attr_mask ( struct bdb_info bdb,
AttributeDescription desc 
)

Definition at line 82 of file attr.c.

{
       int i = bdb_attr_slot( bdb, desc, NULL );
       return i < 0 ? NULL : bdb->bi_attrs[i];
}
int bdb_attr_slot ( struct bdb_info bdb,
AttributeDescription desc,
int insert 
)

Definition at line 33 of file attr.c.

{
       unsigned base = 0, cursor = 0;
       unsigned n = bdb->bi_nattrs;
       int val = 0;
       
       while ( 0 < n ) {
              unsigned pivot = n >> 1;
              cursor = base + pivot;

              val = SLAP_PTRCMP( ad, bdb->bi_attrs[cursor]->ai_desc );
              if ( val < 0 ) {
                     n = pivot;
              } else if ( val > 0 ) {
                     base = cursor + 1;
                     n -= pivot + 1;
              } else {
                     return cursor;
              }
       }
       if ( ins ) {
              if ( val > 0 )
                     ++cursor;
              *ins = cursor;
       }
       return -1;
}

Definition at line 934 of file config.c.

{
       int rc;
       bi->bi_cf_ocs = bdbocs;

       rc = config_register_schema( bdbcfg, bdbocs );
       if ( rc ) return rc;
       return 0;
}

Here is the call graph for this function:

int bdb_cache_add ( struct bdb_info bdb,
EntryInfo pei,
Entry e,
struct berval nrdn,
DB_TXN *  txn,
DB_LOCK *  lock 
)

Definition at line 1130 of file cache.c.

{
       EntryInfo *new, ei;
       int rc, purge = 0;
#ifdef BDB_HIER
       struct berval rdn = e->e_name;
#endif

       ei.bei_id = e->e_id;
       ei.bei_parent = eip;
       ei.bei_nrdn = *nrdn;
       ei.bei_lockpad = 0;

#if 0
       /* Lock this entry so that bdb_add can run to completion.
        * It can only fail if BDB has run out of lock resources.
        */
       rc = bdb_cache_entry_db_lock( bdb, txn, &ei, 0, 0, lock );
       if ( rc ) {
              bdb_cache_entryinfo_unlock( eip );
              return rc;
       }
#endif

#ifdef BDB_HIER
       if ( nrdn->bv_len != e->e_nname.bv_len ) {
              char *ptr = ber_bvchr( &rdn, ',' );
              assert( ptr != NULL );
              rdn.bv_len = ptr - rdn.bv_val;
       }
       ber_dupbv( &ei.bei_rdn, &rdn );
       if ( eip->bei_dkids ) eip->bei_dkids++;
#endif

       if (eip->bei_parent) {
              bdb_cache_entryinfo_lock( eip->bei_parent );
              eip->bei_parent->bei_state &= ~CACHE_ENTRY_NO_GRANDKIDS;
              bdb_cache_entryinfo_unlock( eip->bei_parent );
       }

       rc = bdb_entryinfo_add_internal( bdb, &ei, &new );
       /* bdb_csn_commit can cause this when adding the database root entry */
       if ( new->bei_e ) {
              new->bei_e->e_private = NULL;
#ifdef SLAP_ZONE_ALLOC
              bdb_entry_return( bdb, new->bei_e, new->bei_zseq );
#else
              bdb_entry_return( new->bei_e );
#endif
       }
       new->bei_e = e;
       e->e_private = new;
       new->bei_state |= CACHE_ENTRY_NO_KIDS | CACHE_ENTRY_NO_GRANDKIDS;
       eip->bei_state &= ~CACHE_ENTRY_NO_KIDS;
       bdb_cache_entryinfo_unlock( eip );

       ldap_pvt_thread_rdwr_wunlock( &bdb->bi_cache.c_rwlock );
       ldap_pvt_thread_mutex_lock( &bdb->bi_cache.c_count_mutex );
       ++bdb->bi_cache.c_cursize;
       if ( bdb->bi_cache.c_cursize > bdb->bi_cache.c_maxsize &&
              !bdb->bi_cache.c_purging ) {
              purge = 1;
              bdb->bi_cache.c_purging = 1;
       }
       ldap_pvt_thread_mutex_unlock( &bdb->bi_cache.c_count_mutex );

       new->bei_finders = 1;
       bdb_cache_lru_link( bdb, new );

       if ( purge )
              bdb_cache_lru_purge( bdb );

       return rc;
}

Here is the call graph for this function:

int bdb_cache_children ( Operation op,
DB_TXN *  txn,
Entry e 
)

Definition at line 1108 of file cache.c.

{
       int rc;

       if ( BEI(e)->bei_kids ) {
              return 0;
       }
       if ( BEI(e)->bei_state & CACHE_ENTRY_NO_KIDS ) {
              return DB_NOTFOUND;
       }
       rc = bdb_dn2id_children( op, txn, e );
       if ( rc == DB_NOTFOUND ) {
              BEI(e)->bei_state |= CACHE_ENTRY_NO_KIDS | CACHE_ENTRY_NO_GRANDKIDS;
       }
       return rc;
}
int bdb_cache_delete ( struct bdb_info bdb,
Entry e,
DB_TXN *  txn,
DB_LOCK *  lock 
)

Definition at line 1357 of file cache.c.

{
       EntryInfo *ei = BEI(e);
       int    rc, busy = 0;

       assert( e->e_private != NULL );

       /* Lock the entry's info */
       bdb_cache_entryinfo_lock( ei );

       /* Set this early, warn off any queriers */
       ei->bei_state |= CACHE_ENTRY_DELETED;

       if (( ei->bei_state & ( CACHE_ENTRY_NOT_LINKED |
              CACHE_ENTRY_LOADING | CACHE_ENTRY_ONELEVEL )) ||
              ei->bei_finders > 0 )
              busy = 1;

       bdb_cache_entryinfo_unlock( ei );

       while ( busy ) {
              ldap_pvt_thread_yield();
              busy = 0;
              bdb_cache_entryinfo_lock( ei );
              if (( ei->bei_state & ( CACHE_ENTRY_NOT_LINKED |
                     CACHE_ENTRY_LOADING | CACHE_ENTRY_ONELEVEL )) ||
                     ei->bei_finders > 0 )
                     busy = 1;
              bdb_cache_entryinfo_unlock( ei );
       }

       /* Get write lock on the data */
       rc = bdb_cache_entry_db_relock( bdb, txn, ei, 1, 0, lock );
       if ( rc ) {
              bdb_cache_entryinfo_lock( ei );
              /* couldn't lock, undo and give up */
              ei->bei_state ^= CACHE_ENTRY_DELETED;
              bdb_cache_entryinfo_unlock( ei );
              return rc;
       }

       Debug( LDAP_DEBUG_TRACE, "====> bdb_cache_delete( %ld )\n",
              e->e_id, 0, 0 );

       /* set lru mutex */
       ldap_pvt_thread_mutex_lock( &bdb->bi_cache.c_lru_mutex );

       bdb_cache_entryinfo_lock( ei->bei_parent );
       bdb_cache_entryinfo_lock( ei );
       rc = bdb_cache_delete_internal( &bdb->bi_cache, e->e_private, 1 );
       bdb_cache_entryinfo_unlock( ei );

       /* free lru mutex */
       ldap_pvt_thread_mutex_unlock( &bdb->bi_cache.c_lru_mutex );

       return( rc );
}

Here is the call graph for this function:

void bdb_cache_delete_cleanup ( Cache cache,
EntryInfo ei 
)

Definition at line 1420 of file cache.c.

{
       /* Enter with ei locked */

       /* already freed? */
       if ( !ei->bei_parent ) return;

       if ( ei->bei_e ) {
              ei->bei_e->e_private = NULL;
#ifdef SLAP_ZONE_ALLOC
              bdb_entry_return( ei->bei_bdb, ei->bei_e, ei->bei_zseq );
#else
              bdb_entry_return( ei->bei_e );
#endif
              ei->bei_e = NULL;
       }

       bdb_cache_entryinfo_unlock( ei );
       bdb_cache_entryinfo_free( cache, ei );
}

Here is the call graph for this function:

Definition at line 1211 of file cache.c.

int bdb_cache_entry_db_relock ( struct bdb_info bdb,
DB_TXN *  txn,
EntryInfo ei,
int  rw,
int  tryOnly,
DB_LOCK *  lock 
)

Definition at line 171 of file cache.c.

{
#ifdef NO_DB_LOCK
       return 0;
#else
       int    rc;
       DBT    lockobj;
       DB_LOCKREQ list[2];

       if ( !lock ) return 0;

       DBTzero( &lockobj );
       lockobj.data = &ei->bei_id;
       lockobj.size = sizeof(ei->bei_id) + 1;

       list[0].op = DB_LOCK_PUT;
       list[0].lock = *lock;
       list[1].op = DB_LOCK_GET;
       list[1].lock = *lock;
       list[1].mode = rw ? DB_LOCK_WRITE : DB_LOCK_READ;
       list[1].obj = &lockobj;
       rc = bdb->bi_dbenv->lock_vec(bdb->bi_dbenv, TXN_ID(txn), tryOnly ? DB_LOCK_NOWAIT : 0,
              list, 2, NULL );

       if (rc && !tryOnly) {
              Debug( LDAP_DEBUG_TRACE,
                     "bdb_cache_entry_db_relock: entry %ld, rw %d, rc %d\n",
                     ei->bei_id, rw, rc );
       } else {
              *lock = list[1].lock;
       }
       return rc;
#endif
}
int bdb_cache_entry_db_unlock ( struct bdb_info bdb,
DB_LOCK *  lock 
)

Definition at line 246 of file cache.c.

{
#ifdef NO_DB_LOCK
       return 0;
#else
       int rc;

       if ( !lock || lock->mode == DB_LOCK_NG ) return 0;

       rc = LOCK_PUT ( bdb->bi_dbenv, lock );
       return rc;
#endif
}
int bdb_cache_find_id ( Operation op,
DB_TXN *  tid,
ID  id,
EntryInfo **  eip,
int  flag,
DB_LOCK *  lock 
)

Definition at line 866 of file cache.c.

{
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       Entry  *ep = NULL;
       int    rc = 0, load = 0;
       EntryInfo ei = { 0 };

       ei.bei_id = id;

#ifdef SLAP_ZONE_ALLOC
       slap_zh_rlock(bdb->bi_cache.c_zctx);
#endif
       /* If we weren't given any info, see if we have it already cached */
       if ( !*eip ) {
again: ldap_pvt_thread_rdwr_rlock( &bdb->bi_cache.c_rwlock );
              *eip = (EntryInfo *) avl_find( bdb->bi_cache.c_idtree,
                     (caddr_t) &ei, bdb_id_cmp );
              if ( *eip ) {
                     /* If the lock attempt fails, the info is in use */
                     if ( bdb_cache_entryinfo_trylock( *eip )) {
                            int del = (*eip)->bei_state & CACHE_ENTRY_DELETED;
                            ldap_pvt_thread_rdwr_runlock( &bdb->bi_cache.c_rwlock );
                            /* If this node is being deleted, treat
                             * as if the delete has already finished
                             */
                            if ( del ) {
                                   return DB_NOTFOUND;
                            }
                            /* otherwise, wait for the info to free up */
                            ldap_pvt_thread_yield();
                            goto again;
                     }
                     /* If this info isn't hooked up to its parent yet,
                      * unlock and wait for it to be fully initialized
                      */
                     if ( (*eip)->bei_state & CACHE_ENTRY_NOT_LINKED ) {
                            bdb_cache_entryinfo_unlock( *eip );
                            ldap_pvt_thread_rdwr_runlock( &bdb->bi_cache.c_rwlock );
                            ldap_pvt_thread_yield();
                            goto again;
                     }
                     flag |= ID_LOCKED;
              }
              ldap_pvt_thread_rdwr_runlock( &bdb->bi_cache.c_rwlock );
       }

       /* See if the ID exists in the database; add it to the cache if so */
       if ( !*eip ) {
#ifndef BDB_HIER
              rc = bdb_id2entry( op->o_bd, tid, id, &ep );
              if ( rc == 0 ) {
                     rc = bdb_cache_find_ndn( op, tid,
                            &ep->e_nname, eip );
                     if ( *eip ) flag |= ID_LOCKED;
                     if ( rc ) {
                            ep->e_private = NULL;
#ifdef SLAP_ZONE_ALLOC
                            bdb_entry_return( bdb, ep, (*eip)->bei_zseq );
#else
                            bdb_entry_return( ep );
#endif
                            ep = NULL;
                     }
              }
#else
              rc = hdb_cache_find_parent(op, tid, id, eip );
              if ( rc == 0 ) flag |= ID_LOCKED;
#endif
       }

       /* Ok, we found the info, do we have the entry? */
       if ( rc == 0 ) {
              if ( !( flag & ID_LOCKED )) {
                     bdb_cache_entryinfo_lock( *eip );
                     flag |= ID_LOCKED;
              }

              if ( (*eip)->bei_state & CACHE_ENTRY_DELETED ) {
                     rc = DB_NOTFOUND;
              } else {
                     (*eip)->bei_finders++;
                     (*eip)->bei_state |= CACHE_ENTRY_REFERENCED;
                     if ( flag & ID_NOENTRY ) {
                            bdb_cache_entryinfo_unlock( *eip );
                            return 0;
                     }
                     /* Make sure only one thread tries to load the entry */
load1:
#ifdef SLAP_ZONE_ALLOC
                     if ((*eip)->bei_e && !slap_zn_validate(
                                   bdb->bi_cache.c_zctx, (*eip)->bei_e, (*eip)->bei_zseq)) {
                            (*eip)->bei_e = NULL;
                            (*eip)->bei_zseq = 0;
                     }
#endif
                     if ( !(*eip)->bei_e && !((*eip)->bei_state & CACHE_ENTRY_LOADING)) {
                            load = 1;
                            (*eip)->bei_state |= CACHE_ENTRY_LOADING;
                            flag |= ID_CHKPURGE;
                     }

                     if ( !load ) {
                            /* Clear the uncached state if we are not
                             * loading it, i.e it is already cached or
                             * another thread is currently loading it.
                             */
                            if ( (*eip)->bei_state & CACHE_ENTRY_NOT_CACHED ) {
                                   (*eip)->bei_state ^= CACHE_ENTRY_NOT_CACHED;
                                   flag |= ID_CHKPURGE;
                            }
                     }

                     if ( flag & ID_LOCKED ) {
                            bdb_cache_entryinfo_unlock( *eip );
                            flag ^= ID_LOCKED;
                     }
                     rc = bdb_cache_entry_db_lock( bdb, tid, *eip, load, 0, lock );
                     if ( (*eip)->bei_state & CACHE_ENTRY_DELETED ) {
                            rc = DB_NOTFOUND;
                            bdb_cache_entry_db_unlock( bdb, lock );
                            bdb_cache_entryinfo_lock( *eip );
                            (*eip)->bei_finders--;
                            bdb_cache_entryinfo_unlock( *eip );
                     } else if ( rc == 0 ) {
                            if ( load ) {
                                   if ( !ep) {
                                          rc = bdb_id2entry( op->o_bd, tid, id, &ep );
                                   }
                                   if ( rc == 0 ) {
                                          ep->e_private = *eip;
#ifdef BDB_HIER
                                          while ( (*eip)->bei_state & CACHE_ENTRY_NOT_LINKED )
                                                 ldap_pvt_thread_yield();
                                          bdb_fix_dn( ep, 0 );
#endif
                                          bdb_cache_entryinfo_lock( *eip );

                                          (*eip)->bei_e = ep;
#ifdef SLAP_ZONE_ALLOC
                                          (*eip)->bei_zseq = *((ber_len_t *)ep - 2);
#endif
                                          ep = NULL;
                                          if ( flag & ID_NOCACHE ) {
                                                 /* Set the cached state only if no other thread
                                                  * found the info while we were loading the entry.
                                                  */
                                                 if ( (*eip)->bei_finders == 1 ) {
                                                        (*eip)->bei_state |= CACHE_ENTRY_NOT_CACHED;
                                                        flag ^= ID_CHKPURGE;
                                                 }
                                          }
                                          bdb_cache_entryinfo_unlock( *eip );
                                          bdb_cache_lru_link( bdb, *eip );
                                   }
                                   if ( rc == 0 ) {
                                          /* If we succeeded, downgrade back to a readlock. */
                                          rc = bdb_cache_entry_db_relock( bdb, tid,
                                                 *eip, 0, 0, lock );
                                   } else {
                                          /* Otherwise, release the lock. */
                                          bdb_cache_entry_db_unlock( bdb, lock );
                                   }
                            } else if ( !(*eip)->bei_e ) {
                                   /* Some other thread is trying to load the entry,
                                    * wait for it to finish.
                                    */
                                   bdb_cache_entry_db_unlock( bdb, lock );
                                   bdb_cache_entryinfo_lock( *eip );
                                   flag |= ID_LOCKED;
                                   goto load1;
#ifdef BDB_HIER
                            } else {
                                   /* Check for subtree renames
                                    */
                                   rc = bdb_fix_dn( (*eip)->bei_e, 1 );
                                   if ( rc ) {
                                          bdb_cache_entry_db_relock( bdb,
                                                 tid, *eip, 1, 0, lock );
                                          /* check again in case other modifier did it already */
                                          if ( bdb_fix_dn( (*eip)->bei_e, 1 ) )
                                                 rc = bdb_fix_dn( (*eip)->bei_e, 2 );
                                          bdb_cache_entry_db_relock( bdb,
                                                 tid, *eip, 0, 0, lock );
                                   }
#endif
                            }
                            bdb_cache_entryinfo_lock( *eip );
                            (*eip)->bei_finders--;
                            if ( load )
                                   (*eip)->bei_state ^= CACHE_ENTRY_LOADING;
                            bdb_cache_entryinfo_unlock( *eip );
                     }
              }
       }
       if ( flag & ID_LOCKED ) {
              bdb_cache_entryinfo_unlock( *eip );
       }
       if ( ep ) {
              ep->e_private = NULL;
#ifdef SLAP_ZONE_ALLOC
              bdb_entry_return( bdb, ep, (*eip)->bei_zseq );
#else
              bdb_entry_return( ep );
#endif
       }
       if ( rc == 0 ) {
              int purge = 0;

              if (( flag & ID_CHKPURGE ) || bdb->bi_cache.c_eimax ) {
                     ldap_pvt_thread_mutex_lock( &bdb->bi_cache.c_count_mutex );
                     if ( flag & ID_CHKPURGE ) {
                            bdb->bi_cache.c_cursize++;
                            if ( !bdb->bi_cache.c_purging && bdb->bi_cache.c_cursize > bdb->bi_cache.c_maxsize ) {
                                   purge = 1;
                                   bdb->bi_cache.c_purging = 1;
                            }
                     } else if ( !bdb->bi_cache.c_purging && bdb->bi_cache.c_eimax && bdb->bi_cache.c_leaves > bdb->bi_cache.c_eimax ) {
                            purge = 1;
                            bdb->bi_cache.c_purging = 1;
                     }
                     ldap_pvt_thread_mutex_unlock( &bdb->bi_cache.c_count_mutex );
              }
              if ( purge )
                     bdb_cache_lru_purge( bdb );
       }

#ifdef SLAP_ZONE_ALLOC
       if (rc == 0 && (*eip)->bei_e) {
              slap_zn_rlock(bdb->bi_cache.c_zctx, (*eip)->bei_e);
       }
       slap_zh_runlock(bdb->bi_cache.c_zctx);
#endif
       return rc;
}
int bdb_cache_find_ndn ( Operation op,
DB_TXN *  txn,
struct berval ndn,
EntryInfo **  res 
)

Definition at line 405 of file cache.c.

{
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       EntryInfo     ei, *eip, *ei2;
       int rc = 0;
       char *ptr;

       /* this function is always called with normalized DN */
       if ( *res ) {
              /* we're doing a onelevel search for an RDN */
              ei.bei_nrdn.bv_val = ndn->bv_val;
              ei.bei_nrdn.bv_len = dn_rdnlen( op->o_bd, ndn );
              eip = *res;
       } else {
              /* we're searching a full DN from the root */
              ptr = ndn->bv_val + ndn->bv_len - op->o_bd->be_nsuffix[0].bv_len;
              ei.bei_nrdn.bv_val = ptr;
              ei.bei_nrdn.bv_len = op->o_bd->be_nsuffix[0].bv_len;
              /* Skip to next rdn if suffix is empty */
              if ( ei.bei_nrdn.bv_len == 0 ) {
                     for (ptr = ei.bei_nrdn.bv_val - 2; ptr > ndn->bv_val
                            && !DN_SEPARATOR(*ptr); ptr--) /* empty */;
                     if ( ptr >= ndn->bv_val ) {
                            if (DN_SEPARATOR(*ptr)) ptr++;
                            ei.bei_nrdn.bv_len = ei.bei_nrdn.bv_val - ptr;
                            ei.bei_nrdn.bv_val = ptr;
                     }
              }
              eip = &bdb->bi_cache.c_dntree;
       }
       
       for ( bdb_cache_entryinfo_lock( eip ); eip; ) {
              eip->bei_state |= CACHE_ENTRY_REFERENCED;
              ei.bei_parent = eip;
              ei2 = (EntryInfo *)avl_find( eip->bei_kids, &ei, bdb_rdn_cmp );
              if ( !ei2 ) {
                     DBC *cursor;
                     int len = ei.bei_nrdn.bv_len;
                            
                     if ( BER_BVISEMPTY( ndn )) {
                            *res = eip;
                            return LDAP_SUCCESS;
                     }

                     ei.bei_nrdn.bv_len = ndn->bv_len -
                            (ei.bei_nrdn.bv_val - ndn->bv_val);
                     eip->bei_finders++;
                     bdb_cache_entryinfo_unlock( eip );

                     BDB_LOG_PRINTF( bdb->bi_dbenv, NULL, "slapd Reading %s",
                            ei.bei_nrdn.bv_val );

                     cursor = NULL;
                     rc = bdb_dn2id( op, &ei.bei_nrdn, &ei, txn, &cursor );
                     if (rc) {
                            bdb_cache_entryinfo_lock( eip );
                            eip->bei_finders--;
                            if ( cursor ) cursor->c_close( cursor );
                            *res = eip;
                            return rc;
                     }

                     BDB_LOG_PRINTF( bdb->bi_dbenv, NULL, "slapd Read got %s(%d)",
                            ei.bei_nrdn.bv_val, ei.bei_id );

                     /* DN exists but needs to be added to cache */
                     ei.bei_nrdn.bv_len = len;
                     rc = bdb_entryinfo_add_internal( bdb, &ei, &ei2 );
                     /* add_internal left eip and c_rwlock locked */
                     eip->bei_finders--;
                     ldap_pvt_thread_rdwr_wunlock( &bdb->bi_cache.c_rwlock );
                     if ( cursor ) cursor->c_close( cursor );
                     if ( rc ) {
                            *res = eip;
                            return rc;
                     }
              }
              bdb_cache_entryinfo_lock( ei2 );
              if ( ei2->bei_state & CACHE_ENTRY_DELETED ) {
                     /* In the midst of deleting? Give it a chance to
                      * complete.
                      */
                     bdb_cache_entryinfo_unlock( ei2 );
                     bdb_cache_entryinfo_unlock( eip );
                     ldap_pvt_thread_yield();
                     bdb_cache_entryinfo_lock( eip );
                     *res = eip;
                     return DB_NOTFOUND;
              }
              bdb_cache_entryinfo_unlock( eip );

              eip = ei2;

              /* Advance to next lower RDN */
              for (ptr = ei.bei_nrdn.bv_val - 2; ptr > ndn->bv_val
                     && !DN_SEPARATOR(*ptr); ptr--) /* empty */;
              if ( ptr >= ndn->bv_val ) {
                     if (DN_SEPARATOR(*ptr)) ptr++;
                     ei.bei_nrdn.bv_len = ei.bei_nrdn.bv_val - ptr - 1;
                     ei.bei_nrdn.bv_val = ptr;
              }
              if ( ptr < ndn->bv_val ) {
                     *res = eip;
                     break;
              }
       }

       return rc;
}

Here is the call graph for this function:

int bdb_cache_find_parent ( Operation op,
DB_TXN *  txn,
ID  id,
EntryInfo **  res 
)

Here is the caller graph for this function:

int bdb_cache_modify ( struct bdb_info bdb,
Entry e,
Attribute newAttrs,
DB_TXN *  txn,
DB_LOCK *  lock 
)

Definition at line 1221 of file cache.c.

{
       EntryInfo *ei = BEI(e);
       int rc;
       /* Get write lock on data */
       rc = bdb_cache_entry_db_relock( bdb, txn, ei, 1, 0, lock );

       /* If we've done repeated mods on a cached entry, then e_attrs
        * is no longer contiguous with the entry, and must be freed.
        */
       if ( ! rc ) {
              if ( (void *)e->e_attrs != (void *)(e+1) ) {
                     attrs_free( e->e_attrs ); 
              }
              e->e_attrs = newAttrs;
       }
       return rc;
}

Here is the call graph for this function:

int bdb_cache_modrdn ( struct bdb_info bdb,
Entry e,
struct berval nrdn,
Entry new,
EntryInfo ein,
DB_TXN *  txn,
DB_LOCK *  lock 
)

Definition at line 1249 of file cache.c.

{
       EntryInfo *ei = BEI(e), *pei;
       int rc;
#ifdef BDB_HIER
       struct berval rdn;
#endif

       /* Get write lock on data */
       rc =  bdb_cache_entry_db_relock( bdb, txn, ei, 1, 0, lock );
       if ( rc ) return rc;

       /* If we've done repeated mods on a cached entry, then e_attrs
        * is no longer contiguous with the entry, and must be freed.
        */
       if ( (void *)e->e_attrs != (void *)(e+1) ) {
              attrs_free( e->e_attrs );
       }
       e->e_attrs = new->e_attrs;
       if( e->e_nname.bv_val < e->e_bv.bv_val ||
              e->e_nname.bv_val > e->e_bv.bv_val + e->e_bv.bv_len )
       {
              ch_free(e->e_name.bv_val);
              ch_free(e->e_nname.bv_val);
       }
       e->e_name = new->e_name;
       e->e_nname = new->e_nname;

       /* Lock the parent's kids AVL tree */
       pei = ei->bei_parent;
       bdb_cache_entryinfo_lock( pei );
       avl_delete( &pei->bei_kids, (caddr_t) ei, bdb_rdn_cmp );
       free( ei->bei_nrdn.bv_val );
       ber_dupbv( &ei->bei_nrdn, nrdn );

#ifdef BDB_HIER
       free( ei->bei_rdn.bv_val );

       rdn = e->e_name;
       if ( nrdn->bv_len != e->e_nname.bv_len ) {
              char *ptr = ber_bvchr(&rdn, ',');
              assert( ptr != NULL );
              rdn.bv_len = ptr - rdn.bv_val;
       }
       ber_dupbv( &ei->bei_rdn, &rdn );

       /* If new parent, decrement kid counts */
       if ( ein ) {
              pei->bei_ckids--;
              if ( pei->bei_dkids ) {
                     pei->bei_dkids--;
                     if ( pei->bei_dkids < 2 )
                            pei->bei_state |= CACHE_ENTRY_NO_KIDS | CACHE_ENTRY_NO_GRANDKIDS;
              }
       }
#endif

       if (!ein) {
              ein = ei->bei_parent;
       } else {
              ei->bei_parent = ein;
              bdb_cache_entryinfo_unlock( pei );
              bdb_cache_entryinfo_lock( ein );

              /* new parent now has kids */
              if ( ein->bei_state & CACHE_ENTRY_NO_KIDS )
                     ein->bei_state ^= CACHE_ENTRY_NO_KIDS;
              /* grandparent has grandkids */
              if ( ein->bei_parent )
                     ein->bei_parent->bei_state &= ~CACHE_ENTRY_NO_GRANDKIDS;
#ifdef BDB_HIER
              /* parent might now have grandkids */
              if ( ein->bei_state & CACHE_ENTRY_NO_GRANDKIDS &&
                     !(ei->bei_state & CACHE_ENTRY_NO_KIDS))
                     ein->bei_state ^= CACHE_ENTRY_NO_GRANDKIDS;

              ein->bei_ckids++;
              if ( ein->bei_dkids ) ein->bei_dkids++;
#endif
       }

#ifdef BDB_HIER
       /* Record the generation number of this change */
       ldap_pvt_thread_mutex_lock( &bdb->bi_modrdns_mutex );
       bdb->bi_modrdns++;
       ei->bei_modrdns = bdb->bi_modrdns;
       ldap_pvt_thread_mutex_unlock( &bdb->bi_modrdns_mutex );
#endif

       avl_insert( &ein->bei_kids, ei, bdb_rdn_cmp, avl_dup_error );
       bdb_cache_entryinfo_unlock( ein );
       return rc;
}

Here is the call graph for this function:

Definition at line 1518 of file cache.c.

{
       /* set cache write lock */
       ldap_pvt_thread_rdwr_wlock( &cache->c_rwlock );
       /* set lru mutex */
       ldap_pvt_thread_mutex_lock( &cache->c_lru_mutex );

       Debug( LDAP_DEBUG_TRACE, "====> bdb_cache_release_all\n", 0, 0, 0 );

       avl_free( cache->c_dntree.bei_kids, NULL );
       avl_free( cache->c_idtree, bdb_entryinfo_release );
       for (;cache->c_eifree;cache->c_eifree = cache->c_lruhead) {
              cache->c_lruhead = cache->c_eifree->bei_lrunext;
              bdb_cache_entryinfo_destroy(cache->c_eifree);
       }
       cache->c_cursize = 0;
       cache->c_eiused = 0;
       cache->c_leaves = 0;
       cache->c_idtree = NULL;
       cache->c_lruhead = NULL;
       cache->c_lrutail = NULL;
       cache->c_dntree.bei_kids = NULL;

       /* free lru mutex */
       ldap_pvt_thread_mutex_unlock( &cache->c_lru_mutex );
       /* free cache write lock */
       ldap_pvt_thread_rdwr_wunlock( &cache->c_rwlock );
}

Here is the call graph for this function:

void bdb_cache_return_entry_rw ( struct bdb_info bdb,
Entry e,
int  rw,
DB_LOCK *  lock 
)

Definition at line 261 of file cache.c.

{
       EntryInfo *ei;
       int free = 0;

       ei = e->e_private;
       if ( ei && ( ei->bei_state & CACHE_ENTRY_NOT_CACHED )) {
              bdb_cache_entryinfo_lock( ei );
              if ( ei->bei_state & CACHE_ENTRY_NOT_CACHED ) {
                     /* Releasing the entry can only be done when
                      * we know that nobody else is using it, i.e we
                      * should have an entry_db writelock.  But the
                      * flag is only set by the thread that loads the
                      * entry, and only if no other threads has found
                      * it while it was working.  All other threads
                      * clear the flag, which mean that we should be
                      * the only thread using the entry if the flag
                      * is set here.
                      */
                     ei->bei_e = NULL;
                     ei->bei_state ^= CACHE_ENTRY_NOT_CACHED;
                     free = 1;
              }
              bdb_cache_entryinfo_unlock( ei );
       }
       bdb_cache_entry_db_unlock( bdb, lock );
       if ( free ) {
              e->e_private = NULL;
              bdb_entry_return( e );
       }
}
int bdb_db_cache ( Backend be,
struct berval name,
DB **  db 
)

Definition at line 84 of file dbcache.c.

{
       int i, flags;
       int rc;
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       struct bdb_db_info *db;
       char *file;

       *dbout = NULL;

       for( i=BDB_NDB; i < bdb->bi_ndatabases; i++ ) {
              if( !ber_bvcmp( &bdb->bi_databases[i]->bdi_name, name) ) {
                     *dbout = bdb->bi_databases[i]->bdi_db;
                     return 0;
              }
       }

       ldap_pvt_thread_mutex_lock( &bdb->bi_database_mutex );

       /* check again! may have been added by another thread */
       for( i=BDB_NDB; i < bdb->bi_ndatabases; i++ ) {
              if( !ber_bvcmp( &bdb->bi_databases[i]->bdi_name, name) ) {
                     *dbout = bdb->bi_databases[i]->bdi_db;
                     ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
                     return 0;
              }
       }

       if( i >= BDB_INDICES ) {
              ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
              return -1;
       }

       db = (struct bdb_db_info *) ch_calloc(1, sizeof(struct bdb_db_info));

       ber_dupbv( &db->bdi_name, name );

       rc = db_create( &db->bdi_db, bdb->bi_dbenv, 0 );
       if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY,
                     "bdb_db_cache: db_create(%s) failed: %s (%d)\n",
                     bdb->bi_dbenv_home, db_strerror(rc), rc );
              ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
              ch_free( db );
              return rc;
       }

       if( !BER_BVISNULL( &bdb->bi_db_crypt_key )) {
              rc = db->bdi_db->set_flags( db->bdi_db, DB_ENCRYPT );
              if ( rc ) {
                     Debug( LDAP_DEBUG_ANY,
                            "bdb_db_cache: db set_flags(DB_ENCRYPT)(%s) failed: %s (%d)\n",
                            bdb->bi_dbenv_home, db_strerror(rc), rc );
                     ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
                     db->bdi_db->close( db->bdi_db, 0 );
                     ch_free( db );
                     return rc;
              }
       }

       if( bdb->bi_flags & BDB_CHKSUM ) {
              rc = db->bdi_db->set_flags( db->bdi_db, DB_CHKSUM );
              if ( rc ) {
                     Debug( LDAP_DEBUG_ANY,
                            "bdb_db_cache: db set_flags(DB_CHKSUM)(%s) failed: %s (%d)\n",
                            bdb->bi_dbenv_home, db_strerror(rc), rc );
                     ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
                     db->bdi_db->close( db->bdi_db, 0 );
                     ch_free( db );
                     return rc;
              }
       }

       /* If no explicit size set, use the FS default */
       flags = bdb_db_findsize( bdb, name );
       if ( flags )
              rc = db->bdi_db->set_pagesize( db->bdi_db, flags );

#ifdef BDB_INDEX_USE_HASH
       rc = db->bdi_db->set_h_hash( db->bdi_db, bdb_db_hash );
#endif
       rc = db->bdi_db->set_flags( db->bdi_db, DB_DUP | DB_DUPSORT );

       file = ch_malloc( db->bdi_name.bv_len + sizeof(BDB_SUFFIX) );
       strcpy( file, db->bdi_name.bv_val );
       strcpy( file+db->bdi_name.bv_len, BDB_SUFFIX );

#ifdef HAVE_EBCDIC
       __atoe( file );
#endif
       flags = DB_CREATE | DB_THREAD;
#ifdef DB_AUTO_COMMIT
       if ( !( slapMode & SLAP_TOOL_QUICK ))
              flags |= DB_AUTO_COMMIT;
#endif
       /* Cannot Truncate when Transactions are in use */
       if ( (slapMode & (SLAP_TOOL_QUICK|SLAP_TRUNCATE_MODE)) ==
              (SLAP_TOOL_QUICK|SLAP_TRUNCATE_MODE))
                     flags |= DB_TRUNCATE;

       rc = DB_OPEN( db->bdi_db,
              file, NULL /* name */,
              BDB_INDEXTYPE, bdb->bi_db_opflags | flags, bdb->bi_dbenv_mode );

       ch_free( file );

       if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY,
                     "bdb_db_cache: db_open(%s) failed: %s (%d)\n",
                     name->bv_val, db_strerror(rc), rc );
              ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
              return rc;
       }

       bdb->bi_databases[i] = db;
       bdb->bi_ndatabases = i+1;

       *dbout = db->bdi_db;

       ldap_pvt_thread_mutex_unlock( &bdb->bi_database_mutex );
       return 0;
}

Here is the call graph for this function:

int bdb_db_findsize ( struct bdb_info bdb,
struct berval name 
)

Definition at line 62 of file dbcache.c.

{
       struct bdb_db_pgsize *bp;
       int rc;

       for ( bp = bdb->bi_pagesizes; bp; bp=bp->bdp_next ) {
              rc = strncmp( name->bv_val, bp->bdp_name.bv_val, name->bv_len );
              if ( !rc ) {
                     if ( name->bv_len == bp->bdp_name.bv_len )
                            return bp->bdp_size;
                     if ( name->bv_len < bp->bdp_name.bv_len &&
                            bp->bdp_name.bv_val[name->bv_len] == '.' )
                            return bp->bdp_size;
              }
       }
       return 0;
}
int bdb_dn2id ( Operation op,
struct berval dn,
EntryInfo ei,
DB_TXN *  txn,
DBC **  cursor 
)

Definition at line 248 of file dn2id.c.

{
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       DB *db = bdb->bi_dn2id->bdi_db;
       int           rc;
       DBT           key, data;
       ID            nid;

       Debug( LDAP_DEBUG_TRACE, "=> bdb_dn2id(\"%s\")\n", dn->bv_val, 0, 0 );

       DBTzero( &key );
       key.size = dn->bv_len + 2;
       key.data = op->o_tmpalloc( key.size, op->o_tmpmemctx );
       ((char *)key.data)[0] = DN_BASE_PREFIX;
       AC_MEMCPY( &((char *)key.data)[1], dn->bv_val, key.size - 1 );

       /* store the ID */
       DBTzero( &data );
       data.data = &nid;
       data.ulen = sizeof(ID);
       data.flags = DB_DBT_USERMEM;

       rc = db->cursor( db, txn, cursor, bdb->bi_db_opflags );

       /* fetch it */
       if ( !rc )
              rc = (*cursor)->c_get( *cursor, &key, &data, DB_SET );

       if( rc != 0 ) {
              Debug( LDAP_DEBUG_TRACE, "<= bdb_dn2id: get failed: %s (%d)\n",
                     db_strerror( rc ), rc, 0 );
       } else {
              BDB_DISK2ID( &nid, &ei->bei_id );
              Debug( LDAP_DEBUG_TRACE, "<= bdb_dn2id: got id=0x%lx\n",
                     ei->bei_id, 0, 0 );
       }
       op->o_tmpfree( key.data, op->o_tmpmemctx );
       return rc;
}
int bdb_dn2id_add ( Operation op,
DB_TXN *  tid,
EntryInfo eip,
Entry e 
)

Definition at line 28 of file dn2id.c.

{
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       DB *db = bdb->bi_dn2id->bdi_db;
       int           rc;
       DBT           key, data;
       ID            nid;
       char          *buf;
       struct berval ptr, pdn;

       Debug( LDAP_DEBUG_TRACE, "=> bdb_dn2id_add 0x%lx: \"%s\"\n",
              e->e_id, e->e_ndn, 0 );
       assert( e->e_id != NOID );

       DBTzero( &key );
       key.size = e->e_nname.bv_len + 2;
       key.ulen = key.size;
       key.flags = DB_DBT_USERMEM;
       buf = op->o_tmpalloc( key.size, op->o_tmpmemctx );
       key.data = buf;
       buf[0] = DN_BASE_PREFIX;
       ptr.bv_val = buf + 1;
       ptr.bv_len = e->e_nname.bv_len;
       AC_MEMCPY( ptr.bv_val, e->e_nname.bv_val, e->e_nname.bv_len );
       ptr.bv_val[ptr.bv_len] = '\0';

       DBTzero( &data );
       data.data = &nid;
       data.size = sizeof( nid );
       BDB_ID2DISK( e->e_id, &nid );

       /* store it -- don't override */
       rc = db->put( db, txn, &key, &data, DB_NOOVERWRITE );
       if( rc != 0 ) {
              char buf[ SLAP_TEXT_BUFLEN ];
              snprintf( buf, sizeof( buf ), "%s => bdb_dn2id_add dn=\"%s\" ID=0x%lx",
                     op->o_log_prefix, e->e_name.bv_val, e->e_id );
              Debug( LDAP_DEBUG_ANY, "%s: put failed: %s %d\n",
                     buf, db_strerror(rc), rc );
              goto done;
       }

#ifndef BDB_MULTIPLE_SUFFIXES
       if( !be_issuffix( op->o_bd, &ptr ))
#endif
       {
              buf[0] = DN_SUBTREE_PREFIX;
              rc = db->put( db, txn, &key, &data, DB_NOOVERWRITE );
              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                     "=> bdb_dn2id_add 0x%lx: subtree (%s) put failed: %d\n",
                     e->e_id, ptr.bv_val, rc );
                     goto done;
              }
              
#ifdef BDB_MULTIPLE_SUFFIXES
       if( !be_issuffix( op->o_bd, &ptr ))
#endif
       {
              dnParent( &ptr, &pdn );
       
              key.size = pdn.bv_len + 2;
              key.ulen = key.size;
              pdn.bv_val[-1] = DN_ONE_PREFIX;
              key.data = pdn.bv_val-1;
              ptr = pdn;

              rc = bdb_idl_insert_key( op->o_bd, db, txn, &key, e->e_id );

              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                            "=> bdb_dn2id_add 0x%lx: parent (%s) insert failed: %d\n",
                                   e->e_id, ptr.bv_val, rc );
                     goto done;
              }
       }

#ifndef BDB_MULTIPLE_SUFFIXES
       while( !be_issuffix( op->o_bd, &ptr ))
#else
       for (;;)
#endif
       {
              ptr.bv_val[-1] = DN_SUBTREE_PREFIX;

              rc = bdb_idl_insert_key( op->o_bd, db, txn, &key, e->e_id );

              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                            "=> bdb_dn2id_add 0x%lx: subtree (%s) insert failed: %d\n",
                                   e->e_id, ptr.bv_val, rc );
                     break;
              }
#ifdef BDB_MULTIPLE_SUFFIXES
              if( be_issuffix( op->o_bd, &ptr )) break;
#endif
              dnParent( &ptr, &pdn );

              key.size = pdn.bv_len + 2;
              key.ulen = key.size;
              key.data = pdn.bv_val - 1;
              ptr = pdn;
       }
       }

done:
       op->o_tmpfree( buf, op->o_tmpmemctx );
       Debug( LDAP_DEBUG_TRACE, "<= bdb_dn2id_add 0x%lx: %d\n", e->e_id, rc, 0 );
       return rc;
}

Here is the call graph for this function:

int bdb_dn2id_children ( Operation op,
DB_TXN *  tid,
Entry e 
)

Definition at line 294 of file dn2id.c.

{
       DBT           key, data;
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       DB *db = bdb->bi_dn2id->bdi_db;
       ID            id;
       int           rc;

       Debug( LDAP_DEBUG_TRACE, "=> bdb_dn2id_children(\"%s\")\n",
              e->e_nname.bv_val, 0, 0 );
       DBTzero( &key );
       key.size = e->e_nname.bv_len + 2;
       key.data = op->o_tmpalloc( key.size, op->o_tmpmemctx );
       ((char *)key.data)[0] = DN_ONE_PREFIX;
       AC_MEMCPY( &((char *)key.data)[1], e->e_nname.bv_val, key.size - 1 );

       if ( bdb->bi_idl_cache_size ) {
              rc = bdb_idl_cache_get( bdb, db, &key, NULL );
              if ( rc != LDAP_NO_SUCH_OBJECT ) {
                     op->o_tmpfree( key.data, op->o_tmpmemctx );
                     return rc;
              }
       }
       /* we actually could do a empty get... */
       DBTzero( &data );
       data.data = &id;
       data.ulen = sizeof(id);
       data.flags = DB_DBT_USERMEM;
       data.doff = 0;
       data.dlen = sizeof(id);

       rc = db->get( db, txn, &key, &data, bdb->bi_db_opflags );
       op->o_tmpfree( key.data, op->o_tmpmemctx );

       Debug( LDAP_DEBUG_TRACE, "<= bdb_dn2id_children(\"%s\"): %s (%d)\n",
              e->e_nname.bv_val,
              rc == 0 ? "" : ( rc == DB_NOTFOUND ? "no " :
                     db_strerror(rc) ), rc );

       return rc;
}
int bdb_dn2id_delete ( Operation op,
DB_TXN *  tid,
EntryInfo eip,
Entry e 
)

Definition at line 144 of file dn2id.c.

{
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       DB *db = bdb->bi_dn2id->bdi_db;
       char          *buf;
       DBT           key;
       struct berval pdn, ptr;
       int           rc;

       Debug( LDAP_DEBUG_TRACE, "=> bdb_dn2id_delete 0x%lx: \"%s\"\n",
              e->e_id, e->e_ndn, 0 );

       DBTzero( &key );
       key.size = e->e_nname.bv_len + 2;
       buf = op->o_tmpalloc( key.size, op->o_tmpmemctx );
       key.data = buf;
       key.flags = DB_DBT_USERMEM;
       buf[0] = DN_BASE_PREFIX;
       ptr.bv_val = buf+1;
       ptr.bv_len = e->e_nname.bv_len;
       AC_MEMCPY( ptr.bv_val, e->e_nname.bv_val, e->e_nname.bv_len );
       ptr.bv_val[ptr.bv_len] = '\0';

       /* delete it */
       rc = db->del( db, txn, &key, 0 );
       if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_dn2id_delete 0x%lx: delete failed: %s %d\n",
                     e->e_id, db_strerror(rc), rc );
              goto done;
       }

#ifndef BDB_MULTIPLE_SUFFIXES
       if( !be_issuffix( op->o_bd, &ptr ))
#endif
       {
              buf[0] = DN_SUBTREE_PREFIX;
              rc = bdb_idl_delete_key( op->o_bd, db, txn, &key, e->e_id );
              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                     "=> bdb_dn2id_delete 0x%lx: subtree (%s) delete failed: %d\n",
                     e->e_id, ptr.bv_val, rc );
                     goto done;
              }

#ifdef BDB_MULTIPLE_SUFFIXES
       if( !be_issuffix( op->o_bd, &ptr ))
#endif
       {
              dnParent( &ptr, &pdn );

              key.size = pdn.bv_len + 2;
              key.ulen = key.size;
              pdn.bv_val[-1] = DN_ONE_PREFIX;
              key.data = pdn.bv_val - 1;
              ptr = pdn;

              rc = bdb_idl_delete_key( op->o_bd, db, txn, &key, e->e_id );

              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                            "=> bdb_dn2id_delete 0x%lx: parent (%s) delete failed: %d\n",
                            e->e_id, ptr.bv_val, rc );
                     goto done;
              }
       }

#ifndef BDB_MULTIPLE_SUFFIXES
       while( !be_issuffix( op->o_bd, &ptr ))
#else
       for (;;)
#endif
       {
              ptr.bv_val[-1] = DN_SUBTREE_PREFIX;

              rc = bdb_idl_delete_key( op->o_bd, db, txn, &key, e->e_id );
              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY,
                            "=> bdb_dn2id_delete 0x%lx: subtree (%s) delete failed: %d\n",
                            e->e_id, ptr.bv_val, rc );
                     goto done;
              }
#ifdef BDB_MULTIPLE_SUFFIXES
              if( be_issuffix( op->o_bd, &ptr )) break;
#endif
              dnParent( &ptr, &pdn );

              key.size = pdn.bv_len + 2;
              key.ulen = key.size;
              key.data = pdn.bv_val - 1;
              ptr = pdn;
       }
       }

done:
       op->o_tmpfree( buf, op->o_tmpmemctx );
       Debug( LDAP_DEBUG_TRACE, "<= bdb_dn2id_delete 0x%lx: %d\n", e->e_id, rc, 0 );
       return rc;
}

Here is the call graph for this function:

int bdb_dn2idl ( Operation op,
DB_TXN *  txn,
struct berval ndn,
EntryInfo ei,
ID ids,
ID stack 
)

Definition at line 340 of file dn2id.c.

{
       int           rc;
       DBT           key;
       struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
       DB *db = bdb->bi_dn2id->bdi_db;
       int prefix = ( op->ors_scope == LDAP_SCOPE_ONELEVEL )
              ? DN_ONE_PREFIX : DN_SUBTREE_PREFIX;

       Debug( LDAP_DEBUG_TRACE, "=> bdb_dn2idl(\"%s\")\n",
              ndn->bv_val, 0, 0 );

#ifndef       BDB_MULTIPLE_SUFFIXES
       if ( prefix == DN_SUBTREE_PREFIX
              && ( ei->bei_id == 0 ||
              ( ei->bei_parent->bei_id == 0 && op->o_bd->be_suffix[0].bv_len ))) {
              BDB_IDL_ALL(bdb, ids);
              return 0;
       }
#endif

       DBTzero( &key );
       key.size = ndn->bv_len + 2;
       key.ulen = key.size;
       key.flags = DB_DBT_USERMEM;
       key.data = op->o_tmpalloc( key.size, op->o_tmpmemctx );
       ((char *)key.data)[0] = prefix;
       AC_MEMCPY( &((char *)key.data)[1], ndn->bv_val, key.size - 1 );

       BDB_IDL_ZERO( ids );
       rc = bdb_idl_fetch_key( op->o_bd, db, txn, &key, ids, NULL, 0 );

       if( rc != 0 ) {
              Debug( LDAP_DEBUG_TRACE,
                     "<= bdb_dn2idl: get failed: %s (%d)\n",
                     db_strerror( rc ), rc, 0 );

       } else {
              Debug( LDAP_DEBUG_TRACE,
                     "<= bdb_dn2idl: id=%ld first=%ld last=%ld\n",
                     (long) ids[0],
                     (long) BDB_IDL_FIRST( ids ), (long) BDB_IDL_LAST( ids ) );
       }

       op->o_tmpfree( key.data, op->o_tmpmemctx );
       return rc;
}

Definition at line 211 of file id2entry.c.

{
       /* Our entries are allocated in two blocks; the data comes from
        * the db itself and the Entry structure and associated pointers
        * are allocated in entry_decode. The db data pointer is saved
        * in e_bv.
        */
       if ( e->e_bv.bv_val ) {
              /* See if the DNs were changed by modrdn */
              if( e->e_nname.bv_val < e->e_bv.bv_val || e->e_nname.bv_val >
                     e->e_bv.bv_val + e->e_bv.bv_len ) {
                     ch_free(e->e_name.bv_val);
                     ch_free(e->e_nname.bv_val);
              }
              e->e_name.bv_val = NULL;
              e->e_nname.bv_val = NULL;
              /* In tool mode the e_bv buffer is realloc'd, leave it alone */
              if( !(slapMode & SLAP_TOOL_MODE) ) {
                     free( e->e_bv.bv_val );
              }
              BER_BVZERO( &e->e_bv );
       }
       entry_free( e );
       return 0;
}

Here is the call graph for this function:

void bdb_errcall ( const char *  pfx,
char *  msg 
)

Definition at line 26 of file error.c.

{
#ifdef HAVE_EBCDIC
       if ( msg[0] > 0x7f )
              __etoa( msg );
#endif
       Debug( LDAP_DEBUG_ANY, "bdb(%s): %s\n", pfx, msg, 0 );
}
int bdb_filter_candidates ( Operation op,
DB_TXN *  txn,
Filter f,
ID ids,
ID tmp,
ID stack 
)

Definition at line 101 of file filterindex.c.

{
       int rc = 0;
#ifdef LDAP_COMP_MATCH
       AttributeAliasing *aa;
#endif
       Debug( LDAP_DEBUG_FILTER, "=> bdb_filter_candidates\n", 0, 0, 0 );

       if ( f->f_choice & SLAPD_FILTER_UNDEFINED ) {
              BDB_IDL_ZERO( ids );
              goto out;
       }

       switch ( f->f_choice ) {
       case SLAPD_FILTER_COMPUTED:
              switch( f->f_result ) {
              case SLAPD_COMPARE_UNDEFINED:
              /* This technically is not the same as FALSE, but it
               * certainly will produce no matches.
               */
              /* FALL THRU */
              case LDAP_COMPARE_FALSE:
                     BDB_IDL_ZERO( ids );
                     break;
              case LDAP_COMPARE_TRUE: {
                     struct bdb_info *bdb = (struct bdb_info *)op->o_bd->be_private;
                     BDB_IDL_ALL( bdb, ids );
                     } break;
              case LDAP_SUCCESS:
                     /* this is a pre-computed scope, leave it alone */
                     break;
              }
              break;
       case LDAP_FILTER_PRESENT:
              Debug( LDAP_DEBUG_FILTER, "\tPRESENT\n", 0, 0, 0 );
              rc = presence_candidates( op, rtxn, f->f_desc, ids );
              break;

       case LDAP_FILTER_EQUALITY:
              Debug( LDAP_DEBUG_FILTER, "\tEQUALITY\n", 0, 0, 0 );
#ifdef LDAP_COMP_MATCH
              if ( is_aliased_attribute && ( aa = is_aliased_attribute ( f->f_ava->aa_desc ) ) ) {
                     rc = ava_comp_candidates ( op, rtxn, f->f_ava, aa, ids, tmp, stack );
              }
              else
#endif
              {
                     rc = equality_candidates( op, rtxn, f->f_ava, ids, tmp );
              }
              break;

       case LDAP_FILTER_APPROX:
              Debug( LDAP_DEBUG_FILTER, "\tAPPROX\n", 0, 0, 0 );
              rc = approx_candidates( op, rtxn, f->f_ava, ids, tmp );
              break;

       case LDAP_FILTER_SUBSTRINGS:
              Debug( LDAP_DEBUG_FILTER, "\tSUBSTRINGS\n", 0, 0, 0 );
              rc = substring_candidates( op, rtxn, f->f_sub, ids, tmp );
              break;

       case LDAP_FILTER_GE:
              /* if no GE index, use pres */
              Debug( LDAP_DEBUG_FILTER, "\tGE\n", 0, 0, 0 );
              if( f->f_ava->aa_desc->ad_type->sat_ordering &&
                     ( f->f_ava->aa_desc->ad_type->sat_ordering->smr_usage & SLAP_MR_ORDERED_INDEX ) )
                     rc = inequality_candidates( op, rtxn, f->f_ava, ids, tmp, LDAP_FILTER_GE );
              else
                     rc = presence_candidates( op, rtxn, f->f_ava->aa_desc, ids );
              break;

       case LDAP_FILTER_LE:
              /* if no LE index, use pres */
              Debug( LDAP_DEBUG_FILTER, "\tLE\n", 0, 0, 0 );
              if( f->f_ava->aa_desc->ad_type->sat_ordering &&
                     ( f->f_ava->aa_desc->ad_type->sat_ordering->smr_usage & SLAP_MR_ORDERED_INDEX ) )
                     rc = inequality_candidates( op, rtxn, f->f_ava, ids, tmp, LDAP_FILTER_LE );
              else
                     rc = presence_candidates( op, rtxn, f->f_ava->aa_desc, ids );
              break;

       case LDAP_FILTER_NOT:
              /* no indexing to support NOT filters */
              Debug( LDAP_DEBUG_FILTER, "\tNOT\n", 0, 0, 0 );
              { struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
              BDB_IDL_ALL( bdb, ids );
              }
              break;

       case LDAP_FILTER_AND:
              Debug( LDAP_DEBUG_FILTER, "\tAND\n", 0, 0, 0 );
              rc = list_candidates( op, rtxn, 
                     f->f_and, LDAP_FILTER_AND, ids, tmp, stack );
              break;

       case LDAP_FILTER_OR:
              Debug( LDAP_DEBUG_FILTER, "\tOR\n", 0, 0, 0 );
              rc = list_candidates( op, rtxn,
                     f->f_or, LDAP_FILTER_OR, ids, tmp, stack );
              break;
       case LDAP_FILTER_EXT:
                Debug( LDAP_DEBUG_FILTER, "\tEXT\n", 0, 0, 0 );
                rc = ext_candidates( op, rtxn, f->f_mra, ids, tmp, stack );
                break;
       default:
              Debug( LDAP_DEBUG_FILTER, "\tUNKNOWN %lu\n",
                     (unsigned long) f->f_choice, 0, 0 );
              /* Must not return NULL, otherwise extended filters break */
              { struct bdb_info *bdb = (struct bdb_info *) op->o_bd->be_private;
              BDB_IDL_ALL( bdb, ids );
              }
       }

out:
       Debug( LDAP_DEBUG_FILTER,
              "<= bdb_filter_candidates: id=%ld first=%ld last=%ld\n",
              (long) ids[0],
              (long) BDB_IDL_FIRST( ids ),
              (long) BDB_IDL_LAST( ids ) );

       return rc;
}

Here is the call graph for this function:

int bdb_id2entry ( BackendDB be,
DB_TXN *  tid,
ID  id,
Entry **  e 
)

Definition at line 93 of file id2entry.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       DB *db = bdb->bi_id2entry->bdi_db;
       DBT key, data;
       DBC *cursor;
       EntryHeader eh;
       char buf[16];
       int rc = 0, off;
       ID nid;

       *e = NULL;

       DBTzero( &key );
       key.data = &nid;
       key.size = sizeof(ID);
       BDB_ID2DISK( id, &nid );

       DBTzero( &data );
       data.flags = DB_DBT_USERMEM | DB_DBT_PARTIAL;

       /* fetch it */
       rc = db->cursor( db, tid, &cursor, bdb->bi_db_opflags );
       if ( rc ) return rc;

       /* Get the nattrs / nvals counts first */
       data.ulen = data.dlen = sizeof(buf);
       data.data = buf;
       rc = cursor->c_get( cursor, &key, &data, DB_SET );
       if ( rc ) goto finish;


       eh.bv.bv_val = buf;
       eh.bv.bv_len = data.size;
       rc = entry_header( &eh );
       if ( rc ) goto finish;

       if ( eh.nvals ) {
              /* Get the size */
              data.flags ^= DB_DBT_PARTIAL;
              data.ulen = 0;
              rc = cursor->c_get( cursor, &key, &data, DB_CURRENT );
              if ( rc != DB_BUFFER_SMALL ) goto finish;

              /* Allocate a block and retrieve the data */
              off = eh.data - eh.bv.bv_val;
              eh.bv.bv_len = eh.nvals * sizeof( struct berval ) + data.size;
              eh.bv.bv_val = ch_malloc( eh.bv.bv_len );
              eh.data = eh.bv.bv_val + eh.nvals * sizeof( struct berval );
              data.data = eh.data;
              data.ulen = data.size;

              /* skip past already parsed nattr/nvals */
              eh.data += off;

              rc = cursor->c_get( cursor, &key, &data, DB_CURRENT );
       }

finish:
       cursor->c_close( cursor );

       if( rc != 0 ) {
              return rc;
       }

       if ( eh.nvals ) {
#ifdef SLAP_ZONE_ALLOC
              rc = entry_decode(&eh, e, bdb->bi_cache.c_zctx);
#else
              rc = entry_decode(&eh, e);
#endif
       } else {
              *e = entry_alloc();
       }

       if( rc == 0 ) {
              (*e)->e_id = id;
       } else {
              /* only free on error. On success, the entry was
               * decoded in place.
               */
#ifndef SLAP_ZONE_ALLOC
              ch_free(eh.bv.bv_val);
#endif
       }
#ifdef SLAP_ZONE_ALLOC
       ch_free(eh.bv.bv_val);
#endif

       return rc;
}

Here is the call graph for this function:

int bdb_id2entry_add ( BackendDB be,
DB_TXN *  tid,
Entry e 
)

Definition at line 77 of file id2entry.c.

{
       return bdb_id2entry_put(be, tid, e, DB_NOOVERWRITE);
}

Here is the call graph for this function:

int bdb_id2entry_delete ( BackendDB be,
DB_TXN *  tid,
Entry e 
)

Definition at line 189 of file id2entry.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       DB *db = bdb->bi_id2entry->bdi_db;
       DBT key;
       int rc;
       ID nid;

       DBTzero( &key );
       key.data = &nid;
       key.size = sizeof(ID);
       BDB_ID2DISK( e->e_id, &nid );

       /* delete from database */
       rc = db->del( db, tid, &key, 0 );

       return rc;
}
int bdb_id2entry_update ( BackendDB be,
DB_TXN *  tid,
Entry e 
)

Definition at line 85 of file id2entry.c.

{
       return bdb_id2entry_put(be, tid, e, 0);
}

Here is the call graph for this function:

int bdb_idl_append ( ID a,
ID b 
)
int bdb_idl_append_one ( ID ids,
ID  id 
)
void bdb_idl_cache_add_id ( struct bdb_info bdb,
DB *  db,
DBT *  key,
ID  id 
)

Definition at line 443 of file idl.c.

{
       bdb_idl_cache_entry_t *cache_entry, idl_tmp;
       DBT2bv( key, &idl_tmp.kstr );
       idl_tmp.db = db;
       ldap_pvt_thread_rdwr_wlock( &bdb->bi_idl_tree_rwlock );
       cache_entry = avl_find( bdb->bi_idl_tree, &idl_tmp,
                                  bdb_idl_entry_cmp );
       if ( cache_entry != NULL ) {
              if ( !BDB_IDL_IS_RANGE( cache_entry->idl ) &&
                     cache_entry->idl[0] < BDB_IDL_DB_MAX ) {
                     size_t s = BDB_IDL_SIZEOF( cache_entry->idl ) + sizeof(ID);
                     cache_entry->idl = ch_realloc( cache_entry->idl, s );
              }
              bdb_idl_insert( cache_entry->idl, id );
       }
       ldap_pvt_thread_rdwr_wunlock( &bdb->bi_idl_tree_rwlock );
}

Here is the call graph for this function:

void bdb_idl_cache_del ( struct bdb_info bdb,
DB *  db,
DBT *  key 
)

Definition at line 412 of file idl.c.

{
       bdb_idl_cache_entry_t *matched_idl_entry, idl_tmp;
       DBT2bv( key, &idl_tmp.kstr );
       idl_tmp.db = db;
       ldap_pvt_thread_rdwr_wlock( &bdb->bi_idl_tree_rwlock );
       matched_idl_entry = avl_find( bdb->bi_idl_tree, &idl_tmp,
                                  bdb_idl_entry_cmp );
       if ( matched_idl_entry != NULL ) {
              if ( avl_delete( &bdb->bi_idl_tree, (caddr_t) matched_idl_entry,
                                bdb_idl_entry_cmp ) == NULL ) {
                     Debug( LDAP_DEBUG_ANY, "=> bdb_idl_cache_del: "
                            "AVL delete failed\n",
                            0, 0, 0 );
              }
              --bdb->bi_idl_cache_size;
              ldap_pvt_thread_mutex_lock( &bdb->bi_idl_tree_lrulock );
              IDL_LRU_DELETE( bdb, matched_idl_entry );
              ldap_pvt_thread_mutex_unlock( &bdb->bi_idl_tree_lrulock );
              free( matched_idl_entry->kstr.bv_val );
              if ( matched_idl_entry->idl )
                     free( matched_idl_entry->idl );
              free( matched_idl_entry );
       }
       ldap_pvt_thread_rdwr_wunlock( &bdb->bi_idl_tree_rwlock );
}

Here is the call graph for this function:

void bdb_idl_cache_del_id ( struct bdb_info bdb,
DB *  db,
DBT *  key,
ID  id 
)

Definition at line 467 of file idl.c.

{
       bdb_idl_cache_entry_t *cache_entry, idl_tmp;
       DBT2bv( key, &idl_tmp.kstr );
       idl_tmp.db = db;
       ldap_pvt_thread_rdwr_wlock( &bdb->bi_idl_tree_rwlock );
       cache_entry = avl_find( bdb->bi_idl_tree, &idl_tmp,
                                  bdb_idl_entry_cmp );
       if ( cache_entry != NULL ) {
              bdb_idl_delete( cache_entry->idl, id );
              if ( cache_entry->idl[0] == 0 ) {
                     if ( avl_delete( &bdb->bi_idl_tree, (caddr_t) cache_entry,
                                          bdb_idl_entry_cmp ) == NULL ) {
                            Debug( LDAP_DEBUG_ANY, "=> bdb_idl_cache_del: "
                                   "AVL delete failed\n",
                                   0, 0, 0 );
                     }
                     --bdb->bi_idl_cache_size;
                     ldap_pvt_thread_mutex_lock( &bdb->bi_idl_tree_lrulock );
                     IDL_LRU_DELETE( bdb, cache_entry );
                     ldap_pvt_thread_mutex_unlock( &bdb->bi_idl_tree_lrulock );
                     free( cache_entry->kstr.bv_val );
                     free( cache_entry->idl );
                     free( cache_entry );
              }
       }
       ldap_pvt_thread_rdwr_wunlock( &bdb->bi_idl_tree_rwlock );
}

Here is the call graph for this function:

int bdb_idl_cache_get ( struct bdb_info bdb,
DB *  db,
DBT *  key,
ID ids 
)

Definition at line 295 of file idl.c.

{
       bdb_idl_cache_entry_t idl_tmp;
       bdb_idl_cache_entry_t *matched_idl_entry;
       int rc = LDAP_NO_SUCH_OBJECT;

       DBT2bv( key, &idl_tmp.kstr );
       idl_tmp.db = db;
       ldap_pvt_thread_rdwr_rlock( &bdb->bi_idl_tree_rwlock );
       matched_idl_entry = avl_find( bdb->bi_idl_tree, &idl_tmp,
                                  bdb_idl_entry_cmp );
       if ( matched_idl_entry != NULL ) {
              if ( matched_idl_entry->idl && ids )
                     BDB_IDL_CPY( ids, matched_idl_entry->idl );
              matched_idl_entry->idl_flags |= CACHE_ENTRY_REFERENCED;
              if ( matched_idl_entry->idl )
                     rc = LDAP_SUCCESS;
              else
                     rc = DB_NOTFOUND;
       }
       ldap_pvt_thread_rdwr_runlock( &bdb->bi_idl_tree_rwlock );

       return rc;
}

Here is the call graph for this function:

void bdb_idl_cache_put ( struct bdb_info bdb,
DB *  db,
DBT *  key,
ID ids,
int  rc 
)

Definition at line 325 of file idl.c.

{
       bdb_idl_cache_entry_t idl_tmp;
       bdb_idl_cache_entry_t *ee, *eprev;

       if ( rc == DB_NOTFOUND || BDB_IDL_IS_ZERO( ids ))
              return;

       DBT2bv( key, &idl_tmp.kstr );

       ee = (bdb_idl_cache_entry_t *) ch_malloc(
              sizeof( bdb_idl_cache_entry_t ) );
       ee->db = db;
       ee->idl = (ID*) ch_malloc( BDB_IDL_SIZEOF ( ids ) );
       BDB_IDL_CPY( ee->idl, ids );

       ee->idl_lru_prev = NULL;
       ee->idl_lru_next = NULL;
       ee->idl_flags = 0;
       ber_dupbv( &ee->kstr, &idl_tmp.kstr );
       ldap_pvt_thread_rdwr_wlock( &bdb->bi_idl_tree_rwlock );
       if ( avl_insert( &bdb->bi_idl_tree, (caddr_t) ee,
              bdb_idl_entry_cmp, avl_dup_error ))
       {
              ch_free( ee->kstr.bv_val );
              ch_free( ee->idl );
              ch_free( ee );
              ldap_pvt_thread_rdwr_wunlock( &bdb->bi_idl_tree_rwlock );
              return;
       }
       ldap_pvt_thread_mutex_lock( &bdb->bi_idl_tree_lrulock );
       /* LRU_ADD */
       if ( bdb->bi_idl_lru_head ) {
              assert( bdb->bi_idl_lru_tail != NULL );
              assert( bdb->bi_idl_lru_head->idl_lru_prev != NULL );
              assert( bdb->bi_idl_lru_head->idl_lru_next != NULL );

              ee->idl_lru_next = bdb->bi_idl_lru_head;
              ee->idl_lru_prev = bdb->bi_idl_lru_head->idl_lru_prev;
              bdb->bi_idl_lru_head->idl_lru_prev->idl_lru_next = ee;
              bdb->bi_idl_lru_head->idl_lru_prev = ee;
       } else {
              ee->idl_lru_next = ee->idl_lru_prev = ee;
              bdb->bi_idl_lru_tail = ee;
       }
       bdb->bi_idl_lru_head = ee;

       if ( bdb->bi_idl_cache_size >= bdb->bi_idl_cache_max_size ) {
              int i;
              eprev = bdb->bi_idl_lru_tail;
              for ( i = 0; (ee = eprev) != NULL && i < 10; i++ ) {
                     eprev = ee->idl_lru_prev;
                     if ( eprev == ee ) {
                            eprev = NULL;
                     }
                     if ( ee->idl_flags & CACHE_ENTRY_REFERENCED ) {
                            ee->idl_flags ^= CACHE_ENTRY_REFERENCED;
                            continue;
                     }
                     if ( avl_delete( &bdb->bi_idl_tree, (caddr_t) ee,
                                bdb_idl_entry_cmp ) == NULL ) {
                            Debug( LDAP_DEBUG_ANY, "=> bdb_idl_cache_put: "
                                   "AVL delete failed\n",
                                   0, 0, 0 );
                     }
                     IDL_LRU_DELETE( bdb, ee );
                     i++;
                     --bdb->bi_idl_cache_size;
                     ch_free( ee->kstr.bv_val );
                     ch_free( ee->idl );
                     ch_free( ee );
              }
              bdb->bi_idl_lru_tail = eprev;
              assert( bdb->bi_idl_lru_tail != NULL
                     || bdb->bi_idl_lru_head == NULL );
       }
       bdb->bi_idl_cache_size++;
       ldap_pvt_thread_mutex_unlock( &bdb->bi_idl_tree_lrulock );
       ldap_pvt_thread_rdwr_wunlock( &bdb->bi_idl_tree_rwlock );
}

Here is the call graph for this function:

int bdb_idl_delete ( ID ids,
ID  id 
)

Definition at line 220 of file idl.c.

{
       unsigned x;

#if IDL_DEBUG > 1
       Debug( LDAP_DEBUG_ANY, "delete: %04lx at %d\n", (long) id, x, 0 );
       idl_dump( ids );
#elif IDL_DEBUG > 0
       idl_check( ids );
#endif

       if (BDB_IDL_IS_RANGE( ids )) {
              /* If deleting a range boundary, adjust */
              if ( ids[1] == id )
                     ids[1]++;
              else if ( ids[2] == id )
                     ids[2]--;
              /* deleting from inside a range is a no-op */

              /* If the range has collapsed, re-adjust */
              if ( ids[1] > ids[2] )
                     ids[0] = 0;
              else if ( ids[1] == ids[2] )
                     ids[1] = 1;
              return 0;
       }

       x = bdb_idl_search( ids, id );
       assert( x > 0 );

       if( x <= 0 ) {
              /* internal error */
              return -2;
       }

       if( x > ids[0] || ids[x] != id ) {
              /* not found */
              return -1;

       } else if ( --ids[0] == 0 ) {
              if( x != 1 ) {
                     return -3;
              }

       } else {
              AC_MEMCPY( &ids[x], &ids[x+1], (1+ids[0]-x) * sizeof(ID) );
       }

#if IDL_DEBUG > 1
       idl_dump( ids );
#elif IDL_DEBUG > 0
       idl_check( ids );
#endif

       return 0;
}
int bdb_idl_delete_key ( BackendDB be,
DB *  db,
DB_TXN *  txn,
DBT *  key,
ID  id 
)

Definition at line 904 of file idl.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       int    rc;
       DBT data;
       DBC *cursor;
       ID lo, hi, tmp, nid, nlo, nhi;
       char *err;

       {
              char buf[16];
              Debug( LDAP_DEBUG_ARGS,
                     "bdb_idl_delete_key: %lx %s\n", 
                     (long) id, bdb_show_key( key, buf ), 0 );
       }
       assert( id != NOID );

       if ( bdb->bi_idl_cache_size ) {
              bdb_idl_cache_del( bdb, db, key );
       }

       BDB_ID2DISK( id, &nid );

       DBTzero( &data );
       data.data = &tmp;
       data.size = sizeof( id );
       data.ulen = data.size;
       data.flags = DB_DBT_USERMEM;

       rc = db->cursor( db, tid, &cursor, bdb->bi_db_opflags );
       if ( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_delete_key: "
                     "cursor failed: %s (%d)\n", db_strerror(rc), rc, 0 );
              return rc;
       }
       /* Fetch the first data item for this key, to see if it
        * exists and if it's a range.
        */
       rc = cursor->c_get( cursor, key, &data, DB_SET );
       err = "c_get";
       if ( rc == 0 ) {
              if ( tmp != 0 ) {
                     /* Not a range, just delete it */
                     if (tmp != nid) {
                            /* position to correct item */
                            tmp = nid;
                            rc = cursor->c_get( cursor, key, &data, DB_GET_BOTH );
                            if ( rc != 0 ) {
                                   err = "c_get id";
                                   goto fail;
                            }
                     }
                     rc = cursor->c_del( cursor, 0 );
                     if ( rc != 0 ) {
                            err = "c_del id";
                            goto fail;
                     }
              } else {
                     /* It's a range, see if we need to rewrite
                      * the boundaries
                      */
                     data.data = &nlo;
                     rc = cursor->c_get( cursor, key, &data, DB_NEXT_DUP );
                     if ( rc != 0 ) {
                            err = "c_get lo";
                            goto fail;
                     }
                     BDB_DISK2ID( &nlo, &lo );
                     data.data = &nhi;
                     rc = cursor->c_get( cursor, key, &data, DB_NEXT_DUP );
                     if ( rc != 0 ) {
                            err = "c_get hi";
                            goto fail;
                     }
                     BDB_DISK2ID( &nhi, &hi );
                     if ( id == lo || id == hi ) {
                            if ( id == lo ) {
                                   id++;
                                   lo = id;
                            } else if ( id == hi ) {
                                   id--;
                                   hi = id;
                            }
                            if ( lo >= hi ) {
                            /* The range has collapsed... */
                                   rc = db->del( db, tid, key, 0 );
                                   if ( rc != 0 ) {
                                          err = "del";
                                          goto fail;
                                   }
                            } else {
                                   if ( id == lo ) {
                                          /* reposition on lo slot */
                                          data.data = &nlo;
                                          cursor->c_get( cursor, key, &data, DB_PREV );
                                   }
                                   rc = cursor->c_del( cursor, 0 );
                                   if ( rc != 0 ) {
                                          err = "c_del";
                                          goto fail;
                                   }
                            }
                            if ( lo <= hi ) {
                                   BDB_ID2DISK( id, &nid );
                                   data.data = &nid;
                                   rc = cursor->c_put( cursor, key, &data, DB_KEYFIRST );
                                   if ( rc != 0 ) {
                                          err = "c_put lo/hi";
                                          goto fail;
                                   }
                            }
                     }
              }
       } else {
              /* initial c_get failed, nothing was done */
fail:
              if ( rc != DB_NOTFOUND ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_delete_key: "
                     "%s failed: %s (%d)\n", err, db_strerror(rc), rc );
              }
              cursor->c_close( cursor );
              return rc;
       }
       rc = cursor->c_close( cursor );
       if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY,
                     "=> bdb_idl_delete_key: c_close failed: %s (%d)\n",
                     db_strerror(rc), rc, 0 );
       }

       return rc;
}

Here is the call graph for this function:

int bdb_idl_fetch_key ( BackendDB be,
DB *  db,
DB_TXN *  txn,
DBT *  key,
ID ids,
DBC **  saved_cursor,
int  get_flag 
)

Definition at line 501 of file idl.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       int rc;
       DBT data, key2, *kptr;
       DBC *cursor;
       ID *i;
       void *ptr;
       size_t len;
       int rc2;
       int flags = bdb->bi_db_opflags | DB_MULTIPLE;
       int opflag;

       /* If using BerkeleyDB 4.0, the buf must be large enough to
        * grab the entire IDL in one get(), otherwise BDB will leak
        * resources on subsequent get's.  We can safely call get()
        * twice - once for the data, and once to get the DB_NOTFOUND
        * result meaning there's no more data. See ITS#2040 for details.
        * This bug is fixed in BDB 4.1 so a smaller buffer will work if
        * stack space is too limited.
        *
        * configure now requires Berkeley DB 4.1.
        */
#if DB_VERSION_FULL < 0x04010000
#      define BDB_ENOUGH 5
#else
       /* We sometimes test with tiny IDLs, and BDB always wants buffers
        * that are at least one page in size.
        */
# if BDB_IDL_DB_SIZE < 4096
#   define BDB_ENOUGH 2048
# else
#      define BDB_ENOUGH 1
# endif
#endif
       ID buf[BDB_IDL_DB_SIZE*BDB_ENOUGH];

       char keybuf[16];

       Debug( LDAP_DEBUG_ARGS,
              "bdb_idl_fetch_key: %s\n", 
              bdb_show_key( key, keybuf ), 0, 0 );

       assert( ids != NULL );

       if ( saved_cursor && *saved_cursor ) {
              opflag = DB_NEXT;
       } else if ( get_flag == LDAP_FILTER_GE ) {
              opflag = DB_SET_RANGE;
       } else if ( get_flag == LDAP_FILTER_LE ) {
              opflag = DB_FIRST;
       } else {
              opflag = DB_SET;
       }

       /* only non-range lookups can use the IDL cache */
       if ( bdb->bi_idl_cache_size && opflag == DB_SET ) {
              rc = bdb_idl_cache_get( bdb, db, key, ids );
              if ( rc != LDAP_NO_SUCH_OBJECT ) return rc;
       }

       DBTzero( &data );

       data.data = buf;
       data.ulen = sizeof(buf);
       data.flags = DB_DBT_USERMEM;

       /* If we're not reusing an existing cursor, get a new one */
       if( opflag != DB_NEXT ) {
              rc = db->cursor( db, txn, &cursor, bdb->bi_db_opflags );
              if( rc != 0 ) {
                     Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                            "cursor failed: %s (%d)\n", db_strerror(rc), rc, 0 );
                     return rc;
              }
       } else {
              cursor = *saved_cursor;
       }
       
       /* If this is a LE lookup, save original key so we can determine
        * when to stop. If this is a GE lookup, save the key since it
        * will be overwritten.
        */
       if ( get_flag == LDAP_FILTER_LE || get_flag == LDAP_FILTER_GE ) {
              DBTzero( &key2 );
              key2.flags = DB_DBT_USERMEM;
              key2.ulen = sizeof(keybuf);
              key2.data = keybuf;
              key2.size = key->size;
              AC_MEMCPY( keybuf, key->data, key->size );
              kptr = &key2;
       } else {
              kptr = key;
       }
       len = key->size;
       rc = cursor->c_get( cursor, kptr, &data, flags | opflag );

       /* skip presence key on range inequality lookups */
       while (rc == 0 && kptr->size != len) {
              rc = cursor->c_get( cursor, kptr, &data, flags | DB_NEXT_NODUP );
       }
       /* If we're doing a LE compare and the new key is greater than
        * our search key, we're done
        */
       if (rc == 0 && get_flag == LDAP_FILTER_LE && memcmp( kptr->data,
              key->data, key->size ) > 0 ) {
              rc = DB_NOTFOUND;
       }
       if (rc == 0) {
              i = ids;
              while (rc == 0) {
                     u_int8_t *j;

                     DB_MULTIPLE_INIT( ptr, &data );
                     while (ptr) {
                            DB_MULTIPLE_NEXT(ptr, &data, j, len);
                            if (j) {
                                   ++i;
                                   BDB_DISK2ID( j, i );
                            }
                     }
                     rc = cursor->c_get( cursor, key, &data, flags | DB_NEXT_DUP );
              }
              if ( rc == DB_NOTFOUND ) rc = 0;
              ids[0] = i - ids;
              /* On disk, a range is denoted by 0 in the first element */
              if (ids[1] == 0) {
                     if (ids[0] != BDB_IDL_RANGE_SIZE) {
                            Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                                   "range size mismatch: expected %d, got %ld\n",
                                   BDB_IDL_RANGE_SIZE, ids[0], 0 );
                            cursor->c_close( cursor );
                            return -1;
                     }
                     BDB_IDL_RANGE( ids, ids[2], ids[3] );
              }
              data.size = BDB_IDL_SIZEOF(ids);
       }

       if ( saved_cursor && rc == 0 ) {
              if ( !*saved_cursor )
                     *saved_cursor = cursor;
              rc2 = 0;
       }
       else
              rc2 = cursor->c_close( cursor );
       if (rc2) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                     "close failed: %s (%d)\n", db_strerror(rc2), rc2, 0 );
              return rc2;
       }

       if( rc == DB_NOTFOUND ) {
              return rc;

       } else if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                     "get failed: %s (%d)\n",
                     db_strerror(rc), rc, 0 );
              return rc;

       } else if ( data.size == 0 || data.size % sizeof( ID ) ) {
              /* size not multiple of ID size */
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                     "odd size: expected %ld multiple, got %ld\n",
                     (long) sizeof( ID ), (long) data.size, 0 );
              return -1;

       } else if ( data.size != BDB_IDL_SIZEOF(ids) ) {
              /* size mismatch */
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_fetch_key: "
                     "get size mismatch: expected %ld, got %ld\n",
                     (long) ((1 + ids[0]) * sizeof( ID )), (long) data.size, 0 );
              return -1;
       }

       if ( bdb->bi_idl_cache_max_size ) {
              bdb_idl_cache_put( bdb, db, key, ids, rc );
       }

       return rc;
}

Here is the call graph for this function:

ID bdb_idl_first ( ID ids,
ID cursor 
)

Definition at line 1257 of file idl.c.

{
       ID pos;

       if ( ids[0] == 0 ) {
              *cursor = NOID;
              return NOID;
       }

       if ( BDB_IDL_IS_RANGE( ids ) ) {
              if( *cursor < ids[1] ) {
                     *cursor = ids[1];
              }
              return *cursor;
       }

       if ( *cursor == 0 )
              pos = 1;
       else
              pos = bdb_idl_search( ids, *cursor );

       if( pos > ids[0] ) {
              return NOID;
       }

       *cursor = pos;
       return ids[pos];
}
int bdb_idl_insert ( ID ids,
ID  id 
)

Definition at line 159 of file idl.c.

{
       unsigned x;

#if IDL_DEBUG > 1
       Debug( LDAP_DEBUG_ANY, "insert: %04lx at %d\n", (long) id, x, 0 );
       idl_dump( ids );
#elif IDL_DEBUG > 0
       idl_check( ids );
#endif

       if (BDB_IDL_IS_RANGE( ids )) {
              /* if already in range, treat as a dup */
              if (id >= BDB_IDL_RANGE_FIRST(ids) && id <= BDB_IDL_RANGE_LAST(ids))
                     return -1;
              if (id < BDB_IDL_RANGE_FIRST(ids))
                     ids[1] = id;
              else if (id > BDB_IDL_RANGE_LAST(ids))
                     ids[2] = id;
              return 0;
       }

       x = bdb_idl_search( ids, id );
       assert( x > 0 );

       if( x < 1 ) {
              /* internal error */
              return -2;
       }

       if ( x <= ids[0] && ids[x] == id ) {
              /* duplicate */
              return -1;
       }

       if ( ++ids[0] >= BDB_IDL_DB_MAX ) {
              if( id < ids[1] ) {
                     ids[1] = id;
                     ids[2] = ids[ids[0]-1];
              } else if ( ids[ids[0]-1] < id ) {
                     ids[2] = id;
              } else {
                     ids[2] = ids[ids[0]-1];
              }
              ids[0] = NOID;
       
       } else {
              /* insert id */
              AC_MEMCPY( &ids[x+1], &ids[x], (ids[0]-x) * sizeof(ID) );
              ids[x] = id;
       }

#if IDL_DEBUG > 1
       idl_dump( ids );
#elif IDL_DEBUG > 0
       idl_check( ids );
#endif

       return 0;
}
int bdb_idl_insert_key ( BackendDB be,
DB *  db,
DB_TXN *  txn,
DBT *  key,
ID  id 
)

Definition at line 693 of file idl.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       int    rc;
       DBT data;
       DBC *cursor;
       ID lo, hi, nlo, nhi, nid;
       char *err;

       {
              char buf[16];
              Debug( LDAP_DEBUG_ARGS,
                     "bdb_idl_insert_key: %lx %s\n", 
                     (long) id, bdb_show_key( key, buf ), 0 );
       }

       assert( id != NOID );

       DBTzero( &data );
       data.size = sizeof( ID );
       data.ulen = data.size;
       data.flags = DB_DBT_USERMEM;

       BDB_ID2DISK( id, &nid );

       rc = db->cursor( db, tid, &cursor, bdb->bi_db_opflags );
       if ( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_insert_key: "
                     "cursor failed: %s (%d)\n", db_strerror(rc), rc, 0 );
              return rc;
       }
       data.data = &nlo;
       /* Fetch the first data item for this key, to see if it
        * exists and if it's a range.
        */
       rc = cursor->c_get( cursor, key, &data, DB_SET );
       err = "c_get";
       if ( rc == 0 ) {
              if ( nlo != 0 ) {
                     /* not a range, count the number of items */
                     db_recno_t count;
                     rc = cursor->c_count( cursor, &count, 0 );
                     if ( rc != 0 ) {
                            err = "c_count";
                            goto fail;
                     }
                     if ( count >= BDB_IDL_DB_MAX ) {
                     /* No room, convert to a range */
                            DBT key2 = *key;
                            db_recno_t i;

                            key2.dlen = key2.ulen;
                            key2.flags |= DB_DBT_PARTIAL;

                            BDB_DISK2ID( &nlo, &lo );
                            data.data = &nhi;

                            rc = cursor->c_get( cursor, &key2, &data, DB_NEXT_NODUP );
                            if ( rc != 0 && rc != DB_NOTFOUND ) {
                                   err = "c_get next_nodup";
                                   goto fail;
                            }
                            if ( rc == DB_NOTFOUND ) {
                                   rc = cursor->c_get( cursor, key, &data, DB_LAST );
                                   if ( rc != 0 ) {
                                          err = "c_get last";
                                          goto fail;
                                   }
                            } else {
                                   rc = cursor->c_get( cursor, key, &data, DB_PREV );
                                   if ( rc != 0 ) {
                                          err = "c_get prev";
                                          goto fail;
                                   }
                            }
                            BDB_DISK2ID( &nhi, &hi );
                            /* Update hi/lo if needed, then delete all the items
                             * between lo and hi
                             */
                            if ( id < lo ) {
                                   lo = id;
                                   nlo = nid;
                            } else if ( id > hi ) {
                                   hi = id;
                                   nhi = nid;
                            }
                            data.data = &nid;
                            /* Don't fetch anything, just position cursor */
                            data.flags = DB_DBT_USERMEM | DB_DBT_PARTIAL;
                            data.dlen = data.ulen = 0;
                            rc = cursor->c_get( cursor, key, &data, DB_SET );
                            if ( rc != 0 ) {
                                   err = "c_get 2";
                                   goto fail;
                            }
                            rc = cursor->c_del( cursor, 0 );
                            if ( rc != 0 ) {
                                   err = "c_del range1";
                                   goto fail;
                            }
                            /* Delete all the records */
                            for ( i=1; i<count; i++ ) {
                                   rc = cursor->c_get( cursor, &key2, &data, DB_NEXT_DUP );
                                   if ( rc != 0 ) {
                                          err = "c_get next_dup";
                                          goto fail;
                                   }
                                   rc = cursor->c_del( cursor, 0 );
                                   if ( rc != 0 ) {
                                          err = "c_del range";
                                          goto fail;
                                   }
                            }
                            /* Store the range marker */
                            data.size = data.ulen = sizeof(ID);
                            data.flags = DB_DBT_USERMEM;
                            nid = 0;
                            rc = cursor->c_put( cursor, key, &data, DB_KEYFIRST );
                            if ( rc != 0 ) {
                                   err = "c_put range";
                                   goto fail;
                            }
                            nid = nlo;
                            rc = cursor->c_put( cursor, key, &data, DB_KEYLAST );
                            if ( rc != 0 ) {
                                   err = "c_put lo";
                                   goto fail;
                            }
                            nid = nhi;
                            rc = cursor->c_put( cursor, key, &data, DB_KEYLAST );
                            if ( rc != 0 ) {
                                   err = "c_put hi";
                                   goto fail;
                            }
                     } else {
                     /* There's room, just store it */
                            goto put1;
                     }
              } else {
                     /* It's a range, see if we need to rewrite
                      * the boundaries
                      */
                     hi = id;
                     data.data = &nlo;
                     rc = cursor->c_get( cursor, key, &data, DB_NEXT_DUP );
                     if ( rc != 0 ) {
                            err = "c_get lo";
                            goto fail;
                     }
                     BDB_DISK2ID( &nlo, &lo );
                     if ( id > lo ) {
                            data.data = &nhi;
                            rc = cursor->c_get( cursor, key, &data, DB_NEXT_DUP );
                            if ( rc != 0 ) {
                                   err = "c_get hi";
                                   goto fail;
                            }
                            BDB_DISK2ID( &nhi, &hi );
                     }
                     if ( id < lo || id > hi ) {
                            /* Delete the current lo/hi */
                            rc = cursor->c_del( cursor, 0 );
                            if ( rc != 0 ) {
                                   err = "c_del";
                                   goto fail;
                            }
                            data.data = &nid;
                            rc = cursor->c_put( cursor, key, &data, DB_KEYFIRST );
                            if ( rc != 0 ) {
                                   err = "c_put lo/hi";
                                   goto fail;
                            }
                     }
              }
       } else if ( rc == DB_NOTFOUND ) {
put1:         data.data = &nid;
              rc = cursor->c_put( cursor, key, &data, DB_NODUPDATA );
              /* Don't worry if it's already there */
              if ( rc != 0 && rc != DB_KEYEXIST ) {
                     err = "c_put id";
                     goto fail;
              }
       } else {
              /* initial c_get failed, nothing was done */
fail:
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_insert_key: "
                     "%s failed: %s (%d)\n", err, db_strerror(rc), rc );
              cursor->c_close( cursor );
              return rc;
       }
       /* If key was added (didn't already exist) and using IDL cache,
        * update key in IDL cache.
        */
       if ( !rc && bdb->bi_idl_cache_max_size ) {
              bdb_idl_cache_add_id( bdb, db, key, id );
       }
       rc = cursor->c_close( cursor );
       if( rc != 0 ) {
              Debug( LDAP_DEBUG_ANY, "=> bdb_idl_insert_key: "
                     "c_close failed: %s (%d)\n",
                     db_strerror(rc), rc, 0 );
       }
       return rc;
}

Here is the call graph for this function:

int bdb_idl_intersection ( ID a,
ID b 
)

Definition at line 1047 of file idl.c.

{
       ID ida, idb;
       ID idmax, idmin;
       ID cursora = 0, cursorb = 0, cursorc;
       int swap = 0;

       if ( BDB_IDL_IS_ZERO( a ) || BDB_IDL_IS_ZERO( b ) ) {
              a[0] = 0;
              return 0;
       }

       idmin = IDL_MAX( BDB_IDL_FIRST(a), BDB_IDL_FIRST(b) );
       idmax = IDL_MIN( BDB_IDL_LAST(a), BDB_IDL_LAST(b) );
       if ( idmin > idmax ) {
              a[0] = 0;
              return 0;
       } else if ( idmin == idmax ) {
              a[0] = 1;
              a[1] = idmin;
              return 0;
       }

       if ( BDB_IDL_IS_RANGE( a ) ) {
              if ( BDB_IDL_IS_RANGE(b) ) {
              /* If both are ranges, just shrink the boundaries */
                     a[1] = idmin;
                     a[2] = idmax;
                     return 0;
              } else {
              /* Else swap so that b is the range, a is a list */
                     ID *tmp = a;
                     a = b;
                     b = tmp;
                     swap = 1;
              }
       }

       /* If a range completely covers the list, the result is
        * just the list. If idmin to idmax is contiguous, just
        * turn it into a range.
        */
       if ( BDB_IDL_IS_RANGE( b )
              && BDB_IDL_RANGE_FIRST( b ) <= BDB_IDL_RANGE_FIRST( a )
              && BDB_IDL_RANGE_LAST( b ) >= BDB_IDL_RANGE_LAST( a ) ) {
              if (idmax - idmin + 1 == a[0])
              {
                     a[0] = NOID;
                     a[1] = idmin;
                     a[2] = idmax;
              }
              goto done;
       }

       /* Fine, do the intersection one element at a time.
        * First advance to idmin in both IDLs.
        */
       cursora = cursorb = idmin;
       ida = bdb_idl_first( a, &cursora );
       idb = bdb_idl_first( b, &cursorb );
       cursorc = 0;

       while( ida <= idmax || idb <= idmax ) {
              if( ida == idb ) {
                     a[++cursorc] = ida;
                     ida = bdb_idl_next( a, &cursora );
                     idb = bdb_idl_next( b, &cursorb );
              } else if ( ida < idb ) {
                     ida = bdb_idl_next( a, &cursora );
              } else {
                     idb = bdb_idl_next( b, &cursorb );
              }
       }
       a[0] = cursorc;
done:
       if (swap)
              BDB_IDL_CPY( b, a );

       return 0;
}
ID bdb_idl_next ( ID ids,
ID cursor 
)

Definition at line 1286 of file idl.c.

{
       if ( BDB_IDL_IS_RANGE( ids ) ) {
              if( ids[2] < ++(*cursor) ) {
                     return NOID;
              }
              return *cursor;
       }

       if ( ++(*cursor) <= ids[0] ) {
              return ids[*cursor];
       }

       return NOID;
}
unsigned bdb_idl_search ( ID ids,
ID  id 
)

Definition at line 101 of file idl.c.

{
#define IDL_BINARY_SEARCH 1
#ifdef IDL_BINARY_SEARCH
       /*
        * binary search of id in ids
        * if found, returns position of id
        * if not found, returns first postion greater than id
        */
       unsigned base = 0;
       unsigned cursor = 1;
       int val = 0;
       unsigned n = ids[0];

#if IDL_DEBUG > 0
       idl_check( ids );
#endif

       while( 0 < n ) {
              unsigned pivot = n >> 1;
              cursor = base + pivot + 1;
              val = IDL_CMP( id, ids[cursor] );

              if( val < 0 ) {
                     n = pivot;

              } else if ( val > 0 ) {
                     base = cursor;
                     n -= pivot + 1;

              } else {
                     return cursor;
              }
       }
       
       if( val > 0 ) {
              ++cursor;
       }
       return cursor;

#else
       /* (reverse) linear search */
       int i;

#if IDL_DEBUG > 0
       idl_check( ids );
#endif

       for( i=ids[0]; i; i-- ) {
              if( id > ids[i] ) {
                     break;
              }
       }

       return i+1;
#endif
}
void bdb_idl_sort ( ID ids,
ID tmp 
)
int bdb_idl_union ( ID a,
ID b 
)

Definition at line 1135 of file idl.c.

{
       ID ida, idb;
       ID cursora = 0, cursorb = 0, cursorc;

       if ( BDB_IDL_IS_ZERO( b ) ) {
              return 0;
       }

       if ( BDB_IDL_IS_ZERO( a ) ) {
              BDB_IDL_CPY( a, b );
              return 0;
       }

       if ( BDB_IDL_IS_RANGE( a ) || BDB_IDL_IS_RANGE(b) ) {
over:         ida = IDL_MIN( BDB_IDL_FIRST(a), BDB_IDL_FIRST(b) );
              idb = IDL_MAX( BDB_IDL_LAST(a), BDB_IDL_LAST(b) );
              a[0] = NOID;
              a[1] = ida;
              a[2] = idb;
              return 0;
       }

       ida = bdb_idl_first( a, &cursora );
       idb = bdb_idl_first( b, &cursorb );

       cursorc = b[0];

       /* The distinct elements of a are cat'd to b */
       while( ida != NOID || idb != NOID ) {
              if ( ida < idb ) {
                     if( ++cursorc > BDB_IDL_UM_MAX ) {
                            goto over;
                     }
                     b[cursorc] = ida;
                     ida = bdb_idl_next( a, &cursora );

              } else {
                     if ( ida == idb )
                            ida = bdb_idl_next( a, &cursora );
                     idb = bdb_idl_next( b, &cursorb );
              }
       }

       /* b is copied back to a in sorted order */
       a[0] = cursorc;
       cursora = 1;
       cursorb = 1;
       cursorc = b[0]+1;
       while (cursorb <= b[0] || cursorc <= a[0]) {
              if (cursorc > a[0])
                     idb = NOID;
              else
                     idb = b[cursorc];
              if (cursorb <= b[0] && b[cursorb] < idb)
                     a[cursora++] = b[cursorb++];
              else {
                     a[cursora++] = idb;
                     cursorc++;
              }
       }

       return 0;
}
int bdb_key_change ( Backend be,
DB *  db,
DB_TXN *  txn,
struct berval k,
ID  id,
int  op 
)

Definition at line 65 of file key.c.

{
       int    rc;
       DBT    key;

       Debug( LDAP_DEBUG_TRACE, "=> key_change(%s,%lx)\n",
              op == SLAP_INDEX_ADD_OP ? "ADD":"DELETE", (long) id, 0 );

       DBTzero( &key );
       bv2DBT(k,&key);
       key.ulen = key.size;
       key.flags = DB_DBT_USERMEM;

       if (op == SLAP_INDEX_ADD_OP) {
              /* Add values */

#ifdef BDB_TOOL_IDL_CACHING
              if ( slapMode & SLAP_TOOL_QUICK )
                     rc = bdb_tool_idl_add( be, db, txn, &key, id );
              else
#endif
                     rc = bdb_idl_insert_key( be, db, txn, &key, id );
              if ( rc == DB_KEYEXIST ) rc = 0;
       } else {
              /* Delete values */
              rc = bdb_idl_delete_key( be, db, txn, &key, id );
              if ( rc == DB_NOTFOUND ) rc = 0;
       }

       Debug( LDAP_DEBUG_TRACE, "<= key_change %d\n", rc, 0, 0 );

       return rc;
}

Here is the call graph for this function:

int bdb_key_read ( Backend be,
DB *  db,
DB_TXN *  txn,
struct berval k,
ID ids,
DBC **  saved_cursor,
int  get_flags 
)

Definition at line 30 of file key.c.

{
       int rc;
       DBT key;

       Debug( LDAP_DEBUG_TRACE, "=> key_read\n", 0, 0, 0 );

       DBTzero( &key );
       bv2DBT(k,&key);
       key.ulen = key.size;
       key.flags = DB_DBT_USERMEM;

       rc = bdb_idl_fetch_key( be, db, txn, &key, ids, saved_cursor, get_flag );

       if( rc != LDAP_SUCCESS ) {
              Debug( LDAP_DEBUG_TRACE, "<= bdb_index_read: failed (%d)\n",
                     rc, 0, 0 );
       } else {
              Debug( LDAP_DEBUG_TRACE, "<= bdb_index_read %ld candidates\n",
                     (long) BDB_IDL_N(ids), 0, 0 );
       }

       return rc;
}
int bdb_last_id ( BackendDB be,
DB_TXN *  tid 
)

Definition at line 35 of file nextid.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;
       int rc;
       ID id = 0;
       unsigned char idbuf[sizeof(ID)];
       DBT key, data;
       DBC *cursor;

       DBTzero( &key );
       key.flags = DB_DBT_USERMEM;
       key.data = (char *) idbuf;
       key.ulen = sizeof( idbuf );

       DBTzero( &data );
       data.flags = DB_DBT_USERMEM | DB_DBT_PARTIAL;

       /* Get a read cursor */
       rc = bdb->bi_id2entry->bdi_db->cursor( bdb->bi_id2entry->bdi_db,
              tid, &cursor, 0 );

       if (rc == 0) {
              rc = cursor->c_get(cursor, &key, &data, DB_LAST);
              cursor->c_close(cursor);
       }

       switch(rc) {
       case DB_NOTFOUND:
              rc = 0;
              break;
       case 0:
              BDB_DISK2ID( idbuf, &id );
              break;

       default:
              Debug( LDAP_DEBUG_ANY,
                     "=> bdb_last_id: get failed: %s (%d)\n",
                     db_strerror(rc), rc, 0 );
              goto done;
       }

       bdb->bi_lastid = id;

done:
       return rc;
}
int bdb_modify_internal ( Operation op,
DB_TXN *  tid,
Modifications modlist,
Entry e,
const char **  text,
char *  textbuf,
size_t  textlen 
)

Definition at line 68 of file modify.c.

{
       int rc, err;
       Modification  *mod;
       Modifications *ml;
       Attribute     *save_attrs;
       Attribute     *ap;
       int                  glue_attr_delete = 0;
       int                  got_delete;

       Debug( LDAP_DEBUG_TRACE, "bdb_modify_internal: 0x%08lx: %s\n",
              e->e_id, e->e_dn, 0);

       if ( !acl_check_modlist( op, e, modlist )) {
              return LDAP_INSUFFICIENT_ACCESS;
       }

       /* save_attrs will be disposed of by bdb_cache_modify */
       save_attrs = e->e_attrs;
       e->e_attrs = attrs_dup( e->e_attrs );

       for ( ml = modlist; ml != NULL; ml = ml->sml_next ) {
              int match;
              mod = &ml->sml_mod;
              switch( mod->sm_op ) {
              case LDAP_MOD_ADD:
              case LDAP_MOD_REPLACE:
                     if ( mod->sm_desc == slap_schema.si_ad_structuralObjectClass ) {
                            value_match( &match, slap_schema.si_ad_structuralObjectClass,
                                   slap_schema.si_ad_structuralObjectClass->
                                          ad_type->sat_equality,
                                   SLAP_MR_VALUE_OF_ATTRIBUTE_SYNTAX,
                                   &mod->sm_values[0], &scbva[0], text );
                            if ( !match ) glue_attr_delete = 1;
                     }
              }
              if ( glue_attr_delete )
                     break;
       }

       if ( glue_attr_delete ) {
              Attribute     **app = &e->e_attrs;
              while ( *app != NULL ) {
                     if ( !is_at_operational( (*app)->a_desc->ad_type )) {
                            Attribute *save = *app;
                            *app = (*app)->a_next;
                            attr_free( save );
                            continue;
                     }
                     app = &(*app)->a_next;
              }
       }

       for ( ml = modlist; ml != NULL; ml = ml->sml_next ) {
              mod = &ml->sml_mod;
              got_delete = 0;

              switch ( mod->sm_op ) {
              case LDAP_MOD_ADD:
                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: add %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     err = modify_add_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );
                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     }
                     break;

              case LDAP_MOD_DELETE:
                     if ( glue_attr_delete ) {
                            err = LDAP_SUCCESS;
                            break;
                     }

                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: delete %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     err = modify_delete_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );
                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     } else {
                            got_delete = 1;
                     }
                     break;

              case LDAP_MOD_REPLACE:
                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: replace %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     err = modify_replace_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );
                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     } else {
                            got_delete = 1;
                     }
                     break;

              case LDAP_MOD_INCREMENT:
                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: increment %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     err = modify_increment_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );
                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS,
                                   "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     } else {
                            got_delete = 1;
                     }
                     break;

              case SLAP_MOD_SOFTADD:
                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: softadd %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     /* Avoid problems in index_add_mods()
                      * We need to add index if necessary.
                      */
                     mod->sm_op = LDAP_MOD_ADD;

                     err = modify_add_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );

                     mod->sm_op = SLAP_MOD_SOFTADD;

                     if ( err == LDAP_TYPE_OR_VALUE_EXISTS ) {
                            err = LDAP_SUCCESS;
                     }

                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     }
                     break;

              case SLAP_MOD_SOFTDEL:
                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: softdel %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     /* Avoid problems in index_delete_mods()
                      * We need to add index if necessary.
                      */
                     mod->sm_op = LDAP_MOD_DELETE;

                     err = modify_delete_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );

                     mod->sm_op = SLAP_MOD_SOFTDEL;

                     if ( err == LDAP_NO_SUCH_ATTRIBUTE ) {
                            err = LDAP_SUCCESS;
                     }

                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     }
                     break;

              case SLAP_MOD_ADD_IF_NOT_PRESENT:
                     if ( attr_find( e->e_attrs, mod->sm_desc ) != NULL ) {
                            /* skip */
                            err = LDAP_SUCCESS;
                            break;
                     }

                     Debug(LDAP_DEBUG_ARGS,
                            "bdb_modify_internal: add_if_not_present %s\n",
                            mod->sm_desc->ad_cname.bv_val, 0, 0);
                     /* Avoid problems in index_add_mods()
                      * We need to add index if necessary.
                      */
                     mod->sm_op = LDAP_MOD_ADD;

                     err = modify_add_values( e, mod, get_permissiveModify(op),
                            text, textbuf, textlen );

                     mod->sm_op = SLAP_MOD_ADD_IF_NOT_PRESENT;

                     if( err != LDAP_SUCCESS ) {
                            Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                                   err, *text, 0);
                     }
                     break;

              default:
                     Debug(LDAP_DEBUG_ANY, "bdb_modify_internal: invalid op %d\n",
                            mod->sm_op, 0, 0);
                     *text = "Invalid modify operation";
                     err = LDAP_OTHER;
                     Debug(LDAP_DEBUG_ARGS, "bdb_modify_internal: %d %s\n",
                            err, *text, 0);
              }

              if ( err != LDAP_SUCCESS ) {
                     attrs_free( e->e_attrs );
                     e->e_attrs = save_attrs;
                     /* unlock entry, delete from cache */
                     return err; 
              }

              /* If objectClass was modified, reset the flags */
              if ( mod->sm_desc == slap_schema.si_ad_objectClass ) {
                     e->e_ocflags = 0;
              }

              if ( glue_attr_delete ) e->e_ocflags = 0;


              /* check if modified attribute was indexed
               * but not in case of NOOP... */
              if ( !op->o_noop ) {
                     bdb_modify_idxflags( op, mod->sm_desc, got_delete, e->e_attrs, save_attrs );
              }
       }

       /* check that the entry still obeys the schema */
       ap = NULL;
       rc = entry_schema_check( op, e, save_attrs, get_relax(op), 0, &ap,
              text, textbuf, textlen );
       if ( rc != LDAP_SUCCESS || op->o_noop ) {
              attrs_free( e->e_attrs );
              /* clear the indexing flags */
              for ( ap = save_attrs; ap != NULL; ap = ap->a_next ) {
                     ap->a_flags &= ~(SLAP_ATTR_IXADD|SLAP_ATTR_IXDEL);
              }
              e->e_attrs = save_attrs;

              if ( rc != LDAP_SUCCESS ) {
                     Debug( LDAP_DEBUG_ANY,
                            "entry failed schema check: %s\n",
                            *text, 0, 0 );
              }

              /* if NOOP then silently revert to saved attrs */
              return rc;
       }

       /* structuralObjectClass modified! */
       if ( ap ) {
              assert( ap->a_desc == slap_schema.si_ad_structuralObjectClass );
              if ( !op->o_noop ) {
                     bdb_modify_idxflags( op, slap_schema.si_ad_structuralObjectClass,
                            1, e->e_attrs, save_attrs );
              }
       }

       /* update the indices of the modified attributes */

       /* start with deleting the old index entries */
       for ( ap = save_attrs; ap != NULL; ap = ap->a_next ) {
              if ( ap->a_flags & SLAP_ATTR_IXDEL ) {
                     struct berval *vals;
                     Attribute *a2;
                     ap->a_flags &= ~SLAP_ATTR_IXDEL;
                     a2 = attr_find( e->e_attrs, ap->a_desc );
                     if ( a2 ) {
                            /* need to detect which values were deleted */
                            int i, j;
                            vals = op->o_tmpalloc( (ap->a_numvals + 1) *
                                   sizeof(struct berval), op->o_tmpmemctx );
                            j = 0;
                            for ( i=0; i < ap->a_numvals; i++ ) {
                                   rc = attr_valfind( a2, SLAP_MR_ASSERTED_VALUE_NORMALIZED_MATCH,
                                          &ap->a_nvals[i], NULL, op->o_tmpmemctx );
                                   /* Save deleted values */
                                   if ( rc == LDAP_NO_SUCH_ATTRIBUTE )
                                          vals[j++] = ap->a_nvals[i];
                            }
                            BER_BVZERO(vals+j);
                     } else {
                            /* attribute was completely deleted */
                            vals = ap->a_nvals;
                     }
                     rc = 0;
                     if ( !BER_BVISNULL( vals )) {
                            rc = bdb_index_values( op, tid, ap->a_desc,
                                   vals, e->e_id, SLAP_INDEX_DELETE_OP );
                            if ( rc != LDAP_SUCCESS ) {
                                   Debug( LDAP_DEBUG_ANY,
                                          "%s: attribute \"%s\" index delete failure\n",
                                          op->o_log_prefix, ap->a_desc->ad_cname.bv_val, 0 );
                                   attrs_free( e->e_attrs );
                                   e->e_attrs = save_attrs;
                            }
                     }
                     if ( vals != ap->a_nvals )
                            op->o_tmpfree( vals, op->o_tmpmemctx );
                     if ( rc ) return rc;
              }
       }

       /* add the new index entries */
       for ( ap = e->e_attrs; ap != NULL; ap = ap->a_next ) {
              if (ap->a_flags & SLAP_ATTR_IXADD) {
                     ap->a_flags &= ~SLAP_ATTR_IXADD;
                     rc = bdb_index_values( op, tid, ap->a_desc,
                            ap->a_nvals,
                            e->e_id, SLAP_INDEX_ADD_OP );
                     if ( rc != LDAP_SUCCESS ) {
                            Debug( LDAP_DEBUG_ANY,
                                   "%s: attribute \"%s\" index add failure\n",
                                   op->o_log_prefix, ap->a_desc->ad_cname.bv_val, 0 );
                            attrs_free( e->e_attrs );
                            e->e_attrs = save_attrs;
                            return rc;
                     }
              }
       }

       return rc;
}

Here is the call graph for this function:

Definition at line 491 of file monitor.c.

{
       struct bdb_info             *bdb = (struct bdb_info *) be->be_private;

       if ( !BER_BVISNULL( &bdb->bi_monitor.bdm_ndn ) ) {
              BackendInfo          *mi = backend_info( "monitor" );
              monitor_extra_t             *mbe;

              if ( mi && &mi->bi_extra ) {
                     mbe = mi->bi_extra;
                     mbe->unregister_entry_callback( &bdb->bi_monitor.bdm_ndn,
                            (monitor_callback_t *)bdb->bi_monitor.bdm_cb,
                            NULL, 0, NULL );
              }

              memset( &bdb->bi_monitor, 0, sizeof( bdb->bi_monitor ) );
       }

       return 0;
}

Here is the call graph for this function:

Definition at line 516 of file monitor.c.

{
#ifdef BDB_MONITOR_IDX
       struct bdb_info             *bdb = (struct bdb_info *) be->be_private;

       /* TODO: free tree */
       ldap_pvt_thread_mutex_destroy( &bdb->bi_idx_mutex );
       avl_free( bdb->bi_idx, ch_free );
#endif /* BDB_MONITOR_IDX */

       return 0;
}

Here is the call graph for this function:

Definition at line 313 of file monitor.c.

{
       struct bdb_info             *bdb = (struct bdb_info *) be->be_private;

       if ( bdb_monitor_initialize() == LDAP_SUCCESS ) {
              /* monitoring in back-bdb is on by default */
              SLAP_DBFLAGS( be ) |= SLAP_DBFLAG_MONITORING;
       }

#ifdef BDB_MONITOR_IDX
       bdb->bi_idx = NULL;
       ldap_pvt_thread_mutex_init( &bdb->bi_idx_mutex );
#endif /* BDB_MONITOR_IDX */

       return 0;
}

Here is the call graph for this function:

Definition at line 334 of file monitor.c.

{
       struct bdb_info             *bdb = (struct bdb_info *) be->be_private;
       Attribute            *a, *next;
       monitor_callback_t   *cb = NULL;
       int                  rc = 0;
       BackendInfo          *mi;
       monitor_extra_t             *mbe;
       struct berval dummy = BER_BVC("");

       if ( !SLAP_DBMONITORING( be ) ) {
              return 0;
       }

       mi = backend_info( "monitor" );
       if ( !mi || !mi->bi_extra ) {
              SLAP_DBFLAGS( be ) ^= SLAP_DBFLAG_MONITORING;
              return 0;
       }
       mbe = mi->bi_extra;

       /* don't bother if monitor is not configured */
       if ( !mbe->is_configured() ) {
              static int warning = 0;

              if ( warning++ == 0 ) {
                     Debug( LDAP_DEBUG_ANY, LDAP_XSTRING(bdb_monitor_db_open)
                            ": monitoring disabled; "
                            "configure monitor database to enable\n",
                            0, 0, 0 );
              }

              return 0;
       }

       /* alloc as many as required (plus 1 for objectClass) */
       a = attrs_alloc( 1 + 4 );
       if ( a == NULL ) {
              rc = 1;
              goto cleanup;
       }

       a->a_desc = slap_schema.si_ad_objectClass;
       attr_valadd( a, &oc_olmBDBDatabase->soc_cname, NULL, 1 );
       next = a->a_next;

       {
              struct berval bv = BER_BVC( "0" );

              next->a_desc = ad_olmBDBEntryCache;
              attr_valadd( next, &bv, NULL, 1 );
              next = next->a_next;

              next->a_desc = ad_olmBDBDNCache;
              attr_valadd( next, &bv, NULL, 1 );
              next = next->a_next;

              next->a_desc = ad_olmBDBIDLCache;
              attr_valadd( next, &bv, NULL, 1 );
              next = next->a_next;
       }

       {
              struct berval bv, nbv;
              ber_len_t     pathlen = 0, len = 0;
              char          path[ MAXPATHLEN ] = { '\0' };
              char          *fname = bdb->bi_dbenv_home,
                            *ptr;

              len = strlen( fname );
              if ( fname[ 0 ] != '/' ) {
                     /* get full path name */
                     getcwd( path, sizeof( path ) );
                     pathlen = strlen( path );

                     if ( fname[ 0 ] == '.' && fname[ 1 ] == '/' ) {
                            fname += 2;
                            len -= 2;
                     }
              }

              bv.bv_len = pathlen + STRLENOF( "/" ) + len;
              ptr = bv.bv_val = ch_malloc( bv.bv_len + STRLENOF( "/" ) + 1 );
              if ( pathlen ) {
                     ptr = lutil_strncopy( ptr, path, pathlen );
                     ptr[ 0 ] = '/';
                     ptr++;
              }
              ptr = lutil_strncopy( ptr, fname, len );
              if ( ptr[ -1 ] != '/' ) {
                     ptr[ 0 ] = '/';
                     ptr++;
              }
              ptr[ 0 ] = '\0';
              
              attr_normalize_one( ad_olmDbDirectory, &bv, &nbv, NULL );

              next->a_desc = ad_olmDbDirectory;
              next->a_vals = ch_calloc( sizeof( struct berval ), 2 );
              next->a_vals[ 0 ] = bv;
              next->a_numvals = 1;

              if ( BER_BVISNULL( &nbv ) ) {
                     next->a_nvals = next->a_vals;

              } else {
                     next->a_nvals = ch_calloc( sizeof( struct berval ), 2 );
                     next->a_nvals[ 0 ] = nbv;
              }

              next = next->a_next;
       }

       cb = ch_calloc( sizeof( monitor_callback_t ), 1 );
       cb->mc_update = bdb_monitor_update;
#if 0  /* uncomment if required */
       cb->mc_modify = bdb_monitor_modify;
#endif
       cb->mc_free = bdb_monitor_free;
       cb->mc_private = (void *)bdb;

       /* make sure the database is registered; then add monitor attributes */
       rc = mbe->register_database( be, &bdb->bi_monitor.bdm_ndn );
       if ( rc == 0 ) {
              rc = mbe->register_entry_attrs( &bdb->bi_monitor.bdm_ndn, a, cb,
                     &dummy, 0, &dummy );
       }

cleanup:;
       if ( rc != 0 ) {
              if ( cb != NULL ) {
                     ch_free( cb );
                     cb = NULL;
              }

              if ( a != NULL ) {
                     attrs_free( a );
                     a = NULL;
              }
       }

       /* store for cleanup */
       bdb->bi_monitor.bdm_cb = (void *)cb;

       /* we don't need to keep track of the attributes, because
        * bdb_monitor_free() takes care of everything */
       if ( a != NULL ) {
              attrs_free( a );
       }

       return rc;
}

Here is the call graph for this function:

int bdb_next_id ( BackendDB be,
ID id 
)

Definition at line 24 of file nextid.c.

{
       struct bdb_info *bdb = (struct bdb_info *) be->be_private;

       ldap_pvt_thread_mutex_lock( &bdb->bi_lastid_mutex );
       *out = ++bdb->bi_lastid;
       ldap_pvt_thread_mutex_unlock( &bdb->bi_lastid_mutex );

       return 0;
}
void bdb_reader_flush ( DB_ENV *  env)

Definition at line 1631 of file cache.c.

{
       void *data;
       void *ctx = ldap_pvt_thread_pool_context();

       if ( !ldap_pvt_thread_pool_getkey( ctx, env, &data, NULL ) ) {
              ldap_pvt_thread_pool_setkey( ctx, env, NULL, 0, NULL, NULL );
              bdb_reader_free( env, data );
       }
}

Here is the call graph for this function:

int bdb_reader_get ( Operation op,
DB_ENV *  env,
DB_TXN **  txn 
)

Definition at line 1643 of file cache.c.

{
       int i, rc;
       void *data;
       void *ctx;

       if ( !env || !txn ) return -1;

       /* If no op was provided, try to find the ctx anyway... */
       if ( op ) {
              ctx = op->o_threadctx;
       } else {
              ctx = ldap_pvt_thread_pool_context();
       }

       /* Shouldn't happen unless we're single-threaded */
       if ( !ctx ) {
              *txn = NULL;
              return 0;
       }

       if ( ldap_pvt_thread_pool_getkey( ctx, env, &data, NULL ) ) {
              for ( i=0, rc=1; rc != 0 && i<4; i++ ) {
                     rc = TXN_BEGIN( env, NULL, txn, DB_READ_COMMITTED );
                     if (rc) ldap_pvt_thread_yield();
              }
              if ( rc != 0) {
                     return rc;
              }
              data = *txn;
              if ( ( rc = ldap_pvt_thread_pool_setkey( ctx, env,
                     data, bdb_reader_free, NULL, NULL ) ) ) {
                     TXN_ABORT( *txn );
                     Debug( LDAP_DEBUG_ANY, "bdb_reader_get: err %s(%d)\n",
                            db_strerror(rc), rc, 0 );

                     return rc;
              }
       } else {
              *txn = data;
       }
       return 0;
}

Here is the call graph for this function:

int bdb_tool_idl_add ( BackendDB be,
DB *  db,
DB_TXN *  txn,
DBT *  key,
ID  id 
)

Here is the caller graph for this function:

void bdb_trans_backoff ( int  num_retries)

Definition at line 32 of file trans.c.

{
       int i;
       int delay = 0;
       int pow_retries = 1;
       unsigned long key = 0;
       unsigned long max_key = -1;
       struct timeval timeout;

       lutil_entropy( (unsigned char *) &key, sizeof( unsigned long ));

       for ( i = 0; i < num_retries; i++ ) {
              if ( i >= 5 ) break;
              pow_retries *= 4;
       }

       delay = 16384 * (key * (double) pow_retries / (double) max_key);
       delay = delay ? delay : 1;

       Debug( LDAP_DEBUG_TRACE,  "delay = %d, num_retries = %d\n", delay, num_retries, 0 );

       timeout.tv_sec = delay / 1000000;
       timeout.tv_usec = delay % 1000000;
       select( 0, NULL, NULL, NULL, &timeout );
}

Here is the call graph for this function:

int bdb_attr_index_config LDAP_P ( (struct bdb_info *bdb, const char *fname, int lineno, int argc, char **argv, struct config_reply_s *cr )
int bdb_dn2entry LDAP_P ( (Operation *op, DB_TXN *tid, struct berval *dn, EntryInfo **e, int matched, DB_LOCK *lock)  )
int bdb_index_param LDAP_P ( (Backend *be, AttributeDescription *desc, int ftype, DB **db, slap_mask_t *mask, struct berval *prefix)  )
int bdb_index_entry LDAP_P ( (Operation *op, DB_TXN *t, int r, Entry *e )

Variable Documentation

BI_db_config bdb_db_config
BI_entry_get_rw bdb_entry_get

Definition at line 233 of file proto-bdb.h.

BI_entry_release_rw bdb_entry_release

Definition at line 232 of file proto-bdb.h.

BI_has_subordinates bdb_hasSubordinates
BI_operational bdb_operational
BI_tool_dn2id_get bdb_tool_dn2id_get
BI_tool_entry_close bdb_tool_entry_close
BI_tool_entry_first_x bdb_tool_entry_first_x
BI_tool_entry_get bdb_tool_entry_get
BI_tool_entry_modify bdb_tool_entry_modify
BI_tool_entry_next bdb_tool_entry_next
BI_tool_entry_open bdb_tool_entry_open
BI_tool_entry_put bdb_tool_entry_put
BI_tool_entry_reindex bdb_tool_entry_reindex