764 Commits
Author SHA1 Message Date
Ilija Tovilo 9705fda1bb Merge branch 'PHP-8.6' into master
* PHP-8.6:
  Add NEWS entry
  Avoid state corruption via bailout
2026-10-21 16:34:56 +02:00
Ilija Tovilo d6373dfe15 Merge branch 'PHP-8.5' into PHP-8.6
* PHP-8.5:
  Add NEWS entry
  Avoid state corruption via bailout
2026-10-21 16:33:23 +02:00
Ilija Tovilo c7273b9ba8 Merge branch 'PHP-8.4' into PHP-8.5
* PHP-8.4:
  Add NEWS entry
  Avoid state corruption via bailout
2026-10-21 16:30:04 +02:00
Ilija Tovilo 8a94bb3822 Merge branch 'PHP-8.3' into PHP-8.4
* PHP-8.3:
  Add NEWS entry
  Avoid state corruption via bailout
2026-10-21 16:27:03 +02:00
Ilija Tovilo c1a5f468d0 Merge branch 'PHP-8.2' into PHP-8.3
* PHP-8.2:
  Add NEWS entry
  Avoid state corruption via bailout
2026-10-21 16:12:35 +02:00
3584a98bda Avoid state corruption via bailout
- Replace bailout on OOM with UnwindExit
- Properly reset various globals that may be accessed during startup

Fix GHSA-w8hw-w9fx-j79w (CVE-2026-109618)
Fix GHSA-6wmf-4rv5-p3rp (CVE-2026-109619)

