CVE-2026-55766 Overview
CVE-2026-55766 is an HTTP header injection vulnerability in guzzlehttp/psr7, a widely deployed PSR-7 HTTP message library implementation in PHP. Versions prior to 2.12.1 fail to reject carriage return and line feed (CR/LF) characters in three first-party HTTP start-line fields: the request method, protocol version, and response reason phrase. Applications that place attacker-controlled data into these fields and later serialize the PSR-7 message as raw HTTP/1.x can emit attacker-controlled header lines. The flaw is classified under CWE-93 (Improper Neutralization of CRLF Sequences).
Critical Impact
Attackers can inject arbitrary HTTP headers into serialized messages, enabling request smuggling, cache poisoning, or downstream header manipulation when the malformed output is written to the network.
Affected Products
- guzzlehttp/psr7 versions prior to 2.12.1
- PHP applications using Message::toString() or equivalent serializers on attacker-controlled fields
- Applications consuming Message::parseRequest() or Message::parseResponse() and re-serializing parsed objects
Discovery Timeline
- 2026-06-23 - CVE-2026-55766 published to NVD
- 2026-06-23 - Last updated in NVD database
Technical Details for CVE-2026-55766
Vulnerability Analysis
The guzzlehttp/psr7 library implements PHP's PSR-7 HTTP message interface. Prior to version 2.12.1, the library validated header names and values for CRLF sequences but did not apply the same validation to start-line fields. Specifically, the request method, HTTP protocol version, and response reason phrase accepted raw \r\n byte sequences.
When a PSR-7 Request or Response object containing CRLF in these fields is serialized via Message::toString(), the resulting raw HTTP/1.x message contains injected header lines. Receiving software that does not independently reject the malformed start line will parse the injected lines as legitimate headers.
The vulnerability is reachable through two paths: direct construction of PSR-7 objects with attacker-controlled values, and parsing of malformed raw messages via Message::parseRequest() or Message::parseResponse() followed by re-serialization.
Root Cause
The library's start-line construction logic concatenates field values into the serialized output without filtering CR (0x0D) or LF (0x0A) bytes. PSR-7 header validation routines were not extended to start-line components, leaving these fields as the sole injection surface.
Attack Vector
Exploitation requires three conditions: an application must place attacker-controlled data into the method, version, or reason-phrase field; the PSR-7 message must be serialized to raw HTTP; and the output must be transmitted over the network, forwarded to a proxy, or replayed to a backend that tolerates the malformed start line. Creation of the PSR-7 object alone does not constitute exploitation. The attack complexity is elevated because few applications expose these specific fields to untrusted input.
The vulnerability mechanism is described in detail in the GitHub Security Advisory GHSA-vm85-hxw5-5432. No public proof-of-concept exploit is available at this time.
Detection Methods for CVE-2026-55766
Indicators of Compromise
- Outbound HTTP requests containing unexpected header lines following the request method or HTTP version token
- Server responses with reason phrases containing embedded CRLF sequences or trailing header content
- Application logs showing PSR-7 serialization of input fields containing \r or \n bytes
Detection Strategies
- Inspect composer.lock files across PHP repositories to identify guzzlehttp/psr7 versions earlier than 2.12.1
- Conduct source code review for application code paths that assign user input to the request method, protocol version, or response reason phrase
- Deploy network-layer inspection on egress traffic to detect HTTP/1.x messages with CRLF sequences embedded in start-line fields
Monitoring Recommendations
- Log all uses of Message::toString(), Message::parseRequest(), and Message::parseResponse() for forensic review
- Alert on web application firewall events matching CRLF injection signatures against outbound HTTP traffic from PHP services
- Track PHP dependency manifests in CI/CD pipelines to flag downstream services pinned to vulnerable guzzlehttp/psr7 releases
How to Mitigate CVE-2026-55766
Immediate Actions Required
- Upgrade guzzlehttp/psr7 to version 2.12.1 or later in all PHP projects
- Audit application code for any path that assigns external input to the HTTP method, protocol version, or reason phrase
- Validate that downstream proxies and backends reject malformed HTTP/1.x start lines independently of the originating library
Patch Information
The vulnerability is fixed in guzzlehttp/psr7 version 2.12.1. The patch extends CRLF validation to the request method, protocol version, and response reason phrase fields. Patch details and fix commits are referenced in the GitHub Security Advisory GHSA-vm85-hxw5-5432.
Workarounds
- Sanitize all external input by stripping \r and \n bytes before assigning values to PSR-7 start-line fields
- Wrap calls to Message::toString() with a validator that rejects messages containing CRLF in non-header positions
- Restrict the request method field to a fixed allowlist such as GET, POST, PUT, DELETE, PATCH, HEAD, and OPTIONS
# Upgrade guzzlehttp/psr7 to the patched release
composer require guzzlehttp/psr7:^2.12.1
composer update guzzlehttp/psr7
composer audit
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

