tests: Add a basic test to check if the NSS module works
authorAndreas Schneider <asn@samba.org>
Thu, 2 Apr 2020 08:41:47 +0000 (10:41 +0200)
committerAndreas Schneider <asn@samba.org>
Thu, 2 Apr 2020 08:42:36 +0000 (10:42 +0200)
Signed-off-by: Andreas Schneider <asn@samba.org>
Reviewed-by: Samuel Cabrero <scabrero@suse.de>
tests/CMakeLists.txt
tests/nss_nwrap.c
tests/test_getpwuid_module.c [new file with mode: 0644]

index cdd8e0627ca5ec2f63e168cb8b7d063e8619a7f7..0d57a3f1e77868b0f1830fbb8e234292c2168291 100644 (file)
@@ -25,7 +25,8 @@ set(NWRAP_TESTS
     test_getaddrinfo
     test_getnameinfo
     test_gethostby_name_addr
-    test_gethostent)
+    test_gethostent
+    test_getpwuid_module)
 
 if (HAVE_SHADOW_H)
     list(APPEND NWRAP_TESTS test_shadow)
index 1e63dcee0f976ef2bd466467ecd6da3f46af25bb..62363a2e8665e6e7e22197c9c3237e93241e6f9d 100644 (file)
@@ -1,5 +1,10 @@
 #include "config.h"
 
+#include <errno.h>
+#include <fcntl.h>
+#include <stddef.h>
+#include <stdint.h>
+#include <string.h>
 #include <pwd.h>
 #include <grp.h>
 
@@ -44,6 +49,66 @@ NSS_STATUS _nss_nwrap_initgroups_dyn(char *user, gid_t group, long int *start,
                                     long int *size, gid_t **groups,
                                     long int limit, int *errnop);
 
+#ifndef PTR_DIFF
+#define PTR_DIFF(p1, p2) ((ptrdiff_t)(((const char *)(p1)) - (const char *)(p2)))
+#endif
+
+static int pw_copy_r(const struct passwd *src,
+                    struct passwd *dst,
+                    char *buf,
+                    size_t buflen,
+                    struct passwd **dstp)
+{
+       char *first;
+       char *last;
+       off_t ofs;
+
+       first = src->pw_name;
+
+       last = src->pw_shell;
+       while (*last) last++;
+
+       ofs = PTR_DIFF(last + 1, first);
+
+       if (ofs > (off_t) buflen) {
+               return ERANGE;
+       }
+
+       memcpy(buf, first, ofs);
+
+       ofs = PTR_DIFF(src->pw_name, first);
+       dst->pw_name = buf + ofs;
+       ofs = PTR_DIFF(src->pw_passwd, first);
+       dst->pw_passwd = buf + ofs;
+       dst->pw_uid = src->pw_uid;
+       dst->pw_gid = src->pw_gid;
+#ifdef HAVE_STRUCT_PASSWD_PW_CLASS
+       ofs = PTR_DIFF(src->pw_class, first);
+       dst->pw_class = buf + ofs;
+#endif /* HAVE_STRUCT_PASSWD_PW_CLASS */
+
+#ifdef HAVE_STRUCT_PASSWD_PW_CHANGE
+       dst->pw_change = 0;
+#endif /* HAVE_STRUCT_PASSWD_PW_CHANGE */
+
+#ifdef HAVE_STRUCT_PASSWD_PW_EXPIRE
+       dst->pw_expire = 0;
+#endif /* HAVE_STRUCT_PASSWD_PW_EXPIRE */
+
+       ofs = PTR_DIFF(src->pw_gecos, first);
+       dst->pw_gecos = buf + ofs;
+       ofs = PTR_DIFF(src->pw_dir, first);
+       dst->pw_dir = buf + ofs;
+       ofs = PTR_DIFF(src->pw_shell, first);
+       dst->pw_shell = buf + ofs;
+
+       if (dstp) {
+               *dstp = dst;
+       }
+
+       return 0;
+}
+
 NSS_STATUS _nss_nwrap_setpwent(void)
 {
        return NSS_STATUS_UNAVAIL;
@@ -68,11 +133,23 @@ NSS_STATUS _nss_nwrap_getpwent_r(struct passwd *result, char *buffer,
 NSS_STATUS _nss_nwrap_getpwuid_r(uid_t uid, struct passwd *result,
                                 char *buffer, size_t buflen, int *errnop)
 {
-       (void) uid;
-       (void) result;
-       (void) buffer;
-       (void) buflen;
-       (void) errnop;
+       if (uid == 424242) {
+               char buf[] = "hanswurst\0secret\0\0/home/hanswurst\0/bin/false";
+               const struct passwd src = {
+                       .pw_name   = &buf[0],
+                       .pw_passwd = &buf[10],
+                       .pw_uid    = 424242,
+                       .pw_gid    = 424242,
+                       .pw_gecos  = &buf[17],
+                       .pw_dir    = &buf[18],
+                       .pw_shell  = &buf[34],
+               };
+               memset(buffer, '\0', buflen);
+               pw_copy_r(&src, result, buffer, buflen, NULL);
+               errnop = 0;
+
+               return NSS_STATUS_SUCCESS;
+       }
 
        return NSS_STATUS_UNAVAIL;
 }
diff --git a/tests/test_getpwuid_module.c b/tests/test_getpwuid_module.c
new file mode 100644 (file)
index 0000000..2dbecb1
--- /dev/null
@@ -0,0 +1,36 @@
+#include "config.h"
+
+#include <stdarg.h>
+#include <stddef.h>
+#include <setjmp.h>
+#include <cmocka.h>
+
+#include <pwd.h>
+
+static void test_nwrap_passwd(void **state)
+{
+       struct passwd *pwd;
+       uid_t id = 424242;
+
+       (void) state; /* unused */
+
+       pwd = getpwuid(id);
+       assert_non_null(pwd);
+
+       assert_string_equal(pwd->pw_name, "hanswurst");
+       assert_int_equal(pwd->pw_uid, id);
+       assert_int_equal(pwd->pw_gid, id);
+}
+
+int main(void)
+{
+       int rc;
+
+       const struct CMUnitTest tests[] = {
+               cmocka_unit_test(test_nwrap_passwd),
+       };
+
+       rc = cmocka_run_group_tests(tests, NULL, NULL);
+
+       return rc;
+}