CodeIgniter validation of header name and value
Description
CodeIgniter is a PHP full-stack web framework. Prior to 4.5.8, CodeIgniter lacked proper header validation for its name and value. The potential attacker can construct deliberately malformed headers with Header class. This could disrupt application functionality, potentially causing errors or generating invalid HTTP requests. In some cases, these malformed requests might lead to a DoS scenario if a remote service’s web application firewall interprets them as malicious and blocks further communication with the application. This vulnerability is fixed in 4.5.8.
AI Insight
LLM-synthesized narrative grounded in this CVE's description and references.
CodeIgniter 4.5.7 and earlier lack header name/value validation, allowing malformed HTTP headers that could cause errors or DoS when interpreted maliciously by intermediary services.
Vulnerability
Description
CodeIgniter 4 prior to version 4.5.8 does not validate HTTP header names and values when they are set via the Header class. The root cause is a lack of input validation in the Header::setName() and Header::setValue() methods, allowing arbitrary strings to be assigned without checking conformance to HTTP specifications such as RFC 7230 [1]. This oversight enables an attacker to construct headers with invalid characters or malformed syntax [2].
Exploitation and
Attack Surface
An attacker can leverage this vulnerability by providing specially crafted header names or values through the application’s HTTP interface. No authentication is required if the endpoint that accepts header input is publicly accessible. The malformed headers may then be inserted into outgoing HTTP requests or responses, disrupting normal application flow [2]. The attack surface includes any system that uses the Header class to construct HTTP messages, particularly when user-supplied data influences header values.
Impact
The impact is primarily a denial of service (DoS) scenario. When a remote service or web application firewall (WAF) receives an HTTP request with invalid headers, it may reject the entire request, block the originating IP, or drop communication with the application [2]. This can lead to service disruption for legitimate users. Additionally, malformed headers can cause errors or unexpected behavior within the application itself, potentially affecting broader functionality [2].
Mitigation
Status
The vulnerability is fixed in CodeIgniter version 4.5.8. The patch introduces validation methods such as validateName() and validateValue() that throw an InvalidArgumentException on malformed input [3]. Users should upgrade to the latest version immediately; no official workaround is available for earlier releases [2][3].
AI Insight generated on May 20, 2026. Synthesized from this CVE's description and the cited reference URLs; citations are validated against the source bundle.
Affected packages
Versions sourced from the GitHub Security Advisory.
| Package | Affected versions | Patched versions |
|---|---|---|
codeigniter4/frameworkPackagist | < 4.5.8 | 4.5.8 |
Affected products
3- Range: <4.5.8
- codeigniter4/CodeIgniter4v5Range: < 4.5.8
Patches
15f8aa24280fbMerge commit from fork
3 files changed · +159 −2
system/HTTP/Header.php+70 −2 modified@@ -13,6 +13,7 @@ namespace CodeIgniter\HTTP; +use InvalidArgumentException; use Stringable; /** @@ -54,7 +55,7 @@ class Header implements Stringable */ public function __construct(string $name, $value = null) { - $this->name = $name; + $this->setName($name); $this->setValue($value); } @@ -81,9 +82,12 @@ public function getValue() * Sets the name of the header, overwriting any previous value. * * @return $this + * + * @throws InvalidArgumentException */ public function setName(string $name) { + $this->validateName($name); $this->name = $name; return $this; @@ -95,10 +99,16 @@ public function setName(string $name) * @param array<int|string, array<string, string>|string>|string|null $value * * @return $this + * + * @throws InvalidArgumentException */ public function setValue($value = null) { - $this->value = is_array($value) ? $value : (string) $value; + $value = is_array($value) ? $value : (string) $value; + + $this->validateValue($value); + + $this->value = $value; return $this; } @@ -110,13 +120,17 @@ public function setValue($value = null) * @param array<string, string>|string|null $value * * @return $this + * + * @throws InvalidArgumentException */ public function appendValue($value = null) { if ($value === null) { return $this; } + $this->validateValue($value); + if (! is_array($this->value)) { $this->value = [$this->value]; } @@ -135,13 +149,17 @@ public function appendValue($value = null) * @param array<string, string>|string|null $value * * @return $this + * + * @throws InvalidArgumentException */ public function prependValue($value = null) { if ($value === null) { return $this; } + $this->validateValue($value); + if (! is_array($this->value)) { $this->value = [$this->value]; } @@ -193,4 +211,54 @@ public function __toString(): string { return $this->name . ': ' . $this->getValueLine(); } + + /** + * Validate header name. + * + * Regex is based on code from a guzzlehttp/psr7 library. + * + * @see https://datatracker.ietf.org/doc/html/rfc7230#section-3.2 + * + * @throws InvalidArgumentException + */ + private function validateName(string $name): void + { + if (preg_match('/^[a-zA-Z0-9\'`#$%&*+.^_|~!-]+$/D', $name) !== 1) { + throw new InvalidArgumentException('The header name is not valid as per RFC 7230.'); + } + } + + /** + * Validate header value. + * + * Regex is based on code from a guzzlehttp/psr7 library. + * + * @see https://datatracker.ietf.org/doc/html/rfc7230#section-3.2 + * + * @param array<int|string, array<string, string>|string>|int|string $value + * + * @throws InvalidArgumentException + */ + private function validateValue(array|int|string $value): void + { + if (is_int($value)) { + return; + } + + if (is_array($value)) { + foreach ($value as $key => $val) { + $this->validateValue($key); + $this->validateValue($val); + } + + return; + } + + // The regular expression excludes obs-fold per RFC 7230#3.2.4, as sending folded lines + // is deprecated and rare. This obscure HTTP/1.1 feature is unlikely to impact legitimate + // use cases. Libraries like Guzzle and AMPHP follow the same principle. + if (preg_match('/^[\x20\x09\x21-\x7E\x80-\xFF]*$/D', $value) !== 1) { + throw new InvalidArgumentException('The header value is not valid as per RFC 7230.'); + } + } }
tests/system/HTTP/HeaderTest.php+81 −0 modified@@ -15,6 +15,8 @@ use CodeIgniter\Test\CIUnitTestCase; use Error; +use InvalidArgumentException; +use PHPUnit\Framework\Attributes\DataProvider; use PHPUnit\Framework\Attributes\Group; use stdClass; @@ -234,4 +236,83 @@ public function testHeaderToStringShowsEntireHeader(): void $this->assertSame($expected, (string) $header); } + + /** + * @param string $name + */ + #[DataProvider('invalidNamesProvider')] + public function testInvalidHeaderNames($name): void + { + $this->expectException(InvalidArgumentException::class); + + new Header($name, 'text/html'); + } + + /** + * @return list<list<string>> + */ + public static function invalidNamesProvider(): array + { + return [ + ["Content-Type\r\n\r\n"], + ["Content-Type\r\n"], + ["Content-Type\n"], + ["\tContent-Type\t"], + ["\n\nContent-Type\n\n"], + ["\r\nContent-Type"], + ["\nContent-Type"], + ["Content\r\n-Type"], + ["\n"], + ["\r\n"], + ["\t"], + [' Content-Type '], + ['Content - Type'], + ["Content\x00Type"], + [':Content-Type'], + ['Content-Type:'], + [''], + ]; + } + + /** + * @param array<int|string, array<string, string>|string>|string|null $value + */ + #[DataProvider('invalidValuesProvider')] + public function testInvalidHeaderValues($value): void + { + $this->expectException(InvalidArgumentException::class); + + new Header('X-Test-Header', $value); + } + + /** + * @return list<list<array<(int|string), string>|string>> + */ + public static function invalidValuesProvider(): array + { + return [ + ["Header\n Value"], + ["Header\r\n Value"], + ["Header\r Value"], + ["Header Value\n"], + ["\nHeader Value"], + ["Header Value\r\n"], + ["\n\rHeader Value"], + ["\n\nHeader Value\n\n"], + [ + ["Header\n Value"], + ["Header\r\n Value"], + ], + [ + [ + "Header\n" => 'Value', + ], + ], + [ + [ + 'Header' => "Value\r\n", + ], + ], + ]; + } }
user_guide_src/source/changelogs/v4.5.8.rst+8 −0 modified@@ -10,6 +10,14 @@ Release Date: Unreleased :local: :depth: 3 +******** +SECURITY +******** + +- **Header:** *Validation of header name and value* was fixed. + See the `Security advisory GHSA-x5mq-jjr3-vmx6 <https://github.com/codeigniter4/CodeIgniter4/security/advisories/GHSA-x5mq-jjr3-vmx6>`_ + for more information. + ******** BREAKING ********
Vulnerability mechanics
Generated on May 9, 2026. Inputs: CWE entries + fix-commit diffs from this CVE's patches. Citations validated against bundle.
References
6- github.com/advisories/GHSA-wxmh-65f7-jcvwghsax_refsource_MISCADVISORY
- github.com/advisories/GHSA-x5mq-jjr3-vmx6ghsaADVISORY
- nvd.nist.gov/vuln/detail/CVE-2025-24013ghsaADVISORY
- datatracker.ietf.org/doc/html/rfc7230ghsax_refsource_MISCWEB
- github.com/codeigniter4/CodeIgniter4/commit/5f8aa24280fb09947897d6b322bf1f0e038b13b6ghsax_refsource_MISCWEB
- github.com/codeigniter4/CodeIgniter4/security/advisories/GHSA-x5mq-jjr3-vmx6ghsax_refsource_CONFIRMWEB
News mentions
0No linked articles in our index yet.