Sudo 1.9.8: intercepting commands

A month ago, when sudo 1.9.8 was still under development, we checked out the new log_subcmds option. It allows you log all commands (with some limitations) that are executed by a command started through sudo. For example, you can see if a shell was started through a text editor. The intercept option brings this one step further: you can prevent sub-commands from even running.

Before you begin

To use sudo’s intercept option you need sudo 1.9.8 (or later). At the time of writing it is not available in any of the major Linux distributions. You can download ready-to-use binary packages for some Linux distributions and UNIX variants from the sudo website or build sudo yourself from source. Various BSDs also have an up-to-date version of sudo in ports.

Configuration and testing

Configuring the intercept option has two parts. First of all you need to enable it:

Defaults intercept

And then you can configure what commands you want to prevent from running. If you forget about this second step, it is no different from log_subcmds. Well, actually there are some side effects. For example I have not been able to run the vipw command with intercept enabled even without configuring any further limitations:

czanik@czplaptop:~> sudo -s
czplaptop:/home/czanik # vipw
sh: intercept port not set
sh: /usr/bin/vi: Permission denied
vipw: vi returned with status 126
vipw: /etc/passwd is unchanged
czplaptop:/home/czanik #

However the visudo command keeps working without a problem.

The above configuration intercepts all commands executed through sudo. You can limit the scope:

Defaults!/usr/bin/bash intercept

This setting will intercept only Bash and no other shells or commands.

The next line in the sudoers file prevents user czanik to run the who command from intercepted applications:

czanik ALL = (ALL) ALL, !/usr/bin/who

When I try to run it, the following text appears on the terminal:

czanik@czplaptop:~> sudo -s
czplaptop:/home/czanik # who
Sorry, user czanik is not allowed to execute '/usr/bin/who' as root on czplaptop.
bash: /usr/bin/who: Permission denied

You can also easily disable all shells:

Defaults intercept
Cmnd_Alias SHELLS=/usr/bin/bash, /usr/bin/sh, /usr/bin/csh
czanik ALL = (ALL) ALL, !SHELLS

Once you do this, you cannot use sudo -s any more:

czanik@czplaptop:~> sudo -s
Sorry, user czanik is not allowed to execute '/bin/bash' as root on czplaptop.

However there are some lesser expected side effects as well (at least unexpected to me…): it prevents not only shells but practically everything else executed from an application. Here is when I try to run ls from within vi:

czanik@czplaptop:~> sudo vi /etc/issue 
Sorry, user czanik is not allowed to execute '/bin/bash -c /bin/ls' as root on czplaptop.
Cannot execute shell /bin/bash
Press ENTER or type command to continue
czanik@czplaptop:~>

This is because vi, like most applications, runs its commands through a shell and sudo has been configured to deny access to shells.