]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
Added i_getpw*() and i_getgr*() wrappers for getpw*()/getgr*().
authorTimo Sirainen <tss@iki.fi>
Thu, 17 Mar 2011 14:20:12 +0000 (16:20 +0200)
committerTimo Sirainen <tss@iki.fi>
Thu, 17 Mar 2011 14:20:12 +0000 (16:20 +0200)
These functions make error handling easier.

src/lib/Makefile.am
src/lib/ipwd.c [new file with mode: 0644]
src/lib/ipwd.h [new file with mode: 0644]

index c9afb6546396d8d5702965e0f32127f2f750b74e..6448d30969a13ddba81ccf82494f49bb83146379 100644 (file)
@@ -45,6 +45,7 @@ liblib_la_SOURCES = \
        home-expand.c \
        hostpid.c \
        imem.c \
+       ipwd.c \
        iostream.c \
        istream.c \
        istream-base64-encoder.c \
@@ -157,6 +158,7 @@ headers = \
        home-expand.h \
        hostpid.h \
        imem.h \
+       ipwd.h \
        iostream-internal.h \
        istream.h \
        istream-base64-encoder.h \
diff --git a/src/lib/ipwd.c b/src/lib/ipwd.c
new file mode 100644 (file)
index 0000000..ea432ac
--- /dev/null
@@ -0,0 +1,90 @@
+/* Copyright (c) 2011 Dovecot authors, see the included COPYING file */
+
+#include "lib.h"
+#include "ipwd.h"
+
+#include <unistd.h>
+
+#define DEFAULT_PWBUF_SIZE 16384
+#define DEFAULT_GRBUF_SIZE 16384
+
+static void *pwbuf = NULL, *grbuf = NULL;
+static size_t pwbuf_size, grbuf_size;
+
+static void pw_init(void)
+{
+       long size;
+
+       if (pwbuf == NULL) {
+               size = sysconf(_SC_GETPW_R_SIZE_MAX);
+               if (size < 0)
+                       size = DEFAULT_PWBUF_SIZE;
+
+               pwbuf_size = size;
+               pwbuf = i_malloc(pwbuf_size);
+       }
+}
+
+static void gr_init(void)
+{
+       long size;
+
+       if (grbuf == NULL) {
+               size = sysconf(_SC_GETGR_R_SIZE_MAX);
+               if (size < 0)
+                       size = DEFAULT_GRBUF_SIZE;
+
+               grbuf_size = size;
+               grbuf = i_malloc(grbuf_size);
+       }
+}
+
+void ipwd_deinit(void)
+{
+       i_free_and_null(pwbuf);
+       i_free_and_null(grbuf);
+}
+
+int i_getpwnam(const char *name, struct passwd *pwd_r)
+{
+       struct passwd *result;
+
+       pw_init();
+       errno = getpwnam_r(name, pwd_r, pwbuf, pwbuf_size, &result);
+       if (result != NULL)
+               return 1;
+       return errno == 0 ? 0 : -1;
+}
+
+int i_getpwuid(uid_t uid, struct passwd *pwd_r)
+{
+       struct passwd *result;
+
+       pw_init();
+       errno = getpwuid_r(uid, pwd_r, pwbuf, pwbuf_size, &result);
+       if (result != NULL)
+               return 1;
+       return errno == 0 ? 0 : -1;
+}
+
+int i_getgrnam(const char *name, struct group *grp_r)
+{
+       struct group *result;
+
+       gr_init();
+       errno = getgrnam_r(name, grp_r, grbuf, grbuf_size, &result);
+       if (result != NULL)
+               return 1;
+       return errno == 0 ? 0 : -1;
+}
+
+int i_getgrgid(gid_t gid, struct group *grp_r)
+{
+       struct group *result;
+
+       gr_init();
+       errno = getgrgid_r(gid, grp_r, grbuf, grbuf_size, &result);
+       if (result != NULL)
+               return 1;
+       return errno == 0 ? 0 : -1;
+}
diff --git a/src/lib/ipwd.h b/src/lib/ipwd.h
new file mode 100644 (file)
index 0000000..562ebb2
--- /dev/null
@@ -0,0 +1,23 @@
+#ifndef IPWD_H
+#define IPWD_H
+
+#include <pwd.h>
+#include <grp.h>
+
+/* Replacements for standard getpw/gr*(), fixing their ability to report errors
+   properly. As with standard getpw/gr*(), second call overwrites data used
+   by the first one.
+
+   Functions return 1 if user/group is found, 0 if not or
+   -1 if error (with errno set). */
+
+int i_getpwnam(const char *name, struct passwd *pwd_r);
+int i_getpwuid(uid_t uid, struct passwd *pwd_r);
+
+int i_getgrnam(const char *name, struct group *grp_r);
+int i_getgrgid(gid_t gid, struct group *grp_r);
+
+/* Free memory used by above functions. */
+void ipwd_deinit(void);
+
+#endif