CSP Bypass via iFrame Scripting
Categories
(Core :: DOM: Security, defect)
Tracking
()
People
(Reporter: telavivkeller, Unassigned)
Details
(Keywords: reporter-external, Whiteboard: [reporter-external] [client-bounty-form] [verif?])
Attachments
(1 file)
1.54 KB,
application/zip
|
Details |
Content Security Policy (CSP) serves as a security mechanism for web applications, primarily aimed at mitigating cross-site scripting (XSS) attacks. However, scripting in iFrames is still allowed, even scripting on CSP enforced same-origin parents/children.
This vulnerability stems from the ability of iframes with the same origin as the parent page to execute scripts within the parent's context, irrespective of CSP blockings. The technical process involves:
- Embedding an iframe within the parent page, sharing the same origin.
- Loading scripts within the iframe that would typically be blocked by CSP if loaded directly onto the parent page.
- Exploiting the execution context of the parent page to carry out malicious actions through scripts within the iframe.
The exploitation of CSP bypass via iframes can have significant repercussions:
- XSS Attacks: Malicious scripts executed within the parent page's context can lead to data theft, session hijacking, or unauthorized access to sensitive information.
- Content Injection: Attackers can inject malicious content into the parent page, such as phishing forms or deceptive advertisements, eroding user trust and damaging the application's integrity.
- Data Exfiltration: By leveraging CSP bypass, attackers may exfiltrate sensitive user data accessible within the parent page to external servers, resulting in privacy violations and regulatory compliance issues.
For the PoC, host it at localhost:3000 and visit index.html
. From there, notice that a variable declared in init.js
for index.html
is accessible from iframe.html
, despite the anti-scripting CSP in place.
Reporter | ||
Comment 1•1 year ago
|
||
Keep in mind this also works for frame children (this is probably a bigger impact), see
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Test #2</title>
</head>
<body>
<iframe src="index.html"></iframe>
<script>window.onload = () => { alert(window.frames[0].secret)}</script>
</body>
</html>
Comment 2•1 year ago
|
||
That's not what CSP blocks. CSP blocks the parsing of script (allowed by unsafe-inline) and the evaling of strings into script (allowed by unsafe-eval), but it does not block the actions of script that has already been allowed to run. The same origin policy allows scripting across frames, and CSP does not block that (unless you use the CSP or iframe "sandbox")
Reporter | ||
Comment 3•1 year ago
|
||
Scripting inside an iFrame is OK, but the iFrame shouldn't be able to script in the context of the CSP enforced parent/child.
If a window has scripting disallowed, a same-origin frame shouldn't be allowed to script in it.
Reporter | ||
Comment 4•1 year ago
|
||
The behavior that I am specifically concerned about is that the iFrame, while allowed to script, should not be allowed to script on the CSP-blocked parent window.
Examples from DevTools
From Parent
window.eval("window.secret");
Uncaught EvalError: Refused to evaluate a string as JavaScript because 'unsafe-eval' is not an allowed source of script in the following Content Security Policy directive: "script-src http://localhost:3000/init.js".
From Child
window.eval("window.top.secret")
"Nooo, don't read me!"
window.top.eval("window.secret")
Uncaught EvalError: Refused to evaluate a string as JavaScript because 'unsafe-eval' is not an allowed source of script in the following Content Security Policy directive: "script-src http://localhost:3000/init.js".
As you can see, window.top.*
can be accessed and executed from the child frame. Anything window.eval can do can be done, except for eval
itself.
The same way that <iframe srcdoc="<script>console.log(window.top.secret)</script>"></iframe>
is blocked (via unsafe-inline
), so should an iFrame to same-source script be blocked from accessing the parent.
Comment 5•1 year ago
|
||
I can see the model you're describing, but that's not what the spec says and browsers are currently compatible on this behavior
Comment 6•1 year ago
|
||
The two windows are same-origin so DOM access should be granted according to the same-origin policy. If you want to prevent access from either of the two sides, you should make use of <iframe sandbox>
or the sandbox
CSP attribute.
Updated•10 months ago
|
Description
•