[SCM] Samba Shared Repository - branch master updated

Andrew Tridgell tridge at samba.org
Fri Jan 8 19:54:19 MST 2010


The branch, master has been updated
       via  349f7ba... s4-drs: added filtering by udv in getncchanges
       via  b0090d0... s4-idl: give a enum for attribute cn and a 'NONE' attribute
      from  9e6eb22... s4-drs: fixed the NC in the getncchanges RID alloc reply

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 349f7ba09c4cda14eea4df69bd6dcb082fc23c8d
Author: Andrew Tridgell <tridge at samba.org>
Date:   Sat Jan 9 13:11:27 2010 +1100

    s4-drs: added filtering by udv in getncchanges
    
    When a client supplied an uptodateness_vector, we can use it to filter
    what objects we return. This greatly reduces the amount of replication
    traffic between DCs.

commit b0090d01e061220d9b70a14e5a88b683949fe6a5
Author: Andrew Tridgell <tridge at samba.org>
Date:   Sat Jan 9 13:10:28 2010 +1100

    s4-idl: give a enum for attribute cn and a 'NONE' attribute
    
    The 'NONE' attribute has value 0xFFFFFFFF. Adding this ensures the
    compiler will complain if it is set to use 16 bit enums. We rely on
    being able to store 32 bits in an attid enum.

-----------------------------------------------------------------------

Summary of changes:
 librpc/gen_ndr/drsuapi.h                  |    6 ++-
 librpc/gen_ndr/ndr_drsuapi.c              |    2 +
 librpc/idl/drsuapi.idl                    |    4 +-
 source4/dsdb/common/util.c                |    6 +++
 source4/rpc_server/drsuapi/getncchanges.c |   66 +++++++++++++++++++++++++----
 5 files changed, 73 insertions(+), 11 deletions(-)


Changeset truncated at 500 lines:

diff --git a/librpc/gen_ndr/drsuapi.h b/librpc/gen_ndr/drsuapi.h
index 8596bf3..1f5960d 100644
--- a/librpc/gen_ndr/drsuapi.h
+++ b/librpc/gen_ndr/drsuapi.h
@@ -326,6 +326,7 @@ enum drsuapi_DsAttributeId
 #ifndef USE_UINT_ENUMS
  {
 	DRSUAPI_ATTRIBUTE_objectClass=(int)(0x00000000),
+	DRSUAPI_ATTRIBUTE_cn=(int)(0x00000003),
 	DRSUAPI_ATTRIBUTE_description=(int)(0x0000000d),
 	DRSUAPI_ATTRIBUTE_member=(int)(0x0000001f),
 	DRSUAPI_ATTRIBUTE_instanceType=(int)(0x00020001),
@@ -396,11 +397,13 @@ enum drsuapi_DsAttributeId
 	DRSUAPI_ATTRIBUTE_msDS_Behavior_Version=(int)(0x000905b3),
 	DRSUAPI_ATTRIBUTE_msDS_KeyVersionNumber=(int)(0x000906f6),
 	DRSUAPI_ATTRIBUTE_msDS_HasDomainNCs=(int)(0x0009071c),
-	DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs=(int)(0x0009072c)
+	DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs=(int)(0x0009072c),
+	DRSUAPI_ATTRIBUTE_NONE=(int)(0xFFFFFFFF)
 }
 #else
  { __donnot_use_enum_drsuapi_DsAttributeId=0x7FFFFFFF}
 #define DRSUAPI_ATTRIBUTE_objectClass ( 0x00000000 )
+#define DRSUAPI_ATTRIBUTE_cn ( 0x00000003 )
 #define DRSUAPI_ATTRIBUTE_description ( 0x0000000d )
 #define DRSUAPI_ATTRIBUTE_member ( 0x0000001f )
 #define DRSUAPI_ATTRIBUTE_instanceType ( 0x00020001 )
@@ -472,6 +475,7 @@ enum drsuapi_DsAttributeId
 #define DRSUAPI_ATTRIBUTE_msDS_KeyVersionNumber ( 0x000906f6 )
 #define DRSUAPI_ATTRIBUTE_msDS_HasDomainNCs ( 0x0009071c )
 #define DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs ( 0x0009072c )
+#define DRSUAPI_ATTRIBUTE_NONE ( 0xFFFFFFFF )
 #endif
 ;
 
