Description
The files that define local accounts, and the backups that the shadow tools keep with a -
suffix, have the Debian ownership and at most these modes:
| Files | Owner:group | Maximum mode |
|---|---|---|
/etc/passwd, /etc/passwd-, /etc/group, /etc/group- | root:root | 644 |
/etc/shadow, /etc/shadow-, /etc/gshadow, /etc/gshadow- | root:shadow | 640 |
/etc/shells | root:root | 644 |
/etc/security/opasswd, /etc/security/opasswd.old | root:root | 600 |
Files that do not exist are skipped.
Debian uses group shadow for shadow and gshadow, not root as on other distributions.
Setting them to root:root breaks password checks by unix_chkpwd for non-root programs
(screen lockers, some PAM services).
Rationale
passwd and group must stay readable by everyone for name lookups, but only root may change
them: write access means creating a UID 0 account. shadow and gshadow hold password hashes;
on Debian the shadow group lets unix_chkpwd and screen lockers check a password without
being root, and nobody else may read them. opasswd holds the previous password hashes kept by
pam_pwhistory. The - backups contain the same data as the live files.
Impact
None known: these are the Debian defaults, and the fix only removes extra access.
Setting
| Location | /etc/passwd, /etc/group, /etc/shadow, /etc/gshadow, /etc/shells, /etc/security/opasswd |
| Default | Compliant on a fresh install |
| Recommended | See the table in the description |
Audit
Run stat -c '%n %U:%G %a' /etc/passwd* /etc/group* /etc/shadow* /etc/gshadow* /etc/shells /etc/security/opasswd*
and compare each line with the table above.
Automated: every check must pass. Scanners report each check by its id.
passwd
/etc/passwd and its backup are root:root, mode 644 or stricter.
path: /etc/passwd*
owner: root
group: root
mode: '0644'
group
/etc/group and its backup are root:root, mode 644 or stricter.
path: /etc/group*
owner: root
group: root
mode: '0644'
shadow
/etc/shadow and its backup are root:shadow, mode 640 or stricter.
path: /etc/shadow*
owner: root
group: shadow
mode: '0640'
gshadow
/etc/gshadow and its backup are root:shadow, mode 640 or stricter.
path: /etc/gshadow*
owner: root
group: shadow
mode: '0640'
shells
/etc/shells is root:root, mode 644 or stricter.
path: /etc/shells
owner: root
group: root
mode: '0644'
opasswd
/etc/security/opasswd and its backup are root:root, mode 600 or stricter.
path: /etc/security/opasswd*
owner: root
group: root
mode: '0600'
Remediation
chown root:root /etc/passwd /etc/passwd- /etc/group /etc/group- /etc/shells
chmod u-x,go-wx /etc/passwd /etc/passwd- /etc/group /etc/group- /etc/shells
chown root:shadow /etc/shadow /etc/shadow- /etc/gshadow /etc/gshadow-
chmod u-x,g-wx,o-rwx /etc/shadow /etc/shadow- /etc/gshadow /etc/gshadow-
chown root:root /etc/security/opasswd*
chmod 600 /etc/security/opasswd*
| Restart | none |
| Disruption | none |
Rollback
Not needed: the fix only restores the Debian ownership and removes extra permissions.
passwd
Generated from check passwd: the engine writes the fix for every output, it sets the expected value and the check runs again after.
group
Generated from check group: the engine writes the fix for every output, it sets the expected value and the check runs again after.
shadow
Generated from check shadow: the engine writes the fix for every output, it sets the expected value and the check runs again after.
gshadow
Generated from check gshadow: the engine writes the fix for every output, it sets the expected value and the check runs again after.
shells
Generated from check shells: the engine writes the fix for every output, it sets the expected value and the check runs again after.
opasswd
Generated from check opasswd: the engine writes the fix for every output, it sets the expected value and the check runs again after.
Each release turns these fixes into remediate.sh and an Ansible role per profile: dry run by default, a fix runs only when its check fails.
References
- shadow(5), Debian manual pages Debian, vendor-doc, accessed 2026-10-18
- shells(5), Debian manual pages Debian, vendor-doc, accessed 2026-10-18
- ANSSI-BP-028 v2.0 - Recommandations de configuration d'un système GNU/Linux (R50) ANSSI, guide, accessed 2026-10-18
Mappings
| Framework | ID | Relation | Note |
|---|---|---|---|
| ANSSI-BP-028 - Recommandations de configuration d'un système GNU/Linux2.0 | R50 | partial | R50 covers every sensitive file; this control covers the account databases. |
| NIST SP 800-53 Rev. 55.1.1 | AC-3 | related |
How this control relates to the other framework's: equivalent, stricter, looser, partial or related.
Threats mitigated
Related controls
- related
CB-DEB-AUTH-028Keep the shadow group empty
People and lifecycle
| Authors |
|
| Verified | 2026-10-18 by Sn0wAlice on 12, Proxmox VM 922, Debian 12 genericcloud image, kernel 6.1.0-54-cloud-amd64. Passes on fresh install (shadow and gshadow root:shadow 640); generated fixes report compliant. |
| Verified | 2026-10-18 by Sn0wAlice on 13, Proxmox VM 932, Debian 13 genericcloud image, kernel 6.12.113+deb13-cloud-amd64. Passes on fresh install (shadow and gshadow root:shadow 640); generated fixes report compliant. |
| Introduced in | v0.1.0 |
| Created, updated | 2026-10-18, 2026-10-18 |
| Translations | fr |