summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorJakub Hrozek <jhrozek@redhat.com>2012-03-05 13:04:53 +0100
committerStephen Gallagher <sgallagh@redhat.com>2012-03-09 14:32:36 -0500
commitcd9b250a556f793ec98f4a3744d3a0cef40a1b69 (patch)
treea73b7ae9a96e2c64c0241a31a01d6a4f633f144c
parent0bc2ac6e0648068444145925f2d69e35f88ac857 (diff)
downloadsssd-cd9b250a556f793ec98f4a3744d3a0cef40a1b69.tar.gz
sssd-cd9b250a556f793ec98f4a3744d3a0cef40a1b69.tar.xz
sssd-cd9b250a556f793ec98f4a3744d3a0cef40a1b69.zip
Fix nested groups processing
Instead of keeping the number of parent groups in "state" and having to reset the count when moving to another group on the same level, keep track of the all groups on a particular level along with their parents and parent count.
-rw-r--r--src/providers/ldap/sdap_async_initgroups.c88
1 files changed, 61 insertions, 27 deletions
diff --git a/src/providers/ldap/sdap_async_initgroups.c b/src/providers/ldap/sdap_async_initgroups.c
index 1e2e6178d..b0b533242 100644
--- a/src/providers/ldap/sdap_async_initgroups.c
+++ b/src/providers/ldap/sdap_async_initgroups.c
@@ -1544,6 +1544,8 @@ static void sdap_initgr_rfc2307bis_process(struct tevent_req *subreq)
tevent_req_error(req, ret);
return;
}
+ DEBUG(SSSDBG_TRACE_LIBS,
+ ("Found %d parent groups for user [%s]\n", count, state->name));
/* Add this batch of groups to the list */
if (count > 0) {
@@ -1975,8 +1977,7 @@ struct sdap_rfc2307bis_nested_ctx {
size_t nesting_level;
size_t group_iter;
- struct sysdb_attrs **ldap_parents;
- size_t parents_count;
+ struct sdap_nested_group **processed_groups;
hash_table_t *group_hash;
const char *primary_name;
@@ -1999,6 +2000,9 @@ struct tevent_req *rfc2307bis_nested_groups_send(
struct tevent_req *req;
struct sdap_rfc2307bis_nested_ctx *state;
+ DEBUG(SSSDBG_TRACE_INTERNAL,
+ ("About to process %d groups in nesting level %d\n", num_groups, nesting));
+
req = tevent_req_create(mem_ctx, &state,
struct sdap_rfc2307bis_nested_ctx);
if (!req) return NULL;
@@ -2034,6 +2038,14 @@ struct tevent_req *rfc2307bis_nested_groups_send(
goto done;
}
+ state->processed_groups = talloc_array(state,
+ struct sdap_nested_group *,
+ state->num_groups);
+ if (state->processed_groups == NULL) {
+ ret = ENOMEM;
+ goto done;
+ }
+
ret = rfc2307bis_nested_groups_step(req);
done:
@@ -2058,6 +2070,7 @@ static errno_t rfc2307bis_nested_groups_step(struct tevent_req *req)
TALLOC_CTX *tmp_ctx = NULL;
char *clean_orig_dn;
hash_key_t key;
+ hash_value_t value;
struct sdap_rfc2307bis_nested_ctx *state =
tevent_req_data(req, struct sdap_rfc2307bis_nested_ctx);
@@ -2083,14 +2096,33 @@ static errno_t rfc2307bis_nested_groups_step(struct tevent_req *req)
goto done;
}
- DEBUG(6, ("Processing group [%s]\n", state->primary_name));
+ DEBUG(SSSDBG_TRACE_LIBS, ("Processing group [%s]\n", state->primary_name));
- if (hash_has_key(state->group_hash, &key)) {
+ ret = hash_lookup(state->group_hash, &key, &value);
+ if (ret == HASH_SUCCESS) {
+ DEBUG(SSSDBG_TRACE_INTERNAL, ("Group [%s] was already processed, "
+ "taking a shortcut\n", state->primary_name));
+ state->processed_groups[state->group_iter] =
+ talloc_get_type(value.ptr, struct sdap_nested_group);
talloc_free(key.str);
ret = EOK;
goto done;
}
+ /* Need to try to find parent groups for this group. */
+ state->processed_groups[state->group_iter] =
+ talloc_zero(state->processed_groups, struct sdap_nested_group);
+ if (!state->processed_groups[state->group_iter]) {
+ ret = ENOMEM;
+ goto done;
+ }
+
+ /* this steal doesn't change much now, but will be helpful later on
+ * if we steal the whole processed_group on the hash table */
+ state->processed_groups[state->group_iter]->group =
+ talloc_steal(state->processed_groups[state->group_iter],
+ state->groups[state->group_iter]);
+
/* Get any parent groups for this group */
ret = sysdb_attrs_get_string(state->groups[state->group_iter],
SYSDB_ORIG_DN,
@@ -2196,15 +2228,19 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
return;
}
+ DEBUG(SSSDBG_TRACE_LIBS,
+ ("Found %d parent groups of [%s]\n", count, state->orig_dn));
+ ngr = state->processed_groups[state->group_iter];
+
/* Add this batch of groups to the list */
if (count > 0) {
- state->ldap_parents =
- talloc_realloc(state,
- state->ldap_parents,
+ ngr->ldap_parents =
+ talloc_realloc(ngr,
+ ngr->ldap_parents,
struct sysdb_attrs *,
- state->parents_count + count + 1);
- if (!state->ldap_parents) {
- tevent_req_error(req, ret);
+ ngr->parents_count + count + 1);
+ if (!ngr->ldap_parents) {
+ tevent_req_error(req, ENOMEM);
return;
}
@@ -2214,13 +2250,16 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
* we finish this nesting level.
*/
for (i = 0; i < count; i++) {
- state->ldap_parents[state->parents_count + i] =
- talloc_steal(state->ldap_parents, ldap_groups[i]);
+ ngr->ldap_parents[ngr->parents_count + i] =
+ talloc_steal(ngr->ldap_parents, ldap_groups[i]);
}
- state->parents_count += count;
+ ngr->parents_count += count;
- state->ldap_parents[state->parents_count] = NULL;
+ ngr->ldap_parents[ngr->parents_count] = NULL;
+ DEBUG(SSSDBG_TRACE_INTERNAL,
+ ("Total of %d direct parents after this iteration\n",
+ ngr->parents_count));
}
state->base_iter++;
@@ -2239,16 +2278,7 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
/* Reset the base iterator for future lookups */
state->base_iter = 0;
- ngr = talloc_zero(state->group_hash, struct sdap_nested_group);
- if (!ngr) {
- tevent_req_error(req, ENOMEM);
- return;
- }
-
- ngr->group = talloc_steal(ngr, state->groups[state->group_iter]);
- ngr->ldap_parents = talloc_steal(ngr, state->ldap_parents);
- ngr->parents_count = state->parents_count;
-
+ /* Save the group into the hash table */
key.type = HASH_KEY_STRING;
key.str = talloc_strdup(state, state->primary_name);
if (!key.str) {
@@ -2256,6 +2286,10 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
return;
}
+ /* Steal the nested group entry on the group_hash context so it can
+ * outlive this request */
+ talloc_steal(state->group_hash, ngr);
+
value.type = HASH_VALUE_PTR;
value.ptr = ngr;
@@ -2267,7 +2301,7 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
}
talloc_free(key.str);
- if (state->parents_count == 0) {
+ if (ngr->parents_count == 0) {
/* No parent groups for this group in LDAP
* Move on to the next group
*/
@@ -2298,8 +2332,8 @@ static void rfc2307bis_nested_groups_process(struct tevent_req *subreq)
subreq = rfc2307bis_nested_groups_send(
state, state->ev, state->opts, state->sysdb,
state->dom, state->sh,
- state->ldap_parents,
- state->parents_count,
+ ngr->ldap_parents,
+ ngr->parents_count,
state->group_hash,
state->nesting_level+1);
if (!subreq) {