summaryrefslogtreecommitdiffstats
path: root/php-cve-2026-6735.patch
diff options
context:
space:
mode:
Diffstat (limited to 'php-cve-2026-6735.patch')
-rw-r--r--php-cve-2026-6735.patch226
1 files changed, 226 insertions, 0 deletions
diff --git a/php-cve-2026-6735.patch b/php-cve-2026-6735.patch
new file mode 100644
index 0000000..ba1dbb0
--- /dev/null
+++ b/php-cve-2026-6735.patch
@@ -0,0 +1,226 @@
+From 3322601b31ccedeb13a3203bbe5fd7b6cb4679a9 Mon Sep 17 00:00:00 2001
+From: Remi Collet <remi@remirepo.net>
+Date: Tue, 19 May 2026 09:47:08 +0200
+Subject: [PATCH 5/5] GHSA-7qg2-v9fj-4mwv: [fpm] XSS within status endpoint
+
+Fixes GHSA-7qg2-v9fj-4mwv
+Fixes CVE-2026-6735
+
+(cherry picked from commit 99a5ad7441de9914246c7863adb6997396008b9d)
+(cherry picked from commit 943de7efee24c0e7d826a3469d3b35b4ad0f4193)
+---
+ NEWS | 4 ++
+ sapi/fpm/fpm/fpm_status.c | 20 ++++--
+ .../tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt | 62 +++++++++++++++++++
+ 3 files changed, 82 insertions(+), 4 deletions(-)
+ create mode 100644 sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+
+diff --git a/NEWS b/NEWS
+index b46e2b0c5d..d8ae595068 100644
+--- a/NEWS
++++ b/NEWS
+@@ -3,6 +3,10 @@ PHP NEWS
+
+ Backported from 8.2.31
+
++- FPM:
++ . Fixed GHSA-7qg2-v9fj-4mwv (XSS within status endpoint). (CVE-2026-6735)
++ (Jakub Zelenka)
++
+ - SOAP:
+ . Fixed GHSA-m33r-qmcv-p97q (Use-after-free after header parsing failure with
+ SOAP_PERSISTENCE_SESSION). (CVE-2026-7261) (ilutov)
+diff --git a/sapi/fpm/fpm/fpm_status.c b/sapi/fpm/fpm/fpm_status.c
+index a2ee398d29..d9a8263089 100644
+--- a/sapi/fpm/fpm/fpm_status.c
++++ b/sapi/fpm/fpm/fpm_status.c
+@@ -384,8 +384,8 @@ int fpm_status_handle_request(TSRMLS_D) /* {{{ */
+ /* no need to test the var 'full' */
+ if (full_syntax) {
+ int i, first;
+- size_t len;
+- char *query_string;
++ size_t len, len_uri;
++ char *query_string, *request_uri_string;
+ struct timeval duration, now;
+ #ifdef HAVE_FPM_LQ
+ float cpu;
+@@ -412,13 +412,22 @@ int fpm_status_handle_request(TSRMLS_D) /* {{{ */
+ }
+ }
+
++ request_uri_string = NULL;
++ len_uri = 0;
++ if (proc.request_uri[0] != '\0') {
++ if (!encode) {
++ request_uri_string = proc.request_uri;
++ } else {
++ request_uri_string = php_escape_html_entities_ex((unsigned char *)proc.request_uri, strlen(proc.request_uri), &len_uri, 1, ENT_DISALLOWED | ENT_HTML_DOC_XML1 | ENT_COMPAT, NULL, 1 TSRMLS_CC);
++ }
++ }
+ query_string = NULL;
+ len = 0;
+ if (proc.query_string[0] != '\0') {
+ if (!encode) {
+ query_string = proc.query_string;
+ } else {
+- query_string = php_escape_html_entities_ex((unsigned char *)proc.query_string, strlen(proc.query_string), &len, 1, ENT_HTML_IGNORE_ERRORS & ENT_COMPAT, NULL, 1 TSRMLS_CC);
++ query_string = php_escape_html_entities_ex((unsigned char *)proc.query_string, strlen(proc.query_string), &len, 1, ENT_DISALLOWED | ENT_HTML_DOC_XML1 | ENT_COMPAT, NULL, 1 TSRMLS_CC);
+ }
+ }
+
+@@ -445,7 +454,7 @@ int fpm_status_handle_request(TSRMLS_D) /* {{{ */
+ proc.requests,
+ duration.tv_sec * 1000000UL + duration.tv_usec,
+ proc.request_method[0] != '\0' ? proc.request_method : "-",
+- proc.request_uri[0] != '\0' ? proc.request_uri : "-",
++ request_uri_string ? request_uri_string: "-",
+ query_string ? "?" : "",
+ query_string ? query_string : "",
+ proc.content_length,
+@@ -461,6 +470,9 @@ int fpm_status_handle_request(TSRMLS_D) /* {{{ */
+ if (len > 0 && query_string) {
+ efree(query_string);
+ }
++ if (len_uri > 0 && request_uri_string) {
++ efree(request_uri_string);
++ }
+ }
+
+ if (full_post) {
+diff --git a/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+new file mode 100644
+index 0000000000..55827b1bc8
+--- /dev/null
++++ b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+@@ -0,0 +1,62 @@
++--TEST--
++FPM: Test status page
++--SKIPIF--
++<?php include "skipif.inc"; ?>
++--FILE--
++<?php
++
++include "include.inc";
++
++$logfile = dirname(__FILE__).'/php-fpm.log.tmp';
++$port = 9000+PHP_INT_SIZE;
++
++$cfg = <<<EOT
++[global]
++error_log = $logfile
++[unconfined]
++listen = 127.0.0.1:$port
++pm.status_path = /status
++pm = dynamic
++pm.max_children = 5
++pm.start_servers = 2
++pm.min_spare_servers = 2
++pm.max_spare_servers = 3
++EOT;
++
++$fpm = run_fpm($cfg, $tail);
++if (is_resource($fpm)) {
++ fpm_display_log($tail, 2);
++ try {
++
++ $html = run_request('127.0.0.1', $port, '/<script>alert(1)</script>', '<script>alert(2)</script>');
++
++ $html = run_request('127.0.0.1', $port, '/status', 'full&html');
++ var_dump(strpos($html, 'text/html') && strpos($html, 'DOCTYPE') && strpos($html, 'PHP-FPM Status Page'));
++ var_dump(strpos($html, 'alert(1)') && strpos($html, 'alert(2)'));
++ var_dump(strpos($html, '<script>'));
++ //var_dump($html);
++
++ echo "IPv4 ok\n";
++ } catch (Exception $e) {
++ echo "IPv4 error\n";
++ }
++
++ proc_terminate($fpm);
++ stream_get_contents($tail);
++ fclose($tail);
++ proc_close($fpm);
++}
++
++?>
++--EXPECTF--
++[%d-%s-%d %d:%d:%d] NOTICE: fpm is running, pid %d
++[%d-%s-%d %d:%d:%d] NOTICE: ready to handle connections
++bool(true)
++bool(true)
++bool(false)
++IPv4 ok
++--CLEAN--
++<?php
++ $logfile = dirname(__FILE__).'/php-fpm.log.tmp';
++ @unlink($logfile);
++?>
+--
+2.54.0
+
+From 630b48523b5a0de368138c421bd3dbae6b0552a0 Mon Sep 17 00:00:00 2001
+From: Remi Collet <remi@remirepo.net>
+Date: Tue, 19 May 2026 11:25:29 +0200
+Subject: [PATCH] relax test (may fail when script not in status page)
+
+(cherry picked from commit 31ed74945eb92e073b51bd8ca114a123c9c20990)
+---
+ sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt | 10 +++++-----
+ 1 file changed, 5 insertions(+), 5 deletions(-)
+
+diff --git a/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+index 55827b1bc8..674b4ddcb3 100644
+--- a/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
++++ b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+@@ -32,9 +32,11 @@ if (is_resource($fpm)) {
+
+ $html = run_request('127.0.0.1', $port, '/status', 'full&html');
+ var_dump(strpos($html, 'text/html') && strpos($html, 'DOCTYPE') && strpos($html, 'PHP-FPM Status Page'));
+- var_dump(strpos($html, 'alert(1)') && strpos($html, 'alert(2)'));
+- var_dump(strpos($html, '<script>'));
+- //var_dump($html);
++
++ // output only if script present but not escaped
++ if (strpos($html, 'alert') && strpos($html, '<script>')) {
++ var_dump($html);
++ }
+
+ echo "IPv4 ok\n";
+ } catch (Exception $e) {
+@@ -52,8 +54,6 @@ if (is_resource($fpm)) {
+ [%d-%s-%d %d:%d:%d] NOTICE: fpm is running, pid %d
+ [%d-%s-%d %d:%d:%d] NOTICE: ready to handle connections
+ bool(true)
+-bool(true)
+-bool(false)
+ IPv4 ok
+ --CLEAN--
+ <?php
+--
+2.54.0
+
+From 4abe506a9863ec2f236689fc6b64549cc2fcb260 Mon Sep 17 00:00:00 2001
+From: Remi Collet <remi@remirepo.net>
+Date: Tue, 19 May 2026 11:40:42 +0200
+Subject: [PATCH 2/2] fix test name
+
+(cherry picked from commit 16802565461621322e97ba7ac22e2699885ed73a)
+---
+ sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt | 2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+index 674b4ddcb3..912237c5e2 100644
+--- a/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
++++ b/sapi/fpm/tests/ghsa-7qg2-v9fj-4mwv-status-xss.phpt
+@@ -1,5 +1,5 @@
+ --TEST--
+-FPM: Test status page
++FPM: GHSA-7qg2-v9fj-4mwv - status xss
+ --SKIPIF--
+ <?php include "skipif.inc"; ?>
+ --FILE--
+--
+2.54.0
+