CSRF REASON_NO_REFERER with meta referrer tags

541 views
Skip to first unread message

Jon Dufresne

unread,
Feb 2, 2015, 8:35:15 PM2/2/15
to django-d...@googlegroups.com
Hi,

In the interest of security, I recently started using meta referrer
tags in my HTML [0]. To share the least amount of data as possible, I
opted for the "none" policy [1].

This new HTML5 feature breaks Django POST views. The reason: the CSRF
mechanism checks that, when serving over HTTPS, that a HTTP_REFERER
header is set in order to validate the CSRF check. Otherwise, the CSRF
check fails with REASON_NO_REFERER [2]. There is comment in the code
that reads as follows:

# Suppose user visits http://example.com/
# An active network attacker (man-in-the-middle, MITM) sends a
# POST form that targets https://example.com/detonate-bomb/ and
# submits it via JavaScript.
#
# The attacker will need to provide a CSRF cookie and token, but
# that's no problem for a MITM and the session-independent
# nonce we're using. So the MITM can circumvent the CSRF
# protection. This is true for any HTTP connection, but anyone
# using HTTPS expects better! For this reason, for
# https://example.com/ we need additional protection that treats
# http://example.com/ as completely untrusted. Under HTTPS,
# Barth et al. found that the Referer header is missing for
# same-domain requests in only about 0.2% of cases or less, so
# we can use strict Referer checking.

As of right now Chrome is the only browser (that I've tested) that
actually implements the meta referrer tag, but Firefox's next release
will as well. This combination prevented successful login for users.
Unfortunately I didn't detect this problem early in development as I
develop using HTTP, but serve production using HTTPS.

I'm not convinced that this check is really protecting the user from
an attack. Is there additional documentation, beyond this comment, on
why this is more secure? Is there evidence of other web frameworks
using this same technique? I would like to understand more.

Additionally, as a web user, one may use a Firefox/Chrome extension
that purposely strips the HTTP_REFERER from all requests. Django
applications would be effectively broken for such users. In my
opinion, the HTTP_REFERER can't be considered reliable or trustworthy
for such critical operation.

The question: I'm wondering how Django developers feel about removing
this check (or altering it?) in order to help support meta referrer
tags for developers and projects that wish to use it. If there is
general agreement I'll file a ticket and create a pull request.

Cheers,
Jon


[0] https://blog.mozilla.org/security/2015/01/21/meta-referrer/
[1] http://www.w3.org/TR/referrer-policy/#referrer-policy-state-none
[2] https://github.com/django/django/blob/27dd7e727153cbf12632a2161217340123687c44/django/middleware/csrf.py#L135

Karen Tracey

unread,
Feb 2, 2015, 9:30:05 PM2/2/15
to django-d...@googlegroups.com
This has bee brought up before, see: https://code.djangoproject.com/ticket/16870

I am not aware of any change in this area that would affect the decision made in that ticket.

Raúl Cumplido

unread,
Feb 3, 2015, 3:40:29 AM2/3/15
to django-d...@googlegroups.com
Hi Jon,

I've reopened the bug so we have a new discussion. I think the things have changed slightly in the last two years.

Thanks,
Raul

On Tue, Feb 3, 2015 at 2:29 AM, Karen Tracey <kmtr...@gmail.com> wrote:
This has bee brought up before, see: https://code.djangoproject.com/ticket/16870

I am not aware of any change in this area that would affect the decision made in that ticket.

--
You received this message because you are subscribed to the Google Groups "Django developers (Contributions to Django itself)" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-develop...@googlegroups.com.
To post to this group, send email to django-d...@googlegroups.com.
Visit this group at http://groups.google.com/group/django-developers.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-developers/CACS9rafr6f01-9c7vBNprnz1CTJGgOUyZvfSbOw_da0b_4i4%2BQ%40mail.gmail.com.

For more options, visit https://groups.google.com/d/optout.

James Bennett

unread,
Feb 3, 2015, 3:56:30 AM2/3/15
to django-d...@googlegroups.com
Please keep discussion going in this mailing-list thread, and keep in mind Django's policies regarding re-opening a "wontfix" ticket (which are essentially: don't do it).

Raúl Cumplido

unread,
Feb 3, 2015, 4:06:41 AM2/3/15
to django-d...@googlegroups.com
facepalm... Just read that on the contributing guidelines, didn't know that won't fix bugs where never reopened. So I closed it as won't fix. If the conversation keeps going I suppose a new bug will be opened.

