- User and Group IDs
- User and Group Accounts
- Displaying Database Information With getent
- Setting and Updating User Account Passwords With passwd
- Updating Passwords For Multiple Existing Users With chpasswd
- Changing Password Expiry Information With chage
- Locking and Unlocking User Passwords
- Adding User Accounts With useradd
- Creating and Updating Multiple User Accounts With newusers
- Adding Groups With groupadd
- Modifying a User Account With usermod
- Modifying Groups
- Removing Users
- Removing Groups
- Substituting User Accounts
- Miscellaneous User and Group Commands
- Special Login Files
- Documentation
Managing accounts on your GNU/Linux system is a fundamental part of system administration.
Note: If you are not familiar with the GNU/Linux command line interface, review the Conventions page before proceeding.
User and Group IDs
A user is an entity that needs access to system resources. All GNU/Linux users are assigned a unique user ID (UID), which is an integer.
GNU/Linux uses groups for organizing users. Groups are collections of user accounts with shared permissions. By default, every user belongs to a default group (i.e., their primary group). When a user logs in, their group membership is set to their primary group.
A user's UID is the same as their primary group's unique group ID (GID). It is possible for multiple users to have the same UID, but different account passwords. However, this is usually not a good idea and is not recommended.
Only the root user can add or remove users and groups.
User Account Types
GNU/Linux has four types of accounts:
- root
- System
- Normal
- Network
Specific UID ranges or values are associated with certain types of user accounts:
1-999
- System users. These users do not map to actual people, but are used as security identities for system daemons to implement privilege separation and run system daemons with minimal privileges.
0-99
- Statically allocated system user accounts.
100-499
- System user accounts dynamically allocated by system administrators and post-installation scripts.
1000-65533
and65536-4294967294
- Normal users. Accounts mapped to people.
1000-1499
- System administrators and server operators. This is not required, but may be done for organizational purposes.
10000-65533
- Network accounts. This is not required, but may be done for organizational purposes.
0
- root user (the superuser).
1
or2
- bin user.
48
- apache user.
65534
- nobody user. This account is used for many things (e.g., anonymous access on FTP/HTTP servers), but does not have write access on a system.
65534
is also referred to as the overflow UID. This is where various subsystems map unmappable users to (e.g., file systems only supporting 16-bit UIDs, the Network File System (NFS), or user namespacing).
Pseudo-user accounts belong to certain software systems (e.g., postfix
for the Postfix mail server) or certain devices (e.g., printers). You can access these accounts like other user accounts via the su
command. These accounts are helpful as file or directory owners, in order to fit the access rights tied to file ownership to special requirements without having to use the root account. The same logic applies to groups.
As with UID values, specific GID values are associated with certain types of group accounts:
1-999
- System groups. These groups do not map to actual people, but are used as security identities for system daemons to implement privilege separation and run system daemons with minimal privileges.
0-99
- Statically allocated system group accounts.
100-499
- System group accounts dynamically allocated by system administrators and post installation scripts.
1000-65533
and65536-4294967294
- Normal groups. Accounts mapped to people.
1000-1499
- System administrators and server operators. This is not required, but may be done for organizational purposes.
10000-65533
- Network accounts. This is not required, but may be done for organizational purposes.
0
- root group (the superuser group).
1
or2
- bin group.
50
- staff group.
100
- users group. This is where you can place regular users and give them access to resources by assigning it (i.e., the
users
group) group ownership of things that all users should have access to.
The root user's privileges are tied to UID 0
. GID 0
does not confer any additional access privileges. Administrative groups (e.g., root
, bin
) are similar to the system's pseudo-user accounts. Many files are assigned to groups like this.
User and Group Accounts
There are several files on a GNU/Linux system that pertain to users and groups.
/etc/passwd
Each user on a GNU/Linux system has a corresponding line in the /etc/passwd
file. The file can be viewed by running the following command:
$ less '/etc/passwd' | head
root:x:0:0:root:/root:/bin/bash
daemon:x:1:1:daemon:/usr/sbin:/usr/sbin/nologin
bin:x:2:2:bin:/bin:/usr/sbin/nologin
sys:x:3:3:sys:/dev:/usr/sbin/nologin
sync:x:4:65534:sync:/bin:/bin/sync
games:x:5:60:games:/usr/games:/usr/sbin/nologin
man:x:6:12:man:/var/cache/man:/usr/sbin/nologin
lp:x:7:7:lp:/var/spool/lpd:/usr/sbin/nologin
mail:x:8:8:mail:/var/mail:/usr/sbin/nologin
news:x:9:9:news:/var/spool/news:/usr/sbin/nologin
The file consists of lines made from the following colon-delimited fields:
ex_login_name
- Optional
ex_encrypted_password
ex_UID
ex_GID
ex_GECOS_information
ex_user_home_directory
- Optional
ex_user_login_shell
Usernames should be 8 characters or less to ensure compatibility in heterogeneous environments (e.g., UNIX systems limit usernames to 8 characters).
There are several possible scenarios for the optional password field:
- If the password field is blank, no password is required to authenticate the specified login name. However, some applications that read
/etc/passwd
may decide to not permit any access if the field is not filled. - If the password is an
x
, the encrypted password is stored in the user's corresponding line in the/etc/shadow
file. - If the password field is any other string, it is treated as an encrypted password, as specified by
crypt(3)
.
On GNU/Linux systems, setting the password field to an asterisk (*
) is a common way to disable direct logins to an account, while still preserving its name. An alternative possible password value is *NP*
, which indicates to use a Network Information Service (NIS) server to obtain the password.
Every user must belong to at least one group, i.e., their primary group.
vipw
/etc/passwd
can be edited with the vipw
command:
# vipw
General Electric Comprehensive Operating Supervisor/System (GECOS)
The General Electric Comprehensive Operating Supervisor/System (GECOS) field is used to record general information about an account or its user. Often, this field is used to store the user's real name.
finger
GECOS information for the current user can be viewed with the finger
command (likely, you will need to install this program from your distribution's repository, e.g., # apt install finger
, # dnf install finger
). GECOS information for a specific user(s) can be viewed by providing their login name(s) to the finger
command as an argument.
finger ex_login_name...
chfn
To change the GECOS information for the current user, use the chfn
command. If you have root privileges, you can change the GECOS information for another user by passing their username (login name) to chfn
as an argument:
# chfn ex_login_name
/etc/shadow
The x
value for a password in a /etc/passwd
line is a place holder for the user's password, which is actually stored in encrypted form in the /etc/shadow
file. /etc/shadow
can be viewed by running:
# less '/etc/shadow' | head
root:*:18827:0:99999:7:::
daemon:*:18820:0:99999:7:::
bin:*:18820:0:99999:7:::
sys:*:18820:0:99999:7:::
sync:*:18820:0:99999:7:::
games:*:18820:0:99999:7:::
man:*:18820:0:99999:7:::
lp:*:18820:0:99999:7:::
mail:*:18820:0:99999:7:::
news:*:18820:0:99999:7:::
The file consists of lines made from the following colon-delimited fields:
ex_login_name
ex_encrypted_password
ex_date_of_last_password_change
ex_minimum_password_age
ex_maximum_password_age
ex_password_warning_period
ex_password_inactivity_period
ex_account_expiration_date
The ex_login_name
field corresponds to a line in /etc/passwd
. This field joins the two files.
There are several possible scenarios for the password field:
- If the password field contains a string that is not a valid result of
crypt(3)
(e.g.,!
or*
), the password will be locked and the user will not be able to log in with a password, but other authentication methods (e.g., SSH key authentication) are still allowed. The remaining characters on the line represent the password field before the password was locked. - If the password field is blank, no password is required to authenticate the specified login name. However, some applications that read
/etc/shadow
may decide to not permit any access if the field is not filled.
Only the root user can read and write to the /etc/shadow
file. Only members of the shadow
group can read it.
Fields 3 through 8 in each line describe various aspects and policies for that user's account and password.
- date of last password change
- The days since the UNIX Epoch time (January 1, 1970) that have elapsed since the password was last changed.
- A value of
0
has a special meaning and indicates that the user should change their password the next time that they log in. - An empty field means that password aging features are disabled.
- minimum password age
- The days that must elapse before the password can be changed.
- maximum password age
- The days before the password must be changed.
- An empty field indicates that there are no maximum password age, no password warning period, and no password inactivity period.
- If the maximum password age is less than the minimum password age, the user cannot change their password.
- password warning period
- The days before the password expires during which the user will be warned.
- Both an empty field and value
0
mean that there is no password warning period. - password inactivity period
- The number of days after the password expires in which the user could still log in if their password is changed during login.
- After both expiration of the password and the elapsing of this period, the password is no longer valid and logging in with it is not possible.
- An empty field indicates that there is no enforcement of an inactivity period.
- account expiration date
- The number of days from the UNIX Epoch time, and the day the account will expire and be disabled.
- Account expiration is distinct from password expiration. After account expiration, the user is not allowed to log in. After password expiration, the user is not allowed to log in with their password, unless they are within a password inactivity period, where they will be allowed to change their password upon login.
The last field in the /etc/shadow
file is reserved for future use.
Keep in mind, the field's above are respected by the text console login process. They are not necessarily respected by other parts of the system, including the graphical login screen.
The /etc/shadow
file can be edited by using the vipw
command's -s
option:
# vipw -s
pwck, pwconv, and pwunconv
The pwck
command verifies the integrity of password files by confirming that the /etc/passwd
and /etc/shadow
files are in sync:
# pwck
If the files are not in sync, there are two commands that can be used to resolve the incongruity:
pwconv
creates missing/etc/shadow
users from/etc/passwd
(# pwconv
).pwunconv
creates missing/etc/passwd
users from/etc/shadow
(# pwunconv
).
/etc/group, newgrp, and gpasswd
Each group on a GNU/Linux has a corresponding line in the /etc/group
file. The file can be viewed by running the following command:
$ less '/etc/group' | head
root:x:0:
daemon:x:1:
bin:x:2:
sys:x:3:
adm:x:4:
tty:x:5:
disk:x:6:
lp:x:7:amnesia
mail:x:8:
news:x:9:
The file consists of lines made from the following colon-delimited fields:
ex_group_name
- Optional
ex_encrypted_password
ex_GID
- Optional
ex_user_list
The optional password field is for an optional group password that lets users that are not a member of the group assume group membership using the newgrp
command:
- If the password field is blank, no password is needed to assume the group's membership with the
newgrp
command. - If the password is an
x
, the encrypted password is stored in the group's corresponding line in the/etc/gshadow
file. - A
*
in the optional password field prevents normal users from changing to this group with thenewgrp
command.
If a user is a member of a group that has been assigned a password, they do not need to enter the password when using the newgrp
command with that group.
A group password is assigned through the gpasswd
command:
# gpasswd ex_group
If you do not have root access, but you are a group administrator, you can assign/re-assign a password to that group using gpasswd
, as well.
The /etc/group
ex_user_list
field is a comma-separated list of usernames. Usually, users are not listed in the entry of their primary group in this file.
vigr
/etc/group
can be edited with the vigr
command:
# vigr
/etc/gshadow
The x
value for a password in a /etc/group
line is a place holder for the group's password, which is actually stored in encrypted form in the /etc/gshadow
file. The /etc/gshadow
file can be viewed by running:
# less '/etc/gshadow' | head
root:*::
daemon:*::
bin:*::
sys:*::
adm:*::
tty:*::
disk:*::
lp:*::amnesia
mail:*::
news:*::
The file consists of lines made from the following colon-delimited fields:
ex_group_name
ex_encrypted_password
ex_administrators
ex_members
The ex_group_name
field corresponds to a line in /etc/group
. This field joins the two files.
There are several possible scenarios for the password field:
- If the password field contains a string that is not a valid result of
crypt(3)
(e.g.,!
or*
), the password will be locked and users will not be able to use a password to access the group (group members do not need the password). The remaining characters on the line represent the password field before the password was locked. - If the password field is blank, then only group members can gain the group permissions.
Users listed in the ex_administrators
field are group administrators that are able to add or remove members of the group, and change the group's password. Group administrators also have the same group permissions as group members.
The /etc/gshadow
file can be edited by using the vigr
command's -s
option:
# vigr -s
grpck, grpconv, and grpunconv
The grpck
command verifies the integrity of group files by confirming that the /etc/group
and /etc/gshadow
files are in sync:
# grpck
If the files are not in sync, there are two commands that can be used to resolve the incongruity:
grpconv
creates missing/etc/gshadow
groups from/etc/group
(# grpconv
).grpunconv
creates missing/etc/group
groups from/etc/gshadow
(# grpunconv
).
Displaying Database Information With getent
The getent
command displays entries from databases supported by the Name Service Switch libraries, which are configured in /etc/nsswitch.conf
.
getent ex_database
This command can be used to display the information stored in the previously mentioned user and group files. ex_database
is the database name associated with these files. The accepted database name values are listed in /etc/nsswitch.conf
(e.g., passwd
, shadow
. group
, or gshadow
). Accessing some of these databases will require root access.
Here, database means the totality of all sources from where the C library can obtain information on that topic. Databases are searched in the order determined by the /etc/nsswitch.conf
file.
getent
can be provided one or more keys (e.g., a username) as arguments to show only information related to that key(s).
getent ex_database ex_key...
Setting and Updating User Account Passwords With passwd
The passwd
command is used to change the current user's password. It is also the command that sets the values for what you see regarding a user in /etc/shadow
.
Helpful options include:
-d
,--delete
- Delete a user's password (i.e., make it empty).
- If the password field is blank, no password is required to authenticate the specified login name. However, some applications that read
/etc/shadow
may decide to not permit any access if the field is not filled. -i ex_inactive_days
,--inactive ex_inactive_days
- Set the number of days an account with an expired password can be inactive before it is disabled (i.e., the password inactivity period).
-l ex_login_name
,--lock ex_login_name
- Lock the password of the named account.
- This option adds a
!
to the beginning of the password. The user will not be able to log in with a password, but other authentication methods (e.g., SSH key authentication) are still allowed. -n ex_min_days
,--mindays ex_min_days
- Set the minimum password lifetime in days (i.e., the minimum password age).
- A value of
0
means that the user can change their password at any time. -S
,--status
- Display account status information (e.g., username, whether account has a locked password (
L
), has no password (NP
), or a usable password (P
), date of last password change (date of last password change), minimum password age, maximum password age, password warning period, password inactivity period). -u ex_login_name
,--unlock ex_login_name
- Unlock the password of the named account.
-w ex_warning_days
,--warndays ex_warning_days
- Set the number of warning days before the password expires (i.e., the password warning period).
-x ex_max_days
,--maxdays ex_max_days
- Sets the maximum password lifetime in days (i.e., the maximum password age). After
ex_max_days
, the password must be changed.
If you have root access, you can change the password for a different user account by providing their username as an argument to passwd
:
# passwd ex_login_name
Updating Passwords For Multiple Existing Users With chpasswd
chpasswd
is an interactive command that updates passwords for existing users in batch mode. It reads a list of username and password pairs from the standard input and uses this information to update a group of existing users.
# chpasswd
Each username/password pair is given per line in the following format:
username:password
By default, passwords must be supplied in clear-text, and are subsequently encrypted by chpasswd
.
After you are done entering username/password pairs, enter Ctrl+d to exit.
Alternatively, a file with username/password pairs (one per line) can be passed to chpasswd
:
# chpasswd < ex_file.txt
Changing Password Expiry Information With chage
The chage
command is another command (aside from passwd
) that can be used to change users' password expiry information in /etc/shadow
.
# chage ex_login_name
After invoking chage
without any options, you are presented with a sequence of current expiry information values to change or confirm.
Useful options include:
-d ex_last_days
,--lastday ex_last_days
- Set the number of days since the UNIX Epoch time that the password was last changed (i.e., the date of last password change). A date in the format of
YYYY-MM-DD
may also be used in place ofex_last_days
. -E ex_expire_date
,--expiredate ex_expire_date
- Set the number of days since the UNIX Epoch time, and the date on which the user's account will be disabled (i.e., the account expiration date). The format is either an integer number of days or the date in the format
YYYY-MM-DD
. - Passing the number
-1
asex_expire_date
will remove an account expiration date. -I ex_inactive_days
,--inactive ex_inactive_days
- Set the number of days of inactivity (i.e., no logins) after a password has expired before the user account is locked (i.e., the password inactivity period).
- Passing the number
-1
asex_expire_date
will remove an account's inactivity. -l ex_login_name
,--list ex_login_name
- Show account aging information.
-m ex_min_days
,--mindays ex_min_days
- Set the minimum number of days that the user must wait until they can change their password (i.e., the minimum password age). A value of
0
forex_min_days
means that the user can change their password at any time. -M ex_max_days
,--maxdays ex_max_days
- Set the maximum number of days that can go by before the user must change their password (i.e., the maximum password age).
- A value of
-1
asex_max_days
will remove checking a password's validity. -W ex_warn_days
,--warndays ex_warn_days
- Set the number of warning days before a password change in required (i.e., the password warning period).
Disabling and Enabling User Accounts
The chage
command can be used to disable or enable a user account via its -E
(--expiredate
) option.
To disable a user account, set its ex_expire_date
to 0
:
# chage -E 1 ex_login_name
To enable a user account, set its ex_expire_date
to -1
:
# chage -E -1 ex_login_name
Locking and Unlocking User Passwords
Both the passwd
and usermod
commands can be used to lock and unlock user passwords (i.e., to prevent a user from logging into a system with their password).
A user password can be locked like so:
# passwd -l ex_login_name
Or:
# usermod -L ex_login_name
A user account can be unlocked by running one of the following commands:
# passwd -u ex_login_name
Or:
# usermod -U ex_login_name
Adding User Accounts With useradd
The useradd
command creates new user accounts and updates default new user information.
# useradd ex_login_name
This command uses the /etc/default/useradd
and /etc/login.defs
files as input.
Useful options include:
-b ex_base_directory
,--base-dir ex_base_directory
- Specify the system's base directory if
-d ex_home_directory
is not specified.ex_base_directory
is concatenanted with theex_login_name
to define the home directory. -c ex_comment
,--comment ex_comment
- Any text string. Generally, this is a short description of the login and is currently used as the field for the user's full name (GECOS).
-d ex_home_directory
,--home-dir ex_home_directory
- Specify the home directory.
ex_home_directory
does not have to exist, but will not be created if it is missing. -D
,--defaults
- Display the defaults defined in
/etc/default/useradd
. Can be used to modify defaults when used in conjunction with the-b
,-e
,-f
,-g
, and-s
options. -e ex_expire_date
,--expiredate ex_expire_date
- Set an expiration date on the account, after which it is disabled (i.e., the account expiration date). The date is specified in the format of
YYYY-MM-DD
. -f ex_inactive_days
,--inactive ex_inactive_days
- Specify the number of days after the password has expired in which the user can still log in (if their password is changed during login) before their account is disabled (i.e., the password inactivity period).
-g ex_group
,--gid ex_group
- Specify primary group. Either a GID or group name can be used.
ex_group
must exist. -G ex_secondary_group...
,--groups ex_secondary_group...
- Set secondary group membership. Is either a single value or a list of comma-separated values of groups (e.g.,
ex_secondary_group_1,ex_secondary_group_2
) that the user is to be a secondary member of. -k ex_skeleton_directory
,--skel ex_skeleton_directory
- Specify skeleton directory. This option is only valid if the
-m
option is specified. - The skeleton directory contains the files and directories to be copied to the user's home directory when the directory is created by
useradd
. If this option is not set, the skeleton directory is defined by theSKEL
variable in/etc/default/useradd
or, by default, in/etc/skel
. -m
,--create-home
- Create user's home directory if it does not exist.
- The files and directories contained in the skeleton directory will be copied to the home directory. By default, if this option is not specified and
CREATE_HOME
is not enabled, no home directories are created. -o
,--non-unique
- Allow creation of a user with a non-unique UID. This option is only valid in combination with the
-u
option. -s ex_shell
,--shell ex_shell
- Specify the full path of the filename of the user's login shell.
-u ex_uid
,--uid ex_uid
- Specify UID. This UID must be unique, unless the
-o
option is also used.
After a user is created, their account password is considered locked until it is set. You can set the account password using the previously mentioned passwd
command:
# passwd ex_login_name
Creating and Updating Multiple User Accounts With newusers
newusers
is an interactive command that creates new users in batch mode. It reads user information from the standard input and uses this information to create new users.
# newusers
Each user is provided per line with the following colon-delimited fields:
ex_login_name
ex_clear_text_password
ex_UID
ex_GID
ex_GECOS_info
ex_user_home_directory
ex_user_login_shell
By default, passwords are supplied in clear-text and are encrypted by newusers
.
After you are done entering new users, press Ctrl+d to exit.
Alternatively, a file with new user entries (one per line) can be passed to the newusers
command:
# newusers < ex_file.txt
Aside from creating new users, the newusers
command can be used to update information for existing users, as well.
Adding Groups With groupadd
The groupadd
command creates a new group using the values specified on the command line and the default values from the system.
# groupadd ex_group
A group with a specific GID can be created through the use of the -g
(--gid
) option:
# groupadd -g ex_gid ex_group
Modifying a User Account With usermod
The usermod
command modifies user accounts:
# usermod ex_login_name
Substantive options include:
-c ex_comment
,--comment ex_comment
- The new value of the user's password file comment field. Modifies GECO field in
/etc/passwd
. -d ex_home_directory
,--home ex_home_directory
- The user's new home directory. Changing a user's home directory does not change user ownership of files in the new or old home directory.
-e ex_expire_date
,--expiredate ex_expire_date
- The date on which the user account will be disabled (i.e., the account expiration date). The date is specified in the
YYYY-MM-DD
format. - An empty
ex_expire_date
will disable the expiration of the account. -f ex_inactive_days
,--inactive ex_inactive_days
- The number of days after a password expires until the password is locked (i.e., the password inactivity period).
- An
ex_inactive_days
value of0
locks the password as soon as it expires and a value of-1
disables the feature. -g ex_group
,--gid ex_group
- The group name or GID of the user's new primary group. The group must exist.
- Any object from the user's home directory owned by the previous primary group of the user will be owned by this new group.
- Group ownership of files outside of the user's home directory must be manually fixed.
-G ex_group...
,--groups ex_group...
- A list of secondary groups that the user is also a member of. Each group is separated from the next by a comma, with no intervening white space (e.g.,
ex_group_1,ex_group_2
). ex_group
is a single value or a list of comma-separated values of groups that the user is to be a secondary member of. This overwrites any current secondary group memberships (i.e., if a user is a member of a group that is not specified with this option, they will be removed from the group). This behavior can be changed with the addition of the-a
(--append
) option, which adds the user to the secondary group(s).-l ex_new_login
,--login ex_new_login
- The name of the user that will be changed from
ex_login
toex_new_login
. Nothing else is changed. The user's home directory or mail spool should likely be manually renamed to reflect the new login name. -L
,--lock
- Locks a user's password (which prevents the user from logging into the system with a password). This adds a lock to the user's account by adding an exclamation point (
!
) to the front of the encrypted password in the/etc/shadow
file. -m
,--move-home
- Move the content of the user's home directory to the new location.
- This option is only valid in combination with the
-d
option. -s ex_shell
,--shell ex_shell
- The name of the user's new login shell. Short for
--shell
. Changes the path to the user's login shell. Settingex_shell
to blank causes the system to select the default login shell. -u ex_uid
,--uid ex_uid
- The new UID for the user.
- The user's mailbox, and any files that the user owns and that are located in the user's home directory, will have the file UID automatically changed.
- The ownership of files outside of the user's home directory must be manually fixed.
-U
,--unlock
- Unlock a user's password. Removes the lock on the user's password by removing the exclamation point (
!
) from the front of the encrypted password in the/etc/shadow
file.
Add an Existing User to an Existing Group
usermod
can be used to add an existing user to an existing group:
# usermod -aG ex_group_name... ex_login_name
usermod
's -a
option is short for --append
.
An alternative to the above command is to use the gpasswd
command:
# gpasswd -a ex_login_name ex_group_name
gpasswd
's -a
option is short for --add
.
Remove an Existing User From an Existing Group
usermod
can used to remove an existing user from an existing group:
# usermod -G ex_group... ex_login_name
Above, ex_group...
represents the group or groups that you want ex_login_name
to be a member of (i.e., you would leave off the group(s) that you want to remove the user from).
An alternative to the above command is to use the gpasswd
command:
# gpasswd -d ex_login_name ex_group_name
Here, ex_group_name
represents the group that you want to remove ex_login_name
from. -d
is short for --delete
.
Set Group Administrators
The gpasswd
command can be used to define a group's administrator:
# gpasswd -A ex_login_name... ex_group_name
-A
is short for --administrators
and ex_login_name
can be a comma-separated list of usernames (e.g., ex_login_name_1,ex_login_name_2
).
Modifying Groups
A group's name and GID can be modified with the groupmod
command.
To change the group's name, use the -n
(--new-name
) option:
# groupmod -n ex_new_group_name ex_group_name
To change the group's GID, use the -g
(--gid
) option:
# groupmod -g ex_new_GID ex_group_name
Objects previously group owned by the old GID tied to ex_group_name
will no longer have a group name associated with their group owner's GID. You will just see the old GID as the group owner for these file system objects.
Removing Users
The userdel
command deletes a user account, while retaining that user's home directory.
# userdel ex_login_name
If a user is currently logged in and you need to delete their account, you can lock their account first (# passwd -l ex_login_name
or # usermod -L ex_login_name
) and then kill their login shell (# killall -u ex_login_name
) before you run the userdel
command.
To remove a a user's home directory and mail spool (which is defined by the MAIL_DIR
variable in the /etc/login.defs
file), as well as their user account, add the -r
(--remove
) option to userdel
:
# userdel -r ex_login_name
Other files that belong to the user (e.g., their crontab file) will remain and need to be manually deleted. A quick way to do this is with the find command:
# find '/' -uid ex_uid -delete
Removing Groups
The groupdel
command deletes a group.
# groupdel ex_group_name
The primary group for a user may not be removed until the user's account is deleted first.
Before removing a group, there are several checks you should do:
- Confirm that the group has no secondary members (e.g.,
getent group ex_group_name
). - Confirm that the group is not a primary group for any user account (e.g.,
less '/etc/passwd' | grep ex_group_name
). - Identify all objects owned by the group and change group ownership to another group (e.g.,
# chown -R --from=:old_gid :new_group_owner_name /
or# find / -group ex_old_group_name -exec sudo chgrp new_group_owner_name '{}' \;
).
Substituting User Accounts
There are several commands that can be used to substitute (switch) user accounts on a GNU/Linux system. These commands can be used to switch to any user account, but they are often used to gain access to the root user.
root privileges are required to perform operations like:
- Creating, removing and managing accounts
- Managing software packages
- Removing or modifying system files
- Restarting system services
su
By default, the su
(substitute user) command substitutes your user session with that of the root user. After authenticating as the root user, you are provided with a non-login, interactive shell for the root user.
When employing the su
command, it is considered best practice to specify the full path to the command (for a Debian system, su
is located inside of /usr/bin/
):
/usr/usr/bin/su
From this point on, from the system's point of view, you are indistinguishable from the root user. You are the root user.
If you want a login shell for the root user, you can use su
's -l
(--login
) option:
/usr/bin/su -l
It is recommended to always use the su
command with the -l
option, as it avoids side effects caused by mixed environments.
If you provide su
with a specific username as an argument, you can substitute your user session for that user, instead of the root user.
/usr/bin/su -l ex_login_name
You will need to know ex_login_name
's password, unless you are calling su
as the root user.
The su
command can be used to simply run a separate command as a different user. This can be accomplished by also passing that command (and any of its arguments) to the su
command's -c
(--command
) option:
su ex_login_name -c ex_command
The following example prints out a hello message to the standard output as the amnesia
user:
# su amnesia -c 'echo Hello, world!'
Hello, world!
sudo
A alternative way to substitute user sessions on a GNU/Linux system is to utilize the sudo
(substitute user do) program. sudo
allows permitted users to execute a command as the root user (or another user), as specified by the system's security policy.
Your user's Real User Identifier (RUID) is used to determine the login name with which to query the security policy. Since the system is keeping track of which actual user is employing the sudo
command, a log can be maintained for auditing purposes.
sudo
differs from the su
command in several important ways:
- Depending on how it is configured,
sudo
can ask for either the root user's password or the password of the user using thesudo
command (i.e., the sudoer) when they invokesudo
(the latter is preferable, as it prevents sudoers from having to know and frequently enter the root user's password). - A correctly entered password is retained for 15 minutes (this time period is configurable), for convenience. However, you can manually expire the cached password by running
sudo -k
(-k
is short for--reset-timestamp
). In general,sudo
has more features and allows for more customization thansu
. -
All commands executed via
sudo
are logged using the system's logging mechanism. Failures to usesudo
will appear in the/var/log/auth.log
file for Debian and in/var/log/messages
and/or/var/log/secure
file on Fedora. A typical entry will include:- Calling username
- Terminal information
- Working directory where command was executed
- User account invoked
- Command used, with arguments
A
sudo
entry in a log looks something likeJun 10 09:50:38 tails sudo: amnesia : TTY=pts/2 ; PWD=/home/amnesia ; USER=root ; COMMAND=/usr/bin/passwd
.
You can grant a user the ability to use the sudo
command in at least three ways:
- Create an entry for the user in the
/etc/sudoers
file. - Create a file in the
/etc/sudoers.d/
directory with the user's username as the filename. Then, create an entry inside this file for the user. The permissions for this file should be440
. - Create an entry for the
sudo
group in the/etc/sudoers
file and add the user to this group.
Some GNU/Linux distributions (e.g., Debian, Ubuntu) extend sudo
privileges to the first user account created during installation and completely disable log-ins to the root user account. This prevents naive users from working as the root user all of the time.
/etc/sudoers
The /etc/sudoers
file controls the users that are allowed to use the sudo
command and for what purposes. This is what a /etc/sudoers
file looks like on a basic Debian installation:
#
# This file MUST be edited with the 'visudo' command as root.
#
# Please consider adding local content in /etc/sudoers.d/ instead of
# directly modifying this file.
#
# See the man page for details on how to write a sudoers file.
#
Defaults env_reset
Defaults mail_badpass
Defaults secure_path="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
# Host alias specification
# User alias specification
# Cmnd alias specification
# User privilege specification
root ALL=(ALL:ALL) ALL
# Allow members of group sudo to execute any command
%sudo ALL=(ALL:ALL) ALL
# See sudoers(5) for more information on "#include" directives:
#includedir /etc/sudoers.d
The %sudo ALL=(ALL:ALL) ALL
line is what allows members of the sudo
group to execute any command. The percentage sign (%
) indicates that this a group definition, versus the root ALL=(ALL:ALL) ALL
line which is a user definition.
The %sudo ALL=(ALL:ALL) ALL
line can broken down like so:
%sudo
- The name of the group. Some GNU/Linux distributions, like Fedora, use a
%wheel
group, instead (e.g.,%wheel ALL=(ALL) ALL
). ALL=
- The hosts on the network that the rule applies to (in this case, all hosts).
(ALL:ALL)
- Specifies which users and groups the members of this group can run commands as. Here, all users and all groups are covered.
ALL
- Specifies which commands can be run by members of this group. For this example, all commands are included here.
The %sudo ALL=(ALL:ALL) ALL
line's syntax can be generalized as follows:
who where=(as user:as group) what
Or:
user host=(run as) command
For example, here is a /etc/sudoers
entry for the amnesia
user:
amnesia ALL=(ALL) ALL
Wherever a login name is expected, you may specify a group too. Prefix the group's name with a percent sign to indicate that it is a group, as we saw for the sudo
group above (e.g., %operators ALL=/usr/local/bin/do-backup
).
By default, sudo
runs all commands as root, but you can also specify another user. For example, with amnesia ALL=(mysql) /usr/bin/mysqladmin
, amnesia
can run the mysqladmin
command as the mysql
user. To do so, the amnesia
user must run a command like sudo -u mysql mysqladmin flush-privileges
.
When you only specify a command (without parameters), arbitrary parameters are allowed:
amnesia ALL=/usr/bin/cancel
.
When no parameters should be allowed, the only parameter specified in the sudoers
file must be an empty string amnesia ALL=/usr/bin/passwd ''
.
In this case, amnesia
would only be allowed to change the password of the root user when using passwd
with the sudo
command.
Be careful about commands like vi
that allow users to execute shell commands. These commands are also executed with root privileges. To prevent this, you could add a rule like amnesia ALL= NOEXEC: /usr/bin/vi
. This line stops vi
from running child processes.
You can also specify multiple commands:
amnesia ALL=/usr/bin/cancel [a-z]+,/usr/bin/cupsenable [a-z]+
The above command allows sudo cancel
, as well as sudo cupsenable
, both with (at least) one parameter.
When you specify a directory name (as an absolute pathname with a trailing slash), this stands for all executable files in that directory (but not subdirectories), e.g., amnesia ALL=/usr/bin/
.
A nice feature of sudo
is the -e
(--edit
) or sudoedit
command. These commands create a temporary copy of the file to be edited and then pass that copy to your default editor. Afterwards, it checks whether the copy has been changed, compared to the original, and if so, the copy replaces the original file.
This method has convenient advantages, like the fact that the editor only runs with the ordinary user's privileges so that they cannot spawn a root shell from the editor. Incidentally, the /etc/sudoers
file is evaluated by sudoedit
when it decides whether a user gets to use this feature or not.
/etc/sudoers
supports many options that control the function of sudo
. Run man 8 sudo
and man 5 sudoers
for more information.
visudo
Changes can be made to the /etc/sudoers
file with your system's default editor by using the visudo
command (visudo
checks the VISUAL
environment variable first, then the EDITOR
environment variable, and finally the editor
setting in /etc/sudoers
before falling back to vi
):
# visudo
visudo
ensures that only one user is editing /etc/sudoers
at a time and performs a syntax check immediately after the file is saved (and before putting your new configuration into effect). This is important because, in case of an error, you do not want to end up with a configuration file that will break sudo
. A manual check of /etc/sudoers
can be done at any time by running the # visudo -c
(-c
is short for --check
) command.
For example, if you have a user that you want to give the ability to install software on a Fedora system, but you do not want to give them the full access that comes with adding them to the wheel
group, you can use visudo
to add the following line to the /etc/sudoers
file:
ex_login_name ALL=/usr/bin/dnf
The above line will enable ex_login_name
to utilize the /usr/bin/dnf
command on all network hosts via the sudo
command (e.g., sudo dnf install ex_program
). Additional commands can be specified by separating them with commas (e.g., /usr/bin/dnf,/usr/sbin/shutdown
).
sudoer Aliases
If you have several user accounts that you want to grant the same sudoer permissions, you can add them to a user alias.
User_Alias ex_alias = ex_users
ex_users
is a comma-separated list of users. For example:
# Installer user alias definition
User_Alias INSTALLERS = amnesia,esnowden,wbinney
# INSTALLERS permissions definition
INSTALLERS ALL=/usr/bin/dnf
Above, we used the User_Alias
keyword to create an INSTALLERS
user alias in the /etc/sudoers
file and have added three users to it. Then, we defined the permissions associated with this new INSTALLERS
alias with the INSTALLERS ALL=/usr/bin/dnf
line.
Aliases can be set for hosts (Host_Alias
) and commands (Cmnd_Alias
), as well.
Use Host_Alias
to specify what systems the users can run the commands on. The following is a host alias for a network's file servers:
Host_Alias FILESERVERS = fs_1,fs_2
Use Cmnd_Alias
to define an alias that contains the commands (using the full path) that you want the user you just defined to be able to run. Separate multiple commands with commas.
This is a command alias used to group storage-related commands:
Cmnd_Alias KILLPROCS = /bin/kill,/usr/bin/killall
Command aliases can be mixed with literal commands in the same rule:
amnesia ALL=PRINTING,/usr/bin/accept [a-z]+
A leading !
character can be used to exclude commands that would otherwise be allowed by a configuration:
amnesia ALL=/usr/bin/passwd [a-z]+,!/usr/bin/passwd root
Different kinds of aliases can be combined:
INSTALLERS FILESERVERS=(root) KILLPROCS
Defaults
Previously, we mentioned that you can manually expire a cached password by running sudo -k
. This behavior can be changed in /etc/sudoers
by use of the Defaults
keyword.
For example, the following line sets the timeout to 0
(i.e., password caching is disabled):
Defaults timestamp_timeout=0
Using sudo
To start a non-login, interactive shell for the root user, you can use sudo
's -s
(--shell
) option:
sudo -s
Unlike when using the su
command, when changing to the root user with sudo
, you are not asked for the root user's password. You are asked for the sudoer's password, i.e., your user account's password. This is advantageous, since it isolates permissions between multiple sudoers.
If you want a login shell for the root user, you can use sudo
's -i
(--login
) option:
sudo -i
If you provide sudo
's -u
(--user=
) option with a specific username as an argument, you can switch to that user's account, instead of the root user:
sudo -i -u ex_login_name
Often, sudo
is used to run a command as a different user (usually the root user) via a non-login shell. This can be done by appending the command to the sudo
command. If a specific user is not specified, the root user is assumed:
sudo ex_command
To run a command as a user other than the root user via a non-login shell, pass the username in question to sudo
's -u
option:
sudo -u ex_login_name ex_command
The following example prints out a hello message to the standard output as the amnesia
user:
sudo -u amnesia echo Hello, world!
Hello, world!
Miscellaneous User and Group Commands
whoami
The whoami
command prints the effective UID to the standard output.
$ whoami
amnesia
The command is essentially displaying the content of the LOGNAME
or USER
shell variables.
groups
The groups
command prints the group membership for the current user.
$ groups
amnesia lp dialout cdrom floppy video plugdev netdev lpadmin scanner vboxsf
This command can take one or more login names to show group affiliations for that user(s).
id
The id
command prints the real and effective user and group IDs for the current user. Specifically, this output includes the current user's:
- UID
- Primary group GID
- Group affiliations (including each group's GID)
$ id
uid=1000(amnesia) gid=1000(amnesia) groups=1000(amnesia),7(lp),20(dialout),24(cdrom),25(floppy),44(video),46(plugdev),109(netdev),115(lpadmin),116(scanner),119(vboxsf)
You can provide this command a specific login name as an argument to view the information associated with that user.
The -u
(--user
), -g
(--group
), and -G
(--groups
) options can be used to show just the UID, primary group GID, or all group GIDS, respectively. These options are mutually exclusive.
Also, if you add the -n
(--name
) option to the -u
, -g
, or -G
options, you will see the corresponding name, instead of the numerical UID/GID.
$ id -Gn
amnesia lp dialout cdrom floppy video plugdev netdev lpadmin scanner vboxsf
Essentially, the id -Gn
command above is equivalent to the groups
command.
who
The who
command prints information about users that are logged on to the system to the standard output.
$ who
amnesia :1 2020-08-04 22:43 (:1)
w
Like the who
command, the w
command prints information about users that are logged in, but also displays what they are doing and the system load averages. Specifically, the header includes:
- The current time
- How long the system has been running
- How many users are currently logged on
- The system load averages for the past 1, 5, and 15 minutes
$ w
22:44:19 up 1 min, 1 user, load average: 1.54, 0.86, 0.33
USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT
amnesia :1 :1 22:43 ?xdm? 21.03s 0.00s /bin/sh /usr/lib/gdm3/gdm-x-session
The JCPU
value is the time used by all processes attached to the teletype (tty) terminal. It does not include past background jobs, but does include currently running background jobs.
The PCPU
time is the time used by the current process named in the WHAT
field.
last
The last
command searches the /var/log/wtmp
file and displays a list of all users logged in (and out) since /var/log/wtmp
was created.
$ last
amnesia :1 :1 Tue Aug 4 22:43 still logged in
reboot system boot 5.7.0-1-amd64 Tue Aug 4 22:42 still running
wtmp begins Tue Aug 4 22:42:46 2020
One or more login names and/or ttys can be provided to last
to only view entries for those login names.
Special Login Files
There are several special files that relate to user management:
/bin/false
- If set as a user's login shell, they will not be able to log in.
${HOME}/.hushlogin
- Changes the login process so that it does not perform a mail check, and does not display the last login information or the message of the day to the user.
/etc/issue
- Contains the greeting that is output before a user is asked to log in.
/etc/login.defs
- Defines the defaults for numerous commands (e.g.,
useradd
,userdel
,usermod
, andgroupadd
). Includes entries for mail, password complexity and limitations, UID and GID minimum and maximum values, and whether the user's home directory is created by default. /etc/motd
- After a successful login, the contents of this file are displayed before the user's shell is executed.
motd
stands for Message of the Day. /usr/sbin/nologin
- If set as a user's login shell, this program displays a message that the account is unavailable and exits with a non-zero exit status. If the
/etc/nologin
file is present, no user can log into the system except for the root user and the content of the file (or/etc/nologin.txt
) is displayed instead of a standard message. /etc/securetty
- Specifies from where the root user is allowed to log in from. If
/etc/securetty
does not exist, the root user can log in from anywhere. /etc/usertty
- Used to set the parameters for login locations, days, times, and systems that the user can connect from. Only used on systems that do not have pluggable authentication modules (PAM).
Documentation
You can learn more about the commands discussed in this post by referring to the Linux User's Manual, either at the command line, or online. Additional information on users, groups, and UIDs/GIDs can be found in the systemd documentation.