Skip to main content
added 1608 characters in body
Source Link
SilverlightFox
  • 34.6k
  • 6
  • 76
  • 195

If you need plain HTTP support

The reason you need HSTS is because the Same Origin Policy for cookies is more lax than those of the DOM and during AJAX requests:

cookies have scoping mechanisms that are broader and essentially incompatible with same-origin policy rules (e.g., as noted, no ability to restrict cookies to a specific host or protocol) - sometimes undoing some content security compartmentalization mechanisms that would otherwise be possible under DOM rules.

Therefore only way to protect your cookie containing JS code securely is to have plain HTTP support only on a completely different domain. e.g. https://example.org with HTTPS and HSTS for your secure content and the cookie, and http://example.com for your non-secure content.

An alternative to cookies

If you cannot do the above, the why not use HTML5 Session Storage instead of cookies, and only set or read the value over HTTPS? This method will allow you to store the JavaScript URL in the browser and run it as needed, without the possibility of a MITM intercepting and modifying the value over plain HTTP:

separation means that a value saved to LocalStorage on http://htmlui.com cannot be accessed by pages served from https://htmlui.com (and vice versa). [*]

If you need plain HTTP support

The reason you need HSTS is because the Same Origin Policy for cookies is more lax than those of the DOM and during AJAX requests:

cookies have scoping mechanisms that are broader and essentially incompatible with same-origin policy rules (e.g., as noted, no ability to restrict cookies to a specific host or protocol) - sometimes undoing some content security compartmentalization mechanisms that would otherwise be possible under DOM rules.

Therefore only way to protect your cookie containing JS code securely is to have plain HTTP support only on a completely different domain. e.g. https://example.org with HTTPS and HSTS for your secure content and the cookie, and http://example.com for your non-secure content.

An alternative to cookies

If you cannot do the above, the why not use HTML5 Session Storage instead of cookies, and only set or read the value over HTTPS? This method will allow you to store the JavaScript URL in the browser and run it as needed, without the possibility of a MITM intercepting and modifying the value over plain HTTP:

separation means that a value saved to LocalStorage on http://htmlui.com cannot be accessed by pages served from https://htmlui.com (and vice versa). [*]

Source Link
SilverlightFox
  • 34.6k
  • 6
  • 76
  • 195

Yes, your understanding is correct.

Short answer - set a HSTS Policy (HTTP Strict Transport Security). Once this is set per browser instance, any plain HTTP connection made by the browser will automatically be upgraded to HTTPS.

Note that this only takes effect after the first visit, when the HSTS HTTP header is received over HTTPS. To guard against any attacks setting the cookie before their first visit from a browser, you can apply to have your domain listed in the HSTS Preload. This list is included in builds by major browser vendors, and doesn't require a first visit to a domain to enable HSTS for any preloaded domains.

Using HSTS Preload means that every subdomain on your site will need to use HTTPS - this is good practise anyway, because as you noted the Same Origin Policy for cookies is not very strict when it comes to domains.

The above approach will prevent a Man-In-The-Middle from injecting cookies into your site by intercepting any plain HTTP request and redirecting it to your domain, and will prevent subdomain attacks.

The flow with HSTS

Without preload

First HTTP visit --> Server redirects to HTTPS --> HSTS Set --> Cookie containing JavaScript set Next HTTP Visit | browser upgrades to HTTPS --> Safe JavaScript in cookie runs 

With HSTS preload

First HTTP visit | browser upgrades to HTTPS --> ... 

Any attacker redirecting the user by a MITM attack

Without HSTS

User requests a plain HTTP site --> HTTP 3xx redirect to your site --> Evil cookie set over plain HTTP User requests your site over HTTP --> Server redirects to HTTPS --> Malicious JavaScript is ran 

With HSTS

User requests a plain HTTP site --> HTTP 3xx redirect to your site | browser upgrades connection to HTTPS --> Attack thwarted as attacker cannot MITM the HTTPS connection 

Even with Secure cookies, the server cannot query the fact that the secure flag has been set - all the server gets is the name/value pair. Therefore, there is no way to know that the cookie has been poisoned. HSTS is an effective solution because this cuts off the insecure, plain HTTP channel.

Note that the questions says that a URL is stored in the cookie not direct JavaScript - however including JS code from a third party domain has exactly the same effect - the code runs in the origin of the requesting domain