]> git.ipfire.org Git - thirdparty/shadow.git/log
thirdparty/shadow.git
2 months agosubid: use is_same_user() for owner resolution in find_range
Pat Riehecky [Tue, 10 Mar 2026 14:47:26 +0000 (09:47 -0500)] 
subid: use is_same_user() for owner resolution in find_range

Replace the resolution in find_range with is_same_user(). The
actualy results should be the same.

Previously, find_range performed its own getpwnam() based UID lookup to
handle entries recorded by UID or by username. This duplicated logic
centralized in is_same_user().

is_same_user() resolves ownership by username, UID, and overlapping
entries, making find_range consistent with how ownership is determined
elsewhere.

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
2 months agosubid: use is_same_user() for owner resolution in range queries
Pat Riehecky [Tue, 10 Mar 2026 14:42:48 +0000 (09:42 -0500)] 
subid: use is_same_user() for owner resolution in range queries

Replace direct owner string comparison in range_exists, get_owner_id,
list_owner_ranges, and new_subid_range with is_same_user().

Previously, ownership checks required a literal match against the owner
field. This created a situation where if entries were recorded by UID and
by username not all would be identified.

is_same_user() resolves ownership by username, UID, and overlapping
entries, making range queries consistent with how ownership is determined
elsewhere.

Fixes: 0a7888b1 (2020-06-07; "Create a new libsubid")
CC: Serge Hallyn <serge@hallyn.com>
Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
2 months agosubid: Add is_same_user for unified ID lookups
Pat Riehecky [Tue, 10 Mar 2026 14:39:57 +0000 (09:39 -0500)] 
subid: Add is_same_user for unified ID lookups

Each identifier is resolved via getpw_uid_or_nam and compared
numerically. Accepts usernames, numeric UIDs, or a mix of both.

Numeric resolution ensures stale entries for deleted users cannot
produce false matches, and handles systems with overlapping UIDs.

We do not perform a streq(3) on the passed strings themselves.
In this way we ensure the user is resolvable on the system
eliminating the ability to return results from deleted users
with stale entries.

Returns false if either identifier cannot be resolved, or if the
resolved UIDs do not match.

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
2 months agolib/shadow/passwd/: getpw_uid_or_nam(): Add function
Alejandro Colomar [Wed, 11 Mar 2026 19:29:22 +0000 (20:29 +0100)] 
lib/shadow/passwd/: getpw_uid_or_nam(): Add function

Signed-off-by: Alejandro Colomar <alx@kernel.org>
2 months agoTests: Add a new user with a specified existing numerical primary group
aborah-sudo [Wed, 25 Mar 2026 04:19:33 +0000 (09:49 +0530)] 
Tests: Add a new user with a specified existing numerical primary group

This is the transformation to Python of the test located in
`tests/usertools/01/07_useradd_numerical_primary_group.test`, which checks that `useradd` can add a new user with valid existing group as primary

2 months agotests/system/tests/test_vipw.py: implement basic tests
Iker Pedrosa [Fri, 12 Sep 2025 11:54:35 +0000 (13:54 +0200)] 
tests/system/tests/test_vipw.py: implement basic tests

* Run vipw on passwd file and add a user
* Run vipw on shadow file and add a user
* Run vipw on group file and add a group
* Run vipw on gshadow file and add a group

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agoshare/ansible/: create the /etc/gshadow in OpenSUSE
Iker Pedrosa [Fri, 12 Sep 2025 12:58:57 +0000 (14:58 +0200)] 
share/ansible/: create the /etc/gshadow in OpenSUSE

Temporary workaround to create the /etc/gshadow in OpenSUSE.

Link: <https://forums.opensuse.org/t/no-etc-gshadow-gpasswd-puts-password-hash-into-world-readable-etc-group/179019>
Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agoshare/ansible/roles/ci_run/tasks/: add `vim` dependency
Iker Pedrosa [Thu, 11 Sep 2025 14:11:59 +0000 (16:11 +0200)] 
share/ansible/roles/ci_run/tasks/: add `vim` dependency

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/roles/shadow.py: implement binding for `vipw`
Iker Pedrosa [Thu, 11 Sep 2025 09:38:59 +0000 (11:38 +0200)] 
tests/system/framework/roles/shadow.py: implement binding for `vipw`

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_chgpasswd.py: change multiple group passwords from file
Iker Pedrosa [Thu, 11 Sep 2025 07:11:41 +0000 (09:11 +0200)] 
tests/system/tests/test_chgpasswd.py: change multiple group passwords from file

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_chgpasswd.py: change multiple group passwords interactive
Iker Pedrosa [Wed, 10 Sep 2025 14:57:41 +0000 (16:57 +0200)] 
tests/system/tests/test_chgpasswd.py: change multiple group passwords interactive

