From: Ismail Ramzi <[email protected]> * src/chroot.c (main): When the primary group was inferred from the uid outside the chroot, let a successful getpwuid() inside the chroot replace it, as is already done for the uid and supplemental groups. Previously the gid found outside persisted, so for example 'chroot --userspec=alice NEWROOT' ran with alice's uid from NEWROOT but alice's gid from the host. * NEWS: Mention the bug fix.
Link: https://github.com/coreutils/coreutils/pull/363 --- NEWS | 5 +++++ src/chroot.c | 12 +++++++++--- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/NEWS b/NEWS index 7af271ceb..72f904eee 100644 --- a/NEWS +++ b/NEWS @@ -4,6 +4,11 @@ GNU coreutils NEWS -*- outline -*- ** Bug fixes + 'chroot --userspec=USER' now uses the primary group of USER as looked up + inside the chroot. Previously the group looked up outside the chroot + was used, even when the look-up inside the chroot succeeded. + [bug introduced in coreutils-8.23] + cut, expand, fold, join, numfmt, unexpand, and uniq, no longer consider the \u0085 (next line) character as a separator on non-GLIBC platforms. [bug introduced in coreutils-9.11] diff --git a/src/chroot.c b/src/chroot.c index 8ee41e4e9..cad94264e 100644 --- a/src/chroot.c +++ b/src/chroot.c @@ -228,6 +228,9 @@ main (int argc, char **argv) /* Parsed user and group IDs. */ uid_t uid = -1; gid_t gid = -1; + /* Whether GID was inferred from UID outside the chroot, + in which case a look-up inside the chroot takes precedence. */ + bool gid_inferred = false; GETGROUPS_T *out_gids = NULL; idx_t n_gids = 0; @@ -308,7 +311,10 @@ main (int argc, char **argv) if ((pwd = getpwuid (uid))) { if (gid_unset (gid)) - gid = pwd->pw_gid; + { + gid = pwd->pw_gid; + gid_inferred = true; + } username = pwd->pw_name; } } @@ -362,12 +368,12 @@ main (int argc, char **argv) /* If no gid is supplied or looked up, do so now. Also lookup the username for use with getgroups. */ - if (uid_set (uid) && (! groups || gid_unset (gid))) + if (uid_set (uid) && (! groups || gid_unset (gid) || gid_inferred)) { const struct passwd *pwd; if ((pwd = getpwuid (uid))) { - if (gid_unset (gid)) + if (gid_unset (gid) || gid_inferred) gid = pwd->pw_gid; username = pwd->pw_name; } -- 2.55.0
