Intent to Implement: Subresource Integrity (SRI).

2,471 views
Skip to first unread message

Mike West

unread,
Mar 24, 2014, 3:52:48 AM3/24/14
to blink-dev, Joel Weinberger, rsl...@chromium.org, scary...@gmail.com

Contact emails

mk...@chromium.org, j...@chromium.org


Spec

http://w3c.github.io/webappsec/specs/subresourceintegrity/


Summary

Subresource Integrity defines a mechanism by which user agents may verify that a fetched resource has been delivered without unexpected manipulation. In a nutshell, metadata inlined into HTML elements allows the browser to determine whether the resource that was downloaded matches the resource the page's author expected to download.


Motivation

Websites are amalgams of resources loaded from a variety of sources, only some of which are under the control of the site's author. SRI allows an author the opportunity to lock her site down to a specific set of resources, mitigating the risk that (for instance) a compromised CDN server can execute malicious code on her site.


Compatibility Risk

The core of this spec is low-risk: there's real value in allowing authors to verify the integrity of resources they download, and if we can get the caching semantics right (from a security/privacy perspective), there might be solid performance wins.


Other aspects of the proposal (lowering the bar for mixed content warnings, for example), have generated a good deal of discussion (garment-rending, teeth-gnashing, eye-poking-outing, ...) from knowledgeable folks like Ryan and Chris, and will likely morph before implementation. CCing both here.


Implementation experience, behind a flag, will help us decide where to take the spec, and inform our decisions about what pieces we'd like to ship in the future.


Ongoing technical constraints

None.


Will this feature be supported on all five Blink platforms (Windows, Mac, Linux, Chrome OS and Android)?

Yes.


OWP launch tracking bug?

http://crbug.com/355467


Link to entry on the feature dashboard

http://www.chromestatus.com/features/6183089948590080


Requesting approval to ship?

No. The goal here is simply to gain implementation experience in order to answer some of the key questions in the spec. For example, we need to decide exactly which set of bits we verify. Should we undo content/transport encoding before verification? How should we handle downloads? What about IFramed resources?


If things go well, we'll send a separate intent to ship when the spec is closer to CR.


-mike

Vivek Galatage

unread,
Mar 24, 2014, 4:44:25 AM3/24/14
to Mike West, blink-dev, Joel Weinberger, rsl...@chromium.org, scary...@gmail.com
It might be out-of-context for the discussion, but out of curiosity, how would data compression servers like the one here [1], would behave with respect to the SRI?

If I understand correctly, these servers can transcode some of the contents (e.g. images) to optimize the bandwidth. 


To unsubscribe from this group and stop receiving emails from it, send an email to blink-dev+...@chromium.org.

Mike West

unread,
Mar 24, 2014, 4:52:37 AM3/24/14
to Vivek Galatage, blink-dev, Joel Weinberger, rsl...@chromium.org, scarybeasts, Mark Nottingham
On Mon, Mar 24, 2014 at 9:44 AM, Vivek Galatage <viv...@chromium.org> wrote:
It might be out-of-context for the discussion, but out of curiosity, how would data compression servers like the one here [1], would behave with respect to the SRI?

If I understand correctly, these servers can transcode some of the contents (e.g. images) to optimize the bandwidth. 

We're not able to distinguish "good" manipulation of a resource (compression), from "bad" manipulation (malicious replacement). Basically, an author's choice to use SRI means that she considers the integrity of the resource to be more important than its performance. We send `Cache-Control: no-transform` in order to express this preference.

There will certainly be folks behind proxies that intentionally MitM their connections (corporate proxies are the best-case of this). The 'noncanonical-src' section of the spec <http://w3c.github.io/webappsec/specs/subresourceintegrity/#the-noncanonical-src-attribute-todo-1> allows for a fallback for the cases in which a resource is manipulated, if the author would like to offer such an alternative.

Relatedly, we've gotten a tiny bit of feedback from Akamai (second-hand, through mnot@) with a suggestion that we add a syntax that would make it easier for their services (and services like PageSpeed) to manipulate the expected hashes for resources served to pages which opt-in to their services. I expect we'll need something like that in the future, but it's not in the current draft.

-mike

Ryan Sleevi

unread,
Mar 24, 2014, 3:43:47 PM3/24/14
to Mike West, Vivek Galatage, blink-dev, Joel Weinberger, Ryan Sleevi, scarybeasts, Mark Nottingham, sligh...@chromium.org, Jeffrey Yasskin
First, let me acknowledge that I owe it to the WebApps WG to really carry the discussion in full there. I don't want to fork the discussion, even as I've been intentionally been avoiding getting too embroiled into the ongoing discussions.

I do not think Chrome/Chromium/Blink should implement this.

[More below]

On Mon, Mar 24, 2014 at 1:52 AM, Mike West <mk...@google.com> wrote:
On Mon, Mar 24, 2014 at 9:44 AM, Vivek Galatage <viv...@chromium.org> wrote:
It might be out-of-context for the discussion, but out of curiosity, how would data compression servers like the one here [1], would behave with respect to the SRI?

If I understand correctly, these servers can transcode some of the contents (e.g. images) to optimize the bandwidth. 

We're not able to distinguish "good" manipulation of a resource (compression), from "bad" manipulation (malicious replacement). Basically, an author's choice to use SRI means that she considers the integrity of the resource to be more important than its performance. We send `Cache-Control: no-transform` in order to express this preference.

There will certainly be folks behind proxies that intentionally MitM their connections (corporate proxies are the best-case of this). The 'noncanonical-src' section of the spec <http://w3c.github.io/webappsec/specs/subresourceintegrity/#the-noncanonical-src-attribute-todo-1> allows for a fallback for the cases in which a resource is manipulated, if the author would like to offer such an alternative.

Seems like this sets the Priority of Constituencies wrong, if Authors can override/prevent Users choices? In such a world, why wouldn't Users configure UAs to actively disable SRI?
 

Relatedly, we've gotten a tiny bit of feedback from Akamai (second-hand, through mnot@) with a suggestion that we add a syntax that would make it easier for their services (and services like PageSpeed) to manipulate the expected hashes for resources served to pages which opt-in to their services. I expect we'll need something like that in the future, but it's not in the current draft.

-mike

I think the proposal is actively performance-hostile, and as such, it's extremely unlikely to be adopted by those who would most benefit.

- It's hostile to the user's performance choices, by actively preventing performance-enhancing transcoding proxy the user has opted in to.
- It's hostile to operators' performance choices, because it creates an innate hostility for modules like mod_pagespeed (requiring them to rewrite/strip the headers)
- It's hostile to user agents' performance choices, because it actively prohibits processing content until integrity has been verified.

For the sake of discussion of this spec, I think the discussions of benefits MUST EXCLUDE the mixed content discussion (listed under Section "1.2.3 Fallback" of the specification). That is, the merits of Sub-Resource Integrity must be on their own, without mixed content.

That said, the two concerns are:
- It provides a false sense of security if delivered over HTTP [eg: can UAs ignore such directives for being the silliness they are, if the resources was over HTTP?]
- It can actively harm/degrade security if mixed content is permitted

Given the above performance concerns, it seems highly unlikely that those most at risk / most likely to benefit from SRI (eg: large sites with large performance concerns)  will opt-in.

