Hacker News new | ask | show | jobs
by ryan-c 3924 days ago
This is to prevent files on a 3rd party CDN from being loaded if they've been replaced with malicious ones.
2 comments

Ah, I see. I misunderstood. Though signatures seem to be just adding another part in the deployment process where you update the files themselves as well as the pages they're loaded from.

Is there any security gain from doing that?

If you include content produced by a third party (e.g. JQuery) off a CDN, right now you can use the hash-based SRI mechanism to make sure that only the exact file you specified can be included, otherwise the CDN could suddenly send any compromised code. The file can't be changed, because otherwise the hash wouldn't match.

With a signature, you could specify "include cdn.com/jquery-X if signed by the JQuery project", so JQuery could publish security updates and those could be rolled out to the CDNs and included in all pages automatically, without the siteowners having to make changes (if the security fix doesn't break compatibility).

For your own content, you'd mostly gain the convenience of not having to update the hashes on all the pages including the resource.

This is more convenient but less secure than a straight-up hash. If an attacker compromises the JQuery signing key, they could still serve malicious files. With a hash, the authenticity is ONLY dependant on the TLS connection to the main website, e.g. github.

TL;DR:

* hash: need to compromise the main website, that supplies (and authenticates) the hash

* signature by CDN: attacker can either compromise the main website OR <del>the third party CDN</del> <ins>author/signer of the third-party resource</ins>

(edit: correction as pointed out by response)

It would still help against compromise of the CDN, but not against compromise of the original source.

Of course it's a trade off. For stuff like Google Fonts, the Facebook like button etc I'd expect that hashes won't become common, because the effort of publishing changed hashes and embedding them into sites is to big.

Yes, it's nominally less secure but I trust the authors of major scripts (ex. the Facebook like button) to be able to keep their keys secure. If losing private keys is a major security concern, then TLS is also useless.
It's not "nominal"; losing private keys is a major security concern. No, "TLS is useless" does not follow from that - we have things like forward secrecy which are security models specifically designed to give some protection in the case of private key compromise.

(edit: e.g. see https://en.greatfire.org/blog/2015/sep/popular-chinese-ios-a... just out today)

Especially in the case of a library developer, they hold the keys to many websites, so there is extra incentive for an attacker to break that rather than "some random guy's website". The more third-party signers you trust, the more holes you (and your users) have.

Furthermore, you are forcing your users (who actually run this code) to place their trust in these parties too, which is not a great thing (transitive trust) to force upon someone. (This is not the case for e.g. depending on system libraries explicitly installed by the user.)

A content hash is good enough. The trusted hash is sent over an already trusted channel (TLS).

Thanks for the downmods.

The point is that with a signature you wouldn't have to change all the pages including the resource, but just sign the updated resource with the same key.
It's just a semantic question. Does a URL point to a specific version of a resource or does it point to whatever the server considers to be the resource at a given time.

It would seem more desirable to be able to point to a specific version, instead of allowing a third party to be able to insert implicitly trusted code without acknowledgement.

You're separating which third party can do that, which is useful. I don't think it's at all unusual or wrong for me to decide that, if I'm using minified jQuery, I trust the jQuery project signing key, but I don't really trust whatever CDN I'm using (or that I want the freedom to choose a CDN solely for technical performance and not for security infrastructure).

If that's not convincing, consider the case where it's my own JS. I don't trust myself to run a CDN; I don't trust a CDN with the ability to modify my code. This allows me to build a single-page app that has ridiculously long cache lifetimes (so my own server load is low), and hand the actual, changing code off to a CDN, but verify my own signature on the data.

If that's not convincing, consider that data signing keys can generally be kept on non-internet-facing machines (and you can airgap, use a HSM, whatever), but performant SSL implementations by definition have to have their private key be in memory on an internet-facing server.

That is all fine and it would cover many cases. However, someone other than you is still able to push code to your users without your acknowledgement (assuming you have trusted a third party key).

If you are already using a CDN, put your updated manifest (index.html) there as well.

> However, someone other than you is still able to push code to your users without your acknowledgement (assuming you have trusted a third party key).

Yes, I want that. I just want to control which third parties I trust. That's why it's called a "trusted third party", not just a "third party."

> If you are already using a CDN, put your updated manifest (index.html) there as well.

I'm not sure how this helps. Wouldn't this leave the index.html in the hands of the CDN, such that they are free to modify it?

But if you need to sign updates, a third party CAN'T insert new code without it going through the site owner or a trusted party (e.g. new jQuery versions signed by the jQuery project). And it would seem desirable to be able to roll out a security fix without having to touch every single page that includes it (and the potential cache issues discussed above)
You can create similar semantics. The only difference is in who controls what code goes to your users.

I'd consider jQuery a third party. If only signatures are checked (and not content), then trusted third parties can push whatever code they'd like to your users.