On Tue, Feb 3, 2015 at 8:56 AM, James Bennett <ubern...@gmail.com> wrote:
Please keep discussion going in this mailing-list thread, and keep in mind Django's policies regarding re-opening a "wontfix" ticket (which are essentially: don't do it).

--
You received this message because you are subscribed to the Google Groups "Django developers (Contributions to Django itself)" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-develop...@googlegroups.com.
To post to this group, send email to django-d...@googlegroups.com.
Visit this group at http://groups.google.com/group/django-developers.

Aymeric Augustin

unread,
Feb 3, 2015, 4:31:29 AM2/3/15
to django-d...@googlegroups.com
Hi Jon,

Your request boils down to "make Django's CSRF protection of HTTPS
pages vulnerable to MITM attacks" which isn't acceptable.

Of cours, if that's a tradeoff you want to make, you can make your own
version of CsrfViewMiddleware and put it in MIDDLEWARE_CLASSES.


2015-02-03 2:35 GMT+01:00 Jon Dufresne <jon.du...@gmail.com>:
In the interest of security, I recently started using meta referrer
tags in my HTML [0]. 
 
a policy to send the referrer only for requests to the same origin.

"Origin Only" or "Origin When Cross-Origin" are quite close and alleviate
privacy concerns. The domain name can still leak privacy-sensitive data
for instance if you're building a help site for people suffering from some
illness they don't want to reveal.

However, you're framing this as a security matter, which I don't get. Can
you clarify how removing Referer headers improves security?

--
Aymeric.

Tim Chase

unread,
Feb 3, 2015, 7:09:09 AM2/3/15
to django-d...@googlegroups.com
On 2015-02-03 10:31, Aymeric Augustin wrote:
> Your request boils down to "make Django's CSRF protection of HTTPS
> pages vulnerable to MITM attacks" which isn't acceptable.

If you've got a MITM that can intercept HTTPS, is there any reason to
assume they aren't in a position to spoof DNS as well, rendering the
REFERER information immaterial?

-tkc



Aymeric Augustin

unread,
Feb 3, 2015, 9:19:08 AM2/3/15
to django-d...@googlegroups.com
We're talking about a MITM of an HTTP connection that is then used for
posting a form over an HTTPS connection. Check the comment in the first
message of this thread for details. 

--
Aymeric.

Jon Dufresne

unread,
Feb 3, 2015, 10:44:16 AM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 1:31 AM, Aymeric Augustin
<aymeric....@polytechnique.org> wrote:
> Your request boils down to "make Django's CSRF protection of HTTPS
> pages vulnerable to MITM attacks" which isn't acceptable.

Please. That is a very straw-man like way to have a discussion.

The first thing I asked for was for additional information.
Information on why this helps with CSRF security and information on
what other web technologies use this technique. IMO, the code comment
is very limited in details for such a big jump. I'm not suggesting the
comment be expanded, just wanted to read some external links or
details. Upon receiving that information it would help me understand
if the code is doing something useful and if the code should be
modified.

> http://www.w3.org/TR/referrer-policy/#referrer-policy-states doesn't have
> a policy to send the referrer only for requests to the same origin.
>
> "Origin Only" or "Origin When Cross-Origin" are quite close and alleviate
> privacy concerns. The domain name can still leak privacy-sensitive data
> for instance if you're building a help site for people suffering from some
> illness they don't want to reveal.
>
> However, you're framing this as a security matter, which I don't get. Can
> you clarify how removing Referer headers improves security?

You're right. Privacy is a probably better term for what I'm trying to
achieve. I started with the assumption to share as little information
as possible. In my private application, 99% of the URLs are secured
behind a login. However some URLs are accessed by a unique URL
containing a nonce without a login. Login is not an option for these
URLs. Sharing this URL is considered very bad and I would like to
avoid it happening unintentionally. Additionally, I don't want to leak
any information about my users. Including the fact that they were
using my application. Some of this is real privacy some of this is
common courtesy to the users.

Thanks for the link but I read through that document before choosing "none".

Jon Dufresne

unread,
Feb 3, 2015, 10:54:43 AM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 6:18 AM, Aymeric Augustin
<aymeric....@polytechnique.org> wrote:
> We're talking about a MITM of an HTTP connection that is then used for
> posting a form over an HTTPS connection. Check the comment in the first
> message of this thread for details.

