summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Härdeman <david@hardeman.nu>2007-05-21 14:48:18 +0200
committerDavid Härdeman <david@hardeman.nu>2007-05-21 14:48:18 +0200
commit36d91ba2fe1ecc8120a252c12c19729519bdb078 (patch)
tree3437dfc9dd5056c84215b44d766086c9087a66fa
parent201f1e4dfd09f41cce99182294824af0274898ae (diff)
Add caching uid/gid lookup functions
-rw-r--r--metaentry.c6
-rw-r--r--metastore.c6
-rw-r--r--utils.c119
-rw-r--r--utils.h16
4 files changed, 139 insertions, 8 deletions
diff --git a/metaentry.c b/metaentry.c
index 683a126..a2ab65b 100644
--- a/metaentry.c
+++ b/metaentry.c
@@ -25,8 +25,6 @@
#include <sys/types.h>
#include <sys/stat.h>
#include <unistd.h>
-#include <pwd.h>
-#include <grp.h>
#include <attr/xattr.h>
#include <limits.h>
#include <dirent.h>
@@ -203,14 +201,14 @@ mentry_create(const char *path)
return NULL;
}
- pbuf = getpwuid(sbuf.st_uid);
+ pbuf = xgetpwuid(sbuf.st_uid);
if (!pbuf) {
msg(MSG_ERROR, "getpwuid failed for %i: %s\n",
(int)sbuf.st_uid, strerror(errno));
return NULL;
}
- gbuf = getgrgid(sbuf.st_gid);
+ gbuf = xgetgrgid(sbuf.st_gid);
if (!gbuf) {
msg(MSG_ERROR, "getgrgid failed for %i: %s\n",
(int)sbuf.st_gid, strerror(errno));
diff --git a/metastore.c b/metastore.c
index affcf19..a03e0ef 100644
--- a/metastore.c
+++ b/metastore.c
@@ -20,8 +20,6 @@
#include <sys/types.h>
#include <sys/stat.h>
-#include <pwd.h>
-#include <grp.h>
#include <getopt.h>
#include <utime.h>
#include <attr/xattr.h>
@@ -121,7 +119,7 @@ compare_fix(struct metaentry *real, struct metaentry *stored, int cmp)
if (cmp & DIFF_OWNER) {
msg(MSG_NORMAL, "\tchanging owner from %s to %s\n",
real->path, real->group, stored->group);
- owner = getpwnam(stored->owner);
+ owner = xgetpwnam(stored->owner);
if (!owner) {
msg(MSG_DEBUG, "\tgetpwnam failed: %s\n",
strerror(errno));
@@ -133,7 +131,7 @@ compare_fix(struct metaentry *real, struct metaentry *stored, int cmp)
if (cmp & DIFF_GROUP) {
msg(MSG_NORMAL, "\tchanging group from %s to %s\n",
real->path, real->group, stored->group);
- group = getgrnam(stored->group);
+ group = xgetgrnam(stored->group);
if (!group) {
msg(MSG_DEBUG, "\tgetgrnam failed: %s\n",
strerror(errno));
diff --git a/utils.c b/utils.c
index 7b8e784..aa6df96 100644
--- a/utils.c
+++ b/utils.c
@@ -26,6 +26,9 @@
#include <stdarg.h>
#include <unistd.h>
#include <errno.h>
+#include <sys/types.h>
+#include <grp.h>
+#include <pwd.h>
#include "utils.h"
@@ -182,3 +185,119 @@ read_string(char **from, const char *max)
return read_binary_string(from, strlen(*from) + 1, max);
}
+/* For group caching */
+static struct group *gtable = NULL;
+
+/* Initial setup of the gid table */
+static void
+create_group_table()
+{
+ struct group *tmp;
+ int count, index;
+
+ for (count = 0; getgrent(); count++) /* Do nothing */;
+
+ gtable = xmalloc(sizeof(struct group) * (count + 1));
+ memset(gtable, 0, sizeof(struct group) * (count + 1));
+ setgrent();
+
+ for (index = 0; (tmp = getgrent()) && index < count; index++) {
+ gtable[index].gr_gid = tmp->gr_gid;
+ gtable[index].gr_name = xstrdup(tmp->gr_name);
+ }
+
+ endgrent();
+}
+
+/* Caching version of getgrnam */
+struct group *
+xgetgrnam(const char *name)
+{
+ int i;
+
+ if (!gtable)
+ create_group_table();
+
+ for (i = 0; gtable[i].gr_name; i++) {
+ if (!strcmp(name, gtable[i].gr_name))
+ return &(gtable[i]);
+ }
+
+ return NULL;
+}
+
+/* Caching version of getgrgid */
+struct group *
+xgetgrgid(gid_t gid)
+{
+ int i;
+
+ if (!gtable)
+ create_group_table();
+
+ for (i = 0; gtable[i].gr_name; i++) {
+ if (gtable[i].gr_gid == gid)
+ return &(gtable[i]);
+ }
+
+ return NULL;
+}
+
+/* For user caching */
+static struct passwd *ptable = NULL;
+
+/* Initial setup of the passwd table */
+static void
+create_passwd_table()
+{
+ struct passwd *tmp;
+ int count, index;
+
+ for (count = 0; getpwent(); count++) /* Do nothing */;
+
+ ptable = xmalloc(sizeof(struct passwd) * (count + 1));
+ memset(ptable, 0, sizeof(struct passwd) * (count + 1));
+ setpwent();
+
+ for (index = 0; (tmp = getpwent()) && index < count; index++) {
+ ptable[index].pw_uid = tmp->pw_uid;
+ ptable[index].pw_name = xstrdup(tmp->pw_name);
+ }
+
+ endpwent();
+}
+
+/* Caching version of getpwnam */
+struct passwd *
+xgetpwnam(const char *name)
+{
+ int i;
+
+ if (!ptable)
+ create_passwd_table();
+
+ for (i = 0; ptable[i].pw_name; i++) {
+ if (!strcmp(name, ptable[i].pw_name))
+ return &(ptable[i]);
+ }
+
+ return NULL;
+}
+
+/* Caching version of getpwuid */
+struct passwd *
+xgetpwuid(uid_t uid)
+{
+ int i;
+
+ if (!ptable)
+ create_passwd_table();
+
+ for (i = 0; ptable[i].pw_name; i++) {
+ if (ptable[i].pw_uid == uid)
+ return &(ptable[i]);
+ }
+
+ return NULL;
+}
+
diff --git a/utils.h b/utils.h
index e3096c9..a5f8b54 100644
--- a/utils.h
+++ b/utils.h
@@ -24,6 +24,10 @@
#include <unistd.h>
/* For FILE */
#include <stdio.h>
+/* For struct passwd */
+#include <pwd.h>
+/* For struct group */
+#include <grp.h>
/* Adjusts the verbosity level for msg() */
void adjust_verbosity(int adj);
@@ -69,3 +73,15 @@ char *read_binary_string(char **from, size_t len, const char *max);
/* Reads a normal C string from a file */
char *read_string(char **from, const char *max);
+/* Caching version of getgrnam */
+struct group *xgetgrnam(const char *name);
+
+/* Caching version of getgrgid */
+struct group *xgetgrgid(gid_t gid);
+
+/* Caching version of getpwnam */
+struct passwd *xgetpwnam(const char *name);
+
+/* Caching version of getpwuid */
+struct passwd *xgetpwuid(uid_t uid);
+