Is the Double Submit Cookies mechanism vulnerable anything other than XSS and sub-domain attacks?

All CSRF protection mechanisms are vulnerable to XSS, so that's nothing new. I'm just wondering if I can safely rely on this mechanism so long as I ensure I control all sub-domains.

NOTE: This question is a spin-off of How to protect against login CSRF?

up vote 16 down vote accepted

According to a paper published in Blackhat 2013, it isn't enough for you to implement Double-Submit Cookies in its own sub-domain (e.g. secure.host.com). You really must control all sub-domains:

2.1.1 Naïve Double Submit

Double submit cookie CSRF mitigations are common and implementations can vary a lot. The solution is tempting because it’s scalable and easy to implement. One of the most common variations is the naive:

if (cookievalue != postvalue) 
 throw CSRFCheckError 

With naïve double submit, if an attacker can write a cookie they can obviously defeat the protection. And again, writing cookies is significantly easier then reading them.

The fact that cookies can be written is difficult for many people to understand. After all, doesn’t the same origin policy specify that one domain cannot access cookies from another domain? However, there are two common scenarios where writing cookies across domains is possible:

1) While it’s true that hellokitty.marketing.example.com cannot read cookies or access the DOM from secure.example.com because of the same origin policy, hellokitty.marketing.example.com can write cookies to the parent domain (example.com), and these cookies are then be consumed by secure.example.com (secure.example.com has no good way to distinguish which site set the cookie).

Additionally, there are methods of forcing secure.example.com to always accept your cookie first. What this means is that XSS in hellokitty.marketing.example.com is able to overwrite cookies in secure.example.com.

Secondly, this approach is vulnerable to man-in-the-middle attacks:

2) If an attacker is in the middle, they can usually force a request to the same domain over HTTP. If an application is hosted at https://secure.example.com, even if the cookies are set with the secure flag, a man in the middle can force connections to http://secure.example.com and set (overwrite) any arbitrary cookies (even though the secure flag prevents the attacker from reading those cookies).

Even if the HSTS header is set on the server and the browser visiting the site supports HSTS (this would prevent a man in the middle from forcing plaintext HTTP requests) unless the HSTS header is set in a way that includes all subdomains, a man in the middle can simply force a request to a separate subdomain and overwrite cookies similar to 1. In other words, as long as http://hellokitty.marketing.example.com doesn’t force https, then an attacker can overwrite cookies on any example.com subdomain.

In summary:

  1. You must control all sub-domains.
  2. You must set the Secure flag to ensure the cookies are only sent over HTTPS.
  3. If you care about MiTM attacks, you must transition your entire website to HTTPS, set the HSTS header and ensure it includes all sub-domains. At this time, only 58% of browsers support HSTS (Internet Explorer being a notable exception). This is expected to change over the coming year.

See https://security.stackexchange.com/a/61041/5002 for a discussion of the token length and type of RNG needed to generate values.

Although all XSS attacks trump CSRF protections, these require differing effort from the attacker. A simple protection such as a token is easy for an attacker to get via an XSS attack, as they can simply read the token value from the DOM and use it in any subsequent form submits. A sensitive form that requires password or OTP reauthentication is trickier to attack, as they would need to engineer their attack to capture the user credentials or OTP in some way. However, with full control of the DOM they could mimic the login page to trick the user into thinking they've been logged out and wait for the user to enter their credentials... in this case they could probably log in directly as the victim instead of only executing a CSRF attack. This attack also causes visible disruption to the site, meaning an expert user may suspect something is wrong and refuse to log in on the attacker's form.

With sub-domains there are two risks with double-submit cookies. An attacker on a subdomain reading the cookie value. e.g. if a non host-only cookie is set at example.com level, an attacker controlling foo.example.com will be able to read the cookie value. Setting host-only cookies can counter this attack.

The other risk in an attacker writing cookies. The Same Origin Policy is more lax for cookies than it is for the rest of the DOM. This means that an attacker controlling foo.example.com can set a cookie that will be read when the victim visits either example.com or bar.example.com. They simply set a non-host only at example.com level. Even if the site under attack, say bar.example.com sets host-only cookies over HTTPS, and sets the secure flag to prevent it leaking over plain HTTP, an attacker setting a plain HTTP cookie themselves will still be able to set the cookie to be read for bar.example.com. The reason is the server cannot tell the actual domain that set it, nor can it query the secure flag itself.

Double-submit cookies is also vulnerable to a Man-In-The-Middle attacker that can intercept and change everything apart from HTTPS traffic. Even if the target site, example.com does not listen over plain http (i.e. port 443 only open for TLS), the attacker could redirect any plain http request with HTTP 3xx (e.g. to http://example.com), and then intercept that request, send back a response with the poisoned CSRF cookie set for example.com. The server will take that value, as again it has no way to determine it is not a cookie with the secure flag. This is again due to the lax same origin policy for cookies.

The solution to all this is to implement HTTP Strict Transport Security and to control all subdomains. In supported browsers, this will prevent any plain http connections being made by the browser at all during the lifetime of the HSTS record (maybe years), and will protect cookies from being set by an attacker. HSTS entries can also be submitted to browser vendors for inclusion in the build which means users do not have to visit the site at least once for the HSTS record to be set. See HSTS Preload.

  • I don't want to tie the CSRF token to a session, for two reasons: 1. I want the server to be stateless/RESTful. 2. I need to protect login forms, before the user has authenticated. In such a case, am I still safe? – Gili Jun 6 '14 at 17:39
  • @Gill: I've seen (and replied to that post) too. If you take my approach then yes. ;-) – SilverlightFox Jun 6 '14 at 18:14
  • @Gili: I see. I've updated this answer too. – SilverlightFox Jun 7 '14 at 9:19
  • @SilverlightFox, as it is detailed in Gili’s own answer, double submission is prone to man-in-the-middle notwithstanding HTTPS and the secure flag. Your last paragraph is misleading, please consider editing. – Joó Ádám Sep 18 '15 at 20:59
  • 1
    @JoóÁdám: Thanks. I've rewritten the whole answer - I think the whole lot of it was confusing now that I read it back. – SilverlightFox Sep 19 '15 at 12:54

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.