Co-authored-by: Ilija Tovilo <ilija.tovilo@me.com>
Co-authored-by: Jakub Zelenka <bukka@php.net>
Co-authored-by: Nora Dossche <7771979+ndossche@users.noreply.github.com>
Co-authored-by: Nicolas Grekas <nicolas.grekas@gmail.com>
2026-10-21 16:06:22 +02:00
Gina Peter Banyard 473ad224a1 Zend: use ce parameter name consistently for zend_class_entry* (#24150) 2026-10-06 12:27:28 +01:00
Daniel Scherzer 63b0af4a5c Remove unused INIT_CLASS_ENTRY_INIT_METHODS macro (#23733) 2026-10-03 14:16:28 -07:00
Gina Peter Banyard 40b904316c Zend: add a new zend_call_method_if_exists_ex() (#24082) 2026-10-02 19:15:11 +01:00
Gina Peter Banyard dfbaf9e728 Zend: change signature of zend_is_callable()
The current signature is effectively useless every call uses the _ex variant to be able to grab the FCC and usually the error message.
Something the current signature does not provide, and instead offers parameters that most call sites don't care about.

Closes GH-23996
2026-09-29 22:50:57 +01:00
Gina Peter Banyard 3884053c04 Zend: rename zend_object* parameter to "this_ptr" for zend_call_* functions (#23989)
To be more explicit in what the zend_object* represents.
2026-09-29 16:20:29 +01:00
Gina Peter Banyard cfb1d5ee12 Zend: refactor zend_parse_arg_class() so that it can be reused (#23104)
And stop throwing the exceptions directly, fixing quiet mode handling at the same time.
2026-09-28 14:22:02 +01:00
Gina Peter Banyard ee908f5542 Zend: normalise behaviour around class name ZPP specifier (#23359)
Splitting the behavioural change of #23052 out into this and come up with something that is hopefully more sensible and consistent between fast and slow ZPP and the object or class_name Fast ZPP specifier.
2026-08-21 13:31:45 +01:00
Gina Peter Banyard 3f26310b16 Zend: remove Z_PARAM_FUNC_OR_NULL_WITH_ZVAL() (#23234)
And related Z_PARAM_GET_PREV_ZVAL()

These were introduced in https://github.com/php/php-src/commit/11796229f2f047768ee4870328f8dfd7e1a315a6 to simplify memory management.

But this is no longer relevant (well never was as one could have grabbed the zval from the FCI) since the refactoring to only use FCCs in https://github.com/php/php-src/commit/0e5d654409295e19570fb6a7d2e970d736e0f8a5

The following SourceGraph searches confirm there is no usage:
- https://sourcegraph.com/search?q=context:global+Z_PARAM_FUNC_OR_NULL_WITH_ZVAL&patternType=keyword&sm=0
- https://sourcegraph.com/search?q=context:global+Z_PARAM_GET_PREV_ZVAL&patternType=keyword&sm=0
2026-08-12 23:14:16 +01:00
Gina Peter Banyard f74acb62a3 Zend: remove zend_is_countable() (#23010)
This function is only used once internally, and no usage is reported from a SourceGraph search. [1]

[1] https://sourcegraph.com/search?q=context:global+-f:zend_API.c+-f:zend_API.h+zend_is_countable&patternType=keyword&sm=0
2026-08-12 13:51:03 +01:00
Gina Peter Banyard bad89ea445 Zend: remove zend_parse_parameter() (#23051)
This API is far worse than just using the existing zend_parse_arg_TYPE() APIs.

A SourceGraph search [1] shows this API is effectively only used by ext/ds to which a PR migrating away from this API has been submitted. [2]
The other two usages are from a now deprecated extension [3] and @arnauld-lb's now longer maintained php-go project. [4]

As such we think it is reasonable to remove said API.

[1] https://sourcegraph.com/search?q=context:global+-f:zend_API.c+-f:zend_API.h+zend_parse_parameter%28&patternType=keyword&sm=0
[2] https://github.com/php-ds/ext-ds/pull/232
[3] https://github.com/libvips/php-vips-ext
[4] https://github.com/arnaud-lb/php-go
2026-08-10 18:34:18 +01:00
Tim Düsterhus 909f7229b0 tree-wide: Generate nicer code in Z_PARAM_*() helpers wrapping Z_PARAM_*() (#23100)
Instead of using a fixed variable name for the temporary, it is now derived
from the name of the target variable.
2026-08-07 16:08:46 +02:00
Gina Peter Banyard bbf82d7a84 Zend: Remove ZPP_ERROR_WRONG_COUNT case
As it is unused, the relevant error is handled before and _error_code is assigned ZPP_ERROR_FAILURE.
2026-08-03 01:56:20 +01:00
Gina Peter Banyard add8d542b6 Zend: use C enum for ZPP error states 2026-08-03 01:56:20 +01:00
Gina Peter Banyard e31d8e082d Zend: move some basic forwarding function definitions to the header (#22936) 2026-08-02 21:14:50 +01:00
Gina Peter Banyard 9518d49da0 Zend: add _ex variants for calling known functions/FCC (#22910)
To permit setting the consumed_arg FCI field
2026-07-28 17:29:11 +01:00
Khaled AlamandIlija Tovilo 63e26ab716 Add trait support for internal classes (GH-20976)
Fixes GH-20974

Co-authored-by: Ilija Tovilo <ilija.tovilo@me.com>
2026-07-20 23:32:23 +02:00
Arnaud Le Blanc e60d756f2c zend_API: Add _ex variants of zend_argument_error* (#21829)
These variants take the function as parameter instead of infering it from the
call stack. This is useful in ZEND_TYPE_ASSERT, and will be used in PFA impl.
2026-07-16 18:43:40 +02:00
Pratik Bhujel 7c98e65ca0 Fix GH-22118: Compare equivalent fake closures in FCCs (#22145)
The reason fake closures didn't compare as equal was that two different objects could represent the same fake closure.

Therefore, we need to do a more detailed comparison when one or both operands are closures rather than just comparing pointers.

A good follow-up would be to draft an RFC to fix the semantics of `==` with two different instances of the same fake closure.
2026-06-14 09:51:22 +01:00
Alexandru Pătrănescu eedda2a03c Add consumed_args callback optimization and apply to array_reduce() for carry to improve performance (GH-21340)
* Add consumed_args support for fcall arguments

* Use consumed_args for array_reduce and some other callback-using functions
2026-05-08 15:42:23 +02:00
Gina Peter Banyard b9f64f7afa Improve ZPP weak parsing by returning value directly when possible
These changes are based on a previous PR by @ndossche to reduce codebloat: https://github.com/php/php-src/pull/18436

For zend_parse_arg_str_weak() we can return a `zend_string*` directly, as errors can be indicated by a NULL pointer return.

For zend_parse_arg_double_weak() we can return a `double` directly, as we can represent ZPP errors via `NAN` as booleans and integers never coerce to NAN. One might think that the string `'NAN'` can be coerced to double `NAN`, however PHP doesn't allow this coercion. And an explicit cast to double via `(float)` of such a string results in 0.

For zend_parse_arg_bool_weak() we instead create a new enum zpp_parse_bool_status that represents a tri-state which we return. Allowing us to return the boolean value via the return type instead of using an out pointer.
2026-05-02 15:37:10 +01:00
Tim Düsterhus dec3658d75 zend_API: Make array_init() and array_init_size() inline functions (#21905) 2026-04-29 08:01:54 +02:00
Tim Düsterhus 0471420514 zend_API: Remove _throw() variants of ZPP (#21866) 2026-04-24 18:45:58 +02:00
Arnaud Le Blanc 2c5dc5d8b1 Add ZEND_ACC2_FORBID_DYN_CALLS
Functions that use zend_forbid_dynamic_call() must be flagged with
ZEND_ACC2_FORBID_DYN_CALLS. In stubs, this is done by using
@forbid-dynamic-calls.

To ensure consistency, we assert that the flag exists in
zend_forbid_dynamic_call(), and we assert that flagged functions thrown after a
dynamic call.

Closes GH-21818
2026-04-22 10:15:59 +02:00
Arnaud Le Blanc da58c65519 gen_stub: Support fn_flags2 flags
Change zend_function_entry.flags to a uint64_t to that both ZEND_ACC_ and
ZEND_ACC2_ flags can be represented.

Introduce ZEND_FENTRY_FLAGS(flags, flags2) to pass ZEND_ACC2_ flags to
ZEND_RAW_FENTRY(), ZEND_FENTRY().

Source-level backwards compatibility is maintained, as passing raw ZEND_ACC_
flags to ZEND_RAW_FENTRY(), ZEND_FENTRY() still works.
2026-04-22 10:15:59 +02:00
Ben Ramsey e4394946c2 license-update: update Zend copyright name
RFC: https://wiki.php.net/rfc/php_license_update
2026-04-11 21:20:54 -05:00
Ben Ramsey 084a10afef license-update: Zend source headers
RFC: https://wiki.php.net/rfc/php_license_update
2026-04-11 21:20:54 -05:00
Ilija Tovilo b685fb2a94 More general assert() gcov solution
Fully disable assert() when compiling with gcov instead of overriding individual
macros.
2026-04-05 21:01:52 +02:00
Ilija Tovilo 2b7489437b More gcov improvements
- Suppress debug assertions
- Exclude ext/opcache/jit/ir

Closes GH-21629
2026-04-04 16:01:05 +02:00
Gina Peter Banyard 678382427f Zend: mark callable zval* as const (#21582) 2026-04-03 18:52:09 +01:00
Gina Peter Banyard be1ae8ef6f Zend: add const modifiers (#19571) 2026-03-23 10:52:28 +00:00
Arnaud Le Blanc d16e6f52a4 Generate C enums from internal enums, introduce Z_PARAM_ENUM() (#20917)
Update gen_stubs.php to generate C enums from internal enums, when the stub is annotated with @generate-c-enums. Enum values can be compared to the result of zend_enum_fetch_case_id(zend_object*).

The generated enums are added to separate files named {$extensionName}_decl.h, so that it's possible to include these from anywhere. _arginfo.h files would generate warnings if we tried to include them in a compilation unit that doesn't call the register_{$class} functions, for instance.

Introduce Z_PARAM_ENUM().

* Make ZEND_AST_CONST_ENUM_INIT a 4-children node

* Store enum case id in ZEND_AST_CONST_ENUM_INIT

* Store enum case id in instance

* Expose enum case_id internally

* Generate C enum for internal enums

* Introduce Z_PARAM_ENUM()

* Port extensions
2026-02-03 12:38:04 +01:00
Arnaud Le Blanc 626f3c3c7c Unify arg info representation for internal and user functions
The arg_info member of zend_function is now always a zend_arg_info*. Before,
it was a zend_internal_arg_info* on internal functions, unless the
ZEND_ACC_USER_ARG_INFO flag was set.

Closes GH-19022
2025-12-15 16:50:49 +01:00
Tim Düsterhus db8d35e7eb tree-wide: Replace ZEND_WRONG_PARAM_COUNT() by its definition (#20066)
* tree-wide: Replace `WRONG_PARAM_COUNT` by `ZEND_WRONG_PARAM_COUNT()`

This is a direct alias.

* tree-wide: Replace `ZEND_WRONG_PARAM_COUNT()` by its definition

This macro was hiding control flow (the return statement) and thus was
particularly unhygienic.
2025-11-12 21:28:56 +01:00
Gina Peter Banyard ccda8b16d4 zend_API.c: add const qualifiers 2025-11-07 21:10:52 +00:00
Gina Peter Banyard 55d449fca4 Zend: remove zend_set_hash_symbol() API (#20413)
This is unused both within php-src and a SourceGraph search returned 0 results.

This is also confusing as it talks about symbol tables without actually using any of the corresponding update functions.
2025-11-07 20:01:04 +00:00
Gina Peter Banyard c669fbf370 Zend/zend_compile: add const qualifiers 2025-10-30 12:02:43 +00:00
Gina Peter Banyard 7815ab9b22 Zend: add const qualifiers when possible for _zend_execute_data.func related uses (#20263)
The initial motivation was to see if it is possible to make the `func` field of `_zend_execute_data` constant.

For various reasons, this is not possible, but the added `const` qualifiers during this exploration remain useful.
2025-10-29 13:22:56 +00:00
Gina Peter Banyard c0214e49d2 Zend: remove zend_make_callable() function (#20269)
The name of this function is confusing, it doesn't make a zval callable just normalizes strings to an array pair if the string references a static method.
In general, to store a userland function it is encouraged to store the resolved FCC rather than the zval.

Moreover, a sourcegraph search shows no usage of this API in external open source code.
2025-10-26 18:28:40 +00:00
Gina Peter Banyard 275ec6f335 Zend: make zend_copy_parameters_array() private (#20265)
And slightly refactor implementation.
2025-10-25 22:36:09 +01:00
Tim Düsterhus 6da93a86f2 zend_API: Remove CHECK*NULL_PATH (#20155)
* tree-wide: Replace `CHECK_NULL_PATH()` by `zend_char_has_nul_byte()`

The former is a direct alias of the latter with a more explicit name and the
former is explicitly documented as a “compatibility” alias.

* tree-wide: Replace `CHECK_ZVAL_NULL_PATH()` by its definition

The former is explicitly documented as a “compatibility” alias.

* zend_API: Remove `CHECK*NULL_PATH`

The `CHECK_ZVAL_NULL_PATH()` macro is unsafe, because it implicitly assumes
that the given `zval*` is `IS_STRING`.

Based on a GitHub search there does not seem to be any user outside of PHP, all
hits were just forks / copies of php-src.
2025-10-15 10:24:22 +02:00
Tim Düsterhus f566312b54 zend_API: Remove ZVAL_IS_NULL() (#19986)
The `ZVAL_*()` macros are setters, the `Z_*()` macros are getters.
2025-09-29 12:35:22 +02:00
Gina Peter Banyard ba4a12bc39 Zend: add const qualifier for scope in read property functions (#19949) 2025-09-24 18:53:50 +01:00
Ilija Tovilo 5897071ab6 Fix refcounting on zend_empty_array in ext-uri (GH-19908)
Fixes GH-19892
2025-09-21 21:56:04 +02:00
Gina Peter Banyard f4e2e91d4b core: Remove disable_classes INI setting
RFC: https://wiki.php.net/rfc/deprecations_php_8_5#remove_disable_classes_ini_setting

This took longer to merge than expected but the initial motivation from 2 years ago still applied:

As described in the email to the PHP internals list [1] this feature is fundamentally broken and pointless.

Only internal classes can be disable which brings the following observation. On a minimal build of PHP, with only the mandatory extensions enabled, there are 148 classes/interfaces/traits defined. [2]

Other than the SPL ones (and even then), disabling any of these classes will cause issues within the engine.
Moreover, the SPL ones are not a security concern.

Therefore, any other class that can be disabled must come from an extension that can be disabled altogether. And "disabling" a class from an extension without disabling said extension will render it useless anyway.

If a hosting provided is concerned about an extension, then it should not enable it in the first place. Not break it ad hoc.

Considering the above, I cannot see how this functionality was ever useful.

This is in stark contrast to the disable_functions INI setting, which can be used to selectively remove functionality of an extension without breaking it overall.

What makes this setting particularly broken is that it does not unregister the class, it only overwrites the create CE handler to emit a warning and purge the properties and function hashtables. This leads to various use after free, segfaults, and broken expectations for the engine and extensions which define said classes. On top of that, it is possible to actually instantiate such a class (and even classes which actually disallow this like ext/imap) in userland, and pass it to function that are typed against said class without raising a TypeError. However, when trying to do anything with said object stuff is going to explode in countless ways.

[1] https://news-web.php.net/php.internals/120896
[2] https://gist.github.com/Girgias/63d55ba1e50b580412b004046daed02b
2025-08-25 21:16:55 +01:00