CVE-2025-1736

Improper Input Validation (4.16)
Affects
PHP
in
PHP
No items found.
Versions
<8.1.32, >=8.2.0 <8.2.28, >=8.3.0 <8.3.19, >=8.4.0 <8.4.5

Patch Available.

Exclamation circle icon
Patch Available

This Vulnerability has been fixed in the Never-Ending Support (NES) version offered by HeroDevs.

Overview

PHP is a general-purpose scripting language used mostly for web development. It runs behind web servers through server APIs such as Apache mod_php and PHP-FPM, and powers content management systems and frameworks such as WordPress, Drupal, Moodle and Laravel. Its HTTP stream wrapper lets functions such as file_get_contents() and fopen() make HTTP and HTTPS requests, and the header option of an HTTP stream context adds request headers chosen by the script.

An Improper Input Validation vulnerability (CVE-2025-1736) has been identified in the way PHP's HTTP stream wrapper checks the user-supplied header context option for standard headers, which allows an attacker who can influence that option to make PHP omit headers it would otherwise send, such as the Basic authentication header built from the URL, or to have headers misinterpreted by the server. PHP tracks this issue as GHSA-hgf5-96fm-v528.

Per MITRE CWE-20: The product receives input or data, but it does not validate or incorrectly validates that the input has the properties that are required to process the data safely and correctly.

This issue affects PHP before 8.1.32, PHP 8.2 before 8.2.28, PHP 8.3 before 8.3.19 and PHP 8.4 before 8.4.5, which includes every End-of-Life release line from PHP 5.6 through 8.0, each through its final release.

Details

Module Info

Vulnerability Info

This Medium-severity vulnerability is found in the HTTP stream wrapper of PHP before 8.1.32, 8.2 before 8.2.28, 8.3 before 8.3.19 and 8.4 before 8.4.5, including every End-of-Life release line from PHP 5.6 through 8.0, which never received the upstream fix. The PHP project scores it 6.3 under CVSS 4.0 (CVSS:4.0/AV:N/AC:H/AT:P/PR:N/UI:N/VC:L/VI:N/VA:N/SC:N/SI:N/SA:N).

Before the wrapper adds its own Authorization, Host, User-Agent, From, Content-Length, Content-Type and Connection headers, it looks for each of them in the script's header option and skips the ones the script already provides. HTTP separates header lines with a carriage return and line feed (CRLF), but the check accepted a header name at the start of the block or after a bare line feed. In PHP 7.4.33 it reads:

static zend_bool check_has_header(const char *headers, const char *header) {
    const char *s = headers;
    while ((s = strstr(s, header))) {
        if (s == headers || *(s-1) == '\n') {
            return 1;
        }
        s++;
    }
    return 0;
}

A header string such as X: a, a bare line feed, then Authorization: x therefore counts as already holding an Authorization header, even though a server that splits headers on CRLF reads that text as part of the X header. The wrapper then omits the Basic authentication header it would have built from the credentials in the URL, and other standard headers can be suppressed or misread in the same way. HeroDevs' analysis found that PHP 5.6 and 7.2 performed this check inline and also accepted a match after a space or a tab, so on those lines the NES fix also brings in the stricter check that PHP added in 7.3.

Exploitation needs an application that passes attacker-influenced text into the header option of an HTTP stream context and requests an http or https URL through the wrapper, with allow_url_fopen enabled, under any SAPI. Applications that build the header option only from trusted values are not exposed.

The fix only accepts a match at the start of the header block or right after a CRLF:

static bool check_has_header(const char *headers, const char *header) {
    const char *s = headers;
    while ((s = strstr(s, header))) {
        if (s == headers || (*(s-1) == '\n' && *(s-2) == '\r')) {
            return 1;
        }
        s++;
    }
    return 0;
}

Mitigation

The PHP project publishes security fixes only for its supported release lines. PHP 5.6, 7.0, 7.1, 7.2, 7.3, 7.4 and 8.0 are End-of-Life and will not receive any public updates to address this issue.

Until an upgrade is possible, remove carriage return and line feed characters from any untrusted value before placing it in the header option of an HTTP stream context.

Users of the affected components should apply one of the following mitigations:

  • Upgrade to PHP 8.1.32, 8.2.28, 8.3.19, 8.4.5, or later.
  • Leverage a commercial support partner like HeroDevs (NES for PHP) for post-EOL security support.

Credits

Vulnerability Details
Severity
Level
CVSS Assessment
Low
>=0 <4
Medium
>=4 <6
High
>=6 <8
Critical
>=8 <10
Medium
ID
CVE-2025-1736
PROJECT Affected
PHP
Versions Affected
<8.1.32, >=8.2.0 <8.2.28, >=8.3.0 <8.3.19, >=8.4.0 <8.4.5
NES Versions Affected
Published date
March 30, 2025
≈ Fix date
February 27, 2025
Fixed in
Category
Improper Input Validation (4.16)
Vex Document
Download VEXHow do I use it?
Sign up for the latest vulnerability alerts fixed in
PHP
Rss feed icon
Subscribe via RSS
or

By submitting the form I acknowledge receipt of our Privacy Policy.

Thanks for signing up for our Newsletter! We look forward to connecting with you.
Oops! Something went wrong while submitting the form.