aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--lib/lib.h2
-rw-r--r--lib/xwrap.c32
-rw-r--r--toys/posix/chgrp.c19
3 files changed, 37 insertions, 16 deletions
diff --git a/lib/lib.h b/lib/lib.h
index e5667517..d8a1503e 100644
--- a/lib/lib.h
+++ b/lib/lib.h
@@ -123,6 +123,8 @@ struct passwd *xgetpwuid(uid_t uid);
struct group *xgetgrgid(gid_t gid);
struct passwd *xgetpwnam(char *name);
struct group *xgetgrnam(char *name);
+struct passwd *xgetpwnamid(char *user);
+struct group *xgetgrnamid(char *group);
void xsetuser(struct passwd *pwd);
char *xreadlink(char *name);
long xparsetime(char *arg, long units, long *fraction);
diff --git a/lib/xwrap.c b/lib/xwrap.c
index 44cd1684..54f2cbb5 100644
--- a/lib/xwrap.c
+++ b/lib/xwrap.c
@@ -477,6 +477,38 @@ struct group *xgetgrgid(gid_t gid)
return group;
}
+struct passwd *xgetpwnamid(char *user)
+{
+ struct passwd *up = getpwnam(user);
+ uid_t uid;
+
+ if (!up) {
+ char *s = 0;
+
+ uid = estrtol(user, &s, 10);
+ if (!errno && s && !*s) up = getpwuid(uid);
+ }
+ if (!up) perror_exit("user '%s'", user);
+
+ return up;
+}
+
+struct group *xgetgrnamid(char *group)
+{
+ struct group *gr = getgrnam(group);
+ gid_t gid;
+
+ if (!gr) {
+ char *s = 0;
+
+ gid = estrtol(group, &s, 10);
+ if (!errno && s && !*s) gr = getgrgid(gid);
+ }
+ if (!gr) perror_exit("group '%s'", group);
+
+ return gr;
+}
+
struct passwd *xgetpwnam(char *name)
{
struct passwd *up = getpwnam(name);
diff --git a/toys/posix/chgrp.c b/toys/posix/chgrp.c
index 556b0f19..fb82adbd 100644
--- a/toys/posix/chgrp.c
+++ b/toys/posix/chgrp.c
@@ -82,30 +82,17 @@ void chgrp_main(void)
// Distinguish chown from chgrp
if (ischown) {
char *grp;
- struct passwd *p;
own = xstrdup(*toys.optargs);
if ((grp = strchr(own, ':')) || (grp = strchr(own, '.'))) {
*(grp++) = 0;
TT.group_name = grp;
}
- if (*own) {
- TT.owner_name = own;
- p = getpwnam(own);
- // TODO: trailing garbage?
- if (!p && isdigit(*own)) p=getpwuid(atoi(own));
- if (!p) error_exit("no user '%s'", own);
- TT.owner = p->pw_uid;
- }
+ if (*own) TT.owner = xgetpwnamid(TT.owner_name = own)->pw_uid;
} else TT.group_name = *toys.optargs;
- if (TT.group_name && *TT.group_name) {
- struct group *g;
- g = getgrnam(TT.group_name);
- if (!g) g=getgrgid(atoi(TT.group_name));
- if (!g) error_exit("no group '%s'", TT.group_name);
- TT.group = g->gr_gid;
- }
+ if (TT.group_name && *TT.group_name)
+ TT.group = xgetgrnamid(TT.group_name)->gr_gid;
for (s=toys.optargs+1; *s; s++) {
struct dirtree *new = dirtree_add_node(0, *s, hl);