diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/db/sysdb.h | 17 | ||||
-rw-r--r-- | src/db/sysdb_search.c | 126 | ||||
-rw-r--r-- | src/responder/nss/nsssrv_netgroup.c | 138 | ||||
-rw-r--r-- | src/responder/nss/nsssrv_private.h | 2 | ||||
-rw-r--r-- | src/tests/sysdb-tests.c | 88 |
5 files changed, 212 insertions, 159 deletions
diff --git a/src/db/sysdb.h b/src/db/sysdb.h index 561d37ba..a1d6c912 100644 --- a/src/db/sysdb.h +++ b/src/db/sysdb.h @@ -302,10 +302,17 @@ int sysdb_enumgrent(TALLOC_CTX *mem_ctx, struct ldb_result **res); struct sysdb_netgroup_ctx { - char *hostname; - char *username; - char *domainname; + enum {SYSDB_NETGROUP_TRIPLE_VAL, SYSDB_NETGROUP_GROUP_VAL} type; + union { + struct { + char *hostname; + char *username; + char *domainname; + } triple; + char *groupname; + } value; }; + errno_t sysdb_getnetgr(TALLOC_CTX *mem_ctx, struct sysdb_ctx *ctx, struct sss_domain_info *domain, @@ -665,8 +672,8 @@ errno_t sysdb_attrs_to_list(TALLOC_CTX *memctx, const char *attr_name, char ***_list); -errno_t sysdb_netgr_to_triples(TALLOC_CTX *mem_ctx, +errno_t sysdb_netgr_to_entries(TALLOC_CTX *mem_ctx, struct ldb_result *res, - struct sysdb_netgroup_ctx ***triples); + struct sysdb_netgroup_ctx ***entries); #endif /* __SYS_DB_H__ */ diff --git a/src/db/sysdb_search.c b/src/db/sysdb_search.c index 91519e3a..e983b395 100644 --- a/src/db/sysdb_search.c +++ b/src/db/sysdb_search.c @@ -650,15 +650,16 @@ done: return ret; } -errno_t sysdb_netgr_to_triples(TALLOC_CTX *mem_ctx, +errno_t sysdb_netgr_to_entries(TALLOC_CTX *mem_ctx, struct ldb_result *res, - struct sysdb_netgroup_ctx ***triples) + struct sysdb_netgroup_ctx ***entries) { errno_t ret; size_t size = 0; + size_t c = 0; char *triple_str; TALLOC_CTX *tmp_ctx; - struct sysdb_netgroup_ctx **tmp_triples = NULL; + struct sysdb_netgroup_ctx **tmp_entry = NULL; struct ldb_message_element *el; int i, j; @@ -673,69 +674,84 @@ errno_t sysdb_netgr_to_triples(TALLOC_CTX *mem_ctx, for (i=0; i < res->count; i++) { el = ldb_msg_find_element(res->msgs[i], SYSDB_NETGROUP_TRIPLE); - if (!el) { - /* No triples in this netgroup. It might be a nesting - * container only. - * Skip it and continue on. - */ - continue; + if (el != NULL) { + size += el->num_values; } - - /* Enlarge the array by the value count - * Always keep one extra entry for the NULL terminator - */ - tmp_triples = talloc_realloc(tmp_ctx, tmp_triples, - struct sysdb_netgroup_ctx *, - size+el->num_values+1); - if (!tmp_triples) { - ret = ENOMEM; - goto done; + el = ldb_msg_find_element(res->msgs[i], SYSDB_NETGROUP_MEMBER); + if (el != NULL) { + size += el->num_values; } + } - /* Copy in all of the triples */ - for(j = 0; j < el->num_values; j++) { - triple_str = talloc_strndup(tmp_ctx, - (const char *)el->values[j].data, - el->values[j].length); - if (!triple_str) { - ret = ENOMEM; - goto done; - } + tmp_entry = talloc_array(tmp_ctx, struct sysdb_netgroup_ctx *, size + 1); + if (tmp_entry == NULL) { + ret = ENOMEM; + goto done; + } - tmp_triples[size] = talloc_zero(tmp_triples, - struct sysdb_netgroup_ctx); - if (!tmp_triples[size]) { - ret = ENOMEM; - goto done; + if (size != 0) { + for (i=0; i < res->count; i++) { + el = ldb_msg_find_element(res->msgs[i], SYSDB_NETGROUP_TRIPLE); + if (el != NULL) { + /* Copy in all of the entries */ + for(j = 0; j < el->num_values; j++) { + triple_str = talloc_strndup(tmp_ctx, + (const char *)el->values[j].data, + el->values[j].length); + if (!triple_str) { + ret = ENOMEM; + goto done; + } + + tmp_entry[c] = talloc_zero(tmp_entry, + struct sysdb_netgroup_ctx); + if (!tmp_entry[c]) { + ret = ENOMEM; + goto done; + } + + tmp_entry[c]->type = SYSDB_NETGROUP_TRIPLE_VAL; + ret = sysdb_netgr_split_triple(tmp_entry[c], + triple_str, + &tmp_entry[c]->value.triple.hostname, + &tmp_entry[c]->value.triple.username, + &tmp_entry[c]->value.triple.domainname); + if (ret != EOK) { + goto done; + } + + c++; + } } - - ret = sysdb_netgr_split_triple(tmp_triples[size], - triple_str, - &tmp_triples[size]->hostname, - &tmp_triples[size]->username, - &tmp_triples[size]->domainname); - if (ret != EOK) { - goto done; + el = ldb_msg_find_element(res->msgs[i], SYSDB_NETGROUP_MEMBER); + if (el != NULL) { + for(j = 0; j < el->num_values; j++) { + tmp_entry[c] = talloc_zero(tmp_entry, + struct sysdb_netgroup_ctx); + if (!tmp_entry[c]) { + ret = ENOMEM; + goto done; + } + + tmp_entry[c]->type = SYSDB_NETGROUP_GROUP_VAL; + tmp_entry[c]->value.groupname = talloc_strndup(tmp_entry[c], + (const char *)el->values[j].data, + el->values[j].length); + if (tmp_entry[c]->value.groupname == NULL) { + ret = ENOMEM; + goto done; + } + + c++; + } } - - size++; } } - if (!tmp_triples) { - /* No entries were found - * Create a dummy reply - */ - tmp_triples = talloc_array(tmp_ctx, struct sysdb_netgroup_ctx *, 1); - if (!tmp_triples) { - ret = ENOMEM; - goto done; - } - } /* Add NULL terminator */ - tmp_triples[size] = NULL; + tmp_entry[c] = NULL; - *triples = talloc_steal(mem_ctx, tmp_triples); + *entries = talloc_steal(mem_ctx, tmp_entry); ret = EOK; done: diff --git a/src/responder/nss/nsssrv_netgroup.c b/src/responder/nss/nsssrv_netgroup.c index 706a660c..feda556f 100644 --- a/src/responder/nss/nsssrv_netgroup.c +++ b/src/responder/nss/nsssrv_netgroup.c @@ -401,9 +401,9 @@ static errno_t lookup_netgr_step(struct setent_step_ctx *step_ctx) return ret; } - /* Convert the result to a list of triples */ - ret = sysdb_netgr_to_triples(netgr, step_ctx->dctx->res, - &netgr->triples); + /* Convert the result to a list of entries */ + ret = sysdb_netgr_to_entries(netgr, step_ctx->dctx->res, + &netgr->entries); if (ret == ENOENT) { /* This netgroup was not found in this domain */ if (!step_ctx->dctx->check_provider) { @@ -417,7 +417,7 @@ static errno_t lookup_netgr_step(struct setent_step_ctx *step_ctx) } if (ret != EOK) { - DEBUG(1, ("Failed to convert results into triples\n")); + DEBUG(1, ("Failed to convert results into entries\n")); return EIO; } @@ -465,7 +465,7 @@ static errno_t lookup_netgr_step(struct setent_step_ctx *step_ctx) DEBUG(2, ("No matching domain found for [%s], fail!\n", step_ctx->name)); netgr->ready = true; - netgr->triples = NULL; + netgr->entries = NULL; return ENOENT; } @@ -714,7 +714,7 @@ static void setnetgrent_implicit_done(struct tevent_req *req) } static errno_t nss_cmd_retnetgrent(struct cli_ctx *client, - struct sysdb_netgroup_ctx **triples, + struct sysdb_netgroup_ctx **entries, int num); static errno_t nss_cmd_getnetgrent_process(struct nss_cmd_ctx *cmdctx, struct getent_ctx *netgr) @@ -740,9 +740,9 @@ static errno_t nss_cmd_getnetgrent_process(struct nss_cmd_ctx *cmdctx, return ret; } - if (!netgr->triples || netgr->triples[0] == NULL) { + if (!netgr->entries || netgr->entries[0] == NULL) { /* No entries */ - DEBUG(5, ("No triples found\n")); + DEBUG(5, ("No entries found\n")); ret = fill_empty(client->creq->out); if (ret != EOK) { return nss_cmd_done(cmdctx, ret); @@ -750,7 +750,7 @@ static errno_t nss_cmd_getnetgrent_process(struct nss_cmd_ctx *cmdctx, goto done; } - ret = nss_cmd_retnetgrent(client, netgr->triples, num); + ret = nss_cmd_retnetgrent(client, netgr->entries, num); done: sss_packet_set_error(client->creq->out, ret); @@ -760,13 +760,14 @@ done: } static errno_t nss_cmd_retnetgrent(struct cli_ctx *client, - struct sysdb_netgroup_ctx **triples, + struct sysdb_netgroup_ctx **entries, int count) { size_t len; size_t hostlen = 0; size_t userlen = 0; size_t domainlen = 0; + size_t grouplen = 0; uint8_t *body; size_t blen, rp; errno_t ret; @@ -780,59 +781,88 @@ static errno_t nss_cmd_retnetgrent(struct cli_ctx *client, start = client->netgrent_cur; num = 0; - while (triples[client->netgrent_cur] && - (client->netgrent_cur - start) < count) { - hostlen = 1; - if (triples[client->netgrent_cur]->hostname) { - hostlen += strlen(triples[client->netgrent_cur]->hostname); - } + while (entries[client->netgrent_cur] && + (client->netgrent_cur - start) < count) { + if (entries[client->netgrent_cur]->type == SYSDB_NETGROUP_TRIPLE_VAL) { + hostlen = 1; + if (entries[client->netgrent_cur]->value.triple.hostname) { + hostlen += strlen(entries[client->netgrent_cur]->value.triple.hostname); + } - userlen = 1; - if (triples[client->netgrent_cur]->username) { - userlen += strlen(triples[client->netgrent_cur]->username); - } + userlen = 1; + if (entries[client->netgrent_cur]->value.triple.username) { + userlen += strlen(entries[client->netgrent_cur]->value.triple.username); + } - domainlen = 1; - if (triples[client->netgrent_cur]->domainname) { - domainlen += strlen(triples[client->netgrent_cur]->domainname); - } + domainlen = 1; + if (entries[client->netgrent_cur]->value.triple.domainname) { + domainlen += strlen(entries[client->netgrent_cur]->value.triple.domainname); + } - len = 1 + hostlen + userlen + domainlen; - ret = sss_packet_grow(packet, len); - if (ret != EOK) { - return ret; - } - sss_packet_get_body(packet, &body, &blen); + len = sizeof(uint32_t) + hostlen + userlen + domainlen; + ret = sss_packet_grow(packet, len); + if (ret != EOK) { + return ret; + } + sss_packet_get_body(packet, &body, &blen); - body[rp] = SSS_NETGR_REP_TRIPLE; - rp++; + SAFEALIGN_SET_UINT32(&body[rp], SSS_NETGR_REP_TRIPLE, &rp); - if (hostlen == 1) { - body[rp] = '\0'; - } else { - memcpy(&body[rp], - triples[client->netgrent_cur]->hostname, - hostlen); - } - rp += hostlen; + if (hostlen == 1) { + body[rp] = '\0'; + } else { + memcpy(&body[rp], + entries[client->netgrent_cur]->value.triple.hostname, + hostlen); + } + rp += hostlen; + + if (userlen == 1) { + body[rp] = '\0'; + } else { + memcpy(&body[rp], + entries[client->netgrent_cur]->value.triple.username, + userlen); + } + rp += userlen; + + if (domainlen == 1) { + body[rp] = '\0'; + } else { + memcpy(&body[rp], + entries[client->netgrent_cur]->value.triple.domainname, + domainlen); + } + rp += domainlen; + } else if (entries[client->netgrent_cur]->type == SYSDB_NETGROUP_GROUP_VAL) { + if (entries[client->netgrent_cur]->value.groupname == NULL || + entries[client->netgrent_cur]->value.groupname[0] == '\0') { + DEBUG(1, ("Empty netgroup member. Please check your cache.\n")); + continue; + } - if (userlen == 1) { - body[rp] = '\0'; - } else { - memcpy(&body[rp], - triples[client->netgrent_cur]->username, - userlen); - } - rp += userlen; + grouplen = 1 + strlen(entries[client->netgrent_cur]->value.groupname); + + len = sizeof(uint32_t) + grouplen; + + ret = sss_packet_grow(packet, len); + if (ret != EOK) { + return ret; + } + + sss_packet_get_body(packet, &body, &blen); + + SAFEALIGN_SET_UINT32(&body[rp], SSS_NETGR_REP_GROUP, &rp); - if (domainlen == 1) { - body[rp] = '\0'; - } else { memcpy(&body[rp], - triples[client->netgrent_cur]->domainname, - domainlen); + entries[client->netgrent_cur]->value.groupname, + grouplen); + rp += grouplen; + } else { + DEBUG(1, ("Unexpected value type for netgroup entry. " + "Please check your cache.\n")); + continue; } - rp += domainlen; num++; client->netgrent_cur++; diff --git a/src/responder/nss/nsssrv_private.h b/src/responder/nss/nsssrv_private.h index 15cb6302..4d9f9476 100644 --- a/src/responder/nss/nsssrv_private.h +++ b/src/responder/nss/nsssrv_private.h @@ -61,7 +61,7 @@ struct getent_ctx { /* Netgroup-specific */ hash_table_t *lookup_table; - struct sysdb_netgroup_ctx **triples; + struct sysdb_netgroup_ctx **entries; char *name; char *domain; }; diff --git a/src/tests/sysdb-tests.c b/src/tests/sysdb-tests.c index d2e50bc4..51eda8fd 100644 --- a/src/tests/sysdb-tests.c +++ b/src/tests/sysdb-tests.c @@ -2424,7 +2424,7 @@ START_TEST(test_sysdb_add_netgroup_tuple) const char *username; const char *domainname; struct ldb_result *res; - struct sysdb_netgroup_ctx **triples; + struct sysdb_netgroup_ctx **entries; /* Setup */ ret = setup_sysdb_tests(&test_ctx); @@ -2455,23 +2455,23 @@ START_TEST(test_sysdb_add_netgroup_tuple) &res); fail_unless(ret == EOK, "Failed to retrieve netgr information"); - ret = sysdb_netgr_to_triples(test_ctx, res, &triples); - fail_unless(ret == EOK, "Failed to convert triples"); + ret = sysdb_netgr_to_entries(test_ctx, res, &entries); + fail_unless(ret == EOK, "Failed to convert entries"); - fail_unless(triples && triples[0] && !triples[1], + fail_unless(entries && entries[0] && !entries[1], "Got more than one triple back"); - fail_unless(strcmp(triples[0]->hostname, hostname) == 0, + fail_unless(strcmp(entries[0]->value.triple.hostname, hostname) == 0, "Got [%s], expected [%s] for hostname", - triples[0]->hostname, hostname); + entries[0]->value.triple.hostname, hostname); - fail_unless(strcmp(triples[0]->username, username) == 0, + fail_unless(strcmp(entries[0]->value.triple.username, username) == 0, "Got [%s], expected [%s] for username", - triples[0]->username, username); + entries[0]->value.triple.username, username); - fail_unless(strcmp(triples[0]->domainname, domainname) == 0, + fail_unless(strcmp(entries[0]->value.triple.domainname, domainname) == 0, "Got [%s], expected [%s] for domainname", - triples[0]->domainname, domainname); + entries[0]->value.triple.domainname, domainname); talloc_free(test_ctx); } @@ -2486,7 +2486,7 @@ START_TEST(test_sysdb_remove_netgroup_tuple) const char *username; const char *domainname; struct ldb_result *res; - struct sysdb_netgroup_ctx **triples; + struct sysdb_netgroup_ctx **entries; /* Setup */ ret = setup_sysdb_tests(&test_ctx); @@ -2517,10 +2517,10 @@ START_TEST(test_sysdb_remove_netgroup_tuple) &res); fail_unless(ret == EOK, "Failed to retrieve netgr information"); - ret = sysdb_netgr_to_triples(test_ctx, res, &triples); - fail_unless(ret == EOK, "Failed to convert triples"); + ret = sysdb_netgr_to_entries(test_ctx, res, &entries); + fail_unless(ret == EOK, "Failed to convert entries"); - fail_unless(triples && !triples[0],"Found triples unexpectedly"); + fail_unless(entries && !entries[0],"Found entries unexpectedly"); talloc_free(test_ctx); } @@ -2533,7 +2533,7 @@ START_TEST(test_sysdb_add_netgroup_member) const char *netgrname; const char *membername; struct ldb_result *res; - struct sysdb_netgroup_ctx **triples; + struct sysdb_netgroup_ctx **entries; char *hostname1; char *username1; @@ -2574,37 +2574,37 @@ START_TEST(test_sysdb_add_netgroup_member) &res); fail_unless(ret == EOK, "Failed to retrieve netgr information"); - ret = sysdb_netgr_to_triples(test_ctx, res, &triples); - fail_unless(ret == EOK, "Failed to convert triples"); + ret = sysdb_netgr_to_entries(test_ctx, res, &entries); + fail_unless(ret == EOK, "Failed to convert entries"); - fail_if(!triples, "Received a NULL triple"); - fail_if(!triples[0], "Did not get any responses"); - fail_unless(triples[0] && triples[1] && !triples[2], + fail_if(!entries, "Received a NULL triple"); + fail_if(!entries[0], "Did not get any responses"); + fail_unless(entries[0] && entries[1] && !entries[2], "Did not get exactly two responses"); - fail_unless(strcmp(triples[0]->hostname, hostname1) == 0, + fail_unless(strcmp(entries[0]->value.triple.hostname, hostname1) == 0, "Got [%s], expected [%s] for hostname", - triples[0]->hostname, hostname1); + entries[0]->value.triple.hostname, hostname1); - fail_unless(strcmp(triples[0]->username, username1) == 0, + fail_unless(strcmp(entries[0]->value.triple.username, username1) == 0, "Got [%s], expected [%s] for username", - triples[0]->username, username1); + entries[0]->value.triple.username, username1); - fail_unless(strcmp(triples[0]->domainname, domainname1) == 0, + fail_unless(strcmp(entries[0]->value.triple.domainname, domainname1) == 0, "Got [%s], expected [%s] for domainname", - triples[0]->domainname, domainname1); + entries[0]->value.triple.domainname, domainname1); - fail_unless(strcmp(triples[1]->hostname, hostname2) == 0, + fail_unless(strcmp(entries[1]->value.triple.hostname, hostname2) == 0, "Got [%s], expected [%s] for hostname", - triples[0]->hostname, hostname2); + entries[0]->value.triple.hostname, hostname2); - fail_unless(strcmp(triples[1]->username, username2) == 0, + fail_unless(strcmp(entries[1]->value.triple.username, username2) == 0, "Got [%s], expected [%s] for username", - triples[0]->username, username2); + entries[0]->value.triple.username, username2); - fail_unless(strcmp(triples[1]->domainname, domainname2) == 0, + fail_unless(strcmp(entries[1]->value.triple.domainname, domainname2) == 0, "Got [%s], expected [%s] for domainname", - triples[0]->domainname, domainname2); + entries[0]->value.triple.domainname, domainname2); talloc_free(test_ctx); } @@ -2617,7 +2617,7 @@ START_TEST(test_sysdb_remove_netgroup_member) const char *netgrname; const char *membername; struct ldb_result *res; - struct sysdb_netgroup_ctx **triples; + struct sysdb_netgroup_ctx **entries; char *hostname; char *username; @@ -2649,25 +2649,25 @@ START_TEST(test_sysdb_remove_netgroup_member) &res); fail_unless(ret == EOK, "Failed to retrieve netgr information"); - ret = sysdb_netgr_to_triples(test_ctx, res, &triples); - fail_unless(ret == EOK, "Failed to convert triples"); + ret = sysdb_netgr_to_entries(test_ctx, res, &entries); + fail_unless(ret == EOK, "Failed to convert entries"); - fail_if(!triples, "Received a NULL triple"); - fail_if(!triples[0], "Did not get any responses"); - fail_unless(triples[0] && !triples[1], + fail_if(!entries, "Received a NULL triple"); + fail_if(!entries[0], "Did not get any responses"); + fail_unless(entries[0] && !entries[1], "Did not get exactly one response"); - fail_unless(strcmp(triples[0]->hostname, hostname) == 0, + fail_unless(strcmp(entries[0]->value.triple.hostname, hostname) == 0, "Got [%s], expected [%s] for hostname", - triples[0]->hostname, hostname); + entries[0]->value.triple.hostname, hostname); - fail_unless(strcmp(triples[0]->username, username) == 0, + fail_unless(strcmp(entries[0]->value.triple.username, username) == 0, "Got [%s], expected [%s] for username", - triples[0]->username, username); + entries[0]->value.triple.username, username); - fail_unless(strcmp(triples[0]->domainname, domainname) == 0, + fail_unless(strcmp(entries[0]->value.triple.domainname, domainname) == 0, "Got [%s], expected [%s] for domainname", - triples[0]->domainname, domainname); + entries[0]->value.triple.domainname, domainname); talloc_free(test_ctx); } |