Cross Site Request Forgery (CSRF)
Making a request on the user's behalf.
Overview
If a website automatically sends a user's credentials when you interact with it (cookies are sent automatically), then CSRF can be used to impersonate the user (assuming the website doesn't do anything to prevent it).
Common CSRF Payloads
Different types of endpoints require different techniques:
POST
GET
DELETE/UPDATE
JSON endpoint
XML endpoint
POST
Make a POST form with hidden inputs and use JavaScript to send the POST request automatically when the user navigates to the page.
GET
Make an image with zero width and length and src=
the_csrf_Link
. The GET request is made automatically when the browser tries to load the image.
PUT/DELETE
This one is very difficult. Can only be accomplished with like browser plugins/plugin vulns and stuff.
JSON
You can try to do a CSRF request to a JSON API endpoint.
Caveats (as of august 2021):
The server must not require content-type: application/json in the headers. The method results in a request with a content-type: text/plain header
This method results in one of the fields in the JSON request being
"foo":"="
. In other words, the server must not deny the request because of an unexpected field, or an expected field with the value=
The SameSite cookie attribute must not be Strict
It defaults to Lax on browsers
In Firefox, it always works when SameSite has not been set
Haven’t tested when SameSite has been explicitly set to Lax
In Chrome, it works when SameSite has not been set
But only for two minutes, starting from the time the cookie was assigned to the user
Probably won’t work if SameSite has been explicitly set to Lax
Sample payload from the article. Sends a JSON request to the okcupid API:
Zseano also talked about it in his blog article. Here's his payload (but his is older):
XML
From Zseano's blog:
Login CSRF
Many developers tend to ignore CSRF vulnerabilities on login forms. They assume that CSRF would not be applicable on login forms because the user is not authenticated at that stage. However, CSRF vulnerabilities can still occur on login forms where the user is not authenticated, but the impact and risk is different.
For example, if an attacker uses CSRF to authenticate a victim on a shopping website using the attacker's account, and the victim then enters their credit card information, an attacker may be able to purchase items using the victim's stored card details
Mitigations
OWASP Prevention Cheat Sheet
SameSite
The default option for SameSite these days is Lax, which stops a lot of CSRF requests (cookies aren't sent with POST requests from other domains).
The web application is still vulnerable if:
It does something sensitive in response to a GET request -- cookies are still sent along with GET requests if the user navigates to the site.
The CSRF comes from a subdomain. For example, pages.github.com can still CSRF github.com.
Mitigation Bypasses
Chrome Default SameSite Lax+POST Bypass
While Chrome does set cookies to SameSite=Lax by default, for the first two minutes after the cookie was set, the policy is effectively SameSite=None. This can be used to exploit CSRF in certain cases.
CSRF Tokens
If an anti-CSRF token is added, you can bypass it with:
XSS
Steal the CSRF token (using CSS injection, for example)
Clickjacking
If you can fill in the data you want for them, and then clickjack them into hitting “submit” (through an iframe), then you can make a request on their behalf
CSRF token misconfigurations
Try a blank csrf token
Try to see if accounts can share the same CSRF token. Make 2 accounts and see if the same token works for both.
Change one character in the token, maybe it only checks length or something.
Referrer Header Checking
If the Referrer header is checked, then you can try a few things:
If
site.com/csrf
checks that "site.com" is in the string, you can send the query frommalicious.com/site.com
orsite.com.malicious.com
.Send a blank referrer header and see if that works
Use XSS (like reflected XSS) to achieve the goal.
Last updated