SUDO(8)

๐Ÿ“ฆ version 1.9.17p2, in ubuntu questing, ubuntu resolute, ubuntu stonking

โœจ SUDO(8) ยท System Manager's Manual โœจ

๐ŸŽ€ NAME

okay so the name section is short and sweet ๐ŸŒธ: sudo, sudoedit โ€” execute a command as another user ๐Ÿ’…

๐Ÿงพ SYNOPSIS

sudo -h | -K | -k | -V
sudo -v [-ABkNnS] [-g group] [-h host] [-p prompt] [-u user]
sudo -l [-ABkNnS] [-g group] [-h host] [-p prompt] [-U user] [-u user]
     [command [arg ...]]
sudo [-ABbEHnPS] [-C num] [-D directory] [-g group] [-h host]
     [-p prompt] [-R directory] [-r role] [-t type] [-T timeout]
     [-u user] [VAR=value] [-i | -s] [command [arg ...]]
sudoedit [-ABkNnS] [-C num] [-D directory] [-g group] [-h host]
     [-p prompt] [-R directory] [-r role] [-t type] [-T timeout]
     [-u user] file ...

๐Ÿ’– DESCRIPTION

okay so sudo lets a user who's allowed to do it run a command as the superuser or some other user ๐Ÿ‘‘, as long as the security policy says yes. The user name that gets checked against the policy comes from the invoking user's real user-ID, not their effective one ๐Ÿฆ‹.

sudo has a plugin architecture for security policies, auditing, and input/output logging โœจ. Third parties can build and share their own plugins that play nicely with the sudo front-end ๐Ÿงš. The default security policy is sudoers, which is configured through the file /etc/sudoers, or through LDAP ๐ŸŒˆ. See the โ€œPluginsโ€ section for more info ๐Ÿ’œ.

The security policy decides what privileges, if any, a user gets when running sudo ๐Ÿ”ฅ. It might make the user prove who they are with a password or some other authentication method. If authentication is required and the password isn't entered within a configurable time limit, sudo exits ๐Ÿ’€. That limit is policy-specific, and the default password prompt timeout for the sudoers security policy is 0 minutes, so no pressure ๐Ÿ™ˆ.

Security policies may support credential caching, which lets the user run sudo again for a while without re-authenticating โฐ. By default, the sudoers policy caches credentials per terminal for 15 minutes ๐Ÿ“. See the timestamp_type and timestamp_timeout options in sudoers(5) for more details. Running sudo with the -v option refreshes the cached credentials without running a command ๐Ÿซถ.

โš ๏ธ On systems where sudo is the main way to get superuser privileges, it is imperative to avoid syntax errors in the security policy configuration files ๐Ÿ˜ญ. For the default security policy, sudoers(5), make your changes with the visudo(8) utility, which makes sure no syntax errors sneak in ๐Ÿ›ก๏ธ.

When invoked as sudoedit, the -e option (described below) is implied ๐Ÿ“.

Security policies and audit plugins may log successful and failed attempts to run sudo ๐Ÿ‘€. If an I/O plugin is configured, the running command's input and output may get logged too ๐ŸŽฌ.

๐ŸŽ€ OPTIONS

The options are as follows, bestie ๐Ÿ’…:

  • -A, --askpass โ€” normally, if sudo needs a password, it reads it straight from the user's terminal. With -A (askpass), a helper program (possibly graphical ๐ŸชŸ) is run instead, which reads the password and prints it to the standard output. If the SUDO_ASKPASS environment variable is set, it holds the path to that helper program. Otherwise, if sudo.conf(5) has a line naming the askpass program, that value gets used. For example:
# Path to askpass helper program
Path askpass /usr/bin/ssh-askpass