As a thought exercise, it seems that Sub-Resource Integrity *could* be polyfilled using Service Workers ( https://github.com/slightlyoff/ServiceWorker/ ), which would allow interested sites to gain better implementation and deployment experience, the same security benefits, and without the risk of the Mixed Content.

From reading the discussions, it seems that the most benefit/excitement from Sub-Resource Integrity comes from (a) those expecting UAs to permit mixed-content when SRI is used [Section 1.2.3] and (b) UAs to treat SRI as content-addressable-storage [Section 4], thus freeing caches from URIs.

Both of these 'benefits' seem extremely security-hostile, and thus unlikely to be implemented, so I don't get as excited.

Darin Fisher

unread,
Mar 24, 2014, 4:44:11 PM3/24/14
to Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Mark Nottingham, Alex Russell, Jeffrey Yasskin
How would such a polyfill work? I thought the goal here was to put restrictions on the content served by a third-party? (Service Workers don't get any extra ability to read cross-origin resources.)

-Darin

Jeffrey Yasskin

unread,
Mar 24, 2014, 4:59:38 PM3/24/14
to Darin Fisher, Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Mark Nottingham, Alex Russell, Jeffrey Yasskin
They do get to intercept the request and cache the response, though:
https://github.com/slightlyoff/ServiceWorker/blob/master/explainer.md#cross-origin-resources

Ryan Sleevi

unread,
Mar 24, 2014, 5:00:20 PM3/24/14
to Darin Fisher, Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Mark Nottingham, Alex Russell, Jeffrey Yasskin
Right, sorry for not fully fleshing out how it would look in a SW world - which I fully admit is not a fully fleshed out idea, but more a question about why could or couldn't you do it via SWs.

So, my (likely incomplete/incorrect) understanding of Service Workers was that the fetch() algorithm does allow an opaque object to be exposed to the script, allowing it access to *some* content (read: certain headers) but not 'content' content (eg: the body). That is, specifically, the OpaqueResponse / CORSResponse objects, listed in http://infrequently.org/14/ServiceWorker/spec/service_worker/#response-objects

If we allow such objects to be hashed (eg: via WebCrypto), then we're essentially exposing the same information.

You don't even need to expose the *actual* hash - for example, you could implement digest verification by using the verify() method, with s/signature/hash/ (aka: similar to how HMAC is implemented). You're still exposing to the origin whether or not the digest match(ed/s)

Jeffrey Yasskin

unread,
Mar 24, 2014, 5:00:50 PM3/24/14
to Jeffrey Yasskin, Darin Fisher, Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Mark Nottingham, Alex Russell
Whoops, that doesn't cover "put restrictions on the content served by
a third-party".

William Chan (陈智昌)

unread,
Mar 24, 2014, 5:37:10 PM3/24/14
to Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Mark Nottingham, sligh...@chromium.org, Jeffrey Yasskin
I haven't thought deeply about SRI. I find lots of your arguments fairly compelling, but would like to hear someone more versed in the counterarguments argue the case. Or maybe there's a link to the other side on the WG mailing list archive somewhere?

Some thoughts:
* Some of the performance concerns could be mitigated with a merkle tree, as agl@ has pointed out previously when we've discussed these ideas
* I think lots of the performance concerns apply to blindly using SRI everywhere. But one may want to be more selective. For example, maybe ensuring the integrity of jQuery loaded from the Google CDN. Script resources cannot be progressively processed, so IIUC the performance concern there seems less serious.
* It's true though, that providing an integrity attribute might be a performance footgun in many places.
* Doing the digest verification in ServiceWorker is an interesting idea. I don't know if the right hooks are exposed to do progressive verification with merkle trees though. It does seem true though that the SW could fetch() the entire response and then verify it, and only after verification then send it onward to the renderer. Where would the digest be conveyed if not an integrity attribute? It has to be something that will be sent onward to the ServiceWorker in the Request (http://infrequently.org/14/ServiceWorker/spec/service_worker/#request-interface).
* I don't know if I buy the argument about being hostile to the user's performance choices with regards to a mobile transcoding proxy. Using https:// is hostile to such a proxy, and I still think we want the world to move to https://.
* Are any of the content transformations that CDNs do not possible by the origin itself using mod_pagespeed or the like? If the origin can accomplish all these content transformations itself, then it seems that SRI offers an advanced ability to insulate one's self from compromise of a CDN.

Very interesting conversation. I think the SW idea is an intriguing one, although it seems to miss two things:
* Progressive verification
* Work on a cold load...a SW may not yet be installed on the first page load, which we still care about from a security perspective.


On Mon, Mar 24, 2014 at 12:43 PM, Ryan Sleevi <rsl...@chromium.org> wrote:

Joel Weinberger

unread,
Mar 24, 2014, 7:39:20 PM3/24/14
to William Chan (陈智昌), Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, scarybeasts, Mark Nottingham, sligh...@chromium.org, Jeffrey Yasskin
On Mon, Mar 24, 2014 at 2:37 PM, William Chan (陈智昌) <will...@chromium.org> wrote:
I haven't thought deeply about SRI. I find lots of your arguments fairly compelling, but would like to hear someone more versed in the counterarguments argue the case. Or maybe there's a link to the other side on the WG mailing list archive somewhere?

Some thoughts:
* Some of the performance concerns could be mitigated with a merkle tree, as agl@ has pointed out previously when we've discussed these ideas
Yes, we are considering this, although it is likely that v1 will not include a merkle tree syntax. This is definitely on our plate, however, so if you have any good ideas for syntax, please let us know :-)
* I think lots of the performance concerns apply to blindly using SRI everywhere. But one may want to be more selective. For example, maybe ensuring the integrity of jQuery loaded from the Google CDN. Script resources cannot be progressively processed, so IIUC the performance concern there seems less serious.
* It's true though, that providing an integrity attribute might be a performance footgun in many places.
It's just another tool in the bag. If a developer completely trusts a server, and performance is critical, then don't use SRI. The browser provide's many footguns, and it's up to the developer to pull the trigger.

Mark Nottingham

unread,
Mar 24, 2014, 8:12:37 PM3/24/14
to rsl...@chromium.org, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, sligh...@chromium.org, Jeffrey Yasskin
Hi Ryan,

Responding to a few of the concerns you raise...

On 25 Mar 2014, at 6:43 am, Ryan Sleevi <rsl...@chromium.org> wrote:

[...]
> I think the proposal is actively performance-hostile, and as such, it's extremely unlikely to be adopted by those who would most benefit.
>
> - It's hostile to the user's performance choices, by actively preventing performance-enhancing transcoding proxy the user has opted in to.

How often does that happen? AIUI these proxies are either (a) imposed upon the user by a network, or (b) opted into through the UA, in which case the UA has the opportunity to make sure SRI doesn't interfere.


> - It's hostile to operators' performance choices, because it creates an innate hostility for modules like mod_pagespeed (requiring them to rewrite/strip the headers)

The folks that I talk to from products like that *want* to be doing this sort of thing. Have you asked the mod_pagespeed team what they want?


> - It's hostile to user agents' performance choices, because it actively prohibits processing content until integrity has been verified.

This is indeed an issue.


> For the sake of discussion of this spec, I think the discussions of benefits MUST EXCLUDE the mixed content discussion (listed under Section "1.2.3 Fallback" of the specification). That is, the merits of Sub-Resource Integrity must be on their own, without mixed content.

Why? That seems like a very arbitrary limitation.


> That said, the two concerns are:
> - It provides a false sense of security if delivered over HTTP [eg: can UAs ignore such directives for being the silliness they are, if the resources was over HTTP?]

I'd like to see SRI change so that it's backwards-compatible for the mixed content case; e.g.,

<script src="https://cdn.google.com/jquery?whatever" sri-src="http://cdn.google.com/jquery?whatever" integrity="ni:..."></script>

That way, if the UA ignores SRI, they use the HTTPS URI, and don't have to worry about mixed content.


> - It can actively harm/degrade security if mixed content is permitted

"Can" is different than "will." Can SRI be used in a way that degrades security? Sure, but there are lots of ways you can degrade security in the Web platform.

We address these sorts of things all of the time, through education, best practices, and sensible defaults.

Withholding tools from people out of this kind of concern just means that their use cases won't be met, and they'll hack the tools until they are, perhaps in other ways that degrade security. I know that many browser folk have a justifiably low estimation of the common users' (and even administrators') understanding of security, but I don't think making a Lowest Common Denominator Web is the right answer (either in security UI or capabilities).


> Given the above performance concerns, it seems highly unlikely that those most at risk / most likely to benefit from SRI (eg: large sites with large performance concerns) will opt-in.

All of the conversations I'm having point to the opposite. Intelligently used, SRI helps get around a good deal of the pain with deploying TLS in the medium term, while we sort out the longer-term story of increasing the deployment of HTTPS.


[...]
> From reading the discussions, it seems that the most benefit/excitement from Sub-Resource Integrity comes from (a) those expecting UAs to permit mixed-content when SRI is used [Section 1.2.3] and (b) UAs to treat SRI as content-addressable-storage [Section 4], thus freeing caches from URIs.
>
> Both of these 'benefits' seem extremely security-hostile, and thus unlikely to be implemented, so I don't get as excited.

Without speaking for others - the browser folk outside of Chrome that I talk to are *much* less hostile to SRI, so I don't read the situation the same way.

Regards,

--
Mark Nottingham http://www.mnot.net/



Ryan Sleevi

unread,
Mar 24, 2014, 8:49:13 PM3/24/14
to Mark Nottingham, Ryan Sleevi, Mike West, Vivek Galatage, blink-dev, Joel Weinberger, scarybeasts, Alex Russell, Jeffrey Yasskin
On Mon, Mar 24, 2014 at 5:12 PM, Mark Nottingham <mn...@mnot.net> wrote:
Hi Ryan,

Responding to a few of the concerns you raise...

On 25 Mar 2014, at 6:43 am, Ryan Sleevi <rsl...@chromium.org> wrote:

[...]
> I think the proposal is actively performance-hostile, and as such, it's extremely unlikely to be adopted by those who would most benefit.
>
> - It's hostile to the user's performance choices, by actively preventing performance-enhancing transcoding proxy the user has opted in to.

How often does that happen? AIUI these proxies are either (a) imposed upon the user by a network, or (b) opted into through the UA, in which case the UA has the opportunity to make sure SRI doesn't interfere.

Whether or not a UA knows about it is orthogonal to whether or not the user has opted in to it.

I fully admit, I don't care much for those imposed on the user, but I equally don't like a UA trying to infer a user's will when a proxy is configured. 

Chromium eschews user options/settings in favour of "secure by default", so the first presumption is that we won't be asking the user "Is this a transcoding proxy or not" when a user has a proxy configured. Further, the means of configuring said transcoding proxy isn't always readily apparent (read: LSPs). So we can assume that IF a user has a proxy, we should disable SRI.

Since the proponents of SRI argue this is a security mechanism, that means "disabling a security mechanism" when a user is behind a proxy. That's not a good state. Or breaking the proxy by default. That's also not a good state.
 
> - It's hostile to operators' performance choices, because it creates an innate hostility for modules like mod_pagespeed (requiring them to rewrite/strip the headers)

The folks that I talk to from products like that *want* to be doing this sort of thing. Have you asked the mod_pagespeed team what they want?

Then spell it out in the use cases in the next draft, because that's not a consideration that is captured, and what is captured seems to run quite counter to that.
 
> - It's hostile to user agents' performance choices, because it actively prohibits processing content until integrity has been verified.

This is indeed an issue.


> For the sake of discussion of this spec, I think the discussions of benefits MUST EXCLUDE the mixed content discussion (listed under Section "1.2.3 Fallback" of the specification). That is, the merits of Sub-Resource Integrity must be on their own, without mixed content.

Why? That seems like a very arbitrary limitation.

Because there's such a large host of security/privacy concerns with the use case of mixed content and of caching, with much hand-waving, that it's a much saner, safer principle to say "No" outright if those are the use cases.

Given the high conflict on these two features, the question is - Are there any *other* benefits to SRI that *do not* depend on these two features. If not, we shouldn't be implementing it. If so, we should be solving those before we unleash these security/privacy concerns on users.
 


> That said, the two concerns are:
> - It provides a false sense of security if delivered over HTTP [eg: can UAs ignore such directives for being the silliness they are, if the resources was over HTTP?]

I'd like to see SRI change so that it's backwards-compatible for the mixed content case; e.g.,

<script src="https://cdn.google.com/jquery?whatever" sri-src="http://cdn.google.com/jquery?whatever" integrity="ni:..."></script>

That way, if the UA ignores SRI, they use the HTTPS URI, and don't have to worry about mixed content.

That's certainly a more preferable design.
 
> - It can actively harm/degrade security if mixed content is permitted

"Can" is different than "will."  Can SRI be used in a way that degrades security? Sure, but there are lots of ways you can degrade security in the Web platform.

We address these sorts of things all of the time, through education, best practices, and sensible defaults.

Withholding tools from people out of this kind of concern just means that their use cases won't be met, and they'll hack the tools until they are, perhaps in other ways that degrade security. I know that many browser folk have a justifiably low estimation of the common users' (and even administrators') understanding of security, but I don't think making a Lowest Common Denominator Web is the right answer (either in security UI or capabilities).

"Secure by default" is one of Chromium's design patterns, and that's unlikely to change. Still, this gets into the rathole of mixed-content, which I think for our conversation about supporting SRI, would be best deferred, unless we want to block implementing on dealing with these issues.

If we're going to talk about *implementing* SRI in the near-term, we shouldn't be supporting mixed content. If we are going to talk about supporting mixed content, we shouldn't be implementing SRI until we work through these issues.

