Monday, 2 November 2015

Attacking HTTP Strict Transport Security

Have a look to other posts of this serie:

[6] Attacking the Public Key Infrastructure
[7] Other Attacks
[8] Helper tools

Disclaimer: All this information has been obtained from empirical tests and in a specific period of time, so they could have changed.

In the last few posts we have reviewed how time synchronization works in different operating systems and how we could change the clock using Delorean in each of them. However, we haven't seen any practical attack. What can we do by tampering a computer's clock?

I started this research because I was doing a MitM demo, using SSLStrip, and it didn't work when I tried to visit GMail and other well-known websites. That was weird, because I had done the same demo many times in the past. Debugging the problem I discovered an HTTP header called "Strict-Transport-Security", something that had never seen before.

HTTP Strict Transport Security (aka HSTS) is a security protection that was released in 2012 and, despite is not widely used in the Internet yet, most well-known providers use it at this moment. The server part is really simple, a webserver just needs to set up the "Strict-Transport-Security" header setting the desired policy using the "max-age" and "includeSubdomains" parameters. In the example above, the web server sets a policy in the browser saying "ey! it doesn't matter what happen, please connect to me always using HTTPS for the following 3153600 seconds".

The hardest part in the HSTS feature is in the browser part. A browser needs to read this header and do all the necessary actions to ensure that it follows the policy. Most browsers support HSTS despite IE didn't support it until June 9th 2015. While I was delivering my talk in DEF CON (August 2015), an attendant from the first row correct me when I said "IE doesn't support HSTS". He was right about that, because I'm not an IE user and I tested it for the last time a few months before the talk. I asked him if this was something recent but he told me that "six months ago" (around February) which isn't exactly what I have found documentd. Anyway, It supports HSTS now.

In addition, Google and Mozilla created a Preloaded HSTS list for their browsers (later the idea was used in other browsers). A preloaded list is a list of well-known providers (google, twitter, facebook, paypal, etc) where HSTS is "enforced by default". The goal of this preloaded list is to avoid the security gap when a user have just installed his browser or cleaned his cache, or when he visits a website for the first time, before any HSTS policy has ben set.

Despite information from Google or Mozilla seem to talk about the HSTS preloaded list as a static list, the real truth is that preloaded entries are treated exactly the same than dynamic entries. When a browser is installed or its cache is cleaned, all entries in this list are added as dynamic entries using a default value (10 weeks) and they're updated in the same way than dynamic entries are so, in real life, it doesn't make a difference for a Delorean. 

The only browser that I have found in my research which works in a different way is Apple Safari. It stores a .plist a preloaded list and it forces always HSTS in those hosts. It doesn't matter the local clock.

Since we know that HSTS policy will avoid us from intercepting the first HTTP connection and, as a consequence, from using SSLStrip (or intercepting the communication in any other way), in the amount of seconds specified in the "max-age" parameter, our attack against HSTS is based on updating the local clock in order to make HSTS cache to expire. When there isn't any entry in the HSTS cache, a browser will work as usual, so when typing hostnames such as "" it will connect using HTTP before being redirected to HTTPS.

My talk in BlackHat Europe last year was based in this attack, and it was published several months ago, so you can have a look if my accent doesn't hurt you (as a comment in youtube said) ;)

No comments :