[SCM] Samba Shared Repository - branch master updated - tevent-0-9-8-870-g9eb78be

Andrew Tridgell tridge at samba.org
Thu Oct 1 21:27:59 MDT 2009


The branch, master has been updated
       via  9eb78be4a670615b4e6a722f121f0f0e585b8d6b (commit)
       via  1726038708bcebd706dc4565963611dc86a33699 (commit)
       via  fd22e0304782e20b9bbb29464b6c745d409ff4c6 (commit)
       via  634d9d64766dd125d202f47c2d0cefc9da3c87b6 (commit)
       via  4cb055cacdc8a28f1efee1d40546baa05515e24e (commit)
       via  5d60a7e23ed7d9e6ff6e61dd5e9ee65796a22da4 (commit)
       via  2b332e6dfe25dd3ce33b9cb94e60c4b93bc5e240 (commit)
      from  b529a1e98723c30f965f71fb1e9577edb23219d1 (commit)

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


- Log -----------------------------------------------------------------
commit 9eb78be4a670615b4e6a722f121f0f0e585b8d6b
Author: Andrew Tridgell <tridge at samba.org>
Date:   Thu Oct 1 16:08:02 2009 +1000

    ndr64: added support for trailing gap alignment
    
    NDR64 has a 'trailing gap' alignment, which aligns the end of a
    structure on the overall structure alignment.
    
    This explains the discrepancy we had with the RPC-SAMR test and NDR64

commit 1726038708bcebd706dc4565963611dc86a33699
Author: Andrew Tridgell <tridge at samba.org>
Date:   Thu Sep 24 07:06:03 2009 -0700

    s4-ldb: accept the binary DN OIDs in extended DN modules

commit fd22e0304782e20b9bbb29464b6c745d409ff4c6
Author: Andrew Tridgell <tridge at samba.org>
Date:   Fri Oct 2 12:03:05 2009 +1000

    s4-ldb: Add support for binary blobs in DNs
    
    AD has the concept of a DN prefixed with B:NN:XXXXXX: that contains a
    binary blob. We need to support those in order to give correctly
    formatted binary blobs for things like wellKnownObjects
    
    This implementation is not ideal, as it allows for binary blobs on all
    DNs, whereas it should only allow them on those with a syntax of
    2.5.5.7. We should clean this up in the future, but meanwhile this
    implementation at least gets us a working DC join of w2k8 to s4.
    
    This patch also uses a static function for marking DNs as invalid,
    which is very useful when debugging this code, as you can break on it
    in gdb.

commit 634d9d64766dd125d202f47c2d0cefc9da3c87b6
Author: Andrew Tridgell <tridge at samba.org>
Date:   Fri Oct 2 11:52:16 2009 +1000

    s4-cldap: match w2k8-r2 for cldap netlogon bits
    
    Windows does not set the 3 high bits, which is strange given their
    meaning. I've submitted a CAR on this.

commit 4cb055cacdc8a28f1efee1d40546baa05515e24e
Author: Andrew Tridgell <tridge at samba.org>
Date:   Fri Oct 2 12:02:00 2009 +1000

    ds-flags: use the new name DS_DNS_FOREST_ROOT
    
    Update to use the new DS_DNS_FOREST_ROOT name, which makes it clearer
    what this bit means (according to MS-ADTS doc)

commit 5d60a7e23ed7d9e6ff6e61dd5e9ee65796a22da4
Author: Andrew Tridgell <tridge at samba.org>
Date:   Fri Oct 2 11:49:58 2009 +1000

    s3-ads: removed 3 unused defines
    
    These are in nbt.idl and netlogon.idl as well, no need to have them
    here under different names, especially when the comments are wrong

commit 2b332e6dfe25dd3ce33b9cb94e60c4b93bc5e240
Author: Andrew Tridgell <tridge at samba.org>
Date:   Thu Oct 1 17:29:56 2009 +1000

    idl: use common netlogon bit definitions
    
    The DS_ bits had got a bit ahead of the NBT_ bits.
    
    Ideally we'd make these a single set of bits at some point.
    
    This also removes NBT_SERVER_DNS_FOREST as this bit doesn't exist. I
    think it came from someone mis-reading the docs, which show the bits
    in reverse order within bytes (one of the worst bit table
    representations I have ever seen!)

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

