How to patch CVE 2021-3156

With a single script

*

01 Feb 2021

Wintrmvte

Introduction

On 26th of January, a major vulnerability in widely deployed sudo utility was discovered; it allows privillege escalation to root using a single buffer overflow exploit and a specially crafted command. In this post, we will see how to efficiently patch this with a few lines of shell scripting.

UPDATE: it seems that version 1.9.5p2 is not safe anymore, but when new, safe release of sudo appears, this script can be easily modified to reflect this.

Affected versions

As seen on NIST, every version earlier than 1.9.5p2 is vulnerable to this attack. Let’s look at sudo.ws to find out about the latest stable release :

It seems that it was published on the same day that the exploit was publicly disclosed. Inspecting the above link, we find out that it points to a standard .tar.gz archive:

So in order to update our sudo to latest version, we will simply download, extract and install the stuff from above.

Automatic check of local version

We don’t want our script to download anything if version requirements are already satisfied, so we have to write some basic mechanism that checks if our current release is affected. We can retrieve local version using sudo --version. This is the output:


Sudo version 1.9.5p2
Sudoers policy plugin version 1.9.5p2
Sudoers file grammar version 48
Sudoers I/O plugin version 1.9.5p2
Sudoers audit plugin version 1.9.5p2

As you can see, my version is already patched, but for the sake of this article let’s assume that it isn’t ;> We are interested in the first line of the above - it explicitly shows us what version is in use. Now, let’s try assigning it to a single variable:


$ current_sudo_ver=$(sudo --version|head -1|awk '{print $NF}')
$ echo $current_sudo_ver
1.9.5p2

Great, it is time for initial draft of our script: it will check sudo version and accordingly download and install available patch:


#!/bin/bash
current_sudo_ver=$(sudo --version | head -1 | awk '{print $NF}')
if [[ $current_sudo_version < 1.9 ]]; then
	... our installation function goes here ...
else
	echo "Your release is not affected! :D"
fi

Defining installation function

We will use wget to download latest stable release, tar to extract the archive, cd to change directory to it and make in order to compile and install.


sudo_update(){
	wget https://sudo.ws/dist/sudo-1.9.5p2.tar.gz
	tar -vxzf sudo-1.9.5p2.tar.gz
	cd sudo-1.9.5p2
	sudo ./configure && sudo make && sudo make install  # First we need to launch 'configure' script
	.. 												     # We go one dir node back
	rm -rf sudo-1.9.5p2								    # And remove the folder as it is no longer needed
}

Full script


#!/bin/bash

current_sudo_ver=$(sudo --version | head -1 | awk '{print $NF}')

sudo_update(){
	wget https://sudo.ws/dist/sudo-1.9.5p2.tar.gz
	tar -vxzf sudo-1.9.5p2.tar.gz
	cd sudo-1.9.5p2.tar.gz
	sudo ./configure && sudo make && sudo make install
	rm -rf sudo-1.9.5p2
}

if [[ $current_sudo_version < 1.9 ]]; then
	sudo_update()
else
	echo "Your release is not affected! :D"
fi

Final words

This post was really short and did not introduce anything game-changing, but I hope that it enabled you to get rid of CVE 2021-3156 a bit faster than doing it by hand.