If there's no askpass program available, sudo exits with an error ๐Ÿ˜ค.

  • -B, --bell โ€” rings the bell as part of the password prompt when a terminal is present ๐Ÿ””. This does nothing if an askpass program is being used ๐Ÿ™ƒ.
  • -b, --background โ€” runs the given command in the background ๐ŸŒ™. You can't use shell job control to manage background processes started by sudo, so most interactive commands will fail to work properly in background mode ๐Ÿ’€.
  • -C num, --close-from=num โ€” closes all file descriptors greater than or equal to num before running a command ๐Ÿšช. Values less than 3 aren't allowed ๐Ÿšซ. By default, sudo closes every open file descriptor except standard input, standard output, and standard error when it runs a command. The security policy might restrict your ability to use this option. The sudoers policy only lets you use -C if the administrator has turned on the closefrom_override option ๐Ÿ”’.
  • -D directory, --chdir=directory โ€” runs the command in the specified directory instead of the current working directory ๐Ÿ“‚. The security policy may throw an error if you don't have permission to pick the working directory ๐Ÿ™….
  • -E, --preserve-env โ€” tells the security policy that you want to keep your existing environment variables โœจ. The policy may return an error if you don't have permission to preserve the environment ๐Ÿฅฒ.
  • --preserve-env=list โ€” tells the security policy you want to add the comma-separated list of environment variables to the ones preserved from your environment ๐Ÿ“. Same deal as above: the policy may error if you aren't allowed to preserve the environment. This option can be specified multiple times ๐Ÿ”.
  • -e, --edit โ€” edits one or more files instead of running a command ๐Ÿ“. Instead of a path name, the string "sudoedit" is used when consulting the security policy ๐Ÿ•ต๏ธ. If the policy authorizes you, these steps happen:
    1. Temporary copies are made of the files to be edited, with the owner set to the invoking user ๐Ÿง‘โ€๐ŸŽจ.
    2. The editor specified by the policy runs to edit the temporary files. The sudoers policy checks the SUDO_EDITOR, VISUAL and EDITOR environment variables (in that order) ๐Ÿ–Š๏ธ. If none of SUDO_EDITOR, VISUAL or EDITOR are set, the first program listed in the editor sudoers(5) option is used.
    3. If they've been modified, the temporary files get copied back to their original location and the temporary versions are removed ๐Ÿงน.

To help stop people from editing files they shouldn't, these restrictions are enforced unless the security policy explicitly allows otherwise ๐Ÿ›ก๏ธ:

  • Symbolic links may not be edited (version 1.8.15 and higher) ๐Ÿšซ.
  • Symbolic links along the path to be edited are not followed when the parent directory is writable by the invoking user, unless that user is root (version 1.8.16 and higher) ๐Ÿ”—.
  • Files located in a directory that is writable by the invoking user may not be edited unless that user is root (version 1.8.16 and higher) ๐Ÿ“.

Users are never allowed to edit device special files ๐Ÿ™…โ€โ™€๏ธ.

If the specified file doesn't exist, it gets created โœจ. Unlike most commands run by sudo, the editor runs with the invoking user's environment unmodified ๐ŸŒท. If the temporary file is empty after editing, the user gets prompted before it's installed ๐Ÿซฃ. If, for some reason, sudo can't update a file with its edited version, the user gets a warning and the edited copy stays in a temporary file ๐Ÿ˜ฌ.

  • -g group, --group=group โ€” runs the command with the primary group set to group instead of the primary group from the target user's password database entry ๐ŸŽ€. The group can be a group name or a numeric group-ID (GID) prefixed with the # character (e.g., #0 for GID 0). When running a command as a GID, many shells require that the # be escaped with a backslash (\) ๐Ÿš. If no -u option is given, the command runs as the invoking user. Either way, the primary group gets set to group ๐Ÿ”. The sudoers policy lets you specify any of the target user's groups with -g as long as the -P option isn't in use ๐Ÿ‘ฏ.
  • -H, --set-home โ€” asks the security policy to set the HOME environment variable to the home directory from the target user's password database entry ๐Ÿ . Depending on the policy, this might be the default behavior already ๐Ÿคทโ€โ™€๏ธ.
  • -h, --help โ€” displays a short help message to the standard output and exits ๐Ÿ’.
  • -h host, --host=host โ€” runs the command on the specified host, if the security policy plugin supports remote commands ๐ŸŒ. The sudoers plugin doesn't currently support running remote commands ๐Ÿ™…. This can also be used with the -l option to list a user's privileges for the remote host ๐Ÿ“‹.
  • -i, --login โ€” runs the shell from the target user's password database entry as a login shell ๐ŸŒ™. That means login-specific resource files like .profile, .bash_profile, or .login will be read by the shell ๐Ÿ“œ. If a command is given, it's passed to the shell as a simple command using the -c option. The command and any args get concatenated, separated by spaces, after each character (including white space) is escaped with a backslash (\), except for alphanumerics, underscores, hyphens, and dollar signs ๐Ÿงต. If no command is given, an interactive shell runs ๐Ÿš. sudo tries to change to that user's home directory before running the shell ๐Ÿก. The command runs with an environment similar to the one a user would get at login ๐ŸŒธ. Most shells behave differently when a command is specified versus an interactive session, so check your shell's manual for details ๐Ÿ“–. The Command environment section in the sudoers(5) manual documents how -i affects the environment a command runs in when the sudoers policy is in use ๐Ÿ’….
  • -K, --remove-timestamp โ€” similar to -k, except it removes every cached credential for the user, no matter the terminal or parent process ID ๐Ÿงน. The next time sudo runs, a password must be entered if the security policy requires authentication ๐Ÿ”. You can't use -K together with a command or any other option ๐Ÿ™…โ€โ™€๏ธ. This option doesn't need a password ๐Ÿซถ. Not all security policies support credential caching, so this might not do anything for you ๐Ÿคทโ€โ™€๏ธ.
  • -k, --reset-timestamp โ€” okay so, without a command this one wipes your cached credentials for the current session ๐Ÿงน Next time you run sudo in that session, you'll need to type your password if the security policy wants authentication. By default the sudoers policy keeps a separate cache record for each terminal (or the parent process ID if there's no terminal), so -k can't mess with sudo commands running in a different terminal session ๐Ÿ™ˆ See the timestamp_type option in sudoers(5) for more. This one doesn't need a password, and it was added so you can revoke sudo permissions from a .logout file ๐Ÿšช