Summary of changes:
 librpc/idl/nbt.idl                                 |    5 +-
 librpc/idl/netlogon.idl                            |    6 +-
 librpc/ndr/libndr.h                                |    2 +
 librpc/ndr/ndr_basic.c                             |   18 ++
 pidl/lib/Parse/Pidl/Samba4/NDR/Parser.pm           |    4 +
 source3/include/ads.h                              |    3 -
 source3/libsmb/dsgetdcname.c                       |    2 +-
 source4/cldap_server/netlogon.c                    |   27 +-
 source4/dsdb/samdb/ldb_modules/extended_dn_out.c   |    6 +-
 source4/dsdb/samdb/ldb_modules/extended_dn_store.c |    6 +-
 source4/dsdb/schema/schema_syntax.c                |  136 +++++++--
 source4/lib/ldb/common/ldb_dn.c                    |  318 ++++++++++++++++++--
 source4/lib/ldb/include/ldb.h                      |    7 +
 source4/rpc_server/netlogon/dcerpc_netlogon.c      |    2 +-
 source4/torture/ldap/cldap.c                       |   10 +-
 15 files changed, 471 insertions(+), 81 deletions(-)


Changeset truncated at 500 lines:

diff --git a/librpc/idl/nbt.idl b/librpc/idl/nbt.idl
index fc82b1c..a51132c 100644
--- a/librpc/idl/nbt.idl
+++ b/librpc/idl/nbt.idl
@@ -357,7 +357,10 @@ interface nbt
 		NBT_SERVER_NDNC				= 0x00000400,
 		NBT_SERVER_SELECT_SECRET_DOMAIN_6	= 0x00000800,
 		NBT_SERVER_FULL_SECRET_DOMAIN_6		= 0x00001000,
-		NBT_SERVER_DNS_FOREST			= 0x01000000
+		NBT_SERVER_ADS_WEB_SERVICE		= 0x00002000,
+		NBT_SERVER_HAS_DNS_NAME			= 0x20000000,
+		NBT_SERVER_IS_DEFAULT_NC		= 0x40000000,
+		NBT_SERVER_FOREST_ROOT			= 0x80000000
 	} nbt_server_type;
 
 	typedef [bitmap32bit,public] bitmap {
diff --git a/librpc/idl/netlogon.idl b/librpc/idl/netlogon.idl
index ef2c8a4..b08a893 100644
--- a/librpc/idl/netlogon.idl
+++ b/librpc/idl/netlogon.idl
@@ -1142,9 +1142,9 @@ interface netlogon
 		DS_SERVER_NDNC			 = NBT_SERVER_NDNC,
 		DS_SERVER_SELECT_SECRET_DOMAIN_6 = NBT_SERVER_SELECT_SECRET_DOMAIN_6,
 		DS_SERVER_FULL_SECRET_DOMAIN_6	 = NBT_SERVER_FULL_SECRET_DOMAIN_6,
-		DS_DNS_CONTROLLER		 = 0x20000000,
-		DS_DNS_DOMAIN			 = 0x40000000,
-		DS_DNS_FOREST			 = 0x80000000
+		DS_DNS_CONTROLLER		 = NBT_SERVER_HAS_DNS_NAME,
+		DS_DNS_DOMAIN			 = NBT_SERVER_IS_DEFAULT_NC,
+		DS_DNS_FOREST_ROOT		 = NBT_SERVER_FOREST_ROOT
 	} netr_DsR_DcFlags;
 
 	typedef [public] struct {
diff --git a/librpc/ndr/libndr.h b/librpc/ndr/libndr.h
index f6f5170..3236932 100644
--- a/librpc/ndr/libndr.h
+++ b/librpc/ndr/libndr.h
@@ -500,6 +500,8 @@ enum ndr_err_code ndr_push_align(struct ndr_push *ndr, size_t size);
 enum ndr_err_code ndr_pull_align(struct ndr_pull *ndr, size_t size);
 enum ndr_err_code ndr_push_union_align(struct ndr_push *ndr, size_t size);
 enum ndr_err_code ndr_pull_union_align(struct ndr_pull *ndr, size_t size);
+enum ndr_err_code ndr_push_trailer_align(struct ndr_push *ndr, size_t size);
+enum ndr_err_code ndr_pull_trailer_align(struct ndr_pull *ndr, size_t size);
 enum ndr_err_code ndr_push_bytes(struct ndr_push *ndr, const uint8_t *data, uint32_t n);
 enum ndr_err_code ndr_push_zero(struct ndr_push *ndr, uint32_t n);
 enum ndr_err_code ndr_push_array_uint8(struct ndr_push *ndr, int ndr_flags, const uint8_t *data, uint32_t n);
diff --git a/librpc/ndr/ndr_basic.c b/librpc/ndr/ndr_basic.c
index f3b7e75..807db59 100644
--- a/librpc/ndr/ndr_basic.c
+++ b/librpc/ndr/ndr_basic.c
@@ -573,6 +573,24 @@ _PUBLIC_ enum ndr_err_code ndr_pull_union_align(struct ndr_pull *ndr, size_t siz
 	return NDR_ERR_SUCCESS;
 }
 
+_PUBLIC_ enum ndr_err_code ndr_push_trailer_align(struct ndr_push *ndr, size_t size)
+{
+	/* MS-RPCE section 2.2.5.3.4.1 */
+	if (ndr->flags & LIBNDR_FLAG_NDR64) {
+		return ndr_push_align(ndr, size);
+	}
+	return NDR_ERR_SUCCESS;
+}
+
+_PUBLIC_ enum ndr_err_code ndr_pull_trailer_align(struct ndr_pull *ndr, size_t size)
+{
+	/* MS-RPCE section 2.2.5.3.4.1 */
+	if (ndr->flags & LIBNDR_FLAG_NDR64) {
+		return ndr_pull_align(ndr, size);
+	}
+	return NDR_ERR_SUCCESS;
+}
+
 /*
   push some bytes
 */
diff --git a/pidl/lib/Parse/Pidl/Samba4/NDR/Parser.pm b/pidl/lib/Parse/Pidl/Samba4/NDR/Parser.pm
index 9a02d52..11a43b4 100644
--- a/pidl/lib/Parse/Pidl/Samba4/NDR/Parser.pm
+++ b/pidl/lib/Parse/Pidl/Samba4/NDR/Parser.pm
@@ -1235,6 +1235,8 @@ sub ParseStructPushPrimitives($$$$$)
 	}
 
 	$self->ParseElementPush($_, $ndr, $env, 1, 0) foreach (@{$struct->{ELEMENTS}});
