Line data Source code
1 : /*
2 : ldb database library
3 :
4 : Copyright (C) Stefan Metzmacher <metze@samba.org> 2009
5 :
6 : This program is free software; you can redistribute it and/or modify
7 : it under the terms of the GNU General Public License as published by
8 : the Free Software Foundation; either version 3 of the License, or
9 : (at your option) any later version.
10 :
11 : This program is distributed in the hope that it will be useful,
12 : but WITHOUT ANY WARRANTY; without even the implied warranty of
13 : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 : GNU General Public License for more details.
15 :
16 : You should have received a copy of the GNU General Public License
17 : along with this program. If not, see <http://www.gnu.org/licenses/>.
18 : */
19 :
20 : #include "includes.h"
21 : #include "ldb_module.h"
22 : #include "dsdb/samdb/samdb.h"
23 :
24 4999951 : static int resolve_oids_need_value(struct ldb_context *ldb,
25 : struct dsdb_schema *schema,
26 : const struct dsdb_attribute *a,
27 : const struct ldb_val *valp)
28 : {
29 4999951 : const struct dsdb_attribute *va = NULL;
30 4999951 : const struct dsdb_class *vo = NULL;
31 : const void *p2;
32 4999951 : char *str = NULL;
33 :
34 4999951 : if (a->syntax->oMSyntax != 6) {
35 3933166 : return LDB_ERR_COMPARE_FALSE;
36 : }
37 :
38 1066785 : if (valp) {
39 1066785 : p2 = memchr(valp->data, '.', valp->length);
40 : } else {
41 0 : p2 = NULL;
42 : }
43 :
44 1066785 : if (!p2) {
45 828666 : return LDB_ERR_COMPARE_FALSE;
46 : }
47 :
48 238119 : switch (a->attributeID_id) {
49 11 : case DRSUAPI_ATTID_objectClass:
50 : case DRSUAPI_ATTID_subClassOf:
51 : case DRSUAPI_ATTID_auxiliaryClass:
52 : case DRSUAPI_ATTID_systemPossSuperiors:
53 : case DRSUAPI_ATTID_possSuperiors:
54 11 : str = talloc_strndup(ldb, (char *)valp->data, valp->length);
55 11 : if (!str) {
56 0 : return ldb_oom(ldb);
57 : }
58 11 : vo = dsdb_class_by_governsID_oid(schema, str);
59 11 : talloc_free(str);
60 11 : if (!vo) {
61 0 : return LDB_ERR_COMPARE_FALSE;
62 : }
63 11 : return LDB_ERR_COMPARE_TRUE;
64 172 : case DRSUAPI_ATTID_systemMustContain:
65 : case DRSUAPI_ATTID_systemMayContain:
66 : case DRSUAPI_ATTID_mustContain:
67 : case DRSUAPI_ATTID_mayContain:
68 172 : str = talloc_strndup(ldb, (char *)valp->data, valp->length);
69 172 : if (!str) {
70 0 : return ldb_oom(ldb);
71 : }
72 172 : va = dsdb_attribute_by_attributeID_oid(schema, str);
73 172 : talloc_free(str);
74 172 : if (!va) {
75 96 : return LDB_ERR_COMPARE_FALSE;
76 : }
77 76 : return LDB_ERR_COMPARE_TRUE;
78 237936 : case DRSUAPI_ATTID_governsID:
79 : case DRSUAPI_ATTID_attributeID:
80 : case DRSUAPI_ATTID_attributeSyntax:
81 237936 : return LDB_ERR_COMPARE_FALSE;
82 : }
83 :
84 0 : return LDB_ERR_COMPARE_FALSE;
85 : }
86 :
87 33119349 : static int resolve_oids_parse_tree_need(struct ldb_context *ldb,
88 : struct dsdb_schema *schema,
89 : const struct ldb_parse_tree *tree)
90 : {
91 : unsigned int i;
92 33119349 : const struct dsdb_attribute *a = NULL;
93 : const char *attr;
94 : const char *p1;
95 : const void *p2;
96 33119349 : const struct ldb_val *valp = NULL;
97 : int ret;
98 :
99 33119349 : switch (tree->operation) {
100 10367527 : case LDB_OP_AND:
101 : case LDB_OP_OR:
102 31871626 : for (i=0;i<tree->u.list.num_elements;i++) {
103 21504099 : ret = resolve_oids_parse_tree_need(ldb, schema,
104 21504099 : tree->u.list.elements[i]);
105 21504099 : if (ret != LDB_ERR_COMPARE_FALSE) {
106 0 : return ret;
107 : }
108 : }
109 10367527 : return LDB_ERR_COMPARE_FALSE;
110 519968 : case LDB_OP_NOT:
111 519968 : return resolve_oids_parse_tree_need(ldb, schema,
112 519968 : tree->u.isnot.child);
113 2712899 : case LDB_OP_EQUALITY:
114 : case LDB_OP_GREATER:
115 : case LDB_OP_LESS:
116 : case LDB_OP_APPROX:
117 2712899 : attr = tree->u.equality.attr;
118 2712899 : valp = &tree->u.equality.value;
119 2712899 : break;
120 15415 : case LDB_OP_SUBSTRING:
121 15415 : attr = tree->u.substring.attr;
122 15415 : break;
123 18329442 : case LDB_OP_PRESENT:
124 18329442 : attr = tree->u.present.attr;
125 18329442 : break;
126 1174098 : case LDB_OP_EXTENDED:
127 1174098 : attr = tree->u.extended.attr;
128 1174098 : valp = &tree->u.extended.value;
129 1174098 : break;
130 0 : default:
131 0 : return LDB_ERR_COMPARE_FALSE;
132 : }
133 :
134 22231854 : p1 = strchr(attr, '.');
135 :
136 22231854 : if (valp) {
137 3886997 : p2 = memchr(valp->data, '.', valp->length);
138 : } else {
139 18344857 : p2 = NULL;
140 : }
141 :
142 22231854 : if (!p1 && !p2) {
143 21865133 : return LDB_ERR_COMPARE_FALSE;
144 : }
145 :
146 366721 : if (p1) {
147 11 : a = dsdb_attribute_by_attributeID_oid(schema, attr);
148 : } else {
149 366710 : a = dsdb_attribute_by_lDAPDisplayName(schema, attr);
150 : }
151 366721 : if (!a) {
152 1157 : return LDB_ERR_COMPARE_FALSE;
153 : }
154 :
155 365564 : if (!p2) {
156 0 : return LDB_ERR_COMPARE_FALSE;
157 : }
158 :
159 365564 : return resolve_oids_need_value(ldb, schema, a, valp);
160 : }
161 :
162 3281088 : static int resolve_oids_element_need(struct ldb_context *ldb,
163 : struct dsdb_schema *schema,
164 : const struct ldb_message_element *el)
165 : {
166 : unsigned int i;
167 3281088 : const struct dsdb_attribute *a = NULL;
168 : const char *p1;
169 :
170 3281088 : p1 = strchr(el->name, '.');
171 :
172 3281088 : if (p1) {
173 0 : a = dsdb_attribute_by_attributeID_oid(schema, el->name);
174 : } else {
175 3281088 : a = dsdb_attribute_by_lDAPDisplayName(schema, el->name);
176 : }
177 3281088 : if (!a) {
178 2203 : return LDB_ERR_COMPARE_FALSE;
179 : }
180 :
181 7913196 : for (i=0; i < el->num_values; i++) {
182 : int ret;
183 4634387 : ret = resolve_oids_need_value(ldb, schema, a,
184 4634387 : &el->values[i]);
185 4634387 : if (ret != LDB_ERR_COMPARE_FALSE) {
186 76 : return ret;
187 : }
188 : }
189 :
190 3278809 : return LDB_ERR_COMPARE_FALSE;
191 : }
192 :
193 563202 : static int resolve_oids_message_need(struct ldb_context *ldb,
194 : struct dsdb_schema *schema,
195 : const struct ldb_message *msg)
196 : {
197 : unsigned int i;
198 :
199 3844214 : for (i=0; i < msg->num_elements; i++) {
200 : int ret;
201 3281088 : ret = resolve_oids_element_need(ldb, schema,
202 3281088 : &msg->elements[i]);
203 3281088 : if (ret != LDB_ERR_COMPARE_FALSE) {
204 76 : return ret;
205 : }
206 : }
207 :
208 563126 : return LDB_ERR_COMPARE_FALSE;
209 : }
210 :
211 1019 : static int resolve_oids_replace_value(struct ldb_context *ldb,
212 : struct dsdb_schema *schema,
213 : const struct dsdb_attribute *a,
214 : struct ldb_val *valp)
215 : {
216 1019 : const struct dsdb_attribute *va = NULL;
217 1019 : const struct dsdb_class *vo = NULL;
218 : const void *p2;
219 1019 : char *str = NULL;
220 :
221 1019 : if (a->syntax->oMSyntax != 6) {
222 440 : return LDB_SUCCESS;
223 : }
224 :
225 579 : if (valp) {
226 579 : p2 = memchr(valp->data, '.', valp->length);
227 : } else {
228 0 : p2 = NULL;
229 : }
230 :
231 579 : if (!p2) {
232 284 : return LDB_SUCCESS;
233 : }
234 :
235 295 : switch (a->attributeID_id) {
236 11 : case DRSUAPI_ATTID_objectClass:
237 : case DRSUAPI_ATTID_subClassOf:
238 : case DRSUAPI_ATTID_auxiliaryClass:
239 : case DRSUAPI_ATTID_systemPossSuperiors:
240 : case DRSUAPI_ATTID_possSuperiors:
241 11 : str = talloc_strndup(schema, (char *)valp->data, valp->length);
242 11 : if (!str) {
243 0 : return ldb_oom(ldb);
244 : }
245 11 : vo = dsdb_class_by_governsID_oid(schema, str);
246 11 : talloc_free(str);
247 11 : if (!vo) {
248 0 : return LDB_SUCCESS;
249 : }
250 11 : *valp = data_blob_string_const(vo->lDAPDisplayName);
251 11 : return LDB_SUCCESS;
252 244 : case DRSUAPI_ATTID_systemMustContain:
253 : case DRSUAPI_ATTID_systemMayContain:
254 : case DRSUAPI_ATTID_mustContain:
255 : case DRSUAPI_ATTID_mayContain:
256 244 : str = talloc_strndup(schema, (char *)valp->data, valp->length);
257 244 : if (!str) {
258 0 : return ldb_oom(ldb);
259 : }
260 244 : va = dsdb_attribute_by_attributeID_oid(schema, str);
261 244 : talloc_free(str);
262 244 : if (!va) {
263 0 : return LDB_SUCCESS;
264 : }
265 244 : *valp = data_blob_string_const(va->lDAPDisplayName);
266 244 : return LDB_SUCCESS;
267 40 : case DRSUAPI_ATTID_governsID:
268 : case DRSUAPI_ATTID_attributeID:
269 : case DRSUAPI_ATTID_attributeSyntax:
270 40 : return LDB_SUCCESS;
271 : }
272 :
273 0 : return LDB_SUCCESS;
274 : }
275 :
276 11 : static int resolve_oids_parse_tree_replace(struct ldb_context *ldb,
277 : struct dsdb_schema *schema,
278 : struct ldb_parse_tree *tree)
279 : {
280 : unsigned int i;
281 11 : const struct dsdb_attribute *a = NULL;
282 : const char **attrp;
283 : const char *p1;
284 : const void *p2;
285 11 : struct ldb_val *valp = NULL;
286 : int ret;
287 :
288 11 : switch (tree->operation) {
289 0 : case LDB_OP_AND:
290 : case LDB_OP_OR:
291 0 : for (i=0;i<tree->u.list.num_elements;i++) {
292 0 : ret = resolve_oids_parse_tree_replace(ldb, schema,
293 0 : tree->u.list.elements[i]);
294 0 : if (ret != LDB_SUCCESS) {
295 0 : return ret;
296 : }
297 : }
298 0 : return LDB_SUCCESS;
299 0 : case LDB_OP_NOT:
300 0 : return resolve_oids_parse_tree_replace(ldb, schema,
301 : tree->u.isnot.child);
302 11 : case LDB_OP_EQUALITY:
303 : case LDB_OP_GREATER:
304 : case LDB_OP_LESS:
305 : case LDB_OP_APPROX:
306 11 : attrp = &tree->u.equality.attr;
307 11 : valp = &tree->u.equality.value;
308 11 : break;
309 0 : case LDB_OP_SUBSTRING:
310 0 : attrp = &tree->u.substring.attr;
311 0 : break;
312 0 : case LDB_OP_PRESENT:
313 0 : attrp = &tree->u.present.attr;
314 0 : break;
315 0 : case LDB_OP_EXTENDED:
316 0 : attrp = &tree->u.extended.attr;
317 0 : valp = &tree->u.extended.value;
318 0 : break;
319 0 : default:
320 0 : return LDB_SUCCESS;
321 : }
322 :
323 11 : p1 = strchr(*attrp, '.');
324 :
325 11 : if (valp) {
326 11 : p2 = memchr(valp->data, '.', valp->length);
327 : } else {
328 0 : p2 = NULL;
329 : }
330 :
331 11 : if (!p1 && !p2) {
332 0 : return LDB_SUCCESS;
333 : }
334 :
335 11 : if (p1) {
336 11 : a = dsdb_attribute_by_attributeID_oid(schema, *attrp);
337 : } else {
338 0 : a = dsdb_attribute_by_lDAPDisplayName(schema, *attrp);
339 : }
340 11 : if (!a) {
341 0 : return LDB_SUCCESS;
342 : }
343 :
344 11 : *attrp = a->lDAPDisplayName;
345 :
346 11 : if (!p2) {
347 0 : return LDB_SUCCESS;
348 : }
349 :
350 11 : if (a->syntax->oMSyntax != 6) {
351 0 : return LDB_SUCCESS;
352 : }
353 :
354 11 : return resolve_oids_replace_value(ldb, schema, a, valp);
355 : }
356 :
357 740 : static int resolve_oids_element_replace(struct ldb_context *ldb,
358 : struct dsdb_schema *schema,
359 : struct ldb_message_element *el)
360 : {
361 : unsigned int i;
362 740 : const struct dsdb_attribute *a = NULL;
363 : const char *p1;
364 :
365 740 : p1 = strchr(el->name, '.');
366 :
367 740 : if (p1) {
368 0 : a = dsdb_attribute_by_attributeID_oid(schema, el->name);
369 : } else {
370 740 : a = dsdb_attribute_by_lDAPDisplayName(schema, el->name);
371 : }
372 740 : if (!a) {
373 0 : return LDB_SUCCESS;
374 : }
375 :
376 740 : el->name = a->lDAPDisplayName;
377 :
378 1748 : for (i=0; i < el->num_values; i++) {
379 : int ret;
380 1008 : ret = resolve_oids_replace_value(ldb, schema, a,
381 1008 : &el->values[i]);
382 1008 : if (ret != LDB_SUCCESS) {
383 0 : return ret;
384 : }
385 : }
386 :
387 740 : return LDB_SUCCESS;
388 : }
389 :
390 76 : static int resolve_oids_message_replace(struct ldb_context *ldb,
391 : struct dsdb_schema *schema,
392 : struct ldb_message *msg)
393 : {
394 : unsigned int i;
395 :
396 816 : for (i=0; i < msg->num_elements; i++) {
397 : int ret;
398 740 : ret = resolve_oids_element_replace(ldb, schema,
399 740 : &msg->elements[i]);
400 740 : if (ret != LDB_SUCCESS) {
401 0 : return ret;
402 : }
403 : }
404 :
405 76 : return LDB_SUCCESS;
406 : }
407 :
408 : struct resolve_oids_context {
409 : struct ldb_module *module;
410 : struct ldb_request *req;
411 : };
412 :
413 260 : static int resolve_oids_callback(struct ldb_request *req, struct ldb_reply *ares)
414 : {
415 : struct resolve_oids_context *ac;
416 :
417 260 : ac = talloc_get_type_abort(req->context, struct resolve_oids_context);
418 :
419 260 : if (!ares) {
420 0 : return ldb_module_done(ac->req, NULL, NULL,
421 : LDB_ERR_OPERATIONS_ERROR);
422 : }
423 260 : if (ares->error != LDB_SUCCESS) {
424 16 : return ldb_module_done(ac->req, ares->controls,
425 : ares->response, ares->error);
426 : }
427 :
428 244 : switch (ares->type) {
429 132 : case LDB_REPLY_ENTRY:
430 132 : return ldb_module_send_entry(ac->req, ares->message, ares->controls);
431 :
432 33 : case LDB_REPLY_REFERRAL:
433 33 : return ldb_module_send_referral(ac->req, ares->referral);
434 :
435 79 : case LDB_REPLY_DONE:
436 79 : return ldb_module_done(ac->req, ares->controls,
437 : ares->response, LDB_SUCCESS);
438 :
439 : }
440 0 : return LDB_SUCCESS;
441 : }
442 :
443 11162175 : static int resolve_oids_search(struct ldb_module *module, struct ldb_request *req)
444 : {
445 : struct ldb_context *ldb;
446 : struct dsdb_schema *schema;
447 : struct ldb_parse_tree *tree;
448 : struct ldb_request *down_req;
449 : struct resolve_oids_context *ac;
450 : int ret;
451 11162175 : bool needed = false;
452 : const char * const *attrs1;
453 : const char **attrs2;
454 : unsigned int i;
455 :
456 11162175 : ldb = ldb_module_get_ctx(module);
457 11162175 : schema = dsdb_get_schema(ldb, NULL);
458 :
459 11162175 : if (!schema) {
460 12619 : return ldb_next_request(module, req);
461 : }
462 :
463 : /* do not manipulate our control entries */
464 11149556 : if (ldb_dn_is_special(req->op.search.base)) {
465 54274 : return ldb_next_request(module, req);
466 : }
467 :
468 11095282 : ret = resolve_oids_parse_tree_need(ldb, schema,
469 11095282 : req->op.search.tree);
470 11095282 : if (ret == LDB_ERR_COMPARE_TRUE) {
471 11 : needed = true;
472 11095271 : } else if (ret != LDB_ERR_COMPARE_FALSE) {
473 0 : return ret;
474 : }
475 :
476 11095282 : attrs1 = req->op.search.attrs;
477 :
478 37922680 : for (i=0; attrs1 && attrs1[i]; i++) {
479 : const char *p;
480 : const struct dsdb_attribute *a;
481 :
482 26827398 : p = strchr(attrs1[i], '.');
483 26827398 : if (p == NULL) {
484 26827376 : continue;
485 : }
486 :
487 22 : a = dsdb_attribute_by_attributeID_oid(schema, attrs1[i]);
488 22 : if (a == NULL) {
489 22 : continue;
490 : }
491 :
492 0 : needed = true;
493 0 : break;
494 : }
495 :
496 11095282 : if (!needed) {
497 11095271 : return ldb_next_request(module, req);
498 : }
499 :
500 11 : ac = talloc(req, struct resolve_oids_context);
501 11 : if (ac == NULL) {
502 0 : return ldb_oom(ldb);
503 : }
504 11 : ac->module = module;
505 11 : ac->req = req;
506 :
507 11 : tree = ldb_parse_tree_copy_shallow(ac, req->op.search.tree);
508 11 : if (!tree) {
509 0 : return ldb_oom(ldb);
510 : }
511 :
512 11 : schema = talloc_reference(tree, schema);
513 11 : if (!schema) {
514 0 : return ldb_oom(ldb);
515 : }
516 :
517 11 : ret = resolve_oids_parse_tree_replace(ldb, schema,
518 : tree);
519 11 : if (ret != LDB_SUCCESS) {
520 0 : return ret;
521 : }
522 :
523 11 : attrs2 = str_list_copy_const(ac,
524 11 : discard_const_p(const char *, req->op.search.attrs));
525 11 : if (req->op.search.attrs && !attrs2) {
526 0 : return ldb_oom(ldb);
527 : }
528 :
529 22 : for (i=0; attrs2 && attrs2[i]; i++) {
530 : const char *p;
531 : const struct dsdb_attribute *a;
532 :
533 11 : p = strchr(attrs2[i], '.');
534 11 : if (p == NULL) {
535 11 : continue;
536 : }
537 :
538 0 : a = dsdb_attribute_by_attributeID_oid(schema, attrs2[i]);
539 0 : if (a == NULL) {
540 0 : continue;
541 : }
542 :
543 0 : attrs2[i] = a->lDAPDisplayName;
544 : }
545 :
546 11 : ret = ldb_build_search_req_ex(&down_req, ldb, ac,
547 : req->op.search.base,
548 : req->op.search.scope,
549 : tree,
550 : attrs2,
551 : req->controls,
552 : ac, resolve_oids_callback,
553 : req);
554 11 : LDB_REQ_SET_LOCATION(down_req);
555 11 : if (ret != LDB_SUCCESS) {
556 0 : return ret;
557 : }
558 :
559 : /* go on with the call chain */
560 11 : return ldb_next_request(module, down_req);
561 : }
562 :
563 320298 : static int resolve_oids_add(struct ldb_module *module, struct ldb_request *req)
564 : {
565 : struct ldb_context *ldb;
566 : struct dsdb_schema *schema;
567 : int ret;
568 : struct ldb_message *msg;
569 : struct ldb_request *down_req;
570 : struct resolve_oids_context *ac;
571 :
572 320298 : ldb = ldb_module_get_ctx(module);
573 320298 : schema = dsdb_get_schema(ldb, NULL);
574 :
575 320298 : if (!schema) {
576 0 : return ldb_next_request(module, req);
577 : }
578 :
579 : /* do not manipulate our control entries */
580 320298 : if (ldb_dn_is_special(req->op.add.message->dn)) {
581 371 : return ldb_next_request(module, req);
582 : }
583 :
584 319927 : ret = resolve_oids_message_need(ldb, schema,
585 : req->op.add.message);
586 319927 : if (ret == LDB_ERR_COMPARE_FALSE) {
587 319887 : return ldb_next_request(module, req);
588 40 : } else if (ret != LDB_ERR_COMPARE_TRUE) {
589 0 : return ret;
590 : }
591 :
592 40 : ac = talloc(req, struct resolve_oids_context);
593 40 : if (ac == NULL) {
594 0 : return ldb_oom(ldb);
595 : }
596 40 : ac->module = module;
597 40 : ac->req = req;
598 :
599 40 : msg = ldb_msg_copy_shallow(ac, ac->req->op.add.message);
600 40 : if (!msg) {
601 0 : return ldb_oom(ldb);
602 : }
603 :
604 40 : if (!talloc_reference(msg, schema)) {
605 0 : return ldb_oom(ldb);
606 : }
607 :
608 40 : ret = resolve_oids_message_replace(ldb, schema, msg);
609 40 : if (ret != LDB_SUCCESS) {
610 0 : return ret;
611 : }
612 :
613 40 : ret = ldb_build_add_req(&down_req, ldb, ac,
614 : msg,
615 : req->controls,
616 : ac, resolve_oids_callback,
617 : req);
618 40 : LDB_REQ_SET_LOCATION(down_req);
619 40 : if (ret != LDB_SUCCESS) {
620 0 : return ret;
621 : }
622 :
623 : /* go on with the call chain */
624 40 : return ldb_next_request(module, down_req);
625 : }
626 :
627 243833 : static int resolve_oids_modify(struct ldb_module *module, struct ldb_request *req)
628 : {
629 : struct ldb_context *ldb;
630 : struct dsdb_schema *schema;
631 : int ret;
632 : struct ldb_message *msg;
633 : struct ldb_request *down_req;
634 : struct resolve_oids_context *ac;
635 :
636 243833 : ldb = ldb_module_get_ctx(module);
637 243833 : schema = dsdb_get_schema(ldb, NULL);
638 :
639 243833 : if (!schema) {
640 0 : return ldb_next_request(module, req);
641 : }
642 :
643 : /* do not manipulate our control entries */
644 243833 : if (ldb_dn_is_special(req->op.mod.message->dn)) {
645 558 : return ldb_next_request(module, req);
646 : }
647 :
648 243275 : ret = resolve_oids_message_need(ldb, schema,
649 : req->op.mod.message);
650 243275 : if (ret == LDB_ERR_COMPARE_FALSE) {
651 243239 : return ldb_next_request(module, req);
652 36 : } else if (ret != LDB_ERR_COMPARE_TRUE) {
653 0 : return ret;
654 : }
655 :
656 36 : ac = talloc(req, struct resolve_oids_context);
657 36 : if (ac == NULL) {
658 0 : return ldb_oom(ldb);
659 : }
660 36 : ac->module = module;
661 36 : ac->req = req;
662 :
663 : /* we have to copy the message as the caller might have it as a const */
664 36 : msg = ldb_msg_copy_shallow(ac, req->op.mod.message);
665 36 : if (msg == NULL) {
666 0 : return ldb_oom(ldb);
667 : }
668 :
669 36 : if (!talloc_reference(msg, schema)) {
670 0 : return ldb_oom(ldb);
671 : }
672 :
673 36 : ret = resolve_oids_message_replace(ldb, schema, msg);
674 36 : if (ret != LDB_SUCCESS) {
675 0 : return ret;
676 : }
677 :
678 36 : ret = ldb_build_mod_req(&down_req, ldb, ac,
679 : msg,
680 : req->controls,
681 : ac, resolve_oids_callback,
682 : req);
683 36 : LDB_REQ_SET_LOCATION(down_req);
684 36 : if (ret != LDB_SUCCESS) {
685 0 : return ret;
686 : }
687 :
688 : /* go on with the call chain */
689 36 : return ldb_next_request(module, down_req);
690 : }
691 :
692 : static const struct ldb_module_ops ldb_resolve_oids_module_ops = {
693 : .name = "resolve_oids",
694 : .search = resolve_oids_search,
695 : .add = resolve_oids_add,
696 : .modify = resolve_oids_modify,
697 : };
698 :
699 :
700 4310 : int ldb_resolve_oids_module_init(const char *version)
701 : {
702 4310 : LDB_MODULE_CHECK_VERSION(version);
703 4310 : return ldb_register_module(&ldb_resolve_oids_module_ops);
704 : }
|