Assuming this MITM already has the correct CSRF value, what is
stopping this MITM from adding a REFERER to the HTTPS request?

Jon

Aymeric Augustin

unread,
Feb 3, 2015, 2:39:57 PM2/3/15
to django-d...@googlegroups.com
Le 3 févr. 2015 à 16:54, Jon Dufresne <jon.du...@gmail.com> a écrit :
> Assuming this MITM already has the correct CSRF value, what is
> stopping this MITM from adding a REFERER to the HTTPS request?

While MITM of HTTP is trivial, MITM of HTTPS isn't possible (under Django's security model, which doesn't account for government-level attacks, etc.)

Back then, Facebook fixed Firesheep simply by enforcing HTTPS.

--
Aymeric.

Aymeric Augustin

unread,
Feb 3, 2015, 2:52:12 PM2/3/15
to django-d...@googlegroups.com
Le 3 févr. 2015 à 16:44, Jon Dufresne <jon.du...@gmail.com> a écrit :
>
> However some URLs are accessed by a unique URL
> containing a nonce without a login. Login is not an option for these
> URLs. Sharing this URL is considered very bad and I would like to
> avoid it happening unintentionally.

You can fix that problem by saving some authentication info in the user's session, most likely with a custom auth backend — see django-sesame for an example of how to do this. Then redirect immediately to an URL that doesn't contain the nonce. Of course all this must happen over HTTPS to reduce the likelihood of leaving the nonce in the logs of various caches or reverse proxies.

Another very simple option for fixing referers is to remove all external links from your website. I can't say if that's an acceptable constraint for you.

Even then, you'll still leak the hostname because of DNS requests and possibly URLs e.g. in corporate environments that put their CA in their users' browsers and reverse proxy HTTPS connections...

Depending on your goals, the answer may be Tor Browser.

--
Aymeric.

Stephen J. Butler

unread,
Feb 3, 2015, 3:20:01 PM2/3/15
to django-d...@googlegroups.com
This was my thought on the issue too. If someone is successfully doing
a MITM attack on your SSL sessions then CSRF is the least of your
worries. Maybe the thought is that many Django sites mix HTTP and
HTTPS session, and that the CSRF token would leak from the HTTP
session. But ISTM that you could just use different tokens for HTTP
and HTTPS.

Jon Dufresne

unread,
Feb 3, 2015, 4:38:48 PM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 11:39 AM, Aymeric Augustin
<aymeric.au...@polytechnique.org> wrote:
> Le 3 févr. 2015 à 16:54, Jon Dufresne <jon.du...@gmail.com> a écrit :
>> Assuming this MITM already has the correct CSRF value, what is
>> stopping this MITM from adding a REFERER to the HTTPS request?
>
> While MITM of HTTP is trivial, MITM of HTTPS isn't possible (under Django's security model, which doesn't account for government-level attacks, etc.)

Agreed. My application is 100% over HTTPS, so why do I need the CSRF
referrer check. As you state, MITM is theoretically impossible?

However I'm referring to this comment:

> We're talking about a MITM of an HTTP connection that is then used for
> posting a form over an HTTPS connection. Check the comment in the first
> message of this thread for details.

So the MITM is over HTTP, which we both agree is trivial. This MITM
then makes an HTTPS POST request. Making a HTTPS POST request on its
own is also trivial. To circumvent the CSRF protection the MITM will
need the CSRF token as well as to set the referrer header. If the MITM
is capable of obtaining the CSRF, adding a header to a request seems
like the trivial part.

Jon Dufresne

unread,
Feb 3, 2015, 4:43:11 PM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 11:52 AM, Aymeric Augustin
<aymeric.au...@polytechnique.org> wrote:
> You can fix that problem by saving some authentication info in the user's session, most likely with a custom auth backend — see django-sesame for an example of how to do this. Then redirect immediately to an URL that doesn't contain the nonce. Of course all this must happen over HTTPS to reduce the likelihood of leaving the nonce in the logs of various caches or reverse proxies.

My application is 100% over HTTPS, HTTP traffic is not allowed.

Thanks for these pointers. This may not work exactly for me, but it
certainly is something interesting to think about. I'll look into it
more.

Paul McMillan

unread,
Feb 3, 2015, 5:15:08 PM2/3/15
to django-d...@googlegroups.com
The referer check is primarily there to help make users who choose not
to use HSTS safer.