+
+	$self->pidl("NDR_CHECK(ndr_push_trailer_align($ndr, $struct->{ALIGN}));");
 }
 
 sub ParseStructPushDeferred($$$$)
@@ -1533,6 +1535,8 @@ sub ParseStructPullPrimitives($$$$$)
 	$self->ParseElementPull($_, $ndr, $env, 1, 0) foreach (@{$struct->{ELEMENTS}});
 
 	$self->add_deferred();
+
+	$self->pidl("NDR_CHECK(ndr_pull_trailer_align($ndr, $struct->{ALIGN}));");
 }
 
 sub ParseStructPullDeferred($$$$$)
diff --git a/source3/include/ads.h b/source3/include/ads.h
index 6d9b0ee..30f0b1f 100644
--- a/source3/include/ads.h
+++ b/source3/include/ads.h
@@ -211,9 +211,6 @@ typedef void **ADS_MODLIST;
 #define ADS_LDAP_MATCHING_RULE_BIT_OR	"1.2.840.113556.1.4.804"
 
 #define ADS_PINGS          0x0000FFFF  /* Ping response */
-#define ADS_DNS_CONTROLLER 0x20000000  /* DomainControllerName is a DNS name*/
-#define ADS_DNS_DOMAIN     0x40000000  /* DomainName is a DNS name */
-#define ADS_DNS_FOREST     0x80000000  /* DnsForestName is a DNS name */
 
 /* ads auth control flags */
 #define ADS_AUTH_DISABLE_KERBEROS 0x0001
