4 Copyright (C) Andrew Tridgell 2004
5 Copyright (C) Simo Sorce 2005-2008
7 ** NOTE! The following LGPL license applies to the ldb
8 ** library. This does NOT imply that all of Samba is released
11 This library is free software; you can redistribute it and/or
12 modify it under the terms of the GNU Lesser General Public
13 License as published by the Free Software Foundation; either
14 version 3 of the License, or (at your option) any later version.
16 This library is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
19 Lesser General Public License for more details.
21 You should have received a copy of the GNU Lesser General Public
22 License along with this library; if not, see <http://www.gnu.org/licenses/>.
28 * Component: ldb core API
30 * Description: core API routines interfacing to ldb backends
32 * Author: Andrew Tridgell
35 #define TEVENT_DEPRECATED 1
36 #include "ldb_private.h"
39 static int ldb_context_destructor(void *ptr)
41 struct ldb_context *ldb = talloc_get_type(ptr, struct ldb_context);
43 if (ldb->transaction_active) {
44 ldb_debug(ldb, LDB_DEBUG_FATAL,
45 "A transaction is still active in ldb context [%p] on %s",
46 ldb, (const char *)ldb_get_opaque(ldb, "ldb_url"));
53 this is used to catch debug messages from events
55 static void ldb_tevent_debug(void *context, enum tevent_debug_level level,
56 const char *fmt, va_list ap) PRINTF_ATTRIBUTE(3,0);
58 static void ldb_tevent_debug(void *context, enum tevent_debug_level level,
59 const char *fmt, va_list ap)
61 struct ldb_context *ldb = talloc_get_type(context, struct ldb_context);
62 enum ldb_debug_level ldb_level = LDB_DEBUG_FATAL;
66 case TEVENT_DEBUG_FATAL:
67 ldb_level = LDB_DEBUG_FATAL;
69 case TEVENT_DEBUG_ERROR:
70 ldb_level = LDB_DEBUG_ERROR;
72 case TEVENT_DEBUG_WARNING:
73 ldb_level = LDB_DEBUG_WARNING;
75 case TEVENT_DEBUG_TRACE:
76 ldb_level = LDB_DEBUG_TRACE;
80 vasprintf(&s, fmt, ap);
82 ldb_debug(ldb, ldb_level, "tevent: %s", s);
87 initialise a ldb context
88 The mem_ctx is required
89 The event_ctx is required
91 struct ldb_context *ldb_init(TALLOC_CTX *mem_ctx, struct tevent_context *ev_ctx)
93 struct ldb_context *ldb;
95 const char *modules_path = getenv("LDB_MODULES_PATH");
97 if (modules_path == NULL) {
98 modules_path = LDB_MODULESDIR;
101 ret = ldb_modules_load(modules_path, LDB_VERSION);
102 if (ret != LDB_SUCCESS) {
106 ldb = talloc_zero(mem_ctx, struct ldb_context);
111 /* A new event context so that callers who don't want ldb
112 * operating on thier global event context can work without
113 * having to provide their own private one explicitly */
114 if (ev_ctx == NULL) {
115 ev_ctx = tevent_context_init(ldb);
116 tevent_set_debug(ev_ctx, ldb_tevent_debug, ldb);
117 tevent_loop_allow_nesting(ev_ctx);
120 ret = ldb_setup_wellknown_attributes(ldb);
121 if (ret != LDB_SUCCESS) {
126 ldb_set_utf8_default(ldb);
127 ldb_set_create_perms(ldb, 0666);
128 ldb_set_modules_dir(ldb, LDB_MODULESDIR);
129 ldb_set_event_context(ldb, ev_ctx);
131 /* TODO: get timeout from options if available there */
132 ldb->default_timeout = 300; /* set default to 5 minutes */
134 talloc_set_destructor((TALLOC_CTX *)ldb, ldb_context_destructor);
140 try to autodetect a basedn if none specified. This fixes one of my
141 pet hates about ldapsearch, which is that you have to get a long,
142 complex basedn right to make any use of it.
144 void ldb_set_default_dns(struct ldb_context *ldb)
148 struct ldb_result *res;
149 struct ldb_dn *tmp_dn=NULL;
150 static const char *attrs[] = {
151 "rootDomainNamingContext",
152 "configurationNamingContext",
153 "schemaNamingContext",
154 "defaultNamingContext",
158 tmp_ctx = talloc_new(ldb);
159 ret = ldb_search(ldb, tmp_ctx, &res, ldb_dn_new(tmp_ctx, ldb, NULL),
160 LDB_SCOPE_BASE, attrs, "(objectClass=*)");
161 if (ret != LDB_SUCCESS) {
162 talloc_free(tmp_ctx);
166 if (res->count != 1) {
167 talloc_free(tmp_ctx);
171 if (!ldb_get_opaque(ldb, "rootDomainNamingContext")) {
172 tmp_dn = ldb_msg_find_attr_as_dn(ldb, ldb, res->msgs[0],
173 "rootDomainNamingContext");
174 ldb_set_opaque(ldb, "rootDomainNamingContext", tmp_dn);
177 if (!ldb_get_opaque(ldb, "configurationNamingContext")) {
178 tmp_dn = ldb_msg_find_attr_as_dn(ldb, ldb, res->msgs[0],
179 "configurationNamingContext");
180 ldb_set_opaque(ldb, "configurationNamingContext", tmp_dn);
183 if (!ldb_get_opaque(ldb, "schemaNamingContext")) {
184 tmp_dn = ldb_msg_find_attr_as_dn(ldb, ldb, res->msgs[0],
185 "schemaNamingContext");
186 ldb_set_opaque(ldb, "schemaNamingContext", tmp_dn);
189 if (!ldb_get_opaque(ldb, "defaultNamingContext")) {
190 tmp_dn = ldb_msg_find_attr_as_dn(ldb, ldb, res->msgs[0],
191 "defaultNamingContext");
192 ldb_set_opaque(ldb, "defaultNamingContext", tmp_dn);
195 talloc_free(tmp_ctx);
198 struct ldb_dn *ldb_get_root_basedn(struct ldb_context *ldb)
200 void *opaque = ldb_get_opaque(ldb, "rootDomainNamingContext");
201 return talloc_get_type(opaque, struct ldb_dn);
204 struct ldb_dn *ldb_get_config_basedn(struct ldb_context *ldb)
206 void *opaque = ldb_get_opaque(ldb, "configurationNamingContext");
207 return talloc_get_type(opaque, struct ldb_dn);
210 struct ldb_dn *ldb_get_schema_basedn(struct ldb_context *ldb)
212 void *opaque = ldb_get_opaque(ldb, "schemaNamingContext");
213 return talloc_get_type(opaque, struct ldb_dn);
216 struct ldb_dn *ldb_get_default_basedn(struct ldb_context *ldb)
218 void *opaque = ldb_get_opaque(ldb, "defaultNamingContext");
219 return talloc_get_type(opaque, struct ldb_dn);
223 connect to a database. The URL can either be one of the following forms
227 flags is made up of LDB_FLG_*
229 the options are passed uninterpreted to the backend, and are
232 int ldb_connect(struct ldb_context *ldb, const char *url,
233 unsigned int flags, const char *options[])
237 /* We seem to need to do this here, or else some utilities don't
238 * get ldb backends */
242 url2 = talloc_strdup(ldb, url);
245 return LDB_ERR_OPERATIONS_ERROR;
247 ret = ldb_set_opaque(ldb, "ldb_url", url2);
248 if (ret != LDB_SUCCESS) {
252 ret = ldb_module_connect_backend(ldb, url, options, &ldb->modules);
253 if (ret != LDB_SUCCESS) {
257 if (ldb_load_modules(ldb, options) != LDB_SUCCESS) {
258 ldb_debug(ldb, LDB_DEBUG_FATAL,
259 "Unable to load modules for %s: %s",
260 url, ldb_errstring(ldb));
261 return LDB_ERR_OTHER;
264 /* set the default base dn */
265 ldb_set_default_dns(ldb);
270 void ldb_set_errstring(struct ldb_context *ldb, const char *err_string)
272 if (ldb->err_string) {
273 talloc_free(ldb->err_string);
275 ldb->err_string = talloc_strdup(ldb, err_string);
276 if (ldb->flags & LDB_FLG_ENABLE_TRACING) {
277 ldb_debug(ldb, LDB_DEBUG_TRACE, "ldb_set_errstring: %s", ldb->err_string);
281 void ldb_asprintf_errstring(struct ldb_context *ldb, const char *format, ...)
284 char *old_string = NULL;
286 if (ldb->err_string) {
287 old_string = ldb->err_string;
290 va_start(ap, format);
291 ldb->err_string = talloc_vasprintf(ldb, format, ap);
293 talloc_free(old_string);
296 void ldb_reset_err_string(struct ldb_context *ldb)
298 if (ldb->err_string) {
299 talloc_free(ldb->err_string);
300 ldb->err_string = NULL;
307 set an ldb error based on file:line
309 int ldb_error_at(struct ldb_context *ldb, int ecode,
310 const char *reason, const char *file, int line)
312 if (reason == NULL) {
313 reason = ldb_strerror(ecode);
315 ldb_asprintf_errstring(ldb, "%s at %s:%d", reason, file, line);
320 #define FIRST_OP_NOERR(ldb, op) do { \
321 module = ldb->modules; \
322 while (module && module->ops->op == NULL) module = module->next; \
323 if ((ldb->flags & LDB_FLG_ENABLE_TRACING) && module) { \
324 ldb_debug(ldb, LDB_DEBUG_TRACE, "ldb_trace_request: (%s)->" #op, \
325 module->ops->name); \
329 #define FIRST_OP(ldb, op) do { \
330 FIRST_OP_NOERR(ldb, op); \
331 if (module == NULL) { \
332 ldb_asprintf_errstring(ldb, "unable to find module or backend to handle operation: " #op); \
333 return LDB_ERR_OPERATIONS_ERROR; \
341 int ldb_transaction_start(struct ldb_context *ldb)
343 struct ldb_module *module;
346 ldb_debug(ldb, LDB_DEBUG_TRACE,
347 "start ldb transaction (nesting: %d)",
348 ldb->transaction_active);
350 /* explicit transaction active, count nested requests */
351 if (ldb->transaction_active) {
352 ldb->transaction_active++;
356 /* start a new transaction */
357 ldb->transaction_active++;
358 ldb->prepare_commit_done = false;
360 FIRST_OP(ldb, start_transaction);
362 ldb_reset_err_string(ldb);
364 status = module->ops->start_transaction(module);
365 if (status != LDB_SUCCESS) {
366 if (ldb->err_string == NULL) {
367 /* no error string was setup by the backend */
368 ldb_asprintf_errstring(ldb,
369 "ldb transaction start: %s (%d)",
370 ldb_strerror(status),
374 if ((module && module->ldb->flags & LDB_FLG_ENABLE_TRACING)) {
375 ldb_debug(module->ldb, LDB_DEBUG_TRACE, "start ldb transaction error: %s",
376 ldb_errstring(module->ldb));
382 prepare for transaction commit (first phase of two phase commit)
384 int ldb_transaction_prepare_commit(struct ldb_context *ldb)
386 struct ldb_module *module;
389 if (ldb->prepare_commit_done) {
393 /* commit only when all nested transactions are complete */
394 if (ldb->transaction_active > 1) {
398 ldb->prepare_commit_done = true;
400 if (ldb->transaction_active < 0) {
401 ldb_debug(ldb, LDB_DEBUG_FATAL,
402 "prepare commit called but no ldb transactions are active!");
403 ldb->transaction_active = 0;
404 return LDB_ERR_OPERATIONS_ERROR;
407 /* call prepare transaction if available */
408 FIRST_OP_NOERR(ldb, prepare_commit);
409 if (module == NULL) {
413 status = module->ops->prepare_commit(module);
414 if (status != LDB_SUCCESS) {
415 /* if a module fails the prepare then we need
416 to call the end transaction for everyone */
417 FIRST_OP(ldb, del_transaction);
418 module->ops->del_transaction(module);
419 if (ldb->err_string == NULL) {
420 /* no error string was setup by the backend */
421 ldb_asprintf_errstring(ldb,
422 "ldb transaction prepare commit: %s (%d)",
423 ldb_strerror(status),
426 if ((module && module->ldb->flags & LDB_FLG_ENABLE_TRACING)) {
427 ldb_debug(module->ldb, LDB_DEBUG_TRACE, "prepare commit transaction error: %s",
428 ldb_errstring(module->ldb));
439 int ldb_transaction_commit(struct ldb_context *ldb)
441 struct ldb_module *module;
444 status = ldb_transaction_prepare_commit(ldb);
445 if (status != LDB_SUCCESS) {
449 ldb->transaction_active--;
451 ldb_debug(ldb, LDB_DEBUG_TRACE,
452 "commit ldb transaction (nesting: %d)",
453 ldb->transaction_active);
455 /* commit only when all nested transactions are complete */
456 if (ldb->transaction_active > 0) {
460 if (ldb->transaction_active < 0) {
461 ldb_debug(ldb, LDB_DEBUG_FATAL,
462 "commit called but no ldb transactions are active!");
463 ldb->transaction_active = 0;
464 return LDB_ERR_OPERATIONS_ERROR;
467 ldb_reset_err_string(ldb);
469 FIRST_OP(ldb, end_transaction);
470 status = module->ops->end_transaction(module);
471 if (status != LDB_SUCCESS) {
472 if (ldb->err_string == NULL) {
473 /* no error string was setup by the backend */
474 ldb_asprintf_errstring(ldb,
475 "ldb transaction commit: %s (%d)",
476 ldb_strerror(status),
479 if ((module && module->ldb->flags & LDB_FLG_ENABLE_TRACING)) {
480 ldb_debug(module->ldb, LDB_DEBUG_TRACE, "commit ldb transaction error: %s",
481 ldb_errstring(module->ldb));
483 /* cancel the transaction */
484 FIRST_OP(ldb, del_transaction);
485 module->ops->del_transaction(module);
494 int ldb_transaction_cancel(struct ldb_context *ldb)
496 struct ldb_module *module;
499 ldb->transaction_active--;
501 ldb_debug(ldb, LDB_DEBUG_TRACE,
502 "cancel ldb transaction (nesting: %d)",
503 ldb->transaction_active);
505 /* really cancel only if all nested transactions are complete */
506 if (ldb->transaction_active > 0) {
510 if (ldb->transaction_active < 0) {
511 ldb_debug(ldb, LDB_DEBUG_FATAL,
512 "cancel called but no ldb transactions are active!");
513 ldb->transaction_active = 0;
514 return LDB_ERR_OPERATIONS_ERROR;
517 FIRST_OP(ldb, del_transaction);
519 status = module->ops->del_transaction(module);
520 if (status != LDB_SUCCESS) {
521 if (ldb->err_string == NULL) {
522 /* no error string was setup by the backend */
523 ldb_asprintf_errstring(ldb,
524 "ldb transaction cancel: %s (%d)",
525 ldb_strerror(status),
528 if ((module && module->ldb->flags & LDB_FLG_ENABLE_TRACING)) {
529 ldb_debug(module->ldb, LDB_DEBUG_TRACE, "cancel ldb transaction error: %s",
530 ldb_errstring(module->ldb));
537 cancel a transaction with no error if no transaction is pending
538 used when we fork() to clear any parent transactions
540 int ldb_transaction_cancel_noerr(struct ldb_context *ldb)
542 if (ldb->transaction_active > 0) {
543 return ldb_transaction_cancel(ldb);
549 /* autostarts a transacion if none active */
550 static int ldb_autotransaction_request(struct ldb_context *ldb,
551 struct ldb_request *req)
555 ret = ldb_transaction_start(ldb);
556 if (ret != LDB_SUCCESS) {
560 ret = ldb_request(ldb, req);
561 if (ret == LDB_SUCCESS) {
562 ret = ldb_wait(req->handle, LDB_WAIT_ALL);
565 if (ret == LDB_SUCCESS) {
566 return ldb_transaction_commit(ldb);
568 ldb_transaction_cancel(ldb);
570 if (ldb->err_string == NULL) {
571 /* no error string was setup by the backend */
572 ldb_asprintf_errstring(ldb, "%s (%d)", ldb_strerror(ret), ret);
578 int ldb_wait(struct ldb_handle *handle, enum ldb_wait_type type)
580 struct tevent_context *ev;
584 return LDB_ERR_UNAVAILABLE;
587 if (handle->state == LDB_ASYNC_DONE) {
588 return handle->status;
591 ev = ldb_get_event_context(handle->ldb);
593 return LDB_ERR_OPERATIONS_ERROR;
598 ret = tevent_loop_once(ev);
600 return LDB_ERR_OPERATIONS_ERROR;
602 if (handle->state == LDB_ASYNC_DONE ||
603 handle->status != LDB_SUCCESS) {
604 return handle->status;
609 while (handle->state != LDB_ASYNC_DONE) {
610 ret = tevent_loop_once(ev);
612 return LDB_ERR_OPERATIONS_ERROR;
614 if (handle->status != LDB_SUCCESS) {
615 return handle->status;
618 return handle->status;
624 /* set the specified timeout or, if timeout is 0 set the default timeout */
625 int ldb_set_timeout(struct ldb_context *ldb,
626 struct ldb_request *req,
629 if (req == NULL) return LDB_ERR_OPERATIONS_ERROR;
632 req->timeout = timeout;
634 req->timeout = ldb->default_timeout;
636 req->starttime = time(NULL);
641 /* calculates the new timeout based on the previous starttime and timeout */
642 int ldb_set_timeout_from_prev_req(struct ldb_context *ldb,
643 struct ldb_request *oldreq,
644 struct ldb_request *newreq)
646 if (newreq == NULL) return LDB_ERR_OPERATIONS_ERROR;
648 if (oldreq == NULL) {
649 return ldb_set_timeout(ldb, newreq, 0);
652 newreq->starttime = oldreq->starttime;
653 newreq->timeout = oldreq->timeout;
660 set the permissions for new files to be passed to open() in
661 backends that use local files
663 void ldb_set_create_perms(struct ldb_context *ldb, unsigned int perms)
665 ldb->create_perms = perms;
668 unsigned int ldb_get_create_perms(struct ldb_context *ldb)
670 return ldb->create_perms;
673 void ldb_set_event_context(struct ldb_context *ldb, struct tevent_context *ev)
678 struct tevent_context * ldb_get_event_context(struct ldb_context *ldb)
683 void ldb_request_set_state(struct ldb_request *req, int state)
685 req->handle->state = state;
688 int ldb_request_get_status(struct ldb_request *req)
690 return req->handle->status;
697 static void ldb_trace_request(struct ldb_context *ldb, struct ldb_request *req)
699 TALLOC_CTX *tmp_ctx = talloc_new(req);
702 switch (req->operation) {
704 ldb_debug_add(ldb, "ldb_trace_request: SEARCH\n");
705 ldb_debug_add(ldb, " dn: %s\n",
706 ldb_dn_is_null(req->op.search.base)?"<rootDSE>":
707 ldb_dn_get_linearized(req->op.search.base));
708 ldb_debug_add(ldb, " scope: %s\n",
709 req->op.search.scope==LDB_SCOPE_BASE?"base":
710 req->op.search.scope==LDB_SCOPE_ONELEVEL?"one":
711 req->op.search.scope==LDB_SCOPE_SUBTREE?"sub":"UNKNOWN");
712 ldb_debug_add(ldb, " expr: %s\n",
713 ldb_filter_from_tree(tmp_ctx, req->op.search.tree));
714 if (req->op.search.attrs == NULL) {
715 ldb_debug_add(ldb, " attr: <ALL>\n");
717 for (i=0; req->op.search.attrs[i]; i++) {
718 ldb_debug_add(ldb, " attr: %s\n", req->op.search.attrs[i]);
723 ldb_debug_add(ldb, "ldb_trace_request: DELETE\n");
724 ldb_debug_add(ldb, " dn: %s\n",
725 ldb_dn_get_linearized(req->op.del.dn));
728 ldb_debug_add(ldb, "ldb_trace_request: RENAME\n");
729 ldb_debug_add(ldb, " olddn: %s\n",
730 ldb_dn_get_linearized(req->op.rename.olddn));
731 ldb_debug_add(ldb, " newdn: %s\n",
732 ldb_dn_get_linearized(req->op.rename.newdn));
735 ldb_debug_add(ldb, "ldb_trace_request: EXTENDED\n");
736 ldb_debug_add(ldb, " oid: %s\n", req->op.extended.oid);
737 ldb_debug_add(ldb, " data: %s\n", req->op.extended.data?"yes":"no");
740 ldb_debug_add(ldb, "ldb_trace_request: ADD\n");
741 ldb_debug_add(req->handle->ldb, "%s\n",
742 ldb_ldif_message_string(req->handle->ldb, tmp_ctx,
744 req->op.add.message));
747 ldb_debug_add(ldb, "ldb_trace_request: MODIFY\n");
748 ldb_debug_add(req->handle->ldb, "%s\n",
749 ldb_ldif_message_string(req->handle->ldb, tmp_ctx,
751 req->op.mod.message));
753 case LDB_REQ_REGISTER_CONTROL:
754 ldb_debug_add(ldb, "ldb_trace_request: REGISTER_CONTROL\n");
755 ldb_debug_add(req->handle->ldb, "%s\n",
756 req->op.reg_control.oid);
758 case LDB_REQ_REGISTER_PARTITION:
759 ldb_debug_add(ldb, "ldb_trace_request: REGISTER_PARTITION\n");
760 ldb_debug_add(req->handle->ldb, "%s\n",
761 ldb_dn_get_linearized(req->op.reg_partition.dn));
764 ldb_debug_add(ldb, "ldb_trace_request: UNKNOWN(%u)\n",
769 if (req->controls == NULL) {
770 ldb_debug_add(ldb, " control: <NONE>\n");
772 for (i=0; req->controls && req->controls[i]; i++) {
773 if (req->controls[i]->oid) {
774 ldb_debug_add(ldb, " control: %s crit:%u data:%s\n",
775 req->controls[i]->oid,
776 req->controls[i]->critical,
777 req->controls[i]->data?"yes":"no");
782 ldb_debug_end(ldb, LDB_DEBUG_TRACE);
784 talloc_free(tmp_ctx);
788 check that the element flags don't have any internal bits set
790 static int ldb_msg_check_element_flags(struct ldb_context *ldb,
791 const struct ldb_message *message)
794 for (i=0; i<message->num_elements; i++) {
795 if (message->elements[i].flags & LDB_FLAG_INTERNAL_MASK) {
796 ldb_asprintf_errstring(ldb, "Invalid element flags 0x%08x on element %s in %s\n",
797 message->elements[i].flags, message->elements[i].name,
798 ldb_dn_get_linearized(message->dn));
799 return LDB_ERR_UNSUPPORTED_CRITICAL_EXTENSION;
808 NOTE: the request must be a talloc context.
809 returns LDB_ERR_* on errors.
811 int ldb_request(struct ldb_context *ldb, struct ldb_request *req)
813 struct ldb_module *module;
816 if (req->callback == NULL) {
817 ldb_set_errstring(ldb, "Requests MUST define callbacks");
818 return LDB_ERR_UNWILLING_TO_PERFORM;
821 ldb_reset_err_string(ldb);
823 if (ldb->flags & LDB_FLG_ENABLE_TRACING) {
824 ldb_trace_request(ldb, req);
827 /* call the first module in the chain */
828 switch (req->operation) {
830 /* due to "ldb_build_search_req" base DN always != NULL */
831 if (!ldb_dn_validate(req->op.search.base)) {
832 ldb_asprintf_errstring(ldb, "ldb_search: invalid basedn '%s'",
833 ldb_dn_get_linearized(req->op.search.base));
834 return LDB_ERR_INVALID_DN_SYNTAX;
836 FIRST_OP(ldb, search);
837 ret = module->ops->search(module, req);
840 if (!ldb_dn_validate(req->op.add.message->dn)) {
841 ldb_asprintf_errstring(ldb, "ldb_add: invalid dn '%s'",
842 ldb_dn_get_linearized(req->op.add.message->dn));
843 return LDB_ERR_INVALID_DN_SYNTAX;
846 * we have to normalize here, as so many places
847 * in modules and backends assume we don't have two
848 * elements with the same name
850 ret = ldb_msg_normalize(ldb, req, req->op.add.message,
851 discard_const(&req->op.add.message));
852 if (ret != LDB_SUCCESS) {
854 return LDB_ERR_OPERATIONS_ERROR;
857 ret = ldb_msg_check_element_flags(ldb, req->op.add.message);
858 if (ret != LDB_SUCCESS) {
861 ret = module->ops->add(module, req);
864 if (!ldb_dn_validate(req->op.mod.message->dn)) {
865 ldb_asprintf_errstring(ldb, "ldb_modify: invalid dn '%s'",
866 ldb_dn_get_linearized(req->op.mod.message->dn));
867 return LDB_ERR_INVALID_DN_SYNTAX;
869 FIRST_OP(ldb, modify);
870 ret = ldb_msg_check_element_flags(ldb, req->op.mod.message);
871 if (ret != LDB_SUCCESS) {
874 ret = module->ops->modify(module, req);
877 if (!ldb_dn_validate(req->op.del.dn)) {
878 ldb_asprintf_errstring(ldb, "ldb_delete: invalid dn '%s'",
879 ldb_dn_get_linearized(req->op.del.dn));
880 return LDB_ERR_INVALID_DN_SYNTAX;
883 ret = module->ops->del(module, req);
886 if (!ldb_dn_validate(req->op.rename.olddn)) {
887 ldb_asprintf_errstring(ldb, "ldb_rename: invalid olddn '%s'",
888 ldb_dn_get_linearized(req->op.rename.olddn));
889 return LDB_ERR_INVALID_DN_SYNTAX;
891 if (!ldb_dn_validate(req->op.rename.newdn)) {
892 ldb_asprintf_errstring(ldb, "ldb_rename: invalid newdn '%s'",
893 ldb_dn_get_linearized(req->op.rename.newdn));
894 return LDB_ERR_INVALID_DN_SYNTAX;
896 FIRST_OP(ldb, rename);
897 ret = module->ops->rename(module, req);
900 FIRST_OP(ldb, extended);
901 ret = module->ops->extended(module, req);
904 FIRST_OP(ldb, request);
905 ret = module->ops->request(module, req);
912 int ldb_request_done(struct ldb_request *req, int status)
914 req->handle->state = LDB_ASYNC_DONE;
915 req->handle->status = status;
920 search the database given a LDAP-like search expression
922 returns an LDB error code
924 Use talloc_free to free the ldb_message returned in 'res', if successful
927 int ldb_search_default_callback(struct ldb_request *req,
928 struct ldb_reply *ares)
930 struct ldb_result *res;
933 res = talloc_get_type(req->context, struct ldb_result);
936 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
938 if (ares->error != LDB_SUCCESS) {
939 return ldb_request_done(req, ares->error);
942 switch (ares->type) {
943 case LDB_REPLY_ENTRY:
944 res->msgs = talloc_realloc(res, res->msgs,
945 struct ldb_message *, res->count + 2);
947 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
950 res->msgs[res->count + 1] = NULL;
952 res->msgs[res->count] = talloc_move(res->msgs, &ares->message);
956 case LDB_REPLY_REFERRAL:
958 for (n = 0; res->refs[n]; n++) /*noop*/ ;
963 res->refs = talloc_realloc(res, res->refs, char *, n + 2);
965 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
968 res->refs[n] = talloc_move(res->refs, &ares->referral);
969 res->refs[n + 1] = NULL;
973 /* TODO: we should really support controls on entries
974 * and referrals too! */
975 res->controls = talloc_move(res, &ares->controls);
977 /* this is the last message, and means the request is done */
978 /* we have to signal and eventual ldb_wait() waiting that the
979 * async request operation was completed */
981 return ldb_request_done(req, LDB_SUCCESS);
989 int ldb_modify_default_callback(struct ldb_request *req, struct ldb_reply *ares)
991 struct ldb_result *res;
995 res = talloc_get_type(req->context, struct ldb_result);
998 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1001 if (ares->error != LDB_SUCCESS) {
1004 return ldb_request_done(req, ret);
1007 switch (ares->type) {
1008 case LDB_REPLY_REFERRAL:
1010 for (n = 0; res->refs[n]; n++) /*noop*/ ;
1015 res->refs = talloc_realloc(res, res->refs, char *, n + 2);
1017 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1020 res->refs[n] = talloc_move(res->refs, &ares->referral);
1021 res->refs[n + 1] = NULL;
1024 case LDB_REPLY_DONE:
1026 return ldb_request_done(req, LDB_SUCCESS);
1029 ldb_set_errstring(req->handle->ldb, "Invalid reply type!");
1030 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1034 return ldb_request_done(req, LDB_SUCCESS);
1037 int ldb_op_default_callback(struct ldb_request *req, struct ldb_reply *ares)
1042 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1045 if (ares->error != LDB_SUCCESS) {
1048 return ldb_request_done(req, ret);
1051 if (ares->type != LDB_REPLY_DONE) {
1053 ldb_set_errstring(req->handle->ldb, "Invalid reply type!");
1054 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1058 return ldb_request_done(req, LDB_SUCCESS);
1061 int ldb_build_search_req_ex(struct ldb_request **ret_req,
1062 struct ldb_context *ldb,
1063 TALLOC_CTX *mem_ctx,
1064 struct ldb_dn *base,
1065 enum ldb_scope scope,
1066 struct ldb_parse_tree *tree,
1067 const char * const *attrs,
1068 struct ldb_control **controls,
1070 ldb_request_callback_t callback,
1071 struct ldb_request *parent)
1073 struct ldb_request *req;
1077 req = talloc(mem_ctx, struct ldb_request);
1080 return LDB_ERR_OPERATIONS_ERROR;
1083 req->operation = LDB_SEARCH;
1085 req->op.search.base = ldb_dn_new(req, ldb, NULL);
1087 req->op.search.base = base;
1089 req->op.search.scope = scope;
1091 req->op.search.tree = tree;
1092 if (req->op.search.tree == NULL) {
1093 ldb_set_errstring(ldb, "'tree' can't be NULL");
1095 return LDB_ERR_OPERATIONS_ERROR;
1098 req->op.search.attrs = attrs;
1099 req->controls = controls;
1100 req->context = context;
1101 req->callback = callback;
1103 ldb_set_timeout_from_prev_req(ldb, parent, req);
1105 req->handle = ldb_handle_new(req, ldb);
1106 if (req->handle == NULL) {
1108 return LDB_ERR_OPERATIONS_ERROR;
1112 req->handle->nesting++;
1113 req->handle->parent = parent;
1114 req->handle->flags = parent->handle->flags;
1115 req->handle->custom_flags = parent->handle->custom_flags;
1122 int ldb_build_search_req(struct ldb_request **ret_req,
1123 struct ldb_context *ldb,
1124 TALLOC_CTX *mem_ctx,
1125 struct ldb_dn *base,
1126 enum ldb_scope scope,
1127 const char *expression,
1128 const char * const *attrs,
1129 struct ldb_control **controls,
1131 ldb_request_callback_t callback,
1132 struct ldb_request *parent)
1134 struct ldb_parse_tree *tree;
1137 tree = ldb_parse_tree(mem_ctx, expression);
1139 ldb_set_errstring(ldb, "Unable to parse search expression");
1140 return LDB_ERR_OPERATIONS_ERROR;
1143 ret = ldb_build_search_req_ex(ret_req, ldb, mem_ctx, base,
1144 scope, tree, attrs, controls,
1145 context, callback, parent);
1146 if (ret == LDB_SUCCESS) {
1147 talloc_steal(*ret_req, tree);
1152 int ldb_build_add_req(struct ldb_request **ret_req,
1153 struct ldb_context *ldb,
1154 TALLOC_CTX *mem_ctx,
1155 const struct ldb_message *message,
1156 struct ldb_control **controls,
1158 ldb_request_callback_t callback,
1159 struct ldb_request *parent)
1161 struct ldb_request *req;
1165 req = talloc(mem_ctx, struct ldb_request);
1167 ldb_set_errstring(ldb, "Out of Memory");
1168 return LDB_ERR_OPERATIONS_ERROR;
1171 req->operation = LDB_ADD;
1172 req->op.add.message = message;
1173 req->controls = controls;
1174 req->context = context;
1175 req->callback = callback;
1177 ldb_set_timeout_from_prev_req(ldb, parent, req);
1179 req->handle = ldb_handle_new(req, ldb);
1180 if (req->handle == NULL) {
1182 return LDB_ERR_OPERATIONS_ERROR;
1186 req->handle->nesting++;
1187 req->handle->parent = parent;
1188 req->handle->flags = parent->handle->flags;
1189 req->handle->custom_flags = parent->handle->custom_flags;
1197 int ldb_build_mod_req(struct ldb_request **ret_req,
1198 struct ldb_context *ldb,
1199 TALLOC_CTX *mem_ctx,
1200 const struct ldb_message *message,
1201 struct ldb_control **controls,
1203 ldb_request_callback_t callback,
1204 struct ldb_request *parent)
1206 struct ldb_request *req;
1210 req = talloc(mem_ctx, struct ldb_request);
1212 ldb_set_errstring(ldb, "Out of Memory");
1213 return LDB_ERR_OPERATIONS_ERROR;
1216 req->operation = LDB_MODIFY;
1217 req->op.mod.message = message;
1218 req->controls = controls;
1219 req->context = context;
1220 req->callback = callback;
1222 ldb_set_timeout_from_prev_req(ldb, parent, req);
1224 req->handle = ldb_handle_new(req, ldb);
1225 if (req->handle == NULL) {
1227 return LDB_ERR_OPERATIONS_ERROR;
1231 req->handle->nesting++;
1232 req->handle->parent = parent;
1233 req->handle->flags = parent->handle->flags;
1234 req->handle->custom_flags = parent->handle->custom_flags;
1242 int ldb_build_del_req(struct ldb_request **ret_req,
1243 struct ldb_context *ldb,
1244 TALLOC_CTX *mem_ctx,
1246 struct ldb_control **controls,
1248 ldb_request_callback_t callback,
1249 struct ldb_request *parent)
1251 struct ldb_request *req;
1255 req = talloc(mem_ctx, struct ldb_request);
1257 ldb_set_errstring(ldb, "Out of Memory");
1258 return LDB_ERR_OPERATIONS_ERROR;
1261 req->operation = LDB_DELETE;
1262 req->op.del.dn = dn;
1263 req->controls = controls;
1264 req->context = context;
1265 req->callback = callback;
1267 ldb_set_timeout_from_prev_req(ldb, parent, req);
1269 req->handle = ldb_handle_new(req, ldb);
1270 if (req->handle == NULL) {
1272 return LDB_ERR_OPERATIONS_ERROR;
1276 req->handle->nesting++;
1277 req->handle->parent = parent;
1278 req->handle->flags = parent->handle->flags;
1279 req->handle->custom_flags = parent->handle->custom_flags;
1287 int ldb_build_rename_req(struct ldb_request **ret_req,
1288 struct ldb_context *ldb,
1289 TALLOC_CTX *mem_ctx,
1290 struct ldb_dn *olddn,
1291 struct ldb_dn *newdn,
1292 struct ldb_control **controls,
1294 ldb_request_callback_t callback,
1295 struct ldb_request *parent)
1297 struct ldb_request *req;
1301 req = talloc(mem_ctx, struct ldb_request);
1303 ldb_set_errstring(ldb, "Out of Memory");
1304 return LDB_ERR_OPERATIONS_ERROR;
1307 req->operation = LDB_RENAME;
1308 req->op.rename.olddn = olddn;
1309 req->op.rename.newdn = newdn;
1310 req->controls = controls;
1311 req->context = context;
1312 req->callback = callback;
1314 ldb_set_timeout_from_prev_req(ldb, parent, req);
1316 req->handle = ldb_handle_new(req, ldb);
1317 if (req->handle == NULL) {
1319 return LDB_ERR_OPERATIONS_ERROR;
1323 req->handle->nesting++;
1324 req->handle->parent = parent;
1325 req->handle->flags = parent->handle->flags;
1326 req->handle->custom_flags = parent->handle->custom_flags;
1334 int ldb_extended_default_callback(struct ldb_request *req,
1335 struct ldb_reply *ares)
1337 struct ldb_result *res;
1339 res = talloc_get_type(req->context, struct ldb_result);
1342 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1344 if (ares->error != LDB_SUCCESS) {
1345 return ldb_request_done(req, ares->error);
1348 if (ares->type == LDB_REPLY_DONE) {
1350 /* TODO: we should really support controls on entries and referrals too! */
1351 res->extended = talloc_move(res, &ares->response);
1352 res->controls = talloc_move(res, &ares->controls);
1355 return ldb_request_done(req, LDB_SUCCESS);
1359 ldb_set_errstring(req->handle->ldb, "Invalid reply type!");
1360 return ldb_request_done(req, LDB_ERR_OPERATIONS_ERROR);
1363 int ldb_build_extended_req(struct ldb_request **ret_req,
1364 struct ldb_context *ldb,
1365 TALLOC_CTX *mem_ctx,
1368 struct ldb_control **controls,
1370 ldb_request_callback_t callback,
1371 struct ldb_request *parent)
1373 struct ldb_request *req;
1377 req = talloc(mem_ctx, struct ldb_request);
1379 ldb_set_errstring(ldb, "Out of Memory");
1380 return LDB_ERR_OPERATIONS_ERROR;
1383 req->operation = LDB_EXTENDED;
1384 req->op.extended.oid = oid;
1385 req->op.extended.data = data;
1386 req->controls = controls;
1387 req->context = context;
1388 req->callback = callback;
1390 ldb_set_timeout_from_prev_req(ldb, parent, req);
1392 req->handle = ldb_handle_new(req, ldb);
1393 if (req->handle == NULL) {
1395 return LDB_ERR_OPERATIONS_ERROR;
1399 req->handle->nesting++;
1400 req->handle->parent = parent;
1401 req->handle->flags = parent->handle->flags;
1402 req->handle->custom_flags = parent->handle->custom_flags;
1410 int ldb_extended(struct ldb_context *ldb,
1413 struct ldb_result **_res)
1415 struct ldb_request *req;
1417 struct ldb_result *res;
1421 res = talloc_zero(ldb, struct ldb_result);
1423 return LDB_ERR_OPERATIONS_ERROR;
1426 ret = ldb_build_extended_req(&req, ldb, ldb,
1428 res, ldb_extended_default_callback,
1430 if (ret != LDB_SUCCESS) goto done;
1432 ldb_set_timeout(ldb, req, 0); /* use default timeout */
1434 ret = ldb_request(ldb, req);
1436 if (ret == LDB_SUCCESS) {
1437 ret = ldb_wait(req->handle, LDB_WAIT_ALL);
1443 if (ret != LDB_SUCCESS) {
1452 note that ldb_search() will automatically replace a NULL 'base' value
1453 with the defaultNamingContext from the rootDSE if available.
1455 int ldb_search(struct ldb_context *ldb, TALLOC_CTX *mem_ctx,
1456 struct ldb_result **result, struct ldb_dn *base,
1457 enum ldb_scope scope, const char * const *attrs,
1458 const char *exp_fmt, ...)
1460 struct ldb_request *req;
1461 struct ldb_result *res;
1470 res = talloc_zero(mem_ctx, struct ldb_result);
1472 return LDB_ERR_OPERATIONS_ERROR;
1476 va_start(ap, exp_fmt);
1477 expression = talloc_vasprintf(mem_ctx, exp_fmt, ap);
1482 return LDB_ERR_OPERATIONS_ERROR;
1486 ret = ldb_build_search_req(&req, ldb, mem_ctx,
1487 base?base:ldb_get_default_basedn(ldb),
1493 ldb_search_default_callback,
1495 ldb_req_set_location(req, "ldb_search");
1497 if (ret != LDB_SUCCESS) goto done;
1499 ret = ldb_request(ldb, req);
1501 if (ret == LDB_SUCCESS) {
1502 ret = ldb_wait(req->handle, LDB_WAIT_ALL);
1506 if (ret != LDB_SUCCESS) {
1511 talloc_free(expression);
1519 add a record to the database. Will fail if a record with the given class
1520 and key already exists
1522 int ldb_add(struct ldb_context *ldb,
1523 const struct ldb_message *message)
1525 struct ldb_request *req;
1528 ret = ldb_msg_sanity_check(ldb, message);
1529 if (ret != LDB_SUCCESS) {
1533 ret = ldb_build_add_req(&req, ldb, ldb,
1537 ldb_op_default_callback,
1539 ldb_req_set_location(req, "ldb_add");
1541 if (ret != LDB_SUCCESS) return ret;
1543 /* do request and autostart a transaction */
1544 ret = ldb_autotransaction_request(ldb, req);
1551 modify the specified attributes of a record
1553 int ldb_modify(struct ldb_context *ldb,
1554 const struct ldb_message *message)
1556 struct ldb_request *req;
1559 ret = ldb_msg_sanity_check(ldb, message);
1560 if (ret != LDB_SUCCESS) {
1564 ret = ldb_build_mod_req(&req, ldb, ldb,
1568 ldb_op_default_callback,
1570 ldb_req_set_location(req, "ldb_modify");
1572 if (ret != LDB_SUCCESS) return ret;
1574 /* do request and autostart a transaction */
1575 ret = ldb_autotransaction_request(ldb, req);
1583 delete a record from the database
1585 int ldb_delete(struct ldb_context *ldb, struct ldb_dn *dn)
1587 struct ldb_request *req;
1590 ret = ldb_build_del_req(&req, ldb, ldb,
1594 ldb_op_default_callback,
1596 ldb_req_set_location(req, "ldb_delete");
1598 if (ret != LDB_SUCCESS) return ret;
1600 /* do request and autostart a transaction */
1601 ret = ldb_autotransaction_request(ldb, req);
1608 rename a record in the database
1610 int ldb_rename(struct ldb_context *ldb,
1611 struct ldb_dn *olddn, struct ldb_dn *newdn)
1613 struct ldb_request *req;
1616 ret = ldb_build_rename_req(&req, ldb, ldb,
1621 ldb_op_default_callback,
1623 ldb_req_set_location(req, "ldb_rename");
1625 if (ret != LDB_SUCCESS) return ret;
1627 /* do request and autostart a transaction */
1628 ret = ldb_autotransaction_request(ldb, req);
1636 return the global sequence number
1638 int ldb_sequence_number(struct ldb_context *ldb,
1639 enum ldb_sequence_type type, uint64_t *seq_num)
1641 struct ldb_seqnum_request *seq;
1642 struct ldb_seqnum_result *seqr;
1643 struct ldb_result *res;
1644 TALLOC_CTX *tmp_ctx;
1649 tmp_ctx = talloc_zero(ldb, struct ldb_request);
1650 if (tmp_ctx == NULL) {
1651 ldb_set_errstring(ldb, "Out of Memory");
1652 return LDB_ERR_OPERATIONS_ERROR;
1654 seq = talloc_zero(tmp_ctx, struct ldb_seqnum_request);
1656 ldb_set_errstring(ldb, "Out of Memory");
1657 ret = LDB_ERR_OPERATIONS_ERROR;
1662 ret = ldb_extended(ldb, LDB_EXTENDED_SEQUENCE_NUMBER, seq, &res);
1663 if (ret != LDB_SUCCESS) {
1666 talloc_steal(tmp_ctx, res);
1668 if (strcmp(LDB_EXTENDED_SEQUENCE_NUMBER, res->extended->oid) != 0) {
1669 ldb_set_errstring(ldb, "Invalid OID in reply");
1670 ret = LDB_ERR_OPERATIONS_ERROR;
1673 seqr = talloc_get_type(res->extended->data,
1674 struct ldb_seqnum_result);
1675 *seq_num = seqr->seq_num;
1678 talloc_free(tmp_ctx);
1683 return extended error information
1685 const char *ldb_errstring(struct ldb_context *ldb)
1687 if (ldb->err_string) {
1688 return ldb->err_string;
1695 return a string explaining what a ldb error constant meancs
1697 const char *ldb_strerror(int ldb_err)
1702 case LDB_ERR_OPERATIONS_ERROR:
1703 return "Operations error";
1704 case LDB_ERR_PROTOCOL_ERROR:
1705 return "Protocol error";
1706 case LDB_ERR_TIME_LIMIT_EXCEEDED:
1707 return "Time limit exceeded";
1708 case LDB_ERR_SIZE_LIMIT_EXCEEDED:
1709 return "Size limit exceeded";
1710 case LDB_ERR_COMPARE_FALSE:
1711 return "Compare false";
1712 case LDB_ERR_COMPARE_TRUE:
1713 return "Compare true";
1714 case LDB_ERR_AUTH_METHOD_NOT_SUPPORTED:
1715 return "Auth method not supported";
1716 case LDB_ERR_STRONG_AUTH_REQUIRED:
1717 return "Strong auth required";
1719 case LDB_ERR_REFERRAL:
1720 return "Referral error";
1721 case LDB_ERR_ADMIN_LIMIT_EXCEEDED:
1722 return "Admin limit exceeded";
1723 case LDB_ERR_UNSUPPORTED_CRITICAL_EXTENSION:
1724 return "Unsupported critical extension";
1725 case LDB_ERR_CONFIDENTIALITY_REQUIRED:
1726 return "Confidentiality required";
1727 case LDB_ERR_SASL_BIND_IN_PROGRESS:
1728 return "SASL bind in progress";
1729 case LDB_ERR_NO_SUCH_ATTRIBUTE:
1730 return "No such attribute";
1731 case LDB_ERR_UNDEFINED_ATTRIBUTE_TYPE:
1732 return "Undefined attribute type";
1733 case LDB_ERR_INAPPROPRIATE_MATCHING:
1734 return "Inappropriate matching";
1735 case LDB_ERR_CONSTRAINT_VIOLATION:
1736 return "Constraint violation";
1737 case LDB_ERR_ATTRIBUTE_OR_VALUE_EXISTS:
1738 return "Attribute or value exists";
1739 case LDB_ERR_INVALID_ATTRIBUTE_SYNTAX:
1740 return "Invalid attribute syntax";
1742 case LDB_ERR_NO_SUCH_OBJECT:
1743 return "No such object";
1744 case LDB_ERR_ALIAS_PROBLEM:
1745 return "Alias problem";
1746 case LDB_ERR_INVALID_DN_SYNTAX:
1747 return "Invalid DN syntax";
1749 case LDB_ERR_ALIAS_DEREFERENCING_PROBLEM:
1750 return "Alias dereferencing problem";
1752 case LDB_ERR_INAPPROPRIATE_AUTHENTICATION:
1753 return "Inappropriate authentication";
1754 case LDB_ERR_INVALID_CREDENTIALS:
1755 return "Invalid credentials";
1756 case LDB_ERR_INSUFFICIENT_ACCESS_RIGHTS:
1757 return "insufficient access rights";
1760 case LDB_ERR_UNAVAILABLE:
1761 return "Unavailable";
1762 case LDB_ERR_UNWILLING_TO_PERFORM:
1763 return "Unwilling to perform";
1764 case LDB_ERR_LOOP_DETECT:
1765 return "Loop detect";
1767 case LDB_ERR_NAMING_VIOLATION:
1768 return "Naming violation";
1769 case LDB_ERR_OBJECT_CLASS_VIOLATION:
1770 return "Object class violation";
1771 case LDB_ERR_NOT_ALLOWED_ON_NON_LEAF:
1772 return "Not allowed on non-leaf";
1773 case LDB_ERR_NOT_ALLOWED_ON_RDN:
1774 return "Not allowed on RDN";
1775 case LDB_ERR_ENTRY_ALREADY_EXISTS:
1776 return "Entry already exists";
1777 case LDB_ERR_OBJECT_CLASS_MODS_PROHIBITED:
1778 return "Object class mods prohibited";
1779 /* 70 RESERVED FOR CLDAP */
1780 case LDB_ERR_AFFECTS_MULTIPLE_DSAS:
1781 return "Affects multiple DSAs";
1787 return "Unknown error";
1791 set backend specific opaque parameters
1793 int ldb_set_opaque(struct ldb_context *ldb, const char *name, void *value)
1795 struct ldb_opaque *o;
1797 /* allow updating an existing value */
1798 for (o=ldb->opaque;o;o=o->next) {
1799 if (strcmp(o->name, name) == 0) {
1805 o = talloc(ldb, struct ldb_opaque);
1808 return LDB_ERR_OTHER;
1810 o->next = ldb->opaque;
1818 get a previously set opaque value
1820 void *ldb_get_opaque(struct ldb_context *ldb, const char *name)
1822 struct ldb_opaque *o;
1823 for (o=ldb->opaque;o;o=o->next) {
1824 if (strcmp(o->name, name) == 0) {
1831 int ldb_global_init(void)
1833 /* Provided for compatibility with some older versions of ldb */
1837 /* return the ldb flags */
1838 unsigned int ldb_get_flags(struct ldb_context *ldb)
1843 /* set the ldb flags */
1844 void ldb_set_flags(struct ldb_context *ldb, unsigned flags)
1851 set the location in a ldb request. Used for debugging
1853 void ldb_req_set_location(struct ldb_request *req, const char *location)
1855 if (req && req->handle) {
1856 req->handle->location = location;
1861 return the location set with dsdb_req_set_location
1863 const char *ldb_req_location(struct ldb_request *req)
1865 return req->handle->location;
1869 mark a request as untrusted. This tells the rootdse module to remove
1870 unregistered controls
1872 void ldb_req_mark_untrusted(struct ldb_request *req)
1874 req->handle->flags |= LDB_HANDLE_FLAG_UNTRUSTED;
1878 mark a request as trusted.
1880 void ldb_req_mark_trusted(struct ldb_request *req)
1882 req->handle->flags &= ~LDB_HANDLE_FLAG_UNTRUSTED;
1886 set custom flags. Those flags are set by applications using ldb,
1887 they are application dependent and the same bit can have different
1888 meaning in different application.
1890 void ldb_req_set_custom_flags(struct ldb_request *req, uint32_t flags)
1892 if (req != NULL && req->handle != NULL) {
1893 req->handle->custom_flags = flags;
1899 get custom flags. Those flags are set by applications using ldb,
1900 they are application dependent and the same bit can have different
1901 meaning in different application.
1903 uint32_t ldb_req_get_custom_flags(struct ldb_request *req)
1905 if (req != NULL && req->handle != NULL) {
1906 return req->handle->custom_flags;
1910 * 0 is not something any better or worse than
1911 * anything else as req or the handle is NULL
1918 return true is a request is untrusted
1920 bool ldb_req_is_untrusted(struct ldb_request *req)
1922 return (req->handle->flags & LDB_HANDLE_FLAG_UNTRUSTED) != 0;