Bug #78927 [Opn]: Crash in pcre2_code_free_8, zend_hash_destroy

From: Date: Tue, 10 Dec 2019 08:22:05 +0000
Subject: Bug #78927 [Opn]: Crash in pcre2_code_free_8, zend_hash_destroy
References: 1  Groups: php.bugs 
Request: Send a blank email to php-bugs+get-224181@lists.php.net to get a copy of this message
Edit report at https://bugs.php.net/bug.php?id=78927&edit=1 ID: 78927 Updated by: nikic@php.net Reported by: xnoreq at gmail dot com Summary: Crash in pcre2_code_free_8, zend_hash_destroy Status: Open Type: Bug Package: Reproducible crash Operating System: Linux 5.3.11 PHP Version: 7.4.0 Block user comment: N Private report: N New Comment: The --enable-sealloc flag is passed when building libpcre2 rather than PHP. Looking through the repository you linked, it seems that they indeed use this flag: https://git.archlinux.org/svntogit/packages.git/tree/trunk/PKGBUILD?h=packages/pcre2#n31 This compilation option is known to be incompatible with fork(), causes a range of other issues, and its use is discouraged by PCRE upstream. If you can, please petition ArchLinux to remove this flag and instead properly grant JIT permissions (W+X mmap) to programs that use PCRE JIT. Some references for issues this has caused: https://bugs.php.net/bug.php?id=78630 (tmp mounted noexec) https://bugs.exim.org/show_bug.cgi?id=1749 (the fork issue is mentioned here) https://bugs.exim.org/show_bug.cgi?id=2445 (breaks under low disk conditions) What isn't clear to me is why you're seeing this issue only on PHP 7.4, as it principally should affect PHP 7.3 (also using PCRE2) as well. For now, you can work around this issue by setting pcre.jit=0 for the script that uses forking. Previous Comments: ------------------------------------------------------------------------ [2019-12-09 23:47:36] xnoreq at gmail dot com Here's a simple test-case to reproduce the issue: $ php -f test.php test.php: <?php function regex() { preg_match('/(foo)(bar)(baz)/', 'foobarbaz', $matches, PREG_OFFSET_CAPTURE); } regex(); $pid = pcntl_fork(); if ($pid == -1) { die('error.'); } else if ($pid) { echo 'parent... '; pcntl_wait($pid); echo 'wait done'; } else { echo 'child.'; } ?> ------------------------------------------------------------------------ [2019-12-09 23:39:41] xnoreq at gmail dot com I was using 7.3.12 before. You can find the build files and patches here: https://git.archlinux.org/svntogit/packages.git/tree/repos/extra-x86_64?h=packages/php There's no --enable-sealloc option. ------------------------------------------------------------------------ [2019-12-09 21:16:23] nikic@php.net Thanks, the trace makes much more sense with this being a cli executable. fork() in most cases shouldn't matter, but here there might be a possible interference with the JIT mapped memory used by PCRE. Which Linux distro are you using and do you know how they build their PCRE binaries? If they are using --enable-sealloc, then this may indeed be incompatible with fork(). Which PHP version did you use before the upgrade? PHP 7.3 or something older? ------------------------------------------------------------------------ [2019-12-09 20:59:13] xnoreq at gmail dot com This is tiny tiny rss's update script (update_daemon2.php) which is a cli executable. That's why the process name is also php (and not php-cgi or php-fpm). It forks off do to multiple updates in parallel and I guess that leads to the invalid frees. ------------------------------------------------------------------------ [2019-12-09 08:52:21] nikic@php.net Based on code inspection alone, I don't see what the issue could be. ------------------------------------------------------------------------ The remainder of the comments for this report are too long. To view the rest of the comments, please view the bug report online at https://bugs.php.net/bug.php?id=78927 -- Edit this bug report at https://bugs.php.net/bug.php?id=78927&edit=1

« previous php.bugs (#224181) next »