[SCM] Samba Shared Repository - branch master updated - release-4-0-0alpha8-12-g756f837

Volker Lendecke vlendec at samba.org
Fri Jun 19 12:28:48 GMT 2009


The branch, master has been updated
       via  756f83796fd307ed769bbc049d50c017f5eb4423 (commit)
       via  b9c99a29286c748bbd706fd8757be6ef3fa9abc1 (commit)
       via  663e841ecdd4baddcdc4905a72c78c2868a8c408 (commit)
       via  5cb6bf6f9d733cc085013174024785ab49a8bb51 (commit)
      from  862ae382b80ef158317193ffbbbc9580a50e011c (commit)

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


- Log -----------------------------------------------------------------
commit 756f83796fd307ed769bbc049d50c017f5eb4423
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jun 19 13:06:02 2009 +0200

    Add tiny tldap test

commit b9c99a29286c748bbd706fd8757be6ef3fa9abc1
Author: Volker Lendecke <vl at samba.org>
Date:   Sat Jun 13 11:59:39 2009 +0200

    Add tldap_fetch_rootdse

commit 663e841ecdd4baddcdc4905a72c78c2868a8c408
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jun 19 12:41:16 2009 +0200

    Make tevent_req_is_ldap_error public

commit 5cb6bf6f9d733cc085013174024785ab49a8bb51
Author: Volker Lendecke <vl at samba.org>
Date:   Fri Jun 19 11:45:01 2009 +0200

    Add tldap_context_[gs]etattr
    
    This adds the ability to attach extended information to a tldap_context. This
    will become useful once we start to do automatic reconnects for example, a
    callback function might want attach a pointer to credentials so that it can
    rebind.
    
    The initial user of this will be a cached rootdse, so that things like the
    ability to do paged searches can be cached.

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

Summary of changes:
 source3/Makefile.in          |    2 +-
 source3/include/tldap.h      |    5 ++
 source3/include/tldap_util.h |    7 ++
 source3/lib/tldap.c          |   80 +++++++++++++++++++++++++-
 source3/lib/tldap_util.c     |  131 ++++++++++++++++++++++++++++++++++++++++++
 source3/torture/torture.c    |   36 ++++++++++++
 6 files changed, 259 insertions(+), 2 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/Makefile.in b/source3/Makefile.in
index c657786..5d03886 100644
--- a/source3/Makefile.in
+++ b/source3/Makefile.in
@@ -1005,7 +1005,7 @@ NMBLOOKUP_OBJ = utils/nmblookup.o $(PARAM_OBJ) $(LIBNMB_OBJ) \
 SMBTORTURE_OBJ1 = torture/torture.o torture/nbio.o torture/scanner.o torture/utable.o \
 		torture/denytest.o torture/mangle_test.o
 
-SMBTORTURE_OBJ = $(SMBTORTURE_OBJ1) $(PARAM_OBJ) \
+SMBTORTURE_OBJ = $(SMBTORTURE_OBJ1) $(PARAM_OBJ) $(TLDAP_OBJ) \
 	$(LIBSMB_OBJ) $(LDB_OBJ) $(KRBCLIENT_OBJ) $(LIB_NONSMBD_OBJ) \
 	@LIBWBCLIENT_STATIC@ \
 	$(LIBNDR_GEN_OBJ0)
diff --git a/source3/include/tldap.h b/source3/include/tldap.h
index d57484c..9627244 100644
--- a/source3/include/tldap.h
+++ b/source3/include/tldap.h
@@ -45,7 +45,12 @@ struct tldap_mod {
 	DATA_BLOB *values;
 };
 
+bool tevent_req_is_ldap_error(struct tevent_req *req, int *perr);
+
 struct tldap_context *tldap_context_create(TALLOC_CTX *mem_ctx, int fd);