Without HSTS, a mitm can set CSRF cookies (e.g. by serving an HTTP
page emulating your domain in an iframe on a different unencrypted
page, even if you only ever serve your own page from HTTPS), and then
post (from wherever) to your secured page. By forcing the post to come
from the same domain, we've made this attack significantly less
convenient.

I agree that it's really unfortunate that we don't have a better
mechanism for this in the browsers, but this still seems to be the
best tradeoff we have right now.

-Paul
> --
> You received this message because you are subscribed to the Google Groups "Django developers (Contributions to Django itself)" group.
> To unsubscribe from this group and stop receiving emails from it, send an email to django-develop...@googlegroups.com.
> To post to this group, send email to django-d...@googlegroups.com.
> Visit this group at http://groups.google.com/group/django-developers.
> To view this discussion on the web visit https://groups.google.com/d/msgid/django-developers/CADhq2b6SXqY78qiNdB7BkAQUcBHzAFUON%3DY69mEddu6Q55SWdg%40mail.gmail.com.

Collin Anderson

unread,
Feb 3, 2015, 7:56:20 PM2/3/15
to django-d...@googlegroups.com
If we add Origin checking, could we then allow a missing referrer and token? (check referrer and token if no origin header)

Jon Dufresne

unread,
Feb 3, 2015, 9:31:49 PM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 2:12 PM, Paul McMillan <pa...@mcmillan.ws> wrote:
> The referer check is primarily there to help make users who choose not
> to use HSTS safer.
>
> Without HSTS, a mitm can set CSRF cookies (e.g. by serving an HTTP
> page emulating your domain in an iframe on a different unencrypted
> page, even if you only ever serve your own page from HTTPS), and then
> post (from wherever) to your secured page. By forcing the post to come
> from the same domain, we've made this attack significantly less
> convenient.
>
> I agree that it's really unfortunate that we don't have a better
> mechanism for this in the browsers, but this still seems to be the
> best tradeoff we have right now.

Aren't there existing security mechanisms to handle these situations?
It seems like this is sending the wrong message. Django should be
pushing developers and admins for the best solution to security and
privacy concerns.

Prevent HTTP when using HTTPS: use HSTS. (Apparently not supported by IE11 [0])

Prevent the application from being served in an attacker's iframe: use
X-Frame-Options. (Supported by all major browsers [1])

These seem like much better solutions to the scenario you present.
What does the REFERER check do that is not handled by the above?

At that point, the user's privacy concerns could be handled with the
meta referrer tag.

[0] https://developer.mozilla.org/en-US/docs/Web/Security/HTTP_strict_transport_security#Browser_compatibility
[1] https://developer.mozilla.org/en-US/docs/Web/HTTP/X-Frame-Options#Browser_compatibility

Josh Smeaton

unread,
Feb 3, 2015, 10:09:55 PM2/3/15
to django-d...@googlegroups.com
Just quickly, HSTS[0] and X-Frame-Options[1] are supported and recommended in the security documentation already. As you point out though, HSTS isn't yet a full solution, and, frankly, it scares me a little. Personally, I redirect the / path to HTTPS from HTTP and drop all other HTTP connections.

[1]https://docs.djangoproject.com/en/1.7/topics/security/#clickjacking-protection

Jon Dufresne

unread,
Feb 3, 2015, 11:11:34 PM2/3/15
to django-d...@googlegroups.com
On Tue, Feb 3, 2015 at 7:09 PM, Josh Smeaton <josh.s...@gmail.com> wrote:
> Just quickly, HSTS[0] and X-Frame-Options[1] are supported and recommended
> in the security documentation already. As you point out though, HSTS isn't
> yet a full solution, and, frankly, it scares me a little. Personally, I
> redirect the / path to HTTPS from HTTP and drop all other HTTP connections.

I think that enhances and is consistent with my existing question.

If there are better mechanisms to secure against these attacks *and*
they are already recommended by Django, what is the CSRF REFERER check
doing that isn't already solved by these mechanisms?

By using these other security mechanisms to secure against the attack,
developers can then use the meta referrer tag to help with users'
privacy.

Cheers,
Jon

Josh Smeaton

unread,
Feb 3, 2015, 11:14:51 PM2/3/15
to django-d...@googlegroups.com
For the record, I'm not disagreeing with you. I don't know enough about the topic to understand whether or not the referer check actually provides another layer of security. I think the questions you're asking are good ones.

