]> git.ipfire.org Git - thirdparty/util-linux.git/commitdiff
namei: move icache to lib/
authorKarel Zak <kzak@redhat.com>
Fri, 27 Nov 2015 12:56:01 +0000 (13:56 +0100)
committerKarel Zak <kzak@redhat.com>
Fri, 27 Nov 2015 12:56:01 +0000 (13:56 +0100)
Signed-off-by: Karel Zak <kzak@redhat.com>
include/idcache.h [new file with mode: 0644]
lib/Makemodule.am
lib/idcache.c [new file with mode: 0644]
misc-utils/Makemodule.am
misc-utils/namei.c

diff --git a/include/idcache.h b/include/idcache.h
new file mode 100644 (file)
index 0000000..912edd5
--- /dev/null
@@ -0,0 +1,28 @@
+#ifndef UTIL_LINUX_IDCACHE_H
+#define UTIL_LINUX_IDCACHE_H
+
+#include <sys/types.h>
+#include <pwd.h>
+
+#define IDCACHE_FLAGS_NAMELEN  (1 << 1)
+
+struct identry {
+       unsigned long int       id;
+       char                    *name;
+       struct identry          *next;
+};
+
+struct idcache {
+       struct identry  *ent;   /* first entry */
+       int             width;  /* name width */
+};
+
+
+extern struct idcache *new_idcache(void);
+extern void add_gid(struct idcache *cache, unsigned long int id);
+extern void add_uid(struct idcache *cache, unsigned long int id);
+
+extern void free_idcache(struct idcache *ic);
+extern struct identry *get_id(struct idcache *ic, unsigned long int id);
+
+#endif /* UTIL_LINUX_IDCACHE_H */
index ae0443ea769061b4abeddf28a4277b5547f0ce29..8e1fea25e4ea315167edfd5d564e8d78640c519e 100644 (file)
@@ -8,6 +8,7 @@ libcommon_la_SOURCES = \
        lib/crc32.c \
        lib/crc64.c \
        lib/env.c \
+       lib/idcache.c \
        lib/fileutils.c \
        lib/ismounted.c \
        lib/color-names.c \
diff --git a/lib/idcache.c b/lib/idcache.c
new file mode 100644 (file)
index 0000000..4cb20fd
--- /dev/null
@@ -0,0 +1,113 @@
+
+#include <wchar.h>
+#include <pwd.h>
+#include <grp.h>
+#include <sys/types.h>
+
+#include "c.h"
+#include "idcache.h"
+
+struct identry *get_id(struct idcache *ic, unsigned long int id)
+{
+       struct identry *ent;
+
+       if (!ic)
+               return NULL;
+
+       for (ent = ic->ent; ent; ent = ent->next) {
+               if (ent->id == id)
+                       return ent;
+       }
+
+       return NULL;
+}
+
+struct idcache *new_idcache()
+{
+       return calloc(1, sizeof(struct idcache));
+}
+
+void free_idcache(struct idcache *ic)
+{
+       struct identry *ent = ic->ent;
+
+       while (ent) {
+               struct identry *next = ent->next;
+               free(ent->name);
+               free(ent);
+               ent = next;
+       }
+
+       free(ic);
+}
+
+static void add_id(struct idcache *ic, char *name, unsigned long int id)
+{
+       struct identry *ent, *x;
+       int w = 0;
+
+       ent = calloc(1, sizeof(struct identry));
+       if (!ent)
+               return;
+       ent->id = id;
+
+       if (name) {
+#ifdef HAVE_WIDECHAR
+               wchar_t wc[LOGIN_NAME_MAX + 1];
+
+               if (mbstowcs(wc, name, LOGIN_NAME_MAX) > 0) {
+                       wc[LOGIN_NAME_MAX] = '\0';
+                       w = wcswidth(wc, LOGIN_NAME_MAX);
+               }
+               else
+#endif
+                       w = strlen(name);
+       }
+
+       /* note, we ignore names with non-printable widechars */
+       if (w > 0) {
+               ent->name = strdup(name);
+               if (!ent->name) {
+                       free(ent);
+                       return;
+               }
+       } else {
+               if (asprintf(&ent->name, "%lu", id) < 0) {
+                       free(ent);
+                       return;
+               }
+       }
+
+       for (x = ic->ent; x && x->next; x = x->next);
+
+       if (x)
+               x->next = ent;
+       else
+               ic->ent = ent;
+
+       if (w <= 0)
+               w = ent->name ? strlen(ent->name) : 0;
+       ic->width = ic->width < w ? w : ic->width;
+       return;
+}
+
+void add_uid(struct idcache *cache, unsigned long int id)
+{
+       struct identry *ent= get_id(cache, id);
+
+       if (!ent) {
+               struct passwd *pw = getpwuid((uid_t) id);
+               add_id(cache, pw ? pw->pw_name : NULL, id);
+       }
+}
+
+void add_gid(struct idcache *cache, unsigned long int id)
+{
+       struct identry *ent = get_id(cache, id);
+
+       if (!ent) {
+               struct group *gr = getgrgid((gid_t) id);
+               add_id(cache, gr ? gr->gr_name : NULL, id);
+       }
+}
+
index e7949d0534fdd9b285b16229021e1ec323198c93..f2aa881df54076bdfc623211e87ff303bbe7b76d 100644 (file)
@@ -50,7 +50,7 @@ endif
 if BUILD_NAMEI
 usrbin_exec_PROGRAMS += namei
 dist_man_MANS += misc-utils/namei.1