> Given the above performance concerns, it seems highly unlikely that those most at risk / most likely to benefit from SRI (eg: large sites with large performance concerns)  will opt-in.

All of the conversations I'm having point to the opposite. Intelligently used, SRI helps get around a good deal of the pain with deploying TLS in the medium term, while we sort out the longer-term story of increasing the deployment of HTTPS.

Your comment here is working on the presumption that we'll deploy mixed content SRI support.

As I stated very early in my message, we should talk about SRI without this for the short-term implementation.

Does SRI, without mixed content or content-addressed caching, provide benefit?
 


[...]
> From reading the discussions, it seems that the most benefit/excitement from Sub-Resource Integrity comes from (a) those expecting UAs to permit mixed-content when SRI is used [Section 1.2.3] and (b) UAs to treat SRI as content-addressable-storage [Section 4], thus freeing caches from URIs.
>
> Both of these 'benefits' seem extremely security-hostile, and thus unlikely to be implemented, so I don't get as excited.

Without speaking for others - the browser folk outside of Chrome that I talk to are *much* less hostile to SRI, so I don't read the situation the same way.

Sure. "Unlikely to be implemented in Chrome" could have been a reasonable phrase.

Again, this sort of thread highlights one of the big issues I have with SRI - it feels like a "backdoor proposal", in the "backdoor pilot" sense - that is, the goal is not really for SRI to be useful in itself, but as a solution to allow Mixed Content or to introduce cross-origin caches. Both of these are deeply troubling from security/privacy concerns, and certainly have strong opposition.

The original proposal, as I read it, was NOT to implement either of these features, and thus my response was attempting to deal specifically with the *other* use cases addressed in the spec, which are and remain suspicious regarding value, and potentially polyfillable.

Without the mixed-content or mixed-cache, it seems you're left with a spec that does far more harm than even its potential for good. And I don't think that's a good thing to implement. 

Joel Weinberger

unread,
Mar 24, 2014, 8:59:20 PM3/24/14
to Ryan Sleevi, Mark Nottingham, Mike West, Vivek Galatage, blink-dev, scarybeasts, Alex Russell, Jeffrey Yasskin
Yes. Even over an HTTPS connection, SRI provides the benefit that the content on the server you are loading from is the content you expect. For an extreme example, if you're concerned that https://cdn.google.com is compromised (or is just serving up content on behalf of the NSA), you can rest assured that the script/img/etc that you are looking for hasn't been swapped out from underneath you.

Ryan Sleevi

unread,
Mar 24, 2014, 9:09:56 PM3/24/14
to Joel Weinberger, Ryan Sleevi, Mark Nottingham, Mike West, Vivek Galatage, blink-dev, scarybeasts, Alex Russell, Jeffrey Yasskin
And can this be accomplished by other means, eg: hosting the content on your own page, where you already have a warm connection, where you're hopefully using HTTP 2.0 and getting multi-plexing goodness, where you already have a DNS cache, and where you then no longer have to block resource processing on verifying the integrity? Why or why not?

Alternatively, could you potentially use Service Worker (+modifications?) to accomplish this? Why or why not?

There are, understandably, a number of people excited for SRI. However, it seems no two people are excited for the same reason. Which is, normally speaking, quite exciting, because it means you have something robust that can be applied to a lot of use cases. Except it's more scary than exciting when it's postured as a "security feature" (especially an "anti-NSA" security feature). Equally important is what is the performance impact - if this is a net-negative for performance, why would we believe sites would adopt this?

I recognize the great work that has gone on here, and the number of diverse interests, but I can't help but feel like the math is funny. It maybe improves security, but at a trade-off of performance (caching, transcoding). You can maybe gain that performance back, but at a trade-off of security (mixed-content, content-addressed caching). Do the equations balance? If we only implement part of the spec - as the spec is clear UAs can do - does the calculus still end up as a win for users? Is there a way to facilitate more exploration of the use cases - that is, supporting a robust polyfill - without necessarily committing to the feature?


Mark Nottingham

unread,
Mar 24, 2014, 9:23:05 PM3/24/14
to rsl...@chromium.org, Joel Weinberger, Mike West, Vivek Galatage, blink-dev, scarybeasts, Alex Russell, Jeffrey Yasskin

On 25 Mar 2014, at 12:09 pm, Ryan Sleevi <rsl...@chromium.org> wrote:

> Except it's more scary than exciting when it's postured as a "security feature" (especially an "anti-NSA" security feature).

Wait a minute. Who's doing that?

At best, SRI helps deploy HTTPS where it otherwise couldn't be, because third party, etc. assets aren't yet available via HTTPS. Is that what you're referring to? I haven't heard anyone call this "anti-NSA," so on the face of it that sounds like a straw man.

Cheers,

Ryan Sleevi

unread,
Mar 24, 2014, 9:28:26 PM3/24/14
to Mark Nottingham, Ryan Sleevi, Joel Weinberger, Mike West, Vivek Galatage, blink-dev, scarybeasts, Alex Russell, Jeffrey Yasskin
From one of the spec editors (jww@), in the reply immediately prior to yours:

"or an extreme example, if you're concerned that https://cdn.google.com is compromised (or is just serving up content on behalf of the NSA), you can rest assured that the script/img/etc that you are looking for hasn't been swapped out from underneath you."

And your statement about "helps deploy HTTPS where it otherwise couldn't be" is, once again, conflating a particular *optional* part of the spec with the overall goal. As called out by a different editor of the spec, and as clearly contentious within the WG, I would refer to http://w3c.github.io/webappsec/specs/subresourceintegrity/#the-noncanonical-src-attribute-todo

"This attribute (and fallback in general) only makes sense if we care about allowing cache-friendly (read “HTTP”) URLs to load in an HTTPS context without warnings. I’m not sure we do, so I’m not going to put too much thought into the details here before we discuss things a bit more. (mkwst)"

I'm happy you're engaged in discussing SRI, but I see neither of the editors, nor those proposing to implement SRI, particularly enthused to implement the version of SRI you're defending. Thus my continued attempts to focus on the part of SRI we are discussing implementing. 

Mark Nottingham

unread,
Mar 24, 2014, 9:33:13 PM3/24/14
to rsl...@chromium.org, Joel Weinberger, Mike West, Vivek Galatage, blink-dev, scarybeasts, Alex Russell, Jeffrey Yasskin

On 25 Mar 2014, at 12:28 pm, Ryan Sleevi <rsl...@chromium.org> wrote:

> From one of the spec editors (jww@), in the reply immediately prior to yours:
>
>> "or an extreme example, if you're concerned that https://cdn.google.com is compromised (or is just serving up content on behalf of the NSA), you can rest assured that the script/img/etc that you are looking for hasn't been swapped out from underneath you."

Ah, missed that - thx.

> And your statement about "helps deploy HTTPS where it otherwise couldn't be" is, once again, conflating a particular *optional* part of the spec with the overall goal. As called out by a different editor of the spec, and as clearly contentious within the WG, I would refer to http://w3c.github.io/webappsec/specs/subresourceintegrity/#the-noncanonical-src-attribute-todo
>
>> "This attribute (and fallback in general) only makes sense if we care about allowing cache-friendly (read “HTTP”) URLs to load in an HTTPS context without warnings. I’m not sure we do, so I’m not going to put too much thought into the details here before we discuss things a bit more. (mkwst)"
>
> I'm happy you're engaged in discussing SRI, but I see neither of the editors, nor those proposing to implement SRI, particularly enthused to implement the version of SRI you're defending. Thus my continued attempts to focus on the part of SRI we are discussing implementing.

Fair enough. My impression was that the use cases that SRI attempts to address in v1 is in flux, based upon discussions like this one.

Mike West

unread,
Mar 25, 2014, 7:32:30 AM3/25/14
to blink-dev, rsl...@chromium.org, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
Hooray! This is an interesting enough feature to argue about. At length. :)

First, let me try to be clear about what I intend this "intent" thread to cover:

  1. I intend to add support for an `integrity` attribute on a variety of HTML elements, which allows authors to specify integrity metadata for resources those elements fetch.

  2. I intend to add verification functionality somewhere TBD (probably in Blink, maybe in the network stack, maybe in Service Workers, maybe somewhere else entirely; active discussion with area experts was my main purpose in this thread) that uses the integrity metadata specified in #1 to block the execution or rendering of resources which fail an integrity check.

  3. I intend to add some sort of fallback functionality, similar to what's specified in the 'noncanonical-src' section; folks have convinced me that it's worth implementing even in the case where we entirely throw out the concept of relaxing mixed-content. This section of the spec is, as Ryan notes, under construction. I'll work on that this week to try to make the use case and value more clear (basically, I agree with Mark's suggestion).

  4. I would like to explore the possibilities of caching based on integrity metadata rather than URL. This would have real value in the generalized jQuery case (I think the network team did some experiments in this direction that Chris or Will might be able to detail) and given the mitigations outlined in the spec, I don't believe it's as much of a security footgun as Ryan and Chris seem to.

  5. Given that any integrity guarantee we could make depends entirely on our ability to trust the document which contains the integrity metadata, I think it's pretty reasonable to support integity checks _only_ for documents served over HTTPS. I think I'd be happy to hard-fail integrity checks if the document including metadata is served over HTTP.

     think this would address Ryan's concern #1.

  6. I, personally, am not terribly thrilled about the mixed-content portion of the spec. I understand that others are, I understand the potential value there and I do think we can make it work, but I share Ryan and Chris' general reluctance to change our behavior (though, obviously, not to the same extent :) ). In _this_ intent thread, however, I don't intend to make any change to Blink's mixed-content detection code. If a cosmic event happens, and the security team decides that that such a change is indeed worthwhile, I'd suggest that it should be covered by a separate intent. I think this addresses Ryan's concern #2 for the moment, but certainly lends strength to his suspicion that this proposal is a trojan horse.

With that as background, I think Ryan's suggestion to consider the value of the
proposal without consideration of its potential effect on mixed-content is
reasonable. So why should we do this?

  1. SRI offers authors the ability to reduce the ambient authority of CDNs and other third-parties. I want the benefits of Akamai's or Google's reach, but I don't want to _trust_ them further than I have to in order to gain those benefits. I want the exciting potential of some random third-party widget, and I'm happy for them to bear the hosting costs, but I don't trust them not to pull the rug out from under me. Contractual obligations are good, resource pinning is better.

  2. SRI enables content-based caching, which, if we're careful about it, has distinct advantages for performance. It's probably worth focusing some attention on the mitigations and risks outlined in the spec; if we're missing things there, help would be appreciated.
