arnaud-lb
Repos
181
Followers
377
Following
53

The PHP Interpreter

C
35229
7168

PHP Static Analysis Tool - discover bugs in your code without running it!

11779
807

Production-ready, stable Kafka client for PHP

C
1906
258

Memory profiler for PHP. Helps finding memory leaks in PHP scripts.

C
743
48

php-go allows to call Go code from PHP, with minimal code boilerplate

C
171
18

PHP namespace support for VIM. Types "use" statements for you

254
30

Events

GenericType

Created at 12 hours ago

GenericType

Created at 12 hours ago
create branch
arnaud-lb create branch fast-subtype-check
Created at 13 hours ago

Add generic arrays

Based on https://github.com/php/php-src/compare/master...iluuu1994:php-src:erased-array-types

Created at 15 hours ago

Add generic arrays

Based on https://github.com/php/php-src/compare/master...iluuu1994:php-src:erased-array-types

Created at 15 hours ago
create branch
arnaud-lb create branch generic-arrays
Created at 15 hours ago
Created at 15 hours ago
issue comment
Fix GH-10026: Garbage collection stops after exception in SoapClient

Note that [zend]_bailout() wasn't designed to be caught and continue normal execution

We could try to stop doing this in master.

From my understanding, SOAP leverages zend_catch to convert fatal errors into exceptions. We could do it the other way around.

Unfortunately, SOAP does that for all errors, not only SOAP ones, and it will not be possible to stop using zend_catch for these. Maybe we should stop catching these, as this will result in crashes or memory leaks. Also, fatal errors are less frequent now that many have been replaced by exceptions.

Created at 17 hours ago

Naming

Created at 18 hours ago

Commented code

Created at 20 hours ago

Fixes

Created at 5 days ago
issue comment
Add AMPHP, ReactPHP, Revolt PHP in community job

I've been testing this on https://github.com/arnaud-lb/php-src/actions/runs/4519573556/jobs/7960141152, but it's not very stable yet. In particular, the amphp/byte-stream test suite sometimes causes an assertion failure in libsanitizer, that I can't reproduce locally.

The job duration dangerously approaches 6h indeed. I'll see if I can manage to split it into separate jobs.

Created at 5 days ago
pull request opened
Add AMPHP, ReactPHP, Revolt PHP in community job

This adds AMPHP, ReactPHP, Revolt PHP in community job, as an attempt to spot regressions around Fibers.

Created at 6 days ago
create branch
arnaud-lb create branch community-ci
Created at 6 days ago