Josh

Aymeric Augustin

unread,
Feb 4, 2015, 2:45:47 AM2/4/15
to django-d...@googlegroups.com
Le 4 févr. 2015 à 03:31, Jon Dufresne <jon.du...@gmail.com> a écrit :
>
> Prevent the application from being served in an attacker's iframe: use
> X-Frame-Options. (Supported by all major browsers [1])

That's irrelevant in the scenario we're discussing here. The iframe Paul talks about would be injected by a MITM. It's under the attacker's control, not your control.

--
Aymeric

Erik Romijn

unread,
Feb 4, 2015, 8:59:33 AM2/4/15
to django-d...@googlegroups.com, Jon Dufresne

On 03 Feb 2015, at 16:44, Jon Dufresne <jon.du...@gmail.com> wrote:
> However some URLs are accessed by a unique URL
> containing a nonce without a login. Login is not an option for these
> URLs. Sharing this URL is considered very bad and I would like to
> avoid it happening unintentionally.

I'm not following this: to prevent this case, you are actively
instructing all your users to disable referer headers in their browsers?
If not, how are you controlling what referrers your users send?

URLs without login, which contain a secret nonce, are indeed sensitive
to the nonce leaking through the referer. Dropbox ran into this a
while ago:
https://blog.dropbox.com/2014/05/web-vulnerability-affecting-shared-links/

This also affected Evernote for some time. The common resolution seems
to be not to disable referer headers, which is a client-side issue, but
to mask it by sending all external links through a specific URL first
without the nonce, which works as a simple redirector.

Far from ideal, especially when dealing with more complicated links like
when sharing office documents. But it seems to work for Dropbox and
Evernote. You'll notice for example that when viewing a PDF on Dropbox,
you're not using your in-browser PDF viewer but Dropbox' custom viewer,
which I imagine also modifies all external links.

Erik
signature.asc

Jon Dufresne

unread,
Feb 4, 2015, 10:05:15 AM2/4/15
to django-d...@googlegroups.com
Thank you for the calcification.

Is there detailed documentation on the type of attack this REFERER
check guards against? Whether Django documentation or external
documentation is fine. I would like to have a firm understanding of
the real problem and how this solves it.

Cheers,
Jon

Jon Dufresne

unread,
Feb 4, 2015, 10:13:44 AM2/4/15
to Erik Romijn, django-d...@googlegroups.com
On Wed, Feb 4, 2015 at 5:59 AM, Erik Romijn <ero...@solidlinks.nl> wrote:
>
> On 03 Feb 2015, at 16:44, Jon Dufresne <jon.du...@gmail.com> wrote:
>> However some URLs are accessed by a unique URL
>> containing a nonce without a login. Login is not an option for these
>> URLs. Sharing this URL is considered very bad and I would like to
>> avoid it happening unintentionally.
>
> I'm not following this: to prevent this case, you are actively
> instructing all your users to disable referer headers in their browsers?
> If not, how are you controlling what referrers your users send?

I am not instructing my users to do anything with their headers. This
would never be feasible for me. I mentioned some users may do so
independently.

I *want* to help control referrers using the new meta referrer tag.
This is a new feature not yet supported in all major browsers. See:

https://blog.mozilla.org/security/2015/01/21/meta-referrer/
https://w3c.github.io/webappsec/specs/referrer-policy/#referrer-policy-delivery-meta
https://developer.mozilla.org/en-US/docs/Web/HTML/Element/meta (search
referrer on page)

>
> URLs without login, which contain a secret nonce, are indeed sensitive
> to the nonce leaking through the referer. Dropbox ran into this a
> while ago:
> https://blog.dropbox.com/2014/05/web-vulnerability-affecting-shared-links/
>
> This also affected Evernote for some time. The common resolution seems
> to be not to disable referer headers, which is a client-side issue, but
> to mask it by sending all external links through a specific URL first
> without the nonce, which works as a simple redirector.
>
> Far from ideal, especially when dealing with more complicated links like
> when sharing office documents. But it seems to work for Dropbox and
> Evernote. You'll notice for example that when viewing a PDF on Dropbox,
> you're not using your in-browser PDF viewer but Dropbox' custom viewer,
> which I imagine also modifies all external links.

Thanks. Aymeric suggested a similar scheme to me earlier. I will take
it under consideration.