diff --git a/source3/libsmb/dsgetdcname.c b/source3/libsmb/dsgetdcname.c
index 98b6594..1805470 100644
--- a/source3/libsmb/dsgetdcname.c
+++ b/source3/libsmb/dsgetdcname.c
@@ -686,7 +686,7 @@ static NTSTATUS make_domain_controller_info(TALLOC_CTX *mem_ctx,
 	if (forest_name && *forest_name) {
 		info->forest_name = talloc_strdup(mem_ctx, forest_name);
 		NT_STATUS_HAVE_NO_MEMORY(info->forest_name);
-		flags |= DS_DNS_FOREST;
+		flags |= DS_DNS_FOREST_ROOT;
 	}
 
 	info->dc_flags = flags;
diff --git a/source4/cldap_server/netlogon.c b/source4/cldap_server/netlogon.c
index ecc1369..50a8775 100644
--- a/source4/cldap_server/netlogon.c
+++ b/source4/cldap_server/netlogon.c
@@ -206,35 +206,42 @@ NTSTATUS fill_netlogon_samlogon_response(struct ldb_context *sam_ctx,
 	}
 		
 	server_type      = 
-		NBT_SERVER_DS | NBT_SERVER_TIMESERV |
-		NBT_SERVER_CLOSEST | NBT_SERVER_WRITABLE | 
-		NBT_SERVER_GOOD_TIMESERV | DS_DNS_CONTROLLER |
-		DS_DNS_DOMAIN;
+		DS_SERVER_DS | DS_SERVER_TIMESERV |
+		DS_SERVER_CLOSEST | DS_SERVER_WRITABLE | 
+		DS_SERVER_GOOD_TIMESERV;
+
+#if 0
+	/* w2k8-r2 as a DC does not claim these */
+	server_type |= DS_DNS_CONTROLLER | DS_DNS_DOMAIN;
+#endif
 
 	if (samdb_is_pdc(sam_ctx)) {
 		int *domainFunctionality;
-		server_type |= NBT_SERVER_PDC;
+		server_type |= DS_SERVER_PDC;
 		domainFunctionality = talloc_get_type(ldb_get_opaque(sam_ctx, "domainFunctionality"), int);
 		if (domainFunctionality && *domainFunctionality >= DS_DOMAIN_FUNCTION_2008) {
-			server_type |= NBT_SERVER_FULL_SECRET_DOMAIN_6;
+			server_type |= DS_SERVER_FULL_SECRET_DOMAIN_6;
 		}
 	}
 
 	if (samdb_is_gc(sam_ctx)) {
-		server_type |= NBT_SERVER_GC;
+		server_type |= DS_SERVER_GC;
 	}
 
 	if (str_list_check(services, "ldap")) {
-		server_type |= NBT_SERVER_LDAP;
+		server_type |= DS_SERVER_LDAP;
 	}
 
 	if (str_list_check(services, "kdc")) {
-		server_type |= NBT_SERVER_KDC;
+		server_type |= DS_SERVER_KDC;
 	}
 
+#if 0
+	/* w2k8-r2 as a sole DC does not claim this */
 	if (ldb_dn_compare(ldb_get_root_basedn(sam_ctx), ldb_get_default_basedn(sam_ctx)) == 0) {
-		server_type |= DS_DNS_FOREST;
+		server_type |= DS_DNS_FOREST_ROOT;
 	}
+#endif
 
 	pdc_name         = talloc_asprintf(mem_ctx, "\\\\%s", lp_netbios_name(lp_ctx));
 	domain_uuid      = samdb_result_guid(dom_res->msgs[0], "objectGUID");
diff --git a/source4/dsdb/samdb/ldb_modules/extended_dn_out.c b/source4/dsdb/samdb/ldb_modules/extended_dn_out.c
index f93090a..bb5e379 100644
--- a/source4/dsdb/samdb/ldb_modules/extended_dn_out.c
+++ b/source4/dsdb/samdb/ldb_modules/extended_dn_out.c
@@ -340,7 +340,8 @@ static int extended_callback(struct ldb_request *req, struct ldb_reply *ares)
 		}
 
 		/* Look to see if this attributeSyntax is a DN */
-		if (strcmp(attribute->attributeSyntax_oid, "2.5.5.1") != 0) {
+		if (strcmp(attribute->attributeSyntax_oid, "2.5.5.1") != 0 &&
+		    strcmp(attribute->attributeSyntax_oid, "2.5.5.7") != 0) {
 			continue;
 		}
 
@@ -617,7 +618,8 @@ static int extended_dn_out_dereference_init(struct ldb_module *module)
 			NULL
 		};
 
-		if (strcmp(cur->syntax->attributeSyntax_oid, "2.5.5.1") != 0) {
+		if (strcmp(cur->syntax->attributeSyntax_oid, "2.5.5.1") != 0 &&
+		    strcmp(cur->syntax->attributeSyntax_oid, "2.5.5.7") != 0) {
 			continue;
 		}
 		dereference_control->dereference
diff --git a/source4/dsdb/samdb/ldb_modules/extended_dn_store.c b/source4/dsdb/samdb/ldb_modules/extended_dn_store.c
index 3234f6f..122a9bb 100644
--- a/source4/dsdb/samdb/ldb_modules/extended_dn_store.c
+++ b/source4/dsdb/samdb/ldb_modules/extended_dn_store.c
@@ -303,7 +303,8 @@ static int extended_dn_add(struct ldb_module *module, struct ldb_request *req)
 		}
 
 		/* We only setup an extended DN GUID on these particular DN objects */
