back-ldbm.h 34 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849
  1. /** BEGIN COPYRIGHT BLOCK
  2. * This Program is free software; you can redistribute it and/or modify it under
  3. * the terms of the GNU General Public License as published by the Free Software
  4. * Foundation; version 2 of the License.
  5. *
  6. * This Program is distributed in the hope that it will be useful, but WITHOUT
  7. * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
  8. * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
  9. *
  10. * You should have received a copy of the GNU General Public License along with
  11. * this Program; if not, write to the Free Software Foundation, Inc., 59 Temple
  12. * Place, Suite 330, Boston, MA 02111-1307 USA.
  13. *
  14. * In addition, as a special exception, Red Hat, Inc. gives You the additional
  15. * right to link the code of this Program with code not covered under the GNU
  16. * General Public License ("Non-GPL Code") and to distribute linked combinations
  17. * including the two, subject to the limitations in this paragraph. Non-GPL Code
  18. * permitted under this exception must only link to the code of this Program
  19. * through those well defined interfaces identified in the file named EXCEPTION
  20. * found in the source code files (the "Approved Interfaces"). The files of
  21. * Non-GPL Code may instantiate templates or use macros or inline functions from
  22. * the Approved Interfaces without causing the resulting work to be covered by
  23. * the GNU General Public License. Only Red Hat, Inc. may make changes or
  24. * additions to the list of Approved Interfaces. You must obey the GNU General
  25. * Public License in all respects for all of the Program code and other code used
  26. * in conjunction with the Program except the Non-GPL Code covered by this
  27. * exception. If you modify this file, you may extend this exception to your
  28. * version of the file, but you are not obligated to do so. If you do not wish to
  29. * provide this exception without modification, you must delete this exception
  30. * statement from your version and license this file solely under the GPL without
  31. * exception.
  32. *
  33. *
  34. * Copyright (C) 2001 Sun Microsystems, Inc. Used by permission.
  35. * Copyright (C) 2005 Red Hat, Inc.
  36. * All rights reserved.
  37. * END COPYRIGHT BLOCK **/
  38. #ifdef HAVE_CONFIG_H
  39. # include <config.h>
  40. #endif
  41. /* back-ldbm.h - ldap ldbm back-end header file */
  42. #ifndef _BACK_LDBM_H_
  43. #define _BACK_LDBM_H_
  44. #if defined(irix) || defined(AIX) || defined(HPUX11) || defined(OS_solaris) || defined(linux)
  45. /* built-in 64-bit file I/O support */
  46. #define DB_USE_64LFS
  47. #endif
  48. /* needed by at least HPUX and Solaris, to define off64_t */
  49. #ifdef DB_USE_64LFS
  50. #if !defined(_LARGEFILE64_SOURCE)
  51. #define _LARGEFILE64_SOURCE
  52. #endif
  53. #endif
  54. /* Required to get portable printf/scanf format macros */
  55. #ifdef HAVE_INTTYPES_H
  56. #include <inttypes.h>
  57. /* NSPR uses the print macros a bit differently than ANSI C. We
  58. * need to use ll for a 64-bit integer, even when a long is 64-bit.
  59. */
  60. #undef PRIu64
  61. #define PRIu64 "llu"
  62. #undef PRI64
  63. #define PRI64 "ll"
  64. #else
  65. #error Need to define portable format macros such as PRIu64
  66. #endif /* HAVE_INTTYPES_H */
  67. /* A bunch of random system headers taken from all the source files, no source file should #include
  68. any system headers now */
  69. #include <stdio.h>
  70. #include <string.h>
  71. #include <sys/types.h>
  72. #include <errno.h>
  73. #include <sys/stat.h>
  74. #include <stdlib.h>
  75. #include "prio.h" /* for PR_OpenDir etc */
  76. #include "prlog.h" /* for PR_ASSERT */
  77. /* The following cruft is for ldif2db only */
  78. #ifndef XP_WIN32
  79. #include <unistd.h> /* write/close (ldbm2ldif_write) */
  80. #else
  81. #include <io.h> /* write/close (ldbm2ldif_write) */
  82. #endif
  83. #include <fcntl.h>
  84. #include <time.h>
  85. /* And this cruft is from nextid.c */
  86. #ifndef _WIN32
  87. #include <sys/param.h>
  88. #endif /* ! _WIN32 */
  89. #include <limits.h> /* Used in search.c (why?) */
  90. #ifndef _WIN32
  91. /* for MAXPATHLEN */
  92. #include <sys/param.h>
  93. #define MKDIR(path,mode) mkdir((path),(mode))
  94. #else
  95. /* for mkdir */
  96. #include <direct.h>
  97. #define MKDIR(path,mode) mkdir(path)
  98. #endif
  99. #ifdef HPUX11
  100. #define __BIT_TYPES_DEFINED__
  101. typedef unsigned char u_int8_t;
  102. typedef unsigned int u_int32_t;
  103. typedef unsigned short u_int16_t;
  104. #endif
  105. #include "db.h"
  106. #ifndef DB_BUFFER_SMALL
  107. #define DB_BUFFER_SMALL ENOMEM
  108. #endif
  109. #define dptr data
  110. #define dsize size
  111. #define ID2ENTRY "id2entry" /* main db file name: ID2ENTRY+LDBM_SUFFIX */
  112. #define LDBM_SUFFIX_OLD ".db3"
  113. #define LDBM_SUFFIX ".db4"
  114. #define MEGABYTE (1024 * 1024)
  115. #define GIGABYTE (1024 * MEGABYTE)
  116. /* include NSPR header files */
  117. #include "nspr.h"
  118. #include "plhash.h"
  119. #include "slap.h"
  120. #include "slapi-plugin.h"
  121. #include "slapi-private.h"
  122. #include "avl.h"
  123. #include "ldaplog.h"
  124. #include "portable.h"
  125. #include "proto-slap.h"
  126. /* We should only change the LDBM_VERSION when the format of the db files
  127. * is changing in some (possibly incompatible) way -- so we can detect and
  128. * treat older ldbm versions. Thus, f.e., DS4.1 will still use the same
  129. * LDBM_VERSION as 4.0 and so on...
  130. * Don't make the length of LDBM_VERSION longer than LDBM_VERSION_MAXBUF - 1
  131. */
  132. #define LDBM_VERSION_MAXBUF 64
  133. #define LDBM_DATABASE_TYPE_NAME "ldbm database"
  134. /*
  135. * 232050: Change format of DBVERSION and guardian files
  136. * new format:
  137. * implementation/version/server backend plugin name[/other tag][/other tag]....
  138. * For example:
  139. * bdb/4.2/libback-ldbm/newidl
  140. * This indicates that the files use Berkeley DB version 4.2, they are used
  141. * by the server libback-ldbm database plugin, and the index files use the
  142. * newidl format.
  143. * Starting from DS7.2
  144. */
  145. #define BDB_IMPL "bdb"
  146. #define BDB_BACKEND "libback-ldbm" /* This backend plugin */
  147. #define BDB_NEWIDL "newidl" /* new idl format */
  148. #define BDB_RDNFORMAT "rdn-format" /* Subtree rename enabled */
  149. #define BDB_DNFORMAT "dn-4514" /* DN format RFC 4514 compliant */
  150. #define DBVERSION_NEWIDL 0x1
  151. #define DBVERSION_RDNFORMAT 0x2
  152. #define DBVERSION_DNFORMAT 0x4
  153. #define DBVERSION_ALL 0xffffffff
  154. /*
  155. * While we support both new and old idl index,
  156. * we distinguish them by the following 2 macros.
  157. * When we drop the old idl code, we eliminate LDBM_VERSION_OLD.
  158. * bug #604922
  159. */
  160. #define LDBM_VERSION_BASE "Netscape-ldbm/"
  161. #define LDBM_VERSION "Netscape-ldbm/7.0" /* db42: new idl -> old */
  162. #define LDBM_VERSION_NEW "Netscape-ldbm/7.0_NEW" /* db42: new idl */
  163. #define LDBM_VERSION_OLD "Netscape-ldbm/7.0_CLASSIC" /* db42: old idl */
  164. #define LDBM_VERSION_62 "Netscape-ldbm/6.2" /* db42: old idl */
  165. #define LDBM_VERSION_61 "Netscape-ldbm/6.1" /* db33: old idl */
  166. #define LDBM_VERSION_60 "Netscape-ldbm/6.0" /* db33: old idl */
  167. #define LDBM_VERSION_50 "Netscape-ldbm/5.0"
  168. #define LDBM_VERSION_40 "Netscape-ldbm/4.0"
  169. #define LDBM_VERSION_30 "Netscape-ldbm/3.0"
  170. #define LDBM_VERSION_31 "Netscape-ldbm/3.1"
  171. #define LDBM_FILENAME_SUFFIX ".db4"
  172. #define DBVERSION_FILENAME "DBVERSION"
  173. #define DEFAULT_CACHE_SIZE (size_t)10485760
  174. #define DEFAULT_CACHE_ENTRIES -1 /* no limit */
  175. #define DEFAULT_DNCACHE_SIZE (size_t)10485760
  176. #define DEFAULT_DNCACHE_MAXCOUNT -1 /* no limit */
  177. #define DEFAULT_DBCACHE_SIZE 1000000
  178. #define DEFAULT_MODE 0600
  179. #define DEFAULT_ALLIDSTHRESHOLD 4000
  180. #define DEFAULT_LOOKTHROUGHLIMIT 5000
  181. #define DEFAULT_IDL_TUNE 1
  182. #define DEFAULT_SEARCH_TUNE 0
  183. #define DEFAULT_IMPORT_INDEX_BUFFER_SIZE 0
  184. #define SUBLEN 3
  185. #define LDBM_CACHE_RETRY_COUNT 1000 /* Number of times we re-try a cache operation */
  186. #define IDL_FETCH_RETRY_COUNT 5 /* Number of times we re-try idl_fetch if it returns deadlock */
  187. #define IMPORT_SUBCOUNT_HASHTABLE_SIZE 500 /* Number of buckets in hash used to accumulate subcount for broody parents */
  188. /* minimum max ids that a single index entry can map to in ldbm */
  189. #define SLAPD_LDBM_MIN_MAXIDS 4000
  190. /* clear the following flag to suppress "database files do not exist" warning */
  191. extern int ldbm_warn_if_no_db;
  192. /*
  193. * there is a single index for each attribute. these prefixes insure
  194. * that there is no collision among keys.
  195. */
  196. #define EQ_PREFIX '=' /* prefix for equality keys */
  197. #define APPROX_PREFIX '~' /* prefix for approx keys */
  198. #define SUB_PREFIX '*' /* prefix for substring keys */
  199. #define CONT_PREFIX '\\' /* prefix for continuation keys */
  200. #define RULE_PREFIX ':' /* prefix for matchingRule keys */
  201. #define PRES_PREFIX '+'
  202. /* Values for "disposition" value in idl_insert_key() */
  203. #define IDL_INSERT_NORMAL 1
  204. #define IDL_INSERT_ALLIDS 2
  205. #define IDL_INSERT_NOW_ALLIDS 3
  206. #define DEFAULT_BLOCKSIZE 8192
  207. /*
  208. * The candidate list size at which it is cheaper to apply the filter test
  209. * to the whole list than to continue ANDing in IDLs.
  210. */
  211. #define FILTER_TEST_THRESHOLD (NIDS)10
  212. /* flags to indicate what kind of startup the dblayer should do */
  213. #define DBLAYER_IMPORT_MODE 0x1
  214. #define DBLAYER_NORMAL_MODE 0x2
  215. #define DBLAYER_EXPORT_MODE 0x4
  216. #define DBLAYER_ARCHIVE_MODE 0x8
  217. #define DBLAYER_RESTORE_MODE 0x10
  218. #define DBLAYER_RESTORE_NO_RECOVERY_MODE 0x20
  219. #define DBLAYER_TEST_MODE 0x40
  220. #define DBLAYER_INDEX_MODE 0x80
  221. #define DBLAYER_CLEAN_RECOVER_MODE 0x100
  222. #define DBLAYER_NO_DBTHREADS_MODE 0x1000
  223. #define DBLAYER_RESTORE_MASK (DBLAYER_RESTORE_MODE|DBLAYER_RESTORE_NO_RECOVERY_MODE)
  224. /*
  225. * the id used in the indexes to refer to an entry
  226. */
  227. typedef u_int32_t ID;
  228. #define MAXID ((ID)-3)
  229. #define NOID ((ID)-2)
  230. #define ALLID ((ID)-1)
  231. #define ID_FMT "%u" /* used in printf-like statements */
  232. /*
  233. * effective only on idl_new_fetch
  234. */
  235. #define NEW_IDL_NOOP 1 /* no need to fetch on new idl */
  236. #define NEW_IDL_NO_ALLID 2 /* force to return full idl (no allids) */
  237. #define NEW_IDL_DEFAULT 0
  238. /*
  239. * if the id of any backend instance is above the threshold, then warning
  240. * message will be logged about the need of rebuilding the database in question
  241. */
  242. #define ID_WARNING_THRESHOLD (MAXID * 0.9)
  243. /*
  244. * Use this to count and index into an array of ID.
  245. */
  246. typedef u_int32_t NIDS;
  247. /*
  248. * This structure represents an id block on disk and an id list
  249. * in core.
  250. *
  251. * The fields have the following meanings:
  252. *
  253. * b_nmax maximum number of ids in this block. if this is == ALLIDSBLOCK,
  254. * then this block represents all ids.
  255. * b_nids current number of ids in use in this block. if this
  256. * is == INDBLOCK, then this block is an indirect block
  257. * containing a list of other blocks containing actual ids.
  258. * the list is terminated by an id of NOID.
  259. * b_ids a list of the actual ids themselves
  260. */
  261. typedef struct block {
  262. NIDS b_nmax; /* max number of ids in this list */
  263. #define ALLIDSBLOCK 0 /* == 0 => this is an allid block */
  264. NIDS b_nids; /* current number of ids used */
  265. #define INDBLOCK 0 /* == 0 => this is an indirect blk */
  266. ID b_ids[1]; /* the ids - actually bigger */
  267. } Block, IDList;
  268. #define ALLIDS( idl ) ((idl)->b_nmax == ALLIDSBLOCK)
  269. #define INDIRECT_BLOCK( idl ) ((idl)->b_nids == INDBLOCK)
  270. #define IDL_NIDS(idl) (idl ? (idl)->b_nids : (NIDS)0)
  271. typedef size_t idl_iterator;
  272. /* small hashtable implementation used in the entry cache -- the table
  273. * stores little identical structs, and relies on using a (void *) inside
  274. * the struct to store linkage information.
  275. */
  276. typedef int (*HashTestFn)(const void *, const void *);
  277. typedef unsigned long (*HashFn)(const void *, size_t);
  278. typedef struct {
  279. u_long offset; /* offset of linkage info in user struct */
  280. u_long size; /* members in array below */
  281. HashFn hashfn; /* compute a hash value on a key */
  282. HashTestFn testfn; /* function to test if two entries are equal */
  283. void * slot[1]; /* actually much bigger */
  284. } Hashtable;
  285. /* use this macro to find the offset of the linkage info into your structure
  286. * (required for hashtable to work correctly)
  287. * HASHLOC(struct mything, linkptr)
  288. */
  289. #define HASHLOC(mem, node) (u_long)&(((mem *)0L)->node)
  290. /* type to set ep_type */
  291. #define CACHE_TYPE_ENTRY 0
  292. #define CACHE_TYPE_DN 1
  293. struct backcommon {
  294. int ep_type; /* to distinguish backdn from backentry */
  295. struct backcommon *ep_lrunext; /* for the cache */
  296. struct backcommon *ep_lruprev; /* for the cache */
  297. ID ep_id; /* entry id */
  298. char ep_state; /* state in the cache */
  299. #define ENTRY_STATE_DELETED 0x1 /* entry is marked as deleted */
  300. #define ENTRY_STATE_CREATING 0x2 /* entry is being created; don't touch it */
  301. #define ENTRY_STATE_NOTINCACHE 0x4 /* cache_add failed; not in the cache */
  302. int ep_refcnt; /* entry reference cnt */
  303. size_t ep_size; /* for cache tracking */
  304. };
  305. /* From ep_type through ep_size MUST be identical to backcommon */
  306. struct backentry {
  307. int ep_type; /* to distinguish backdn from backentry */
  308. struct backcommon *ep_lrunext; /* for the cache */
  309. struct backcommon *ep_lruprev; /* for the cache */
  310. ID ep_id; /* entry id */
  311. char ep_state; /* state in the cache */
  312. int ep_refcnt; /* entry reference cnt */
  313. size_t ep_size; /* for cache tracking */
  314. Slapi_Entry *ep_entry; /* real entry */
  315. Slapi_Entry *ep_vlventry;
  316. void * ep_dn_link; /* linkage for the 3 hash */
  317. void * ep_id_link; /* tables used for */
  318. void * ep_uuid_link; /* looking up entries */
  319. PRLock *ep_mutexp; /* protection for mods */
  320. };
  321. /* From ep_type through ep_size MUST be identical to backcommon */
  322. struct backdn {
  323. int ep_type; /* to distinguish backdn from backentry */
  324. struct backcommon *ep_lrunext; /* for the cache */
  325. struct backcommon *ep_lruprev; /* for the cache */
  326. ID ep_id; /* entry id */
  327. char ep_state; /* state in the cache; share ENTRY_STATE_* */
  328. int ep_refcnt; /* entry reference cnt */
  329. size_t ep_size; /* for cache tracking */
  330. Slapi_DN *dn_sdn;
  331. void *dn_id_link; /* for hash table */
  332. };
  333. /* for the in-core cache of entries */
  334. struct cache {
  335. size_t c_maxsize; /* max size in bytes */
  336. Slapi_Counter *c_cursize; /* size in bytes */
  337. long c_maxentries; /* max entries allowed (-1: no limit) */
  338. long c_curentries; /* current # entries in cache */
  339. Hashtable *c_dntable;
  340. Hashtable *c_idtable;
  341. #ifdef UUIDCACHE_ON
  342. Hashtable *c_uuidtable;
  343. #endif
  344. Slapi_Counter *c_hits; /* for analysis of hits/misses */
  345. Slapi_Counter *c_tries;
  346. struct backcommon *c_lruhead; /* add entries here */
  347. struct backcommon *c_lrutail; /* remove entries here */
  348. PRLock *c_mutex; /* lock for cache operations */
  349. PRLock *c_emutexalloc_mutex;
  350. };
  351. #define CACHE_ADD(cache, p, a) cache_add((cache), (void *)(p), (void **)(a))
  352. #define CACHE_RETURN(cache, p) cache_return((cache), (void **)(p))
  353. #define CACHE_REMOVE(cache, p) cache_remove((cache), (void *)(p))
  354. /* various modules keep private data inside the attrinfo structure */
  355. typedef struct dblayer_private dblayer_private;
  356. typedef struct dblayer_private_env dblayer_private_env;
  357. typedef struct idl_private idl_private;
  358. typedef struct attrcrypt_private attrcrypt_private;
  359. /*
  360. * Special attributes for an index entry to change the substring index width.
  361. * By default, substring index width is 3, i.e., search with the filter
  362. * "(cn=abc*)" is an indexed search, but "(cn=ab*)" or "(cn=a*)" isn't.
  363. * There is a big performance gap between the indexed search and the unindexed
  364. * search especially when the database is large. To convert such unindexed
  365. * search to the indexed search to speed up the query, these nsSubStr
  366. * attributes are introduced.
  367. *
  368. * How to use the nsSubStr attributes:
  369. * 1) turn the target index to extensibleobject by adding
  370. * "objectClass: extensibleObject" to the index entry
  371. * 2) set the length to each nsSubStr attribute of the index
  372. * dn: cn=sn, cn=index, cn=userRoot, cn=ldbm database, cn=plugins, cn=config
  373. * objectClass: extensibleObject
  374. * nsSubStrBegin: 2
  375. * nsSubStrMiddle: 3
  376. * nsSubStrEnd: 2
  377. * [...]
  378. *
  379. * By default, the minimum key length triplets of substring index is 3, 3, 3.
  380. * The length is changed by setting the triplets nsSubStrBegin, nsSubStrMiddle,
  381. * nsSubStrEnd, respectively.
  382. *
  383. * Note: If any of the key length value is modified, the index file needs
  384. * to be regenerated. Otherwise, the index file is going to have mixed
  385. * key length.
  386. * To change the key length,
  387. * 1) stop the server,
  388. * 2) run db2index -t <attr>,
  389. * 3) start the server.
  390. */
  391. #define INDEX_ATTR_SUBSTRBEGIN "nsSubStrBegin"
  392. #define INDEX_ATTR_SUBSTRMIDDLE "nsSubStrMiddle"
  393. #define INDEX_ATTR_SUBSTREND "nsSubStrEnd"
  394. #define INDEX_SUBSTRBEGIN 0
  395. #define INDEX_SUBSTRMIDDLE 1
  396. #define INDEX_SUBSTREND 2
  397. typedef int (*dup_compare_fn_type)(
  398. #if 1000*DB_VERSION_MAJOR + 100*DB_VERSION_MINOR >= 3200
  399. DB *db,
  400. #endif
  401. const DBT *,const DBT *);
  402. /* for the cache of attribute information (which are indexed, etc.) */
  403. struct attrinfo {
  404. char *ai_type; /* type name (cn, sn, ...) */
  405. int ai_indexmask; /* how the attr is indexed */
  406. #define INDEX_PRESENCE 0x01
  407. #define INDEX_EQUALITY 0x02
  408. #define INDEX_APPROX 0x04
  409. #define INDEX_SUB 0x08
  410. #define INDEX_UNKNOWN 0x10
  411. #define INDEX_FROMINIT 0x20
  412. #define INDEX_RULES 0x40
  413. #define INDEX_VLV 0x80
  414. #define INDEX_SUBTREE 0x100
  415. #define INDEX_ANY (INDEX_PRESENCE | INDEX_EQUALITY | INDEX_APPROX | INDEX_SUB | INDEX_RULES | INDEX_VLV | INDEX_SUBTREE)
  416. #define INDEX_OFFLINE 0x1000 /* index is being generated, or
  417. * has been created but not indexed
  418. * yet. */
  419. #define IS_INDEXED( a ) ( a & INDEX_ANY )
  420. char **ai_index_rules; /* matching rule OIDs */
  421. void *ai_dblayer; /* private data used by the dblayer code */
  422. PRInt32 ai_dblayer_count; /* used by the dblayer code */
  423. idl_private *ai_idl; /* private data used by the IDL code (eg locking the IDLs) */
  424. attrcrypt_private *ai_attrcrypt; /* private data used by the attribute encryption code (eg is it enabled or not) */
  425. value_compare_fn_type ai_key_cmp_fn; /* function used to compare two index keys -
  426. The function is the compare function provided by
  427. attr_get_value_cmp_fn - this function is used to order
  428. the keys in the index so that we can use ORDERING
  429. searches. In order for this function to be used,
  430. the syntax plugin must define a compare function,
  431. and either the attribute definition schema must
  432. specify an ORDERING matching rule, or the index
  433. configuration must define an ORDERING matching rule.
  434. */
  435. dup_compare_fn_type ai_dup_cmp_fn; /* function used to compare dups -
  436. used to order duplicates belonging
  437. to the same index key. By default,
  438. idl_new_compare_dups is set.
  439. If some special ordering is needed,
  440. special compare fn is set here.
  441. (e.g., for entryrdn) */
  442. int *ai_substr_lens; /* if the attribute nsSubStrXxx is specivied in
  443. * an index instance (dse.ldif), the substr key
  444. * len value(s) are stored here. If not specified,
  445. * the default length triplet is 2, 3, 2.
  446. */
  447. Slapi_Attr ai_sattr; /* interface to syntax and matching rule plugins */
  448. };
  449. #define MAXDBCACHE 20
  450. struct id_array {
  451. int ida_next_index; /*The next index that is free*/
  452. int ida_size; /*The size of this puppy*/
  453. ID *ida_ids; /*The array of ids*/
  454. };
  455. typedef struct id_array Id_Array;
  456. struct _db_upgrade_info {
  457. char *old_version_string;
  458. int old_dbversion_major;
  459. int old_dbversion_minor;
  460. int type;
  461. int action;
  462. };
  463. typedef struct _db_upgrade_info db_upgrade_info;
  464. /* Values for dbversion_stuff->type */
  465. #define DBVERSION_COMPATIBLE 0x10
  466. #define DBVERSION_UPGRADABLE 0x20
  467. #define DBVERSION_SOL 0x40
  468. #define DBVERSION_OLD_IDL 0x1
  469. #define DBVERSION_NEW_IDL 0x2
  470. #define DBVERSION_RDN_FORMAT 0x4
  471. /* Values for dbversion_stuff->action + return value */
  472. #define DBVERSION_NO_UPGRADE 0x0
  473. #define DBVERSION_NEED_IDL_OLD2NEW 0x100
  474. #define DBVERSION_NEED_IDL_NEW2OLD 0x200
  475. #define DBVERSION_UPGRADE_3_4 0x400 /* bdb 3.3 -> 4.2 */
  476. /* The log file format changed;
  477. * No database formats changed;
  478. * db extention: .db3 -> .db4
  479. */
  480. #define DBVERSION_UPGRADE_4_4 0x800 /* bdb 4.2 -> 4.3 -> 4.4 -> 4.5 */
  481. /* The log file format changed;
  482. * No database formats changed;
  483. * no db extention change
  484. */
  485. #define DBVERSION_NEED_DN2RDN 0x1000/* DN to RDN (subtree-rename) format */
  486. #define DBVERSION_NEED_RDN2DN 0x2000/* RDN to DN (original) format */
  487. #define DBVERSION_NOT_SUPPORTED 0x10000000
  488. #define DBVERSION_TYPE 0x1
  489. #define DBVERSION_ACTION 0x2
  490. struct ldbminfo {
  491. int li_mode;
  492. int li_lookthroughlimit;
  493. int li_allidsthreshold;
  494. char *li_directory;
  495. int li_reslimit_lookthrough_handle;
  496. size_t li_dbcachesize;
  497. int li_dbncache;
  498. int li_import_cache_autosize; /* % of free memory to use
  499. * for the import caches
  500. * (-1=default, 80% on cmd import)
  501. * (0 = off) -- overrides
  502. * import cache size settings */
  503. int li_cache_autosize; /* % of free memory to use
  504. * for the combined caches
  505. * (0 = off) -- overrides
  506. * other cache size settings */
  507. int li_cache_autosize_split; /* % of li_cache_autosize to
  508. * use for the libdb cache.
  509. * the rest is split up among
  510. * the instance entry caches */
  511. unsigned long li_cache_autosize_ec; /* new instances created while
  512. * the server is up, should
  513. * use this as the entry cache
  514. * size (0 = autosize off) */
  515. size_t li_import_cachesize; /* size of the mpool for
  516. * imports */
  517. PRLock *li_dbcache_mutex;
  518. PRCondVar *li_dbcache_cv;
  519. int li_shutdown; /* flag to tell any BE threads
  520. * to end */
  521. PRLock *li_shutdown_mutex; /* protect shutdown flag */
  522. dblayer_private *li_dblayer_private; /* session ptr for databases */
  523. int li_noparentcheck; /* check if parent exists on
  524. * add */
  525. /* the next 2 fields are for the params that don't get changed until
  526. * the server is restarted (used by the admin console)
  527. */
  528. char *li_new_directory;
  529. size_t li_new_dbcachesize;
  530. int li_new_dbncache;
  531. db_upgrade_info *upgrade_info;
  532. int li_filter_bypass; /* bypass filter testing,
  533. * when possible */
  534. int li_filter_bypass_check; /* check that filter bypass
  535. * is doing the right thing */
  536. int li_use_vlv; /* use vlv indexes to short-
  537. * circuit matches when
  538. * possible */
  539. void *li_identity; /* The ldbm plugin needs to keep
  540. * track of its identity so it can
  541. * perform internal ops. Its
  542. * identity is given to it when
  543. * its init function is called. */
  544. Objset *li_instance_set; /* A set containing the ldbm
  545. * instances. */
  546. PRLock *li_config_mutex;
  547. /* There are times when we need a pointer to the ldbm database
  548. * plugin, so we will store a pointer to it here. Examples of
  549. * when we need it are when we create a new instance and when
  550. * we need the name of the plugin to do internal ops. */
  551. struct slapdplugin *li_plugin;
  552. /* factory extension markers for the Connection struct -- bulk import
  553. * uses this to store state info on a Connection.
  554. */
  555. int li_bulk_import_object;
  556. int li_bulk_import_handle;
  557. /* maximum number of pass before merging the files during an import */
  558. int li_maxpassbeforemerge;
  559. /* charray of attributes to exclude from LDIF export */
  560. char **li_attrs_to_exclude_from_export;
  561. int li_flags;
  562. int li_fat_lock; /* 608146 -- make this configurable, first */
  563. int li_legacy_errcode; /* 615428 -- in case legacy err code is expected */
  564. Slapi_Counter *li_global_usn_counter; /* global USN counter */
  565. };
  566. /* li_flags could store these bits defined in ../slapi-plugin.h
  567. * task flag (pb_task_flags) *
  568. * SLAPI_TASK_RUNNING_AS_TASK
  569. * SLAPI_TASK_RUNNING_FROM_COMMANDLINE
  570. */
  571. /* allow conf w/o CONFIG_FLAG_ALLOW_RUNNING_CHANGE to be updated */
  572. #define LI_FORCE_MOD_CONFIG 0x10
  573. /* Structure used to hold stuff for the lifetime of an LDAP transaction */
  574. /* If we do clever stuff like LDAP transactions, we'll need a stack of TXN ID's */
  575. typedef struct back_txn back_txn;
  576. struct back_txn {
  577. DB_TXN *back_txn_txn; /* Transaction ID for the database */
  578. };
  579. typedef void * back_txnid;
  580. #define RETRY_TIMES 50
  581. /* Structure used to communicate information about subordinatecount on import/upgrade */
  582. struct _import_subcount_stuff {
  583. PLHashTable *hashtable;
  584. };
  585. typedef struct _import_subcount_stuff import_subcount_stuff;
  586. /* Handy structures for modify operations */
  587. struct _modify_context {
  588. int new_entry_in_cache;
  589. struct backentry *old_entry;
  590. struct backentry *new_entry;
  591. Slapi_Mods *smods;
  592. int attr_encrypt;
  593. };
  594. typedef struct _modify_context modify_context;
  595. #define INSTANCE_DB_SUFFIX "-db"
  596. #define INSTANCE_CHANGELOG_SUFFIX "-changelog"
  597. /* This structure was moved here from dblayer.c because the ldbm_instance
  598. * structure uses the dblayer_handle structure. */
  599. struct tag_dblayer_handle; typedef struct tag_dblayer_handle dblayer_handle;
  600. struct tag_dblayer_handle
  601. {
  602. DB* dblayer_dbp;
  603. PRLock *dblayer_lock; /* used when anyone wants exclusive access to a file */
  604. dblayer_handle *dblayer_handle_next;
  605. void **dblayer_handle_ai_backpointer; /* Voodo magic pointer to the place where we store a
  606. pointer to this handle in the attrinfo structure */
  607. };
  608. /* This structure was moved here from perfctrs.c so the ldbm_instance structure
  609. * could use it. */
  610. struct _perfctrs_private {
  611. #if defined(_WIN32)
  612. /* Handle to the shared memory object */
  613. HANDLE hMemory;
  614. /* Handle to the update event */
  615. HANDLE hEvent;
  616. #else
  617. /* Nothing yet */
  618. #endif
  619. /* Pointer to the shared memory */
  620. void *memory;
  621. };
  622. typedef struct _perfctrs_private perfctrs_private;
  623. typedef struct _attrcrypt_state_private attrcrypt_state_private;
  624. /* flags for ldbm_instance */
  625. /* please lock inst_config_mutex before changing inst_flags */
  626. #define INST_FLAG_BUSY 0x0001 /* instance is doing an import or
  627. * restore. */
  628. #define INST_FLAG_READONLY 0x0002 /* instance is truly readonly */
  629. /* Structure used to hold instance specific information. */
  630. typedef struct ldbm_instance {
  631. char *inst_name; /* Name given for this instance. */
  632. backend *inst_be; /* pointer back to the backend */
  633. struct ldbminfo *inst_li; /* pointer back to global info */
  634. int inst_flags; /* see above */
  635. PRLock *inst_config_mutex;
  636. PRInt32 *inst_ref_count; /* Keeps track of how many operations
  637. * are currently using this instance */
  638. char *inst_dir_name; /* The name of the directory in the db
  639. * directory that holds the index files
  640. * for this instance. Relative to the
  641. * parent of the instance name dir */
  642. char *inst_parent_dir_name; /* Absolute parent dir for this inst */
  643. PRLock *inst_db_mutex; /* Used to synchronize modify operations
  644. * on this instance. */
  645. dblayer_handle *inst_handle_head; /* These are used to maintain a list */
  646. dblayer_handle *inst_handle_tail; /* of open db handles for this instance */
  647. PRLock *inst_handle_list_mutex;
  648. DB *inst_id2entry; /* id2entry for this instance. */
  649. perfctrs_private inst_perf_private; /* Private data for the performace
  650. * counters specific to this instance */
  651. attrcrypt_state_private *inst_attrcrypt_state_private;
  652. int attrcrypt_configured; /* Are any attributes configured for encryption ? */
  653. Avlnode *inst_attrs; /* Keeps track of what's indexed for
  654. * this instance. */
  655. struct cache inst_cache; /* The entry cache for this instance. */
  656. PRLock *inst_nextid_mutex;
  657. ID inst_nextid;
  658. PRCondVar *inst_indexer_cv; /* indexer thread cond var */
  659. PRThread *inst_indexer_tid; /* for the indexer thread */
  660. long inst_cache_hits; /* used during imports to figure out when
  661. * a pass should end. */
  662. long inst_cache_misses;
  663. char *inst_dataversion; /* The user data version tag. Used by
  664. * replication. */
  665. dblayer_private_env *import_env; /* use a different DB_ENV for imports */
  666. int require_index; /* set to 1 to require an index be used
  667. * in search */
  668. struct cache inst_dncache; /* The dn cache for this instance. */
  669. } ldbm_instance;
  670. /*
  671. * This structure is passed through the PBlock from ldbm_back_search to
  672. * ldbm_back_next_search_entry. It contains the candidate result set
  673. * determined by ldbm_back_search, to be served up by ldbm_back_next_search_entry.
  674. */
  675. typedef struct _back_search_result_set
  676. {
  677. IDList* sr_candidates; /* the search results */
  678. idl_iterator sr_current; /* the current position in the search results */
  679. struct backentry* sr_entry; /* the last entry returned */
  680. int sr_lookthroughcount; /* how many have we examined? */
  681. int sr_lookthroughlimit; /* how many can we examine? */
  682. int sr_virtuallistview; /* is this a VLV Search */
  683. Slapi_Entry* sr_vlventry; /* a special VLV Entry for when the ACL check fails */
  684. int sr_flags; /* Magic flags, defined below */
  685. int sr_current_sizelimit; /* Current sizelimit */
  686. } back_search_result_set;
  687. #define SR_FLAG_CAN_SKIP_FILTER_TEST 1 /* If set in sr_flags, means that we can safely skip the filter test */
  688. #include "proto-back-ldbm.h"
  689. #include "ldbm_config.h"
  690. /* flags used when adding/removing index items */
  691. #define BE_INDEX_ADD 1
  692. #define BE_INDEX_DEL 2
  693. #define BE_INDEX_PRESENCE 4 /* (w/DEL) remove the presence index */
  694. #define BE_INDEX_TOMBSTONE 8 /* Index entry as a tombstone */
  695. #define BE_INDEX_DONT_ENCRYPT 16 /* Disable any encryption if this flag is set */
  696. #define BE_INDEX_EQUALITY 32 /* (w/DEL) remove the equality index */
  697. #define BE_INDEX_NORMALIZED SLAPI_ATTR_FLAG_NORMALIZED /* value already normalized (0x200) */
  698. /* Name of attribute type used for binder-based look through limit */
  699. #define LDBM_LOOKTHROUGHLIMIT_AT "nsLookThroughLimit"
  700. /* OIDs for attribute types used internally */
  701. #define LDBM_ENTRYDN_OID "2.16.840.1.113730.3.1.602"
  702. #define LDBM_DNCOMP_OID "2.16.840.1.113730.3.1.603"
  703. #define LDBM_PARENTID_OID "2.16.840.1.113730.3.1.604"
  704. #define LDBM_ENTRYID_OID "2.16.840.1.113730.3.1.605"
  705. #define LDBM_ENTRYUSN_OID "2.16.840.1.113730.3.1.606"
  706. #define LDBM_ENTRYRDN_OID "2.16.840.1.113730.3.1.607"
  707. #define LDBM_ANCESTORID_STR "ancestorid"
  708. #define LDBM_ENTRYDN_STR "entrydn"
  709. #define LDBM_ENTRYRDN_STR "entryrdn"
  710. #define LDBM_NUMSUBORDINATES_STR "numsubordinates"
  711. #define LDBM_PARENTID_STR "parentid"
  712. /* Name of psuedo attribute used to track default indexes */
  713. #define LDBM_PSEUDO_ATTR_DEFAULT ".default"
  714. /* for checking disk full errors. */
  715. #define LDBM_OS_ERR_IS_DISKFULL( err ) ((err)==ENOSPC || (err)==EFBIG)
  716. /* flag: open_flag for dblayer_get_index_file -> dblayer_open_file */
  717. #define DBOPEN_CREATE 0x1 /* oprinary mode: create a db file if needed */
  718. #define DBOPEN_TRUNCATE 0x2 /* oprinary mode: truncate a db file if needed */
  719. /* whether we call fat lock or not [608146] */
  720. #define SERIALLOCK(li) (li->li_fat_lock)
  721. /*
  722. * 0: SUCCESS
  723. * libdb returns negative error codes
  724. * Linux errno's < 140, for now
  725. * Chose any positive value other than the above values.
  726. * Being used to specify duplicated DN is found in entrydn or entryrdn.
  727. */
  728. #define LDBM_ERROR_FOUND_DUPDN 9999
  729. /* Initial entryusn value */
  730. #define INITIALUSN (PRUint64)(-1)
  731. /* changelog backup dir name
  732. * starting with '.' to reduce the risk to match an ordinary backend name */
  733. #define CHANGELOG_BACKUPDIR ".repl_changelog_backup"
  734. /* For dblayer_get_aux_id2entry_ext */
  735. #define DBLAYER_AUX_ID2ENTRY_TMP 0x1
  736. #endif /* _back_ldbm_h_ */