import shadow-utils-4.6-11.el8

This commit is contained in:
CentOS Sources 2020-11-03 06:46:34 -05:00 committed by Andrew Lukoshko
parent 263a8e0ea1
commit e968dbc1ea
5 changed files with 985 additions and 5 deletions

View File

@ -0,0 +1,642 @@
From 140510de9de4771feb3af1d859c09604043a4c9b Mon Sep 17 00:00:00 2001
From: ikerexxe <ipedrosa@redhat.com>
Date: Fri, 27 Mar 2020 14:23:02 +0100
Subject: [PATCH 1/2] usermod: check only local groups with -G option
Check only local groups when adding new supplementary groups to a user
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1727236
---
src/usermod.c | 220 ++++++++++++++++++++++++++++++++------------------
1 file changed, 143 insertions(+), 77 deletions(-)
diff --git a/src/usermod.c b/src/usermod.c
index 05b98715..ef430296 100644
--- a/src/usermod.c
+++ b/src/usermod.c
@@ -183,6 +183,7 @@ static bool sub_gid_locked = false;
static void date_to_str (/*@unique@*//*@out@*/char *buf, size_t maxsize,
long int date);
static int get_groups (char *);
+static struct group * get_local_group (char * grp_name);
static /*@noreturn@*/void usage (int status);
static void new_pwent (struct passwd *);
static void new_spent (struct spwd *);
@@ -196,7 +197,9 @@ static void grp_update (void);
static void process_flags (int, char **);
static void close_files (void);
+static void close_group_files (void);
static void open_files (void);
+static void open_group_files (void);
static void usr_update (void);
static void move_home (void);
static void update_lastlog (void);
@@ -253,6 +256,11 @@ static int get_groups (char *list)
return 0;
}
+ /*
+ * Open the group files
+ */
+ open_group_files ();
+
/*
* So long as there is some data to be converted, strip off each
* name and look it up. A mix of numerical and string values for
@@ -272,7 +280,7 @@ static int get_groups (char *list)
* Names starting with digits are treated as numerical GID
* values, otherwise the string is looked up as is.
*/
- grp = prefix_getgr_nam_gid (list);
+ grp = get_local_group (list);
/*
* There must be a match, either by GID value or by
@@ -322,6 +330,8 @@ static int get_groups (char *list)
gr_free ((struct group *)grp);
} while (NULL != list);
+ close_group_files ();
+
user_groups[ngroups] = (char *) 0;
/*
@@ -334,6 +344,44 @@ static int get_groups (char *list)
return 0;
}
+/*
+ * get_local_group - checks if a given group name exists locally
+ *
+ * get_local_group() checks if a given group name exists locally.
+ * If the name exists the group information is returned, otherwise NULL is
+ * returned.
+ */
+static struct group * get_local_group(char * grp_name)
+{
+ const struct group *grp;
+ struct group *result_grp = NULL;
+ long long int gid;
+ char *endptr;
+
+ gid = strtoll (grp_name, &endptr, 10);
+ if ( ('\0' != *grp_name)
+ && ('\0' == *endptr)
+ && (ERANGE != errno)
+ && (gid == (gid_t)gid)) {
+ grp = gr_locate_gid ((gid_t) gid);
+ }
+ else {
+ grp = gr_locate(grp_name);
+ }
+
+ if (grp != NULL) {
+ result_grp = __gr_dup (grp);
+ if (NULL == result_grp) {
+ fprintf (stderr,
+ _("%s: Out of memory. Cannot find group '%s'.\n"),
+ Prog, grp_name);
+ fail_exit (E_GRP_UPDATE);
+ }
+ }
+
+ return result_grp;
+}
+
#ifdef ENABLE_SUBIDS
struct ulong_range
{
@@ -1447,50 +1495,7 @@ static void close_files (void)
}
if (Gflg || lflg) {
- if (gr_close () == 0) {
- fprintf (stderr,
- _("%s: failure while writing changes to %s\n"),
- Prog, gr_dbname ());
- SYSLOG ((LOG_ERR,
- "failure while writing changes to %s",
- gr_dbname ()));
- fail_exit (E_GRP_UPDATE);
- }
-#ifdef SHADOWGRP
- if (is_shadow_grp) {
- if (sgr_close () == 0) {
- fprintf (stderr,
- _("%s: failure while writing changes to %s\n"),
- Prog, sgr_dbname ());
- SYSLOG ((LOG_ERR,
- "failure while writing changes to %s",
- sgr_dbname ()));
- fail_exit (E_GRP_UPDATE);
- }
- }
-#endif
-#ifdef SHADOWGRP
- if (is_shadow_grp) {
- if (sgr_unlock () == 0) {
- fprintf (stderr,
- _("%s: failed to unlock %s\n"),
- Prog, sgr_dbname ());
- SYSLOG ((LOG_ERR,
- "failed to unlock %s",
- sgr_dbname ()));
- /* continue */
- }
- }
-#endif
- if (gr_unlock () == 0) {
- fprintf (stderr,
- _("%s: failed to unlock %s\n"),
- Prog, gr_dbname ());
- SYSLOG ((LOG_ERR,
- "failed to unlock %s",
- gr_dbname ()));
- /* continue */
- }
+ close_group_files ();
}
if (is_shadow_pwd) {
@@ -1559,6 +1564,60 @@ static void close_files (void)
#endif
}
+/*
+ * close_group_files - close all of the files that were opened
+ *
+ * close_group_files() closes all of the files that were opened related
+ * with groups. This causes any modified entries to be written out.
+ */
+static void close_group_files (void)
+{
+ if (gr_close () == 0) {
+ fprintf (stderr,
+ _("%s: failure while writing changes to %s\n"),
+ Prog, gr_dbname ());
+ SYSLOG ((LOG_ERR,
+ "failure while writing changes to %s",
+ gr_dbname ()));
+ fail_exit (E_GRP_UPDATE);
+ }
+#ifdef SHADOWGRP
+ if (is_shadow_grp) {
+ if (sgr_close () == 0) {
+ fprintf (stderr,
+ _("%s: failure while writing changes to %s\n"),
+ Prog, sgr_dbname ());
+ SYSLOG ((LOG_ERR,
+ "failure while writing changes to %s",
+ sgr_dbname ()));
+ fail_exit (E_GRP_UPDATE);
+ }
+ }
+#endif
+#ifdef SHADOWGRP
+ if (is_shadow_grp) {
+ if (sgr_unlock () == 0) {
+ fprintf (stderr,
+ _("%s: failed to unlock %s\n"),
+ Prog, sgr_dbname ());
+ SYSLOG ((LOG_ERR,
+ "failed to unlock %s",
+ sgr_dbname ()));
+ /* continue */
+ }
+ }
+#endif
+ if (gr_unlock () == 0) {
+ fprintf (stderr,
+ _("%s: failed to unlock %s\n"),
+ Prog, gr_dbname ());
+ SYSLOG ((LOG_ERR,
+ "failed to unlock %s",
+ gr_dbname ()));
+ /* continue */
+ }
+}
+
/*
* open_files - lock and open the password files
*
@@ -1594,38 +1653,7 @@ static void open_files (void)
}
if (Gflg || lflg) {
- /*
- * Lock and open the group file. This will load all of the
- * group entries.
- */
- if (gr_lock () == 0) {
- fprintf (stderr,
- _("%s: cannot lock %s; try again later.\n"),
- Prog, gr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
- gr_locked = true;
- if (gr_open (O_CREAT | O_RDWR) == 0) {
- fprintf (stderr,
- _("%s: cannot open %s\n"),
- Prog, gr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
-#ifdef SHADOWGRP
- if (is_shadow_grp && (sgr_lock () == 0)) {
- fprintf (stderr,
- _("%s: cannot lock %s; try again later.\n"),
- Prog, sgr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
- sgr_locked = true;
- if (is_shadow_grp && (sgr_open (O_CREAT | O_RDWR) == 0)) {
- fprintf (stderr,
- _("%s: cannot open %s\n"),
- Prog, sgr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
-#endif
+ open_group_files ();
}
#ifdef ENABLE_SUBIDS
if (vflg || Vflg) {
@@ -1661,6 +1689,44 @@ static void open_files (void)
#endif /* ENABLE_SUBIDS */
}
+/*
+ * open_group_files - lock and open the group files
+ *
+ * open_group_files() loads all of the group entries.
+ */
+static void open_group_files (void)
+{
+ if (gr_lock () == 0) {
+ fprintf (stderr,
+ _("%s: cannot lock %s; try again later.\n"),
+ Prog, gr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+ gr_locked = true;
+ if (gr_open (O_CREAT | O_RDWR) == 0) {
+ fprintf (stderr,
+ _("%s: cannot open %s\n"),
+ Prog, gr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+
+#ifdef SHADOWGRP
+ if (is_shadow_grp && (sgr_lock () == 0)) {
+ fprintf (stderr,
+ _("%s: cannot lock %s; try again later.\n"),
+ Prog, sgr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+ sgr_locked = true;
+ if (is_shadow_grp && (sgr_open (O_CREAT | O_RDWR) == 0)) {
+ fprintf (stderr,
+ _("%s: cannot open %s\n"),
+ Prog, sgr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+#endif
+}
+
/*
* usr_update - create the user entries
*
--
2.25.4
From 8762f465d487a52bf68f9c0b7c3c1eb3caea7bc9 Mon Sep 17 00:00:00 2001
From: ikerexxe <ipedrosa@redhat.com>
Date: Mon, 30 Mar 2020 09:08:23 +0200
Subject: [PATCH 2/2] useradd: check only local groups with -G option
Check only local groups when adding new supplementary groups to a user
Resolves: https://bugzilla.redhat.com/show_bug.cgi?id=1727236
---
src/useradd.c | 234 +++++++++++++++++++++++++++++++++-----------------
1 file changed, 157 insertions(+), 77 deletions(-)
diff --git a/src/useradd.c b/src/useradd.c
index 645d4a40..90210233 100644
--- a/src/useradd.c
+++ b/src/useradd.c
@@ -211,6 +211,7 @@ static void get_defaults (void);
static void show_defaults (void);
static int set_defaults (void);
static int get_groups (char *);
+static struct group * get_local_group (char * grp_name);
static void usage (int status);
static void new_pwent (struct passwd *);
@@ -220,7 +221,10 @@ static void grp_update (void);
static void process_flags (int argc, char **argv);
static void close_files (void);
+static void close_group_files (void);
+static void unlock_group_files (void);
static void open_files (void);
+static void open_group_files (void);
static void open_shadow (void);
static void faillog_reset (uid_t);
static void lastlog_reset (uid_t);
@@ -731,6 +735,11 @@ static int get_groups (char *list)
return 0;
}
+ /*
+ * Open the group files
+ */
+ open_group_files ();
+
/*
* So long as there is some data to be converted, strip off
* each name and look it up. A mix of numerical and string
@@ -749,7 +758,7 @@ static int get_groups (char *list)
* Names starting with digits are treated as numerical
* GID values, otherwise the string is looked up as is.
*/
- grp = prefix_getgr_nam_gid (list);
+ grp = get_local_group (list);
/*
* There must be a match, either by GID value or by
@@ -799,6 +808,9 @@ static int get_groups (char *list)
user_groups[ngroups++] = xstrdup (grp->gr_name);
} while (NULL != list);
+ close_group_files ();
+ unlock_group_files ();
+
user_groups[ngroups] = (char *) 0;
/*
@@ -811,6 +823,44 @@ static int get_groups (char *list)
return 0;
}
+/*
+ * get_local_group - checks if a given group name exists locally
+ *
+ * get_local_group() checks if a given group name exists locally.
+ * If the name exists the group information is returned, otherwise NULL is
+ * returned.
+ */
+static struct group * get_local_group(char * grp_name)
+{
+ const struct group *grp;
+ struct group *result_grp = NULL;
+ long long int gid;
+ char *endptr;
+
+ gid = strtoll (grp_name, &endptr, 10);
+ if ( ('\0' != *grp_name)
+ && ('\0' == *endptr)
+ && (ERANGE != errno)
+ && (gid == (gid_t)gid)) {
+ grp = gr_locate_gid ((gid_t) gid);
+ }
+ else {
+ grp = gr_locate(grp_name);
+ }
+
+ if (grp != NULL) {
+ result_grp = __gr_dup (grp);
+ if (NULL == result_grp) {
+ fprintf (stderr,
+ _("%s: Out of memory. Cannot find group '%s'.\n"),
+ Prog, grp_name);
+ fail_exit (E_GRP_UPDATE);
+ }
+ }
+
+ return result_grp;
+}
+
/*
* usage - display usage message and exit
*/
@@ -1530,23 +1580,9 @@ static void close_files (void)
SYSLOG ((LOG_ERR, "failure while writing changes to %s", spw_dbname ()));
fail_exit (E_PW_UPDATE);
}
- if (do_grp_update) {
- if (gr_close () == 0) {
- fprintf (stderr,
- _("%s: failure while writing changes to %s\n"), Prog, gr_dbname ());
- SYSLOG ((LOG_ERR, "failure while writing changes to %s", gr_dbname ()));
- fail_exit (E_GRP_UPDATE);
- }
-#ifdef SHADOWGRP
- if (is_shadow_grp && (sgr_close () == 0)) {
- fprintf (stderr,
- _("%s: failure while writing changes to %s\n"),
- Prog, sgr_dbname ());
- SYSLOG ((LOG_ERR, "failure while writing changes to %s", sgr_dbname ()));
- fail_exit (E_GRP_UPDATE);
- }
-#endif
- }
+
+ close_group_files ();
+
#ifdef ENABLE_SUBIDS
if (is_sub_uid && (sub_uid_close () == 0)) {
fprintf (stderr,
@@ -1587,34 +1623,9 @@ static void close_files (void)
/* continue */
}
pw_locked = false;
- if (gr_unlock () == 0) {
- fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, gr_dbname ());
- SYSLOG ((LOG_ERR, "failed to unlock %s", gr_dbname ()));
-#ifdef WITH_AUDIT
- audit_logger (AUDIT_ADD_USER, Prog,
- "unlocking-group-file",
- user_name, AUDIT_NO_ID,
- SHADOW_AUDIT_FAILURE);
-#endif
- /* continue */
- }
- gr_locked = false;
-#ifdef SHADOWGRP
- if (is_shadow_grp) {
- if (sgr_unlock () == 0) {
- fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, sgr_dbname ());
- SYSLOG ((LOG_ERR, "failed to unlock %s", sgr_dbname ()));
-#ifdef WITH_AUDIT
- audit_logger (AUDIT_ADD_USER, Prog,
- "unlocking-gshadow-file",
- user_name, AUDIT_NO_ID,
- SHADOW_AUDIT_FAILURE);
-#endif
- /* continue */
- }
- sgr_locked = false;
- }
-#endif
+
+ unlock_group_files ();
+
#ifdef ENABLE_SUBIDS
if (is_sub_uid) {
if (sub_uid_unlock () == 0) {
@@ -1647,6 +1658,71 @@ static void close_files (void)
#endif /* ENABLE_SUBIDS */
}
+/*
+ * close_group_files - close all of the files that were opened
+ *
+ * close_group_files() closes all of the files that were opened related
+ * with groups. This causes any modified entries to be written out.
+ */
+static void close_group_files (void)
+{
+ if (do_grp_update) {
+ if (gr_close () == 0) {
+ fprintf (stderr,
+ _("%s: failure while writing changes to %s\n"), Prog, gr_dbname ());
+ SYSLOG ((LOG_ERR, "failure while writing changes to %s", gr_dbname ()));
+ fail_exit (E_GRP_UPDATE);
+ }
+#ifdef SHADOWGRP
+ if (is_shadow_grp && (sgr_close () == 0)) {
+ fprintf (stderr,
+ _("%s: failure while writing changes to %s\n"),
+ Prog, sgr_dbname ());
+ SYSLOG ((LOG_ERR, "failure while writing changes to %s", sgr_dbname ()));
+ fail_exit (E_GRP_UPDATE);
+ }
+#endif /* SHADOWGRP */
+ }
+}
+
+/*
+ * unlock_group_files - unlock all of the files that were locked
+ *
+ * unlock_group_files() unlocks all of the files that were locked related
+ * with groups. This causes any modified entries to be written out.
+ */
+static void unlock_group_files (void)
+{
+ if (gr_unlock () == 0) {
+ fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, gr_dbname ());
+ SYSLOG ((LOG_ERR, "failed to unlock %s", gr_dbname ()));
+#ifdef WITH_AUDIT
+ audit_logger (AUDIT_ADD_USER, Prog,
+ "unlocking-group-file",
+ user_name, AUDIT_NO_ID,
+ SHADOW_AUDIT_FAILURE);
+#endif /* WITH_AUDIT */
+ /* continue */
+ }
+ gr_locked = false;
+#ifdef SHADOWGRP
+ if (is_shadow_grp) {
+ if (sgr_unlock () == 0) {
+ fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, sgr_dbname ());
+ SYSLOG ((LOG_ERR, "failed to unlock %s", sgr_dbname ()));
+#ifdef WITH_AUDIT
+ audit_logger (AUDIT_ADD_USER, Prog,
+ "unlocking-gshadow-file",
+ user_name, AUDIT_NO_ID,
+ SHADOW_AUDIT_FAILURE);
+#endif /* WITH_AUDIT */
+ /* continue */
+ }
+ sgr_locked = false;
+ }
+#endif /* SHADOWGRP */
+}
+
/*
* open_files - lock and open the password files
*
@@ -1668,37 +1744,8 @@ static void open_files (void)
/* shadow file will be opened by open_shadow(); */
- /*
- * Lock and open the group file.
- */
- if (gr_lock () == 0) {
- fprintf (stderr,
- _("%s: cannot lock %s; try again later.\n"),
- Prog, gr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
- gr_locked = true;
- if (gr_open (O_CREAT | O_RDWR) == 0) {
- fprintf (stderr, _("%s: cannot open %s\n"), Prog, gr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
-#ifdef SHADOWGRP
- if (is_shadow_grp) {
- if (sgr_lock () == 0) {
- fprintf (stderr,
- _("%s: cannot lock %s; try again later.\n"),
- Prog, sgr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
- sgr_locked = true;
- if (sgr_open (O_CREAT | O_RDWR) == 0) {
- fprintf (stderr,
- _("%s: cannot open %s\n"),
- Prog, sgr_dbname ());
- fail_exit (E_GRP_UPDATE);
- }
- }
-#endif
+ open_group_files ();
+
#ifdef ENABLE_SUBIDS
if (is_sub_uid) {
if (sub_uid_lock () == 0) {
@@ -1733,6 +1780,39 @@ static void open_files (void)
#endif /* ENABLE_SUBIDS */
}
+static void open_group_files (void)
+{
+ if (gr_lock () == 0) {
+ fprintf (stderr,
+ _("%s: cannot lock %s; try again later.\n"),
+ Prog, gr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+ gr_locked = true;
+ if (gr_open (O_CREAT | O_RDWR) == 0) {
+ fprintf (stderr, _("%s: cannot open %s\n"), Prog, gr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+
+#ifdef SHADOWGRP
+ if (is_shadow_grp) {
+ if (sgr_lock () == 0) {
+ fprintf (stderr,
+ _("%s: cannot lock %s; try again later.\n"),
+ Prog, sgr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+ sgr_locked = true;
+ if (sgr_open (O_CREAT | O_RDWR) == 0) {
+ fprintf (stderr,
+ _("%s: cannot open %s\n"),
+ Prog, sgr_dbname ());
+ fail_exit (E_GRP_UPDATE);
+ }
+ }
+#endif /* SHADOWGRP */
+}
+
static void open_shadow (void)
{
if (!is_shadow_pwd) {
--
2.25.4

View File

@ -0,0 +1,201 @@
From a847899b521b0df0665e442845bcff23407d9ea0 Mon Sep 17 00:00:00 2001
From: Duncan Overbruck <mail@duncano.de>
Date: Sat, 11 Jan 2020 22:19:37 +0100
Subject: [PATCH] add new HOME_MODE login.defs(5) option
This option can be used to set a separate mode for useradd(8) and
newusers(8) to create the home directories with.
If this option is not set, the current behavior of using UMASK
or the default umask is preserved.
There are many distributions that set UMASK to 077 by default just
to create home directories not readable by others and use things like
/etc/profile, bashrc or sudo configuration files to set a less
restrictive
umask. This has always resulted in bug reports because it is hard
to follow as users tend to change files like bashrc and are not about
setting the umask to counteract the umask set in /etc/login.defs.
A recent change in sudo has also resulted in many bug reports about
this. sudo now tries to respect the umask set by pam modules and on
systems where pam does not set a umask, the login.defs UMASK value is
used.
---
etc/login.defs | 7 ++++++-
lib/getdef.c | 1 +
man/login.defs.5.xml | 4 ++++
man/login.defs.d/UMASK.xml | 3 ++-
src/newusers.c | 6 +++---
src/useradd.c | 5 +++--
6 files changed, 19 insertions(+), 7 deletions(-)
diff --git a/etc/login.defs b/etc/login.defs
index cd2597dc..a2f8cd50 100644
--- a/etc/login.defs
+++ b/etc/login.defs
@@ -195,12 +195,17 @@ KILLCHAR 025
# Default initial "umask" value used by login(1) on non-PAM enabled systems.
# Default "umask" value for pam_umask(8) on PAM enabled systems.
# UMASK is also used by useradd(8) and newusers(8) to set the mode for new
-# home directories.
+# home directories if HOME_MODE is not set.
# 022 is the default value, but 027, or even 077, could be considered
# for increased privacy. There is no One True Answer here: each sysadmin
# must make up their mind.
UMASK 022
+# HOME_MODE is used by useradd(8) and newusers(8) to set the mode for new
+# home directories.
+# If HOME_MODE is not set, the value of UMASK is used to create the mode.
+HOME_MODE 0700
+
#
# Password aging controls:
#
diff --git a/lib/getdef.c b/lib/getdef.c
index bbb273f4..00f6abfe 100644
--- a/lib/getdef.c
+++ b/lib/getdef.c
@@ -93,6 +93,7 @@ static struct itemdef def_table[] = {
{"FAKE_SHELL", NULL},
{"GID_MAX", NULL},
{"GID_MIN", NULL},
+ {"HOME_MODE", NULL},
{"HUSHLOGIN_FILE", NULL},
{"KILLCHAR", NULL},
{"LOGIN_RETRIES", NULL},
diff --git a/man/login.defs.5.xml b/man/login.defs.5.xml
index ebf60ba3..9e95da20 100644
--- a/man/login.defs.5.xml
+++ b/man/login.defs.5.xml
@@ -50,6 +50,7 @@
<!ENTITY FAKE_SHELL SYSTEM "login.defs.d/FAKE_SHELL.xml">
<!ENTITY FTMP_FILE SYSTEM "login.defs.d/FTMP_FILE.xml">
<!ENTITY GID_MAX SYSTEM "login.defs.d/GID_MAX.xml">
+<!ENTITY HOME_MODE SYSTEM "login.defs.d/HOME_MODE.xml">
<!ENTITY HUSHLOGIN_FILE SYSTEM "login.defs.d/HUSHLOGIN_FILE.xml">
<!ENTITY ISSUE_FILE SYSTEM "login.defs.d/ISSUE_FILE.xml">
<!ENTITY KILLCHAR SYSTEM "login.defs.d/KILLCHAR.xml">
@@ -185,6 +186,7 @@
&FAKE_SHELL;
&FTMP_FILE;
&GID_MAX; <!-- documents also GID_MIN -->
+ &HOME_MODE;
&HUSHLOGIN_FILE;
&ISSUE_FILE;
&KILLCHAR;
@@ -401,6 +403,7 @@
ENCRYPT_METHOD
GID_MAX GID_MIN
MAX_MEMBERS_PER_GROUP MD5_CRYPT_ENAB
+ HOME_MODE
PASS_MAX_DAYS PASS_MIN_DAYS PASS_WARN_AGE
<phrase condition="sha_crypt">SHA_CRYPT_MAX_ROUNDS
SHA_CRYPT_MIN_ROUNDS</phrase>
@@ -481,6 +484,7 @@
<para>
CREATE_HOME
GID_MAX GID_MIN
+ HOME_MODE
MAIL_DIR MAX_MEMBERS_PER_GROUP
PASS_MAX_DAYS PASS_MIN_DAYS PASS_WARN_AGE
SUB_GID_COUNT SUB_GID_MAX SUB_GID_MIN
diff --git a/man/login.defs.d/HOME_MODE.xml b/man/login.defs.d/HOME_MODE.xml
new file mode 100644
index 00000000..21aa55f7
--- /dev/null
+++ b/man/login.defs.d/HOME_MODE.xml
@@ -0,0 +1,43 @@
+<!--
+ Copyright (c) 1991 - 1993, Julianne Frances Haugh
+ Copyright (c) 1991 - 1993, Chip Rosenthal
+ Copyright (c) 2007 - 2009, Nicolas François
+ All rights reserved.
+
+ Redistribution and use in source and binary forms, with or without
+ modification, are permitted provided that the following conditions
+ are met:
+ 1. Redistributions of source code must retain the above copyright
+ notice, this list of conditions and the following disclaimer.
+ 2. Redistributions in binary form must reproduce the above copyright
+ notice, this list of conditions and the following disclaimer in the
+ documentation and/or other materials provided with the distribution.
+ 3. The name of the copyright holders or contributors may not be used to
+ endorse or promote products derived from this software without
+ specific prior written permission.
+
+ THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+-->
+<varlistentry>
+ <term><option>HOME_MODE</option> (number)</term>
+ <listitem>
+ <para>
+ The mode for new home directories. If not specified,
+ the <option>UMASK</option> is used to create the mode.
+ </para>
+ <para>
+ <command>useradd</command> and <command>newusers</command> use this
+ to set the mode of the home directory they create.
+ </para>
+ </listitem>
+</varlistentry>
diff --git a/man/login.defs.d/UMASK.xml b/man/login.defs.d/UMASK.xml
index d7b71a5e..0f061dbb 100644
--- a/man/login.defs.d/UMASK.xml
+++ b/man/login.defs.d/UMASK.xml
@@ -37,7 +37,8 @@
</para>
<para>
<command>useradd</command> and <command>newusers</command> use this
- mask to set the mode of the home directory they create
+ mask to set the mode of the home directory they create if
+ <option>HOME_MODE</option> is not set.
</para>
<para condition="no_pam">
It is also used by <command>login</command> to define users' initial
diff --git a/src/newusers.c b/src/newusers.c
index 99c69f78..e9fe0e27 100644
--- a/src/newusers.c
+++ b/src/newusers.c
@@ -1216,9 +1216,9 @@ int main (int argc, char **argv)
if ( ('\0' != fields[5][0])
&& (access (newpw.pw_dir, F_OK) != 0)) {
/* FIXME: should check for directory */
- mode_t msk = 0777 & ~getdef_num ("UMASK",
- GETDEF_DEFAULT_UMASK);
- if (mkdir (newpw.pw_dir, msk) != 0) {
+ mode_t mode = getdef_num ("HOME_MODE",
+ 0777 & ~getdef_num ("UMASK", GETDEF_DEFAULT_UMASK));
+ if (mkdir (newpw.pw_dir, mode) != 0) {
fprintf (stderr,
_("%s: line %d: mkdir %s failed: %s\n"),
Prog, line, newpw.pw_dir,
diff --git a/src/useradd.c b/src/useradd.c
index 4af0f7c6..8b453e3c 100644
--- a/src/useradd.c
+++ b/src/useradd.c
@@ -2152,8 +2152,9 @@ static void create_home (void)
fail_exit (E_HOMEDIR);
}
(void) chown (prefix_user_home, user_id, user_gid);
- chmod (prefix_user_home,
- 0777 & ~getdef_num ("UMASK", GETDEF_DEFAULT_UMASK));
+ mode_t mode = getdef_num ("HOME_MODE",
+ 0777 & ~getdef_num ("UMASK", GETDEF_DEFAULT_UMASK));
+ chmod (prefix_user_home, mode);
home_added = true;
#ifdef WITH_AUDIT
audit_logger (AUDIT_USER_MGMT, Prog,
--
2.25.2

View File

@ -0,0 +1,108 @@
From fd4405b763d26649339069532e79bd45013c8c38 Mon Sep 17 00:00:00 2001
From: Tomas Mraz <tmraz@fedoraproject.org>
Date: Mon, 20 Jan 2020 13:58:07 +0100
Subject: [PATCH] Do not mistake a regular user process for a namespaced one
In case there is a regular user with a process running on a system
with uid falling into a namespaced uid range of another user.
The user with the colliding namespaced uid range will not be
allowed to be deleted without forcing the action with -f.
The user_busy() is adjusted to check whether the suspected process
is really a namespaced process in a different namespace.
---
libmisc/user_busy.c | 44 ++++++++++++++++++++++++++++++++++++--------
1 file changed, 36 insertions(+), 8 deletions(-)
diff --git a/libmisc/user_busy.c b/libmisc/user_busy.c
index b0867568..324bb946 100644
--- a/libmisc/user_busy.c
+++ b/libmisc/user_busy.c
@@ -39,6 +39,7 @@
#include <sys/types.h>
#include <dirent.h>
#include <fcntl.h>
+#include <unistd.h>
#include "defines.h"
#include "prototypes.h"
#ifdef ENABLE_SUBIDS
@@ -106,6 +107,31 @@ static int user_busy_utmp (const char *name)
#endif /* !__linux__ */
#ifdef __linux__
+#ifdef ENABLE_SUBIDS
+#define in_parentuid_range(uid) ((uid) >= parentuid && (uid) < parentuid + range)
+static int different_namespace (const char *sname)
+{
+ /* 41: /proc/xxxxxxxxxx/task/xxxxxxxxxx/ns/user + \0 */
+ char path[41];
+ char buf[512], buf2[512];
+ ssize_t llen1, llen2;
+
+ snprintf (path, 41, "/proc/%s/ns/user", sname);
+
+ if ((llen1 = readlink (path, buf, sizeof(buf))) == -1)
+ return 0;
+
+ if ((llen2 = readlink ("/proc/self/ns/user", buf2, sizeof(buf2))) == -1)
+ return 0;
+
+ if (llen1 == llen2 && memcmp (buf, buf2, llen1) == 0)
+ return 0; /* same namespace */
+
+ return 1;
+}
+#endif /* ENABLE_SUBIDS */
+
+
static int check_status (const char *name, const char *sname, uid_t uid)
{
/* 40: /proc/xxxxxxxxxx/task/xxxxxxxxxx/status + \0 */
@@ -114,7 +140,6 @@ static int check_status (const char *name, const char *sname, uid_t uid)
FILE *sfile;
snprintf (status, 40, "/proc/%s/status", sname);
- status[39] = '\0';
sfile = fopen (status, "r");
if (NULL == sfile) {
@@ -123,26 +148,29 @@ static int check_status (const char *name, const char *sname, uid_t uid)
while (fgets (line, sizeof (line), sfile) == line) {
if (strncmp (line, "Uid:\t", 5) == 0) {
unsigned long ruid, euid, suid;
+
assert (uid == (unsigned long) uid);
+ (void) fclose (sfile);
if (sscanf (line,
"Uid:\t%lu\t%lu\t%lu\n",
&ruid, &euid, &suid) == 3) {
if ( (ruid == (unsigned long) uid)
|| (euid == (unsigned long) uid)
- || (suid == (unsigned long) uid)
+ || (suid == (unsigned long) uid) ) {
+ return 1;
+ }
#ifdef ENABLE_SUBIDS
- || have_sub_uids(name, ruid, 1)
- || have_sub_uids(name, euid, 1)
- || have_sub_uids(name, suid, 1)
-#endif /* ENABLE_SUBIDS */
+ if ( different_namespace (sname)
+ && ( have_sub_uids(name, ruid, 1)
+ || have_sub_uids(name, euid, 1)
+ || have_sub_uids(name, suid, 1))
) {
- (void) fclose (sfile);
return 1;
}
+#endif /* ENABLE_SUBIDS */
} else {
/* Ignore errors. This is just a best effort. */
}
- (void) fclose (sfile);
return 0;
}
}
--
2.25.2

View File

@ -15,6 +15,20 @@
MAIL_DIR /var/spool/mail
#MAIL_FILE .mail
# Default initial "umask" value used by login(1) on non-PAM enabled systems.
# Default "umask" value for pam_umask(8) on PAM enabled systems.
# UMASK is also used by useradd(8) and newusers(8) to set the mode for new
# home directories if HOME_MODE is not set.
# 022 is the default value, but 027, or even 077, could be considered
# for increased privacy. There is no One True Answer here: each sysadmin
# must make up their mind.
UMASK 022
# HOME_MODE is used by useradd(8) and newusers(8) to set the mode for new
# home directories.
# If HOME_MODE is not set, the value of UMASK is used to create the mode.
HOME_MODE 0700
# Password aging controls:
#
# PASS_MAX_DAYS Maximum number of days a password may be used.
@ -59,10 +73,6 @@ SYS_GID_MAX 999
#
CREATE_HOME yes
# The permission mask is initialized to this value. If not specified,
# the permission mask will be initialized to 022.
UMASK 077
# This enables userdel to remove user groups if no members exist.
#
USERGROUPS_ENAB yes

View File

@ -1,7 +1,7 @@
Summary: Utilities for managing accounts and shadow password files
Name: shadow-utils
Version: 4.6
Release: 8%{?dist}
Release: 11%{?dist}
Epoch: 2
URL: http://pkg-shadow.alioth.debian.org/
Source0: https://github.com/shadow-maint/shadow/releases/download/%{version}/shadow-%{version}.tar.xz
@ -37,6 +37,12 @@ Patch38: shadow-4.6-sysugid-min-limit.patch
Patch39: shadow-4.6-chgrp-guard.patch
Patch40: shadow-4.6-ignore-login-prompt.patch
Patch41: shadow-4.6-use-lckpwdf.patch
# Upstreamed
Patch42: shadow-4.6-regular-user.patch
# Upstreamed
Patch43: shadow-4.6-home_mode-directive.patch
# Upstreamed
Patch44: shadow-4.6-check-local-groups.patch
License: BSD and GPLv2+
Group: System Environment/Base
@ -96,6 +102,9 @@ are used for managing group accounts.
%patch39 -p1 -b .chgrp-guard
%patch40 -p1 -b .login-prompt
%patch41 -p1 -b .use-lckpwdf
%patch42 -p1 -b .regular-user
%patch43 -p1 -b .home_mode-directive
%patch44 -p1 -b .check-local-groups
iconv -f ISO88591 -t utf-8 doc/HOWTO > doc/HOWTO.utf8
cp -f doc/HOWTO.utf8 doc/HOWTO
@ -250,6 +259,16 @@ done
%{_mandir}/man8/vigr.8*
%changelog
* Fri Aug 7 2020 Iker Pedrosa <ipedrosa@redhat.com> - 2:4.6-11
- change UMASK value and add HOME_MODE in login.defs (#1777718)
* Tue May 5 2020 Iker Pedrosa <ipedrosa@redhat.com> - 2:4.6-10
- check only local groups when adding new supplementary groups to a user
* Fri Apr 17 2020 Iker Pedrosa <ipedrosa@redhat.com> - 2:4.6-9
- do not mistake a regular user process for a namespaced one (#1788696)
- add HOME_MODE support in login.defs (#1777718)
* Fri Jun 7 2019 Tomáš Mráz <tmraz@redhat.com> - 2:4.6-8
- properly audit group password change
- do not add uid of a new (not yet added) user to the audit message