+bool tldap_context_setattr(struct tldap_context *ld,
+			   const char *name, const void *pptr);
+void *tldap_context_getattr(struct tldap_context *ld, const char *name);
 
 struct tevent_req *tldap_sasl_bind_send(TALLOC_CTX *mem_ctx,
 					struct tevent_context *ev,
diff --git a/source3/include/tldap_util.h b/source3/include/tldap_util.h
index 06b1036..8869d1e 100644
--- a/source3/include/tldap_util.h
+++ b/source3/include/tldap_util.h
@@ -54,4 +54,11 @@ bool tldap_pull_uint64(struct tldap_message *msg, const char *attr,
 bool tldap_pull_uint32(struct tldap_message *msg, const char *attr,
 		       uint32_t *presult);
 
+struct tevent_req *tldap_fetch_rootdse_send(TALLOC_CTX *mem_ctx,
+					    struct tevent_context *ev,
+					    struct tldap_context *ld);
+int tldap_fetch_rootdse_recv(struct tevent_req *req);
+int tldap_fetch_rootdse(struct tldap_context *ld);
+struct tldap_message *tldap_rootdse(struct tldap_context *ld);
+
 #endif
diff --git a/source3/lib/tldap.c b/source3/lib/tldap.c
index c70b8ca..e1dd676 100644
--- a/source3/lib/tldap.c
+++ b/source3/lib/tldap.c
@@ -19,7 +19,7 @@
 
 #include "includes.h"
 
-static bool tevent_req_is_ldap_error(struct tevent_req *req, int *perr)
+bool tevent_req_is_ldap_error(struct tevent_req *req, int *perr)
 {
 	enum tevent_req_state state;
 	uint64_t err;
@@ -44,6 +44,11 @@ static bool tevent_req_is_ldap_error(struct tevent_req *req, int *perr)
 	return true;
 }
 
+struct tldap_ctx_attribute {
+	char *name;
+	void *ptr;
+};
+
 struct tldap_context {
 	int ld_version;
 	int ld_deref;
@@ -64,6 +69,8 @@ struct tldap_context {
 	void (*log_fn)(void *context, enum tldap_debug_level level,
 		       const char *fmt, va_list ap);
 	void *log_private;
+
+	struct tldap_ctx_attribute *ctx_attrs;
 };
 
 struct tldap_message {
@@ -134,6 +141,77 @@ struct tldap_context *tldap_context_create(TALLOC_CTX *mem_ctx, int fd)
 	return ctx;
 }
 
+static struct tldap_ctx_attribute *tldap_context_findattr(
+	struct tldap_context *ld, const char *name)
+{
+	int i, num_attrs;
+
+	num_attrs = talloc_array_length(ld->ctx_attrs);
+
+	for (i=0; i<num_attrs; i++) {
+		if (strcmp(ld->ctx_attrs[i].name, name) == 0) {
+			return &ld->ctx_attrs[i];
+		}
+	}
+	return NULL;
+}
+
+bool tldap_context_setattr(struct tldap_context *ld,
+			   const char *name, const void *_pptr)
+{
+	struct tldap_ctx_attribute *tmp, *attr;
+	char *tmpname;
+	int num_attrs;
+	void **pptr = (void **)_pptr;
+
+	attr = tldap_context_findattr(ld, name);
+	if (attr != NULL) {
+		/*
+		 * We don't actually delete attrs, we don't expect tons of
+		 * attributes being shuffled around.
+		 */
+		TALLOC_FREE(attr->ptr);
+		if (*pptr != NULL) {
+			attr->ptr = talloc_move(ld->ctx_attrs, pptr);
+			*pptr = NULL;
+		}
+		return true;
+	}
+
+	tmpname = talloc_strdup(ld, name);
+	if (tmpname == NULL) {
+		return false;
+	}
+
+	num_attrs = talloc_array_length(ld->ctx_attrs);
+
+	tmp = talloc_realloc(ld, ld->ctx_attrs, struct tldap_ctx_attribute,
+			     num_attrs+1);
+	if (tmp == NULL) {
+		TALLOC_FREE(tmpname);
+		return false;
+	}
+	tmp[num_attrs].name = talloc_move(tmp, &tmpname);
+	if (*pptr != NULL) {
+		tmp[num_attrs].ptr = talloc_move(tmp, pptr);
+	} else {
+		tmp[num_attrs].ptr = NULL;
+	}
+	*pptr = NULL;
+	ld->ctx_attrs = tmp;
+	return true;
+}
+
+void *tldap_context_getattr(struct tldap_context *ld, const char *name)
+{
+	struct tldap_ctx_attribute *attr = tldap_context_findattr(ld, name);
+
+	if (attr == NULL) {
+		return NULL;
+	}
+	return attr->ptr;
+}
+
 struct read_ldap_state {
 	uint8_t *buf;
 	bool done;
diff --git a/source3/lib/tldap_util.c b/source3/lib/tldap_util.c
index 7c57916..042665f 100644
--- a/source3/lib/tldap_util.c
+++ b/source3/lib/tldap_util.c
@@ -378,3 +378,134 @@ bool tldap_pull_uint32(struct tldap_message *msg, const char *attr,
 	*presult = (uint32_t)result;
 	return true;
 }
+
+struct tldap_fetch_rootdse_state {
+	struct tldap_context *ld;
+	struct tldap_message *rootdse;
+};
+
+static void tldap_fetch_rootdse_done(struct tevent_req *subreq);
+
+struct tevent_req *tldap_fetch_rootdse_send(TALLOC_CTX *mem_ctx,
+					    struct tevent_context *ev,
+					    struct tldap_context *ld)
+{
+	struct tevent_req *req, *subreq;
+	struct tldap_fetch_rootdse_state *state;
+	static const char *attrs[2] = { "*", "+" };
+
+	req = tevent_req_create(mem_ctx, &state,
+				struct tldap_fetch_rootdse_state);
+	if (req == NULL) {
+		return NULL;
+	}
+	state->ld = ld;
+	state->rootdse = NULL;
+
+	subreq = tldap_search_send(
+		mem_ctx, ev, ld, "", TLDAP_SCOPE_BASE, "(objectclass=*)",
+		attrs, ARRAY_SIZE(attrs), 0, NULL, NULL, 0, 0, 0);
+	if (tevent_req_nomem(subreq, req)) {
+		return tevent_req_post(req, ev);
+	}
+	tevent_req_set_callback(subreq, tldap_fetch_rootdse_done, req);
+	return req;
+}
+
+static void tldap_fetch_rootdse_done(struct tevent_req *subreq)
+{
+	struct tevent_req *req = tevent_req_callback_data(
+		subreq, struct tevent_req);
+	struct tldap_fetch_rootdse_state *state = tevent_req_data(
+		req, struct tldap_fetch_rootdse_state);
+	struct tldap_message *msg;
+	int rc;
+
+	rc = tldap_search_recv(subreq, state, &msg);
+	if (rc != TLDAP_SUCCESS) {
+		TALLOC_FREE(subreq);
+		tevent_req_error(req, rc);
+		return;
+	}
+
+	switch (tldap_msg_type(msg)) {
+	case TLDAP_RES_SEARCH_ENTRY:
+		if (state->rootdse != NULL) {
+			goto protocol_error;
+		}
+		state->rootdse = msg;
+		break;
+	case TLDAP_RES_SEARCH_RESULT:
+		TALLOC_FREE(subreq);
+		if (state->rootdse == NULL) {
+			goto protocol_error;
+		}
+		tevent_req_done(req);
+		break;
+	default:
+		goto protocol_error;
+	}
+	tevent_req_done(req);
+	return;
+
+protocol_error:
+	tevent_req_error(req, TLDAP_PROTOCOL_ERROR);
+	return;
+}
+
+int tldap_fetch_rootdse_recv(struct tevent_req *req)
+{
+	struct tldap_fetch_rootdse_state *state = tevent_req_data(
+		req, struct tldap_fetch_rootdse_state);
+	int err;
+	char *dn;
+
+	if (tevent_req_is_ldap_error(req, &err)) {
+		return err;
+	}
+	/* Trigger parsing the dn, just to make sure it's ok */
+	if (!tldap_entry_dn(state->rootdse, &dn)) {
+		return TLDAP_DECODING_ERROR;
+	}
+	if (!tldap_context_setattr(state->ld, "tldap:rootdse",
+				   &state->rootdse)) {
+		return TLDAP_NO_MEMORY;
+	}
+	return 0;
+}
+
+int tldap_fetch_rootdse(struct tldap_context *ld)
+{
+	TALLOC_CTX *frame = talloc_stackframe();
+	struct tevent_context *ev;
+	struct tevent_req *req;
+	int result;
+
+	ev = event_context_init(frame);
+	if (ev == NULL) {
+		result = TLDAP_NO_MEMORY;
+		goto fail;
+	}
+
+	req = tldap_fetch_rootdse_send(frame, ev, ld);
+	if (req == NULL) {
+		result = TLDAP_NO_MEMORY;
+		goto fail;
+	}
+
+	if (!tevent_req_poll(req, ev)) {
+		result = TLDAP_OPERATIONS_ERROR;
+		goto fail;
+	}
+
+	result = tldap_fetch_rootdse_recv(req);
+ fail:
+	TALLOC_FREE(frame);
+	return result;
+}
+
+struct tldap_message *tldap_rootdse(struct tldap_context *ld)
+{
+	return talloc_get_type(tldap_context_getattr(ld, "tldap:rootdse"),
+			       struct tldap_message);
+}
diff --git a/source3/torture/torture.c b/source3/torture/torture.c
index baa8a15..7a4a5fc 100644
--- a/source3/torture/torture.c
+++ b/source3/torture/torture.c
@@ -5585,6 +5585,41 @@ static bool run_shortname_test(int dummy)
 	return correct;
 }
 
+static bool run_tldap(int dummy)
+{
+	struct tldap_context *ld;
+	int fd, rc;
+	NTSTATUS status;
+	struct sockaddr_storage addr;
+
+	if (!resolve_name(host, &addr, 0)) {
+		d_printf("could not find host %s\n", host);
+		return false;
+	}
+	status = open_socket_out(&addr, 389, 9999, &fd);
+	if (!NT_STATUS_IS_OK(status)) {
+		d_printf("open_socket_out failed: %s\n", nt_errstr(status));
+		return false;
+	}
+
+	ld = tldap_context_create(talloc_tos(), fd);
+	if (ld == NULL) {
+		close(fd);
+		d_printf("tldap_context_create failed\n");
+		return false;
+	}
+
+	rc = tldap_fetch_rootdse(ld);
+	if (rc != TLDAP_SUCCESS) {
+		d_printf("tldap_fetch_rootdse failed: %s\n",
+			 tldap_errstr(talloc_tos(), ld, rc));
+		return false;
+	}
+
+	TALLOC_FREE(ld);
+	return true;
+}
+
 static bool run_local_substitute(int dummy)
 {
 	bool ok = true;
@@ -6250,6 +6285,7 @@ static struct {
 	{ "WINDOWS-WRITE", run_windows_write, 0},
 	{ "CLI_ECHO", run_cli_echo, 0},
 	{ "GETADDRINFO", run_getaddrinfo_send, 0},
+	{ "TLDAP", run_tldap },
 	{ "LOCAL-SUBSTITUTE", run_local_substitute, 0},
 	{ "LOCAL-GENCACHE", run_local_gencache, 0},
 	{ "LOCAL-RBTREE", run_local_rbtree, 0},


-- 
Samba Shared Repository


More information about the samba-cvs mailing list