-		if (strcmp(schema_attr->attributeSyntax_oid, "2.5.5.1") != 0) {
+		if (strcmp(schema_attr->attributeSyntax_oid, "2.5.5.1") != 0 &&
+		    strcmp(schema_attr->attributeSyntax_oid, "2.5.5.7") != 0) {
 			continue;
 		}
 
@@ -376,7 +377,8 @@ static int extended_dn_modify(struct ldb_module *module, struct ldb_request *req
 		}
 
 		/* We only setup an extended DN GUID on these particular DN objects */
-		if (strcmp(schema_attr->attributeSyntax_oid, "2.5.5.1") != 0) {
+		if (strcmp(schema_attr->attributeSyntax_oid, "2.5.5.1") != 0 &&
+		    strcmp(schema_attr->attributeSyntax_oid, "2.5.5.7") != 0) {
 			continue;
 		}
 		
diff --git a/source4/dsdb/schema/schema_syntax.c b/source4/dsdb/schema/schema_syntax.c
index c564471..cbbd4a8 100644
--- a/source4/dsdb/schema/schema_syntax.c
+++ b/source4/dsdb/schema/schema_syntax.c
@@ -1204,6 +1204,8 @@ static WERROR dsdb_syntax_DN_ldb_to_drsuapi(struct ldb_context *ldb,
 	return WERR_OK;
 }
 
+
+
 static WERROR dsdb_syntax_DN_BINARY_drsuapi_to_ldb(struct ldb_context *ldb, 
 						   const struct dsdb_schema *schema,
 						   const struct dsdb_attribute *attr,
@@ -1212,6 +1214,7 @@ static WERROR dsdb_syntax_DN_BINARY_drsuapi_to_ldb(struct ldb_context *ldb,
 						   struct ldb_message_element *out)
 {
 	uint32_t i;
+	int ret;
 
 	out->flags	= 0;
 	out->name	= talloc_strdup(mem_ctx, attr->lDAPDisplayName);
@@ -1222,39 +1225,81 @@ static WERROR dsdb_syntax_DN_BINARY_drsuapi_to_ldb(struct ldb_context *ldb,
 	W_ERROR_HAVE_NO_MEMORY(out->values);
 
 	for (i=0; i < out->num_values; i++) {
-		struct drsuapi_DsReplicaObjectIdentifier3Binary id3b;
-		char *binary;
-		char *str;
+		struct drsuapi_DsReplicaObjectIdentifier3Binary id3;
 		enum ndr_err_code ndr_err;
+		DATA_BLOB guid_blob;
+		struct ldb_dn *dn;
+		TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
+		if (!tmp_ctx) {
+			W_ERROR_HAVE_NO_MEMORY(tmp_ctx);
+		}
 
 		if (in->value_ctr.values[i].blob == NULL) {
+			talloc_free(tmp_ctx);
 			return WERR_FOOBAR;
 		}
 
 		if (in->value_ctr.values[i].blob->length == 0) {
+			talloc_free(tmp_ctx);
 			return WERR_FOOBAR;
 		}
 
-		ndr_err = ndr_pull_struct_blob_all(in->value_ctr.values[i].blob,
-						   out->values, schema->iconv_convenience, &id3b,
-						   (ndr_pull_flags_fn_t)ndr_pull_drsuapi_DsReplicaObjectIdentifier3Binary);
+		
+		/* windows sometimes sends an extra two pad bytes here */
+		ndr_err = ndr_pull_struct_blob(in->value_ctr.values[i].blob,
+					       tmp_ctx, schema->iconv_convenience, &id3,
+					       (ndr_pull_flags_fn_t)ndr_pull_drsuapi_DsReplicaObjectIdentifier3Binary);
 		if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
 			NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+			talloc_free(tmp_ctx);
 			return ntstatus_to_werror(status);
 		}
 
-		/* TODO: handle id3.guid and id3.sid */
-		binary = data_blob_hex_string(out->values, &id3b.binary);
-		W_ERROR_HAVE_NO_MEMORY(binary);
+		dn = ldb_dn_new(tmp_ctx, ldb, id3.dn);
+		if (!dn) {
+			talloc_free(tmp_ctx);
+			/* If this fails, it must be out of memory, as it does not do much parsing */
+			W_ERROR_HAVE_NO_MEMORY(dn);
+		}
 
-		str = talloc_asprintf(out->values, "B:%u:%s:%s",
-				      (unsigned int)(id3b.binary.length * 2), /* because of 2 hex chars per byte */
-				      binary,
-				      id3b.dn);
-		W_ERROR_HAVE_NO_MEMORY(str);
+		ndr_err = ndr_push_struct_blob(&guid_blob, tmp_ctx, schema->iconv_convenience, &id3.guid,
+					       (ndr_push_flags_fn_t)ndr_push_GUID);
+		if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+			NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+			talloc_free(tmp_ctx);
+			return ntstatus_to_werror(status);
+		}
 
-		/* TODO: handle id3.guid and id3.sid */
-		out->values[i] = data_blob_string_const(str);
+		ret = ldb_dn_set_extended_component(dn, "GUID", &guid_blob);
+		if (ret != LDB_SUCCESS) {
+			talloc_free(tmp_ctx);
+			return WERR_FOOBAR;
+		}
+
+		talloc_free(guid_blob.data);
+
+		if (id3.__ndr_size_sid) {
+			DATA_BLOB sid_blob;
+			ndr_err = ndr_push_struct_blob(&sid_blob, tmp_ctx, schema->iconv_convenience, &id3.sid,
+						       (ndr_push_flags_fn_t)ndr_push_dom_sid);
+			if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+				NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+				talloc_free(tmp_ctx);
+				return ntstatus_to_werror(status);
+			}
+
+			ret = ldb_dn_set_extended_component(dn, "SID", &sid_blob);
+			if (ret != LDB_SUCCESS) {
+				talloc_free(tmp_ctx);
+				return WERR_FOOBAR;
+			}
+		}
+
+		/* set binary stuff */
+		ldb_dn_set_binary(dn, &id3.binary);
+
+		out->values[i] = data_blob_string_const(ldb_dn_get_extended_linearized(out->values, dn, 1));
+		talloc_free(tmp_ctx);
 	}
 
 	return WERR_OK;
@@ -1285,27 +1330,72 @@ static WERROR dsdb_syntax_DN_BINARY_ldb_to_drsuapi(struct ldb_context *ldb,
 	W_ERROR_HAVE_NO_MEMORY(blobs);
 
 	for (i=0; i < in->num_values; i++) {
-		struct drsuapi_DsReplicaObjectIdentifier3Binary id3b;
+		struct drsuapi_DsReplicaObjectIdentifier3Binary id3;
 		enum ndr_err_code ndr_err;
+		const DATA_BLOB *guid_blob, *sid_blob;
+		struct ldb_dn *dn;
+		TALLOC_CTX *tmp_ctx = talloc_new(mem_ctx);
+		W_ERROR_HAVE_NO_MEMORY(tmp_ctx);
 
 		out->value_ctr.values[i].blob	= &blobs[i];
 
-		/* TODO: handle id3b.guid and id3b.sid, id3.binary */
-		ZERO_STRUCT(id3b);
-		id3b.dn		= (const char *)in->values[i].data;
-		id3b.binary	= data_blob(NULL, 0);
+		dn = ldb_dn_from_ldb_val(tmp_ctx, ldb, &in->values[i]);
+
+		W_ERROR_HAVE_NO_MEMORY(dn);
+
+		guid_blob = ldb_dn_get_extended_component(dn, "GUID");
 
-		ndr_err = ndr_push_struct_blob(&blobs[i], blobs, schema->iconv_convenience, &id3b,
-					       (ndr_push_flags_fn_t)ndr_push_drsuapi_DsReplicaObjectIdentifier3Binary);
+		ZERO_STRUCT(id3);
+
+		if (guid_blob) {
+			ndr_err = ndr_pull_struct_blob_all(guid_blob, 
+							   tmp_ctx, schema->iconv_convenience, &id3.guid,
+							   (ndr_pull_flags_fn_t)ndr_pull_GUID);
+			if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+				NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+				talloc_free(tmp_ctx);
+				return ntstatus_to_werror(status);
+			}
+		}
+
+		sid_blob = ldb_dn_get_extended_component(dn, "SID");
+		if (sid_blob) {
+			
+			ndr_err = ndr_pull_struct_blob_all(sid_blob, 
+							   tmp_ctx, schema->iconv_convenience, &id3.sid,
+							   (ndr_pull_flags_fn_t)ndr_pull_dom_sid);
+			if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+				NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+				talloc_free(tmp_ctx);
+				return ntstatus_to_werror(status);
+			}
+		}
+
+		id3.dn = ldb_dn_get_linearized(dn);
+		if (strncmp(id3.dn, "B:", 2) == 0) {
+			id3.dn = strchr(id3.dn, ':');
+			id3.dn = strchr(id3.dn+1, ':');
+			id3.dn = strchr(id3.dn+1, ':');
+			id3.dn++;
+		}
+
+		/* get binary stuff */
+		ldb_dn_get_binary(dn, &id3.binary);
+
+		ndr_err = ndr_push_struct_blob(&blobs[i], blobs, schema->iconv_convenience, &id3, (ndr_push_flags_fn_t)ndr_push_drsuapi_DsReplicaObjectIdentifier3Binary);
 		if (!NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
 			NTSTATUS status = ndr_map_error2ntstatus(ndr_err);
+			talloc_free(tmp_ctx);
 			return ntstatus_to_werror(status);
 		}
+		talloc_free(tmp_ctx);
 	}
 
 	return WERR_OK;
 }
 