This is the transformation to Python of the test located in
`tests/grouptools/chgpasswd/02_chgpasswd_multiple_groups/chgpasswd.test`,
which checks that `chgpasswd` is able to change the password of multiple
groups in batch.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/roles/shadow.py: implement binding for `chgpasswd`
Iker Pedrosa [Wed, 10 Sep 2025 14:53:02 +0000 (16:53 +0200)] 
tests/system/framework/roles/shadow.py: implement binding for `chgpasswd`

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_gpasswd.py: add user to group membership as non-root user
Iker Pedrosa [Wed, 10 Sep 2025 10:58:24 +0000 (12:58 +0200)] 
tests/system/tests/test_gpasswd.py: add user to group membership as non-root user

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_gpasswd.py: add user as group administrator
Iker Pedrosa [Wed, 10 Sep 2025 10:20:19 +0000 (12:20 +0200)] 
tests/system/tests/test_gpasswd.py: add user as group administrator

This is the transformation to Python of the test located in
`tests/grouptools/gpasswd/50_gpasswd_change_admin_list/gpasswd.test`,
which checks that `gpasswd` is able to add a user as a group
administrator.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/conftest.py: import markers plugin
Iker Pedrosa [Wed, 10 Sep 2025 10:18:30 +0000 (12:18 +0200)] 
tests/system/conftest.py: import markers plugin

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_gpasswd.py: add user to group membership as root user
Iker Pedrosa [Wed, 10 Sep 2025 09:26:56 +0000 (11:26 +0200)] 
tests/system/tests/test_gpasswd.py: add user to group membership as root user

This is the transformation to Python of the test located in
`tests/grouptools/gpasswd/31_gpasswd_add_user_to_group/gpasswd.test`,
which checks that `gpasswd` is able to add a user to a group membership
running as root.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/roles/shadow.py: implement binding for `gpasswd`
Iker Pedrosa [Wed, 10 Sep 2025 07:53:15 +0000 (09:53 +0200)] 
tests/system/framework/roles/shadow.py: implement binding for `gpasswd`

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_chpasswd.py: change multiple user passwords from file
Iker Pedrosa [Tue, 9 Sep 2025 11:14:07 +0000 (13:14 +0200)] 
tests/system/tests/test_chpasswd.py: change multiple user passwords from file

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_chpasswd.py: change multiple user passwords interactive
Iker Pedrosa [Tue, 9 Sep 2025 07:30:23 +0000 (09:30 +0200)] 
tests/system/tests/test_chpasswd.py: change multiple user passwords interactive

This is the transformation to Python of the test located in
`tests/usertools/chpasswd/02_chpasswd_multiple_users/chpasswd.test`,
which checks that `chpasswd` is able to change the password of multiple
users in batch.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/roles/shadow.py: implement binding for `chpasswd`
Iker Pedrosa [Mon, 8 Sep 2025 14:49:56 +0000 (16:49 +0200)] 
tests/system/framework/roles/shadow.py: implement binding for `chpasswd`

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agoshare/ansible/: create the chpasswd PAM service file
Iker Pedrosa [Mon, 8 Sep 2025 14:50:35 +0000 (16:50 +0200)] 
share/ansible/: create the chpasswd PAM service file

Temporary workaround to create the chpasswd PAM service file. Fedora
will soon provide this service file and we'll be able to remove the
workaround.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_passwd.py: lock user password
Iker Pedrosa [Mon, 23 Feb 2026 13:35:28 +0000 (14:35 +0100)] 
tests/system/tests/test_passwd.py: lock user password

This is the transformation to Python of the test located in
`tests/passwd/06_passwd_-l_root_lock_account/passwd.test`,
which checks that `passwd` is able to lock a user's password.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_passwd.py: change user password as root in interactive mode
Iker Pedrosa [Tue, 9 Sep 2025 07:23:30 +0000 (09:23 +0200)] 
tests/system/tests/test_passwd.py: change user password as root in interactive mode

This is the transformation to Python of the test located in
`tests/passwd/18_passwd_root_change_password_user/passwd.test`,
which checks that `passwd` is able to change a user's password running
as root in interactive mode.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/tests/test_passwd.py: change user password as root using stdin
Iker Pedrosa [Mon, 8 Sep 2025 09:10:05 +0000 (11:10 +0200)] 
tests/system/tests/test_passwd.py: change user password as root using stdin

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/misc/__init__.py: password pattern
Iker Pedrosa [Tue, 9 Sep 2025 07:20:17 +0000 (09:20 +0200)] 
tests/system/framework/misc/__init__.py: password pattern

Expose shadow's password regex pattern in a function.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/framework/roles/shadow.py: implement binding for `passwd`
Iker Pedrosa [Thu, 4 Sep 2025 14:13:50 +0000 (16:13 +0200)] 
tests/system/framework/roles/shadow.py: implement binding for `passwd`

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agoshare/ansible/roles/ci_run/tasks/fedora.yml: add dependency
Iker Pedrosa [Mon, 8 Sep 2025 10:34:21 +0000 (12:34 +0200)] 
share/ansible/roles/ci_run/tasks/fedora.yml: add dependency

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agotests/system/etc/login.defs: define ENCRYPT_METHOD
Iker Pedrosa [Mon, 8 Sep 2025 10:34:48 +0000 (12:34 +0200)] 
tests/system/etc/login.defs: define ENCRYPT_METHOD

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
2 months agoTests: Add a new user with a specified non-existing primary group
aborah-sudo [Mon, 23 Mar 2026 05:12:09 +0000 (10:42 +0530)] 
Tests: Add a new user with a specified non-existing primary group

