Repository navigation
Conversation
…ions Fixes GHSA-m8rr-4c36-8gq4 Fixes CVE-2026-7258 (cherry picked from commit 8bdee7e)
…array offset Fixes GHSA-96wq-48vp-hh57 Fixes CVE-2026-7568 (cherry picked from commit dd77cfe)
…b_check_encoding() via mb_ereg_search_init() Fixes GHSA-wm6j-2649-pv75 Fixes CVE-2026-7259 (cherry picked from commit df8ae9c)
Fixes GHSA-7qg2-v9fj-4mwv Fixes CVE-2026-6735 (cherry picked from commit 13e72d1)
Fixes GHSA-hmxp-6pc4-f3vv Fixes CVE-2026-7262 (cherry picked from commit 9992b81)
…ailure with SOAP_PERSISTENCE_SESSION Fixes GHSA-m33r-qmcv-p97q Fixes CVE-2026-7261 (cherry picked from commit b9f81de)
…th Apache Map Fixes GHSA-85c2-q967-79q5 Fixes CVE-2026-6722 (cherry picked from commit 84e3004)
There was a problem hiding this comment.
Code Review
This pull request implements extensive security hardening and bug fixes across the PHP core and various extensions. The primary change involves casting arguments to unsigned char for character classification and transformation functions to avoid undefined behavior. It also addresses several critical vulnerabilities, including null pointer dereferences in mbstring and SOAP, use-after-free and reference counting issues in SOAP, integer overflows in metaphone, and an XSS vulnerability in the FPM status page. Feedback indicates that several calls to isxdigit, isspace, and isdigit in ext/standard/filters.c and ext/standard/strnatcmp.c were missed and should be updated with the appropriate casts for consistency.
| } | ||
|
|
||
| if (!isxdigit((int) *ps)) { | ||
| if (!isxdigit(*ps)) { |
There was a problem hiding this comment.
The isxdigit() function expects an int that is representable as an unsigned char or is EOF. Passing a signed char directly can lead to undefined behavior if the value is negative. To be consistent with the rest of the changes in this pull request, this should be cast to unsigned char.
if (!isxdigit((unsigned char)*ps)) {|
|
||
| /* Skip consecutive whitespace */ | ||
| while (isspace((int)(unsigned char)ca)) { | ||
| while (isspace(ca)) { |
There was a problem hiding this comment.
The isspace() function expects an int that is representable as an unsigned char or is EOF. Since ca is a char, it should be cast to unsigned char before being passed to isspace(). This is inconsistent with the correct changes made on lines 106 and 110 of this same file.
while (isspace((unsigned char)ca)) {| } | ||
|
|
||
| while (isspace((int)(unsigned char)cb)) { | ||
| while (isspace(cb)) { |
|
|
||
| /* process run of digits */ | ||
| if (isdigit((int)(unsigned char)ca) && isdigit((int)(unsigned char)cb)) { | ||
| if (isdigit(ca) && isdigit(cb)) { |
php_imagettftext_common() serves the bbox functions, where $size is argument #1, and the drawing ones, where it is php#2, but its two size checks hardcode 2. imageftbbox(NAN, ...) therefore blamed $angle. Also fix the upper bound itself: (double)LONG_MAX rounds up to 2^63, so (double)LONG_MAX / 64 is 2^57 and the check let 2^57 through, whose product with 64 is LONG_MAX + 1. The bound is now exclusive, and the reported values use integer division, which gives the largest size that is actually representable. The lower bound stays inclusive: (double)LONG_MIN / 64 is exactly -2^57 and its product with 64 is LONG_MIN. Co-authored-by: NickSdot <32384907+NickSdot@users.noreply.github.com> Close phpGH-23541
There are two optimizations: 1. This patch implements the JIT counterpart of the VM change 2d6b869 to optimize comparisons against empty arrays. 2. This patch ensures that if a type can be array, the element count check happens inline rather than going to a slow path. PHP demo code for #1: ```php function f(array $a) { if ($a) return 0; return 1; } ``` Before #1 (for func JIT in this case): ```asm .L1: movq $0x418d88c0, (%r14) ; EX(opline) = opline leaq 0x50(%r14), %rdi ; arg = &CV0($a) movabsq $zend_is_true, %rax callq *%rax testb %al, %al je .L2 ``` After #1: ```asm .L1: movq 0x50(%r14), %rax ; Z_ARRVAL($a) cmpl $0, 0x1c(%rax) ; compare nNumOfElements je .L2 ``` PHP demo code for php#2: ```php function is_empty(array $a) { if ($a === []) return 1; return 2; } ``` Before php#2: ```asm .L1: leaq 0x50(%r14), %rdi ; arg1 = &CV0($a) movl $0x418d8ad8, %esi ; arg2 = &literal [] movabsq $zend_is_identical, %rax callq *%rax testb %al, %al je .L2 ``` After php#2: ```asm .L1: movq 0x50(%r14), %rax ; Z_ARRVAL($a) cmpl $0, 0x1c(%rax) ; compare nNumOfElements jne .L2 ``` It ain't much, but it should help. I think many small frontend improvements can make a nice change in total together.
WIP for Alpinelinux