summaryrefslogtreecommitdiff
path: root/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
diff options
context:
space:
mode:
authorAndrew Bartlett <abartlet@samba.org>2010-06-13 15:54:23 +1000
committerAndrew Bartlett <abartlet@samba.org>2010-06-16 09:57:51 +1000
commitffa787772fe6b88a846209e1733d004d80c99afc (patch)
treeaaef0375b5f416e1f1cc592bd479a3de0b6acd97 /source4/dsdb/samdb/ldb_modules/repl_meta_data.c
parentecfce7365c8d3fffc5b8eeda13b18e2605ff7b02 (diff)
downloadsamba-ffa787772fe6b88a846209e1733d004d80c99afc.tar.gz
samba-ffa787772fe6b88a846209e1733d004d80c99afc.tar.bz2
samba-ffa787772fe6b88a846209e1733d004d80c99afc.zip
s4:dsdb Handle backlinks for Windows 2000 level linked attributes
This revives the code from 5964acfa741d691c0196f91c0796122ec025f177, before tridge and I simplified this too much, and removed the Windows 2000 functional level linked attribute support. By telling the linked_attributes module that repl_meta_data has handled the links, we avoid a conflict for the new style (functional level 2003 and above) linked attributes. However, we still need backlinks for 2000 style linked attributes, so this allows that code in the linked_attributes module to be revived to handle those. Andrew Bartlett
Diffstat (limited to 'source4/dsdb/samdb/ldb_modules/repl_meta_data.c')
-rw-r--r--source4/dsdb/samdb/ldb_modules/repl_meta_data.c47
1 files changed, 36 insertions, 11 deletions
diff --git a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
index db2415b397..8994ee4014 100644
--- a/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
+++ b/source4/dsdb/samdb/ldb_modules/repl_meta_data.c
@@ -50,8 +50,6 @@
#include "libcli/security/security.h"
#include "lib/util/tsort.h"
-#define W2K3_LINKED_ATTRIBUTES 1
-
struct replmd_private {
TALLOC_CTX *la_ctx;
struct la_entry *la_list;
@@ -734,6 +732,7 @@ static int replmd_add(struct ldb_module *module, struct ldb_request *req)
char *time_str;
int ret;
unsigned int i;
+ unsigned int functional_level;
uint32_t ni=0;
bool allow_add_guid = false;
bool remove_current_guid = false;
@@ -753,6 +752,8 @@ static int replmd_add(struct ldb_module *module, struct ldb_request *req)
ldb = ldb_module_get_ctx(module);
+ functional_level = dsdb_functional_level(ldb);
+
ldb_debug(ldb, LDB_DEBUG_TRACE, "replmd_add\n");
ac = replmd_ctx_init(module, req);
@@ -875,8 +876,7 @@ static int replmd_add(struct ldb_module *module, struct ldb_request *req)
continue;
}
-#if W2K3_LINKED_ATTRIBUTES
- if (sa->linkID != 0 && dsdb_functional_level(ldb) > DS_DOMAIN_FUNCTION_2000) {
+ if (sa->linkID != 0 && functional_level > DS_DOMAIN_FUNCTION_2000) {
ret = replmd_add_fix_la(module, e, ac->seq_num, our_invocation_id, t, &guid, sa);
if (ret != LDB_SUCCESS) {
talloc_free(ac);
@@ -886,7 +886,6 @@ static int replmd_add(struct ldb_module *module, struct ldb_request *req)
replPropertyMetaData in FL above w2k */
continue;
}
-#endif
m->attid = sa->attributeID_id;
m->version = 1;
@@ -974,6 +973,14 @@ static int replmd_add(struct ldb_module *module, struct ldb_request *req)
return ret;
}
+ if (functional_level == DS_DOMAIN_FUNCTION_2000) {
+ ret = ldb_request_add_control(down_req, DSDB_CONTROL_APPLY_LINKS, false, NULL);
+ if (ret != LDB_SUCCESS) {
+ talloc_free(ac);
+ return ret;
+ }
+ }
+
/* mark the control done */
if (control) {
control->critical = 0;
@@ -1021,7 +1028,6 @@ static int replmd_update_rpmd_element(struct ldb_context *ldb,
if (a->attributeID_id == omd->ctr.ctr1.array[i].attid) break;
}
-#if W2K3_LINKED_ATTRIBUTES
if (a->linkID != 0 && dsdb_functional_level(ldb) > DS_DOMAIN_FUNCTION_2000) {
/* linked attributes are not stored in
replPropertyMetaData in FL above w2k, but we do
@@ -1032,7 +1038,6 @@ static int replmd_update_rpmd_element(struct ldb_context *ldb,
}
return LDB_SUCCESS;
}
-#endif
if (i == omd->ctr.ctr1.count) {
/* we need to add a new one */
@@ -1959,10 +1964,6 @@ static int replmd_modify_handle_linked_attribs(struct ldb_module *module,
return LDB_SUCCESS;
}
-#if !W2K3_LINKED_ATTRIBUTES
- return LDB_SUCCESS;
-#endif
-
if (dsdb_functional_level(ldb) == DS_DOMAIN_FUNCTION_2000) {
/* don't do anything special for linked attributes */
return LDB_SUCCESS;
@@ -2057,6 +2058,7 @@ static int replmd_modify(struct ldb_module *module, struct ldb_request *req)
bool is_urgent = false;
struct loadparm_context *lp_ctx;
char *referral;
+ unsigned int functional_level;
/* do not manipulate our control entries */
if (ldb_dn_is_special(req->op.mod.message->dn)) {
@@ -2064,6 +2066,8 @@ static int replmd_modify(struct ldb_module *module, struct ldb_request *req)
}
ldb = ldb_module_get_ctx(module);
+ functional_level = dsdb_functional_level(ldb);
+
lp_ctx = talloc_get_type(ldb_get_opaque(ldb, "loadparm"),
struct loadparm_context);
@@ -2123,6 +2127,18 @@ static int replmd_modify(struct ldb_module *module, struct ldb_request *req)
talloc_free(ac);
return ret;
}
+
+ /* If we are in functional level 2000, then
+ * replmd_modify_handle_linked_attribs will have done
+ * nothing */
+ if (functional_level == DS_DOMAIN_FUNCTION_2000) {
+ ret = ldb_request_add_control(down_req, DSDB_CONTROL_APPLY_LINKS, false, NULL);
+ if (ret != LDB_SUCCESS) {
+ talloc_free(ac);
+ return ret;
+ }
+ }
+
talloc_steal(down_req, msg);
/* we only change whenChanged and uSNChanged if the seq_num
@@ -3551,11 +3567,20 @@ static int replmd_extended_replicated_objects(struct ldb_module *module, struct
if (!req->controls) return replmd_replicated_request_werror(ar, WERR_NOMEM);
}
+ /* This allows layers further down to know if a change came in over replication */
ret = ldb_request_add_control(req, DSDB_CONTROL_REPLICATED_UPDATE_OID, false, NULL);
if (ret != LDB_SUCCESS) {
return ret;
}
+ /* If this change contained linked attributes in the body
+ * (rather than in the links section) we need to update
+ * backlinks in linked_attributes */
+ ret = ldb_request_add_control(req, DSDB_CONTROL_APPLY_LINKS, false, NULL);
+ if (ret != LDB_SUCCESS) {
+ return ret;
+ }
+
ar->controls = req->controls;
req->controls = ctrls;