AntiSnatchOr.com - Keep It Simple Stupid

  • about
  • security advisories
  • contact
  • publications
  • my books
Home › Blogs › euronymous's blog

Enumerate potential DOM-based XSS vulnerable code

euronymous — 28 April, 2011 - 10:01

While waiting for Stefano di Paola release of DOMinator, I've spent a little amount of time writing a Ruby script that uses Stefano regular expressions and list the potentially DOM-based XSS vulnerable piece of code.

The output needs manual verification, but at least it's something.

Thanks .mario and Stefano for your research on the topic. And thanks Michal for the "bugfix" regarding regex :-)
# Given a set of JS/HTML/whatever files it search for potential DOM-based XSS
# injection points based on regular expressions from https://code.google.com/p/domxsswiki/wiki/FindingDOMXSS
#
# author: Michele "antisnatchor" Orru' (regex credit goes to Mario ".mario" Heiderich)
# v. 0.1

require "net/http"
require "net/https"
require "uri"
require "erb"
require "singleton"
require "rubygems"

MAIN_URL = 'http://compraonline.mediaworld.it'
MAIN_DOMAIN = 'compraonline.mediaworld.it'
PORT = 80
HTTP_PROXY_HOST = '172.31.229.10'
HTTP_PROXY_PORT = 8888

PATHS_TO_TEST = ['/resources/script/new_hp.js',
				 '/resources/script/commonTop.js',
				 '/resources/script/scripter.js'
				]

puts "[+] starting requests to #{MAIN_URL}"
   Net::HTTP::Proxy(HTTP_PROXY_HOST, HTTP_PROXY_PORT).start(MAIN_DOMAIN) {|http|
    PATHS_TO_TEST.each{|path|
      url = URI.parse(MAIN_URL + ':' + PORT.to_s + path)
      req = Net::HTTP::Get.new(url.path)
         http.request(req) do |res|
         line = 1
         response = res.body.to_s.split("\n")
           response.each{|i|
             # apply DOM-based xss regex to each HTTP response line, printing out lineNumber and lineContent
             # that would potentially be vulnerable to DOM-based XSS (NEED MANUAL VERIFICATION!)
             if(i.scan(/((src|href|data|location|code|value|action)\s*["'\]]*\s*\+?\s*=)|((replace|assign|navigate|getResponseHeader|open(Dialog)?|showModalDialog|eval|evaluate|execCommand|execScript|setTimeout|setInterval)\s*["'\]]*\s*\()/).size > 0 ||
                i.scan(/(location\s*[\[.])|([.\[]\s*["']?\s*(arguments|dialogArguments|innerHTML|write(ln)?|open(Dialog)?|showModalDialog|cookie|URL|documentURI|baseURI|referrer|name|opener|parent|top|content|self|frames)\W)|(localStorage|sessionStorage|Database)/).size > 0)
              puts "[#{path}]-#{line}: #{i}"
             end
             line += 1
           }
         end
    }
   }


A sample of the output is the following:
[/resources/script/commonTop.js]-104:           top.location.href = apUrl;
[/resources/script/commonTop.js]-108:           top.location.href = url;
[/resources/script/commonTop.js]-113:   document.location.href = "http://" + server + "/webapp/wcs/stores/servlet/ListOrdersView?" +apDefUrl;
[/resources/script/commonTop.js]-117:   top.location.href = "http://" + server + "/webapp/wcs/stores/servlet/BrandsView?" + apDefUrl;
[/resources/script/commonTop.js]-124:           document.cookie = name + "=" + "; expires=Thu, 01-Jan-70 00:00:01 GMT";
[/resources/script/commonTop.js]-125:           top.location.href = "http://" + serverMobi;
[/resources/script/commonTop.js]-127:           top.location.href = "http://" + server + "/webapp/wcs/stores/servlet/PartnerVisit?onlyInsert
=Y&partnerId=7990000000000006500&storeId=20000&bannerId=home_mwcol&url=compraonline.mediaworld.it/html/LINKPROMO.html?content=/offerte/mobi/sez1.html";
[/resources/script/commonTop.js]-132:   document.location.href = "http://" + server + "/webapp/wcs/stores/servlet/ContactUsView?storeId=20000";
[/resources/script/commonTop.js]-136:   formObj.searchString.value = formObj.searchString.value.replace(/%/g,"");
[/resources/script/commonTop.js]-138:   if( formObj.searchString.value.replace(/^\s+|\s+$/g,"").length < 2 )
[/resources/script/commonTop.js]-149:           formObj.categoryId.value = document.getElementById('catGroupId').options[document.getElement
ById('catGroupId').selectedIndex].value;
[/resources/script/commonTop.js]-156:   window.open("http://" + server +"/webapp/wcs/stores/servlet/NewsletterView?" + apDefUrl,"newsletter"
,"width=440,height=354,scrollbars=no,resizable=no");
[/resources/script/scripter.js]-75:                     this.layer.document.writeln(body[i]);
[/resources/script/scripter.js]-82:     this.element.innerHTML = body;
[/resources/script/scripter.js]-88:     this.element.innerHTML = body;
  • euronymous's blog

Recent blog posts

  • Advances in BeEF: AthCon 2012
  • Debugging Ruby 1.9.3p125
  • BeEF on OpenBSD
  • Meet BeEF at DeepSec 2011
  • My BeEF talk at CONFidence 2011
  • JBoss JMX Deploy Exploit
  • Enumerate potential DOM-based XSS vulnerable code
  • I will speak at Confidence 2011
  • DotCloud Beta Multiple Vulnerabilities
  • OpenCMS <= 7.5.3 multiple vulnerabilities
more

Who's online

There are currently 0 users and 1 guest online.

Powered by Drupal, an open source content management system
  • about
  • security advisories
  • contact
  • publications
  • my books