- From: Maciej Stachowiak <mjs@apple.com>
- Date: Wed, 04 Nov 2009 21:36:47 -0800
- To: Tyler Close <tyler.close@gmail.com>
- Cc: "Mark S. Miller" <erights@google.com>, Anne van Kesteren <annevk@opera.com>, "Henry S. Thompson" <ht@inf.ed.ac.uk>, Jonas Sicking <jonas@sicking.cc>, Arthur Barstow <Art.Barstow@nokia.com>, public-webapps <public-webapps@w3.org>
On Nov 3, 2009, at 5:33 PM, Tyler Close wrote:
> I was just catching up on email and thought it might be useful to
> respond to this one even though it's a couple weeks old now, since in
> general the group seems to want more examples.
Thanks for the reply.
>
> On Mon, Oct 12, 2009 at 7:19 AM, Maciej Stachowiak <mjs@apple.com>
> wrote:
>> As a side note, I should add that Tyler's scenario would be much
>> simpler
>> overall if printer.example.net used a grant of read access to the
>> photo it
>> wants to print on storage.example.org, instead of granting write
>> access to a
>> new location.
>
> In this scenario, photo.example.com has the opportunity to take the
> role of attacker in a CSRF-like attack. In the legitimate case,
> photo.example.com is expected to send a URL to printer.example.net
> which identifies the photo to be printed, such as
> <http://storage.example.org/photo123>. In the attack case,
> photo.example.com could send the URL that identifies the
> printer.example.net client list, such as
> <http://storage.example.org/clients123>. Consequently,
> photo.example.com receives a print out of the printer.example.net
> client list, instead of a photo printout.
What's the attack here? Is it information disclosure or vandalism? If
the user should not have access to the printer.exmple.com client list,
then printer.example.com should not be able to access that resource
with the user's cookie. So I don't think there is a risk of
information disclosure. There is the possibility of vandalism - that
the photo site wastes the user's money by making them print something
other than the photo they wanted. But it could do this simply by
providing the URL to a resource that it does have access to, but which
contains something undesirable (goatse for example). So I think there
isn't a real vulnerability here.
That being said, my understanding of this threat was greatly improved
by the discussion at TPAC. I now think the best way to address multi-
site collaboration is by applying the DBAD discipline. Here's how I
would do it in this case:
The storage service is designed to allow collaborative access by
multiple sites, therefore it needs to let them distinguish their own
requests from third-party requests. One way to do so is to partition
resources such that each is owned by exactly one storage domain. The
only way to share information cross-domain is to copy. Resource names
include the domain that owns them. Then it offers the following
command set (angle brackets are used to delimit metasyntactic
variables):
(This may be more complicated than needed, for the sake of clarity):
Read <from>
If the <from> resource is owned by the domain specified by Origin,
return the data.
Write <to>\n
<filedata>
If the <from> resource is owned by the domain specified by Origin,
store <filedata> at the resource.
SameDomainCopy <from> <to>
<from> and <to> must be in the same domain and must match Origin.
GetReadToken <resource>
If the Origin header matches <resource>, return a one-time read
token which can be used to copy a resource cross-domain
GetWriteToken <resource>
If the Origin header matches <resource>, return a one-time read
token which can be used to copy a resource cross-domain
CrossDomainCopy <from-domain> <from-resource> <read-token> <to-domain>
<to-resource> <write-token>
<read-token> must be a valid read token for <from-resource>, and
<from-resource> must be owned by <from-domain>. <write-token> must be
a valid write token for <to-resource>, and <to-resource> must be owned
by <to-domain>. Origin must match at least one of <from-domain> or <to-
domain>.
This allows two sites to agree to copy a resource from one to the
other on storage.exmple.org without introducing a confused deputy
hazard.
In the original scenario, photo.example.com would get a resource name
and a write token from printer.example.net, would obtain its own read
token for the resource to copy using GetReadToken, and then issue a
copy request with both domains and both tokens using CrossDomainCopy.
It's impossible for printer.example,net to make photo.example.com
accidentally overwrite its own resources in this case, because the
request on behalf of a third party is distinct from any request it
would make on its own behalf. You could argue that neither Origin nor
Cookie in the cross-domain network resources are necessary to make
this work, but I think in this case they can make the system easier to
build and more robust.
>
>> Or it can just ask photo.example.com to read the photo from
>> storage.example.org and send the actual data. Either of these much
>> less
>> abusable than writing, and would be a safer approach, whether or
>> not the
>> overall design depends on secret tokens. The grant of read access
>> can be
>> one-time or time-limited if necessary. Thus, I think the scenario is
>> somewhat contrived. Likely cross-site interactions would not
>> involve such a
>> complex process to transfer data. The root of the vulnerability in
>> Tyler's
>> scenario is writing in a shared namespace to transfer data, instead
>> of
>> simply granting read access to the existing copy, or transferring
>> the actual
>> data bits.
>
> The semantics of the request, read versus write, are not relevant to
> the attack. As Maciej explained in the TPAC meeting today, the actual
> problem occurs when a request is composed using data received from 2
> or more sites. As an historical note, it's interesting to observe the
> initial misstep here and so conjecture that web developers may also
> misunderstand the dangers and so use CORS-with-Origin in an insecure
> way.
>
> A request composed from data received from 2 or more sites should be a
> common pattern in any *cross-origin* application. It's the nature of
> the problem space. There's no need for examples to be complicated to
> demonstrate the problem. If people find Maciej's example simpler, it
> demonstrates the vulnerability just as well.
I don't really agree that composing a request from data received from
2 or more sites is likely to be common. Sites are doing cross-domain
collaboration now, using techniques like OAuth, JSONP, or asking the
user for their password for another site. To my knowledge, the sites
doing this are general having a pure bilateral interaction that is
well modeled by the example in my CORS background slide.
Regards,
Maciej
Received on Thursday, 5 November 2009 05:37:25 UTC