hacktricks/pentesting-web/http-request-smuggling/browser-http-request-smuggling.md
2022-08-21 22:53:18 +00:00

11 KiB

Browser HTTP Request Smuggling

Support HackTricks and get benefits!

Do you work in a cybersecurity company? Do you want to see your company advertised in HackTricks? or do you want to have access the latest version of the PEASS or download HackTricks in PDF? Check the SUBSCRIPTION PLANS!

Discover The PEASS Family, our collection of exclusive NFTs

Get the official PEASS & HackTricks swag

Join the 💬 Discord group or the telegram group or follow me on Twitter 🐦@carlospolopm.

Share your hacking tricks submitting PRs to the hacktricks github repo.

CL.0/H2.0 browser-compatible desync

This vulnerability occurs when the Content Length (CL) header is being completely ignored by the backend server. Then, the back-end treats the body as the start of the second request's method. Ignoring the CL is equivalent to treating it as having a value of 0, so this is a CL.0 desync - a known but lesser-explored attack class.

The attack was possible because the back-end server simply wasn't expecting a POST request.

{% hint style="warning" %} Note that this vulnerability is being triggered by a completely valid, specification-compliant HTTP request. This meant the front-end has zero chance of protecting against it, and it could even be triggered by a browser. {% endhint %}

The only difference between CL.0 and H2.0 is that the second one is using HTTP2 (which has an implicit content-length header) but the backend isn't using that either.

Client-Side Desync

Traditional desync attacks poison the connection between a front-end and back-end server, and are therefore impossible on websites that don't use a front-end/back-end architecture. These are server-side desync from now on. Most server-side desyncs can only be triggered by a custom HTTP client issuing a malformed request.

The ability for a browser to cause a desync enables a whole new class of threat called client-side desync (CSD).
A CSD attack starts with the victim visiting the attacker's website, which then makes their browser send two cross-domain requests to the vulnerable website. The first request is crafted to desync the browser's connection and make the second request trigger a harmful response, typically giving the attacker control of the victim's account.

Detect

A CSD vector is a HTTP request with two key properties.

First, the server must ignore the request's Content-Length (CL). This typically happens because the request either triggered a server error, or the server simply wasn't expecting a POST request to the chosen endpoint. Try targeting static files and server-level redirects, and triggering errors via overlong-URLs, and semi-malformed ones like /%2e%2e.

Secondly, the request must be triggerable in a web-browser cross-domain. Browsers severely restrict control over cross-domain requests, so you have limited control over headers, and if your request has a body you'll need to use the HTTP POST method. Ultimately you only control the URL, plus a few odds and ends like the Referer header, the body, and latter part of the Content-Type.

CL ignore testing

The way to test this missconfig is to send 2 requests and smuggle one in the middle. If the smuggled connection affected the response of the second request, it means that it's vulnerable:

{% hint style="warning" %} Note that you cannot test this vuln by just sending a Content-Length bigger than the one sent and looking for a timeout because some servers respond even if they didn't receive the whole body. {% endhint %}

It's important to note whether the target website supports HTTP/2. CSD attacks typically exploit HTTP/1.1 connection reuse and web browsers prefer to use HTTP/2 whenever possible, so if the target website supports HTTP/2 your attacks are unlikely to work. There's one exception; some forward proxies don't support HTTP/2 so you can exploit anyone using them. This includes corporate proxies, certain intrusive VPNs and even some security tools.

Confirm

First, select a site to launch the attack from. This site must be accessed over HTTPS and located on a different domain than the target.

Next, ensure that you don't have a proxy configured, then browse to your attack site. Open the developer tools and switch to the Network tab. To help with debugging potential issues later, I recommend making the following adjustments:

  • Select the "Preserve log" checkbox.
  • Right-click on the column headers and enable the "Connection ID" column.

Switch to the developer console and execute JavaScript to replicate your attack sequence using fetch(). This may look something like:

fetch('https://example.com/', {
  method: 'POST',
     body: "GET /hopefully404 HTTP/1.1\r\nX: Y", // malicious prefix
     mode: 'no-cors', // ensure connection ID is visible
     credentials: 'include' // poison 'with-cookies' pool
}).then(() => {
     location = 'https://example.com/' // use the poisoned connection
})

I've set the fetch mode 'no-cors' to ensure Chrome displays the connection ID in the Network tab. I've also set credentials: 'include' as Chrome has two separate connection pools - one for requests with cookies and one for requests without. You'll usually want to exploit navigations, and those use the 'with-cookies' pool, so it's worth getting into the habit of always poisoning that pool.

When you execute this, you should see two requests in the Network tab with the same connection ID, and the second one should trigger a 404:

If this works as expected, congratulations - you've found yourself a client-side desync!

Exploitation - Store

One option is to identify functionality on the target site that lets you store text data, and craft the prefix so that your victim's cookies, authentication headers, or password end up being stored somewhere you can retrieve them. This attack flow works almost identically to server-side request smuggling, so I won't dwell on it.

Exploitation - Chain&pivot

Under normal circumstances, many classes of server-side attack can only be launched by an attacker with direct access to the target website as they rely on HTTP requests that browsers refuse to send, like tampering with HTTP headers - web cache poisoning, most server-side request smuggling, host-header attacks, User-Agent based SQLi, CSRF JSON Content-type and numerous others.

The simplest path to a successful attack came from two key techniques usually used for server-side desync attacks: JavaScript resource poisoning via Host-header redirects, and using the HEAD method to splice together a response with harmful HTML. Both techniques needed to be adapted to overcome some novel challenges associated with operating in the victim's browser.

Exploit Examples

Stacked HEAD example

  • Coloured exploit

  • JS exploit
fetch('https://www.capitalone.ca/assets', {
    method: 'POST',
    
        // use a cache-buster to delay the response
        body: `HEAD /404/?cb=${Date.now()} HTTP/1.1\r\nHost: www.capitalone.ca\r\n\r\nGET /x?x=<script>alert(1)</script> HTTP/1.1\r\nX: Y`,
        credentials: 'include',
        mode: 'cors' // throw an error instead of following redirect
}).catch(() => {
        location = 'https://www.capitalone.ca/'
})va

Explanation:

  • Abuse of CL.0 in /assets (it redirects to /assets/ and doesn't check the CL)
  • Smuggle a HEAD request (because HEAD responses still contains a content-length)
  • Smuggle a GET request whose content is going be reflected in the response with the payload.
    • Because of the content-length of the HEAD req, the response of this request will be the body of the HEAD req
  • Set cors mode. Normally this isn't done, but in this case the response of the server to de initial POST is a redirect that if followed the exploit won't work. Therefore, cors mode is used to trigger an error and redirect the victim with the catch.

Host header redirect + client-side cache poisoning

References

Support HackTricks and get benefits!

Do you work in a cybersecurity company? Do you want to see your company advertised in HackTricks? or do you want to have access the latest version of the PEASS or download HackTricks in PDF? Check the SUBSCRIPTION PLANS!

Discover The PEASS Family, our collection of exclusive NFTs

Get the official PEASS & HackTricks swag

Join the 💬 Discord group or the telegram group or follow me on Twitter 🐦@carlospolopm.

Share your hacking tricks submitting PRs to the hacktricks github repo.