On Wednesday 22 June 2011 15:51:25 Tito wrote:
>
> On Wednesday 22 June 2011 08:06:28 Tito wrote:
> >
> > On Wednesday 22 June 2011 04:18:32 Denys Vlasenko wrote:
> > > On Wednesday 22 June 2011 01:03, Tito wrote:
> > > > > Applied, thanks!
> > > >
> > > > Hi Denys,
> > > > i suspect that:
> > > >
> > > > opt_complementary = "?1:u--g:g--u:G--u:u--G:g--G:G--g:r?ugG:n?ugG"
> > > >
> > > > should be before
> > > >
> > > > if (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] == 'g')) {
> > > > option_mask32 = opt = getopt32(argv, "") | JUST_ALL_GROUPS |
> > > > NAME_NOT_NUMBER;
> > > > } else {
> > > >
> > > > as else the max args (= 1) statement is not enforced for groups.
> > > > At least something like this is needed:
> > >
> > > coreutils groups can take more than one arg.
> > >
> > Hi,
> > Yes, but id doesn't and our groups doesn't. Even bb's groups' help text
> > says [USER].
> >
> > Ciao,
> > Tito
>
> Hi,
> attached a patch that allows group to use multiple usernames.
> Little tested, seems to work, looks a little ugly.... ;-).
>
> Ciao,
> Tito
>
> --- coreutils/id.c.original 2011-06-22 14:29:58.000000000 +0200
> +++ coreutils/id.c 2011-06-22 15:41:38.000000000 +0200
> @@ -51,7 +51,7 @@
> //usage: "uid=1000(andersen) gid=1000(andersen)\n"
>
> //usage:#define groups_trivial_usage
> -//usage: "[USER]"
> +//usage: "[USERS]"
> //usage:#define groups_full_usage "\n\n"
> //usage: "Print the group memberships of USER or for the current
> process"
> //usage:
> @@ -158,19 +158,15 @@
> int i;
> int status = EXIT_SUCCESS;
> const char *prefix;
> - const char *username;
> + /* Are we groups or id? */
> + int do_groups = (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] ==
> 'g'));
> #if ENABLE_SELINUX
> security_context_t scontext = NULL;
> #endif
>
> - if (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] == 'g')) {
> - /* TODO: coreutils groups prepend "USER : " prefix,
> - * and accept many usernames. Example:
> - * # groups root root
> - * root : root
> - * root : root
> - */
> + if (do_groups) {
> opt = option_mask32 = getopt32(argv, "") | JUST_ALL_GROUPS |
> NAME_NOT_NUMBER;
> + do_groups = argc - optind;
> } else {
> /* Don't allow -n -r -nr -ug -rug -nug -rnug -uZ -gZ -GZ*/
> /* Don't allow more than one username */
> @@ -179,92 +175,97 @@
> opt = getopt32(argv, "rnugG" IF_SELINUX("Z"));
> }
>
> - username = argv[optind];
> - if (username) {
> - struct passwd *p = xgetpwnam(username);
> - euid = ruid = p->pw_uid;
> - egid = rgid = p->pw_gid;
> - } else {
> - egid = getegid();
> - rgid = getgid();
> - euid = geteuid();
> - ruid = getuid();
> - }
> - /* JUST_ALL_GROUPS ignores -r PRINT_REAL flag even if man page for */
> - /* id says: print the real ID instead of the effective ID, with -ugG */
> - /* in fact in this case egid is always printed if egid != rgid */
> - if (!opt || (opt & JUST_ALL_GROUPS)) {
> - gid_t *groups;
> - int n;
> -
> - if (!opt) {
> - /* Default Mode */
> - status |= print_user(ruid, "uid=");
> - status |= print_group(rgid, " gid=");
> - if (euid != ruid)
> - status |= print_user(euid, " euid=");
> - if (egid != rgid)
> - status |= print_group(egid, " egid=");
> + //argc -= optind;
> + argv += optind;
> + do {
> + if (*argv) {
> + struct passwd *p = xgetpwnam(*argv);
> + euid = ruid = p->pw_uid;
> + egid = rgid = p->pw_gid;
> } else {
> - /* JUST_ALL_GROUPS */
> - status |= print_group(rgid, NULL);
> - if (egid != rgid)
> - status |= print_group(egid, " ");
> - }
> - /* We are supplying largish buffer, trying
> - * to not run get_groups() twice. That might be slow
> - * ("user database in remote SQL server" case) */
> - groups = xmalloc(64 * sizeof(gid_t));
> - n = 64;
> - if (get_groups(username, rgid, groups, &n) < 0) {
> - /* Need bigger buffer after all */
> - groups = xrealloc(groups, n * sizeof(gid_t));
> - get_groups(username, rgid, groups, &n);
> - }
> - if (n > 0) {
> - /* Print the list */
> - prefix = " groups=";
> - for (i = 0; i < n; i++) {
> - if (opt && (groups[i] == rgid || groups[i] ==
> egid))
> - continue;
> - status |= print_group(groups[i], opt ? " " :
> prefix);
> - prefix = ",";
> - }
> - } else if (n < 0) { /* error in get_groups() */
> - if (ENABLE_DESKTOP)
> - bb_error_msg_and_die("can't get groups");
> - return EXIT_FAILURE;
> + egid = getegid();
> + rgid = getgid();
> + euid = geteuid();
> + ruid = getuid();
> + }
> + /* JUST_ALL_GROUPS ignores -r PRINT_REAL flag even if man page
> for */
> + /* id says: print the real ID instead of the effective ID, with
> -ugG */
> + /* in fact in this case egid is always printed if egid != rgid
> */
> + if (!opt || (opt & JUST_ALL_GROUPS)) {
> + gid_t *groups;
> + int n;
> +
> + if (!opt) {
> + /* Default Mode */
> + status |= print_user(ruid, "uid=");
> + status |= print_group(rgid, " gid=");
> + if (euid != ruid)
> + status |= print_user(euid, " euid=");
> + if (egid != rgid)
> + status |= print_group(egid, " egid=");
> + } else {
> + if (do_groups)
> + printf("%s : ", *argv ? *argv :
> xuid2uname(euid));
> + /* JUST_ALL_GROUPS */
> + status |= print_group(rgid, NULL);
> + if (egid != rgid)
> + status |= print_group(egid, " ");
> + }
> + /* We are supplying largish buffer, trying
> + * to not run get_groups() twice. That might be slow
> + * ("user database in remote SQL server" case) */
> + groups = xmalloc(64 * sizeof(gid_t));
> + n = 64;
> + if (get_groups(*argv, rgid, groups, &n) < 0) {
> + /* Need bigger buffer after all */
> + groups = xrealloc(groups, n * sizeof(gid_t));
> + get_groups(*argv, rgid, groups, &n);
> + }
> + if (n > 0) {
> + /* Print the list */
> + prefix = " groups=";
> + for (i = 0; i < n; i++) {
> + if (opt && (groups[i] == rgid ||
> groups[i] == egid))
> + continue;
> + status |= print_group(groups[i], opt ?
> " " : prefix);
> + prefix = ",";
> + }
> + } else if (n < 0) { /* error in get_groups() */
> + if (ENABLE_DESKTOP)
> + bb_error_msg_and_die("can't get
> groups");
> + return EXIT_FAILURE;
> + }
> + if (ENABLE_FEATURE_CLEAN_UP || do_groups)
> + free(groups);
> + #if ENABLE_SELINUX
> + if (is_selinux_enabled()) {
> + if (getcon(&scontext) == 0)
> + printf(" context=%s", scontext);
> + }
> + #endif
> + } else if (opt & PRINT_REAL) {
> + euid = ruid;
> + egid = rgid;
> + }
> +
> + if (opt & JUST_USER)
> + status |= print_user(euid, NULL);
> + else if (opt & JUST_GROUP)
> + status |= print_group(egid, NULL);
> + #if ENABLE_SELINUX
> + else if (opt & JUST_CONTEXT) {
> + selinux_or_die();
> + if (username || getcon(&scontext)) {
> + bb_error_msg_and_die("can't get process
> context%s",
> + username ? " for a different user" :
> "");
> + }
> + fputs(scontext, stdout);
> }
> + /* freecon(NULL) seems to be harmless */
> if (ENABLE_FEATURE_CLEAN_UP)
> - free(groups);
> -#if ENABLE_SELINUX
> - if (is_selinux_enabled()) {
> - if (getcon(&scontext) == 0)
> - printf(" context=%s", scontext);
> - }
> -#endif
> - } else if (opt & PRINT_REAL) {
> - euid = ruid;
> - egid = rgid;
> - }
> -
> - if (opt & JUST_USER)
> - status |= print_user(euid, NULL);
> - else if (opt & JUST_GROUP)
> - status |= print_group(egid, NULL);
> -#if ENABLE_SELINUX
> - else if (opt & JUST_CONTEXT) {
> - selinux_or_die();
> - if (username || getcon(&scontext)) {
> - bb_error_msg_and_die("can't get process context%s",
> - username ? " for a different user" : "");
> - }
> - fputs(scontext, stdout);
> - }
> - /* freecon(NULL) seems to be harmless */
> - if (ENABLE_FEATURE_CLEAN_UP)
> - freecon(scontext);
> -#endif
> - bb_putchar('\n');
> + freecon(scontext);
> + #endif
> + bb_putchar('\n');
> + } while (do_groups-- > 1 && *argv++);
> fflush_stdout_and_exit(status);
> }
>
Hi,
Just for future reference the same patch created with --ignore-all-space
switch to show the real code changes.
Ciao,
Tito
--- coreutils/id.c.original 2011-06-22 14:29:58.000000000 +0200
+++ coreutils/id.c 2011-06-22 15:41:38.000000000 +0200
@@ -51,7 +51,7 @@
//usage: "uid=1000(andersen) gid=1000(andersen)\n"
//usage:#define groups_trivial_usage
-//usage: "[USER]"
+//usage: "[USERS]"
//usage:#define groups_full_usage "\n\n"
//usage: "Print the group memberships of USER or for the current process"
//usage:
@@ -158,19 +158,15 @@
int i;
int status = EXIT_SUCCESS;
const char *prefix;
- const char *username;
+ /* Are we groups or id? */
+ int do_groups = (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] ==
'g'));
#if ENABLE_SELINUX
security_context_t scontext = NULL;
#endif
- if (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] == 'g')) {
- /* TODO: coreutils groups prepend "USER : " prefix,
- * and accept many usernames. Example:
- * # groups root root
- * root : root
- * root : root
- */
+ if (do_groups) {
opt = option_mask32 = getopt32(argv, "") | JUST_ALL_GROUPS |
NAME_NOT_NUMBER;
+ do_groups = argc - optind;
} else {
/* Don't allow -n -r -nr -ug -rug -nug -rnug -uZ -gZ -GZ*/
/* Don't allow more than one username */
@@ -179,9 +175,11 @@
opt = getopt32(argv, "rnugG" IF_SELINUX("Z"));
}
- username = argv[optind];
- if (username) {
- struct passwd *p = xgetpwnam(username);
+ //argc -= optind;
+ argv += optind;
+ do {
+ if (*argv) {
+ struct passwd *p = xgetpwnam(*argv);
euid = ruid = p->pw_uid;
egid = rgid = p->pw_gid;
} else {
@@ -206,6 +204,8 @@
if (egid != rgid)
status |= print_group(egid, " egid=");
} else {
+ if (do_groups)
+ printf("%s : ", *argv ? *argv :
xuid2uname(euid));
/* JUST_ALL_GROUPS */
status |= print_group(rgid, NULL);
if (egid != rgid)
@@ -216,10 +216,10 @@
* ("user database in remote SQL server" case) */
groups = xmalloc(64 * sizeof(gid_t));
n = 64;
- if (get_groups(username, rgid, groups, &n) < 0) {
+ if (get_groups(*argv, rgid, groups, &n) < 0) {
/* Need bigger buffer after all */
groups = xrealloc(groups, n * sizeof(gid_t));
- get_groups(username, rgid, groups, &n);
+ get_groups(*argv, rgid, groups, &n);
}
if (n > 0) {
/* Print the list */
@@ -235,7 +235,7 @@
bb_error_msg_and_die("can't get groups");
return EXIT_FAILURE;
}
- if (ENABLE_FEATURE_CLEAN_UP)
+ if (ENABLE_FEATURE_CLEAN_UP || do_groups)
free(groups);
#if ENABLE_SELINUX
if (is_selinux_enabled()) {
@@ -266,5 +266,6 @@
freecon(scontext);
#endif
bb_putchar('\n');
+ } while (do_groups-- > 1 && *argv++);
fflush_stdout_and_exit(status);
}
--- coreutils/id.c.original 2011-06-22 14:29:58.000000000 +0200
+++ coreutils/id.c 2011-06-22 15:41:38.000000000 +0200
@@ -51,7 +51,7 @@
//usage: "uid=1000(andersen) gid=1000(andersen)\n"
//usage:#define groups_trivial_usage
-//usage: "[USER]"
+//usage: "[USERS]"
//usage:#define groups_full_usage "\n\n"
//usage: "Print the group memberships of USER or for the current process"
//usage:
@@ -158,19 +158,15 @@
int i;
int status = EXIT_SUCCESS;
const char *prefix;
- const char *username;
+ /* Are we groups or id? */
+ int do_groups = (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] == 'g'));
#if ENABLE_SELINUX
security_context_t scontext = NULL;
#endif
- if (ENABLE_GROUPS && (!ENABLE_ID || applet_name[0] == 'g')) {
- /* TODO: coreutils groups prepend "USER : " prefix,
- * and accept many usernames. Example:
- * # groups root root
- * root : root
- * root : root
- */
+ if (do_groups) {
opt = option_mask32 = getopt32(argv, "") | JUST_ALL_GROUPS | NAME_NOT_NUMBER;
+ do_groups = argc - optind;
} else {
/* Don't allow -n -r -nr -ug -rug -nug -rnug -uZ -gZ -GZ*/
/* Don't allow more than one username */
@@ -179,9 +175,11 @@
opt = getopt32(argv, "rnugG" IF_SELINUX("Z"));
}
- username = argv[optind];
- if (username) {
- struct passwd *p = xgetpwnam(username);
+ //argc -= optind;
+ argv += optind;
+ do {
+ if (*argv) {
+ struct passwd *p = xgetpwnam(*argv);
euid = ruid = p->pw_uid;
egid = rgid = p->pw_gid;
} else {
@@ -206,6 +204,8 @@
if (egid != rgid)
status |= print_group(egid, " egid=");
} else {
+ if (do_groups)
+ printf("%s : ", *argv ? *argv : xuid2uname(euid));
/* JUST_ALL_GROUPS */
status |= print_group(rgid, NULL);
if (egid != rgid)
@@ -216,10 +216,10 @@
* ("user database in remote SQL server" case) */
groups = xmalloc(64 * sizeof(gid_t));
n = 64;
- if (get_groups(username, rgid, groups, &n) < 0) {
+ if (get_groups(*argv, rgid, groups, &n) < 0) {
/* Need bigger buffer after all */
groups = xrealloc(groups, n * sizeof(gid_t));
- get_groups(username, rgid, groups, &n);
+ get_groups(*argv, rgid, groups, &n);
}
if (n > 0) {
/* Print the list */
@@ -235,7 +235,7 @@
bb_error_msg_and_die("can't get groups");
return EXIT_FAILURE;
}
- if (ENABLE_FEATURE_CLEAN_UP)
+ if (ENABLE_FEATURE_CLEAN_UP || do_groups)
free(groups);
#if ENABLE_SELINUX
if (is_selinux_enabled()) {
@@ -266,5 +266,6 @@
freecon(scontext);
#endif
bb_putchar('\n');
+ } while (do_groups-- > 1 && *argv++);
fflush_stdout_and_exit(status);
}
_______________________________________________
busybox mailing list
[email protected]
http://lists.busybox.net/mailman/listinfo/busybox