30

I have been reading about cross-subdomain cookie attacks here.

A quick overview of how it works (from Wikipedia):

  1. A web site www.example.com hands out subdomains to untrusted third parties
  2. One such party, Mallory, who now controls evil.example.com, lures Alice to her site
  3. A visit to evil.example.com sets a session cookie with the domain .example.com on Alice's browser
  4. When Alice visits www.example.com, this cookie will be sent with the request, as the specs for cookies states, and Alice will have the session specified by Mallory's cookie.
  5. If Alice now logs on, Mallory can use her account.

We are building a web app where customers will have their own subdomains: subdomain.ourapp.com.

Each customer will be able to upload template files which can contain javascript (for client side interaction).

Since javascript can be used to read/write cookies, how can we prevent the session fixation attack above? Note that we are only storing the session id in the cookie.

Sites like squarespace.com also allows users to inject their own javascript into their on pages on their own subdomain. Since it would be next to impossible to try and filter out javascript statements that set/read cookies in uploaded template files, how can we mitigate this attack vector?

1

5 Answers 5

11

The specific scenario can be prevented easily: Create a new sessionid on login.

Please note that the issues exists across domains, if the sessionid is an url-parameter.

Generating a new sesionid, however, not be sufficient to prevent other kinds of attack: Once Alice is logged in and visits Mallory's subdomain, will the cookie be transmitted?

It is common practice to use a completely different domain for all trusted activity. For example Google uses google.com for trusted activities and *.googleusercontent.com for untrusted sites.

3
  • 4
    +1 for "use a completely different domain for all trusted activity." It's the only way, and this problem the question is presenting is just another nail in the coffin of shared-domain hosting IMO.
    – TildalWave
    Apr 6, 2013 at 17:13
  • 1
    I am currently forcing session ids to be stored in cookies. All session data is stored on the server and we are regenerating the id when the user logs on and logs off. The idea of something like *.googleusercontent.com is interesting. But in this case, wouldn't a.googleusercontent.com still be able to attack b.googleusercontent.com?
    – F21
    Apr 6, 2013 at 23:49
  • While this may prevent the attacker from logging in as the victim, it does not prevent the opposite (login CSRF attacks): en.wikipedia.org/wiki/…
    – Gili
    Jun 5, 2014 at 19:24
10

The safest answer is to use entirely different domains.

If you use subdomains of the same domain, start by learning about the details of the possible attacks. There's a lot already written about this, on this site. See, e.g.,

If you use subdomains of the same domain, here are some steps you can take to protect yourself: store all state on the server side (do not use cookies to store state on the client; instead, the only cookie you use should be a session ID); create a new session ID on login and logout; make sure the cookie is scoped to the subdomain (e.g., its scope should be foo.ourapp.com, not .ourapp.com); check at the server side to make sure you don't receive multiple cookies with the name; make sure to protect yourself against session fixation; if you use CORS, be very careful with your cross-domain policy to make sure you don't allow cross-subdomain requests.

9

Public Suffix has a list of domains that all vendors (Chrome/Firefox/IE/Safari/Opera) use to avoid this problem of stealing cookies from other subdomains (along side other features). The list is updated daily and is maintained on Github.

I got this information from Heroku's blog.

I have verified that Google's googleusercontent.com domain is included in the list along with herokuapp.com , herokussl.com domains.

4
  • 2
    Amazing project, I hope my private dynamic DNS will be accepted. It's quite sad that there's no standard for cookie permissions on the web server level (e.g. domain.tld could answer a cookie request, similar to CORS, to determine if the origin is allowed). Oct 2, 2016 at 11:38
  • ouch. i just wasted literally hours trying to figure out why i couldn't set a cookie on one of my dyndns sites in the parent domain so i could access it from another (complex multi-homed solution which requires this), and now i find out that the browser is deliberately blocking me as a security measure due to some public black-hole list???
    – Michael
    Jul 22, 2018 at 7:45
  • @Dodekeract What do you mean by "my private dynamic DNS will be accepted", is there some place you can submit your sub-domains to bypass this block?
    – Michael
    Jul 22, 2018 at 7:49
  • 1
    @michael I’m not talking about any particular subdomain. I’m operating a small dynamic DNS provider. Jul 23, 2018 at 10:53
0

I just had an idea. We can borrow an idea from the Encrypted Token Pattern: encrypt the cookie value!

If the cookie is only accessed by the server, you can use cheap symmetric encryption. Otherwise, use the more expensive public-key encryption.

This will allow you to detect when malicious subdomains delete your cookie and/or detect their attempts to write fake cookies.

2
  • 1
    This wouldn't really help if we store only the session id in the cookie and store session data on the server.
    – F21
    Jun 10, 2014 at 23:11
  • 1
    @F21: You're right. You can play all kind of tricks (such as binding each session ID to an IP address) but ultimately security.stackexchange.com/a/33854/5002 is a safer solution. That being said, it is still vulnerable to login CSRF attacks.
    – Gili
    Jun 11, 2014 at 20:02
0

I managed to solve this issue by storing exact subdomain in Session data on Server. And sending exact subdomain in cookie domain setting.

If user visit dom1.website.com first time I will store it in Session, and check in all future request that it match else reset session on server.

So if user using managed to trick browser and managed to send same cookie for dom2.website.com code will check the domain name value stored in Session will not match the domain it submitted against. so it will reset session on server.

Only side effect is that session on dom1.website.com will be cleared as well.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .