CVE-2019-14902 dsdb: Add comments explaining why SD propagation needs to be done...
[samba.git] / source4 / dsdb / samdb / ldb_modules / descriptor.c
1 /*
2    ldb database library
3
4    Copyright (C) Simo Sorce  2006-2008
5    Copyright (C) Andrew Bartlett <abartlet@samba.org> 2005-2007
6    Copyright (C) Nadezhda Ivanova  2009
7
8    This program is free software; you can redistribute it and/or modify
9    it under the terms of the GNU General Public License as published by
10    the Free Software Foundation; either version 3 of the License, or
11    (at your option) any later version.
12
13    This program is distributed in the hope that it will be useful,
14    but WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16    GNU General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program.  If not, see <http://www.gnu.org/licenses/>.
20 */
21
22 /*
23  *  Name: ldb
24  *
25  *  Component: DS Security descriptor module
26  *
27  *  Description:
28  *  - Calculate the security descriptor of a newly created object
29  *  - Perform sd recalculation on a move operation
30  *  - Handle sd modification invariants
31  *
32  *  Author: Nadezhda Ivanova
33  */
34
35 #include "includes.h"
36 #include <ldb_module.h>
37 #include "util/dlinklist.h"
38 #include "dsdb/samdb/samdb.h"
39 #include "librpc/ndr/libndr.h"
40 #include "librpc/gen_ndr/ndr_security.h"
41 #include "libcli/security/security.h"
42 #include "auth/auth.h"
43 #include "param/param.h"
44 #include "dsdb/samdb/ldb_modules/util.h"
45 #include "lib/util/binsearch.h"
46
47 struct descriptor_changes {
48         struct descriptor_changes *prev, *next;
49         struct descriptor_changes *children;
50         struct ldb_dn *nc_root;
51         struct ldb_dn *dn;
52         bool force_self;
53         bool force_children;
54         struct ldb_dn *stopped_dn;
55 };
56
57 struct descriptor_data {
58         TALLOC_CTX *trans_mem;
59         struct descriptor_changes *changes;
60 };
61
62 struct descriptor_context {
63         struct ldb_module *module;
64         struct ldb_request *req;
65         struct ldb_message *msg;
66         struct ldb_reply *search_res;
67         struct ldb_reply *search_oc_res;
68         struct ldb_val *parentsd_val;
69         struct ldb_message_element *sd_element;
70         struct ldb_val *sd_val;
71         uint32_t sd_flags;
72         int (*step_fn)(struct descriptor_context *);
73 };
74
75 static struct dom_sid *get_default_ag(TALLOC_CTX *mem_ctx,
76                                struct ldb_dn *dn,
77                                struct security_token *token,
78                                struct ldb_context *ldb)
79 {
80         TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
81         const struct dom_sid *domain_sid = samdb_domain_sid(ldb);
82         struct dom_sid *da_sid = dom_sid_add_rid(tmp_ctx, domain_sid, DOMAIN_RID_ADMINS);
83         struct dom_sid *ea_sid = dom_sid_add_rid(tmp_ctx, domain_sid, DOMAIN_RID_ENTERPRISE_ADMINS);
84         struct dom_sid *sa_sid = dom_sid_add_rid(tmp_ctx, domain_sid, DOMAIN_RID_SCHEMA_ADMINS);
85         struct dom_sid *dag_sid;
86         struct ldb_dn *nc_root;
87         int ret;
88
89         ret = dsdb_find_nc_root(ldb, tmp_ctx, dn, &nc_root);
90         if (ret != LDB_SUCCESS) {
91                 talloc_free(tmp_ctx);
92                 return NULL;
93         }
94
95         if (ldb_dn_compare(nc_root, ldb_get_schema_basedn(ldb)) == 0) {
96                 if (security_token_has_sid(token, sa_sid)) {
97                         dag_sid = dom_sid_dup(mem_ctx, sa_sid);
98                 } else if (security_token_has_sid(token, ea_sid)) {
99                         dag_sid = dom_sid_dup(mem_ctx, ea_sid);
100                 } else if (security_token_has_sid(token, da_sid)) {
101                         dag_sid = dom_sid_dup(mem_ctx, da_sid);
102                 } else if (security_token_is_system(token)) {
103                         dag_sid = dom_sid_dup(mem_ctx, sa_sid);
104                 } else {
105                         dag_sid = NULL;
106                 }
107         } else if (ldb_dn_compare(nc_root, ldb_get_config_basedn(ldb)) == 0) {
108                 if (security_token_has_sid(token, ea_sid)) {
109                         dag_sid = dom_sid_dup(mem_ctx, ea_sid);
110                 } else if (security_token_has_sid(token, da_sid)) {
111                         dag_sid = dom_sid_dup(mem_ctx, da_sid);
112                 } else if (security_token_is_system(token)) {
113                         dag_sid = dom_sid_dup(mem_ctx, ea_sid);
114                 } else {
115                         dag_sid = NULL;
116                 }
117         } else if (ldb_dn_compare(nc_root, ldb_get_default_basedn(ldb)) == 0) {
118                 if (security_token_has_sid(token, da_sid)) {
119                         dag_sid = dom_sid_dup(mem_ctx, da_sid);
120                 } else if (security_token_has_sid(token, ea_sid)) {
121                                 dag_sid = dom_sid_dup(mem_ctx, ea_sid);
122                 } else if (security_token_is_system(token)) {
123                         dag_sid = dom_sid_dup(mem_ctx, da_sid);
124                 } else {
125                         dag_sid = NULL;
126                 }
127         } else {
128                 dag_sid = NULL;
129         }
130
131         talloc_free(tmp_ctx);
132         return dag_sid;
133 }
134
135 static struct security_descriptor *get_sd_unpacked(struct ldb_module *module, TALLOC_CTX *mem_ctx,
136                                             const struct dsdb_class *objectclass)
137 {
138         struct ldb_context *ldb = ldb_module_get_ctx(module);
139         struct security_descriptor *sd;
140         const struct dom_sid *domain_sid = samdb_domain_sid(ldb);
141
142         if (!objectclass->defaultSecurityDescriptor || !domain_sid) {
143                 return NULL;
144         }
145
146         sd = sddl_decode(mem_ctx,
147                          objectclass->defaultSecurityDescriptor,
148                          domain_sid);
149         return sd;
150 }
151
152 static struct dom_sid *get_default_group(TALLOC_CTX *mem_ctx,
153                                          struct ldb_context *ldb,
154                                          struct dom_sid *dag)
155 {
156         /*
157          * This depends on the function level of the DC
158          * which is 2008R2 in our case. Which means it is
159          * higher than 2003 and we should use the
160          * "default administrator group" also as owning group.
161          *
162          * This matches dcpromo for a 2003 domain
163          * on a Windows 2008R2 DC.
164          */
165         return dag;
166 }
167
168 static struct security_descriptor *descr_handle_sd_flags(TALLOC_CTX *mem_ctx,
169                                                          struct security_descriptor *new_sd,
170                                                          struct security_descriptor *old_sd,
171                                                          uint32_t sd_flags)
172 {
173         struct security_descriptor *final_sd; 
174         /* if there is no control or control == 0 modify everything */
175         if (!sd_flags) {
176                 return new_sd;
177         }
178
179         final_sd = talloc_zero(mem_ctx, struct security_descriptor);
180         final_sd->revision = SECURITY_DESCRIPTOR_REVISION_1;
181         final_sd->type = SEC_DESC_SELF_RELATIVE;
182
183         if (sd_flags & (SECINFO_OWNER)) {
184                 if (new_sd->owner_sid) {
185                         final_sd->owner_sid = talloc_memdup(mem_ctx, new_sd->owner_sid, sizeof(struct dom_sid));
186                 }
187                 final_sd->type |= new_sd->type & SEC_DESC_OWNER_DEFAULTED;
188         }
189         else if (old_sd) {
190                 if (old_sd->owner_sid) {
191                         final_sd->owner_sid = talloc_memdup(mem_ctx, old_sd->owner_sid, sizeof(struct dom_sid));
192                 }
193                 final_sd->type |= old_sd->type & SEC_DESC_OWNER_DEFAULTED;
194         }
195
196         if (sd_flags & (SECINFO_GROUP)) {
197                 if (new_sd->group_sid) {
198                         final_sd->group_sid = talloc_memdup(mem_ctx, new_sd->group_sid, sizeof(struct dom_sid));
199                 }
200                 final_sd->type |= new_sd->type & SEC_DESC_GROUP_DEFAULTED;
201         } 
202         else if (old_sd) {
203                 if (old_sd->group_sid) {
204                         final_sd->group_sid = talloc_memdup(mem_ctx, old_sd->group_sid, sizeof(struct dom_sid));
205                 }
206                 final_sd->type |= old_sd->type & SEC_DESC_GROUP_DEFAULTED;
207         }
208
209         if (sd_flags & (SECINFO_SACL)) {
210                 final_sd->sacl = security_acl_dup(mem_ctx,new_sd->sacl);
211                 final_sd->type |= new_sd->type & (SEC_DESC_SACL_PRESENT |
212                         SEC_DESC_SACL_DEFAULTED|SEC_DESC_SACL_AUTO_INHERIT_REQ |
213                         SEC_DESC_SACL_AUTO_INHERITED|SEC_DESC_SACL_PROTECTED |
214                         SEC_DESC_SERVER_SECURITY);
215         } 
216         else if (old_sd && old_sd->sacl) {
217                 final_sd->sacl = security_acl_dup(mem_ctx,old_sd->sacl);
218                 final_sd->type |= old_sd->type & (SEC_DESC_SACL_PRESENT |
219                         SEC_DESC_SACL_DEFAULTED|SEC_DESC_SACL_AUTO_INHERIT_REQ |
220                         SEC_DESC_SACL_AUTO_INHERITED|SEC_DESC_SACL_PROTECTED |
221                         SEC_DESC_SERVER_SECURITY);
222         }
223
224         if (sd_flags & (SECINFO_DACL)) {
225                 final_sd->dacl = security_acl_dup(mem_ctx,new_sd->dacl);
226                 final_sd->type |= new_sd->type & (SEC_DESC_DACL_PRESENT |
227                         SEC_DESC_DACL_DEFAULTED|SEC_DESC_DACL_AUTO_INHERIT_REQ |
228                         SEC_DESC_DACL_AUTO_INHERITED|SEC_DESC_DACL_PROTECTED |
229                         SEC_DESC_DACL_TRUSTED);
230         } 
231         else if (old_sd && old_sd->dacl) {
232                 final_sd->dacl = security_acl_dup(mem_ctx,old_sd->dacl);
233                 final_sd->type |= old_sd->type & (SEC_DESC_DACL_PRESENT |
234                         SEC_DESC_DACL_DEFAULTED|SEC_DESC_DACL_AUTO_INHERIT_REQ |
235                         SEC_DESC_DACL_AUTO_INHERITED|SEC_DESC_DACL_PROTECTED |
236                         SEC_DESC_DACL_TRUSTED);
237         }
238         /* not so sure about this */
239         final_sd->type |= new_sd->type & SEC_DESC_RM_CONTROL_VALID;
240         return final_sd;
241 }
242
243 static DATA_BLOB *get_new_descriptor(struct ldb_module *module,
244                                      struct ldb_dn *dn,
245                                      TALLOC_CTX *mem_ctx,
246                                      const struct dsdb_class *objectclass,
247                                      const struct ldb_val *parent,
248                                      const struct ldb_val *object,
249                                      const struct ldb_val *old_sd,
250                                      uint32_t sd_flags)
251 {
252         struct security_descriptor *user_descriptor = NULL, *parent_descriptor = NULL;
253         struct security_descriptor *old_descriptor = NULL;
254         struct security_descriptor *new_sd, *final_sd;
255         DATA_BLOB *linear_sd;
256         enum ndr_err_code ndr_err;
257         struct ldb_context *ldb = ldb_module_get_ctx(module);
258         struct auth_session_info *session_info
259                 = ldb_get_opaque(ldb, DSDB_SESSION_INFO);
260         const struct dom_sid *domain_sid = samdb_domain_sid(ldb);
261         char *sddl_sd;
262         struct dom_sid *default_owner;
263         struct dom_sid *default_group;
264         struct security_descriptor *default_descriptor = NULL;
265         struct GUID *object_list = NULL;
266
267         if (objectclass != NULL) {
268                 default_descriptor = get_sd_unpacked(module, mem_ctx, objectclass);
269                 object_list = talloc_zero_array(mem_ctx, struct GUID, 2);
270                 if (object_list == NULL) {
271                         return NULL;
272                 }
273                 object_list[0] = objectclass->schemaIDGUID;
274         }
275
276         if (object) {
277                 user_descriptor = talloc(mem_ctx, struct security_descriptor);
278                 if (!user_descriptor) {
279                         return NULL;
280                 }
281                 ndr_err = ndr_pull_struct_blob(object, user_descriptor, 
282                                                user_descriptor,
283                                                (ndr_pull_flags_fn_t)ndr_pull_security_descriptor);
284
285                 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
286                         talloc_free(user_descriptor);
287                         return NULL;
288                 }
289         } else {
290                 user_descriptor = default_descriptor;
291         }
292
293         if (old_sd) {
294                 old_descriptor = talloc(mem_ctx, struct security_descriptor);
295                 if (!old_descriptor) {
296                         return NULL;
297                 }
298                 ndr_err = ndr_pull_struct_blob(old_sd, old_descriptor, 
299                                                old_descriptor,
300                                                (ndr_pull_flags_fn_t)ndr_pull_security_descriptor);
301
302                 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
303                         talloc_free(old_descriptor);
304                         return NULL;
305                 }
306         }
307
308         if (parent) {
309                 parent_descriptor = talloc(mem_ctx, struct security_descriptor);
310                 if (!parent_descriptor) {
311                         return NULL;
312                 }
313                 ndr_err = ndr_pull_struct_blob(parent, parent_descriptor, 
314                                                parent_descriptor,
315                                                (ndr_pull_flags_fn_t)ndr_pull_security_descriptor);
316
317                 if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
318                         talloc_free(parent_descriptor);
319                         return NULL;
320                 }
321         }
322
323         if (user_descriptor && default_descriptor &&
324             (user_descriptor->dacl == NULL))
325         {
326                 user_descriptor->dacl = default_descriptor->dacl;
327                 user_descriptor->type |= default_descriptor->type & (
328                         SEC_DESC_DACL_PRESENT |
329                         SEC_DESC_DACL_DEFAULTED|SEC_DESC_DACL_AUTO_INHERIT_REQ |
330                         SEC_DESC_DACL_AUTO_INHERITED|SEC_DESC_DACL_PROTECTED |
331                         SEC_DESC_DACL_TRUSTED);
332         }
333
334         if (user_descriptor && default_descriptor &&
335             (user_descriptor->sacl == NULL))
336         {
337                 user_descriptor->sacl = default_descriptor->sacl;
338                 user_descriptor->type |= default_descriptor->type & (
339                         SEC_DESC_SACL_PRESENT |
340                         SEC_DESC_SACL_DEFAULTED|SEC_DESC_SACL_AUTO_INHERIT_REQ |
341                         SEC_DESC_SACL_AUTO_INHERITED|SEC_DESC_SACL_PROTECTED |
342                         SEC_DESC_SERVER_SECURITY);
343         }
344
345
346         if (!(sd_flags & SECINFO_OWNER) && user_descriptor) {
347                 user_descriptor->owner_sid = NULL;
348
349                 /*
350                  * We need the correct owner sid
351                  * when calculating the DACL or SACL
352                  */
353                 if (old_descriptor) {
354                         user_descriptor->owner_sid = old_descriptor->owner_sid;
355                 }
356         }
357         if (!(sd_flags & SECINFO_GROUP) && user_descriptor) {
358                 user_descriptor->group_sid = NULL;
359
360                 /*
361                  * We need the correct group sid
362                  * when calculating the DACL or SACL
363                  */
364                 if (old_descriptor) {
365                         user_descriptor->group_sid = old_descriptor->group_sid;
366                 }
367         }
368         if (!(sd_flags & SECINFO_DACL) && user_descriptor) {
369                 user_descriptor->dacl = NULL;
370
371                 /*
372                  * We add SEC_DESC_DACL_PROTECTED so that
373                  * create_security_descriptor() skips
374                  * the unused inheritance calculation
375                  */
376                 user_descriptor->type |= SEC_DESC_DACL_PROTECTED;
377         }
378         if (!(sd_flags & SECINFO_SACL) && user_descriptor) {
379                 user_descriptor->sacl = NULL;
380
381                 /*
382                  * We add SEC_DESC_SACL_PROTECTED so that
383                  * create_security_descriptor() skips
384                  * the unused inheritance calculation
385                  */
386                 user_descriptor->type |= SEC_DESC_SACL_PROTECTED;
387         }
388
389         default_owner = get_default_ag(mem_ctx, dn,
390                                        session_info->security_token, ldb);
391         default_group = get_default_group(mem_ctx, ldb, default_owner);
392         new_sd = create_security_descriptor(mem_ctx,
393                                             parent_descriptor,
394                                             user_descriptor,
395                                             true,
396                                             object_list,
397                                             SEC_DACL_AUTO_INHERIT |
398                                             SEC_SACL_AUTO_INHERIT,
399                                             session_info->security_token,
400                                             default_owner, default_group,
401                                             map_generic_rights_ds);
402         if (!new_sd) {
403                 return NULL;
404         }
405         final_sd = descr_handle_sd_flags(mem_ctx, new_sd, old_descriptor, sd_flags);
406
407         if (!final_sd) {
408                 return NULL;
409         }
410
411         if (final_sd->dacl) {
412                 final_sd->dacl->revision = SECURITY_ACL_REVISION_ADS;
413         }
414         if (final_sd->sacl) {
415                 final_sd->sacl->revision = SECURITY_ACL_REVISION_ADS;
416         }
417
418         sddl_sd = sddl_encode(mem_ctx, final_sd, domain_sid);
419         DEBUG(10, ("Object %s created with descriptor %s\n\n", ldb_dn_get_linearized(dn), sddl_sd));
420
421         linear_sd = talloc(mem_ctx, DATA_BLOB);
422         if (!linear_sd) {
423                 return NULL;
424         }
425
426         ndr_err = ndr_push_struct_blob(linear_sd, mem_ctx,
427                                        final_sd,
428                                        (ndr_push_flags_fn_t)ndr_push_security_descriptor);
429         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
430                 return NULL;
431         }
432
433         return linear_sd;
434 }
435
436 static DATA_BLOB *descr_get_descriptor_to_show(struct ldb_module *module,
437                                                TALLOC_CTX *mem_ctx,
438                                                struct ldb_val *sd,
439                                                uint32_t sd_flags)
440 {
441         struct security_descriptor *old_sd, *final_sd;
442         DATA_BLOB *linear_sd;
443         enum ndr_err_code ndr_err;
444
445         old_sd = talloc(mem_ctx, struct security_descriptor);
446         if (!old_sd) {
447                 return NULL;
448         }
449         ndr_err = ndr_pull_struct_blob(sd, old_sd, 
450                                        old_sd,
451                                        (ndr_pull_flags_fn_t)ndr_pull_security_descriptor);
452
453         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
454                 talloc_free(old_sd);
455                 return NULL;
456         }
457
458         final_sd = descr_handle_sd_flags(mem_ctx, old_sd, NULL, sd_flags);
459
460         if (!final_sd) {
461                 return NULL;
462         }
463
464         linear_sd = talloc(mem_ctx, DATA_BLOB);
465         if (!linear_sd) {
466                 return NULL;
467         }
468
469         ndr_err = ndr_push_struct_blob(linear_sd, mem_ctx,
470                                        final_sd,
471                                        (ndr_push_flags_fn_t)ndr_push_security_descriptor);
472         if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
473                 return NULL;
474         }
475
476         return linear_sd;
477 }
478
479 static struct descriptor_context *descriptor_init_context(struct ldb_module *module,
480                                                           struct ldb_request *req)
481 {
482         struct ldb_context *ldb;
483         struct descriptor_context *ac;
484
485         ldb = ldb_module_get_ctx(module);
486
487         ac = talloc_zero(req, struct descriptor_context);
488         if (ac == NULL) {
489                 ldb_set_errstring(ldb, "Out of Memory");
490                 return NULL;
491         }
492
493         ac->module = module;
494         ac->req = req;
495         return ac;
496 }
497
498 static int descriptor_search_callback(struct ldb_request *req, struct ldb_reply *ares)
499 {
500         struct descriptor_context *ac;
501         struct ldb_val *sd_val = NULL;
502         struct ldb_message_element *sd_el;
503         DATA_BLOB *show_sd;
504         int ret = LDB_SUCCESS;
505
506         ac = talloc_get_type(req->context, struct descriptor_context);
507
508         if (!ares) {
509                 ret = LDB_ERR_OPERATIONS_ERROR;
510                 goto fail;
511         }
512         if (ares->error != LDB_SUCCESS) {
513                 return ldb_module_done(ac->req, ares->controls,
514                                         ares->response, ares->error);
515         }
516
517         switch (ares->type) {
518         case LDB_REPLY_ENTRY:
519                 sd_el = ldb_msg_find_element(ares->message, "nTSecurityDescriptor");
520                 if (sd_el) {
521                         sd_val = sd_el->values;
522                 }
523
524                 if (sd_val) {
525                         show_sd = descr_get_descriptor_to_show(ac->module, ac->req,
526                                                                sd_val, ac->sd_flags);
527                         if (!show_sd) {
528                                 ret = LDB_ERR_OPERATIONS_ERROR;
529                                 goto fail;
530                         }
531                         ldb_msg_remove_attr(ares->message, "nTSecurityDescriptor");
532                         ret = ldb_msg_add_steal_value(ares->message, "nTSecurityDescriptor", show_sd);
533                         if (ret != LDB_SUCCESS) {
534                                 goto fail;
535                         }
536                 }
537                 return ldb_module_send_entry(ac->req, ares->message, ares->controls);
538
539         case LDB_REPLY_REFERRAL:
540                 return ldb_module_send_referral(ac->req, ares->referral);
541
542         case LDB_REPLY_DONE:
543                 return ldb_module_done(ac->req, ares->controls,
544                                         ares->response, ares->error);
545         }
546
547 fail:
548         talloc_free(ares);
549         return ldb_module_done(ac->req, NULL, NULL, ret);
550 }
551
552 static int descriptor_add(struct ldb_module *module, struct ldb_request *req)
553 {
554         struct ldb_context *ldb = ldb_module_get_ctx(module);
555         struct ldb_request *add_req;
556         struct ldb_message *msg;
557         struct ldb_result *parent_res;
558         const struct ldb_val *parent_sd = NULL;
559         const struct ldb_val *user_sd;
560         struct ldb_dn *dn = req->op.add.message->dn;
561         struct ldb_dn *parent_dn, *nc_root;
562         struct ldb_message_element *objectclass_element, *sd_element;
563         int ret;
564         const struct dsdb_schema *schema;
565         DATA_BLOB *sd;
566         const struct dsdb_class *objectclass;
567         static const char * const parent_attrs[] = { "nTSecurityDescriptor", NULL };
568         uint32_t instanceType;
569         bool isNC = false;
570         uint32_t sd_flags = dsdb_request_sd_flags(req, NULL);
571
572         /* do not manipulate our control entries */
573         if (ldb_dn_is_special(dn)) {
574                 return ldb_next_request(module, req);
575         }
576
577         user_sd = ldb_msg_find_ldb_val(req->op.add.message, "nTSecurityDescriptor");
578         sd_element = ldb_msg_find_element(req->op.add.message, "nTSecurityDescriptor");
579         /* nTSecurityDescriptor without a value is an error, letting through so it is handled */
580         if (user_sd == NULL && sd_element) {
581                 return ldb_next_request(module, req);
582         }
583
584         ldb_debug(ldb, LDB_DEBUG_TRACE,"descriptor_add: %s\n", ldb_dn_get_linearized(dn));
585
586         instanceType = ldb_msg_find_attr_as_uint(req->op.add.message, "instanceType", 0);
587
588         if (instanceType & INSTANCE_TYPE_IS_NC_HEAD) {
589                 isNC = true;
590         }
591
592         if (!isNC) {
593                 ret = dsdb_find_nc_root(ldb, req, dn, &nc_root);
594                 if (ret != LDB_SUCCESS) {
595                         ldb_debug(ldb, LDB_DEBUG_TRACE,"descriptor_add: Could not find NC root for %s\n",
596                                 ldb_dn_get_linearized(dn));
597                         return ret;
598                 }
599
600                 if (ldb_dn_compare(dn, nc_root) == 0) {
601                         DEBUG(0, ("Found DN %s being a NC by the old method\n", ldb_dn_get_linearized(dn)));
602                         isNC = true;
603                 }
604         }
605
606         if (isNC) {
607                 DEBUG(2, ("DN: %s is a NC\n", ldb_dn_get_linearized(dn)));
608         }
609         if (!isNC) {
610                 /* if the object has a parent, retrieve its SD to
611                  * use for calculation. Unfortunately we do not yet have
612                  * instanceType, so we use dsdb_find_nc_root. */
613
614                 parent_dn = ldb_dn_get_parent(req, dn);
615                 if (parent_dn == NULL) {
616                         return ldb_oom(ldb);
617                 }
618
619                 /* we aren't any NC */
620                 ret = dsdb_module_search_dn(module, req, &parent_res, parent_dn,
621                                             parent_attrs,
622                                             DSDB_FLAG_NEXT_MODULE |
623                                             DSDB_FLAG_AS_SYSTEM |
624                                             DSDB_SEARCH_SHOW_RECYCLED,
625                                             req);
626                 if (ret != LDB_SUCCESS) {
627                         ldb_debug(ldb, LDB_DEBUG_TRACE,"descriptor_add: Could not find SD for %s\n",
628                                   ldb_dn_get_linearized(parent_dn));
629                         return ret;
630                 }
631                 if (parent_res->count != 1) {
632                         return ldb_operr(ldb);
633                 }
634                 parent_sd = ldb_msg_find_ldb_val(parent_res->msgs[0], "nTSecurityDescriptor");
635         }
636
637         schema = dsdb_get_schema(ldb, req);
638
639         objectclass_element = ldb_msg_find_element(req->op.add.message, "objectClass");
640         if (objectclass_element == NULL) {
641                 return ldb_operr(ldb);
642         }
643
644         objectclass = dsdb_get_last_structural_class(schema,
645                                                      objectclass_element);
646         if (objectclass == NULL) {
647                 return ldb_operr(ldb);
648         }
649
650         /*
651          * The SD_FLAG control is ignored on add
652          * and we default to all bits set.
653          */
654         sd_flags = SECINFO_OWNER|SECINFO_GROUP|SECINFO_SACL|SECINFO_DACL;
655
656         sd = get_new_descriptor(module, dn, req,
657                                 objectclass, parent_sd,
658                                 user_sd, NULL, sd_flags);
659         if (sd == NULL) {
660                 return ldb_operr(ldb);
661         }
662         msg = ldb_msg_copy_shallow(req, req->op.add.message);
663         if (msg == NULL) {
664                 return ldb_oom(ldb);
665         }
666         if (sd_element != NULL) {
667                 sd_element->values[0] = *sd;
668         } else {
669                 ret = ldb_msg_add_steal_value(msg,
670                                               "nTSecurityDescriptor",
671                                               sd);
672                 if (ret != LDB_SUCCESS) {
673                         return ret;
674                 }
675         }
676
677         ret = ldb_build_add_req(&add_req, ldb, req,
678                                 msg,
679                                 req->controls,
680                                 req, dsdb_next_callback,
681                                 req);
682         LDB_REQ_SET_LOCATION(add_req);
683         if (ret != LDB_SUCCESS) {
684                 return ldb_error(ldb, ret,
685                                  "descriptor_add: Error creating new add request.");
686         }
687
688         return ldb_next_request(module, add_req);
689 }
690
691 static int descriptor_modify(struct ldb_module *module, struct ldb_request *req)
692 {
693         struct ldb_context *ldb = ldb_module_get_ctx(module);
694         struct ldb_request *mod_req;
695         struct ldb_message *msg;
696         struct ldb_result *current_res, *parent_res;
697         const struct ldb_val *old_sd = NULL;
698         const struct ldb_val *parent_sd = NULL;
699         const struct ldb_val *user_sd;
700         struct ldb_dn *dn = req->op.mod.message->dn;
701         struct ldb_dn *parent_dn;
702         struct ldb_message_element *objectclass_element, *sd_element;
703         int ret;
704         uint32_t instanceType;
705         bool explicit_sd_flags = false;
706         uint32_t sd_flags = dsdb_request_sd_flags(req, &explicit_sd_flags);
707         const struct dsdb_schema *schema;
708         DATA_BLOB *sd;
709         const struct dsdb_class *objectclass;
710         static const char * const parent_attrs[] = { "nTSecurityDescriptor", NULL };
711         static const char * const current_attrs[] = { "nTSecurityDescriptor",
712                                                       "instanceType",
713                                                       "objectClass", NULL };
714         struct ldb_control *sd_propagation_control;
715         int cmp_ret = -1;
716
717         /* do not manipulate our control entries */
718         if (ldb_dn_is_special(dn)) {
719                 return ldb_next_request(module, req);
720         }
721
722         sd_propagation_control = ldb_request_get_control(req,
723                                         DSDB_CONTROL_SEC_DESC_PROPAGATION_OID);
724         if (sd_propagation_control != NULL) {
725                 if (sd_propagation_control->data != module) {
726                         return ldb_operr(ldb);
727                 }
728                 if (req->op.mod.message->num_elements != 0) {
729                         return ldb_operr(ldb);
730                 }
731                 if (explicit_sd_flags) {
732                         return ldb_operr(ldb);
733                 }
734                 if (sd_flags != 0xF) {
735                         return ldb_operr(ldb);
736                 }
737                 if (sd_propagation_control->critical == 0) {
738                         return ldb_operr(ldb);
739                 }
740
741                 sd_propagation_control->critical = 0;
742         }
743
744         sd_element = ldb_msg_find_element(req->op.mod.message, "nTSecurityDescriptor");
745         if (sd_propagation_control == NULL && sd_element == NULL) {
746                 return ldb_next_request(module, req);
747         }
748
749         /*
750          * nTSecurityDescriptor with DELETE is not supported yet.
751          * TODO: handle this correctly.
752          */
753         if (sd_propagation_control == NULL &&
754             LDB_FLAG_MOD_TYPE(sd_element->flags) == LDB_FLAG_MOD_DELETE)
755         {
756                 return ldb_module_error(module,
757                                         LDB_ERR_UNWILLING_TO_PERFORM,
758                                         "MOD_DELETE for nTSecurityDescriptor "
759                                         "not supported yet");
760         }
761
762         user_sd = ldb_msg_find_ldb_val(req->op.mod.message, "nTSecurityDescriptor");
763         /* nTSecurityDescriptor without a value is an error, letting through so it is handled */
764         if (sd_propagation_control == NULL && user_sd == NULL) {
765                 return ldb_next_request(module, req);
766         }
767
768         ldb_debug(ldb, LDB_DEBUG_TRACE,"descriptor_modify: %s\n", ldb_dn_get_linearized(dn));
769
770         ret = dsdb_module_search_dn(module, req, &current_res, dn,
771                                     current_attrs,
772                                     DSDB_FLAG_NEXT_MODULE |
773                                     DSDB_FLAG_AS_SYSTEM |
774                                     DSDB_SEARCH_SHOW_RECYCLED,
775                                     req);
776         if (ret != LDB_SUCCESS) {
777                 ldb_debug(ldb, LDB_DEBUG_ERROR,"descriptor_modify: Could not find %s\n",
778                           ldb_dn_get_linearized(dn));
779                 return ret;
780         }
781
782         instanceType = ldb_msg_find_attr_as_uint(current_res->msgs[0],
783                                                  "instanceType", 0);
784         /* if the object has a parent, retrieve its SD to
785          * use for calculation */
786         if (!ldb_dn_is_null(current_res->msgs[0]->dn) &&
787             !(instanceType & INSTANCE_TYPE_IS_NC_HEAD)) {
788                 parent_dn = ldb_dn_get_parent(req, dn);
789                 if (parent_dn == NULL) {
790                         return ldb_oom(ldb);
791                 }
792                 ret = dsdb_module_search_dn(module, req, &parent_res, parent_dn,
793                                             parent_attrs,
794                                             DSDB_FLAG_NEXT_MODULE |
795                                             DSDB_FLAG_AS_SYSTEM |
796                                             DSDB_SEARCH_SHOW_RECYCLED,
797                                             req);
798                 if (ret != LDB_SUCCESS) {
799                         ldb_debug(ldb, LDB_DEBUG_ERROR, "descriptor_modify: Could not find SD for %s\n",
800                                   ldb_dn_get_linearized(parent_dn));
801                         return ret;
802                 }
803                 if (parent_res->count != 1) {
804                         return ldb_operr(ldb);
805                 }
806                 parent_sd = ldb_msg_find_ldb_val(parent_res->msgs[0], "nTSecurityDescriptor");
807         }
808
809         schema = dsdb_get_schema(ldb, req);
810
811         objectclass_element = ldb_msg_find_element(current_res->msgs[0], "objectClass");
812         if (objectclass_element == NULL) {
813                 return ldb_operr(ldb);
814         }
815
816         objectclass = dsdb_get_last_structural_class(schema,
817                                                      objectclass_element);
818         if (objectclass == NULL) {
819                 return ldb_operr(ldb);
820         }
821
822         old_sd = ldb_msg_find_ldb_val(current_res->msgs[0], "nTSecurityDescriptor");
823         if (old_sd == NULL) {
824                 return ldb_operr(ldb);
825         }
826
827         if (sd_propagation_control != NULL) {
828                 /*
829                  * This just triggers a recalculation of the
830                  * inherited aces.
831                  */
832                 user_sd = old_sd;
833         }
834
835         sd = get_new_descriptor(module, dn, req,
836                                 objectclass, parent_sd,
837                                 user_sd, old_sd, sd_flags);
838         if (sd == NULL) {
839                 return ldb_operr(ldb);
840         }
841         msg = ldb_msg_copy_shallow(req, req->op.mod.message);
842         if (msg == NULL) {
843                 return ldb_oom(ldb);
844         }
845         cmp_ret = data_blob_cmp(old_sd, sd);
846         if (sd_propagation_control != NULL) {
847                 if (cmp_ret == 0) {
848                         /*
849                          * The nTSecurityDescriptor is unchanged,
850                          * which means we can stop the processing.
851                          *
852                          * We mark the control as critical again,
853                          * as we have not processed it, so the caller
854                          * can tell that the descriptor was unchanged.
855                          */
856                         sd_propagation_control->critical = 1;
857                         return ldb_module_done(req, NULL, NULL, LDB_SUCCESS);
858                 }
859
860                 ret = ldb_msg_add_empty(msg, "nTSecurityDescriptor",
861                                         LDB_FLAG_MOD_REPLACE,
862                                         &sd_element);
863                 if (ret != LDB_SUCCESS) {
864                         return ldb_oom(ldb);
865                 }
866                 ret = ldb_msg_add_value(msg, "nTSecurityDescriptor",
867                                         sd, NULL);
868                 if (ret != LDB_SUCCESS) {
869                         return ldb_oom(ldb);
870                 }
871         } else if (cmp_ret != 0) {
872                 struct ldb_dn *nc_root;
873
874                 ret = dsdb_find_nc_root(ldb, msg, dn, &nc_root);
875                 if (ret != LDB_SUCCESS) {
876                         return ldb_oom(ldb);
877                 }
878
879                 /*
880                  * Force SD propagation on children of this record
881                  */
882                 ret = dsdb_module_schedule_sd_propagation(module, nc_root,
883                                                           dn, false);
884                 if (ret != LDB_SUCCESS) {
885                         return ldb_operr(ldb);
886                 }
887                 sd_element->values[0] = *sd;
888         } else {
889                 sd_element->values[0] = *sd;
890         }
891
892         ret = ldb_build_mod_req(&mod_req, ldb, req,
893                                 msg,
894                                 req->controls,
895                                 req,
896                                 dsdb_next_callback,
897                                 req);
898         LDB_REQ_SET_LOCATION(mod_req);
899         if (ret != LDB_SUCCESS) {
900                 return ret;
901         }
902
903         return ldb_next_request(module, mod_req);
904 }
905
906 static int descriptor_search(struct ldb_module *module, struct ldb_request *req)
907 {
908         int ret;
909         struct ldb_context *ldb;
910         struct ldb_request *down_req;
911         struct descriptor_context *ac;
912         bool explicit_sd_flags = false;
913         uint32_t sd_flags = dsdb_request_sd_flags(req, &explicit_sd_flags);
914         bool show_sd = explicit_sd_flags;
915
916         if (!show_sd &&
917             ldb_attr_in_list(req->op.search.attrs, "nTSecurityDescriptor"))
918         {
919                 show_sd = true;
920         }
921
922         if (!show_sd) {
923                 return ldb_next_request(module, req);
924         }
925
926         ldb = ldb_module_get_ctx(module);
927         ac = descriptor_init_context(module, req);
928         if (ac == NULL) {
929                 return ldb_operr(ldb);
930         }
931         ac->sd_flags = sd_flags;
932
933         ret = ldb_build_search_req_ex(&down_req, ldb, ac,
934                                       req->op.search.base,
935                                       req->op.search.scope,
936                                       req->op.search.tree,
937                                       req->op.search.attrs,
938                                       req->controls,
939                                       ac, descriptor_search_callback,
940                                       ac->req);
941         LDB_REQ_SET_LOCATION(down_req);
942         if (ret != LDB_SUCCESS) {
943                 return ret;
944         }
945
946         return ldb_next_request(ac->module, down_req);
947 }
948
949 static int descriptor_rename(struct ldb_module *module, struct ldb_request *req)
950 {
951         struct ldb_context *ldb = ldb_module_get_ctx(module);
952         struct ldb_dn *olddn = req->op.rename.olddn;
953         struct ldb_dn *newdn = req->op.rename.newdn;
954         int ret;
955
956         /* do not manipulate our control entries */
957         if (ldb_dn_is_special(req->op.rename.olddn)) {
958                 return ldb_next_request(module, req);
959         }
960
961         ldb_debug(ldb, LDB_DEBUG_TRACE,"descriptor_rename: %s\n",
962                   ldb_dn_get_linearized(olddn));
963
964         if (ldb_dn_compare(olddn, newdn) != 0) {
965                 struct ldb_dn *nc_root;
966
967                 ret = dsdb_find_nc_root(ldb, req, newdn, &nc_root);
968                 if (ret != LDB_SUCCESS) {
969                         return ldb_oom(ldb);
970                 }
971
972                 /*
973                  * Force SD propagation on this record (get a new
974                  * inherited SD from the potentially new parent
975                  */
976                 ret = dsdb_module_schedule_sd_propagation(module, nc_root,
977                                                           newdn, true);
978                 if (ret != LDB_SUCCESS) {
979                         return ldb_operr(ldb);
980                 }
981         }
982
983         return ldb_next_request(module, req);
984 }
985
986 static int descriptor_extended_sec_desc_propagation(struct ldb_module *module,
987                                                     struct ldb_request *req)
988 {
989         struct descriptor_data *descriptor_private =
990                 talloc_get_type_abort(ldb_module_get_private(module),
991                 struct descriptor_data);
992         struct ldb_context *ldb = ldb_module_get_ctx(module);
993         struct dsdb_extended_sec_desc_propagation_op *op;
994         TALLOC_CTX *parent_mem = NULL;
995         struct descriptor_changes *parent_change = NULL;
996         struct descriptor_changes *c;
997         int ret;
998
999         op = talloc_get_type(req->op.extended.data,
1000                              struct dsdb_extended_sec_desc_propagation_op);
1001         if (op == NULL) {
1002                 ldb_debug(ldb, LDB_DEBUG_FATAL,
1003                           "descriptor_extended_sec_desc_propagation: "
1004                           "invalid extended data\n");
1005                 return LDB_ERR_PROTOCOL_ERROR;
1006         }
1007
1008         if (descriptor_private->trans_mem == NULL) {
1009                 return ldb_module_operr(module);
1010         }
1011
1012         parent_mem = descriptor_private->trans_mem;
1013
1014         for (c = descriptor_private->changes; c; c = c->next) {
1015                 ret = ldb_dn_compare(c->nc_root, op->nc_root);
1016                 if (ret != 0) {
1017                         continue;
1018                 }
1019
1020                 ret = ldb_dn_compare(c->dn, op->dn);
1021                 if (ret == 0) {
1022                         if (op->include_self) {
1023                                 c->force_self = true;
1024                         } else {
1025                                 c->force_children = true;
1026                         }
1027                         return ldb_module_done(req, NULL, NULL, LDB_SUCCESS);
1028                 }
1029
1030                 ret = ldb_dn_compare_base(c->dn, op->dn);
1031                 if (ret != 0) {
1032                         continue;
1033                 }
1034
1035                 parent_mem = c;
1036                 parent_change = c;
1037                 break;
1038         }
1039
1040         c = talloc_zero(parent_mem, struct descriptor_changes);
1041         if (c == NULL) {
1042                 return ldb_module_oom(module);
1043         }
1044         c->nc_root = ldb_dn_copy(c, op->nc_root);
1045         if (c->nc_root == NULL) {
1046                 return ldb_module_oom(module);
1047         }
1048         c->dn = ldb_dn_copy(c, op->dn);
1049         if (c->dn == NULL) {
1050                 return ldb_module_oom(module);
1051         }
1052         if (op->include_self) {
1053                 c->force_self = true;
1054         } else {
1055                 c->force_children = true;
1056         }
1057
1058         if (parent_change != NULL) {
1059                 DLIST_ADD_END(parent_change->children, c);
1060         } else {
1061                 DLIST_ADD_END(descriptor_private->changes, c);
1062         }
1063
1064         return ldb_module_done(req, NULL, NULL, LDB_SUCCESS);
1065 }
1066
1067 static int descriptor_extended(struct ldb_module *module, struct ldb_request *req)
1068 {
1069         if (strcmp(req->op.extended.oid, DSDB_EXTENDED_SEC_DESC_PROPAGATION_OID) == 0) {
1070                 return descriptor_extended_sec_desc_propagation(module, req);
1071         }
1072
1073         return ldb_next_request(module, req);
1074 }
1075
1076 static int descriptor_init(struct ldb_module *module)
1077 {
1078         struct ldb_context *ldb = ldb_module_get_ctx(module);
1079         int ret;
1080         struct descriptor_data *descriptor_private;
1081
1082         ret = ldb_mod_register_control(module, LDB_CONTROL_SD_FLAGS_OID);
1083         if (ret != LDB_SUCCESS) {
1084                 ldb_debug(ldb, LDB_DEBUG_ERROR,
1085                         "descriptor: Unable to register control with rootdse!\n");
1086                 return ldb_operr(ldb);
1087         }
1088
1089         descriptor_private = talloc_zero(module, struct descriptor_data);
1090         if (descriptor_private == NULL) {
1091                 ldb_oom(ldb);
1092                 return LDB_ERR_OPERATIONS_ERROR;
1093         }
1094         ldb_module_set_private(module, descriptor_private);
1095
1096         return ldb_next_init(module);
1097 }
1098
1099 static int descriptor_sd_propagation_object(struct ldb_module *module,
1100                                             struct ldb_message *msg,
1101                                             bool *stop)
1102 {
1103         struct ldb_context *ldb = ldb_module_get_ctx(module);
1104         struct ldb_request *sub_req;
1105         struct ldb_result *mod_res;
1106         struct ldb_control *sd_propagation_control;
1107         int ret;
1108
1109         *stop = false;
1110
1111         mod_res = talloc_zero(msg, struct ldb_result);
1112         if (mod_res == NULL) {
1113                 return ldb_module_oom(module);
1114         }
1115
1116         ret = ldb_build_mod_req(&sub_req, ldb, mod_res,
1117                                 msg,
1118                                 NULL,
1119                                 mod_res,
1120                                 ldb_modify_default_callback,
1121                                 NULL);
1122         LDB_REQ_SET_LOCATION(sub_req);
1123         if (ret != LDB_SUCCESS) {
1124                 return ldb_module_operr(module);
1125         }
1126
1127         ldb_req_mark_trusted(sub_req);
1128
1129         ret = ldb_request_add_control(sub_req,
1130                                       DSDB_CONTROL_SEC_DESC_PROPAGATION_OID,
1131                                       true, module);
1132         if (ret != LDB_SUCCESS) {
1133                 return ldb_module_operr(module);
1134         }
1135
1136         sd_propagation_control = ldb_request_get_control(sub_req,
1137                                         DSDB_CONTROL_SEC_DESC_PROPAGATION_OID);
1138         if (sd_propagation_control == NULL) {
1139                 return ldb_module_operr(module);
1140         }
1141
1142         ret = dsdb_request_add_controls(sub_req,
1143                                         DSDB_FLAG_AS_SYSTEM |
1144                                         DSDB_SEARCH_SHOW_RECYCLED);
1145         if (ret != LDB_SUCCESS) {
1146                 return ldb_module_operr(module);
1147         }
1148
1149         ret = descriptor_modify(module, sub_req);
1150         if (ret == LDB_SUCCESS) {
1151                 ret = ldb_wait(sub_req->handle, LDB_WAIT_ALL);
1152         }
1153         if (ret != LDB_SUCCESS) {
1154                 ldb_asprintf_errstring(ldb_module_get_ctx(module),
1155                                        "descriptor_modify on %s failed: %s",
1156                                        ldb_dn_get_linearized(msg->dn),
1157                                        ldb_errstring(ldb_module_get_ctx(module)));
1158                 return LDB_ERR_OPERATIONS_ERROR;
1159         }
1160
1161         if (sd_propagation_control->critical != 0) {
1162                 *stop = true;
1163         }
1164
1165         talloc_free(mod_res);
1166
1167         return LDB_SUCCESS;
1168 }
1169
1170 static int descriptor_sd_propagation_msg_sort(struct ldb_message **m1,
1171                                               struct ldb_message **m2)
1172 {
1173         struct ldb_dn *dn1 = (*m1)->dn;
1174         struct ldb_dn *dn2 = (*m2)->dn;
1175
1176         /*
1177          * This sorts in tree order, parents first
1178          */
1179         return ldb_dn_compare(dn2, dn1);
1180 }
1181
1182 static int descriptor_sd_propagation_dn_sort(struct ldb_dn *dn1,
1183                                              struct ldb_dn *dn2)
1184 {
1185         /*
1186          * This sorts in tree order, parents first
1187          */
1188         return ldb_dn_compare(dn2, dn1);
1189 }
1190
1191 static int descriptor_sd_propagation_recursive(struct ldb_module *module,
1192                                                struct descriptor_changes *change)
1193 {
1194         struct ldb_context *ldb = ldb_module_get_ctx(module);
1195         struct ldb_result *res = NULL;
1196         unsigned int i;
1197         const char * const no_attrs[] = { "@__NONE__", NULL };
1198         struct descriptor_changes *c;
1199         struct descriptor_changes *stopped_stack = NULL;
1200         enum ldb_scope scope;
1201         int ret;
1202
1203         /*
1204          * First confirm this object has children, or exists (depending on change->force_self)
1205          * 
1206          * LDB_SCOPE_SUBTREE searches are expensive.
1207          *
1208          * Note: that we do not search for deleted/recycled objects
1209          *
1210          * We know this is safe against a rename race as we are in the
1211          * prepare_commit(), so must be in a transaction.
1212          */
1213         ret = dsdb_module_search(module,
1214                                  change,
1215                                  &res,
1216                                  change->dn,
1217                                  LDB_SCOPE_ONELEVEL,
1218                                  no_attrs,
1219                                  DSDB_FLAG_NEXT_MODULE |
1220                                  DSDB_FLAG_AS_SYSTEM,
1221                                  NULL, /* parent_req */
1222                                  "(objectClass=*)");
1223         if (ret != LDB_SUCCESS) {
1224                 return ret;
1225         }
1226
1227         if (res->count == 0 && !change->force_self) {
1228                 TALLOC_FREE(res);
1229                 return LDB_SUCCESS;
1230         } else if (res->count == 0 && change->force_self) {
1231                 scope = LDB_SCOPE_BASE;
1232         } else {
1233                 scope = LDB_SCOPE_SUBTREE;
1234         }
1235
1236         /*
1237          * Note: that we do not search for deleted/recycled objects
1238          */
1239         ret = dsdb_module_search(module,
1240                                  change,
1241                                  &res,
1242                                  change->dn,
1243                                  scope,
1244                                  no_attrs,
1245                                  DSDB_FLAG_NEXT_MODULE |
1246                                  DSDB_FLAG_AS_SYSTEM,
1247                                  NULL, /* parent_req */
1248                                  "(objectClass=*)");
1249         if (ret != LDB_SUCCESS) {
1250                 return ret;
1251         }
1252
1253         TYPESAFE_QSORT(res->msgs, res->count,
1254                        descriptor_sd_propagation_msg_sort);
1255
1256         for (c = change->children; c; c = c->next) {
1257                 struct ldb_message *msg = NULL;
1258
1259                 BINARY_ARRAY_SEARCH_P(res->msgs, res->count, dn, c->dn,
1260                                       descriptor_sd_propagation_dn_sort,
1261                                       msg);
1262
1263                 if (msg == NULL) {
1264                         ldb_debug(ldb, LDB_DEBUG_WARNING,
1265                                 "descriptor_sd_propagation_recursive: "
1266                                 "%s not found under %s",
1267                                 ldb_dn_get_linearized(c->dn),
1268                                 ldb_dn_get_linearized(change->dn));
1269                         continue;
1270                 }
1271
1272                 msg->elements = (struct ldb_message_element *)c;
1273         }
1274
1275         DLIST_ADD(stopped_stack, change);
1276
1277         if (change->force_self) {
1278                 i = 0;
1279         } else {
1280                 i = 1;
1281         }
1282
1283         for (; i < res->count; i++) {
1284                 struct descriptor_changes *cur;
1285                 bool stop = false;
1286
1287                 cur = talloc_get_type(res->msgs[i]->elements,
1288                                       struct descriptor_changes);
1289                 res->msgs[i]->elements = NULL;
1290                 res->msgs[i]->num_elements = 0;
1291
1292                 if (cur != NULL) {
1293                         DLIST_REMOVE(change->children, cur);
1294                 }
1295
1296                 for (c = stopped_stack; c; c = stopped_stack) {
1297                         ret = ldb_dn_compare_base(c->dn,
1298                                                   res->msgs[i]->dn);
1299                         if (ret == 0) {
1300                                 break;
1301                         }
1302
1303                         c->stopped_dn = NULL;
1304                         DLIST_REMOVE(stopped_stack, c);
1305                 }
1306
1307                 if (cur != NULL) {
1308                         DLIST_ADD(stopped_stack, cur);
1309                 }
1310
1311                 if (stopped_stack->stopped_dn != NULL) {
1312                         ret = ldb_dn_compare_base(stopped_stack->stopped_dn,
1313                                                   res->msgs[i]->dn);
1314                         if (ret == 0) {
1315                                 continue;
1316                         }
1317                         stopped_stack->stopped_dn = NULL;
1318                 }
1319
1320                 ret = descriptor_sd_propagation_object(module, res->msgs[i],
1321                                                        &stop);
1322                 if (ret != LDB_SUCCESS) {
1323                         return ret;
1324                 }
1325
1326                 if (cur != NULL && cur->force_children) {
1327                         continue;
1328                 }
1329
1330                 if (stop) {
1331                         stopped_stack->stopped_dn = res->msgs[i]->dn;
1332                         continue;
1333                 }
1334         }
1335
1336         TALLOC_FREE(res);
1337         return LDB_SUCCESS;
1338 }
1339
1340 static int descriptor_start_transaction(struct ldb_module *module)
1341 {
1342         struct descriptor_data *descriptor_private =
1343                 talloc_get_type_abort(ldb_module_get_private(module),
1344                 struct descriptor_data);
1345
1346         if (descriptor_private->trans_mem != NULL) {
1347                 return ldb_module_operr(module);
1348         }
1349
1350         descriptor_private->trans_mem = talloc_new(descriptor_private);
1351         if (descriptor_private->trans_mem == NULL) {
1352                 return ldb_module_oom(module);
1353         }
1354         descriptor_private->changes = NULL;
1355
1356         return ldb_next_start_trans(module);
1357 }
1358
1359 static int descriptor_prepare_commit(struct ldb_module *module)
1360 {
1361         struct descriptor_data *descriptor_private =
1362                 talloc_get_type_abort(ldb_module_get_private(module),
1363                 struct descriptor_data);
1364         struct descriptor_changes *c, *n;
1365         int ret;
1366
1367         for (c = descriptor_private->changes; c; c = n) {
1368                 n = c->next;
1369                 DLIST_REMOVE(descriptor_private->changes, c);
1370
1371                 ret = descriptor_sd_propagation_recursive(module, c);
1372                 if (ret == LDB_ERR_NO_SUCH_OBJECT) {
1373                         continue;
1374                 }
1375                 if (ret != LDB_SUCCESS) {
1376                         return ret;
1377                 }
1378         }
1379
1380         return ldb_next_prepare_commit(module);
1381 }
1382
1383 static int descriptor_end_transaction(struct ldb_module *module)
1384 {
1385         struct descriptor_data *descriptor_private =
1386                 talloc_get_type_abort(ldb_module_get_private(module),
1387                 struct descriptor_data);
1388
1389         TALLOC_FREE(descriptor_private->trans_mem);
1390         descriptor_private->changes = NULL;
1391
1392         return ldb_next_end_trans(module);
1393 }
1394
1395 static int descriptor_del_transaction(struct ldb_module *module)
1396 {
1397         struct descriptor_data *descriptor_private =
1398                 talloc_get_type_abort(ldb_module_get_private(module),
1399                 struct descriptor_data);
1400
1401         TALLOC_FREE(descriptor_private->trans_mem);
1402         descriptor_private->changes = NULL;
1403
1404         return ldb_next_del_trans(module);
1405 }
1406
1407 static const struct ldb_module_ops ldb_descriptor_module_ops = {
1408         .name              = "descriptor",
1409         .search            = descriptor_search,
1410         .add               = descriptor_add,
1411         .modify            = descriptor_modify,
1412         .rename            = descriptor_rename,
1413         .init_context      = descriptor_init,
1414         .extended          = descriptor_extended,
1415         .start_transaction = descriptor_start_transaction,
1416         .prepare_commit    = descriptor_prepare_commit,
1417         .end_transaction   = descriptor_end_transaction,
1418         .del_transaction   = descriptor_del_transaction,
1419 };
1420
1421 int ldb_descriptor_module_init(const char *version)
1422 {
1423         LDB_MODULE_CHECK_VERSION(version);
1424         return ldb_register_module(&ldb_descriptor_module_ops);
1425 }