Remove xfail from tests that do not fail anymore (#10871)

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Remove xfail from tests that do not fail anymore (#10871)

ext/psql: pg_meta_data, extended mode, fix typo for pseudo typtype.

Closes GH-10865.

Merge branch 'PHP-8.1' into PHP-8.2

Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Fixes GH-8789. Fixes GH-10015.

This is one small part of the underlying bug for GH-10737, as in my attempts to reproduce the issue I constantly hit this crash easily. (The fix for the other underlying issue for that bug will follow soon.)

It's possible that a signal arrives at a thread that never handled a PHP request before. This causes the signal globals to dereference a NULL pointer because the TSRM pointers for the thread aren't set up to point to the thread resources yet.

PR GH-9766 previously fixed this for master by ignoring the signal if the thread didn't handle a PHP request yet. While this fixes the crash bug, I think the solution is suboptimal for 3 reasons:

  1. The signal is ignored and a message is printed saying there is a bug. However, this is not a bug at all. For example in Apache, the signal set up happens on child process creation, and the thread resource creation happens lazily when the first request is handled by the thread. Hence, the fact that the thread resources aren't set up yet is not actually buggy behaviour.

  2. I believe since it was believed to be buggy behaviour, that fix was only applied to master, so 8.1 & 8.2 keep on crashing.

  3. We can do better than ignoring the signal. By just acting in the same way as if the signals aren't active. This means we need to take the same path as if the TSRM had already shut down.

Closes GH-10861.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Destroy file_handle in fpm_main

If it's not in the CG(open_files) list, we need to destroy the file handle ourselves.

Co-authored-by: Jakub Zelenka bukka@php.net

Closes GH-10707.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Destroy file_handle in fpm_main

Fix NUL byte in exception string terminating Exception::__toString()

Fixes GH-10810 Closes GH-10873

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix NUL byte in exception string terminating Exception::__toString()

Fix bug #74129: Incorrect SCRIPT_NAME with apache ProxyPassMatch

This happens when there are spaces are in the path info. The reason is that Apache decodes the path info part in the SCRIPT_NAME as per CGI RFC. FPM tries to strip path info from the SCRIPT_NAME but the comparison is done against SCRIPT_FILENAME which is not decoded. For that to work we have to decode it before comparison if there is any encoded character.

Closes GH-10869

Merge branch 'PHP-8.1' into PHP-8.2

Fix GH-10885: Leaking stream_socket_server context

php_stream_context_set already increases the refcount.

Closes GH-10886

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix GH-10885: Leaking stream_socket_server context

Fix GH-10052: Browscap crashes PHP 8.1.12 on request shutdown (apache2)

get_browser() implements a lazy parse system for the browscap INI configuration. There are two possible moments when a browscap configuration can be loaded: during module startup or during request. In case of module startup, the strings are persistent strings, while for the request they are not.

The INI parser must therefore know whether to create persistent or non-persistent strings. It does this by looking at CG(ini_parser_unbuffered_errors). If that value is 1 it's persistent, otherwise non-persistent. Note that this also controls how the errors are reported: if it's 1 then the errors are sent to stderr, otherwise we get E_WARNINGs.

Currently, a hardcoded value of 1 is always used for that CG value in browscap_read_file(). This means we'll always create persistent strings and we'll not report parse errors correctly as E_WARNINGs. We fix both the crash and the lack of warnings by passing the value of persistent instead of a hardcoded 1.

This is also in line with how other INI parsing code is called in ext/standard: they also make sure that during request a value of 0 is passed.

Closes GH-10883.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix GH-10052: Browscap crashes PHP 8.1.12 on request shutdown (apache2)

Fix GH-10521: ftp_get/ftp_nb_get resumepos offset is maximum 10GB

The char arrays were too small for a long on 64-bit systems, which resulted in cutting off the string at the end with a NUL byte. Use a size of MAX_LENGTH_OF_LONG to fix this issue instead of a fixed size of 11 chars.

Closes GH-10525.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix GH-10521: ftp_get/ftp_nb_get resumepos offset is maximum 10GB

[skip ci] Add CONFLICTS file for curl tests

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: [skip ci] Add CONFLICTS file for curl tests
Created at 6 days ago

Remove xfail from tests that do not fail anymore (#10871)

ext/psql: pg_meta_data, extended mode, fix typo for pseudo typtype.

Closes GH-10865.

Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Fixes GH-8789. Fixes GH-10015.

This is one small part of the underlying bug for GH-10737, as in my attempts to reproduce the issue I constantly hit this crash easily. (The fix for the other underlying issue for that bug will follow soon.)

It's possible that a signal arrives at a thread that never handled a PHP request before. This causes the signal globals to dereference a NULL pointer because the TSRM pointers for the thread aren't set up to point to the thread resources yet.

PR GH-9766 previously fixed this for master by ignoring the signal if the thread didn't handle a PHP request yet. While this fixes the crash bug, I think the solution is suboptimal for 3 reasons:

  1. The signal is ignored and a message is printed saying there is a bug. However, this is not a bug at all. For example in Apache, the signal set up happens on child process creation, and the thread resource creation happens lazily when the first request is handled by the thread. Hence, the fact that the thread resources aren't set up yet is not actually buggy behaviour.

  2. I believe since it was believed to be buggy behaviour, that fix was only applied to master, so 8.1 & 8.2 keep on crashing.

  3. We can do better than ignoring the signal. By just acting in the same way as if the signals aren't active. This means we need to take the same path as if the TSRM had already shut down.

Closes GH-10861.

Destroy file_handle in fpm_main

If it's not in the CG(open_files) list, we need to destroy the file handle ourselves.

Co-authored-by: Jakub Zelenka bukka@php.net

Closes GH-10707.

Fix NUL byte in exception string terminating Exception::__toString()

Fixes GH-10810 Closes GH-10873

Fix bug #74129: Incorrect SCRIPT_NAME with apache ProxyPassMatch

This happens when there are spaces are in the path info. The reason is that Apache decodes the path info part in the SCRIPT_NAME as per CGI RFC. FPM tries to strip path info from the SCRIPT_NAME but the comparison is done against SCRIPT_FILENAME which is not decoded. For that to work we have to decode it before comparison if there is any encoded character.

Closes GH-10869

Fix GH-10885: Leaking stream_socket_server context

php_stream_context_set already increases the refcount.

Closes GH-10886

Fix GH-10052: Browscap crashes PHP 8.1.12 on request shutdown (apache2)

get_browser() implements a lazy parse system for the browscap INI configuration. There are two possible moments when a browscap configuration can be loaded: during module startup or during request. In case of module startup, the strings are persistent strings, while for the request they are not.

The INI parser must therefore know whether to create persistent or non-persistent strings. It does this by looking at CG(ini_parser_unbuffered_errors). If that value is 1 it's persistent, otherwise non-persistent. Note that this also controls how the errors are reported: if it's 1 then the errors are sent to stderr, otherwise we get E_WARNINGs.

Currently, a hardcoded value of 1 is always used for that CG value in browscap_read_file(). This means we'll always create persistent strings and we'll not report parse errors correctly as E_WARNINGs. We fix both the crash and the lack of warnings by passing the value of persistent instead of a hardcoded 1.

This is also in line with how other INI parsing code is called in ext/standard: they also make sure that during request a value of 0 is passed.

Closes GH-10883.

Fix GH-10521: ftp_get/ftp_nb_get resumepos offset is maximum 10GB

The char arrays were too small for a long on 64-bit systems, which resulted in cutting off the string at the end with a NUL byte. Use a size of MAX_LENGTH_OF_LONG to fix this issue instead of a fixed size of 11 chars.

Closes GH-10525.

[skip ci] Add CONFLICTS file for curl tests

ext/curl: suppress -Wdeprecated-declarations in curl_arginfo.h

Disable the warning before including curl_arginfo.h.

(Follow-up for https://github.com/php/php-src/pull/10531)

Updated to version 2023.1 (2023a)

Fix GH-10583: DateTime modify with tz pattern should not update linked timezone

Merge remote-tracking branch 'derickr/issue10583' into PHP-8.1

Updated to version 2023.2 (2023b)

Fix GH-8979: Possible Memory Leak with SSL-enabled MySQL connections

The stream context inside mysqlnd_vio::enable_ssl() is leaking. In particular: when php_stream_context_set() get called the refcount of context is increased by 1, which means that context will now have a refcount of 2. Later on we remove the context from the stream by calling php_stream_context_set(stream, NULL) but that leaves our context with a refcount of 1, and therefore it's never destroyed. In my test case this yielded a leak of 1456 bytes per connection (but could be more depending on your settings ofc).

Annoyingly, Valgrind doesn't find it because the context is still in the EG(regular_list) and will thus be destroyed at the end of the request. However, I still think this bug needs to be fixed because as the users in the issue report already mentioned: there can be long-running PHP scripts.

Fix it by decreasing the refcount to transfer the ownership.

Closes GH-10909.

Fix phpGH-10648: add check function pointer into mbfl_encoding

Previously, mbstring used the same logic for encoding validation as for encoding conversion.

However, there are cases where we want to use different logic for validation and conversion. For example, if a string ends up with missing input required by the encoding, or if a character is input that is invalid as an encoding but can be converted, the conversion should succeed and the validation should fail.

To achieve this, a function pointer mb_check_fn has been added to struct mbfl_encoding to implement the logic used for validation. Also, added implementation of validation logic for UTF-7, UTF7-IMAP, ISO-2022-JP and JIS.

(The same change has already been made to PHP 8.2 and 8.3; see 6fc8d014df. This commit is backporting the change to PHP 8.1.)

Created at 6 days ago

Remove xfail from tests that do not fail anymore (#10871)

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Remove xfail from tests that do not fail anymore (#10871)

Merge branch 'PHP-8.2'

  • PHP-8.2: Remove xfail from tests that do not fail anymore (#10871)

ext/psql: pg_meta_data, extended mode, fix typo for pseudo typtype.

Closes GH-10865.

Merge branch 'PHP-8.1' into PHP-8.2

Merge branch 'PHP-8.2'

Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Fixes GH-8789. Fixes GH-10015.

This is one small part of the underlying bug for GH-10737, as in my attempts to reproduce the issue I constantly hit this crash easily. (The fix for the other underlying issue for that bug will follow soon.)

It's possible that a signal arrives at a thread that never handled a PHP request before. This causes the signal globals to dereference a NULL pointer because the TSRM pointers for the thread aren't set up to point to the thread resources yet.

PR GH-9766 previously fixed this for master by ignoring the signal if the thread didn't handle a PHP request yet. While this fixes the crash bug, I think the solution is suboptimal for 3 reasons:

  1. The signal is ignored and a message is printed saying there is a bug. However, this is not a bug at all. For example in Apache, the signal set up happens on child process creation, and the thread resource creation happens lazily when the first request is handled by the thread. Hence, the fact that the thread resources aren't set up yet is not actually buggy behaviour.

  2. I believe since it was believed to be buggy behaviour, that fix was only applied to master, so 8.1 & 8.2 keep on crashing.

  3. We can do better than ignoring the signal. By just acting in the same way as if the signals aren't active. This means we need to take the same path as if the TSRM had already shut down.

Closes GH-10861.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Merge branch 'PHP-8.2'

  • PHP-8.2: Fix GH-8789 and GH-10015: Fix ZTS zend signal crashes due to NULL globals

Destroy file_handle in fpm_main

If it's not in the CG(open_files) list, we need to destroy the file handle ourselves.

Co-authored-by: Jakub Zelenka bukka@php.net

Closes GH-10707.

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Destroy file_handle in fpm_main

Merge branch 'PHP-8.2'

  • PHP-8.2: Destroy file_handle in fpm_main

Fix NUL byte in exception string terminating Exception::__toString()

Fixes GH-10810 Closes GH-10873

Merge branch 'PHP-8.1' into PHP-8.2

  • PHP-8.1: Fix NUL byte in exception string terminating Exception::__toString()

Merge branch 'PHP-8.2'

  • PHP-8.2: Fix NUL byte in exception string terminating Exception::__toString()

Fix bug #74129: Incorrect SCRIPT_NAME with apache ProxyPassMatch

This happens when there are spaces are in the path info. The reason is that Apache decodes the path info part in the SCRIPT_NAME as per CGI RFC. FPM tries to strip path info from the SCRIPT_NAME but the comparison is done against SCRIPT_FILENAME which is not decoded. For that to work we have to decode it before comparison if there is any encoded character.

Closes GH-10869

Merge branch 'PHP-8.1' into PHP-8.2

Merge branch 'PHP-8.2'

Fix GH-10755: Memory leak in phar_rename_archive()

In phar_renmae_archive() context, added one reference but immediately destroyed another, so do not need to increase refcount. With removal of refcount++ line, PHP/Zend no longer reports memory leak. Updated bug69958.phpt test file accordingly.

Closes GH-10856

Use new ZSTR_INIT_LITERAL macro (#10879)

Created at 6 days ago

Remove WeakMap entries whose key is only reacheable through the entry value

Created at 6 days ago
pull request opened
[wip] Remove WeakMap entries whose key is only reacheable through the entry value

See https://github.com/php/php-src/issues/10043#issuecomment-1336155884

In a WeakMap like

$map = new WeakMap();
$map[$key] = $value;

$map[$key] should be removed during GC if $key is only reachable through $map[$key].

For example:

class Container {
    public function __construct(public readonly stdClass $value) {
    }
}

$key = new stdClass;
$value = new Container($key);

$map = new WeakMap();
$map[$key] = $value;

$key = null;
$value = null;
gc_collect_cycles(); // Should remove $map[$key]

This currently does not happen because $key is referenced by $value, and there is no cycle involving them:

graph LR
    R[Root Set] --> K[$key]
    R[Root Set] --> V[$value]
    R[Root Set] --> M[$map]
    V --> K
    M --> V

In this PR, I add a virtual reference from from all objects used as WeakMap key, to the corresponding values, so that the graph looks like this:

graph LR
   R[Root Set] --> K[$key]
   R[Root Set] --> V[$value]
   R[Root Set] --> M[$map]
   M -.-> E["Entry ($map, $key)"]
   K -.-> E
   E --> V[$value]
   V --> K

The virtual reference doesn't increase the refcount, so we must only scan the Entry -> $value reference once.

Implementation:

  • For objects with the IS_OBJ_WEAKLY_REFERENCED flag, we traverse their values through the WeakMaps as if the values was returned by obj->handlers->get_gc
  • We avoid scanning Entry->$value references twice by flagging them during the initial scan. Subsequent scans follow the reference depending on the flag. The flag is reset before the end of gc_collect_cycles().

This targets master because of the risk and the slight BC break.

Created at 6 days ago

Remove WeakMap entries whose key is only reacheable through the entry value

Created at 6 days ago
create branch
arnaud-lb create branch gh10043
Created at 6 days ago