To sudo or not to sudo – demystifying CVE-2019-14287

A new vulnerability kickstarted last week spreading kernel panics and loss of UDP packets among Linux users reading about it.

The vulnerability, found in the popular Linux tool Sudo allows unintended users to execute commands as root.

While all vulnerabilities are important and should be mitigated as soon as possible, this particular one seems to be shrouded in a cloud of mystic smoke making it look bigger and fiercer then it should be perceived as.

If you think sudo is some kind of martial art

If this is the first time you hear about this, sudo is a Linux command which “allows a system administrator to delegate authority to give certain users (or groups of users) the ability to run some (or all) commands as root or another user”.

In other words, an all powerful command which allows a user to run commands as if run by another user. Depending on the configuration, certain restrictions can be imposed, like allowing a user to run ONLY a certain command or allowing the user to impersonate ONLY a certain user/group.

Recipe of the vulnerability

Versions affected: < 1.8.28

Configuration file containing a line allowing a user to run a command as ANY OTHER user EXCEPT root:
Format:

user host = (ALL, !root) command

Example:
totally-secure-user bit-sentinel = (ALL, !root) /usr/bin/id

Command to be run as totally-secure-user:

sudo -u#-1 id -u
sudo -u#4294967295 id -u

As you can see in the picture below, id -u returned 0 which is the uid for root.

Why does this work?

First of all, why the flipping bits would you allow a user to run a specific command as any other user than root?

Usually, non eccentric people would allow a user to run commands as root or as any member of a certain group.

Running sudo -u# allows a user to run a command as the user with ID uid. As you may or may not know, sudo initially runs as root and then passes the ID parameter to setresuid and setreuid system calls to change the effective user ID of the command.

Reading the manual for those functions we learn that -1 is a special value 

Supplying a value of -1 for either the real or effective user ID forces the system to leave that ID unchanged.

according to setreuid manual.

If one of the arguments equals -1, the corresponding value is not changed.

According to setresuid manual.

Let’s recap what happens with an example (based on the configuration above):

  1. user totally-secure-user runs 
    sudo -u#-1 id -u
  2. the sudo process starts with root as effective user
  3. sudo sends -1 parameter to setresuid and setreuid
  4. those don’t change the effective user of the command to be run
  5. BANG id -u runs as root

Ok, -1 is referenced in the manual and all, but what about that weird random number 4294967295?

Its quite easy, setresuid and setreuid parameters are of type uid_t, which is a 32 bit unsigned int. An unsigned int only interprets values as positive numbers and as it is a 32 bit variable, it’s values will be in the range 0 -> 4294967295. 

So, what happens when we send -1 as a parameter? Well, somewhere along the underlying code lines is a convention that -1 is represented as 4294967295, thus either values will get the wanted result.

How the vulnerability was solved?

As we can see in the patch, this vulnerability was mitigated by not allowing values equal to -1 as the id.

How to check if you are vulnerable?

  1. Run sudo -V and check if your version is < 1.8.28
  2. Check if your config files contains ! and if there are any runas user that include root(be it written as !root or !#0 or other reference shenanigans

Note: Depending on your configuration you should check both your default configuration file(/etc/sudoers by default in Ubuntu) and all the files from the folders included with the #includedir directive inside it.

Mitigation

  1. Update sudo to 1.8.28 or greater
  2. Remove all lines containing vulnerable lines

Where you can see the logs of such activities?

Commands executed with sudo are logged by default in /var/log/auth.log (Ubuntu).

Will show up in logs as:

The logging format includes USER= followed by username or id as which the command was/wasn’t ran. Thus, in the example we see root or #-1 or #4294967295 as values.

As many defensive mechanisms only look in logs after suspicious activity run by USER=root, exploiting this vulnerability will not raise any alerts as USER will be set to #-1 or #4294967295. Thus an update to the rules to include those values is advised.

Conclusion

To put it in a nutshell, even though a vulnerability is a vulnerability, some become more famous due to the hype created around them. One should always make a thoroughly investigation or ask a professional’s opinion when necessary.

Credit and useful links

  • Joe Vennix (Apple Information Security) as the original reporter
  • https://www.sudo.ws/alerts/minus_1_uid.html
  • https://access.redhat.com/security/cve/cve-2019-14287

The article was written by Ionut Bucur, acting as a Junior Cyber Security Penetration Tester at Bit Sentinel.


[email protected]

get in touch