Understanding the /etc/shadow File in Linux

By 

Updated on

6 min read

/etc/shadow File

The /etc/shadow file is a system file that stores hashed passwords and password aging information for each user account on a Linux system. It works alongside /etc/passwd , which contains basic user account details but does not store passwords.

The file is owned by the root user and the shadow group, and has 640 permissions . Only privileged processes can read it, which prevents regular users from accessing password hashes.

This guide explains the /etc/shadow file format, what each field means, and how to query password information safely.

/etc/shadow Format

The /etc/shadow file contains one entry per line, each representing a user account. To view the contents, use cat with sudo:

Terminal
sudo cat /etc/shadow

The first line typically describes the root user, followed by system and normal user accounts. New entries are appended at the end of the file.

Each line contains nine colon-separated fields:

txt
mark:$6$.n.:17736:0:99999:7:::
[--] [----] [---] - [---] ----
|      |      |   |   |   |||+-----------> 9. Unused
|      |      |   |   |   ||+------------> 8. Expiration date
|      |      |   |   |   |+-------------> 7. Inactivity period
|      |      |   |   |   +--------------> 6. Warning period
|      |      |   |   +------------------> 5. Maximum password age
|      |      |   +----------------------> 4. Minimum password age
|      |      +--------------------------> 3. Last password change
|      +---------------------------------> 2. Encrypted Password
+----------------------------------------> 1. Username

Field Descriptions

  1. Username — The login name for the user account. This matches the username in /etc/passwd.

  2. Encrypted Password — The hashed password in $type$salt$hash format. The $type prefix identifies the hashing algorithm:

    • $1$ — MD5
    • $2b$ — bcrypt
    • $5$ — SHA-256
    • $6$ — SHA-512
    • $y$ — yescrypt (default on modern distributions such as Debian 13, Ubuntu 22.04+, and Fedora 35+)

    If the password field contains an asterisk (*) or an exclamation point (!), the user cannot log in using password authentication. Other login methods like key-based authentication or switching to the user are still allowed.

    A !! field usually means the account does not currently have a usable password entry. This is common for newly created accounts without an initial password and for some locked-password states.

  3. Last password change — The date when the password was last changed, expressed as the number of days since January 1, 1970 (the Unix epoch).

  4. Minimum password age — The number of days that must pass before the user can change the password again. A value of 0 means the password can be changed at any time.

  5. Maximum password age — The number of days after which the user must change the password. The default value is 99999 (approximately 274 years), which effectively means the password never expires.

  6. Warning period — The number of days before the password expires during which the user receives a warning message at login.

  7. Inactivity period — The number of days after the password expires before the account is disabled. If the user does not log in within this window, the account is locked. This field is often empty.

  8. Expiration date — The date when the account is disabled, expressed as days since the Unix epoch. An empty field means the account does not expire.

  9. Unused — Reserved for future use. This field is currently ignored.

Example Entry

The following is an example /etc/shadow entry:

txt
linuxize:$y$j9T$zYHn...$x5rG...:18009:0:120:7:14::

This entry contains the following information about the user “linuxize”:

  • The password is hashed with yescrypt ($y$). The hash is truncated here for readability.
  • The password was last changed on April 23, 2019 (day 18009 since the epoch).
  • There is no minimum password age (0).
  • The password must be changed at least every 120 days.
  • The user receives a warning message 7 days before the password expires.
  • If the user does not log in within 14 days after the password expires, the account is disabled.
  • There is no account expiration date.

Viewing Password Information

Do not edit the /etc/shadow file by hand. Always use the appropriate commands to query and modify password information.

To view the password aging information for a specific user, use the chage command with the -l option:

Terminal
sudo chage -l linuxize

For safer day-to-day checks, query only the user you need with getent shadow username instead of printing the entire shadow file.

output
Last password change                    : Apr 23, 2019
Password expires                        : Aug 21, 2019
Password inactive                       : Sep 04, 2019
Account expires                         : never
Minimum number of days between password change  : 0
Maximum number of days between password change  : 120
Number of days of warning before password expires : 7

To look up a single user entry from the shadow database, use getent:

Terminal
sudo getent shadow linuxize

To change a user password, use the passwd command:

Terminal
sudo passwd linuxize

To modify password aging settings such as the maximum age or warning period, use chage:

Terminal
sudo chage -M 90 -W 14 linuxize

This sets the maximum password age to 90 days and the warning period to 14 days.

Quick Reference

TaskCommand
View the shadow filesudo cat /etc/shadow
Look up a single usersudo getent shadow username
View password aging infosudo chage -l username
Change a user passwordsudo passwd username
Set maximum password agesudo chage -M DAYS username
Set warning periodsudo chage -W DAYS username
Lock a user accountsudo passwd -l username
Unlock a user accountsudo passwd -u username

Troubleshooting

Permission denied when reading /etc/shadow
The file is readable only by root and the shadow group. Use sudo to read it: sudo cat /etc/shadow.

Password field shows ! or *
The account does not have a usable password. An ! or !! means the account is locked or has no password set. A * means password authentication was never enabled for this account (common for system accounts).

chage shows “password must be changed”
The password has exceeded its maximum age. The user must set a new password with passwd at the next login, or an administrator can reset it with sudo passwd username.

Shadow entry missing for a user that exists in /etc/passwd
Run sudo pwconv to synchronize /etc/passwd and /etc/shadow. This creates missing shadow entries.

FAQ

What is the difference between /etc/passwd and /etc/shadow?
/etc/passwd contains user account information (username, UID, home directory, shell) and is readable by all users. /etc/shadow stores the hashed passwords and password aging data and is readable only by root.

How do I check which hashing algorithm my system uses?
Check the ENCRYPT_METHOD setting in /etc/login.defs. On modern distributions, the default is YESCRYPT or SHA512.

What does a !! password field mean?
!! usually means the account does not currently have a usable password entry. This is common on newly created accounts before a password is set and in some locked-password states.

Can I move passwords back to /etc/passwd?
You should not. Storing passwords in /etc/passwd is insecure because that file is world-readable. The shadow file exists specifically to keep password hashes protected.

How do I force a user to change their password at next login?
Run sudo chage -d 0 username. This sets the last password change date to the epoch, which forces a password change at the next login.

Conclusion

The /etc/shadow file stores hashed passwords and password aging information for every user on a Linux system. Use chage -l to view password aging details and passwd to change passwords. Never edit the file directly.

If you have any questions, feel free to leave a comment below.

Linuxize Weekly Newsletter

A quick weekly roundup of new tutorials, news, and tips.

About the authors

Dejan Panovski

Dejan Panovski

Dejan Panovski is the founder of Linuxize, an RHCSA-certified Linux system administrator and DevOps engineer based in Skopje, Macedonia. Author of 800+ Linux tutorials with 20+ years of experience turning complex Linux tasks into clear, reliable guides.

View author page