This is the transformation to Python of the test located in
`tests/usertools/01/06_useradd_invalid_named_primary_group.test`, which checks that `useradd` can not add a new user with invalid existing group as primary

2 months agolib/attr.h: exclude MCST LCC compiler from ATTR_MALLOC
a1batross [Sun, 22 Mar 2026 10:41:03 +0000 (15:41 +0500)] 
lib/attr.h: exclude MCST LCC compiler from ATTR_MALLOC

This particular compiler defines GCC compatibility like Clang but doesn't support this attribute.

Signed-off-by: Alibek Omarov <a1ba.omarov@gmail.com>
3 months agolib/string/README: [v]aprintf(3) are in libc
Alejandro Colomar [Thu, 19 Mar 2026 00:45:24 +0000 (01:45 +0100)] 
lib/string/README: [v]aprintf(3) are in libc

[v]aprintf(3) are now part of a libc implementation: gnulib.
They are also documented in a manual page.  Thus, refer to them as
[v]aprintf(3).

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agoTests: Add a new user with a valid existing group as primary
aborah-sudo [Tue, 17 Mar 2026 05:22:28 +0000 (10:52 +0530)] 
Tests: Add a new user with a valid existing group as primary

This is the transformation to Python of the test located in
`tests/usertools/01/08_useradd_named_primary_group.test`, which checks that `useradd` can add a new user with a valid existing group as primary

3 months agousermod: make fail_exit the reverse of the locking in open_files
Pat Riehecky [Tue, 10 Mar 2026 13:30:49 +0000 (08:30 -0500)] 
usermod: make fail_exit the reverse of the locking in open_files

Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
3 months agousermod: close_files should unlock in reverse of open_files
Pat Riehecky [Tue, 10 Mar 2026 13:42:32 +0000 (08:42 -0500)] 
usermod: close_files should unlock in reverse of open_files

Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
3 months agousermod: only unlock on close_files if we actually locked them
Pat Riehecky [Tue, 10 Mar 2026 13:37:29 +0000 (08:37 -0500)] 
usermod: only unlock on close_files if we actually locked them

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
3 months agousermod: only lock shadow file as needed
Pat Riehecky [Mon, 9 Mar 2026 16:43:12 +0000 (11:43 -0500)] 
usermod: only lock shadow file as needed

When setting user attributes that have nothing to do with shadow
we don't need to lock it.

Closes: https://github.com/shadow-maint/shadow/issues/1540
Signed-off-by: Pat Riehecky <riehecky@fnal.gov>
3 months agoTests: Add a new user with a specified non-existing gid
aborah-sudo [Fri, 13 Mar 2026 05:33:10 +0000 (11:03 +0530)] 
Tests: Add a new user with a specified non-existing gid

This is the transformation to Python of the test located in
`tests/usertools/01/05_useradd_invalid_numeric_primary_group.test`, which checks that `useradd` fails to create a new user with non-existing group

3 months agolib/io/README: Add file
Alejandro Colomar [Fri, 13 Mar 2026 00:53:38 +0000 (01:53 +0100)] 
lib/io/README: Add file

This documents the main APIs under 'lib/io/'.

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/, src/: Use fgets_a() instead of its pattern
Alejandro Colomar [Mon, 12 Aug 2024 01:24:48 +0000 (03:24 +0200)] 
lib/, src/: Use fgets_a() instead of its pattern

Except for the updated includes, this patch has been scripted with a
semantic patch:

$ cat ~/tmp/spatch/fgets_fgets_a.sp
@@
expression a, b;
@@

- fgets(a, countof(a), b)
+ fgets_a(a, b)

Applied as:

$ find lib* src -type f \
| xargs spatch --sp-file ~/tmp/spatch/fgets_fgets_a.sp --in-place;

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/io/: fgets_a(): Add macro
Alejandro Colomar [Mon, 12 Aug 2024 01:20:46 +0000 (03:20 +0200)] 
lib/io/: fgets_a(): Add macro

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/: Use countof() instead of hardcoded lengths
Alejandro Colomar [Mon, 12 Aug 2024 01:01:10 +0000 (03:01 +0200)] 
lib/: Use countof() instead of hardcoded lengths

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/fields.c: change_field(): Use a VLA
Alejandro Colomar [Mon, 12 Aug 2024 00:57:18 +0000 (02:57 +0200)] 
lib/fields.c: change_field(): Use a VLA

This allows using countof(), which is safer than a decoupled use of
the variable containing the length of the array.

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/, src/: Use countof() instead of sizeof() with fgets(3)
Alejandro Colomar [Mon, 12 Aug 2024 00:50:26 +0000 (02:50 +0200)] 
lib/, src/: Use countof() instead of sizeof() with fgets(3)

Except for the added includes, this patch has been scripted with a
semantic patch:

$ cat ~/tmp/spatch/fgets_nitems.sp
@@
expression a, b, c;
@@

- fgets(a, sizeof(b), c)
+ fgets(a, countof(b), c)

@@
expression a, b, c;
@@

- fgets(a, sizeof b, c)
+ fgets(a, countof(b), c)

