diff options
Diffstat (limited to 'source4/dsdb/schema/schema_init.c')
-rw-r--r-- | source4/dsdb/schema/schema_init.c | 72 |
1 files changed, 67 insertions, 5 deletions
diff --git a/source4/dsdb/schema/schema_init.c b/source4/dsdb/schema/schema_init.c index 752d4f57dd..efbd38a4ba 100644 --- a/source4/dsdb/schema/schema_init.c +++ b/source4/dsdb/schema/schema_init.c @@ -699,9 +699,10 @@ WERROR dsdb_attribute_from_ldb(const struct dsdb_schema *schema, return WERR_OK; } -WERROR dsdb_set_attribute_from_ldb(struct ldb_context *ldb, - struct dsdb_schema *schema, - struct ldb_message *msg) +WERROR dsdb_set_attribute_from_ldb_dups(struct ldb_context *ldb, + struct dsdb_schema *schema, + struct ldb_message *msg, + bool checkdups) { WERROR status; struct dsdb_attribute *attr = talloc_zero(schema, struct dsdb_attribute); @@ -729,12 +730,44 @@ WERROR dsdb_set_attribute_from_ldb(struct ldb_context *ldb, return WERR_DS_ATT_SCHEMA_REQ_SYNTAX; } + if (checkdups) { + const struct dsdb_attribute *a2; + struct dsdb_attribute **a; + uint32_t i; + + a2 = dsdb_attribute_by_attributeID_id(schema, + attr->attributeID_id); + if (a2 == NULL) { + goto done; + } + + i = schema->attributes_to_remove_size; + a = talloc_realloc(schema, schema->attributes_to_remove, + struct dsdb_attribute *, i + 1); + if (a == NULL) { + return WERR_NOMEM; + } + /* Mark the old attribute as to be removed */ + a[i] = discard_const_p(struct dsdb_attribute, a2); + schema->attributes_to_remove = a; + schema->attributes_to_remove_size++; + } + +done: DLIST_ADD(schema->attributes, attr); return WERR_OK; } -WERROR dsdb_set_class_from_ldb(struct dsdb_schema *schema, - struct ldb_message *msg) +WERROR dsdb_set_attribute_from_ldb(struct ldb_context *ldb, + struct dsdb_schema *schema, + struct ldb_message *msg) +{ + return dsdb_set_attribute_from_ldb_dups(ldb, schema, msg, false); +} + +WERROR dsdb_set_class_from_ldb_dups(struct dsdb_schema *schema, + struct ldb_message *msg, + bool checkdups) { WERROR status; struct dsdb_class *obj = talloc_zero(schema, struct dsdb_class); @@ -792,10 +825,39 @@ WERROR dsdb_set_class_from_ldb(struct dsdb_schema *schema, GET_BOOL_LDB(msg, "isDefunct", obj, isDefunct, false); GET_BOOL_LDB(msg, "systemOnly", obj, systemOnly, false); + if (checkdups) { + const struct dsdb_class *c2; + struct dsdb_class **c; + uint32_t i; + + c2 = dsdb_class_by_governsID_id(schema, obj->governsID_id); + if (c2 == NULL) { + goto done; + } + + i = schema->classes_to_remove_size; + c = talloc_realloc(schema, schema->classes_to_remove, + struct dsdb_class *, i + 1); + if (c == NULL) { + return WERR_NOMEM; + } + /* Mark the old class to be removed */ + c[i] = discard_const_p(struct dsdb_class, c2); + schema->classes_to_remove = c; + schema->classes_to_remove_size++; + } + +done: DLIST_ADD(schema->classes, obj); return WERR_OK; } +WERROR dsdb_set_class_from_ldb(struct dsdb_schema *schema, + struct ldb_message *msg) +{ + return dsdb_set_class_from_ldb_dups(schema, msg, false); +} + #define dsdb_oom(error_string, mem_ctx) *error_string = talloc_asprintf(mem_ctx, "dsdb out of memory at %s:%d\n", __FILE__, __LINE__) /* |