Blame SOURCES/0044-NSS-Initgr-memory-cache-should-work-with-fq-names.patch

6cf099
From 5c5a094438ac6c81d99066ec58778cab23e0a939 Mon Sep 17 00:00:00 2001
6cf099
From: Lukas Slebodnik <lslebodn@redhat.com>
6cf099
Date: Mon, 13 Jul 2015 10:40:06 +0200
6cf099
Subject: [PATCH 44/47] NSS: Initgr memory cache should work with fq names
6cf099
MIME-Version: 1.0
6cf099
Content-Type: text/plain; charset=UTF-8
6cf099
Content-Transfer-Encoding: 8bit
6cf099
6cf099
We need to stored two versions of name to the initgroups memory cache.
6cf099
Otherwise it could be stored many times if sssd is configured with
6cf099
case_sensitive = false. It would be impossible to invalidate all
6cf099
version of names after user login. As a result of this wrong user
6cf099
groups could be returned from initgroups memory cache.
6cf099
6cf099
Therefore we store raw name provided by glibc function
6cf099
and internal sanitized fully qualified name,
6cf099
which is unique for particular user.
6cf099
6cf099
This patch also increase average space for initgroups
6cf099
because there are also stored two quite long names in case of
6cf099
fq names.
6cf099
6cf099
Resolves:
6cf099
https://fedorahosted.org/sssd/ticket/2712
6cf099
6cf099
Reviewed-by: Michal Židek <mzidek@redhat.com>
6cf099
(cherry picked from commit dda0258705de7255e6ec54b7f9adbde83a220996)
6cf099
---
6cf099
 src/responder/nss/nsssrv_cmd.c        | 30 +++++++++++++++++++++++++-----
6cf099
 src/responder/nss/nsssrv_mmap_cache.c | 32 +++++++++++++++++++++-----------
6cf099
 src/responder/nss/nsssrv_mmap_cache.h |  1 +
6cf099
 src/responder/nss/nsssrv_private.h    |  2 ++
6cf099
 src/util/mmap_cache.h                 |  7 ++++---
6cf099
 5 files changed, 53 insertions(+), 19 deletions(-)
6cf099
6cf099
diff --git a/src/responder/nss/nsssrv_cmd.c b/src/responder/nss/nsssrv_cmd.c
6cf099
index 0bfbf0eab115826ebde53b4cfcf6661f2f6328c7..aa64432d51f15ed17212b8c40eebf5c9322bc784 100644
6cf099
--- a/src/responder/nss/nsssrv_cmd.c
6cf099
+++ b/src/responder/nss/nsssrv_cmd.c
6cf099
@@ -1354,6 +1354,7 @@ static int nss_cmd_getbynam(enum sss_cli_command cmd, struct cli_ctx *cctx)
6cf099
     }
6cf099
 
6cf099
     rawname = (const char *)body;
6cf099
+    dctx->mc_name = rawname;
6cf099
 
6cf099
     DEBUG(SSSDBG_TRACE_FUNC, "Running command [%d] with input [%s].\n",
6cf099
                                dctx->cmdctx->cmd, rawname);
6cf099
@@ -3940,6 +3941,13 @@ void nss_update_initgr_memcache(struct nss_ctx *nctx,
6cf099
     }
6cf099
 
