From f26b61dfe246c750a42f1f9fb28f9df5981bc841 Mon Sep 17 00:00:00 2001 From: Stephen Gallagher Date: Mon, 3 Oct 2011 11:28:35 -0400 Subject: LDAP: Add support for multiple search bases for user enumeration --- src/providers/ldap/ldap_id.c | 3 ++- src/providers/ldap/ldap_id_enum.c | 3 ++- src/providers/ldap/sdap_async.h | 3 ++- src/providers/ldap/sdap_async_users.c | 48 +++++++++++++++++++++++++++++++---- 4 files changed, 49 insertions(+), 8 deletions(-) (limited to 'src') diff --git a/src/providers/ldap/ldap_id.c b/src/providers/ldap/ldap_id.c index 3e93bb852..c381c19b1 100644 --- a/src/providers/ldap/ldap_id.c +++ b/src/providers/ldap/ldap_id.c @@ -172,7 +172,8 @@ static void users_get_connect_done(struct tevent_req *subreq) sdap_id_op_handle(state->op), state->attrs, state->filter, dp_opt_get_int(state->ctx->opts->basic, - SDAP_SEARCH_TIMEOUT)); + SDAP_SEARCH_TIMEOUT), + false); if (!subreq) { tevent_req_error(req, ENOMEM); return; diff --git a/src/providers/ldap/ldap_id_enum.c b/src/providers/ldap/ldap_id_enum.c index 45f4ef78a..9923379db 100644 --- a/src/providers/ldap/ldap_id_enum.c +++ b/src/providers/ldap/ldap_id_enum.c @@ -482,7 +482,8 @@ static struct tevent_req *enum_users_send(TALLOC_CTX *memctx, sdap_id_op_handle(state->op), state->attrs, state->filter, dp_opt_get_int(state->ctx->opts->basic, - SDAP_ENUM_SEARCH_TIMEOUT)); + SDAP_ENUM_SEARCH_TIMEOUT), + true); if (!subreq) { ret = ENOMEM; goto fail; diff --git a/src/providers/ldap/sdap_async.h b/src/providers/ldap/sdap_async.h index ef18c775a..262c04a0d 100644 --- a/src/providers/ldap/sdap_async.h +++ b/src/providers/ldap/sdap_async.h @@ -49,7 +49,8 @@ struct tevent_req *sdap_get_users_send(TALLOC_CTX *memctx, struct sdap_handle *sh, const char **attrs, const char *filter, - int timeout); + int timeout, + bool enumeration); int sdap_get_users_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx, char **timestamp); diff --git a/src/providers/ldap/sdap_async_users.c b/src/providers/ldap/sdap_async_users.c index b2623a3fd..cf9a8d33c 100644 --- a/src/providers/ldap/sdap_async_users.c +++ b/src/providers/ldap/sdap_async_users.c @@ -433,6 +433,7 @@ struct sdap_get_users_state { const char *base_filter; char *filter; int timeout; + bool enumeration; char *higher_usn; struct sysdb_attrs **users; @@ -454,7 +455,8 @@ struct tevent_req *sdap_get_users_send(TALLOC_CTX *memctx, struct sdap_handle *sh, const char **attrs, const char *filter, - int timeout) + int timeout, + bool enumeration) { errno_t ret; struct tevent_req *req; @@ -476,6 +478,7 @@ struct tevent_req *sdap_get_users_send(TALLOC_CTX *memctx, state->base_filter = filter; state->base_iter = 0; state->search_bases = search_bases; + state->enumeration = enumeration; ret = sdap_get_users_next_base(req); if (ret != EOK) { @@ -527,19 +530,49 @@ static void sdap_get_users_process(struct tevent_req *subreq) struct sdap_get_users_state *state = tevent_req_data(req, struct sdap_get_users_state); int ret; + size_t count, i; + struct sysdb_attrs **users; + bool next_base = false; ret = sdap_get_generic_recv(subreq, state, - &state->count, &state->users); + &count, &users); talloc_zfree(subreq); if (ret) { tevent_req_error(req, ret); return; } - DEBUG(6, ("Search for users, returned %d results.\n", state->count)); + DEBUG(6, ("Search for users, returned %d results.\n", count)); - if (state->count == 0) { - /* No users found in this search */ + if (state->enumeration || count == 0) { + /* No users found in this search or enumerating */ + next_base = true; + } + + /* Add this batch of users to the list */ + if (count > 0) { + state->users = + talloc_realloc(state, + state->users, + struct sysdb_attrs *, + state->count + count + 1); + if (!state->users) { + tevent_req_error(req, ENOMEM); + return; + } + + /* Copy the new users into the list + * They're already allocated on 'state' + */ + for (i = 0; i < count; i++) { + state->users[state->count + i] = users[i]; + } + + state->count += count; + state->users[state->count] = NULL; + } + + if (next_base) { state->base_iter++; if (state->search_bases[state->base_iter]) { /* There are more search bases to try */ @@ -549,7 +582,12 @@ static void sdap_get_users_process(struct tevent_req *subreq) } return; } + } + /* No more search bases + * Return ENOENT if no users were found + */ + if (state->count == 0) { tevent_req_error(req, ENOENT); return; } -- cgit