At what cost would we attain these benefits?

  1. Ryan, quite correctly, claims that the priority of constituencies obligates us to consider the user above site authors. I agree with this completely. I disagree, however, that making it more difficult for some kinds of transcoding proxies to operate violates this priority. If it did, I think we'd have to be more willing to weaken HTTPS in general, as that certainly has the same effect on proxies sitting between the user and the resources they wish to download.

    We block proxies' ability to MitM connections by default, even if a user really wants that behavior. If a user (or the company she works for) wishes to negate the security guarantees of that behavior, we allow them to opt-out by adding a new root to the set locally trusted. Allowing an opt-out of SRI (perhaps by installing an extension which strips or modifies the integrity metadata) is similarly available.

  2. Performance impacts. I suspect that the advantage of not loading jQuery anew every time you hit a new website would be substantial. Would that, and similarly-shared resources outweigh the impact of delaying rendering/execution until the resource is loaded? Possibly. If we make progressive validation via merkle trees or similar is a 1.0 requirement rather than being something we can push out to the next version of the spec, we can mitigate this risk.

    We don't have a syntax for that yet. We don't really have good ideas about how such a syntax should look. Suggestions welcome. :)
*shrug* I think it's a very reasonable feature to experiment with/implement. With implementation experience and experimentation, we'll be able to make more informed decisions about _shipping_ when we get to a more stable state. That's how I'd like to proceed. 

Thanks!

-mike



-Mike

William Chan (陈智昌)

unread,
Mar 25, 2014, 7:51:33 PM3/25/14
to Mike West, blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

First, thanks for this email. It's much clearer now. Here are some comments on particular points.

From the "intents" part:
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance. I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

From the "why do this" part:

(1) I think missing in this explanation is that, even if you trust a CDN to be well-intentioned, it is still vulnerable to compromise. SRI would help mitigate that.

On Tue, Mar 25, 2014 at 4:32 AM, Mike West <mk...@chromium.org> wrote:
Hooray! This is an interesting enough feature to argue about. At length. :)

First, let me try to be clear about what I intend this "intent" thread to cover:

  1. I intend to add support for an `integrity` attribute on a variety of HTML elements, which allows authors to specify integrity metadata for resources those elements fetch.

  2. I intend to add verification functionality somewhere TBD (probably in Blink, maybe in the network stack, maybe in Service Workers, maybe somewhere else entirely; active discussion with area experts was my main purpose in this thread) that uses the integrity metadata specified in #1 to block the execution or rendering of resources which fail an integrity check.

  3. I intend to add some sort of fallback functionality, similar to what's specified in the 'noncanonical-src' section; folks have convinced me that it's worth implementing even in the case where we entirely throw out the concept of relaxing mixed-content. This section of the spec is, as Ryan notes, under construction. I'll work on that this week to try to make the use case and value more clear (basically, I agree with Mark's suggestion).

  4. I would like to explore the possibilities of caching based on integrity metadata rather than URL. This would have real value in the generalized jQuery case (I think the network team did some experiments in this direction that Chris or Will might be able to detail) and given the mitigations outlined in the spec, I don't believe it's as much of a security footgun as Ryan and Chris seem to.

  5. Given that any integrity guarantee we could make depends entirely on our ability to trust the document which contains the integrity metadata, I think it's pretty reasonable to support integity checks _only_ for documents served over HTTPS. I think I'd be happy to hard-fail integrity checks if the document including metadata is served over HTTP.

     think this would address Ryan's concern #1.

  6. I, personally, am not terribly thrilled about the mixed-content portion of the spec. I understand that others are, I understand the potential value there and I do think we can make it work, but I share Ryan and Chris' general reluctance to change our behavior (though, obviously, not to the same extent :) ). In _this_ intent thread, however, I don't intend to make any change to Blink's mixed-content detection code. If a cosmic event happens, and the security team decides that that such a change is indeed worthwhile, I'd suggest that it should be covered by a separate intent. I think this addresses Ryan's concern #2 for the moment, but certainly lends strength to his suspicion that this proposal is a trojan horse.

With that as background, I think Ryan's suggestion to consider the value of the
proposal without consideration of its potential effect on mixed-content is
reasonable. So why should we do this?

  1. SRI offers authors the ability to reduce the ambient authority of CDNs and other third-parties. I want the benefits of Akamai's or Google's reach, but I don't want to _trust_ them further than I have to in order to gain those benefits. I want the exciting potential of some random third-party widget, and I'm happy for them to bear the hosting costs, but I don't trust them not to pull the rug out from under me. Contractual obligations are good, resource pinning is better.

  2. SRI enables content-based caching, which, if we're careful about it, has distinct advantages for performance. It's probably worth focusing some attention on the mitigations and risks outlined in the spec; if we're missing things there, help would be appreciated.
At what cost would we attain these benefits?

  1. Ryan, quite correctly, claims that the priority of constituencies obligates us to consider the user above site authors. I agree with this completely. I disagree, however, that making it more difficult for some kinds of transcoding proxies to operate violates this priority. If it did, I think we'd have to be more willing to weaken HTTPS in general, as that certainly has the same effect on proxies sitting between the user and the resources they wish to download.

    We block proxies' ability to MitM connections by default, even if a user really wants that behavior. If a user (or the company she works for) wishes to negate the security guarantees of that behavior, we allow them to opt-out by adding a new root to the set locally trusted. Allowing an opt-out of SRI (perhaps by installing an extension which strips or modifies the integrity metadata) is similarly available.

  2. Performance impacts. I suspect that the advantage of not loading jQuery anew every time you hit a new website would be substantial. Would that, and similarly-shared resources outweigh the impact of delaying rendering/execution until the resource is loaded? Possibly. If we make progressive validation via merkle trees or similar is a 1.0 requirement rather than being something we can push out to the next version of the spec, we can mitigate this risk.

    We don't have a syntax for that yet. We don't really have good ideas about how such a syntax should look. Suggestions welcome. :)
*shrug* I think it's a very reasonable feature to experiment with/implement. With implementation experience and experimentation, we'll be able to make more informed decisions about _shipping_ when we get to a more stable state. That's how I'd like to proceed. 

If we're just discussing implementation and not shipping, and assuming development time is free, I think this is very worthwhile to explore, at least from understanding the performance perspective. Since there are developers excited about spending their time exploring this space, I don't see a good reason to tell them not to spend their time on this (other than being less excited about the potential performance gains of content addressable caching). There are some interesting implementation issues in managing a content addressable cache, but I think we can implement it reasonably cleanly without imposing a large architectural burden. I went through a similar thought exercise for a different feature earlier this week and believe it quite tractable.

Chris Bentzel

unread,
Mar 25, 2014, 8:39:22 PM3/25/14
to William Chan (陈智昌), Mike West, blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
Assuming that we decide to implement this, how will the deployment strategy go beyond that?

The Blink process seems to focus on implementing new APIs behind a runtime flag, and then enabling the API by default after there's a significant amount of implementation and spec maturity.

However, that process may not be appropriate for this API.

As others have pointed out, I'm worried that a number of middleware (transparent proxies, anti-virus software, data-loss prevention, etc) will manipulate the content and make it impossible to widely enforce SRI. But this won't be known until this is deployed and measured on a number of users. Could this API be enabled for a swath of users (with some services opting in), without going the fully-shipped route to measure this?

Alternately, would it make sense to do probes for some random content on the web inside of Chrome now and see how common manipulations are?

Elliott Sprehn

unread,
Mar 25, 2014, 8:51:50 PM3/25/14
to Chris Bentzel, William Chan (陈智昌), Mike West, blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
We could use a Finch experiment to only enable it for some users, we just need a way for developers to make it always happen for testing.

Mike West

unread,
Mar 26, 2014, 9:38:33 AM3/26/14
to William Chan (陈智昌), blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Wed, Mar 26, 2014 at 12:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

Sorry. I thought using GMail's formatting tools would make the email easier to read. I should have stuck to plain text.
 
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

That makes sense. I'd like to ensure that we don't end up writing validation code 80 times across the codebase, but we certainly don't need to do work in the network stack to make that possible.

That said, the network stack is a nicely central place to do this kind of work. :) Would progressive hashing make you less concerned about the buffering requirements?
 