diff --git a/librpc/gen_ndr/ndr_drsuapi.c b/librpc/gen_ndr/ndr_drsuapi.c
index 16388e7..5b31d1e 100644
--- a/librpc/gen_ndr/ndr_drsuapi.c
+++ b/librpc/gen_ndr/ndr_drsuapi.c
@@ -1379,6 +1379,7 @@ _PUBLIC_ void ndr_print_drsuapi_DsAttributeId(struct ndr_print *ndr, const char
 		ndr_set_flags(&ndr->flags, LIBNDR_PRINT_ARRAY_HEX);
 		switch (r) {
 			case DRSUAPI_ATTRIBUTE_objectClass: val = "DRSUAPI_ATTRIBUTE_objectClass"; break;
+			case DRSUAPI_ATTRIBUTE_cn: val = "DRSUAPI_ATTRIBUTE_cn"; break;
 			case DRSUAPI_ATTRIBUTE_description: val = "DRSUAPI_ATTRIBUTE_description"; break;
 			case DRSUAPI_ATTRIBUTE_member: val = "DRSUAPI_ATTRIBUTE_member"; break;
 			case DRSUAPI_ATTRIBUTE_instanceType: val = "DRSUAPI_ATTRIBUTE_instanceType"; break;
@@ -1450,6 +1451,7 @@ _PUBLIC_ void ndr_print_drsuapi_DsAttributeId(struct ndr_print *ndr, const char
 			case DRSUAPI_ATTRIBUTE_msDS_KeyVersionNumber: val = "DRSUAPI_ATTRIBUTE_msDS_KeyVersionNumber"; break;
 			case DRSUAPI_ATTRIBUTE_msDS_HasDomainNCs: val = "DRSUAPI_ATTRIBUTE_msDS_HasDomainNCs"; break;
 			case DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs: val = "DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs"; break;
+			case DRSUAPI_ATTRIBUTE_NONE: val = "DRSUAPI_ATTRIBUTE_NONE"; break;
 		}
 		ndr_print_enum(ndr, name, "ENUM", val, r);
 		ndr->flags = _flags_save_ENUM;
diff --git a/librpc/idl/drsuapi.idl b/librpc/idl/drsuapi.idl
index 2994958..dadaeee 100644
--- a/librpc/idl/drsuapi.idl
+++ b/librpc/idl/drsuapi.idl
@@ -437,6 +437,7 @@ interface drsuapi
 
 	typedef [flag(NDR_PAHEX),v1_enum,public] enum {
 		DRSUAPI_ATTRIBUTE_objectClass			= 0x00000000,
+		DRSUAPI_ATTRIBUTE_cn				= 0x00000003,
 		DRSUAPI_ATTRIBUTE_description			= 0x0000000d,
 		DRSUAPI_ATTRIBUTE_member			= 0x0000001f,
 		DRSUAPI_ATTRIBUTE_instanceType			= 0x00020001,
@@ -507,7 +508,8 @@ interface drsuapi
 		DRSUAPI_ATTRIBUTE_msDS_Behavior_Version		= 0x000905b3,
 		DRSUAPI_ATTRIBUTE_msDS_KeyVersionNumber		= 0x000906f6,
 		DRSUAPI_ATTRIBUTE_msDS_HasDomainNCs		= 0x0009071c,
-		DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs		= 0x0009072c
+		DRSUAPI_ATTRIBUTE_msDS_hasMasterNCs		= 0x0009072c,		
+		DRSUAPI_ATTRIBUTE_NONE				= 0xFFFFFFFF
 	} drsuapi_DsAttributeId;
 
 	typedef struct {
diff --git a/source4/dsdb/common/util.c b/source4/dsdb/common/util.c
index 70750ca..632025d 100644
--- a/source4/dsdb/common/util.c
+++ b/source4/dsdb/common/util.c
@@ -2810,6 +2810,12 @@ int drsuapi_DsReplicaCursor2_compare(const struct drsuapi_DsReplicaCursor2 *c1,
 	return GUID_compare(&c1->source_dsa_invocation_id, &c2->source_dsa_invocation_id);
 }
 
+int drsuapi_DsReplicaCursor_compare(const struct drsuapi_DsReplicaCursor *c1,
+				    const struct drsuapi_DsReplicaCursor *c2)
+{
+	return GUID_compare(&c1->source_dsa_invocation_id, &c2->source_dsa_invocation_id);
+}
+
 /*
   see if we are a RODC
 
diff --git a/source4/rpc_server/drsuapi/getncchanges.c b/source4/rpc_server/drsuapi/getncchanges.c
index d0ce819..46996c7 100644
--- a/source4/rpc_server/drsuapi/getncchanges.c
+++ b/source4/rpc_server/drsuapi/getncchanges.c
@@ -30,6 +30,7 @@
 #include "rpc_server/dcerpc_server_proto.h"
 #include "../libcli/drsuapi/drsuapi.h"
 #include "libcli/security/security.h"
+#include "lib/util/binsearch.h"
 
 /*
   build a DsReplicaObjectIdentifier from a ldb msg
@@ -57,6 +58,29 @@ static struct drsuapi_DsReplicaObjectIdentifier *get_object_identifier(TALLOC_CT
 	return identifier;
 }
 
+static int udv_compare(const struct GUID *guid1, struct GUID guid2)
+{
+	return GUID_compare(guid1, &guid2);
+}
+
+/*
+  see if we can filter an attribute using the uptodateness_vector
+ */
+static bool udv_filter(const struct drsuapi_DsReplicaCursorCtrEx *udv,
+		       const struct GUID *originating_invocation_id,
+		       uint64_t originating_usn)
+{
+	const struct drsuapi_DsReplicaCursor *c;
+	if (udv == NULL) return false;
+	BINARY_ARRAY_SEARCH(udv->cursors, udv->count, source_dsa_invocation_id, 
+			    originating_invocation_id, udv_compare, c);
+	if (c && originating_usn <= c->highest_usn) {
+		return true;
+	}
+	return false;
+	
+}
+
 /* 
   drsuapi_DsGetNCChanges for one object
 */
@@ -67,7 +91,8 @@ static WERROR get_nc_changes_build_object(struct drsuapi_DsReplicaObjectListItem
 					  struct dsdb_schema *schema,
 					  DATA_BLOB *session_key,
 					  uint64_t highest_usn,
-					  uint32_t replica_flags)
+					  uint32_t replica_flags,
+					  struct drsuapi_DsReplicaCursorCtrEx *uptodateness_vector)
 {
 	const struct ldb_val *md_value;
 	int i, n;
@@ -156,6 +181,14 @@ static WERROR get_nc_changes_build_object(struct drsuapi_DsReplicaObjectListItem
 			}
 		}
 
+		/* filter by uptodateness_vector */
+		if (md.ctr.ctr1.array[i].attid != DRSUAPI_ATTRIBUTE_instanceType &&
+		    udv_filter(uptodateness_vector,
+			       &md.ctr.ctr1.array[i].originating_invocation_id, 
+			       md.ctr.ctr1.array[i].originating_usn)) {
+			continue;
+		}
+
 		obj->meta_data_ctr->meta_data[n].originating_change_time = md.ctr.ctr1.array[i].originating_change_time;
 		obj->meta_data_ctr->meta_data[n].version = md.ctr.ctr1.array[i].version;
 		obj->meta_data_ctr->meta_data[n].originating_invocation_id = md.ctr.ctr1.array[i].originating_invocation_id;
@@ -164,11 +197,15 @@ static WERROR get_nc_changes_build_object(struct drsuapi_DsReplicaObjectListItem
 		n++;
 	}
 
-	/*
-	  note that if n==0 we still need to send the change, as it
-	  could be a rename, which changes the uSNChanged, but not any
-	  of the replicated attributes
-	 */
+	/* ignore it if its an empty change. Note that renames always
+	 * change the 'name' attribute, so they won't be ignored by
+	 * this */
+	if (n == 0 ||
+	    (n == 1 && attids[0] == DRSUAPI_ATTRIBUTE_instanceType)) {
+		talloc_free(obj->meta_data_ctr);
+		obj->meta_data_ctr = NULL;
+		return WERR_OK;
+	}
 
 	obj->meta_data_ctr->count = n;
 
@@ -302,7 +339,8 @@ static WERROR get_nc_changes_add_links(struct ldb_context *sam_ctx,
 				       uint32_t replica_flags,
 				       struct ldb_message *msg,
 				       struct drsuapi_DsReplicaLinkedAttribute **la_list,
-				       uint32_t *la_count)
+				       uint32_t *la_count,
+				       struct drsuapi_DsReplicaCursorCtrEx *uptodateness_vector)
 {
 	int i;
 	TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
@@ -668,6 +706,7 @@ struct drsuapi_getncchanges_state {
 	struct ldb_dn *last_dn;
 	struct drsuapi_DsReplicaLinkedAttribute *la_list;
 	uint32_t la_count;
+	struct drsuapi_DsReplicaCursorCtrEx *uptodateness_vector;
 };
 
 /* 
@@ -880,6 +919,14 @@ WERROR dcesrv_drsuapi_DsGetNCChanges(struct dcesrv_call_state *dce_call, TALLOC_
 			      (comparison_fn_t)site_res_cmp_usn_order);
 		}
 
+		getnc_state->uptodateness_vector = talloc_steal(getnc_state, req8->uptodateness_vector);
+		if (getnc_state->uptodateness_vector) {
+			/* make sure its sorted */
+			qsort(getnc_state->uptodateness_vector->cursors, 
+			      getnc_state->uptodateness_vector->count,
+			      sizeof(getnc_state->uptodateness_vector->cursors[0]),
+			      (comparison_fn_t)drsuapi_DsReplicaCursor_compare);
+		}
 	}
 
 	/* Prefix mapping */
@@ -935,7 +982,7 @@ WERROR dcesrv_drsuapi_DsGetNCChanges(struct dcesrv_call_state *dce_call, TALLOC_
 		werr = get_nc_changes_build_object(obj, msg,
 						   b_state->sam_ctx, getnc_state->ncRoot_dn, 
 						   schema, &session_key, getnc_state->min_usn,
-						   req8->replica_flags);
+						   req8->replica_flags, getnc_state->uptodateness_vector);
 		if (!W_ERROR_IS_OK(werr)) {
 			return werr;
 		}
@@ -946,7 +993,8 @@ WERROR dcesrv_drsuapi_DsGetNCChanges(struct dcesrv_call_state *dce_call, TALLOC_
 						req8->replica_flags,
 						msg,
 						&getnc_state->la_list,
-						&getnc_state->la_count);
+						&getnc_state->la_count,
+						getnc_state->uptodateness_vector);
 		if (!W_ERROR_IS_OK(werr)) {
 			return werr;
 		}


-- 
Samba Shared Repository


More information about the samba-cvs mailing list