6cf099
     if (changed) {
6cf099
+        char *fq_name = sss_tc_fqname(tmp_ctx, dom->names, dom, name);
6cf099
+        if (!fq_name) {
6cf099
+            DEBUG(SSSDBG_CRIT_FAILURE,
6cf099
+                  "Could not create fq name\n");
6cf099
+            goto done;
6cf099
+        }
6cf099
+
6cf099
         for (i = 0; i < gnum; i++) {
6cf099
             id = groups[i];
6cf099
 
6cf099
@@ -3951,7 +3959,7 @@ void nss_update_initgr_memcache(struct nss_ctx *nctx,
6cf099
             }
6cf099
         }
6cf099
 
6cf099
-        to_sized_string(&delete_name, name);
6cf099
+        to_sized_string(&delete_name, fq_name);
6cf099
         ret = sss_mmap_cache_initgr_invalidate(nctx->initgr_mc_ctx,
6cf099
                                                &delete_name);
6cf099
         if (ret != EOK && ret != ENOENT) {
6cf099
@@ -3971,6 +3979,7 @@ static int fill_initgr(struct sss_packet *packet,
6cf099
                        struct sss_domain_info *dom,
6cf099
                        struct ldb_result *res,
6cf099
                        struct nss_ctx *nctx,
6cf099
+                       const char *mc_name,
6cf099
                        const char *name)
6cf099
 {
6cf099
     uint8_t *body;
6cf099
@@ -4059,9 +4068,18 @@ static int fill_initgr(struct sss_packet *packet,
6cf099
     }
6cf099
 
6cf099
     if (nctx->initgr_mc_ctx) {
6cf099
-        to_sized_string(&rawname, name);
6cf099
+        struct sized_string unique_name;
6cf099
+        char *fq_name = sss_tc_fqname(packet, dom->names, dom, name);
6cf099
+        if (!fq_name) {
6cf099
+            DEBUG(SSSDBG_CRIT_FAILURE,
6cf099
+                  "Could not create fq name\n");
6cf099
+            return ENOMEM;
6cf099
+        }
6cf099
+
6cf099
+        to_sized_string(&rawname, mc_name);
6cf099
+        to_sized_string(&unique_name, fq_name);
6cf099
         ret = sss_mmap_cache_initgr_store(&nctx->initgr_mc_ctx, &rawname,
6cf099
-                                          num - skipped, gids);
6cf099
+                                          &unique_name, num - skipped, gids);
6cf099
         if (ret != EOK && ret != ENOMEM) {
6cf099
             DEBUG(SSSDBG_CRIT_FAILURE,
6cf099
                   "Failed to store user %s(%s) in mmap cache!\n",
6cf099
@@ -4089,7 +4107,7 @@ static int nss_cmd_initgr_send_reply(struct nss_dom_ctx *dctx)
6cf099
     }
6cf099
 
6cf099
     ret = fill_initgr(cctx->creq->out, dctx->domain, dctx->res, nctx,
6cf099
-                      dctx->rawname);
6cf099
+                      dctx->mc_name, cmdctx->name);
6cf099
     if (ret) {
6cf099
         return ret;
6cf099
     }
6cf099
@@ -4137,8 +4155,10 @@ static int nss_cmd_initgroups_search(struct nss_dom_ctx *dctx)
6cf099
         name = sss_get_cased_name(dctx, cmdctx->name, dom->case_sensitive);
6cf099
         if (!name) return ENOMEM;
6cf099
 
6cf099
-        name = sss_reverse_replace_space(dctx, name,
6cf099
+        name = sss_reverse_replace_space(cmdctx, name,
6cf099
                                          nctx->rctx->override_space);
6cf099
+        /* save name so it can be used in initgr reply */
6cf099
+        cmdctx->name = name;
6cf099
         if (name == NULL) {
6cf099
             DEBUG(SSSDBG_CRIT_FAILURE,
6cf099
                   "sss_reverse_replace_space failed\n");
6cf099
diff --git a/src/responder/nss/nsssrv_mmap_cache.c b/src/responder/nss/nsssrv_mmap_cache.c
6cf099
index ab9e769b1f4d5d17a8c41429afce292298239bc5..62f4c543c628712810b6dfbc669c586c39ca609d 100644
6cf099
--- a/src/responder/nss/nsssrv_mmap_cache.c
6cf099
+++ b/src/responder/nss/nsssrv_mmap_cache.c
6cf099
@@ -31,8 +31,8 @@
6cf099
 #define SSS_AVG_PASSWD_PAYLOAD (MC_SLOT_SIZE * 4)
6cf099
 /* short group name and no gids (private user group */
6cf099
 #define SSS_AVG_GROUP_PAYLOAD (MC_SLOT_SIZE * 3)
6cf099
-/* average place for 40 supplementary groups */
6cf099
-#define SSS_AVG_INITGROUP_PAYLOAD (MC_SLOT_SIZE * 4)
6cf099
+/* average place for 40 supplementary groups + 2 names */
6cf099
+#define SSS_AVG_INITGROUP_PAYLOAD (MC_SLOT_SIZE * 5)
6cf099
 
6cf099
 #define MC_NEXT_BARRIER(val) ((((val) + 1) & 0x00ffffff) | 0xf0000000)
6cf099
 
6cf099
@@ -965,6 +965,7 @@ done:
6cf099
 
6cf099
 errno_t sss_mmap_cache_initgr_store(struct sss_mc_ctx **_mcc,
6cf099
                                     struct sized_string *name,
6cf099
+                                    struct sized_string *unique_name,
6cf099
                                     uint32_t num_groups,
6cf099
                                     uint8_t *gids_buf)
6cf099
 {
6cf099
@@ -973,6 +974,7 @@ errno_t sss_mmap_cache_initgr_store(struct sss_mc_ctx **_mcc,
6cf099
     struct sss_mc_initgr_data *data;
6cf099
     size_t data_len;
6cf099
     size_t rec_len;
6cf099
+    size_t pos;
6cf099
     int ret;
6cf099
 
6cf099
     if (mcc == NULL) {
6cf099
@@ -980,20 +982,22 @@ errno_t sss_mmap_cache_initgr_store(struct sss_mc_ctx **_mcc,
6cf099
         return EINVAL;
6cf099
     }
6cf099
 
6cf099
-    /* array of gids + name */
6cf099
-    data_len = num_groups * sizeof(uint32_t) + name->len;
6cf099
+    /* array of gids + name + unique_name */
6cf099
+    data_len = num_groups * sizeof(uint32_t) + name->len + unique_name->len;
6cf099
     rec_len = sizeof(struct sss_mc_rec) + sizeof(struct sss_mc_initgr_data)
6cf099
               + data_len;
6cf099
     if (rec_len > mcc->dt_size) {
6cf099
         return ENOMEM;
6cf099
     }
6cf099
 
6cf099
-    ret = sss_mc_get_record(_mcc, rec_len, name, &rec);
6cf099
+    /* use unique name for searching potential old records */
6cf099
+    ret = sss_mc_get_record(_mcc, rec_len, unique_name, &rec);
6cf099
     if (ret != EOK) {
6cf099
         return ret;
6cf099
     }
6cf099
 
6cf099
     data = (struct sss_mc_initgr_data *)rec->data;
6cf099
+    pos = 0;
6cf099
 
6cf099
     MC_RAISE_BARRIER(rec);
6cf099
 
6cf099
@@ -1001,16 +1005,22 @@ errno_t sss_mmap_cache_initgr_store(struct sss_mc_ctx **_mcc,
6cf099
      * Use the first key twice.
6cf099
      */
6cf099
     sss_mmap_set_rec_header(mcc, rec, rec_len, mcc->valid_time_slot,
6cf099
-                            name->str, name->len, name->str, name->len);
6cf099
+                            name->str, name->len,
6cf099
+                            unique_name->str, unique_name->len);
6cf099
 
6cf099
     /* initgroups struct */
6cf099
-    data->strs_len = name->len;
6cf099
+    data->strs_len = name->len + unique_name->len;
6cf099
     data->data_len = data_len;
6cf099
-    data->reserved = MC_INVALID_VAL32;
6cf099
     data->num_groups = num_groups;
6cf099
-    memcpy(data->gids, gids_buf, num_groups * sizeof(uint32_t));
6cf099
-    memcpy(&data->gids[num_groups], name->str, name->len);
6cf099
-    data->strs = data->name = MC_PTR_DIFF(&data->gids[num_groups], data);
6cf099
+    memcpy((char *)data->gids + pos, gids_buf, num_groups * sizeof(uint32_t));
6cf099
+    pos += num_groups * sizeof(uint32_t);
6cf099
+
6cf099
+    memcpy((char *)data->gids + pos, unique_name->str, unique_name->len);
6cf099
+    data->strs = data->unique_name = MC_PTR_DIFF((char *)data->gids + pos, data);
6cf099
+    pos += unique_name->len;
6cf099
+
6cf099
+    memcpy((char *)data->gids + pos, name->str, name->len);
6cf099
+    data->name = MC_PTR_DIFF((char *)data->gids + pos, data);
6cf099
 
6cf099
     MC_LOWER_BARRIER(rec);
6cf099
 
6cf099
diff --git a/src/responder/nss/nsssrv_mmap_cache.h b/src/responder/nss/nsssrv_mmap_cache.h
6cf099
index b09e4a6f8efa364ae7a6407bab9d8a2a2143c812..b84fbc8edef69db96c17a48a4862d63942297c66 100644
6cf099
--- a/src/responder/nss/nsssrv_mmap_cache.h
6cf099
+++ b/src/responder/nss/nsssrv_mmap_cache.h
6cf099
@@ -53,6 +53,7 @@ errno_t sss_mmap_cache_gr_store(struct sss_mc_ctx **_mcc,
6cf099
 
6cf099
 errno_t sss_mmap_cache_initgr_store(struct sss_mc_ctx **_mcc,
6cf099
                                     struct sized_string *name,
6cf099
+                                    struct sized_string *unique_name,
6cf099
                                     uint32_t num_groups,
6cf099
                                     uint8_t *gids_buf);
6cf099
 
6cf099
diff --git a/src/responder/nss/nsssrv_private.h b/src/responder/nss/nsssrv_private.h
6cf099
index e9f00b114975ef760aaaac45e6e91f6e40c52b9a..e5a2486f1fb9a8de39ec90f802f596b2c2f6af7f 100644
6cf099
--- a/src/responder/nss/nsssrv_private.h
6cf099
+++ b/src/responder/nss/nsssrv_private.h
6cf099
@@ -79,6 +79,8 @@ struct nss_dom_ctx {
6cf099
 
6cf099
     /* Service-specific */
6cf099
     const char *protocol;
6cf099
+
6cf099
+    const char *mc_name;
6cf099
 };
6cf099
 
6cf099
 struct setent_step_ctx {
6cf099
diff --git a/src/util/mmap_cache.h b/src/util/mmap_cache.h
6cf099
index b5917b3c0973276e43e9fe160cec7528b1224f8f..22c1ae62d1ff0c816c23bd8b26140990d692134c 100644
6cf099
--- a/src/util/mmap_cache.h
6cf099
+++ b/src/util/mmap_cache.h
6cf099
@@ -138,14 +138,15 @@ struct sss_mc_grp_data {
6cf099
 };
6cf099
 
6cf099
 struct sss_mc_initgr_data {
6cf099
-    rel_ptr_t name;         /* ptr to name string, rel. to struct base addr */
6cf099
+    rel_ptr_t unique_name;  /* ptr to unique name string, rel. to struct base addr */
6cf099
+    rel_ptr_t name;         /* ptr to raw name string, rel. to struct base addr */
6cf099
     rel_ptr_t strs;         /* ptr to concatenation of all strings */
6cf099
-    uint32_t reserved;
6cf099
     uint32_t strs_len;      /* length of strs */
6cf099
     uint32_t data_len;      /* all initgroups data len */
6cf099
     uint32_t num_groups;    /* number of groups */
6cf099
     uint32_t gids[0];       /* array of all groups
6cf099
-                             * string with name is stored after gids */
6cf099
+                             * string with name and unique_name is stored
6cf099
+                             * after gids */
6cf099
 };
6cf099
 
6cf099
 #pragma pack()
6cf099
-- 
6cf099
2.4.3
6cf099