properly notify nscd to flush its cache

Peter Vrabec <[email protected]> Tue, 4 Apr 2006 08:51:19 +0200
Newsgroups gmane.linux.pld.shadow.general
Message-ID <[email protected]>
Hi Tomasz ,

shadow-utils doesn't properly notify nscd that it needs
to flush its cache.
shadow-4.0.14/lib/nscd.c has:
int nscd_flush_cache (char *service)
{
        int sock = nscd_open_socket ();
        request_header req;
        struct iovec iov[2];
        ssize_t nbytes;

        if (sock == -1)
                return -1;

        req.version = NSCD_VERSION;
        req.type = INVALIDATE;
        req.key_len = strlen (service);

        iov[0].iov_base = &req;
        iov[0].iov_len = sizeof (req);
        iov[1].iov_base = service;
        iov[1].iov_len = req.key_len;

        nbytes = writev (sock, iov, 2);

        close (sock);
        return (nbytes != iov[0].iov_len + iov[1].iov_len ? (-1) : 0);
}

which is wrong, the INVALIDATE request's key is supposed to contain the
trailing '\0' character and req.key_len is supposed to include that as
well. Compare that to what nscd does for nscd -i:
          if (strcmp (arg, "passwd") == 0)
            req.key_len = sizeof "passwd";
          else if (strcmp (arg, "group") == 0)
            req.key_len = sizeof "group";
          else if (strcmp (arg, "hosts") == 0)
            req.key_len = sizeof "hosts";
          else
            return ARGP_ERR_UNKNOWN;

          req.version = NSCD_VERSION;
          req.type = INVALIDATE;

So, shadow-utils needs to change the
req.key_len = strlen (service);
line in lib/nscd.c to:
req.key_len = strlen (service) + 1;



see: https://bugzilla.redhat.com/bugzilla/show_bug.cgi?id=186803
shadow-4.0.15-nscdFlushCache.patch (text/x-patch, 352 B)
--- shadow-4.0.15/lib/nscd.c.nscdFlushCash	2006-04-04 08:18:08.000000000 +0200
+++ shadow-4.0.15/lib/nscd.c	2006-04-04 08:18:30.000000000 +0200
@@ -87,7 +87,7 @@
 
 	req.version = NSCD_VERSION;
 	req.type = INVALIDATE;
-	req.key_len = strlen (service);
+	req.key_len = strlen (service) + 1;
 
 	iov[0].iov_base = &req;
 	iov[0].iov_len = sizeof (req);