The `php_serialize` decode function has to return `FAILURE`, if the
unserialization failed on anything but an empty string.
The `php` decode function has also to return `FAILURE`, if there is
trailing garbage in the string.
The "callable name" may be the same for multiple distinct callables.
The code already worked around this for the case of instance methods,
but there are other cases in which callable names clash, such as
the use of self:: reported in the referenced bug.
Rather than trying to generate a unique name for callables, compare
the content of the alfi structures. This is less efficient if there
are many autoload functions, but autoload *registration* does not
need to be particularly efficient.
As a side-effect, this no longer permits unregistering non-callables.
Replace EG(autoload_func) with a C level zend_autoload hook.
This avoids having to do one indirection through PHP function
calls. The need for EG(autoload_func) was a leftover from the
__autoload() implementation.
Additionally, drop special-casing of spl_autoload(), and instead
register it just like any other autoloading function. This fixes
bug #71236 as a side-effect.
Finally, change spl_autoload_functions() to always return an array.
The distinction between false and an empty array no longer makes
sense here.
Closes GH-5696.
This is a bit tricky: In this cases we have "namespace as", which
means that we will only recognize "namespace" as an identifier when
the lookahead token is already at the "as". This means that
zend_lex_tstring picks up the wrong identifier.
We solve this by actually assigning the identifier as the semantic
value on the parser stack -- as in almost all cases we will not
actually need the identifier, this is just an (offset, size)
reference, not a copy of the string.
Additionally, we need to teach the lexer feedback mechanism used
by tokenizer TOKEN_PARSE mode to apply feedback to something
other than the very last token. To that purpose we pass through
the token text and check the tokens in reverse order to find the
right one.
Closes GH-5668.
This solves [#79628](https://bugs.php.net/79628).
Similar to `ReflectionClass::getMethods()` and `ReflectionClass::getProperties()`,
this new `$filter` argument allows the filtering of constants defined in a class by
their visibility.
For that, we create three new constants for `ReflectionClassConstant`:
* `IS_PUBLIC`
* `IS_PROTECTED`
* `IS_PRIVATE`
Closes GH-5649.
It should be noted that we still throw the usual fopen warnings,
but the final fatal error becomes an Error exception. Combine
with @ to suppress FS warnings.
Closes GH-5641.
Overriding the given INI values in modifier callbacks is not possible,
so instead of enforcing "normalized" internal values, we just reject
the attempted changes.
Currently, it's possible to disable the json extension with
`./configure --disable-json` (for historical reasons that no longer apply).
However, JSON is widely used in many use cases - web sites, logging output,
and as a data format that can be used to share data with many applications
and programming languages,
so I'd personally find it useful if it was always enabled.
Examples of where this would be useful:
- For internal classes to be able to implement `JsonSerializable`
which currently requires a hard dependency on the JSON extension.
- For PHP users to publish single-file scripts that use json_encode and
json_decode and don't require polyfills or less readable var_export output.
(polyfills are less efficient and may have issues with recursive data
structures)
- So that php-src's own modules, tools and test cases can start using JSON
if it's a good choice for encoding a value. (same for PECLs)
https://wiki.php.net/rfc/jsond mentions that in PHP 5,
> The current Json Parser in the json extension does not have a free license
> which is a problem for many Linux distros.
> This has been referenced at Bug #63520.
> That results in not packaging json extension in the many Linux distributions.
Starting in php 7.0 with the switch to jsond,
It looks like licensing is no longer an issue.
Changes:
- Remove all flags related to JSON such as `configure --disable-json`
- Require that JSON be compiled statically instead of as a shared library
Examples of uses of JSON in various distros
(backwards incompatible changes such as changing packaging are typically
reserved for major versions, and 8.0 is a major version)
- JSON is required by `php-cli` or `php` in ubuntu:
https://packages.ubuntu.com/focal/php/
- The php-json package has to be installed separately
from the PHP binary in Fedora repos.
Closes GH-5495
Even if that header file is available, we better consider it private,
and don't include it. The information about whether SSL support is
enabled is now missing (`USE_(OPEN)SSL`), and it seems there is no
alternative way to get it (`PQinitSSL()` is always defined), so we
remove it from the PHP info. Furthermore, the `PG_VERSION` and
`PG_VERSION_STR` macros are no longer available, but as of libpq 9.1
there is `PQlibVersion()` which allows us to construct `PG_VERSION` in
a most likely backwards compatible manner. The additional information
available through `PG_VERSION_STR` is lost, though, so we define
`PGSQL_LIBPQ_VERSION_STR` basically as alias of `PGSQL_LIBPQ_VERSION`,
and deprecate it right away.
Since we are now requiring at least libpq 9.1, we can remove some
further compatibility code and additional checks.
Regarding the raised requirements: official support for PostGreSQL 9.0
ended on 2015-10-08, and even CentOS 7 already has PostGreSQL 9.2, so
this is not supposed to be too much of an issue.
We can safely assume that users have at the very least libpq 7.4, for
which official support ended on 2010-10-01; even CentOS 6 has 8.4 now.
It is also noteworthy that PDO_PGSQL already requires libpq 7.4 or
later.
If opcache.record_warnings is enabled, opcache will record
compilation warnings and replay them when the file is included
again. The primary use case I have in mind for this is automated
testing of the opcache file cache.
This resolves bug #76535.
Aside from a few very specific syntax errors for which detailed exceptions are
thrown, generally PHP just emits the default error messages generated by bison on syntax
error. These messages are very uninformative; they just say "Unexpected ... at line ...".
This is most problematic with constructs which can span an arbitrary number of lines, such
as blocks of code delimited by { }, 'if' conditions delimited by ( ), and so on. If a closing
delimiter is missed, the block will run for the entire remainder of the source file (which
could be thousands of lines), and then at the end, a parse error will be thrown with the
dreaded words: "Unexpected end of file".
Therefore, track the positions of opening and closing delimiters and ensure that they match
up correctly. If any mismatch or missing delimiter is detected, immediately throw a parse
error which points the user to the offending line. This is best done in the *lexer* and not
in the parser.
Thanks to Nikita Popov and George Peter Banyard for suggesting improvements.
Fixes bug #79368.
Closes GH-5364.
It is hard to impossible to work around iconv() implementations which
do not properly set errno according to POSIX. We therefore do no
longer allow to build against such iconv() implementations.
Co-Authored-By: Nikita Popov <nikita.ppv@googlemail.com>
Don't special-case nested arrays/objects in str_replace(), instead
perform a string cast on them as well. For arrays, this will always
result in the usual conversion warning.
This behavior is consistent with preg_replace(). If we didn't want
to cast the array to string here, we should instead perform the
replacement recursively. Silently copying it is just confusing.
Currently, trait methods are aliased will continue to use the
original function name. In a few places in the codebase, we will
try to look up the actual method name instead. However, this does
not work if an aliased method is used indirectly
(https://bugs.php.net/bug.php?id=69180).
I think it would be better to instead actually change the method
name to the alias. This is in principle easy: We have to allow
function_name to be changed even if op array is otherwise shared
(similar to static_variables). This means we need to addref/release
the function_name separately, but I don't think there is a
performance concern here (especially as everything is usually
interned).
There is a bit of complication in opcache, where we need to make
sure that the function name is released the correct number of times
(interning may overwrite the name in the original op_array, but we
need to release it as many times as the op_array is shared).
Fixes bug #69180.
Fixes bug #74939.
Closes GH-5226.
Make ReflectionClassConstant->class the declaring class, not the
class on which the constant was fetched. This matches the behavior
for properties and methods.
While the `$command` passed to `proc_open()` had to be wrapped in
double-quotes manually, that was implicitly done for all other
program execution functions. This could easily introduce bugs and
even security issues when switching from one to another program
execution function.
Furthermore we ensure that the additional quotes are always
unwrapped regardless of what is passed as `$command` by passing
the `/s` flag to cmd.exe. As it was, `shell_exec('path with
spaces/program.exe')` did execute program.exe, but adding an
argument (`shell_exec('path with spaces/program.exe -h)`) failed
to execute program.exe, because cmd.exe stripped the additional
quotes.
While these changes obviously can cause BC breaks, we feel that in
the long run the benefits of having consistent behavior for all
program execution functions outweighs the drawbacks of potentially
breaking some code now.