However, In my opinion, the user's privacy needs go beyond this one
scenario. When going cross origin, it is never the business of the
final destination where I started. Interestingly enough, the links
above have an "origin-when-crossorigin" mode (but not
"no-referrer-when-crossorigin"). However, this is not supported on
Chrome and so it defaults to "no-referrer" which, once again, breaks
Django POST over HTTPS.

Paul McMillan

unread,
Feb 4, 2015, 10:35:57 PM2/4/15
to django-d...@googlegroups.com
I'll reply to several emails at once here:

> If we add Origin checking, could we then allow a missing referrer and token?

Yes, we can support the origin header and allow a missing referer.

There's a ticket for that here:
https://code.djangoproject.com/ticket/16010
and I agree that it's long overdue. Do we have any information on
whether the referrer meta tag also influences the origin header? If it
doesn't, this whole conversation is a bit pointless...

> Aren't there existing security mechanisms to handle these situations?
> It seems like this is sending the wrong message. Django should be
> pushing developers and admins for the best solution to security and
> privacy concerns.
>
> Prevent HTTP when using HTTPS: use HSTS. (Apparently not supported by IE11 [0])

HSTS fixes the problem after the first visit, it can't fix the problem
before the user has visited the site (or ever in IE11, or for sites
which need unencrypted subdomains, or which are served at a
subdomain). We need to provide the best protection we can, so we still
need to check the referer.

As Aymeric said, the XFO header doesn't do anything to prevent a MITM
from sending whatever they want.

> However, In my opinion, the user's privacy needs go beyond this one
> scenario.

I will remind you that suppressing the referer header in question does
_absolutely nothing_ to enhance your user's privacy since it is only
relevant when the user is making a post from one page of your site to
another page of your site. Your webserver logs each of those requests,
and so where the traffic came from is immediately obvious. I agree
that chrome should support no-referrer-when-crossorigin, but since all
of this conversation is in reference to a proposed standard which is
not finalized yet, I would argue that this is an issue you can and
should bring up with the editors of the referrer-policy draft spec
(last revised 6 days ago). If they update the spec, I expect that
chrome will be updated to match it in short order.

> Is there detailed documentation on the type of attack this REFERER
> check guards against? Whether Django documentation or external
> documentation is fine. I would like to have a firm understanding of
> the real problem and how this solves it.

We don't have detailed documentation about every type of CSRF attack
that we defend against (such a document would be impossible to
maintain). However, I will try to lay this out more clearly for you
here.

setup:
user -> mitm -> server

Server is configured properly:
* HTTPS with good ciphers
* long-lived HSTS including all subdomains, served from yoursite.com
* X-Frame-Options: Deny
* Secure cookies
* permanent redirect from http to https

The user has never been to your site on this computer before (maybe
they're logging in from a library computer, or a friend's computer, or
this is their first visit to your site).

The user types yoursite.com into the address bar and hits enter.

The mitm sees the request for http://yoursite.com, and rewrites the
301 redirect response your server sends to add a csrftoken=aaa cookie.

The user continues to your website. They log in.

Some time later, the user browses to aol.com (or any other insecure
site). The mitm sees this traffic, and on-the-fly, rewrites the html
that aol.com serves to include a script which posts a form to your
server, including a form field containing the CSRF value that the
attacker now knows (because the attacker set the csrf cookie in the
first place). This post (because it is prepared by the user's browser)
includes all cookies set for your domain (including the session and
the csrf token).

The user's browser may or may not send a referer with this post, but
in either case the origin does NOT match your original server, and
Django rejects the attack. If we remove the referer check in Django,
this attack is accepted (since it has a correct matching CSRF token
and a valid user session), and your application is compromised.

For websites and browsers that don't support HSTS (or websites which
aren't at the top level domain, or which don't include all subdomains
in the HSTS), this attack works every single time the user visits your
page. For browsers which do support HSTS (and your server has it
enabled) the attack is viable any time until the first time a browser
visits your page. Django has to provide the _best_ possible CSRF
protection it can, so it is not an option to exclude protection for
the first visit, or for sites which use non-https subdomains or parent
domains, or for browsers that don't support HSTS.

Hopefully you see why this check is important. You should find out
whether the referrer metatag also influences the origin header - if it
doesn't, fixing the ticket mentioned above would make most of your
concerns go away.

Regards,
-Paul
Reply all
Reply to author
Forward
0 new messages