ldb: add LDB_FLG_DONT_CREATE_DB
[Samba.git] / lib / ldb / ldb_tdb / ldb_tdb.c
blob8c4989f6095a48a6209db33cac7eff33750e0d22
1 /*
2 ldb database library
4 Copyright (C) Andrew Tridgell 2004
5 Copyright (C) Stefan Metzmacher 2004
6 Copyright (C) Simo Sorce 2006-2008
7 Copyright (C) Matthias Dieter Wallnöfer 2009-2010
9 ** NOTE! The following LGPL license applies to the ldb
10 ** library. This does NOT imply that all of Samba is released
11 ** under the LGPL
13 This library is free software; you can redistribute it and/or
14 modify it under the terms of the GNU Lesser General Public
15 License as published by the Free Software Foundation; either
16 version 3 of the License, or (at your option) any later version.
18 This library is distributed in the hope that it will be useful,
19 but WITHOUT ANY WARRANTY; without even the implied warranty of
20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21 Lesser General Public License for more details.
23 You should have received a copy of the GNU Lesser General Public
24 License along with this library; if not, see <http://www.gnu.org/licenses/>.
28 * Name: ldb_tdb
30 * Component: ldb tdb backend
32 * Description: core functions for tdb backend
34 * Author: Andrew Tridgell
35 * Author: Stefan Metzmacher
37 * Modifications:
39 * - description: make the module use asynchronous calls
40 * date: Feb 2006
41 * Author: Simo Sorce
43 * - description: make it possible to use event contexts
44 * date: Jan 2008
45 * Author: Simo Sorce
47 * - description: fix up memory leaks and small bugs
48 * date: Oct 2009
49 * Author: Matthias Dieter Wallnöfer
52 #include "ldb_tdb.h"
53 #include "ldb_private.h"
54 #include <tdb.h>
57 prevent memory errors on callbacks
59 struct ltdb_req_spy {
60 struct ltdb_context *ctx;
64 map a tdb error code to a ldb error code
66 int ltdb_err_map(enum TDB_ERROR tdb_code)
68 switch (tdb_code) {
69 case TDB_SUCCESS:
70 return LDB_SUCCESS;
71 case TDB_ERR_CORRUPT:
72 case TDB_ERR_OOM:
73 case TDB_ERR_EINVAL:
74 return LDB_ERR_OPERATIONS_ERROR;
75 case TDB_ERR_IO:
76 return LDB_ERR_PROTOCOL_ERROR;
77 case TDB_ERR_LOCK:
78 case TDB_ERR_NOLOCK:
79 return LDB_ERR_BUSY;
80 case TDB_ERR_LOCK_TIMEOUT:
81 return LDB_ERR_TIME_LIMIT_EXCEEDED;
82 case TDB_ERR_EXISTS:
83 return LDB_ERR_ENTRY_ALREADY_EXISTS;
84 case TDB_ERR_NOEXIST:
85 return LDB_ERR_NO_SUCH_OBJECT;
86 case TDB_ERR_RDONLY:
87 return LDB_ERR_INSUFFICIENT_ACCESS_RIGHTS;
88 default:
89 break;
91 return LDB_ERR_OTHER;
95 lock the database for read - use by ltdb_search and ltdb_sequence_number
97 int ltdb_lock_read(struct ldb_module *module)
99 void *data = ldb_module_get_private(module);
100 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
101 int ret = 0;
103 if (ltdb->in_transaction == 0 &&
104 ltdb->read_lock_count == 0) {
105 ret = tdb_lockall_read(ltdb->tdb);
107 if (ret == 0) {
108 ltdb->read_lock_count++;
110 return ret;
114 unlock the database after a ltdb_lock_read()
116 int ltdb_unlock_read(struct ldb_module *module)
118 void *data = ldb_module_get_private(module);
119 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
120 if (ltdb->in_transaction == 0 && ltdb->read_lock_count == 1) {
121 tdb_unlockall_read(ltdb->tdb);
122 return 0;
124 ltdb->read_lock_count--;
125 return 0;
130 form a TDB_DATA for a record key
131 caller frees
133 note that the key for a record can depend on whether the
134 dn refers to a case sensitive index record or not
136 TDB_DATA ltdb_key(struct ldb_module *module, struct ldb_dn *dn)
138 struct ldb_context *ldb = ldb_module_get_ctx(module);
139 TDB_DATA key;
140 char *key_str = NULL;
141 const char *dn_folded = NULL;
144 most DNs are case insensitive. The exception is index DNs for
145 case sensitive attributes
147 there are 3 cases dealt with in this code:
149 1) if the dn doesn't start with @ then uppercase the attribute
150 names and the attributes values of case insensitive attributes
151 2) if the dn starts with @ then leave it alone -
152 the indexing code handles the rest
155 dn_folded = ldb_dn_get_casefold(dn);
156 if (!dn_folded) {
157 goto failed;
160 key_str = talloc_strdup(ldb, "DN=");
161 if (!key_str) {
162 goto failed;
165 key_str = talloc_strdup_append_buffer(key_str, dn_folded);
166 if (!key_str) {
167 goto failed;
170 key.dptr = (uint8_t *)key_str;
171 key.dsize = strlen(key_str) + 1;
173 return key;
175 failed:
176 errno = ENOMEM;
177 key.dptr = NULL;
178 key.dsize = 0;
179 return key;
183 check special dn's have valid attributes
184 currently only @ATTRIBUTES is checked
186 static int ltdb_check_special_dn(struct ldb_module *module,
187 const struct ldb_message *msg)
189 struct ldb_context *ldb = ldb_module_get_ctx(module);
190 unsigned int i, j;
192 if (! ldb_dn_is_special(msg->dn) ||
193 ! ldb_dn_check_special(msg->dn, LTDB_ATTRIBUTES)) {
194 return LDB_SUCCESS;
197 /* we have @ATTRIBUTES, let's check attributes are fine */
198 /* should we check that we deny multivalued attributes ? */
199 for (i = 0; i < msg->num_elements; i++) {
200 if (ldb_attr_cmp(msg->elements[i].name, "distinguishedName") == 0) continue;
202 for (j = 0; j < msg->elements[i].num_values; j++) {
203 if (ltdb_check_at_attributes_values(&msg->elements[i].values[j]) != 0) {
204 ldb_set_errstring(ldb, "Invalid attribute value in an @ATTRIBUTES entry");
205 return LDB_ERR_INVALID_ATTRIBUTE_SYNTAX;
210 return LDB_SUCCESS;
215 we've made a modification to a dn - possibly reindex and
216 update sequence number
218 static int ltdb_modified(struct ldb_module *module, struct ldb_dn *dn)
220 int ret = LDB_SUCCESS;
221 struct ltdb_private *ltdb = talloc_get_type(ldb_module_get_private(module), struct ltdb_private);
223 /* only allow modifies inside a transaction, otherwise the
224 * ldb is unsafe */
225 if (ltdb->in_transaction == 0) {
226 ldb_set_errstring(ldb_module_get_ctx(module), "ltdb modify without transaction");
227 return LDB_ERR_OPERATIONS_ERROR;
230 if (ldb_dn_is_special(dn) &&
231 (ldb_dn_check_special(dn, LTDB_INDEXLIST) ||
232 ldb_dn_check_special(dn, LTDB_ATTRIBUTES)) )
234 if (ltdb->warn_reindex) {
235 ldb_debug(ldb_module_get_ctx(module),
236 LDB_DEBUG_ERROR, "Reindexing %s due to modification on %s",
237 tdb_name(ltdb->tdb), ldb_dn_get_linearized(dn));
239 ret = ltdb_reindex(module);
242 /* If the modify was to a normal record, or any special except @BASEINFO, update the seq number */
243 if (ret == LDB_SUCCESS &&
244 !(ldb_dn_is_special(dn) &&
245 ldb_dn_check_special(dn, LTDB_BASEINFO)) ) {
246 ret = ltdb_increase_sequence_number(module);
249 /* If the modify was to @OPTIONS, reload the cache */
250 if (ret == LDB_SUCCESS &&
251 ldb_dn_is_special(dn) &&
252 (ldb_dn_check_special(dn, LTDB_OPTIONS)) ) {
253 ret = ltdb_cache_reload(module);
256 return ret;
260 store a record into the db
262 int ltdb_store(struct ldb_module *module, const struct ldb_message *msg, int flgs)
264 void *data = ldb_module_get_private(module);
265 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
266 TDB_DATA tdb_key, tdb_data;
267 struct ldb_val ldb_data;
268 int ret = LDB_SUCCESS;
270 tdb_key = ltdb_key(module, msg->dn);
271 if (tdb_key.dptr == NULL) {
272 return LDB_ERR_OTHER;
275 ret = ldb_pack_data(ldb_module_get_ctx(module),
276 msg, &ldb_data);
277 if (ret == -1) {
278 talloc_free(tdb_key.dptr);
279 return LDB_ERR_OTHER;
282 tdb_data.dptr = ldb_data.data;
283 tdb_data.dsize = ldb_data.length;
285 ret = tdb_store(ltdb->tdb, tdb_key, tdb_data, flgs);
286 if (ret != 0) {
287 ret = ltdb_err_map(tdb_error(ltdb->tdb));
288 goto done;
291 done:
292 talloc_free(tdb_key.dptr);
293 talloc_free(ldb_data.data);
295 return ret;
300 check if a attribute is a single valued, for a given element
302 static bool ldb_tdb_single_valued(const struct ldb_schema_attribute *a,
303 struct ldb_message_element *el)
305 if (!a) return false;
306 if (el != NULL) {
307 if (el->flags & LDB_FLAG_INTERNAL_FORCE_SINGLE_VALUE_CHECK) {
308 /* override from a ldb module, for example
309 used for the description field, which is
310 marked multi-valued in the schema but which
311 should not actually accept multiple
312 values */
313 return true;
315 if (el->flags & LDB_FLAG_INTERNAL_DISABLE_SINGLE_VALUE_CHECK) {
316 /* override from a ldb module, for example used for
317 deleted linked attribute entries */
318 return false;
321 if (a->flags & LDB_ATTR_FLAG_SINGLE_VALUE) {
322 return true;
324 return false;
327 static int ltdb_add_internal(struct ldb_module *module,
328 const struct ldb_message *msg,
329 bool check_single_value)
331 struct ldb_context *ldb = ldb_module_get_ctx(module);
332 int ret = LDB_SUCCESS;
333 unsigned int i, j;
335 for (i=0;i<msg->num_elements;i++) {
336 struct ldb_message_element *el = &msg->elements[i];
337 const struct ldb_schema_attribute *a = ldb_schema_attribute_by_name(ldb, el->name);
339 if (el->num_values == 0) {
340 ldb_asprintf_errstring(ldb, "attribute '%s' on '%s' specified, but with 0 values (illegal)",
341 el->name, ldb_dn_get_linearized(msg->dn));
342 return LDB_ERR_CONSTRAINT_VIOLATION;
344 if (check_single_value &&
345 el->num_values > 1 &&
346 ldb_tdb_single_valued(a, el)) {
347 ldb_asprintf_errstring(ldb, "SINGLE-VALUE attribute %s on %s specified more than once",
348 el->name, ldb_dn_get_linearized(msg->dn));
349 return LDB_ERR_CONSTRAINT_VIOLATION;
352 /* Do not check "@ATTRIBUTES" for duplicated values */
353 if (ldb_dn_is_special(msg->dn) &&
354 ldb_dn_check_special(msg->dn, LTDB_ATTRIBUTES)) {
355 continue;
358 /* TODO: This is O(n^2) - replace with more efficient check */
359 for (j=0; j<el->num_values; j++) {
360 if (ldb_msg_find_val(el, &el->values[j]) != &el->values[j]) {
361 ldb_asprintf_errstring(ldb,
362 "attribute '%s': value #%u on '%s' provided more than once",
363 el->name, j, ldb_dn_get_linearized(msg->dn));
364 return LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
369 ret = ltdb_store(module, msg, TDB_INSERT);
370 if (ret != LDB_SUCCESS) {
371 if (ret == LDB_ERR_ENTRY_ALREADY_EXISTS) {
372 ldb_asprintf_errstring(ldb,
373 "Entry %s already exists",
374 ldb_dn_get_linearized(msg->dn));
376 return ret;
379 ret = ltdb_index_add_new(module, msg);
380 if (ret != LDB_SUCCESS) {
381 return ret;
384 ret = ltdb_modified(module, msg->dn);
386 return ret;
390 add a record to the database
392 static int ltdb_add(struct ltdb_context *ctx)
394 struct ldb_module *module = ctx->module;
395 struct ldb_request *req = ctx->req;
396 int ret = LDB_SUCCESS;
398 ret = ltdb_check_special_dn(module, req->op.add.message);
399 if (ret != LDB_SUCCESS) {
400 return ret;
403 ldb_request_set_state(req, LDB_ASYNC_PENDING);
405 if (ltdb_cache_load(module) != 0) {
406 return LDB_ERR_OPERATIONS_ERROR;
409 ret = ltdb_add_internal(module, req->op.add.message, true);
411 return ret;
415 delete a record from the database, not updating indexes (used for deleting
416 index records)
418 int ltdb_delete_noindex(struct ldb_module *module, struct ldb_dn *dn)
420 void *data = ldb_module_get_private(module);
421 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
422 TDB_DATA tdb_key;
423 int ret;
425 tdb_key = ltdb_key(module, dn);
426 if (!tdb_key.dptr) {
427 return LDB_ERR_OTHER;
430 ret = tdb_delete(ltdb->tdb, tdb_key);
431 talloc_free(tdb_key.dptr);
433 if (ret != 0) {
434 ret = ltdb_err_map(tdb_error(ltdb->tdb));
437 return ret;
440 static int ltdb_delete_internal(struct ldb_module *module, struct ldb_dn *dn)
442 struct ldb_message *msg;
443 int ret = LDB_SUCCESS;
445 msg = ldb_msg_new(module);
446 if (msg == NULL) {
447 return LDB_ERR_OPERATIONS_ERROR;
450 /* in case any attribute of the message was indexed, we need
451 to fetch the old record */
452 ret = ltdb_search_dn1(module, dn, msg, LDB_UNPACK_DATA_FLAG_NO_DATA_ALLOC);
453 if (ret != LDB_SUCCESS) {
454 /* not finding the old record is an error */
455 goto done;
458 ret = ltdb_delete_noindex(module, dn);
459 if (ret != LDB_SUCCESS) {
460 goto done;
463 /* remove any indexed attributes */
464 ret = ltdb_index_delete(module, msg);
465 if (ret != LDB_SUCCESS) {
466 goto done;
469 ret = ltdb_modified(module, dn);
470 if (ret != LDB_SUCCESS) {
471 goto done;
474 done:
475 talloc_free(msg);
476 return ret;
480 delete a record from the database
482 static int ltdb_delete(struct ltdb_context *ctx)
484 struct ldb_module *module = ctx->module;
485 struct ldb_request *req = ctx->req;
486 int ret = LDB_SUCCESS;
488 ldb_request_set_state(req, LDB_ASYNC_PENDING);
490 if (ltdb_cache_load(module) != 0) {
491 return LDB_ERR_OPERATIONS_ERROR;
494 ret = ltdb_delete_internal(module, req->op.del.dn);
496 return ret;
500 find an element by attribute name. At the moment this does a linear search,
501 it should be re-coded to use a binary search once all places that modify
502 records guarantee sorted order
504 return the index of the first matching element if found, otherwise -1
506 static int find_element(const struct ldb_message *msg, const char *name)
508 unsigned int i;
509 for (i=0;i<msg->num_elements;i++) {
510 if (ldb_attr_cmp(msg->elements[i].name, name) == 0) {
511 return i;
514 return -1;
519 add an element to an existing record. Assumes a elements array that we
520 can call re-alloc on, and assumed that we can re-use the data pointers from
521 the passed in additional values. Use with care!
523 returns 0 on success, -1 on failure (and sets errno)
525 static int ltdb_msg_add_element(struct ldb_context *ldb,
526 struct ldb_message *msg,
527 struct ldb_message_element *el)
529 struct ldb_message_element *e2;
530 unsigned int i;
532 if (el->num_values == 0) {
533 /* nothing to do here - we don't add empty elements */
534 return 0;
537 e2 = talloc_realloc(msg, msg->elements, struct ldb_message_element,
538 msg->num_elements+1);
539 if (!e2) {
540 errno = ENOMEM;
541 return -1;
544 msg->elements = e2;
546 e2 = &msg->elements[msg->num_elements];
548 e2->name = el->name;
549 e2->flags = el->flags;
550 e2->values = talloc_array(msg->elements,
551 struct ldb_val, el->num_values);
552 if (!e2->values) {
553 errno = ENOMEM;
554 return -1;
556 for (i=0;i<el->num_values;i++) {
557 e2->values[i] = el->values[i];
559 e2->num_values = el->num_values;
561 ++msg->num_elements;
563 return 0;
567 delete all elements having a specified attribute name
569 static int msg_delete_attribute(struct ldb_module *module,
570 struct ldb_context *ldb,
571 struct ldb_message *msg, const char *name)
573 unsigned int i;
574 int ret;
575 struct ldb_message_element *el;
577 el = ldb_msg_find_element(msg, name);
578 if (el == NULL) {
579 return LDB_ERR_NO_SUCH_ATTRIBUTE;
581 i = el - msg->elements;
583 ret = ltdb_index_del_element(module, msg->dn, el);
584 if (ret != LDB_SUCCESS) {
585 return ret;
588 talloc_free(el->values);
589 if (msg->num_elements > (i+1)) {
590 memmove(el, el+1, sizeof(*el) * (msg->num_elements - (i+1)));
592 msg->num_elements--;
593 msg->elements = talloc_realloc(msg, msg->elements,
594 struct ldb_message_element,
595 msg->num_elements);
596 return LDB_SUCCESS;
600 delete all elements matching an attribute name/value
602 return LDB Error on failure
604 static int msg_delete_element(struct ldb_module *module,
605 struct ldb_message *msg,
606 const char *name,
607 const struct ldb_val *val)
609 struct ldb_context *ldb = ldb_module_get_ctx(module);
610 unsigned int i;
611 int found, ret;
612 struct ldb_message_element *el;
613 const struct ldb_schema_attribute *a;
615 found = find_element(msg, name);
616 if (found == -1) {
617 return LDB_ERR_NO_SUCH_ATTRIBUTE;
620 i = (unsigned int) found;
621 el = &(msg->elements[i]);
623 a = ldb_schema_attribute_by_name(ldb, el->name);
625 for (i=0;i<el->num_values;i++) {
626 bool matched;
627 if (a->syntax->operator_fn) {
628 ret = a->syntax->operator_fn(ldb, LDB_OP_EQUALITY, a,
629 &el->values[i], val, &matched);
630 if (ret != LDB_SUCCESS) return ret;
631 } else {
632 matched = (a->syntax->comparison_fn(ldb, ldb,
633 &el->values[i], val) == 0);
635 if (matched) {
636 if (el->num_values == 1) {
637 return msg_delete_attribute(module, ldb, msg, name);
640 ret = ltdb_index_del_value(module, msg->dn, el, i);
641 if (ret != LDB_SUCCESS) {
642 return ret;
645 if (i<el->num_values-1) {
646 memmove(&el->values[i], &el->values[i+1],
647 sizeof(el->values[i])*
648 (el->num_values-(i+1)));
650 el->num_values--;
652 /* per definition we find in a canonicalised message an
653 attribute value only once. So we are finished here */
654 return LDB_SUCCESS;
658 /* Not found */
659 return LDB_ERR_NO_SUCH_ATTRIBUTE;
664 modify a record - internal interface
666 yuck - this is O(n^2). Luckily n is usually small so we probably
667 get away with it, but if we ever have really large attribute lists
668 then we'll need to look at this again
670 'req' is optional, and is used to specify controls if supplied
672 int ltdb_modify_internal(struct ldb_module *module,
673 const struct ldb_message *msg,
674 struct ldb_request *req)
676 struct ldb_context *ldb = ldb_module_get_ctx(module);
677 void *data = ldb_module_get_private(module);
678 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
679 TDB_DATA tdb_key, tdb_data;
680 struct ldb_val ldb_data;
681 struct ldb_message *msg2;
682 unsigned int i, j, k;
683 int ret = LDB_SUCCESS, idx;
684 struct ldb_control *control_permissive = NULL;
686 if (req) {
687 control_permissive = ldb_request_get_control(req,
688 LDB_CONTROL_PERMISSIVE_MODIFY_OID);
691 tdb_key = ltdb_key(module, msg->dn);
692 if (!tdb_key.dptr) {
693 return LDB_ERR_OTHER;
696 tdb_data = tdb_fetch(ltdb->tdb, tdb_key);
697 if (!tdb_data.dptr) {
698 talloc_free(tdb_key.dptr);
699 return ltdb_err_map(tdb_error(ltdb->tdb));
702 msg2 = ldb_msg_new(tdb_key.dptr);
703 if (msg2 == NULL) {
704 free(tdb_data.dptr);
705 ret = LDB_ERR_OTHER;
706 goto done;
709 ldb_data.data = tdb_data.dptr;
710 ldb_data.length = tdb_data.dsize;
712 ret = ldb_unpack_data(ldb_module_get_ctx(module), &ldb_data, msg2);
713 free(tdb_data.dptr);
714 if (ret == -1) {
715 ret = LDB_ERR_OTHER;
716 goto done;
719 if (!msg2->dn) {
720 msg2->dn = msg->dn;
723 for (i=0; i<msg->num_elements; i++) {
724 struct ldb_message_element *el = &msg->elements[i], *el2;
725 struct ldb_val *vals;
726 const struct ldb_schema_attribute *a = ldb_schema_attribute_by_name(ldb, el->name);
727 const char *dn;
729 switch (msg->elements[i].flags & LDB_FLAG_MOD_MASK) {
730 case LDB_FLAG_MOD_ADD:
732 if (el->num_values == 0) {
733 ldb_asprintf_errstring(ldb,
734 "attribute '%s': attribute on '%s' specified, but with 0 values (illegal)",
735 el->name, ldb_dn_get_linearized(msg2->dn));
736 ret = LDB_ERR_CONSTRAINT_VIOLATION;
737 goto done;
740 /* make a copy of the array so that a permissive
741 * control can remove duplicates without changing the
742 * original values, but do not copy data as we do not
743 * need to keep it around once the operation is
744 * finished */
745 if (control_permissive) {
746 el = talloc(msg2, struct ldb_message_element);
747 if (!el) {
748 ret = LDB_ERR_OTHER;
749 goto done;
751 *el = msg->elements[i];
752 el->values = talloc_array(el, struct ldb_val, el->num_values);
753 if (el->values == NULL) {
754 ret = LDB_ERR_OTHER;
755 goto done;
757 for (j = 0; j < el->num_values; j++) {
758 el->values[j] = msg->elements[i].values[j];
762 if (el->num_values > 1 && ldb_tdb_single_valued(a, el)) {
763 ldb_asprintf_errstring(ldb, "SINGLE-VALUE attribute %s on %s specified more than once",
764 el->name, ldb_dn_get_linearized(msg2->dn));
765 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
766 goto done;
769 /* Checks if element already exists */
770 idx = find_element(msg2, el->name);
771 if (idx == -1) {
772 if (ltdb_msg_add_element(ldb, msg2, el) != 0) {
773 ret = LDB_ERR_OTHER;
774 goto done;
776 ret = ltdb_index_add_element(module, msg2->dn,
777 el);
778 if (ret != LDB_SUCCESS) {
779 goto done;
781 } else {
782 j = (unsigned int) idx;
783 el2 = &(msg2->elements[j]);
785 /* We cannot add another value on a existing one
786 if the attribute is single-valued */
787 if (ldb_tdb_single_valued(a, el)) {
788 ldb_asprintf_errstring(ldb, "SINGLE-VALUE attribute %s on %s specified more than once",
789 el->name, ldb_dn_get_linearized(msg2->dn));
790 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
791 goto done;
794 /* Check that values don't exist yet on multi-
795 valued attributes or aren't provided twice */
796 /* TODO: This is O(n^2) - replace with more efficient check */
797 for (j = 0; j < el->num_values; j++) {
798 if (ldb_msg_find_val(el2, &el->values[j]) != NULL) {
799 if (control_permissive) {
800 /* remove this one as if it was never added */
801 el->num_values--;
802 for (k = j; k < el->num_values; k++) {
803 el->values[k] = el->values[k + 1];
805 j--; /* rewind */
807 continue;
810 ldb_asprintf_errstring(ldb,
811 "attribute '%s': value #%u on '%s' already exists",
812 el->name, j, ldb_dn_get_linearized(msg2->dn));
813 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
814 goto done;
816 if (ldb_msg_find_val(el, &el->values[j]) != &el->values[j]) {
817 ldb_asprintf_errstring(ldb,
818 "attribute '%s': value #%u on '%s' provided more than once",
819 el->name, j, ldb_dn_get_linearized(msg2->dn));
820 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
821 goto done;
825 /* Now combine existing and new values to a new
826 attribute record */
827 vals = talloc_realloc(msg2->elements,
828 el2->values, struct ldb_val,
829 el2->num_values + el->num_values);
830 if (vals == NULL) {
831 ldb_oom(ldb);
832 ret = LDB_ERR_OTHER;
833 goto done;
836 for (j=0; j<el->num_values; j++) {
837 vals[el2->num_values + j] =
838 ldb_val_dup(vals, &el->values[j]);
841 el2->values = vals;
842 el2->num_values += el->num_values;
844 ret = ltdb_index_add_element(module, msg2->dn, el);
845 if (ret != LDB_SUCCESS) {
846 goto done;
850 break;
852 case LDB_FLAG_MOD_REPLACE:
854 if (el->num_values > 1 && ldb_tdb_single_valued(a, el)) {
855 ldb_asprintf_errstring(ldb, "SINGLE-VALUE attribute %s on %s specified more than once",
856 el->name, ldb_dn_get_linearized(msg2->dn));
857 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
858 goto done;
862 * We don't need to check this if we have been
863 * pre-screened by the repl_meta_data module
864 * in Samba, or someone else who can claim to
865 * know what they are doing.
867 if (!(el->flags & LDB_FLAG_INTERNAL_DISABLE_SINGLE_VALUE_CHECK)) {
868 /* TODO: This is O(n^2) - replace with more efficient check */
869 for (j=0; j<el->num_values; j++) {
870 if (ldb_msg_find_val(el, &el->values[j]) != &el->values[j]) {
871 ldb_asprintf_errstring(ldb,
872 "attribute '%s': value #%u on '%s' provided more than once",
873 el->name, j, ldb_dn_get_linearized(msg2->dn));
874 ret = LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS;
875 goto done;
880 /* Checks if element already exists */
881 idx = find_element(msg2, el->name);
882 if (idx != -1) {
883 j = (unsigned int) idx;
884 el2 = &(msg2->elements[j]);
886 /* we consider two elements to be
887 * equal only if the order
888 * matches. This allows dbcheck to
889 * fix the ordering on attributes
890 * where order matters, such as
891 * objectClass
893 if (ldb_msg_element_equal_ordered(el, el2)) {
894 continue;
897 /* Delete the attribute if it exists in the DB */
898 if (msg_delete_attribute(module, ldb, msg2,
899 el->name) != 0) {
900 ret = LDB_ERR_OTHER;
901 goto done;
905 /* Recreate it with the new values */
906 if (ltdb_msg_add_element(ldb, msg2, el) != 0) {
907 ret = LDB_ERR_OTHER;
908 goto done;
911 ret = ltdb_index_add_element(module, msg2->dn, el);
912 if (ret != LDB_SUCCESS) {
913 goto done;
916 break;
918 case LDB_FLAG_MOD_DELETE:
919 dn = ldb_dn_get_linearized(msg2->dn);
920 if (dn == NULL) {
921 ret = LDB_ERR_OTHER;
922 goto done;
925 if (msg->elements[i].num_values == 0) {
926 /* Delete the whole attribute */
927 ret = msg_delete_attribute(module, ldb, msg2,
928 msg->elements[i].name);
929 if (ret == LDB_ERR_NO_SUCH_ATTRIBUTE &&
930 control_permissive) {
931 ret = LDB_SUCCESS;
932 } else {
933 ldb_asprintf_errstring(ldb,
934 "attribute '%s': no such attribute for delete on '%s'",
935 msg->elements[i].name, dn);
937 if (ret != LDB_SUCCESS) {
938 goto done;
940 } else {
941 /* Delete specified values from an attribute */
942 for (j=0; j < msg->elements[i].num_values; j++) {
943 ret = msg_delete_element(module,
944 msg2,
945 msg->elements[i].name,
946 &msg->elements[i].values[j]);
947 if (ret == LDB_ERR_NO_SUCH_ATTRIBUTE &&
948 control_permissive) {
949 ret = LDB_SUCCESS;
950 } else if (ret == LDB_ERR_NO_SUCH_ATTRIBUTE) {
951 ldb_asprintf_errstring(ldb,
952 "attribute '%s': no matching attribute value while deleting attribute on '%s'",
953 msg->elements[i].name, dn);
955 if (ret != LDB_SUCCESS) {
956 goto done;
960 break;
961 default:
962 ldb_asprintf_errstring(ldb,
963 "attribute '%s': invalid modify flags on '%s': 0x%x",
964 msg->elements[i].name, ldb_dn_get_linearized(msg->dn),
965 msg->elements[i].flags & LDB_FLAG_MOD_MASK);
966 ret = LDB_ERR_PROTOCOL_ERROR;
967 goto done;
971 ret = ltdb_store(module, msg2, TDB_MODIFY);
972 if (ret != LDB_SUCCESS) {
973 goto done;
976 ret = ltdb_modified(module, msg2->dn);
977 if (ret != LDB_SUCCESS) {
978 goto done;
981 done:
982 talloc_free(tdb_key.dptr);
983 return ret;
987 modify a record
989 static int ltdb_modify(struct ltdb_context *ctx)
991 struct ldb_module *module = ctx->module;
992 struct ldb_request *req = ctx->req;
993 int ret = LDB_SUCCESS;
995 ret = ltdb_check_special_dn(module, req->op.mod.message);
996 if (ret != LDB_SUCCESS) {
997 return ret;
1000 ldb_request_set_state(req, LDB_ASYNC_PENDING);
1002 if (ltdb_cache_load(module) != 0) {
1003 return LDB_ERR_OPERATIONS_ERROR;
1006 ret = ltdb_modify_internal(module, req->op.mod.message, req);
1008 return ret;
1012 rename a record
1014 static int ltdb_rename(struct ltdb_context *ctx)
1016 struct ldb_module *module = ctx->module;
1017 void *data = ldb_module_get_private(module);
1018 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
1019 struct ldb_request *req = ctx->req;
1020 struct ldb_message *msg;
1021 int ret = LDB_SUCCESS;
1022 TDB_DATA tdb_key, tdb_key_old;
1024 ldb_request_set_state(req, LDB_ASYNC_PENDING);
1026 if (ltdb_cache_load(ctx->module) != 0) {
1027 return LDB_ERR_OPERATIONS_ERROR;
1030 msg = ldb_msg_new(ctx);
1031 if (msg == NULL) {
1032 return LDB_ERR_OPERATIONS_ERROR;
1035 /* we need to fetch the old record to re-add under the new name */
1036 ret = ltdb_search_dn1(module, req->op.rename.olddn, msg,
1037 LDB_UNPACK_DATA_FLAG_NO_DATA_ALLOC);
1038 if (ret != LDB_SUCCESS) {
1039 /* not finding the old record is an error */
1040 return ret;
1043 /* We need to, before changing the DB, check if the new DN
1044 * exists, so we can return this error to the caller with an
1045 * unmodified DB */
1046 tdb_key = ltdb_key(module, req->op.rename.newdn);
1047 if (!tdb_key.dptr) {
1048 talloc_free(msg);
1049 return LDB_ERR_OPERATIONS_ERROR;
1052 tdb_key_old = ltdb_key(module, req->op.rename.olddn);
1053 if (!tdb_key_old.dptr) {
1054 talloc_free(msg);
1055 talloc_free(tdb_key.dptr);
1056 return LDB_ERR_OPERATIONS_ERROR;
1059 /* Only declare a conflict if the new DN already exists, and it isn't a case change on the old DN */
1060 if (tdb_key_old.dsize != tdb_key.dsize || memcmp(tdb_key.dptr, tdb_key_old.dptr, tdb_key.dsize) != 0) {
1061 if (tdb_exists(ltdb->tdb, tdb_key)) {
1062 talloc_free(tdb_key_old.dptr);
1063 talloc_free(tdb_key.dptr);
1064 ldb_asprintf_errstring(ldb_module_get_ctx(module),
1065 "Entry %s already exists",
1066 ldb_dn_get_linearized(req->op.rename.newdn));
1067 /* finding the new record already in the DB is an error */
1068 talloc_free(msg);
1069 return LDB_ERR_ENTRY_ALREADY_EXISTS;
1072 talloc_free(tdb_key_old.dptr);
1073 talloc_free(tdb_key.dptr);
1075 /* Always delete first then add, to avoid conflicts with
1076 * unique indexes. We rely on the transaction to make this
1077 * atomic
1079 ret = ltdb_delete_internal(module, msg->dn);
1080 if (ret != LDB_SUCCESS) {
1081 talloc_free(msg);
1082 return ret;
1085 msg->dn = ldb_dn_copy(msg, req->op.rename.newdn);
1086 if (msg->dn == NULL) {
1087 talloc_free(msg);
1088 return LDB_ERR_OPERATIONS_ERROR;
1091 /* We don't check single value as we can have more than 1 with
1092 * deleted attributes. We could go through all elements but that's
1093 * maybe not the most efficient way
1095 ret = ltdb_add_internal(module, msg, false);
1097 talloc_free(msg);
1099 return ret;
1102 static int ltdb_start_trans(struct ldb_module *module)
1104 void *data = ldb_module_get_private(module);
1105 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
1107 if (tdb_transaction_start(ltdb->tdb) != 0) {
1108 return ltdb_err_map(tdb_error(ltdb->tdb));
1111 ltdb->in_transaction++;
1113 ltdb_index_transaction_start(module);
1115 return LDB_SUCCESS;
1118 static int ltdb_prepare_commit(struct ldb_module *module)
1120 void *data = ldb_module_get_private(module);
1121 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
1123 if (ltdb->in_transaction != 1) {
1124 return LDB_SUCCESS;
1127 if (ltdb_index_transaction_commit(module) != 0) {
1128 tdb_transaction_cancel(ltdb->tdb);
1129 ltdb->in_transaction--;
1130 return ltdb_err_map(tdb_error(ltdb->tdb));
1133 if (tdb_transaction_prepare_commit(ltdb->tdb) != 0) {
1134 ltdb->in_transaction--;
1135 return ltdb_err_map(tdb_error(ltdb->tdb));
1138 ltdb->prepared_commit = true;
1140 return LDB_SUCCESS;
1143 static int ltdb_end_trans(struct ldb_module *module)
1145 void *data = ldb_module_get_private(module);
1146 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
1148 if (!ltdb->prepared_commit) {
1149 int ret = ltdb_prepare_commit(module);
1150 if (ret != LDB_SUCCESS) {
1151 return ret;
1155 ltdb->in_transaction--;
1156 ltdb->prepared_commit = false;
1158 if (tdb_transaction_commit(ltdb->tdb) != 0) {
1159 return ltdb_err_map(tdb_error(ltdb->tdb));
1162 return LDB_SUCCESS;
1165 static int ltdb_del_trans(struct ldb_module *module)
1167 void *data = ldb_module_get_private(module);
1168 struct ltdb_private *ltdb = talloc_get_type(data, struct ltdb_private);
1170 ltdb->in_transaction--;
1172 if (ltdb_index_transaction_cancel(module) != 0) {
1173 tdb_transaction_cancel(ltdb->tdb);
1174 return ltdb_err_map(tdb_error(ltdb->tdb));
1177 tdb_transaction_cancel(ltdb->tdb);
1178 return LDB_SUCCESS;
1182 return sequenceNumber from @BASEINFO
1184 static int ltdb_sequence_number(struct ltdb_context *ctx,
1185 struct ldb_extended **ext)
1187 struct ldb_context *ldb;
1188 struct ldb_module *module = ctx->module;
1189 struct ldb_request *req = ctx->req;
1190 TALLOC_CTX *tmp_ctx = NULL;
1191 struct ldb_seqnum_request *seq;
1192 struct ldb_seqnum_result *res;
1193 struct ldb_message *msg = NULL;
1194 struct ldb_dn *dn;
1195 const char *date;
1196 int ret = LDB_SUCCESS;
1198 ldb = ldb_module_get_ctx(module);
1200 seq = talloc_get_type(req->op.extended.data,
1201 struct ldb_seqnum_request);
1202 if (seq == NULL) {
1203 return LDB_ERR_OPERATIONS_ERROR;
1206 ldb_request_set_state(req, LDB_ASYNC_PENDING);
1208 if (ltdb_lock_read(module) != 0) {
1209 return LDB_ERR_OPERATIONS_ERROR;
1212 res = talloc_zero(req, struct ldb_seqnum_result);
1213 if (res == NULL) {
1214 ret = LDB_ERR_OPERATIONS_ERROR;
1215 goto done;
1218 tmp_ctx = talloc_new(req);
1219 if (tmp_ctx == NULL) {
1220 ret = LDB_ERR_OPERATIONS_ERROR;
1221 goto done;
1224 dn = ldb_dn_new(tmp_ctx, ldb, LTDB_BASEINFO);
1225 if (dn == NULL) {
1226 ret = LDB_ERR_OPERATIONS_ERROR;
1227 goto done;
1230 msg = ldb_msg_new(tmp_ctx);
1231 if (msg == NULL) {
1232 ret = LDB_ERR_OPERATIONS_ERROR;
1233 goto done;
1236 ret = ltdb_search_dn1(module, dn, msg, 0);
1237 if (ret != LDB_SUCCESS) {
1238 goto done;
1241 switch (seq->type) {
1242 case LDB_SEQ_HIGHEST_SEQ:
1243 res->seq_num = ldb_msg_find_attr_as_uint64(msg, LTDB_SEQUENCE_NUMBER, 0);
1244 break;
1245 case LDB_SEQ_NEXT:
1246 res->seq_num = ldb_msg_find_attr_as_uint64(msg, LTDB_SEQUENCE_NUMBER, 0);
1247 res->seq_num++;
1248 break;
1249 case LDB_SEQ_HIGHEST_TIMESTAMP:
1250 date = ldb_msg_find_attr_as_string(msg, LTDB_MOD_TIMESTAMP, NULL);
1251 if (date) {
1252 res->seq_num = ldb_string_to_time(date);
1253 } else {
1254 res->seq_num = 0;
1255 /* zero is as good as anything when we don't know */
1257 break;
1260 *ext = talloc_zero(req, struct ldb_extended);
1261 if (*ext == NULL) {
1262 ret = LDB_ERR_OPERATIONS_ERROR;
1263 goto done;
1265 (*ext)->oid = LDB_EXTENDED_SEQUENCE_NUMBER;
1266 (*ext)->data = talloc_steal(*ext, res);
1268 done:
1269 talloc_free(tmp_ctx);
1270 ltdb_unlock_read(module);
1271 return ret;
1274 static void ltdb_request_done(struct ltdb_context *ctx, int error)
1276 struct ldb_context *ldb;
1277 struct ldb_request *req;
1278 struct ldb_reply *ares;
1280 ldb = ldb_module_get_ctx(ctx->module);
1281 req = ctx->req;
1283 /* if we already returned an error just return */
1284 if (ldb_request_get_status(req) != LDB_SUCCESS) {
1285 return;
1288 ares = talloc_zero(req, struct ldb_reply);
1289 if (!ares) {
1290 ldb_oom(ldb);
1291 req->callback(req, NULL);
1292 return;
1294 ares->type = LDB_REPLY_DONE;
1295 ares->error = error;
1297 req->callback(req, ares);
1300 static void ltdb_timeout(struct tevent_context *ev,
1301 struct tevent_timer *te,
1302 struct timeval t,
1303 void *private_data)
1305 struct ltdb_context *ctx;
1306 ctx = talloc_get_type(private_data, struct ltdb_context);
1308 if (!ctx->request_terminated) {
1309 /* request is done now */
1310 ltdb_request_done(ctx, LDB_ERR_TIME_LIMIT_EXCEEDED);
1313 if (ctx->spy) {
1314 /* neutralize the spy */
1315 ctx->spy->ctx = NULL;
1316 ctx->spy = NULL;
1318 talloc_free(ctx);
1321 static void ltdb_request_extended_done(struct ltdb_context *ctx,
1322 struct ldb_extended *ext,
1323 int error)
1325 struct ldb_context *ldb;
1326 struct ldb_request *req;
1327 struct ldb_reply *ares;
1329 ldb = ldb_module_get_ctx(ctx->module);
1330 req = ctx->req;
1332 /* if we already returned an error just return */
1333 if (ldb_request_get_status(req) != LDB_SUCCESS) {
1334 return;
1337 ares = talloc_zero(req, struct ldb_reply);
1338 if (!ares) {
1339 ldb_oom(ldb);
1340 req->callback(req, NULL);
1341 return;
1343 ares->type = LDB_REPLY_DONE;
1344 ares->response = ext;
1345 ares->error = error;
1347 req->callback(req, ares);
1350 static void ltdb_handle_extended(struct ltdb_context *ctx)
1352 struct ldb_extended *ext = NULL;
1353 int ret;
1355 if (strcmp(ctx->req->op.extended.oid,
1356 LDB_EXTENDED_SEQUENCE_NUMBER) == 0) {
1357 /* get sequence number */
1358 ret = ltdb_sequence_number(ctx, &ext);
1359 } else {
1360 /* not recognized */
1361 ret = LDB_ERR_UNSUPPORTED_CRITICAL_EXTENSION;
1364 ltdb_request_extended_done(ctx, ext, ret);
1367 static void ltdb_callback(struct tevent_context *ev,
1368 struct tevent_timer *te,
1369 struct timeval t,
1370 void *private_data)
1372 struct ltdb_context *ctx;
1373 int ret;
1375 ctx = talloc_get_type(private_data, struct ltdb_context);
1377 if (ctx->request_terminated) {
1378 goto done;
1381 switch (ctx->req->operation) {
1382 case LDB_SEARCH:
1383 ret = ltdb_search(ctx);
1384 break;
1385 case LDB_ADD:
1386 ret = ltdb_add(ctx);
1387 break;
1388 case LDB_MODIFY:
1389 ret = ltdb_modify(ctx);
1390 break;
1391 case LDB_DELETE:
1392 ret = ltdb_delete(ctx);
1393 break;
1394 case LDB_RENAME:
1395 ret = ltdb_rename(ctx);
1396 break;
1397 case LDB_EXTENDED:
1398 ltdb_handle_extended(ctx);
1399 goto done;
1400 default:
1401 /* no other op supported */
1402 ret = LDB_ERR_PROTOCOL_ERROR;
1405 if (!ctx->request_terminated) {
1406 /* request is done now */
1407 ltdb_request_done(ctx, ret);
1410 done:
1411 if (ctx->spy) {
1412 /* neutralize the spy */
1413 ctx->spy->ctx = NULL;
1414 ctx->spy = NULL;
1416 talloc_free(ctx);
1419 static int ltdb_request_destructor(void *ptr)
1421 struct ltdb_req_spy *spy = talloc_get_type(ptr, struct ltdb_req_spy);
1423 if (spy->ctx != NULL) {
1424 spy->ctx->spy = NULL;
1425 spy->ctx->request_terminated = true;
1426 spy->ctx = NULL;
1429 return 0;
1432 static int ltdb_handle_request(struct ldb_module *module,
1433 struct ldb_request *req)
1435 struct ldb_control *control_permissive;
1436 struct ldb_context *ldb;
1437 struct tevent_context *ev;
1438 struct ltdb_context *ac;
1439 struct tevent_timer *te;
1440 struct timeval tv;
1441 unsigned int i;
1443 ldb = ldb_module_get_ctx(module);
1445 control_permissive = ldb_request_get_control(req,
1446 LDB_CONTROL_PERMISSIVE_MODIFY_OID);
1448 for (i = 0; req->controls && req->controls[i]; i++) {
1449 if (req->controls[i]->critical &&
1450 req->controls[i] != control_permissive) {
1451 ldb_asprintf_errstring(ldb, "Unsupported critical extension %s",
1452 req->controls[i]->oid);
1453 return LDB_ERR_UNSUPPORTED_CRITICAL_EXTENSION;
1457 if (req->starttime == 0 || req->timeout == 0) {
1458 ldb_set_errstring(ldb, "Invalid timeout settings");
1459 return LDB_ERR_TIME_LIMIT_EXCEEDED;
1462 ev = ldb_get_event_context(ldb);
1464 ac = talloc_zero(ldb, struct ltdb_context);
1465 if (ac == NULL) {
1466 ldb_oom(ldb);
1467 return LDB_ERR_OPERATIONS_ERROR;
1470 ac->module = module;
1471 ac->req = req;
1473 tv.tv_sec = 0;
1474 tv.tv_usec = 0;
1475 te = tevent_add_timer(ev, ac, tv, ltdb_callback, ac);
1476 if (NULL == te) {
1477 talloc_free(ac);
1478 return LDB_ERR_OPERATIONS_ERROR;
1481 if (req->timeout > 0) {
1482 tv.tv_sec = req->starttime + req->timeout;
1483 tv.tv_usec = 0;
1484 ac->timeout_event = tevent_add_timer(ev, ac, tv,
1485 ltdb_timeout, ac);
1486 if (NULL == ac->timeout_event) {
1487 talloc_free(ac);
1488 return LDB_ERR_OPERATIONS_ERROR;
1492 /* set a spy so that we do not try to use the request context
1493 * if it is freed before ltdb_callback fires */
1494 ac->spy = talloc(req, struct ltdb_req_spy);
1495 if (NULL == ac->spy) {
1496 talloc_free(ac);
1497 return LDB_ERR_OPERATIONS_ERROR;
1499 ac->spy->ctx = ac;
1501 talloc_set_destructor((TALLOC_CTX *)ac->spy, ltdb_request_destructor);
1503 return LDB_SUCCESS;
1506 static int ltdb_init_rootdse(struct ldb_module *module)
1508 /* ignore errors on this - we expect it for non-sam databases */
1509 ldb_mod_register_control(module, LDB_CONTROL_PERMISSIVE_MODIFY_OID);
1511 /* there can be no module beyond the backend, just return */
1512 return LDB_SUCCESS;
1515 static const struct ldb_module_ops ltdb_ops = {
1516 .name = "tdb",
1517 .init_context = ltdb_init_rootdse,
1518 .search = ltdb_handle_request,
1519 .add = ltdb_handle_request,
1520 .modify = ltdb_handle_request,
1521 .del = ltdb_handle_request,
1522 .rename = ltdb_handle_request,
1523 .extended = ltdb_handle_request,
1524 .start_transaction = ltdb_start_trans,
1525 .end_transaction = ltdb_end_trans,
1526 .prepare_commit = ltdb_prepare_commit,
1527 .del_transaction = ltdb_del_trans,
1531 connect to the database
1533 static int ltdb_connect(struct ldb_context *ldb, const char *url,
1534 unsigned int flags, const char *options[],
1535 struct ldb_module **_module)
1537 struct ldb_module *module;
1538 const char *path;
1539 int tdb_flags, open_flags;
1540 struct ltdb_private *ltdb;
1542 /* parse the url */
1543 if (strchr(url, ':')) {
1544 if (strncmp(url, "tdb://", 6) != 0) {
1545 ldb_debug(ldb, LDB_DEBUG_ERROR,
1546 "Invalid tdb URL '%s'", url);
1547 return LDB_ERR_OPERATIONS_ERROR;
1549 path = url+6;
1550 } else {
1551 path = url;
1554 tdb_flags = TDB_DEFAULT | TDB_SEQNUM;
1556 /* check for the 'nosync' option */
1557 if (flags & LDB_FLG_NOSYNC) {
1558 tdb_flags |= TDB_NOSYNC;
1561 /* and nommap option */
1562 if (flags & LDB_FLG_NOMMAP) {
1563 tdb_flags |= TDB_NOMMAP;
1566 if (flags & LDB_FLG_RDONLY) {
1567 open_flags = O_RDONLY;
1568 } else if (flags & LDB_FLG_DONT_CREATE_DB) {
1569 open_flags = O_RDWR;
1570 } else {
1571 open_flags = O_CREAT | O_RDWR;
1574 ltdb = talloc_zero(ldb, struct ltdb_private);
1575 if (!ltdb) {
1576 ldb_oom(ldb);
1577 return LDB_ERR_OPERATIONS_ERROR;
1580 /* note that we use quite a large default hash size */
1581 ltdb->tdb = ltdb_wrap_open(ltdb, path, 10000,
1582 tdb_flags, open_flags,
1583 ldb_get_create_perms(ldb), ldb);
1584 if (!ltdb->tdb) {
1585 ldb_asprintf_errstring(ldb,
1586 "Unable to open tdb '%s': %s", path, strerror(errno));
1587 ldb_debug(ldb, LDB_DEBUG_ERROR,
1588 "Unable to open tdb '%s': %s", path, strerror(errno));
1589 talloc_free(ltdb);
1590 if (errno == EACCES || errno == EPERM) {
1591 return LDB_ERR_INSUFFICIENT_ACCESS_RIGHTS;
1593 return LDB_ERR_OPERATIONS_ERROR;
1596 if (getenv("LDB_WARN_UNINDEXED")) {
1597 ltdb->warn_unindexed = true;
1600 if (getenv("LDB_WARN_REINDEX")) {
1601 ltdb->warn_reindex = true;
1604 ltdb->sequence_number = 0;
1606 module = ldb_module_new(ldb, ldb, "ldb_tdb backend", &ltdb_ops);
1607 if (!module) {
1608 ldb_oom(ldb);
1609 talloc_free(ltdb);
1610 return LDB_ERR_OPERATIONS_ERROR;
1612 ldb_module_set_private(module, ltdb);
1613 talloc_steal(module, ltdb);
1615 if (ltdb_cache_load(module) != 0) {
1616 ldb_asprintf_errstring(ldb,
1617 "Unable to load ltdb cache records of tdb '%s'", path);
1618 talloc_free(module);
1619 return LDB_ERR_OPERATIONS_ERROR;
1622 *_module = module;
1623 return LDB_SUCCESS;
1626 int ldb_tdb_init(const char *version)
1628 LDB_MODULE_CHECK_VERSION(version);
1629 return ldb_register_backend("tdb", ltdb_connect, false);