Thursday, September 13, 2012

Remote JavaScript Inclusion

Presentation by Steven Van Acker, DistriNet KULeuven at OWASP chapter meeting

The basic conclusion of Steven is that browsers don't care what they execute. If they find a script to execute they will. Browsers have a basic principle called origin separation, which basically means that site A can't mess with the javascript from site B. The origin is based on the tuple protocol, website, port. For example http,, 80.

A new problem was created when we wanted to make cross-website applications. For example if Facebook wants to integrate the functionality of Google Maps. They have 3 options. The first is to build their own, the second is to make a browser with a javascript which doesn't implement the origin separation, or the last one is to use the API of and execute it on There is thus code executed in context.

This is a potential problem. The website of qTip plugin for the jQuery framework had a problem in the beginning of the year 2012. The malicious person left on the website a manipulated version of the library. The problem was of course that people executed the malicious script in the context of their website.

For his research Steven used a crawler that downloads websites together with the javascripts on the remote sites they point to and executed the javascripts for dynamic inclusions. The crawler is based on HTMLUnit. The list of websites to crawl was the Alexa top 10.000 and in total the crawler downloaded from 3.300.000 sites. A funny anecdote is that one website did 295 includes.

The conclusions of his research was that he found 5 new vectors of attack:

  • Cross-User Scripting: src= http://localhost/script.js. This could be used in an attack be dropping the javascript upfront on the victim's system.
  • Cross-Network Scripting: src= http://local_network_ip/script.js. This could be used in the same way as the Cross-User Scripting but then the javascript is dropped on a webserver on the network.
  • Stale IP attack: When the javascript is pointing to an IP address instead of a domain name, one only has to obtain the IP, fire up a web server with a malicious script with the correct name. Steven saw even IP addresses that were pointing to DHCP pools.
  • Stale domain name attack: When the javascript is pointing to a domain name which is not registered any more, one only has to obtain the domain name, fire up a web server with a malicious script with the correct name.
  • Typo squatting attack: When the programmer makes a type, one registers that 'wrong' domain, fire up a web server with a malicious script with the correct name.

As mitigation strategies Steven points out that you can't rely on the end user and thus it is up to the programmer and maintainer to do this. A solution could be using a fined-grained javascript sandbox to detect malicious activity, but this isn't a mature thing right now so we need a better thing. Another solution he came up with is to actually download the remote scripts and host them yourself.

To check if this would be a feasible solution Steven downloaded the top 1000 libraries he found and checked in 3 consecutive downloads if they changed. This way he could filter out the dynamic generated libraries. He ended up with a pool of 803 scripts that weren't dynamic. Over a period of a week 89,79% was never modified and 96,76% was only modified once. So his conclusion is that hosting your own copy is actually an actual possibility.

This doesn't exclude you can't have a malicious javascript but you still do your due diligence and check the script you are hosting and be aware of the fact that functionality may break but that is part of using somebody's API.