Applied as:

$ find lib* src/ -type f \
| xargs spatch --sp-file ~/tmp/spatch/fgets_nitems.sp --in-place;

Reviewed-by: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agousermod: Update passwd entry when shadowing entry
Tobias Stoeckmann [Sun, 15 Mar 2026 23:31:47 +0000 (00:31 +0100)] 
usermod: Update passwd entry when shadowing entry

If a new shadow entry is created, the passwd entry's password hash is
moved into shadow file and replaced with an "x". If this happens, update
the passwd file as well, otherwise the "x" is not written to disk.

Resolves: https://github.com/shadow-maint/shadow/issues/1580

Reproducer (as root):
```
BASE=$(mktemp -d)
mkdir -p $BASE/etc
useradd -P $BASE user
touch $BASE/etc/shadow
usermod -P $BASE -e 0 user
cat $BASE/etc/passwd
```

Incorrect output (before):
```
user:!:1000:1000::/home/user:/bin/bash
```

Correct output (after):
```
user:x:1000:1000::/home/user:/bin/bash
```

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
3 months agolib/, src/: Remove superfluous #include <assert.h>
Alejandro Colomar [Fri, 13 Mar 2026 16:01:21 +0000 (17:01 +0100)] 
lib/, src/: Remove superfluous #include <assert.h>

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/, src/, tests/: #undef NDEBUG before #include <assert.h>
Alejandro Colomar [Fri, 13 Mar 2026 15:57:52 +0000 (16:57 +0100)] 
lib/, src/, tests/: #undef NDEBUG before #include <assert.h>

Otherwise, assert(3) might do nothing, which would be unsafe.

The goal would be to not use assert(3) at all, actually, but as long as
we use it, we should make sure we do actually use it.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/, src/, tests/: Move <assert.h> to be the last #include
Alejandro Colomar [Thu, 12 Mar 2026 12:39:33 +0000 (13:39 +0100)] 
lib/, src/, tests/: Move <assert.h> to be the last #include

<assert.h> should always be the last include.  Otherwise, you risk some
indirect inclusion might affect the behavior of assert(3).

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/sysconf: Move sysconf handling into own file
Tobias Stoeckmann [Fri, 13 Mar 2026 16:23:45 +0000 (17:23 +0100)] 
lib/sysconf: Move sysconf handling into own file

Move sysconf() calls and error handling into its own file.

While at it, adjust the data type for ngroup max value.

Requested-by: Alejandro Colomar <alx@kernel.org>
Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
3 months agousermod: Check sysconf return value
Tobias Stoeckmann [Wed, 11 Mar 2026 21:35:22 +0000 (22:35 +0100)] 
usermod: Check sysconf return value

Verify that sysconf does not return -1. It is not important if it's due
to an error or due to a missing upper boundary. In both cases, fall back
to a constant value.

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
3 months agouseradd: Check sysconf return value
Tobias Stoeckmann [Wed, 11 Mar 2026 21:34:05 +0000 (22:34 +0100)] 
useradd: Check sysconf return value

Verify that sysconf does not return -1. It is not important if it's due
to an error or due to a missing upper boundary. In both cases, fall back
to a constant value.

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
3 months agostrchriscntrl: reject C1 control bytes (0x80-0x9F)
KhaelK-Praetorian [Wed, 11 Mar 2026 03:04:55 +0000 (22:04 -0500)] 
strchriscntrl: reject C1 control bytes (0x80-0x9F)

glibc's iscntrl() does not classify C1 control bytes as control
characters in any locale. The iscntrl() check was added as part of the
fix for CVE-2023-29383, which blocked C0 control characters, but C1
bytes were never considered.