When you pair -k with a command or an option that might need a password, sudo ignores your cached credentials. So it'll prompt you for a password (if the security policy requires one) and won't update your cached credentials either. Main character move ๐Ÿ’…

Not all security policies support credential caching.

  • -l, --list โ€” list your privileges ๐Ÿ“‹ Without a command, this shows what the invoking user (or the user picked with -U) can do on the current host. If you specify it multiple times and the security policy supports verbose output, you get a longer list ๐Ÿ‘€

If you give a command that the policy allows for the invoking user (or the user picked with -U) on this host, sudo shows the fully-qualified path to the command along with any args. Use -l more than once (if the policy supports it) and the matching rule shows up in verbose format next to the command ๐Ÿ” If the command isn't allowed by the policy, sudo exits with a status value of 1. Big oof ๐Ÿ’€

  • -N, --no-update โ€” don't update the cached credentials, even if you authenticate successfully โœ‹ Unlike -k, existing cached credentials still get used if they're valid. To check whether your cached credentials are valid (or whether no authentication is needed at all), you can use:
sudo -Nnv

Not all security policies support credential caching.

  • -n, --non-interactive โ€” no prompting, bestie ๐Ÿค sudo won't ask you for any input of any kind. If the command needs a password, sudo displays an error message and exits instead.
  • -P, --preserve-groups โ€” keeps your group vector exactly as it is ๐Ÿซถ By default the sudoers policy resets the group vector to the list of groups the target user belongs to. The real and effective group-IDs still get set to match the target user, though.
  • -p prompt, --prompt=prompt โ€” swap in a custom password prompt โœจ You can use these percent (%) escape sequences, which the sudoers policy supports:
    • %H โ€” the full host name, domain included (only if the machine's host name is fully qualified or the fqdn option is set in sudoers(5)) ๐ŸŒ
    • %h โ€” the local host name, no domain ๐Ÿ 
    • %p โ€” the name of the user whose password is being requested (respects the rootpw, targetpw, and runaspw flags in sudoers(5)) ๐Ÿ”‘
    • %U โ€” the login name of the user the command will run as (defaults to root unless -u is also specified) ๐Ÿ‘‘
    • %u โ€” your invoking user's login name ๐Ÿง
    • %% โ€” two % characters in a row collapse into a single % ๐Ÿ’…

Your custom prompt overrides the default prompt from either the security policy or the SUDO_PROMPT environment variable. On systems that use PAM, it also overrides the prompt set by a PAM module, unless the passprompt_override flag is disabled in sudoers. ๐ŸŽ€

  • -R directory, --chroot=directory โ€” change to the specified root directory (see chroot(8)) before running the command ๐ŸŒณ The security policy might throw an error if you don't have permission to pick that root directory.
This option is deprecated and will be removed in a future version of sudo. Don't get too attached to it, bestie ๐Ÿ˜ญ
  • -r role, --role=role โ€” run the command with an SELinux security context that includes the role you specify ๐Ÿฆ‹
  • -S, --stdin โ€” the prompt goes to standard error, and the password gets read from standard input instead of the terminal device โŒจ๏ธ Handy for scripts ๐Ÿงš
  • -s, --shell โ€” run a shell ๐Ÿš It uses the shell in the SHELL environment variable if that's set, or the shell from the invoking user's password database entry. If you give a command, it gets passed to the shell as a simple command using the -c option. The command and its args get joined with spaces, after every character (including white space) is escaped with a backslash (\), except for alphanumerics, underscores, hyphens, and dollar signs. If there's no command, you get an interactive shell โœจ Most shells act differently when a command is given versus an interactive session, so check your shell's manual for the deets ๐Ÿ“–
  • -t type, --type=type โ€” run the command with an SELinux security context that includes the type you specify ๐ŸŒˆ If you don't specify a type, the default type comes from the role.
  • -U user, --other-user=user โ€” pairs with -l to list the privileges for user instead of for you ๐Ÿ‘€ The security policy might not let you peek at other users' privileges. With the sudoers policy, -U is limited to root and to users who have the "list" privilege for the specified user, or who can run any command as root or user on the current host ๐Ÿ”’
  • -T timeout, --command-timeout=timeout โ€” set a timeout for the command โฐ If the timeout runs out before the command exits, the command gets terminated ๐Ÿ’€ The security policy might restrict your ability to set timeouts. The sudoers policy requires that user-specified timeouts be explicitly enabled.
  • -u user, --user=user โ€” run the command as someone other than the default target user (usually root) ๐Ÿงš The user can be a user name or a numeric user-ID (UID) prefixed with the # character (e.g., #0 for UID 0). When running commands as a UID, many shells need the # escaped with a backslash (\) ๐Ÿ™ˆ Some security policies only allow UIDs that are in the password database. The sudoers policy allows UIDs that aren't in the password database, as long as the targetpw option isn't set. Other security policies might not support this at all.
  • -V, --version โ€” prints the sudo version string, plus the version string of any configured plugins ๐Ÿ”ข If the invoking user is already root, -V also displays the options passed to configure when sudo was built. Plugins might show extra info, like default options ๐Ÿค“
  • -v, --validate โ€” update your cached credentials, authenticating you if needed โœ… For the sudoers plugin, this extends the sudo timeout by another 15 minutes by default, but it doesn't run a command. Not all security policies support cached credentials.
  • -- โ€” the -- marks the end of the sudo options ๐Ÿšง Anything after it gets passed to the command.

Options that take a value can only be specified once, unless the description says otherwise ๐Ÿ™…โ€โ™€๏ธ This helps protect against problems caused by poorly written scripts that invoke sudo with user-controlled input. Protect yourself, babe ๐Ÿ›ก๏ธ

You can also pass environment variables for the command as options to sudo, in the form VAR=value. For example: LD_LIBRARY_PATH=/usr/local/pkg/lib. These might be subject to restrictions from the security policy plugin โœจ The sudoers policy treats environment variables passed as options the same way as existing environment variables, with one important difference. If the setenv option is set in sudoers, and the command to be run has the SETENV tag set or the matched command is ALL, you can set variables that would otherwise be forbidden ๐Ÿ‘‘ See sudoers(5) for more info.

โœจ COMMAND EXECUTION โœจ

okay so when sudo runs a command, the security policy decides the execution environment ๐Ÿ’… Usually the real and effective user and group IDs get set to match the target user from the password database, and the group vector gets set up from the group database (unless you passed -P) ๐Ÿซถ

the security policy can set any of these for the command:

  • real and effective user-ID ๐Ÿ‘‘
  • real and effective group-ID ๐Ÿ‘‘
  • supplementary group-IDs ๐ŸŽ€
  • the environment list ๐ŸŒธ
  • current working directory ๐Ÿ“‚
  • file creation mode mask (umask) ๐Ÿฆ‹
  • SELinux role and type ๐Ÿ”ฅ
  • scheduling priority (aka nice value) โญ

โœจ Process model โœจ

there are two distinct ways sudo can run a command, bestie ๐Ÿงš

if an I/O logging plugin is set up to log terminal I/O, or the security policy explicitly asks for it, sudo allocates a new pseudo-terminal (โ€œptyโ€) and calls fork(2) to make a second sudo process called the monitor ๐Ÿ’œ the monitor creates a new terminal session where it's the leader and the pty is its controlling terminal, calls fork(2) again, sets up the execution environment as described above, and then uses the execve(2) system call to run the command in the child process ๐Ÿฆ‹ the monitor exists to relay job control signals between your terminal and the pty the command runs in, so you can suspend and resume the command like normal ๐Ÿ™Œ without it, the command would be in what POSIX calls an โ€œorphaned process groupโ€ and it would not get any job control signals from the kernel ๐Ÿ’€ when the command exits or gets killed by a signal, the monitor passes the exit status up to the main sudo process and exits. then the main sudo process passes the exit status to the security policy's close function, plus the close function of any configured audit plugin, and exits ๐ŸŒˆ this mode is the default for sudo versions 1.9.14 and above when using the sudoers policy ๐Ÿ’–

if no pty is used, sudo calls fork(2), sets up the execution environment as described above, and uses execve(2) to run the command in the child process ๐ŸŒธ the main sudo process waits until the command finishes, then passes the exit status to the security policy's close function, plus the close function of any configured audit plugins, and exits โœจ as a special case, if the policy plugin doesn't define a close function, sudo just executes the command directly instead of calling fork(2) first ๐Ÿ™ˆ the sudoers policy plugin only defines a close function when I/O logging is enabled, a pty is required, an SELinux role is specified, the command has an associated timeout, or the pam_session or pam_setcred options are enabled. both pam_session and pam_setcred are enabled by default on systems using PAM ๐Ÿซถ this mode is the default for sudo versions prior to 1.9.14 when using the sudoers policy ๐Ÿ“

on systems that use PAM, the security policy's close function is responsible for closing the PAM session ๐Ÿ” it may also log the command's exit status ๐Ÿ“

โœจ Signal handling โœจ

when the command runs as a child of the sudo process, sudo relays any signals it receives over to the command ๐Ÿ“ก SIGINT and SIGQUIT only get relayed when the command is running in a new pty, or when the signal was sent by a user process and not the kernel. this stops the command from getting SIGINT twice every time you hit control-C ๐Ÿ™„ some signals, like SIGSTOP and SIGKILL, can't be caught, so they won't be relayed to the command ๐Ÿ’€ as a general rule, use SIGTSTP instead of SIGSTOP when you want to suspend a command being run by sudo ๐Ÿ’œ

as a special case, sudo won't relay signals that were sent by the command it's running. this stops the command from accidentally killing itself ๐Ÿ˜ญ on some systems, the reboot(8) utility sends SIGTERM to all non-system processes other than itself before rebooting the system. this keeps sudo from relaying the SIGTERM it received back to reboot(8), which might then exit before the system was actually rebooted, leaving it in a half-dead state similar to single user mode ๐Ÿ’€ heads up though, this check only applies to the command run by sudo and not to any other processes that command may create. so running a script that calls reboot(8) or shutdown(8) via sudo may leave the system in this undefined state, unless reboot(8) or shutdown(8) are run using the exec() family of functions instead of system() (which puts a shell between the command and the calling process) โš ๏ธ

โœจ Plugins โœจ

plugins can be specified with Plugin directives in the sudo.conf(5) file ๐Ÿงฉ they may be loaded as dynamic shared objects (on systems that support them), or compiled directly into the sudo binary. if there's no sudo.conf(5) file, or it doesn't have any Plugin lines, sudo uses sudoers(5) for the policy, auditing, and I/O logging plugins ๐ŸŽ€ check the sudo.conf(5) manual for details on the /etc/sudo.conf file, and the sudo_plugin(5) manual for more info about the sudo plugin architecture ๐Ÿ“š


โœจ EXIT VALUE โœจ

okay this part is so important ๐Ÿฅบ if a command runs successfully, the exit status from sudo is the exit status of the program that was executed ๐Ÿ’ฏ if the command died from a signal, sudo sends itself the same signal that killed the command ๐Ÿ’€

if you use the -l option without a command, sudo exits with 0 if you're allowed to run sudo and you authenticated successfully (as the security policy requires) โœ… if a command is given with -l, the exit value is only 0 if the security policy permits that command. otherwise it's 1 ๐Ÿ™…โ€โ™€๏ธ

if there's an authentication failure, a configuration or permission problem, or the given command can't be executed, sudo exits with 1 ๐Ÿ˜ญ in that last case, the error string gets printed to standard error. if sudo can't stat(2) one or more entries in your PATH, an error gets printed to standard error too. (if the directory doesn't exist or isn't really a directory, the entry gets ignored and no error is printed ๐Ÿ™ˆ) this shouldn't happen under normal circumstances โœจ the most common reason stat(2) returns โ€œpermission deniedโ€ is if you're running an automounter and one of the directories in your PATH lives on a machine that's currently unreachable ๐ŸŒ


โœจ SECURITY NOTES โœจ

sudo really tries to be safe when it executes external commands ๐Ÿ›ก๏ธ

to prevent command spoofing, sudo checks "." and "" (both mean the current directory) last when it searches for a command in your PATH (if one or both are in there) ๐Ÿ•ต๏ธโ€โ™€๏ธ depending on the security policy, your PATH environment variable may be modified, replaced, or passed through unchanged to the program sudo runs ๐Ÿซง

never give someone sudo privileges to run files that are writable by them, or that live in a directory they can write to ๐Ÿšซ if the user can modify or replace the command, there's no way to limit what other commands they can run ๐Ÿ’€

by default, sudo only logs the command it explicitly runs. if someone runs a command like sudo su or sudo sh, any commands run from that shell aren't subject to sudo's security policy ๐Ÿ˜ฑ the same goes for commands that offer shell escapes (including most editors) ๐Ÿ“ if I/O logging is enabled, those subsequent commands will have their input and/or output logged, but there won't be traditional logs for them. so be careful when you give users access to commands via sudo, and check that the command won't accidentally give them an effective root shell ๐Ÿ‘‘ for ways to handle this, see the Preventing shell escapes section in sudoers(5) ๐Ÿ“–

to protect potentially sensitive info, sudo disables core dumps by default while it's running (they get re-enabled for the command that runs) ๐Ÿ”’ this is a historical practice from a time when most operating systems let set-user-ID processes dump core by default ๐Ÿฆ– if you want to debug sudo crashes, you can re-enable core dumps by setting "disable_coredump" to false in the sudo.conf(5) file like this ๐Ÿ”ง

    Set disable_coredump false

see the sudo.conf(5) manual for more info ๐Ÿซถ ๐Ÿ’…

โœจ ENVIRONMENT โœจ

okay so sudo reads and sets a bunch of environment variables ๐ŸŒธ but bestie, the security policy is the one with the final say on what the command's environment actually looks like ๐Ÿ’…

  • EDITOR โ€” the default editor for -e (sudoedit) mode, but only if neither SUDO_EDITOR nor VISUAL is set ๐Ÿ“
  • MAIL โ€” gets set to the mail spool of the target user when you pass -i, or when env_reset is on in sudoers. (Unless MAIL is in the env_keep list, then it stays put ๐Ÿซถ)
  • HOME โ€” gets set to the target user's home directory when you use -i or -H, when you use -s and set_home is set in sudoers, when always_set_home is enabled in sudoers, or when env_reset is enabled in sudoers and HOME isn't in the env_keep list ๐Ÿก
  • LOGNAME โ€” gets set to the target user's login name when you use -i, when the set_logname option is enabled in sudoers, or when the env_reset option is enabled in sudoers (unless LOGNAME is in env_keep) ๐ŸŽ€
  • PATH โ€” the security policy is allowed to override this one ๐Ÿฆ‹
  • SHELL โ€” used to figure out which shell to run with the -s option ๐Ÿš
  • SUDO_ASKPASS โ€” the path to a helper program that reads the password when there's no terminal around, or when you pass the -A option ๐Ÿ”
  • SUDO_COMMAND โ€” gets set to the command sudo ran, args included. The args get chopped off at 4096 characters to prevent a potential execution error ๐Ÿ’€
  • SUDO_EDITOR โ€” the default editor for -e (sudoedit) mode ๐Ÿ“
  • SUDO_GID โ€” the group-ID of the person who invoked sudo ๐ŸŒˆ
  • SUDO_HOME โ€” the home directory of the person who invoked sudo ๐Ÿ 
  • SUDO_PROMPT โ€” the default password prompt, unless you used the -p option ๐Ÿ’œ
  • SUDO_PS1 โ€” if this is set, PS1 gets set to its value for the program being run โญ
  • SUDO_TTY โ€” the terminal device of the person who invoked sudo, if there is one ๐Ÿ–ฅ๏ธ
  • SUDO_UID โ€” the user-ID of the person who invoked sudo ๐Ÿงš
  • SUDO_USER โ€” the login name of the person who invoked sudo ๐Ÿ“
  • USER โ€” set to the same value as LOGNAME, which we just covered ๐Ÿซง
  • VISUAL โ€” the default editor for -e (sudoedit) mode, but only if SUDO_EDITOR isn't set ๐ŸŒท

โœจ FILES โœจ

okay this one's short and sweet ๐Ÿฌ

  • /etc/sudo.conf โ€” the sudo front-end configuration ๐Ÿ”ง

โœจ EXAMPLES โœจ

these examples assume your security policy is properly configured, so make sure that's sorted before you try them ๐Ÿซถ

To get a file listing of an unreadable directory:

$ sudo ls /usr/local/protected

To list the home directory of user yaz on a machine where the file system holding ~yaz is not exported as root:

$ sudo -u yaz ls ~yaz

To edit the index.html file as user www:

$ sudoedit -u www ~www/htdocs/index.html

To view system logs that only root and the users in the adm group can access:

$ sudo -g adm more /var/log/syslog

To run an editor as jim with a different primary group:

$ sudoedit -u jim -g audio ~jim/sound.txt

To shut down a machine:

$ sudo shutdown -r +15 "quick reboot"

To make a usage listing of the directories in the /home partition. The commands run in a sub-shell so that the โ€˜cdโ€™ command and file redirection can actually work ๐Ÿง 

$ sudo sh -c "cd /home ; du -s * | sort -rn > USAGE"

โœจ DIAGNOSTICS โœจ

here are the error messages sudo might throw at you, so you know what's going on when it happens ๐Ÿ™ˆ

Error messages produced by sudo include:

editing files in a writable directory is not permitted

by default, sudoedit won't let you edit a file when any of the parent directories are writable by the user who invoked it. This avoids a race condition that could let the user overwrite an arbitrary file ๐Ÿšซ. See the sudoedit_checkdir option in sudoers(5) for more information.

by default, sudoedit doesn't follow symbolic links when it opens files ๐Ÿ”—. See the sudoedit_follow option in sudoers(5) for more information.

effective uid is not 0, is sudo installed setuid root?

sudo wasn't run with root privileges. The sudo binary has to be owned by the root user and have the set-user-ID bit set. It also can't be located on a file system mounted with the โ€˜nosuidโ€™ option, or on an NFS file system that maps uid 0 to an unprivileged uid ๐Ÿ˜ค

effective uid is not 0, is sudo on a file system with the 'nosuid' option set or an NFS file system without root privileges?

sudo wasn't run with root privileges. The sudo binary has the right owner and permissions, but it still didn't run as root anyway ๐Ÿ˜ญ. The most common reason is that the file system the sudo binary lives on is mounted with the โ€˜nosuidโ€™ option, or it's an NFS file system that maps uid 0 to an unprivileged uid.

fatal error, unable to load plugins

an error happened while loading or initializing the plugins specified in sudo.conf(5) ๐Ÿ”Œ

invalid environment variable name

one or more environment variable names you passed via the -E option had an equal sign (โ€˜=โ€™) in them. The arguments to -E should just be environment variable names, without any value attached ๐Ÿ™…โ€โ™€๏ธ

no password was provided

when sudo tried to read the password, it didn't get any characters. This can happen when there's no terminal available (or you used the -S option) and standard input got redirected from /dev/null ๐Ÿ•ณ๏ธ

a terminal is required to read the password

sudo needs to read the password, but there's no mechanism available to do it. Remote commands run via ssh(1) don't have a terminal by default, but passing the -t option to ssh(1) makes it allocate one, which should let sudo read the password ๐Ÿ’ป. To let sudo run local commands without a terminal, you can use the -S option to read the password from standard input, or configure an askpass helper either through the sudo.conf(5) file or by setting the SUDO_ASKPASS environment variable ๐Ÿ”.

no writable temporary directory found

sudoedit couldn't find a usable temporary directory to store its intermediate files ๐Ÿ“‚

The โ€œno new privilegesโ€ flag is set, which prevents sudo from running as root.

sudo was run by a process that has the Linux โ€œno new privilegesโ€ flag set. This makes the set-user-ID bit get ignored when running an executable, which stops sudo from working. The most likely cause is running sudo inside a container that sets this flag. Check the container's documentation to see if you can configure it so the flag isn't set ๐Ÿ“ฆ

sudo must be owned by uid 0 and have the setuid bit set

sudo wasn't run with root privileges. The sudo binary doesn't have the correct owner or permissions. It has to be owned by the root user and have the set-user-ID bit set ๐Ÿ› ๏ธ

sudoedit is not supported on this platform

sudoedit only works on systems that support setting the effective user-ID ๐Ÿ™ƒ

timed out reading password

you didn't enter a password before the password timeout expired. That's 5 minutes by default โฐ

you do not exist in the passwd database

your user-ID doesn't show up in the system passwd database ๐Ÿ‘ป

you may not specify environment variables in edit mode

you can only specify environment variables when you're running a command. When you're editing a file, the editor runs with your environment left completely unmodified ๐Ÿ™…


โœจ SEE ALSO โœจ

if you want to keep going, check these out ๐Ÿฆ‹


โœจ HISTORY โœจ

for a brief history of sudo, check out the HISTORY.md file in the sudo distribution, at https://www.sudo.ws/about/history/ ๐Ÿ“œ


โœจ AUTHORS โœจ

so many people have worked on sudo over the years ๐Ÿซถ this version is made up of code written mainly by:

Todd C. Miller ๐Ÿ‘‘

For an exhaustive list of everyone who's contributed to sudo, see the CONTRIBUTORS.md file in the sudo distribution, at https://www.sudo.ws/about/contributors/ ๐ŸŒˆ


โœจ CAVEATS โœจ

okay real talk, these are the things you need to be careful about ๐Ÿซฃ

There is no easy way to stop a user from getting a root shell if that user is allowed to run arbitrary commands via sudo ๐Ÿ˜ฌ. Also, lots of programs (like editors) let you run commands through shell escapes, which means you can skip sudo's checks entirely. That said, on most systems you can block shell escapes with the noexec functionality in the sudoers(5) plugin ๐Ÿ”’.

It's not meaningful to run the โ€˜cdโ€™ command directly via sudo, bestie, like this:

$ sudo cd /usr/local/protected

because when the command exits, the parent process (your shell) is still in the same directory it was before ๐Ÿ™ƒ. The -D option can be used to run a command in a specific directory instead.

Running shell scripts via sudo can expose the same kernel bugs that make set-user-ID shell scripts unsafe on some operating systems. (If your OS has a /dev/fd/ directory, set-user-ID shell scripts are generally safe ๐Ÿซง.)


โœจ BUGS โœจ

if you think you've found a bug in sudo, you can either file a report in the sudo bug database at https://bugzilla.sudo.ws/, or open an issue at https://github.com/sudo-project/sudo/issues ๐Ÿ›. If you'd rather use email, you can send messages to the sudo-workers mailing list at https://www.sudo.ws/mailman/listinfo/sudo-workers (public), or to <sudo@sudo.ws> (private) ๐Ÿ’Œ.

๐Ÿšจ Please do NOT report security vulnerabilities through public GitHub issues, Bugzilla, or mailing lists! Instead, email them to <Todd.Miller@sudo.ws>. You can encrypt your message with PGP if you'd like, using the key found at https://www.sudo.ws/dist/PGPKEYS ๐Ÿ”

โœจ SUPPORT โœจ

you can get limited free support through the sudo-users mailing list. Check https://www.sudo.ws/mailman/listinfo/sudo-users to subscribe or to search the archives ๐Ÿ’ฌ


โœจ DISCLAIMER โœจ

sudo is provided โ€œAS ISโ€, and any express or implied warranties, including but not limited to the implied warranties of merchantability and fitness for a particular purpose, are disclaimed ๐Ÿ™…. For complete details, see the LICENSE.md file distributed with sudo, or https://www.sudo.ws/about/license/ ๐Ÿ“„


That's a wrap on the sudo manual, bestie! ๐ŸŽ€ You made it through the whole thing, and honestly? Iconic behaviour ๐Ÿ’…โœจ Go touch grass, then go sudo responsibly ๐Ÿซถ๐ŸŒธ

๐Ÿ“ฆ where this page comes from