php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Bug #80968 JIT segfault with return from required file
Submitted: 2021-04-19 02:09 UTC Modified: 2021-05-11 08:21 UTC
From: ryan dot brothers at gmail dot com Assigned: dmitry (profile)
Status: Closed Package: JIT
PHP Version: 8.0.3 OS: Linux
Private report: No CVE-ID: None
 [2021-04-19 02:09 UTC] ryan dot brothers at gmail dot com
Description:
------------
I am seeing a few segfaults when running PHP 8.0.3 with JIT enabled under nginx/php-fpm on CentOS 8.  I'm not sure if all the segfaults I'm getting are related, but I've been able to reproduce one of them so far.

To reproduce, set-up scripts 1.php and 2.php as listed, and then go to 1.php via nginx/php-fpm.  You may have to hit the URL a few times to get the segfault.

My php.ini has:
opcache.jit = tracing
opcache.jit_buffer_size = 100M

Please let me know if I can give any more info to help reproduce it.

Thank you for your help.

Test script:
---------------
1.php:

<?php
class c1
{
	public static function __callStatic($method_name, $arguments)
	{
		return require('2.php');
	}
}

$data = array(1, 2);

for ($i = 0; $i < 100; $i++)
{
	c1::test($data);
}

=======

2.php:

<?php
if (is_array($arguments[0]) == true)
{
	foreach ($arguments[0] as $item)
	{
		c1::test($item);
	}
}

return $arguments[0];


Expected result:
----------------
No output.

Actual result:
--------------
nginx returns "An error occurred."

php-fpm.log has:
[18-Apr-2021 21:53:25] WARNING: [pool www] child 193586 exited on signal 11 (SIGSEGV) after 11.391747 seconds from start

/var/log/messages has:
Apr 18 21:53:25 server1 kernel: traps: php-fpm[193586] general protection fault ip:55fa3e1d2dbf sp:7ffe87e6d8c0 error:0 in php-fpm[55fa3e0e4000+11c000]


Patches

Pull Requests

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2021-04-19 10:34 UTC] nikic@php.net
I'm not able to reproduce this on current master. It's possible that the issue has already been fixed.
 [2021-04-23 01:55 UTC] ryan dot brothers at gmail dot com
Thanks, I was able to reproduce the issue in master.  It seems to be related to certain php.ini files.  What I did was take the default php.ini-development file, but added these 4 lines at the top of the file:

zend_extension = opcache
opcache.enable = 1
opcache.jit = tracing
opcache.jit_buffer_size = 100M

When I do that, I can reproduce the issue.  The same issue happens if I start with php.ini-production and add the 4 lines.

Please let me know if this helps to reproduce the issue, or I'll try to narrow it down further.  Thank you again for your help.
 [2021-05-04 13:17 UTC] philippreddigau+php at gmail dot com
We can also confirm this issue on PHP 8.0.5 alpine based docker image.
Disabling the feature, fixes the problem.

dmesg logs:
1. Crash after refeshing the site:
[27876.626172] php-fpm[65114]: segfault at 0 ip 0000000000000000 sp 00007ffcf2210d50 error 14 in zero (deleted)[41e5e000+6400000]
[27876.626353] Code: Unable to access opcode bytes at RIP 0xffffffffffffffd6.

2. Crash after try to access again 
[27925.466121] php-fpm[65115]: segfault at 18 ip 0000558b23029c94 sp 00007ffcf2210d38 error 4 in php-fpm[558b23000000+3ba000]
[27925.466297] Code: eb 19 49 83 c7 20 80 bb 22 02 00 00 00 74 0c 5a 5b 5d 41 5c 41 5d e9 7b c2 30 00 58 5b 5d 41 5c 41 5d c3 55 53 51 49 8b 46 08 <48> 8b 68 18 48 8b 50 30 4d 89 3e 8b 58 2c 49 89 56 08 48 8b 55 48

3. Crash, refreshing again
[27945.021344] php-fpm[65116]: segfault at 0 ip 0000000000000000 sp 00007ffcf22084a8 error 14 in zero (deleted)[41e5e000+6400000]
[27945.021448] Code: Unable to access opcode bytes at RIP 0xffffffffffffffd6.
 [2021-05-05 07:52 UTC] philippreddigau+php at gmail dot com
Added a repository with docker image that reproduces the issue:
https://github.com/ItsReddi/sandbox

Reproduce:
1) clone repo
2) docker-compose up -d
3) Refresh one or multiple times at http://localhost:8080/php/bug_80968.php
 [2021-05-05 13:34 UTC] nikic@php.net
-Status: Open +Status: Verified
 [2021-05-05 13:34 UTC] nikic@php.net
Not sure what I did wrong before, but I can reproduce the issue now (using built-in server, just --repeat mode doesn't seem to be sufficient) and get this assertion failure:

php: ext/opcache/jit/zend_jit_trace.c:340: zend_jit_trace_type_to_info_ex: Assertion `info & (1 << type)' failed.

type is IS_UNDEF and the opline is the RETURN in __callStatic().
 [2021-05-05 14:47 UTC] nikic@php.net
-Summary: jit segfault on php-fpm +Summary: JIT segfault with return from required file
 [2021-05-05 14:47 UTC] nikic@php.net
Slightly reduced variant just to show that this has no relation to __callStatic trampolines:

1.php
<?php
function foo($arguments) { 
    var_dump(require('2.php'));
}
for ($i = 0; $i < 100; $i++) {
    foo([[1, 2]]);
}

2.php
<?php 
if (is_array($arguments[0])) {
    foreach ($arguments[0] as $item) {
        foo([$item]);
    }
}
return $arguments[0];
 [2021-05-11 08:21 UTC] nikic@php.net
-Assigned To: +Assigned To: dmitry
 [2021-05-20 13:51 UTC] git@php.net
Automatic comment on behalf of dstogov
Revision: https://github.com/php/php-src/commit/6e2d47e071f5343b3de169a2dc6ce648d145d1a2
Log: Fixed bug #80968 (JIT segfault with return from required file)
 [2021-05-20 13:51 UTC] git@php.net
-Status: Verified +Status: Closed
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Nov 21 12:01:29 2024 UTC