Subresource Integrity

If you’ve been keeping up with recent browser developments you may have noticed that in the past few weeks both Chrome and Firefox have started to support subresource integrity, with companies like Github making an active push for other sites to make use of the functionality. This is a low-risk change that offers tremendous security gains for your users, so we just pushed out an update that makes it easier to start using subresource integrity on your website.

Subresource integrity is a new browser feature that allows websites to ensure the integrity of resources loaded from external sources, such as content delivery networks (CDNs). This is a common technique used by websites to speed up the loading of assets, including common Javascript libraries like jQuery.

As is the nature of loading arbitrary code, this has always opened up websites to the possibility of being attacked through their CDN: an insecure or malicious CDN holds the potential to insert malicious code onto any website to which it serves assets. Subresource integrity serves to mitigate this attack by ensuring that all loaded resources contain the exact content expected by the website. This is done through the use of a cryptographic digest, computed on all fetched resources, that is then compared against an expected digest. This provides the browser the capability of detecting resources that have been tampered with, allowing it the opportunity to abort the loading of the resources before any malicious code is executed.

Protecting a resource is done by adding the “integrity” attribute to an asset’s HTML tag:

<script src=""

It’s an elegant solution to a very serious risk, and it’s a solution we recommend implementing. It won’t secure all of your users, with Microsoft Edge still not supporting the feature, but it can serve as a valuable line of defense in the event of a breach of your CDN. Many of the popular web frameworks provide libraries that make it easy to enable subresource integrity on your assets, and further instructions on making use of the technology are available on the Mozilla Developer Network.

Going forward, all Tinfoil Security scans will flag external resources that are not protected by subresource integrity. Give it a try by signing up for our 30-day free trial.

Quinn Wilton

Quinn Wilton is the Grand Magistrate of Security at Tinfoil Security, and the company's resident programming language theorist. When she isn't coding in a functional language like Elixir, she's probably hacking on an interpreter for an esolang of her own, or playing around with dependent types in Idris. Security is always at the forefront of her thoughts, and she enjoys building tools which make it easy for other engineers to write secure code. Her love for security is matched only by her love for bad movies - and does she ever love bad movies.

Tags: browser security security New Feature

How To Fix POODLE (And Why You’re Probably Still Vulnerable)

The internet has been in an uproar over the past few days as a result of Google’s announcement of the POODLE vulnerability, which effectively breaks SSLv3 completely. We’ve scanned every single site that has passed verification with Tinfoil Security (that is, signed up and verified ownership) using our free testing tool, and sent emails to all those customers that have vulnerable sites. Our anonymized statistics of websites that have been tested show that 68%—that is, more than two-thirds—of the internet is vulnerable as I write this.

There has been a lot of misinformation flying around the internet over the past few days, and a lot of overly technical (or not technical enough) “how to” guides that are actually incorrect. This isn’t because the internet intends to mislead, but simply because cryptography of any sort, but especially TLS/SSL, is hard. We don’t claim to be experts, but we try really hard to be well-versed. With that in mind, this is our guide on how to protect your servers and what mistakes you’ve probably (unintentionally) made.

How Everyone Is Messing Up Cipher Disabling

The simplest thing to think is “OK, so it looks like if I disable any cipher suite that has CBC in the name, I’ll be fine.” This is wrong, and everyone is doing it, because it is what everyone is recommending.

There are a number of cipher suites, specifically AES128-SHA, AES256-SHA, and similar, that do not contain CBC in the OpenSSL cipher suite name. In reality, these cipher suites are named TLS_RSA_WITH_AES_128_CBC_SHA and TLS_RSA_WITH_AES_256_CBC_SHA, respectively. These cipher suites do work in CBC mode, no matter what OpenSSL chooses to call them!

We’ve disclosed this exact vulnerability to many companies at this point, including some large, extremely engineering-focused companies I guarantee you've heard of, all of whom have mitigated it now by disabling these last few ciphers. Given that we continue to see this exact mistake across most of the websites we’re testing, you should make sure you check it on yours too.

Your best option

Disable SSLv3 completely. Do not support it as a protocol at all, and reject any clients which require it. Unfortunately, this proves hard to do for many companies, as they have legacy clients whom they need to support that only support SSLv3 (specifically, IE6 on Windows XP and older Android clients, usually).

Our recommendation is simple: if, in any way, you can completely disable support for older clients that require SSLv3 and disable support for that protocol entirely, please do it.

Your next best option

If you must maintain support for SSLv3, your next best option is to enable the TLS_FALLBACK_SCSV cipher suite value. This cipher is a patch submitted to OpenSSL by Google (the same guys who found the exploit in the first place). This cipher solves the issue of retrying failed connections, thus preventing attackers from forcing browsers to use SSLv3. Additionally, it may also help prevent future exploits, as it prevents downgrading from TLS 1.2 to 1.1 or 1.0 as well.

Our recommendation: Make sure that you support the TLS_FALLBACK_SCSV cipher suite value. If you use OpenSSL 1.0.1, make sure you upgrade to 1.0.1j. Similarly, if you use 1.0.0, make sure to upgrade to 1.0.0o, and if you use OpenSSL 0.9.8, upgrade to 0.9.8zc.

Your last resort

If you cannot disable SSLv3, and if you cannot upgrade OpenSSL to support TLS_FALLBACK_SCSV for some reason, you have one additional option left: carefully disable all cipher suites for SSLv3 that run in CBC (cipher-block chaining) mode. Really, you should do this anyway, since TLS_FALLBACK_SCSV doesn’t actually resolve POODLE for anybody using SSLv3, it just prevents any newer clients from downgrading to SSLv3 and thus becoming vulnerable, limiting the number of clients that are affected.