(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

In a nutshell, the current failure mode is to block the resource completely in cases where MitM proxies manipulate them. In cases of important scripts, this would result in breaking the site entirely.

The suggestion, then, is to have a fallback mechanism which would not be integrity checked. Perhaps it would be hosted on the same server as the page itself; you wouldn't get the benefits of your globally awesome CDN, but you'd trust (at least) the source of the file. This would enable your application to function correctly in environments that would be otherwise entirely broken (Global MegaCorp with its draconian IT department, for example).
 
(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance.
 
I'd love to see whatever data you've gathered in the past.

It's a bit chicken-and-egg, isn't it? Current best-practice creates conditions in which this kind of caching is less effective than it could be. For example, if content-based caching existed, developers might have more incentive to split out the libraries from the rest of their code, and to use The Canonical Version rather than stripping things down.

I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

This is certainly something to be concerned about. We try to mitigate the risk with the recommendations in http://w3c.github.io/webappsec/specs/subresourceintegrity/#recommendations-1 Suggestions for and critique of this section of the spec would be very much appreciated.
 
(1) I think missing in this explanation is that, even if you trust a CDN to be well-intentioned, it is still vulnerable to compromise. SRI would help mitigate that.

I agree. We mention that in the spec, but I neglected to spell out that threat here.

-mike

Mike West

unread,
Mar 26, 2014, 9:42:41 AM3/26/14
to Chris Bentzel, William Chan (陈智昌), blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Wed, Mar 26, 2014 at 1:39 AM, Chris Bentzel <cben...@chromium.org> wrote:
As others have pointed out, I'm worried that a number of middleware (transparent proxies, anti-virus software, data-loss prevention, etc) will manipulate the content and make it impossible to widely enforce SRI. But this won't be known until this is deployed and measured on a number of users. Could this API be enabled for a swath of users (with some services opting in), without going the fully-shipped route to measure this?

I agree with you and Elliott. Finding a large-enough service willing to experiment, and running a Finch experiment would be a reasonable way of evaluating whether or not this feature is deployable on the web at large. I can poke at folks inside and outside Google to gauge interest.
 
Alternately, would it make sense to do probes for some random content on the web inside of Chrome now and see how common manipulations are?

It might. We could, for example, hard-code the hashes of some common scripts at well-known URLs (http://code.jquery.com/jquery-1.11.0.min.js for example) and add some counters. Is that along the lines of what you're suggesting?

-mike 

William Chan (陈智昌)

unread,
Mar 26, 2014, 12:45:56 PM3/26/14
to Mike West, blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Wed, Mar 26, 2014 at 6:38 AM, Mike West <mk...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 12:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

Sorry. I thought using GMail's formatting tools would make the email easier to read. I should have stuck to plain text.
 
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

That makes sense. I'd like to ensure that we don't end up writing validation code 80 times across the codebase, but we certainly don't need to do work in the network stack to make that possible.

That said, the network stack is a nicely central place to do this kind of work. :) Would progressive hashing make you less concerned about the buffering requirements?

Only if it were mandatory and had well-defined limits on the amount of data that needs to be read before being able to do digest verification of a chunk and handing off a verified data chunk to the consumer.

I think that the network stack is the wrong place to do this due to this being primarily a web platform feature. We should implement this in the web resource loading part of our code instead. I suggest either doing it in the Blink loader or the Chromium browser-side multiprocess resource loader (ResourceDispatcherHost). This way, our other non-web network stack consumers don't get affected by this. Since the browser process is essentially our kernel, it's probably advisable not to do excessive buffering there. So I guess my overall recommendation is to implement in the Blink resource loader. Wait, I forgot that this needs to interact with SW. SW is opt-in on the part of the document, so perhaps SW should be allowed to ignore the integrity attribute. It's too early in the morning to think this completely through, and this gbus is giving me a headache. I'll think about this later, or likely someone else can figure it out.

 
(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

In a nutshell, the current failure mode is to block the resource completely in cases where MitM proxies manipulate them. In cases of important scripts, this would result in breaking the site entirely.

The suggestion, then, is to have a fallback mechanism which would not be integrity checked. Perhaps it would be hosted on the same server as the page itself; you wouldn't get the benefits of your globally awesome CDN, but you'd trust (at least) the source of the file. This would enable your application to function correctly in environments that would be otherwise entirely broken (Global MegaCorp with its draconian IT department, for example).

Thanks for the explanation. I believe this reason can be safely ignored because IIUC, we possess the facility at the browser to fail open WRT additional CA trust anchors. This is how we disable key pinning when additional CA trust anchors are present. My recommendation would be to disable the integrity check in these cases. I think the fallback would discourage adoption, since it is actively painful for users behind these MITM proxies. Of course, I hate these MITM proxies so maybe we should hurt folks behind them so they complain to their IT admins :P I kid...I kid...but only kinda.


(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance.
 
I'd love to see whatever data you've gathered in the past.

Turns out I would too. I went into GMail looking for this data, but have been unable to find much more than discussion with Steve Souders about how much of jQuery is hosted on Google Hosted Libraries. IIRC, I dropped by his and Ilya's office to chat with this about this, web perfy stuff in general, and the meaning of life, but there is no record of the actual substance of that chat, so I have no interesting data to share other than vague recollections which I think you can safely ignore. We can also /summon souders and igrigorik to see if they remember. But I think you're best off gathering data on your own.


It's a bit chicken-and-egg, isn't it? Current best-practice creates conditions in which this kind of caching is less effective than it could be. For example, if content-based caching existed, developers might have more incentive to split out the libraries from the rest of their code, and to use The Canonical Version rather than stripping things down.

That's only true if the primary thing you're looking to save is network byte transfer / time. But from a web perf standpoint, self-hosting can be better in *some* (don't generalize too much from this, despite my verbose explanation) situations because parsing a huge blob of jQuery rather than the stripped down individual module you need is significantly more computationally expensive, especially on mobile where it's a non-trivial portion of page load time. In mobile web perf, you have to balance all the local resources (CPU, disk I/O for caches, network, etc) since they're all potentially the bottleneck, so a pure caching win does not necessarily translate into better performance. Now, folks (jochen?) are looking at whether or not we can cache the v8 parsed script representation (the ASTs) to save on a lot of the CPU time, but we're not there yet, and it just adds more flexibility/variables into how to schedule work for optimal performance.


I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

This is certainly something to be concerned about. We try to mitigate the risk with the recommendations in http://w3c.github.io/webappsec/specs/subresourceintegrity/#recommendations-1 Suggestions for and critique of this section of the spec would be very much appreciated.

I missed this section in an earlier pass. I think the CORS restriction in particular mitigates this privacy concern greatly.

Ryan Sleevi

unread,
Mar 26, 2014, 8:44:25 PM3/26/14
to William Chan (陈智昌), Mike West, blink-dev, Ryan Sleevi, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Wed, Mar 26, 2014 at 9:45 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 6:38 AM, Mike West <mk...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 12:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

Sorry. I thought using GMail's formatting tools would make the email easier to read. I should have stuck to plain text.
 
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

That makes sense. I'd like to ensure that we don't end up writing validation code 80 times across the codebase, but we certainly don't need to do work in the network stack to make that possible.

That said, the network stack is a nicely central place to do this kind of work. :) Would progressive hashing make you less concerned about the buffering requirements?

Only if it were mandatory and had well-defined limits on the amount of data that needs to be read before being able to do digest verification of a chunk and handing off a verified data chunk to the consumer.

You don't digest chunks though (at least, there is still no incremental hashing). So you have to buffer the entire thing. Now, you don't *have* to keep it in memory - that is, you can update the digest in chunks while spooling to a file-backed cache entry - but this is something where, at whatever layer integrity metadata is integrated, *something* has to hold back all the data until things are verified.
 

I think that the network stack is the wrong place to do this due to this being primarily a web platform feature. We should implement this in the web resource loading part of our code instead. I suggest either doing it in the Blink loader or the Chromium browser-side multiprocess resource loader (ResourceDispatcherHost). This way, our other non-web network stack consumers don't get affected by this. Since the browser process is essentially our kernel, it's probably advisable not to do excessive buffering there. So I guess my overall recommendation is to implement in the Blink resource loader. Wait, I forgot that this needs to interact with SW. SW is opt-in on the part of the document, so perhaps SW should be allowed to ignore the integrity attribute. It's too early in the morning to think this completely through, and this gbus is giving me a headache. I'll think about this later, or likely someone else can figure it out.

Yet another reason why I favour the explore by SW aspect - it's still very unclear, from reading the spec, how this is supposed to interplay with Extensions (whether "Cloud to Butt" style extensions or things like HTTPS Everywhere), how it's meant to interplay with Service Workers, and how it's meant to interplay with opt-in client features for transcoding.

That's not to say these can't be solved, but I feel like the spec should be clearer here.
 

 
(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

In a nutshell, the current failure mode is to block the resource completely in cases where MitM proxies manipulate them. In cases of important scripts, this would result in breaking the site entirely.

The suggestion, then, is to have a fallback mechanism which would not be integrity checked. Perhaps it would be hosted on the same server as the page itself; you wouldn't get the benefits of your globally awesome CDN, but you'd trust (at least) the source of the file. This would enable your application to function correctly in environments that would be otherwise entirely broken (Global MegaCorp with its draconian IT department, for example).

Thanks for the explanation. I believe this reason can be safely ignored because IIUC, we possess the facility at the browser to fail open WRT additional CA trust anchors. This is how we disable key pinning when additional CA trust anchors are present. My recommendation would be to disable the integrity check in these cases. I think the fallback would discourage adoption, since it is actively painful for users behind these MITM proxies. Of course, I hate these MITM proxies so maybe we should hurt folks behind them so they complain to their IT admins :P I kid...I kid...but only kinda.

I do not think we should be trying to apply heuristics like the "additional CA trust anchors" (which are far, far from perfect) here. 

This again presumes we're doing the mixed-content path, which from talking with security, no one is really keen on, me especially. I'm especially concerned by this use case, because it seems to be combined with an attempt to retrofit "authentication" onto the "opportunistic obfuscation" proposals for HTTP.

I mean, we can discuss this in depth and figure out the whole security story, but my goal in continuing to try to defer this particular use case is to at the minimal set of functionality first - which the spec itself is happy to call out minimal - before we start making changes to the promises web browsers try to make to users today regarding privacy and integrity.
 


(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance.
 
I'd love to see whatever data you've gathered in the past.

Turns out I would too. I went into GMail looking for this data, but have been unable to find much more than discussion with Steve Souders about how much of jQuery is hosted on Google Hosted Libraries. IIRC, I dropped by his and Ilya's office to chat with this about this, web perfy stuff in general, and the meaning of life, but there is no record of the actual substance of that chat, so I have no interesting data to share other than vague recollections which I think you can safely ignore. We can also /summon souders and igrigorik to see if they remember. But I think you're best off gathering data on your own.


It's a bit chicken-and-egg, isn't it? Current best-practice creates conditions in which this kind of caching is less effective than it could be. For example, if content-based caching existed, developers might have more incentive to split out the libraries from the rest of their code, and to use The Canonical Version rather than stripping things down.

That's only true if the primary thing you're looking to save is network byte transfer / time. But from a web perf standpoint, self-hosting can be better in *some* (don't generalize too much from this, despite my verbose explanation) situations because parsing a huge blob of jQuery rather than the stripped down individual module you need is significantly more computationally expensive, especially on mobile where it's a non-trivial portion of page load time. In mobile web perf, you have to balance all the local resources (CPU, disk I/O for caches, network, etc) since they're all potentially the bottleneck, so a pure caching win does not necessarily translate into better performance. Now, folks (jochen?) are looking at whether or not we can cache the v8 parsed script representation (the ASTs) to save on a lot of the CPU time, but we're not there yet, and it just adds more flexibility/variables into how to schedule work for optimal performance.


I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

This is certainly something to be concerned about. We try to mitigate the risk with the recommendations in http://w3c.github.io/webappsec/specs/subresourceintegrity/#recommendations-1 Suggestions for and critique of this section of the spec would be very much appreciated.

I missed this section in an earlier pass. I think the CORS restriction in particular mitigates this privacy concern greatly.

I'm not sure I fully understand why you feel CORS reduces it. Is it because you believe not a lot of resources are wide-open with CORS like this?

I'm also not sold on the SHA-512 (why not SHA-256? Or SHA-384?) It doesn't feel like the spec really deals with the substance of the security concerns here.

The goal of the attacker is to passively probe whether or not you have a given resource cached. The hash of the resource they are targeting is known. Thus the strength of the hash doesn't matter here.

For example, couldn't I programmatically exploit this by creating an img with a .src of a Blob/Data URI, set the .integrity attribute to the hash of what I want to probe for, and then inject into the DOM? There is no network traffic, I can ensure the Blob URI doesn't match the integrity attribute (thus always fails). However, IF the user has the resource cached in the content-address cache, the resource embedding will succeed - thus revealing where the user had been.
 

 
(1) I think missing in this explanation is that, even if you trust a CDN to be well-intentioned, it is still vulnerable to compromise. SRI would help mitigate that.

I agree. We mention that in the spec, but I neglected to spell out that threat here.

-mike


Absent both caching and mixed-content - both of which I think need more fleshing out - I'm quite mixed on the value here.

If it's a script you know about/control, you can obviously host it locally (eg: not on the CDN). As Will mentions, there are many times where doing so can actually *improve* performance, compared to just throwing the whole-dang-library together.

If it's a script you don't control - which is commonly the case for the analytics scripts that seem to be the risk the editors' are concerned about - it implies that the CDN/analytics provider is versioning their resources, and that site operators can review these versions, and whitelist the hash. Except the CDNs aren't - they frequently change - and so instead we're just encouraging a more broken web. The further insult is that "broken web" is exactly a use case being striven for (The Section 1.2.1 "mashup" example)

If anything, I expect CDNs/analytics would be *opposed* to this change - not because of the security benefits, but because of the massive support hurdles. My anecdata is that very few analytics firms (eg: http://w3c.github.io/webappsec/specs/subresourceintegrity/#use-cases-examples ) actually version their analytics scripts.


We should only do this if there are clear security (without sacrificing performance) wins or performance (without sacrificing security) wins. Of these, the only "Use Case" that strikes me as meeting the criteria of clear wins in *either* category is the "Injecting Active Content" analytics example, which arguably can be used to improve security. The rest seem social issues whose "real" solution is non-technical, or which require much further specification/review/discussion (mixed-content, caching).

For the analytics case, it seems like if site operators *really* are concerned about that, there are other technical solutions
 - Moving the analytics 'dynamic' code to an iframe, communicated with via a static, non-CDN'd JS file in the main document
 - Hosting the analytics JS locally
 - Exploring the Service Worker route

William Chan (陈智昌)

unread,
Mar 26, 2014, 10:51:05 PM3/26/14
to Ryan Sleevi, Mike West, blink-dev, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Wed, Mar 26, 2014 at 5:44 PM, Ryan Sleevi <rsl...@chromium.org> wrote:



On Wed, Mar 26, 2014 at 9:45 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 6:38 AM, Mike West <mk...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 12:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

Sorry. I thought using GMail's formatting tools would make the email easier to read. I should have stuck to plain text.
 
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

That makes sense. I'd like to ensure that we don't end up writing validation code 80 times across the codebase, but we certainly don't need to do work in the network stack to make that possible.

That said, the network stack is a nicely central place to do this kind of work. :) Would progressive hashing make you less concerned about the buffering requirements?

Only if it were mandatory and had well-defined limits on the amount of data that needs to be read before being able to do digest verification of a chunk and handing off a verified data chunk to the consumer.

You don't digest chunks though (at least, there is still no incremental hashing). So you have to buffer the entire thing. Now, you don't *have* to keep it in memory - that is, you can update the digest in chunks while spooling to a file-backed cache entry - but this is something where, at whatever layer integrity metadata is integrated, *something* has to hold back all the data until things are verified.

I indeed was implying the requirement of some form of incremental hashing, as we've previously mentioned many times.
 
 

I think that the network stack is the wrong place to do this due to this being primarily a web platform feature. We should implement this in the web resource loading part of our code instead. I suggest either doing it in the Blink loader or the Chromium browser-side multiprocess resource loader (ResourceDispatcherHost). This way, our other non-web network stack consumers don't get affected by this. Since the browser process is essentially our kernel, it's probably advisable not to do excessive buffering there. So I guess my overall recommendation is to implement in the Blink resource loader. Wait, I forgot that this needs to interact with SW. SW is opt-in on the part of the document, so perhaps SW should be allowed to ignore the integrity attribute. It's too early in the morning to think this completely through, and this gbus is giving me a headache. I'll think about this later, or likely someone else can figure it out.

Yet another reason why I favour the explore by SW aspect - it's still very unclear, from reading the spec, how this is supposed to interplay with Extensions (whether "Cloud to Butt" style extensions or things like HTTPS Everywhere), how it's meant to interplay with Service Workers, and how it's meant to interplay with opt-in client features for transcoding.

That's not to say these can't be solved, but I feel like the spec should be clearer here.

I don't think that's a reason to say an absolute "no", but it's a reason to say, "hold on, let's work this through first", which is the purpose of this email, AIUI.
 
 

 
(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

In a nutshell, the current failure mode is to block the resource completely in cases where MitM proxies manipulate them. In cases of important scripts, this would result in breaking the site entirely.

The suggestion, then, is to have a fallback mechanism which would not be integrity checked. Perhaps it would be hosted on the same server as the page itself; you wouldn't get the benefits of your globally awesome CDN, but you'd trust (at least) the source of the file. This would enable your application to function correctly in environments that would be otherwise entirely broken (Global MegaCorp with its draconian IT department, for example).

Thanks for the explanation. I believe this reason can be safely ignored because IIUC, we possess the facility at the browser to fail open WRT additional CA trust anchors. This is how we disable key pinning when additional CA trust anchors are present. My recommendation would be to disable the integrity check in these cases. I think the fallback would discourage adoption, since it is actively painful for users behind these MITM proxies. Of course, I hate these MITM proxies so maybe we should hurt folks behind them so they complain to their IT admins :P I kid...I kid...but only kinda.

I do not think we should be trying to apply heuristics like the "additional CA trust anchors" (which are far, far from perfect) here.

Don't they only have to be as accurate as they currently are for key pinning? If not, I'd like to understand why.
 

This again presumes we're doing the mixed-content path, which from talking with security, no one is really keen on, me especially. I'm especially concerned by this use case, because it seems to be combined with an attempt to retrofit "authentication" onto the "opportunistic obfuscation" proposals for HTTP.

Can you explain why this presumes the mixed-content path? I'm not excited about that either, so I'm curious why that is implied here. I don't think a fallback mechanism that isn't integrity checked has to be http:// instead. But I might have misunderstood as I'm rather new to this discussion.
 

I mean, we can discuss this in depth and figure out the whole security story, but my goal in continuing to try to defer this particular use case is to at the minimal set of functionality first - which the spec itself is happy to call out minimal - before we start making changes to the promises web browsers try to make to users today regarding privacy and integrity.
 


(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance.
 
I'd love to see whatever data you've gathered in the past.

Turns out I would too. I went into GMail looking for this data, but have been unable to find much more than discussion with Steve Souders about how much of jQuery is hosted on Google Hosted Libraries. IIRC, I dropped by his and Ilya's office to chat with this about this, web perfy stuff in general, and the meaning of life, but there is no record of the actual substance of that chat, so I have no interesting data to share other than vague recollections which I think you can safely ignore. We can also /summon souders and igrigorik to see if they remember. But I think you're best off gathering data on your own.


It's a bit chicken-and-egg, isn't it? Current best-practice creates conditions in which this kind of caching is less effective than it could be. For example, if content-based caching existed, developers might have more incentive to split out the libraries from the rest of their code, and to use The Canonical Version rather than stripping things down.

That's only true if the primary thing you're looking to save is network byte transfer / time. But from a web perf standpoint, self-hosting can be better in *some* (don't generalize too much from this, despite my verbose explanation) situations because parsing a huge blob of jQuery rather than the stripped down individual module you need is significantly more computationally expensive, especially on mobile where it's a non-trivial portion of page load time. In mobile web perf, you have to balance all the local resources (CPU, disk I/O for caches, network, etc) since they're all potentially the bottleneck, so a pure caching win does not necessarily translate into better performance. Now, folks (jochen?) are looking at whether or not we can cache the v8 parsed script representation (the ASTs) to save on a lot of the CPU time, but we're not there yet, and it just adds more flexibility/variables into how to schedule work for optimal performance.


I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

This is certainly something to be concerned about. We try to mitigate the risk with the recommendations in http://w3c.github.io/webappsec/specs/subresourceintegrity/#recommendations-1 Suggestions for and critique of this section of the spec would be very much appreciated.

I missed this section in an earlier pass. I think the CORS restriction in particular mitigates this privacy concern greatly.

I'm not sure I fully understand why you feel CORS reduces it. Is it because you believe not a lot of resources are wide-open with CORS like this?

Joel pointed out to me that CORS headers are already used out in the while without the expectation that we'd add this semantic here. So yes, adding this additional policy semantic might be problematic. I had not previously considered that. But if we were talking about something that didn't already have existing use, I don't think it would be problematic, except potentially as a footgun. But if an origin server has to opt-in to allow their users to leak browsing history of that origin, that strikes me as a reasonable mitigation. But I do agree that it's problematic if we reuse a previous opt-in signal in a way that was not previously intended, thus breaking backwards compat with previous privacy expectations.


I'm also not sold on the SHA-512 (why not SHA-256? Or SHA-384?) It doesn't feel like the spec really deals with the substance of the security concerns here.

The goal of the attacker is to passively probe whether or not you have a given resource cached. The hash of the resource they are targeting is known. Thus the strength of the hash doesn't matter here.

For example, couldn't I programmatically exploit this by creating an img with a .src of a Blob/Data URI, set the .integrity attribute to the hash of what I want to probe for, and then inject into the DOM? There is no network traffic, I can ensure the Blob URI doesn't match the integrity attribute (thus always fails). However, IF the user has the resource cached in the content-address cache, the resource embedding will succeed - thus revealing where the user had been.
 

 
(1) I think missing in this explanation is that, even if you trust a CDN to be well-intentioned, it is still vulnerable to compromise. SRI would help mitigate that.

I agree. We mention that in the spec, but I neglected to spell out that threat here.

-mike


Absent both caching and mixed-content - both of which I think need more fleshing out - I'm quite mixed on the value here.

If it's a script you know about/control, you can obviously host it locally (eg: not on the CDN). As Will mentions, there are many times where doing so can actually *improve* performance, compared to just throwing the whole-dang-library together.

If it's a script you don't control - which is commonly the case for the analytics scripts that seem to be the risk the editors' are concerned about - it implies that the CDN/analytics provider is versioning their resources, and that site operators can review these versions, and whitelist the hash. Except the CDNs aren't - they frequently change - and so instead we're just encouraging a more broken web. The further insult is that "broken web" is exactly a use case being striven for (The Section 1.2.1 "mashup" example)

If anything, I expect CDNs/analytics would be *opposed* to this change - not because of the security benefits, but because of the massive support hurdles. My anecdata is that very few analytics firms (eg: http://w3c.github.io/webappsec/specs/subresourceintegrity/#use-cases-examples ) actually version their analytics scripts.


We should only do this if there are clear security (without sacrificing performance) wins or performance (without sacrificing security) wins. Of these, the only "Use Case" that strikes me as meeting the criteria of clear wins in *either* category is the "Injecting Active Content" analytics example, which arguably can be used to improve security. The rest seem social issues whose "real" solution is non-technical, or which require much further specification/review/discussion (mixed-content, caching).

For the analytics case, it seems like if site operators *really* are concerned about that, there are other technical solutions
 - Moving the analytics 'dynamic' code to an iframe, communicated with via a static, non-CDN'd JS file in the main document
 - Hosting the analytics JS locally
 - Exploring the Service Worker route

You've mentioned the analytics case a number of times. I agree with your analysis there. What do you think about the jQuery case? jQuery is indeed versioned on CDNs, like Google Hosted Libraries. It seems to me that there is a non-zero security win for integrity protecting jQuery to insulate against CDN compromise (or outright malicious behavior, of which I'm more skeptical). I don't know if I think this security win is big, but I think that the non-incremental integrity mechanism is fairly cheap.

Mike West

unread,
Mar 27, 2014, 5:30:22 AM3/27/14
to William Chan (陈智昌), Ryan Sleevi, blink-dev, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
Before diving into the detail, let's say that I modify the intent to implement to something super minimal. Based on the discussion here, it sounds like Will would be interested in (and Ryan wouldn't be actively against) the following:

1. Add `integrity` attributes for a bunch of elements.
2. Use those attributes to verify the resource before rendering it.
3. Add a CSP directive to set the document's response to a verification failure (which I forgot to mention before, sorry).
4. Nothing else.
5. Certainly not touching mixed-content, fallback, caching, etc.
6. No, really. None of that.
7. I mean it.

This would provide a mechanism for authors to opt-in to a security win of some unknown size (let's say it's _huge_, because that would make me feel better), at the cost of blocking rendering until the resource is validated. Implementing this subset would allow us to determine exactly what that performance impact is, and also allow us to determine whether any of this makes sense on the web as it exists today (see Chris' concerns about transcoding proxies).

WDYT?

On Thu, Mar 27, 2014 at 3:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 5:44 PM, Ryan Sleevi <rsl...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 9:45 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 6:38 AM, Mike West <mk...@chromium.org> wrote:
On Wed, Mar 26, 2014 at 12:51 AM, William Chan (陈智昌) <will...@chromium.org> wrote:
I tried to inline responses, but it ruined the numbering which came from formatting. So I'm top-posting instead. Sorry if this bothers anyone.

Sorry. I thought using GMail's formatting tools would make the email easier to read. I should have stuck to plain text.
 
(2) From my perspective, were we to implement SRI, it's best not to do so in the network stack. It would lead to significant buffering requirements within the network stack. Our resource loading is flow controlled by being mostly pull-oriented (renderer pulls data from the network stack which pulls data from the network and opens up network receive windows to accept more data). If the network stack were to have to verify integrity before passing data onward to the consumer, that would increase its own buffering (and thus memory) requirements, which is more correctly delegated to the consumer.

That makes sense. I'd like to ensure that we don't end up writing validation code 80 times across the codebase, but we certainly don't need to do work in the network stack to make that possible.

That said, the network stack is a nicely central place to do this kind of work. :) Would progressive hashing make you less concerned about the buffering requirements?

Only if it were mandatory and had well-defined limits on the amount of data that needs to be read before being able to do digest verification of a chunk and handing off a verified data chunk to the consumer.

You don't digest chunks though (at least, there is still no incremental hashing). So you have to buffer the entire thing. Now, you don't *have* to keep it in memory - that is, you can update the digest in chunks while spooling to a file-backed cache entry - but this is something where, at whatever layer integrity metadata is integrated, *something* has to hold back all the data until things are verified.

I indeed was implying the requirement of some form of incremental hashing, as we've previously mentioned many times.
 
 

I think that the network stack is the wrong place to do this due to this being primarily a web platform feature. We should implement this in the web resource loading part of our code instead. I suggest either doing it in the Blink loader or the Chromium browser-side multiprocess resource loader (ResourceDispatcherHost). This way, our other non-web network stack consumers don't get affected by this. Since the browser process is essentially our kernel, it's probably advisable not to do excessive buffering there. So I guess my overall recommendation is to implement in the Blink resource loader. Wait, I forgot that this needs to interact with SW. SW is opt-in on the part of the document, so perhaps SW should be allowed to ignore the integrity attribute. It's too early in the morning to think this completely through, and this gbus is giving me a headache. I'll think about this later, or likely someone else can figure it out.

Yet another reason why I favour the explore by SW aspect - it's still very unclear, from reading the spec, how this is supposed to interplay with Extensions (whether "Cloud to Butt" style extensions or things like HTTPS Everywhere), how it's meant to interplay with Service Workers, and how it's meant to interplay with opt-in client features for transcoding.

That's not to say these can't be solved, but I feel like the spec should be clearer here.

I don't think that's a reason to say an absolute "no", but it's a reason to say, "hold on, let's work this through first", which is the purpose of this email, AIUI.

1. The intent here was indeed to gather implementation experience to inform the specification process. We don't want to specify something in the abstract, only to find that it's unimplementable after we've hit CR.

2. For clarity: SRI shouldn't restrict extensions. I've added a note to the spec to that effect in response to exactly the concerns you're raising. I'd expect the implementation to work similarly to the CSP implementation I'm also responsible for.

3. Opt-in transcoders would need to be updated with an understanding of the integrity attribute. Since mechanisms like PageSpeed are already updating the URLs in an HTML document they process, updating the hashes at the same time is probably not a huge deal</hand-waving>. I need to talk to that team; I haven't yet.

 
(3) Just doublechecking, mnot's suggestion was about structuring the fallback so that user agents that don't implement noncanonical-src still work by loading from the src attribute, right? What's the reason for having the alternate src URI in the first place? The document mentions using a HTTP URI (to be "cache-friendly"), but I assume that's only if we wanted to relax our mixed content policy. But your comment suggests there is another reason. Can you explain that? It's not anywhere in these emails, or else I've missed it (sorry).

In a nutshell, the current failure mode is to block the resource completely in cases where MitM proxies manipulate them. In cases of important scripts, this would result in breaking the site entirely.

The suggestion, then, is to have a fallback mechanism which would not be integrity checked. Perhaps it would be hosted on the same server as the page itself; you wouldn't get the benefits of your globally awesome CDN, but you'd trust (at least) the source of the file. This would enable your application to function correctly in environments that would be otherwise entirely broken (Global MegaCorp with its draconian IT department, for example).

Thanks for the explanation. I believe this reason can be safely ignored because IIUC, we possess the facility at the browser to fail open WRT additional CA trust anchors. This is how we disable key pinning when additional CA trust anchors are present. My recommendation would be to disable the integrity check in these cases. I think the fallback would discourage adoption, since it is actively painful for users behind these MITM proxies. Of course, I hate these MITM proxies so maybe we should hurt folks behind them so they complain to their IT admins :P I kid...I kid...but only kinda.

I do not think we should be trying to apply heuristics like the "additional CA trust anchors" (which are far, far from perfect) here.

Don't they only have to be as accurate as they currently are for key pinning? If not, I'd like to understand why.
 

This again presumes we're doing the mixed-content path, which from talking with security, no one is really keen on, me especially. I'm especially concerned by this use case, because it seems to be combined with an attempt to retrofit "authentication" onto the "opportunistic obfuscation" proposals for HTTP.

Can you explain why this presumes the mixed-content path? I'm not excited about that either, so I'm curious why that is implied here. I don't think a fallback mechanism that isn't integrity checked has to be http:// instead. But I might have misunderstood as I'm rather new to this discussion.

I've updated the spec so that it's (hopefully) clear that the fallback mechanism does not require the mixed-content alterations that folks are concerned about.
 
 
I mean, we can discuss this in depth and figure out the whole security story, but my goal in continuing to try to defer this particular use case is to at the minimal set of functionality first - which the spec itself is happy to call out minimal - before we start making changes to the promises web browsers try to make to users today regarding privacy and integrity.

This is pretty reasonable criticism, thanks. I've attempted to outline such a minimal approach above.
 
 
(4) Indeed, there is experimental data evaluating the potential gains of this approach. I need to go find it again. I forget the details, but I think they weren't that impressive. JQuery is often self-hosted and stripped down, so the hit rate is less than one might imagine. Let me confirm that though (I wish GMail search worked better). That said, the gains will often be in the long-tail where less experienced developers are unaware of Google Hosted Libraries or the advantages of self-hosting a stripped down version of jQuery. And I am increasingly more concerned about long tail performance.
 
I'd love to see whatever data you've gathered in the past.

Turns out I would too. I went into GMail looking for this data, but have been unable to find much more than discussion with Steve Souders about how much of jQuery is hosted on Google Hosted Libraries. IIRC, I dropped by his and Ilya's office to chat with this about this, web perfy stuff in general, and the meaning of life, but there is no record of the actual substance of that chat, so I have no interesting data to share other than vague recollections which I think you can safely ignore. We can also /summon souders and igrigorik to see if they remember. But I think you're best off gathering data on your own.


It's a bit chicken-and-egg, isn't it? Current best-practice creates conditions in which this kind of caching is less effective than it could be. For example, if content-based caching existed, developers might have more incentive to split out the libraries from the rest of their code, and to use The Canonical Version rather than stripping things down.

That's only true if the primary thing you're looking to save is network byte transfer / time. But from a web perf standpoint, self-hosting can be better in *some* (don't generalize too much from this, despite my verbose explanation) situations because parsing a huge blob of jQuery rather than the stripped down individual module you need is significantly more computationally expensive, especially on mobile where it's a non-trivial portion of page load time. In mobile web perf, you have to balance all the local resources (CPU, disk I/O for caches, network, etc) since they're all potentially the bottleneck, so a pure caching win does not necessarily translate into better performance. Now, folks (jochen?) are looking at whether or not we can cache the v8 parsed script representation (the ASTs) to save on a lot of the CPU time, but we're not there yet, and it just adds more flexibility/variables into how to schedule work for optimal performance.

I will stop pretending to know anything about perf. :)

If we do content-based caching at some point after working through the general concerns, my claim is only that it would be a speed-bump over the specific cases where we would have missed the URL-based cache for content that we've already downloaded. Since we have a URL-based cache, that speed-bump seems valuable. I have no numbers to back up any of that, which is why I'm sending this email in the first place. :)
 


I'm also concerned about the privacy implications here from being able to, compute a digest from a 3rd party origin's resource, and use that as the integrity metadata to see if that site has been visited before, without even necessarily visiting the website. I'm no privacy expert, so I defer to others as to whether or not this is a serious issue.

This is certainly something to be concerned about. We try to mitigate the risk with the recommendations in http://w3c.github.io/webappsec/specs/subresourceintegrity/#recommendations-1 Suggestions for and critique of this section of the spec would be very much appreciated.

I missed this section in an earlier pass. I think the CORS restriction in particular mitigates this privacy concern greatly.

I'm not sure I fully understand why you feel CORS reduces it. Is it because you believe not a lot of resources are wide-open with CORS like this?

Joel pointed out to me that CORS headers are already used out in the while without the expectation that we'd add this semantic here. So yes, adding this additional policy semantic might be problematic. I had not previously considered that. But if we were talking about something that didn't already have existing use, I don't think it would be problematic, except potentially as a footgun. But if an origin server has to opt-in to allow their users to leak browsing history of that origin, that strikes me as a reasonable mitigation. But I do agree that it's problematic if we reuse a previous opt-in signal in a way that was not previously intended, thus breaking backwards compat with previous privacy expectations.


I'm also not sold on the SHA-512 (why not SHA-256? Or SHA-384?) It doesn't feel like the spec really deals with the substance of the security concerns here.

This point was a misguided attempt to make it more difficult for an attacker to poison the content-based cache by creating an intentional collision with some widely-used resource. It was later pointed out to me that an attacker sufficiently advanced to create a malicious JS file that collided with jQuery would probably have broken most of the web's security in the process. So... maybe we can drop this restriction. :)
 

The goal of the attacker is to passively probe whether or not you have a given resource cached. The hash of the resource they are targeting is known. Thus the strength of the hash doesn't matter here.

For example, couldn't I programmatically exploit this by creating an img with a .src of a Blob/Data URI, set the .integrity attribute to the hash of what I want to probe for, and then inject into the DOM? There is no network traffic, I can ensure the Blob URI doesn't match the integrity attribute (thus always fails). However, IF the user has the resource cached in the content-address cache, the resource embedding will succeed - thus revealing where the user had been.

I agree with you that this attack would be possible. I disagree that it would be new.

If a resource is served with`Access-Control-Allow-Origin: *`, it's explicitly public, and explicitly removes the usual same-origin restrictions. It is available to anyone and everyone via XHR. Determining whether such a resource at a specific URL has been cached is a fairly accurate timing attack.

I'm not at all saying that this sort of caching mechanism is a slam-dunk. It raises real questions about origin-based restrictions (like canvas tainting, CSP, etc).

Fortunately(?), I think these questions are all actually _more_ pressing for Service Workers, which we're already running ahead with. :)

  
(1) I think missing in this explanation is that, even if you trust a CDN to be well-intentioned, it is still vulnerable to compromise. SRI would help mitigate that.

I agree. We mention that in the spec, but I neglected to spell out that threat here.

-mike


Absent both caching and mixed-content - both of which I think need more fleshing out - I'm quite mixed on the value here.

If it's a script you know about/control, you can obviously host it locally (eg: not on the CDN). As Will mentions, there are many times where doing so can actually *improve* performance, compared to just throwing the whole-dang-library together.

If it's a script you don't control - which is commonly the case for the analytics scripts that seem to be the risk the editors' are concerned about - it implies that the CDN/analytics provider is versioning their resources, and that site operators can review these versions, and whitelist the hash. Except the CDNs aren't - they frequently change - and so instead we're just encouraging a more broken web. The further insult is that "broken web" is exactly a use case being striven for (The Section 1.2.1 "mashup" example)

I think we phrased it slightly differently, by focusing on the fact that authors would have the ability to opt-in to pinning a resource with content they'd reviewed.

Moreover, it would be possible to use this feature to support a review process without breaking anything. If integrity validation is performed in report-only mode, authors would be notified when resources unexpectedly change (or when users are being served different resources than the author expected (perhaps because the provider has been compromised, and is serving malicious code to everyone but the author's IP range)), without actually blocking the content.

You expressed some reservations with a report-only approach, but we didn't get a chance to get into a detailed discussion of what negative impacts it might have.
 

If anything, I expect CDNs/analytics would be *opposed* to this change - not because of the security benefits, but because of the massive support hurdles. My anecdata is that very few analytics firms (eg: http://w3c.github.io/webappsec/specs/subresourceintegrity/#use-cases-examples ) actually version their analytics scripts.


We should only do this if there are clear security (without sacrificing performance) wins or performance (without sacrificing security) wins. Of these, the only "Use Case" that strikes me as meeting the criteria of clear wins in *either* category is the "Injecting Active Content" analytics example, which arguably can be used to improve security. The rest seem social issues whose "real" solution is non-technical, or which require much further specification/review/discussion (mixed-content, caching).

I'll attempt to summarize this in a way that makes my position sound better: "The core of the specification improves security by blocking unexpected active content, but I'm concerned about the performance impact, and think it might annoy analytics and widget providers. I'm very much against the mixed-content bits, and think that the caching bits need a lot more thought."

Is that at all accurate?
 

For the analytics case, it seems like if site operators *really* are concerned about that, there are other technical solutions
 - Moving the analytics 'dynamic' code to an iframe, communicated with via a static, non-CDN'd JS file in the main document
 - Hosting the analytics JS locally
 - Exploring the Service Worker route

You've mentioned the analytics case a number of times. I agree with your analysis there. What do you think about the jQuery case? jQuery is indeed versioned on CDNs, like Google Hosted Libraries. It seems to me that there is a non-zero security win for integrity protecting jQuery to insulate against CDN compromise (or outright malicious behavior, of which I'm more skeptical). I don't know if I think this security win is big, but I think that the non-incremental integrity mechanism is fairly cheap.

-mike 

Ryan Sleevi

unread,
Mar 27, 2014, 7:06:37 PM3/27/14
to Mike West, William Chan (陈智昌), Ryan Sleevi, blink-dev, Joel Weinberger, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
On Thu, Mar 27, 2014 at 2:30 AM, Mike West <mk...@google.com> wrote:
Before diving into the detail, let's say that I modify the intent to implement to something super minimal. Based on the discussion here, it sounds like Will would be interested in (and Ryan wouldn't be actively against) the following:

1. Add `integrity` attributes for a bunch of elements.
2. Use those attributes to verify the resource before rendering it.
3. Add a CSP directive to set the document's response to a verification failure (which I forgot to mention before, sorry).
4. Nothing else.
5. Certainly not touching mixed-content, fallback, caching, etc.
6. No, really. None of that.
7. I mean it.

This would provide a mechanism for authors to opt-in to a security win of some unknown size (let's say it's _huge_, because that would make me feel better), at the cost of blocking rendering until the resource is validated. Implementing this subset would allow us to determine exactly what that performance impact is, and also allow us to determine whether any of this makes sense on the web as it exists today (see Chris' concerns about transcoding proxies).

WDYT?

Hah, I think it will be _minor_ to _negligible_ (compared to alternatives), but that's what experimentation is all about ;)

Only question is that there seems to be a large compatibility risk ( http://www.chromium.org/blink#compatibility ), but the only way you'll get the data you want seems to be if you ship. Is that correct?

If it's behind experimental web features, then yeah, sure, let's experiment and see how ugly it turns out to implement, and how that can be used to improve the spec. Will suggests that I have a far too rosy view of how Resource Loading works in Blink, and so the performance degradation may be minimal compared to our already existing missed-opportunities.
 
<snip>
 
 

If anything, I expect CDNs/analytics would be *opposed* to this change - not because of the security benefits, but because of the massive support hurdles. My anecdata is that very few analytics firms (eg: http://w3c.github.io/webappsec/specs/subresourceintegrity/#use-cases-examples ) actually version their analytics scripts.


We should only do this if there are clear security (without sacrificing performance) wins or performance (without sacrificing security) wins. Of these, the only "Use Case" that strikes me as meeting the criteria of clear wins in *either* category is the "Injecting Active Content" analytics example, which arguably can be used to improve security. The rest seem social issues whose "real" solution is non-technical, or which require much further specification/review/discussion (mixed-content, caching).

I'll attempt to summarize this in a way that makes my position sound better: "The core of the specification improves security by blocking unexpected active content, but I'm concerned about the performance impact, and think it might annoy analytics and widget providers. I'm very much against the mixed-content bits, and think that the caching bits need a lot more thought."

Is that at all accurate?
 
<snip>

Yes. 

j...@google.com

unread,
Sep 23, 2014, 7:14:21 PM9/23/14
to blin...@chromium.org, mk...@google.com, will...@chromium.org, rsl...@chromium.org, j...@google.com, viv...@chromium.org, scary...@gmail.com, sligh...@chromium.org, jyas...@chromium.org, mn...@mnot.net, sle...@google.com
Just an update that my initial implementation of SRI *only* for secure hosts to secure resources (and only for scripts) just landed: https://codereview.chromium.org/566083003/. I plan on adding in style tag support soon, as well as console error messages.
--Joel

Joel Weinberger

unread,
Sep 23, 2014, 7:17:22 PM9/23/14
to Ryan Sleevi, Mike West, William Chan (陈智昌), Ryan Sleevi, blink-dev, Vivek Galatage, scarybeasts, Alex Russell, Jeffrey Yasskin, Mark Nottingham
Just an update that my initial implementation of SRI *only* for secure hosts to secure resources (and only for scripts) just landed: https://codereview.chromium.org/566083003/. I plan on adding in style tag support soon, as well as console error messages.
--Joel
Reply all
Reply to author
Forward
0 new messages