Tuesday, April 03, 2007

Bypassing arbitrary URL redirection/relative URL checks

Background: Phishing attacks sometimes attempt to gain a victim’s trust by leveraging web pages that allow arbitrary URL redirection. For example, let’s say the attacker is targeting victims who have accounts with a popular bank named WoodGrove Bank. If the bank’s web site (http://www.woodgrovebank.com/) contains a page that takes a URL as input and redirects to that URL, an attacker could make the input URL the URL of his phishing site. The phishing email might contain a URL that looks like http://www.woodgrovebank.com/redir.aspx?URL=http://www.badguy.com. The second part of this URL (badguy.com) could be obfuscated to confuse the user on where the link will bring the victim. Often victims will look at the first part of a link to determine where they end up. In this case the page finally loaded in the web browser is on badguy.com and could look like a page on woodgrovebank.com. If the user isn’t careful, he might be fooled into disclosing account information to badguy.com.

Common mitigation: When URL redirection functionality is present on a site it is commonly mitigated by one of two methods.

  1. Redirection by ID – Instead of taking a URL as input, the site has a list of URLs where redirection is allowed. Instead of passing in the full URL, an identifier is passed in to represent the redirection URL. For example: http://www.woodgrovebank.com/redir.aspx?ID=27 might redirect to http://www.microsoft.com/ie.

  2. Redirection to only relative URLs – If redirection only needs to be supported within the same domain, it is common to check the URL and redirect only if it is on the same domain (a relative URL).

Defeating the security check: The first method of mitigation is good from a security standpoint - the attacker can no longer send in the redirection URL. The second method allows the attacker to control the URL, but places some constraints on the URL. How might a developer implement a check for relative URLs? Perhaps he would verify the URL begins with slash ‘/’. Relative URLs like /accounts/login.aspx would be allowed, but URLs like http://www.badguy.com/ would be rejected. Looks good, but how might this go wrong?

What if a URL looks like //www.example.com? It passes the relative URL test (first char is a slash), but it actually redirects the browser to http://www.example.com/. This works with both server-side redirection (HTTP 30x with Location header) and client-side redirects (setting document.location, window.location.replace, etc).

Test cases to defeat relative URL checks like this include the following:

  • //www.example.com
  • And of course encoded variations of the cases above.

Works with both Internet Explorer and FireFox.

1 Comments:

Anonymous said...

great post!

10:19 PM  

Post a Comment

<< Home