This means that if you have to use SSLv3, your only real option left is to use some form of an RC4 cipher. This also isn’t perfect (there is a known attack on it by way of Royal Holloway, but it requires 224 connections), but is better than using any of these CBC ciphers which can be broken much faster.

If your configuration doesn't allow you to disable these CBC ciphers only for SSLv3 (for example, if you run nginx), you should consider using something like HAProxy to terminate SSL traffic in front of it and disabling / redirecting around it there. This, however, is hard and prone to error so you can go with the next recommended option: make sure your preferred cipher is set to RC4, rather than any CBC cipher.

Our recommendation: The following cipher suites that SSLv3 is able to use must be disabled in order to effectively prevent POODLE:


Check, and check again.

We’ve been updating our tester constantly and improving its detection and results. We’ve added even more information regarding supported ciphers and the like. When you think you’ve fixed your server against POODLE, you should run another check.

We will continue to keep our eyes on this and attempt to update this post with more ways companies are making common mistakes in mitigating this attack, but if you follow the above directions, you should be OK. Scan yourself for even more vulnerabilities using the button below.

Feel free to chat with us or email us at any time.

Michael "Borski" Borohovski

Michael Borohovski is cofounder and CTO at Tinfoil Security. He got his start in security when he was just 13 years old, and has been programming for longer than he can remember. When he's not busy breaking software or building it, he also loves singing, juggling, and magic tricks. Yes, magic tricks.

Tags: browser security SSL poodle 0day

Building A Browser Extension? Be Careful Not To Accidentally XSS the Whole Internet.

Update/TL;DRIf you didn’t generate it, assume it’s malicious.

Sometimes, the state of your website’s security can be affected by resources and services outside your control. The topic of today? Browser extensions.

Recently, we disclosed a vulnerability to a well-known company (let’s refer to them as Company) in their browser extension (specifically, in Chrome). To their credit, Company responded rapidly and fixed the issue within 2 days - major props to them for responding so quickly. Before we get into the vulnerability, let’s talk a little about what the extension does.

Chrome extensions? Not much harm can come from that...

From the Company’s feature description, the browser extension automatically takes content you want to share and pops it into a message, ready to go. This sounds great! And for the most part, it is. Occasionally, though, we are reminded that extensions can be dangerous, and now is one of those times. Browser extensions are effectively allowed to run any arbitrary JavaScript they’d like on any page you visit, changing the DOM at will. In Company’s case, they were trying to make their customers’ lives easier by finding any text that looked like a Twitter hashtag or Twitter handle and converting it into a clickable link that automatically searches for that hashtag or handle. Well-intentioned, as is most of what we do as software engineers.

Sounds great. So where’s the vulnerability?

The vulnerability boils down to the following: if a page had a hashtag in its content that, as part of the hashtag, had an HTML-escaped element appended, it would get unescaped and then, by definition, inserted directly into the DOM by Company’s browser extension. Consider the following example:


If this showed up in the text of a page, the extension noticed the #tinfoil hashtag and attempted to convert it into a link. So the above became something like the following:

 <a class="_company_extension" a="" href="#" #tinfoil"="" "javascript:var e = document.createEvent(&quot;CustomEvent&quot;); e.initCustomEvent(&quot;extensionEvent&quot;, true, true, {type: &quot;hash&quot;, value: &quot;#tinfoil&quot;}); document.body.dispatchEvent(e); return false;">#tinfoil</a><script>alert('XSS'​)</script>

You’ll notice that this is malformed HTML to begin with (the #tinfoil attribute of the a tag, for example), but the more important issue is that the Company’s browser extension actually unescapes the escaped HTML for the script tag and, in doing so, inserts it into the DOM. Of course, the link still works, pulling up a search for #tinfoil as it should, so if we weren’t popping up an alert box, the user would be none the wiser.

Uh what does this mean for me?

Well, effectively this means that if you were using the Company’s browser extension within Chrome, it would execute any malicious JS stored on any website you were visiting. For example, suppose you were logged into a financial service and viewing the discussion forums for help on a topic - someone could have posted this malicious hashtag in response creating a persistent, or stored, XSS. Worse is that even if said financial service had taken the proper precautions to prevent XSS by escaping HTML into its HTML entities (as we recommend), the Company’s browser extension would still have re-encoded it and run the malicious JavaScript. Essentially, Company had accidentally XSS’d the whole internet.

Okay. So what can we learn from this?

User generated content occurs everywhere, and it is always important to escape any input you may receive. The mantra we often use is: “If you didn’t generate it, assume it’s malicious.” In this case, the document returned by the website the user is visiting should be considered potentially malicious. The extension is acting on data it did not create, and as such should treat it more carefully than it would other data, by escaping everything it can. So if you’re building a browser extension, be sure to treat the DOM of whatever page you’re modifying as dangerous, because it is.

We love to talk about these sorts of issues, so feel free to chat with us via email or in our support chat. :)

Michael "Borski" Borohovski

Michael Borohovski is cofounder and CTO at Tinfoil Security. He got his start in security when he was just 13 years old, and has been programming for longer than he can remember. When he's not busy breaking software or building it, he also loves singing, juggling, and magic tricks. Yes, magic tricks.

Tags: XSS browser extensions browser security chrome google google chrome security