From c84fe85f9e2f778c6575afb9efeda970aabf400c Mon Sep 17 00:00:00 2001 From: Simo Sorce Date: Wed, 18 Nov 2009 12:05:27 -0500 Subject: Filter by id range before actually storing entries. This way we do not need to check for id ranges on every search. --- server/providers/ldap/sdap_async_accounts.c | 24 +++++++++ server/providers/proxy.c | 77 +++++++++++++++++++++++------ server/responder/nss/nsssrv_cmd.c | 16 ------ server/util/util.h | 3 ++ 4 files changed, 89 insertions(+), 31 deletions(-) (limited to 'server') diff --git a/server/providers/ldap/sdap_async_accounts.c b/server/providers/ldap/sdap_async_accounts.c index 292c85f0d..07e165f0d 100644 --- a/server/providers/ldap/sdap_async_accounts.c +++ b/server/providers/ldap/sdap_async_accounts.c @@ -128,6 +128,14 @@ static struct tevent_req *sdap_save_user_send(TALLOC_CTX *memctx, } uid = l; + /* check that the uid is valid for this domain */ + if (OUT_OF_ID_RANGE(uid, dom->id_min, dom->id_max)) { + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->name)); + ret = EINVAL; + goto fail; + } + ret = sysdb_attrs_get_el(state->attrs, opts->user_map[SDAP_AT_USER_GID].sys_name, &el); if (ret) goto fail; @@ -145,6 +153,14 @@ static struct tevent_req *sdap_save_user_send(TALLOC_CTX *memctx, } gid = l; + /* check that the gid is valid for this domain */ + if (OUT_OF_ID_RANGE(gid, dom->id_min, dom->id_max)) { + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->name)); + ret = EINVAL; + goto fail; + } + user_attrs = sysdb_new_attrs(state); if (user_attrs == NULL) { ret = ENOMEM; @@ -903,6 +919,14 @@ static struct tevent_req *sdap_save_group_send(TALLOC_CTX *memctx, } gid = l; + /* check that the gid is valid for this domain */ + if (OUT_OF_ID_RANGE(gid, dom->id_min, dom->id_max)) { + DEBUG(2, ("Group [%s] filtered out! (id out of range)\n", + state->name)); + ret = EINVAL; + goto fail; + } + group_attrs = sysdb_new_attrs(state); if (!group_attrs) { ret = ENOMEM; diff --git a/server/providers/proxy.c b/server/providers/proxy.c index 0a3734484..fbd8f1623 100644 --- a/server/providers/proxy.c +++ b/server/providers/proxy.c @@ -369,6 +369,7 @@ static void get_pw_name_process(struct tevent_req *subreq) struct proxy_state *state = tevent_req_data(req, struct proxy_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; size_t buflen; @@ -416,7 +417,12 @@ static void get_pw_name_process(struct tevent_req *subreq) state->pwd->pw_uid, state->pwd->pw_gid)); /* uid=0 or gid=0 are invalid values */ - if (state->pwd->pw_uid == 0 || state->pwd->pw_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->pwd->pw_uid, dom->id_min, dom->id_max) || + OUT_OF_ID_RANGE(state->pwd->pw_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->name)); delete_user = true; break; } @@ -561,6 +567,7 @@ static void get_pw_uid_process(struct tevent_req *subreq) struct proxy_state *state = tevent_req_data(req, struct proxy_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; size_t buflen; @@ -609,7 +616,12 @@ static void get_pw_uid_process(struct tevent_req *subreq) state->pwd->pw_uid, state->pwd->pw_gid)); /* uid=0 or gid=0 are invalid values */ - if (state->pwd->pw_uid == 0 || state->pwd->pw_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->pwd->pw_uid, dom->id_min, dom->id_max) || + OUT_OF_ID_RANGE(state->pwd->pw_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->name)); delete_user = true; break; } @@ -764,6 +776,7 @@ static void enum_users_process(struct tevent_req *subreq) struct enum_users_state *state = tevent_req_data(req, struct enum_users_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *newbuf; int ret; @@ -832,7 +845,13 @@ again: state->pwd->pw_uid, state->pwd->pw_gid)); /* uid=0 or gid=0 are invalid values */ - if (state->pwd->pw_uid == 0 || state->pwd->pw_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->pwd->pw_uid, dom->id_min, dom->id_max) || + OUT_OF_ID_RANGE(state->pwd->pw_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->pwd->pw_name)); + goto again; /* skip */ } @@ -931,6 +950,7 @@ static void get_gr_name_process(struct tevent_req *subreq) struct proxy_state *state = tevent_req_data(req, struct proxy_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; char *newbuf; @@ -999,7 +1019,11 @@ again: state->grp->gr_name, state->grp->gr_gid)); /* gid=0 is an invalid value */ - if (state->grp->gr_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->grp->gr_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("Group [%s] filtered out! (id out of range)\n", + state->name)); delete_group = true; break; } @@ -1148,6 +1172,7 @@ static void get_gr_gid_process(struct tevent_req *subreq) struct proxy_state *state = tevent_req_data(req, struct proxy_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; char *newbuf; @@ -1214,7 +1239,11 @@ again: state->grp->gr_name, state->grp->gr_gid)); /* gid=0 is an invalid value */ - if (state->grp->gr_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->grp->gr_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("Group [%s] filtered out! (id out of range)\n", + state->grp->gr_name)); delete_group = true; break; } @@ -1374,6 +1403,7 @@ static void enum_groups_process(struct tevent_req *subreq) struct enum_groups_state *state = tevent_req_data(req, struct enum_groups_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; const char **members; char *newbuf; @@ -1439,14 +1469,20 @@ again: return; case NSS_STATUS_SUCCESS: - /* gid=0 is an invalid value */ - if (state->grp->gr_gid == 0) { - goto again; /* skip */ - } DEBUG(7, ("Group found (%s, %d)\n", state->grp->gr_name, state->grp->gr_gid)); + /* gid=0 is an invalid value */ + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->grp->gr_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("Group [%s] filtered out! (id out of range)\n", + state->grp->gr_name)); + + goto again; /* skip */ + } + DEBUG_GR_MEM(7, state); if (state->grp->gr_mem && state->grp->gr_mem[0]) { @@ -1547,6 +1583,7 @@ static void get_initgr_process(struct tevent_req *subreq) struct proxy_state *state = tevent_req_data(req, struct proxy_state); struct proxy_ctx *ctx = state->ctx; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; size_t buflen; @@ -1587,7 +1624,12 @@ static void get_initgr_process(struct tevent_req *subreq) case NSS_STATUS_SUCCESS: /* uid=0 or gid=0 are invalid values */ - if (state->pwd->pw_uid == 0 || state->pwd->pw_gid == 0) { + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->pwd->pw_uid, dom->id_min, dom->id_max) || + OUT_OF_ID_RANGE(state->pwd->pw_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("User [%s] filtered out! (id out of range)\n", + state->name)); delete_user = true; break; } @@ -1833,11 +1875,12 @@ static struct tevent_req *get_group_from_gid_send(TALLOC_CTX *mem_ctx, { struct tevent_req *req, *subreq; struct proxy_state *state; + struct sss_domain_info *dom = ctx->be->domain; enum nss_status status; char *buffer; char *newbuf; size_t buflen; - bool delete_user = false; + bool delete_group = false; int ret; req = tevent_req_create(mem_ctx, &state, struct proxy_state); @@ -1890,14 +1933,18 @@ again: case NSS_STATUS_NOTFOUND: - delete_user = true; + delete_group = true; break; case NSS_STATUS_SUCCESS: /* gid=0 is an invalid value */ - if (state->grp->gr_gid == 0) { - delete_user = true; + /* also check that the id is in the valid range for this domain */ + if (OUT_OF_ID_RANGE(state->grp->gr_gid, dom->id_min, dom->id_max)) { + + DEBUG(2, ("Group [%s] filtered out! (id out of range)\n", + state->grp->gr_name)); + delete_group = true; break; } @@ -1927,7 +1974,7 @@ again: goto fail; } - if (delete_user) { + if (delete_group) { subreq = sysdb_delete_group_send(state, state->ev, NULL, state->handle, state->domain, diff --git a/server/responder/nss/nsssrv_cmd.c b/server/responder/nss/nsssrv_cmd.c index 2466ae718..4473e6c8f 100644 --- a/server/responder/nss/nsssrv_cmd.c +++ b/server/responder/nss/nsssrv_cmd.c @@ -174,14 +174,6 @@ static int fill_pwent(struct sss_packet *packet, } } - /* check that the uid is valid for this domain */ - if ((dom->id_min && (uid < dom->id_min)) || - (dom->id_max && (uid > dom->id_max))) { - DEBUG(4, ("User [%s@%s] filtered out! (id out of range)\n", - name, domain)); - continue; - } - if (!packet_initialized) { /* first 2 fields (len and reserved), filled up later */ ret = sss_packet_grow(packet, 2*sizeof(uint32_t)); @@ -1555,14 +1547,6 @@ static int fill_grent(struct sss_packet *packet, } } - /* check that the gid is valid for this domain */ - if ((dom->id_min && (gid < dom->id_min)) || - (dom->id_max && (gid > dom->id_max))) { - DEBUG(4, ("Group [%s@%s] filtered out! (id out of range)\n", - name, domain)); - continue; - } - nsize = strlen(name) + 1; /* includes terminating \0 */ if (add_domain) nsize += delim + dom_len; diff --git a/server/util/util.h b/server/util/util.h index 661bcebb9..3ca43a409 100644 --- a/server/util/util.h +++ b/server/util/util.h @@ -152,6 +152,9 @@ errno_t set_debug_file_from_fd(const int fd); } \ } while (0) +#define OUT_OF_ID_RANGE(id, min, max) \ + (id == 0 || (min && (id < min)) || (max && (id > max))) + #include "util/dlinklist.h" /* From debug.c */ -- cgit