summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKarel Zak2015-11-27 13:56:01 +0100
committerKarel Zak2015-11-27 13:56:01 +0100
commit04a5cb58b62598b86173a03af8e900d58f2bfed1 (patch)
tree1b4f897a4a174b7fc5ed52666ca16c3392899a33
parentlsns: new command (diff)
downloadkernel-qcow2-util-linux-04a5cb58b62598b86173a03af8e900d58f2bfed1.tar.gz
kernel-qcow2-util-linux-04a5cb58b62598b86173a03af8e900d58f2bfed1.tar.xz
kernel-qcow2-util-linux-04a5cb58b62598b86173a03af8e900d58f2bfed1.zip
namei: move icache to lib/
Signed-off-by: Karel Zak <kzak@redhat.com>
-rw-r--r--include/idcache.h28
-rw-r--r--lib/Makemodule.am1
-rw-r--r--lib/idcache.c113
-rw-r--r--misc-utils/Makemodule.am2
-rw-r--r--misc-utils/namei.c111
5 files changed, 156 insertions, 99 deletions
diff --git a/include/idcache.h b/include/idcache.h
new file mode 100644
index 000000000..912edd58f
--- /dev/null
+++ b/include/idcache.h
@@ -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 */
diff --git a/lib/Makemodule.am b/lib/Makemodule.am
index ae0443ea7..8e1fea25e 100644
--- a/lib/Makemodule.am
+++ b/lib/Makemodule.am
@@ -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
index 000000000..4cb20fd2d
--- /dev/null
+++ b/lib/idcache.c
@@ -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);
+ }
+}
+
diff --git a/misc-utils/Makemodule.am b/misc-utils/Makemodule.am
index e7949d053..f2aa881df 100644
--- a/misc-utils/Makemodule.am
+++ b/misc-utils/Makemodule.am
@@ -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
diff --git a/misc-utils/namei.c b/misc-utils/namei.c
index 15bec9960..41557cac3 100644
--- a/misc-utils/namei.c
+++ b/misc-utils/namei.c
@@ -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;