+
+
 static WERROR dsdb_syntax_PRESENTATION_ADDRESS_drsuapi_to_ldb(struct ldb_context *ldb, 
 							      const struct dsdb_schema *schema,
 							      const struct dsdb_attribute *attr,
diff --git a/source4/lib/ldb/common/ldb_dn.c b/source4/lib/ldb/common/ldb_dn.c
index 12a513f..798b85d 100644
--- a/source4/lib/ldb/common/ldb_dn.c
+++ b/source4/lib/ldb/common/ldb_dn.c
@@ -77,8 +77,17 @@ struct ldb_dn {
 
 	unsigned int ext_comp_num;
 	struct ldb_dn_ext_component *ext_components;
+
+	char extra_type;
+	struct ldb_val extra_val;
 };
 
+/* it is helpful to be able to break on this in gdb */
+static void ldb_dn_mark_invalid(struct ldb_dn *dn)
+{
+	dn->invalid = true;
+}
+
 /* strdn may be NULL */
 struct ldb_dn *ldb_dn_from_ldb_val(void *mem_ctx,
                                    struct ldb_context *ldb,
@@ -94,6 +103,13 @@ struct ldb_dn *ldb_dn_from_ldb_val(void *mem_ctx,
 		return NULL;
 	}
 
+	/* if the DN starts with B: then it has a binary blob
+	 * attached. Called the binary dn parser, which will call back
+	 * here for the rest of the DN */
+	if (strdn->data && strncmp((char *)strdn->data, "B:", 2) == 0) {
+		return ldb_dn_binary_from_ldb_val(mem_ctx, ldb, strdn);
+	}
+
 	dn = talloc_zero(mem_ctx, struct ldb_dn);
 	LDB_DN_NULL_FAILED(dn);
 
@@ -141,13 +157,180 @@ failed:
 	return NULL;
 }
 
+/*
+  a version of strhex_to_str internal to ldb, for use by the binary
+  ldb code
+ */
+static size_t ldb_strhex_to_str(char *p, size_t p_len, const char *strhex, 
+				size_t strhex_len)
+{
+	size_t i;
+	size_t num_chars = 0;
+	uint8_t   lonybble, hinybble;
+	const char     *hexchars = "0123456789ABCDEF";
+	char           *p1 = NULL, *p2 = NULL;
+
+	for (i = 0; i < strhex_len && strhex[i] != 0; i++) {
+		if (!(p1 = strchr(hexchars, toupper((unsigned char)strhex[i]))))
+			break;
+
+		i++; /* next hex digit */
+
+		if (!(p2 = strchr(hexchars, toupper((unsigned char)strhex[i]))))
+			break;
+
+		/* get the two nybbles */
+		hinybble = PTR_DIFF(p1, hexchars);
+		lonybble = PTR_DIFF(p2, hexchars);
+
+		if (num_chars >= p_len) {
+			break;
+		}
+
+		p[num_chars] = (hinybble << 4) | lonybble;
+		num_chars++;


-- 
Samba Shared Repository


More information about the samba-cvs mailing list