The byte 0x9B is the C1 encoding of CSI (Control Sequence Introducer),
equivalent to ESC [. On terminals that interpret C1 codes (VTE-based
terminals such as GNOME Terminal, Tilix, Terminator, XFCE Terminal),
an attacker can inject terminal escape sequences into GECOS fields via
chfn. This allows visual spoofing of /etc/passwd output, for example
making a user's UID appear as 0 when viewed with cat.

Explicitly check for bytes in the 0x80-0x9F range in strchriscntrl()
so that valid_field() returns -1 (rejected) instead of 1 (non-ASCII
warning) for these bytes.

Before (unpatched chfn accepts C1 bytes and writes them to /etc/passwd):

  $ cat /etc/passwd | grep ubuntu
  ubuntu:x:1000:1000:ubuntu,,,:/home/ubuntu:/bin/bash
  $ chfn -r $'\xc2\x9b17D0\xc2\x9b3P\xc2\x9b1C0\xc2\x9b3P\xc2\x9b1Croot\xc2\x9b8m'
  Password:
  chfn: room number with non-ASCII characters: [...]
  $ cat /etc/passwd | grep ubuntu
  ubuntu:x:0:0:root,,:/home/ubuntu:/bin/bash

After (patched chfn rejects C1 bytes, /etc/passwd unchanged):

  $ chfn -r $'\xc2\x9b17D0\xc2\x9b3P\xc2\x9b1C0\xc2\x9b3P\xc2\x9b1Croot\xc2\x9b8m'
  Password:
  chfn: invalid room number: [...]
  $ cat /etc/passwd | grep ubuntu
  ubuntu:x:1000:1000:ubuntu,,,:/home/ubuntu:/bin/bash

Tested on Shadow 4.17.4-2ubuntu2 (Ubuntu 25.10, aarch64).

3 months agousermod: Create shadow entry with -e 0 or -f 0
Tobias Stoeckmann [Wed, 11 Mar 2026 20:15:10 +0000 (21:15 +0100)] 
usermod: Create shadow entry with -e 0 or -f 0

If -e 0 or -f 0 are supplied but no shadow entry exists, these flags are
silently ignored. Internally, the supplied values (0) are compared with
static long values which are initially 0 as well. If they are identical,
usermod drops the flags.

This does not match usermod's manual page, which states that a missing
shadow entry is created. This is also true for any other valid command
line values, e.g. -e 1 or -f 1.

Reviewed-by: Alejandro Colomar <alx@kernel.org>
Signed-off-by: Tobias Stoeckmann <tobias@stoeckmann.org>
3 months agoTests: Add user with existing UID without -o flag
aborah-sudo [Wed, 11 Mar 2026 08:27:42 +0000 (13:57 +0530)] 
Tests: Add user with existing UID without -o flag

This is the transformation to Python of the test located in
`04_useradd_add_user_with_existing_UID_fail`, which checks that `useradd` fails to create a new user with existing UID without -o flag

3 months agolib/commonio.c: Diagnose non-text files
Alejandro Colomar [Wed, 11 Mar 2026 22:07:44 +0000 (23:07 +0100)] 
lib/commonio.c: Diagnose non-text files

Closes: <https://github.com/shadow-maint/shadow/issues/1581>
Reported-by: Tim Zhou <tizhou@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agoci: run unit-tests in Ubuntu build
Iker Pedrosa [Tue, 10 Mar 2026 09:32:47 +0000 (10:32 +0100)] 
ci: run unit-tests in Ubuntu build

Run unit-tests as part of the Ubuntu build

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agoci: add missing `cmocka` dependency for Ubuntu runners
Iker Pedrosa [Tue, 10 Mar 2026 09:48:16 +0000 (10:48 +0100)] 
ci: add missing `cmocka` dependency for Ubuntu runners

`cmocka` is required to run unit-tests

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agoTests: Add a new user with specified UID and GID
aborah-sudo [Mon, 9 Mar 2026 05:50:21 +0000 (11:20 +0530)] 
Tests: Add a new user with specified UID and GID

This is the transformation to Python of the test located in
`tests/usertools/01/04_useradd_specified_UID_and_GID.test`,
which checks that `useradd` is able to create a new user with specified uid and gid

3 months agoTests: Create user with custom uid options
aborah-sudo [Wed, 4 Mar 2026 06:59:16 +0000 (12:29 +0530)] 
Tests: Create user with custom uid options

This is the transformation to Python of the test located in
`tests/usertools/01/04_useradd_specified_UID.test`,

which checks that `useradd` is able to create a new user with specified uid

3 months agolib/io/syslog.h: SYSLOG_C(): Call setlocale(3) and free(3) unconditionally
Alejandro Colomar [Wed, 23 Jul 2025 00:23:57 +0000 (02:23 +0200)] 
lib/io/syslog.h: SYSLOG_C(): Call setlocale(3) and free(3) unconditionally

Both setlocale(3) and free(3) are okay to call with a null pointer.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/io/syslog.h: SYSLOG_C(): Use a single local variable
Alejandro Colomar [Wed, 23 Jul 2025 17:59:02 +0000 (19:59 +0200)] 
lib/io/syslog.h: SYSLOG_C(): Use a single local variable

There's no need for two variables, and this avoids one assignment.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/io/syslog.h: Rename local variable
Alejandro Colomar [Wed, 23 Jul 2025 17:58:07 +0000 (19:58 +0200)] 
lib/io/syslog.h: Rename local variable

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/io/syslog.h: SYSLOG_C(): Split code to helper macro
Alejandro Colomar [Wed, 23 Jul 2025 17:50:04 +0000 (19:50 +0200)] 
lib/io/syslog.h: SYSLOG_C(): Split code to helper macro

The name of this macro makes it more evident what it does.  It's a
C-locale version of syslog(3).  We need to implement it as a macro
so that arguments such as strerror(3) are evaluated after setting
the C locale.  This would be impossible with a function.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/: Move <syslog.h> wrappers to "io/syslog.h"
Alejandro Colomar [Tue, 22 Jul 2025 23:41:11 +0000 (01:41 +0200)] 
lib/: Move <syslog.h> wrappers to "io/syslog.h"

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agoTests: Create user with comment, expiredate, inactive, shell and custom home
aborah-sudo [Mon, 2 Mar 2026 07:04:18 +0000 (12:34 +0530)] 
Tests: Create user with comment, expiredate, inactive, shell and custom home

This is the transformation to Python of the test located in
`tests/usertools/01/03_useradd_additional_options.test`, which checks that
`useradd` is able to create a new user with comment, expiredate, inactive, shell and custom home

3 months agoFix build failure on hosts with gcc 10
Chen Qi [Wed, 11 Feb 2026 05:17:04 +0000 (05:17 +0000)] 
Fix build failure on hosts with gcc 10

We cannot just uname these unused parameters because gcc 10
need them. There will be error like below with gcc 10:

  lib/copydir.c:103:11: error: parameter name omitted

The Debian bullseye uses gcc 10 by default.

Most of the changes are done manually. Some changes in tests/unit
are done via the following shell command:
sed -i -e 's#void \*\*#MAYBE_UNUSED void \*\* _1#g'  tests/unit/test_*.c

Closes: <https://github.com/shadow-maint/shadow/issues/1530>
Signed-off-by: Chen Qi <Qi.Chen@windriver.com>
3 months agoci: run privileged system tests in CI
Hadi Chokr [Thu, 12 Feb 2026 11:20:01 +0000 (12:20 +0100)] 
ci: run privileged system tests in CI

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agotests: add privileged useradd test for BTRFS subvolume homes
Hadi Chokr [Thu, 12 Feb 2026 11:17:52 +0000 (12:17 +0100)] 
tests: add privileged useradd test for BTRFS subvolume homes

Add a privileged system test that verifies useradd can create home
directories as BTRFS subvolumes.

This test requires elevated privileges to use:
The BTRFS filesystem Framework class to create a /home directory on
BTRFS and check if the Users Home directory is a BTRFS Subvolume.

The test is intentionally isolated and excluded from default test runs
to prevent accidental execution on host systems.

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agotests: add privileged topology and test configuration
Hadi Chokr [Thu, 12 Feb 2026 11:16:39 +0000 (12:16 +0100)] 
tests: add privileged topology and test configuration

Extend the Python system test framework with a dedicated privileged
topology and configuration, while keeping privileged tests excluded
by default. And include a BTRFS Framework class for BTRFS Operations.

This ensures:
- Clear separation between safe and destructive tests
- No accidental execution of privileged tests in normal CI or local runs
- Explicit opt-in for privileged environments

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agodoc: document privileged containers and privileged system tests
Hadi Chokr [Thu, 12 Feb 2026 11:14:54 +0000 (12:14 +0100)] 
doc: document privileged containers and privileged system tests

Document the distinction between unprivileged and privileged execution
modes for containers and system tests.

Add explicit warnings that privileged tests must never be run on the
host system, as they may mount filesystems, create loop devices, or
modify kernel-visible state.

Provide clear guidance on when privileged tests are acceptable and how
to execute them safely in disposable environments.

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agoshare: add privileged container support for CI and system tests
Hadi Chokr [Thu, 12 Feb 2026 11:13:46 +0000 (12:13 +0100)] 
share: add privileged container support for CI and system tests

Introduce opt-in privileged container execution for CI and local runs.
This enables filesystem-level tests (e.g. BTRFS, mounts) while keeping
unprivileged execution as the default and safe path.

Changes include:
- Separate privileged and unprivileged builders
- Conditional Ansible roles and inventories
- Privileged test execution wiring
- --privileged support in container-build.sh

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agolib/string/strcmp/: str{,case}eq(): Simplify implementation
Alejandro Colomar [Thu, 26 Feb 2026 16:54:24 +0000 (17:54 +0100)] 
lib/string/strcmp/: str{,case}eq(): Simplify implementation

A one-liner macro is simpler, and works just fine.

We don't need the function at all, since we don't use it as a callback.
The macro changes the return type, but we don't really care about that
detail; we could cast it to bool, but we don't really need that, so keep
it simple.

Reviewed-by: Kees Cook <kees@kernel.org>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/string/strchr/: strnul(): Simplify implementation
Alejandro Colomar [Thu, 19 Feb 2026 01:01:09 +0000 (02:01 +0100)] 
lib/string/strchr/: strnul(): Simplify implementation

This avoids an __auto_type local variable, and a GNU statement
expression.

Reviewed-by: Kees Cook <kees@kernel.org>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/defines.h, lib/, src/: Redefine SYSLOG() as a variadic macro
Alejandro Colomar [Tue, 22 Jul 2025 22:08:22 +0000 (00:08 +0200)] 
lib/defines.h, lib/, src/: Redefine SYSLOG() as a variadic macro

The double parentheses were used to fake a variadic macro with a
non-variadic one.  With a variadic macro, we remove the weird double
parentheses that were needed to call this macro, which BTW were
error-prone.  This would have prevented the bug fixed in 3f5ae5d5f1fd
(2025-09-10; "src/su.c: Fix incorrect (non-matching) parentheses").

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agousermod: Add option to automatically find subordinate IDs
Richard Weinberger [Mon, 23 Feb 2026 20:19:21 +0000 (21:19 +0100)] 
usermod: Add option to automatically find subordinate IDs

Tools such as useradd(8) automatically select subordinate UID and GID
ranges based on settings in login.defs.
But when one wants to add subordinate IDs to an existing user, these
ranges have to be specified manually using the -w and -v options
of usermod(8).

Add a new -S / --add-subids option to usermod(8) which will, just like
useradd(8), find a range based on the settings in login.defs.

Signed-off-by: Richard Weinberger <richard@nod.at>
3 months agolib/string/README: streq(3) and strnul(3) are in libc
Alejandro Colomar [Sun, 22 Feb 2026 14:49:17 +0000 (15:49 +0100)] 
lib/string/README: streq(3) and strnul(3) are in libc

streq(3) and strnul(3) are now part of a libc implementation: gnulib.
They are also documented in a manual page.  Thus, refer to them as
streq(3) and strnul(3).

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agodoc/contributions/coding_style.md: Refer to the man-pages style guide
Alejandro Colomar [Wed, 25 Feb 2026 11:54:59 +0000 (12:54 +0100)] 
doc/contributions/coding_style.md: Refer to the man-pages style guide

Reported-by: "Evgeny Grin (Karlson2k)" <k2k@drgrin.dev>
Reported-by: Richard Weinberger <richard@nod.at>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agouseradd: Correctly set subuid/subgid when using -F
ndostert [Mon, 23 Feb 2026 20:50:16 +0000 (21:50 +0100)] 
useradd: Correctly set subuid/subgid when using -F

The -F flag should bypass the -r flag and UID checks.

Closes: <shadow-maint#1255>
Signed-off-by: ndostert <crawax@cwxlab.fr>
Co-authored-by: Alejandro Colomar <alx@kernel.org>
Fixes: 3f7a72e9677b (2022-08-01; "useradd: add -F option for updating /etc/sub[ig]id for system accounts")
3 months ago*/: chgpasswd(8): -m,--md5: Remove option
Alejandro Colomar [Sat, 27 Dec 2025 11:52:14 +0000 (12:52 +0100)] 
*/: chgpasswd(8): -m,--md5: Remove option

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months ago*/: chpasswd(8): -m,--md5: Remove option
Alejandro Colomar [Sat, 27 Dec 2025 11:36:11 +0000 (12:36 +0100)] 
*/: chpasswd(8): -m,--md5: Remove option

This was the command-line equivalent of MD5_CRYPT_ENAB.  It deserves
the same fate.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/salt.c: Compact conditionals
Alejandro Colomar [Sat, 27 Dec 2025 01:07:15 +0000 (02:07 +0100)] 
lib/salt.c: Compact conditionals

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months ago*/: Remove support for MD5_CRYPT_ENAB
Alejandro Colomar [Sat, 27 Dec 2025 01:02:24 +0000 (02:02 +0100)] 
*/: Remove support for MD5_CRYPT_ENAB

It has been deprecated for a very long time.  In fact, the first commit
that documented MD5_CRYPT_ENAB already documented it as deprecated.
6e3ad7a27546 (2007-11-20).

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months ago*/: expiry(1): Remove program
Alejandro Colomar [Mon, 15 Dec 2025 23:18:45 +0000 (00:18 +0100)] 
*/: expiry(1): Remove program

Password expiration is deprecated, and will be eventually removed.

The functionality of expiry(1) is the most superfluous of password
expiry and can be removed early.  This shouldn't conflict with any
existing regulations about password expiry.

Link: <https://github.com/shadow-maint/shadow/pull/1432>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agosrc/: Cosmetic
Alejandro Colomar [Fri, 26 Dec 2025 17:29:10 +0000 (18:29 +0100)] 
src/: Cosmetic

Fix style.

Reviewed-by: Serge Hallyn <serge@hallyn.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months ago*: Make support for SHA256 and SHA512 unconditional
Alejandro Colomar [Fri, 26 Dec 2025 14:14:17 +0000 (15:14 +0100)] 
*: Make support for SHA256 and SHA512 unconditional

This is necessary for later changing the fallback from the insecure DES
to something secure such as SHA512.

Link: <https://github.com/shadow-maint/shadow/issues/1278>
Reviewed-by: Serge Hallyn <serge@hallyn.com>
Cc: Andre Boscatto <andreboscatto@gmail.com>
Cc: Iker Pedrosa <ipedrosa@redhat.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/btrfs.c: Remove hardcoded Paths and resolve them via env to increase portability
Hadi Chokr [Sat, 24 Jan 2026 17:54:33 +0000 (18:54 +0100)] 
lib/btrfs.c: Remove hardcoded Paths and resolve them via env to increase portability

Signed-off-by: Hadi Chokr <hadichokr@icloud.com>
3 months agolib/setupenv.c: Remove code wrapped in '#if 0'
Alejandro Colomar [Sat, 3 Jan 2026 23:21:04 +0000 (00:21 +0100)] 
lib/setupenv.c: Remove code wrapped in '#if 0'

This has not been tested in a long time --if ever--.

If we ever want to implement something, we should start from scratch.
But if we've survived for so long without it, I suspect we don't want
it at all.

Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agoconfigure.ac: fix checks for lastlog support
Mike Gilbert [Wed, 18 Feb 2026 19:00:51 +0000 (14:00 -0500)] 
configure.ac: fix checks for lastlog support

The check for lastlog.h was removed by mistake in a previous changset.

The configure script should terminate with an error if lastlog support
was requested but lastlog.h is not available.

Partial functionality is provided if ll_host is not a member of
struct lastlog.

Fixes: 1bdcfa8d3710 (2023-07-15; "lastlog: stop building by default")
Fixes: 9eea4bc9cf95 (2024-11-12, 2025-02-07; "configure.ac: Remove unused AC_CHECK_HEADERS() checks")
Signed-off-by: Mike Gilbert <floppym@gentoo.org>
3 months agosrc/useradd.c: Refactor long expression into many simple conditionals
Alejandro Colomar [Wed, 18 Feb 2026 20:10:05 +0000 (21:10 +0100)] 
src/useradd.c: Refactor long expression into many simple conditionals

Co-authored-by: Serge Hallyn <serge@hallyn.com>
Signed-off-by: Serge Hallyn <serge@hallyn.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agosrc/useradd.c: Factor out logic to helper functions
Alejandro Colomar [Wed, 18 Feb 2026 20:02:10 +0000 (21:02 +0100)] 
src/useradd.c: Factor out logic to helper functions

Co-authored-by: Serge Hallyn <serge@hallyn.com>
Signed-off-by: Serge Hallyn <serge@hallyn.com>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agolib/prefix_flag.c: Remove 't' flag from fopen(3)
Alejandro Colomar [Wed, 18 Feb 2026 13:54:43 +0000 (14:54 +0100)] 
lib/prefix_flag.c: Remove 't' flag from fopen(3)

It is a Windows extension ignored by musl and glibc.  It is not in POSIX
nor ISO C.

Since most of our calls to fopen(3) don't use it, let's be consistent
and not use it anywhere.

Closes: <https://github.com/shadow-maint/shadow/issues/1541>
Acked-by: Mike Frysinger <vapier@gentoo.org>
Signed-off-by: Alejandro Colomar <alx@kernel.org>
3 months agotests/unit/test_chkhash.c: add invalid hashes
Iker Pedrosa [Fri, 6 Feb 2026 15:20:37 +0000 (16:20 +0100)] 
tests/unit/test_chkhash.c: add invalid hashes

Add comprehensive negative testing condition validation:
- Invalid algorithm prefixes and hash length validation
- Invalid delimiter handling
- Invalid salt characters and rounds parameter testing

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add edge test cases
Iker Pedrosa [Fri, 6 Feb 2026 15:18:52 +0000 (16:18 +0100)] 
tests/unit/test_chkhash.c: add edge test cases

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add special test cases
Iker Pedrosa [Wed, 4 Feb 2026 10:15:56 +0000 (11:15 +0100)] 
tests/unit/test_chkhash.c: add special test cases

*, ! and empty strings are special valid cases for shadow's second
field. Add test cases for them.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add MD5 and DES hash validation tests
Iker Pedrosa [Wed, 4 Feb 2026 09:31:47 +0000 (10:31 +0100)] 
tests/unit/test_chkhash.c: add MD5 and DES hash validation tests

Add basic MD5 and DES algorithm validation tests.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add SHA-256 hash validation tests
Iker Pedrosa [Wed, 4 Feb 2026 09:22:29 +0000 (10:22 +0100)] 
tests/unit/test_chkhash.c: add SHA-256 hash validation tests

Add comprehensive SHA-256 algorithm validation tests covering rounds and
salt cases.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add SHA-512 hash validation tests
Iker Pedrosa [Sun, 1 Feb 2026 14:11:20 +0000 (15:11 +0100)] 
tests/unit/test_chkhash.c: add SHA-512 hash validation tests

Add comprehensive SHA-512 algorithm validation tests covering rounds and
salt cases.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add bcrypt hash validation tests
Iker Pedrosa [Sun, 1 Feb 2026 09:46:18 +0000 (10:46 +0100)] 
tests/unit/test_chkhash.c: add bcrypt hash validation tests

Add comprehensive bcrypt algorithm validation tests covering all
variants ($2a$, $2b$, $2x$, $2y$) with different cost factors.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agotests/unit/test_chkhash.c: add unit tests for `is_valid_hash()`
Iker Pedrosa [Fri, 30 Jan 2026 14:56:23 +0000 (15:56 +0100)] 
tests/unit/test_chkhash.c: add unit tests for `is_valid_hash()`

Introduce unit testing infrastructure for the `is_valid_hash()`
function. Add yescrypt algorithm validation tests.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
3 months agolib/chkhash.c: fix yescrypt hash length comment
Iker Pedrosa [Fri, 6 Feb 2026 15:31:56 +0000 (16:31 +0100)] 
lib/chkhash.c: fix yescrypt hash length comment

Fix misleading comment that stated "43-char (minimum) hash" when
the actual regex pattern requires exactly 43 characters. Update
comment to accurately reflect the implementation behavior.

Signed-off-by: Iker Pedrosa <ipedrosa@redhat.com>
Reviewed-by: Alejandro Colomar <alx@kernel.org>
3 months agoconfigure.ac: simplify fgetpwent_r check
Mike Gilbert [Tue, 17 Feb 2026 18:48:41 +0000 (13:48 -0500)] 
configure.ac: simplify fgetpwent_r check

Signed-off-by: Mike Gilbert <floppym@gentoo.org>