-namei_SOURCES = misc-utils/namei.c lib/strutils.c
+namei_SOURCES = misc-utils/namei.c lib/strutils.c lib/idcache.c
 endif
 
 if BUILD_WHEREIS
index 15bec99607a5d768c0e11da285d707223a2accf2..41557cac304a257750fdc1110d2bc861d7661f45 100644 (file)
@@ -38,6 +38,7 @@
 #include "widechar.h"
 #include "strutils.h"
 #include "closestream.h"
+#include "idcache.h"
 
 #ifndef MAXSYMLINKS
 #define MAXSYMLINKS 256
@@ -65,103 +66,10 @@ struct namei {
        int             noent;          /* is this item not existing */
 };
 
-struct idcache {
-       unsigned long int       id;
-       char                    *name;
-       struct idcache          *next;
-};
-
 static int flags;
-static int uwidth;             /* maximal width of username */
-static int gwidth;             /* maximal width of groupname */
 static struct idcache *gcache; /* groupnames */
 static struct idcache *ucache; /* usernames */
 
-static struct idcache *
-get_id(struct idcache *ic, unsigned long int id)
-{
-       while(ic) {
-               if (ic->id == id)
-                       return ic;
-               ic = ic->next;
-       }
-       return NULL;
-}
-
-static void
-free_idcache(struct idcache *ic)
-{
-       while(ic) {
-               struct idcache *next = ic->next;
-               free(ic->name);
-               free(ic);
-               ic = next;
-       }
-}
-
-static void
-add_id(struct idcache **ic, char *name, unsigned long int id, int *width)
-{
-       struct idcache *nc, *x;
-       int w = 0;
-
-       nc = xcalloc(1, sizeof(*nc));
-       nc->id = id;
-
-       if (name) {
-#ifdef HAVE_WIDECHAR
-               wchar_t wc[LOGIN_NAME_MAX + 1];
-
-               if (mbstowcs(wc, name, LOGIN_NAME_MAX) > 0) {
-                       wc[LOGIN_NAME_MAX] = '\0';
-                       w = wcswidth(wc, LOGIN_NAME_MAX);
-               }
-               else
-#endif
-                       w = strlen(name);
-       }
-       /* note, we ignore names with non-printable widechars */
-       if (w > 0)
-               nc->name = xstrdup(name);
-       else
-               xasprintf(&nc->name, "%lu", id);
-
-       for (x = *ic; x && x->next; x = x->next);
-
-       /* add 'nc' at end of the 'ic' list */
-       if (x)
-               x->next = nc;
-       else
-               *ic = nc;
-       if (w <= 0)
-               w = nc->name ? strlen(nc->name) : 0;
-
-       *width = *width < w ? w : *width;
-       return;
-}
-
-static void
-add_uid(unsigned long int id)
-{
-       struct idcache *ic = get_id(ucache, id);
-
-       if (!ic) {
-               struct passwd *pw = getpwuid((uid_t) id);
-               add_id(&ucache, pw ? pw->pw_name : NULL, id, &uwidth);
-       }
-}
-
-static void
-add_gid(unsigned long int id)
-{
-       struct idcache *ic = get_id(gcache, id);
-
-       if (!ic) {
-               struct group *gr = getgrgid((gid_t) id);
-               add_id(&gcache, gr ? gr->gr_name : NULL, id, &gwidth);
-       }
-}
-
 static void
 free_namei(struct namei *nm)
 {
@@ -254,8 +162,8 @@ new_namei(struct namei *parent, const char *path, const char *fname, int lev)
        if (S_ISLNK(nm->st.st_mode))
                readlink_to_namei(nm, path);
        if (flags & NAMEI_OWNERS) {
-               add_uid(nm->st.st_uid);
-               add_gid(nm->st.st_gid);
+               add_uid(ucache, nm->st.st_uid);
+               add_gid(gcache, nm->st.st_gid);
        }
 
        if ((flags & NAMEI_MNTS) && S_ISDIR(nm->st.st_mode)) {
@@ -371,7 +279,7 @@ print_namei(struct namei *nm, char *path)
                        if (flags & NAMEI_MODES)
                                blanks += 9;
                        if (flags & NAMEI_OWNERS)
-                               blanks += uwidth + gwidth + 2;
+                               blanks += ucache->width + gcache->width + 2;
                        if (!(flags & NAMEI_VERTICAL))
                                blanks += 1;
                        blanks += nm->level * 2;
@@ -397,9 +305,9 @@ print_namei(struct namei *nm, char *path)
                        printf("%c", md[0]);
 
                if (flags & NAMEI_OWNERS) {
-                       printf(" %-*s", uwidth,
+                       printf(" %-*s", ucache->width,
                                get_id(ucache, nm->st.st_uid)->name);
-                       printf(" %-*s", gwidth,
+                       printf(" %-*s", gcache->width,
                                get_id(gcache, nm->st.st_gid)->name);
                }
 
@@ -505,6 +413,13 @@ main(int argc, char **argv)
                usage(EXIT_FAILURE);
        }
 
+       ucache = new_idcache();
+       if (!ucache)
+               err(EXIT_FAILURE, _("failed to allocate UID cache"));
+       gcache = new_idcache();
+       if (!gcache)
+               err(EXIT_FAILURE, _("failed to allocate GID cache"));
+
        for(; optind < argc; optind++) {
                char *path = argv[optind];
                struct namei *nm = NULL;