Update: Nope, my solution won’t work. As Christian Matthies points out in the comments, it is possible to spoof the HTTP Host header as well (his link in the comment is broken because of an extra comma, but this one works). As a kludge, browsers could be modified to prevent Host header spoofing, but (a) it would take a long time to deploy to the world at large, and (b) it would be only a bandaid for a much bigger problem.
Summary: While there’s no way to protect browsers against the DNS rebinding attack, you can protect web sites and web services by forcing them to check the HTTP
Host
header with every request. This is easy to do for RESTful services going through a regular web server like Apache — you get it by default with virtual hosts — but might be trickier for WS-* services.
If you or your company is using HTTP-based web services (either WS-* or REST), you might be in trouble — a new exploit allows a web site from outside your firewall to use a web browser as a proxy to read any web site or service inside your firewall.
Artur Bergman at O’Reilly has a posting on the DNS rebinding (aka anti-DNS-pinning) attack that works against all major browsers, including all versions of Firefox and MSIE. There’s no obvious general fix for this, though there’s a Firefox extension that helps a tiny bit.
The attack
In a DNS-rebinding attack, the attacker is able to force your browser to read data from any IP address that your browser has access to, even if you’re behind a router/firewall, by changing the IP address associated with a domain name you’ve connected to. That means that given an IP address, an outside attacker can read your local website (at 127.0.0.1), anything behind your corporate firewall (such as an Intranet accounting page or a web service), or — I think (haven’t tested yet) — a website that you’re logged into using a cookie (HTTP authentication will force a popup, since the browser will see a different domain name, even if you’re logged into the site in another tab/window). If you run a local web server on your computer (say, at 127.0.0.1), you can go to http://www.jumperz.net/index.php?i=2&a=1&b=7, type in the local address, and see jumperz.net use the exploit display the source of your home page.
The defence
There’s no way to protect the browser yet, but you can protect your HTTP-based sites and services from this attack very easily — in fact, many sites on the web are already unknowingly protected, though I don’t know if most enterprise web services are.
The trick is in the HTTP Host
header. While the DNS rebinding attack can associate a new IP address with a hostname, it cannot change the hostname itself, so the browser will still send the original hostname to the new host. Nearly all shared-hosting servers — and many servers at dedicated hosts as well — will check the Host
header to decide what pages to serve out. As long as the site does something harmless when it gets an unrecognized hostname (such as returning a “501 Not implemented” HTTP status code), the site will be safe the attack. In Apache, for example, you use the ServerName directive for each virtual host, and just make sure that there’s a default virtual host that returns an error or at least does nothing harmful.
For Web Services, the same thing applies. It’s often tempting to use IP addresses instead of hostnames for web services (including RESTful services), especially during development, but doing so opens you right up to a DNS-rebinding attack, which could be very harmful if you’re using real data for development and testing. To protect your HTTP-based services from this attack, you need to make sure that every web service is accessed via a hostname rather than a raw IP address, and that every service checks its hostname. For RESTful services, this is trivially easy (since you’re probably going through Apache or something similar anyway, just as with a web site); for WS-* services, I don’t know the implementations well enough to be sure, but it should be possible to force them to check the Host
header somehow.
Even if you’re not building web services, managing an enterprise intranet, or running a public web site, don’t forget to protect the web server on your local computer, if you have one.
Pingback: » Protecting web sites and services from DNS rebinding attacks
David, it’s not immediately apparent to me whether this exploit will relay services that are not hosted on port 80. I don’t see why is shouldn’t, but the jumperz.net page you link to doesn’t work with non-80 ports.
Pingback: University Update - Firefox - Protecting web sites and services from DNS rebinding attacks
stand: I think that the port-80 limit is just a feature of the jumperz.net demo, though you would probably have to stay on the same port as the original web page. I’ll have to look at the exploit in more detail.
Well, keep in mind that the host header can be spoofed with Anti Anti Anti DNS Pinning also. Check out http://christ1an.blogspot.com/2007/07/dns-pinning-explained.html, an article I wrote on this matter a few weeks ago.
This works because jumperz.com’s bind is sending back incorrect DNS responses, yes?
This component lets you protect Java web applications from
DNS rebinding: http://www.servletsuite.com/servlets/hostflt.htm
Hmm.. I am getting the following error.
Please wait for 15 seconds.
f1()
ERROR: Access is denied.
ERROR: http://1188829961575.jumperz.net/exploits/dnsp3.jsp?address=127.0.0.1
ERROR: 50
What does it mean ?