Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
22 changes: 20 additions & 2 deletions ext/opcache/ZendAccelerator.c
Original file line number Diff line number Diff line change
Expand Up @@ -1544,8 +1544,26 @@ static void zend_accel_add_key(zend_string *key, zend_accel_hash_entry *bucket)
/* Must perform the same check as phar_compile_file(). */
static zend_always_inline bool is_phar_file(const zend_string *filename)
{
return filename && strstr(ZSTR_VAL(filename), ".phar") &&
!strstr(ZSTR_VAL(filename), "://");
if (!filename || strstr(ZSTR_VAL(filename), "://")) {
return false;
}

const char *path = ZSTR_VAL(filename);
const char *basename = zend_memrchr(path, '/', ZSTR_LEN(filename));
#if defined(PHP_WIN32) || defined(ZEND_WIN32)
const char *backslash = zend_memrchr(path, '\\', ZSTR_LEN(filename));
if (backslash && (!basename || backslash > basename)) {
basename = backslash;
}
#endif
const char *marker = basename ? basename + 1 : path;
while ((marker = strstr(marker, ".phar"))) {
marker += sizeof(".phar") - 1;
if (*marker == '\0' || *marker == '.') {
return true;
}
}
return false;
}

static zend_persistent_script *store_script_in_file_cache(zend_persistent_script *new_persistent_script)
Expand Down
80 changes: 80 additions & 0 deletions ext/opcache/tests/gh25130.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
--TEST--
GH-25130: Harmonize opcache is_phar_file marker check with ext/phar
--EXTENSIONS--
opcache
--CONFLICTS--
server
--FILE--
<?php
$dir = __DIR__ . '/gh25130';
@mkdir($dir . '/dir.phar', 0777, true);
@mkdir($dir . '/dir.pharabcd', 0777, true);

file_put_contents($dir . '/prepend.php', <<<'PHP'
<?php
class Interceptor {
public function url_stat(string $path, int $flags): array|false {
$logFile = __DIR__ . '/stat_calls.log';
file_put_contents($logFile, basename($path) . "\n", FILE_APPEND);
return false;
}
}
stream_wrapper_unregister('phar');
stream_wrapper_register('phar', 'Interceptor');
PHP);

file_put_contents($dir . '/dir.phar/test.php', '<?php echo 1;');
file_put_contents($dir . '/dir.pharabcd/test.php', '<?php echo 2;');
file_put_contents($dir . '/test.pharma.php', '<?php echo 3;');
file_put_contents($dir . '/test.pharma.report.php', '<?php echo 4;');
file_put_contents($dir . '/test.pharma.phar.php', '<?php echo 5;');
file_put_contents($dir . '/test.phar.php', '<?php echo 6;');
file_put_contents($dir . '/include_test_phar.php', '<?php include __DIR__ . "/test.phar";');
file_put_contents($dir . '/test.phar', '<?php echo 7;');

include 'php_cli_server.inc';
$ini = trim((string) getenv('TEST_PHP_EXTRA_ARGS'));
$ini .= ($ini !== '' ? ' ' : '') . '-d opcache.enable=1 -d opcache.enable_cli=1 -d opcache.file_update_protection=0 -d auto_prepend_file=' . $dir . '/prepend.php';
php_cli_server_start($ini);

$endpoints = [
'/gh25130/dir.phar/test.php',
'/gh25130/dir.pharabcd/test.php',
'/gh25130/test.pharma.php',
'/gh25130/test.pharma.report.php',
'/gh25130/test.pharma.phar.php',
'/gh25130/test.phar.php',
'/gh25130/include_test_phar.php',
];

foreach ($endpoints as $endpoint) {
file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . $endpoint);
file_get_contents('http://' . PHP_CLI_SERVER_ADDRESS . $endpoint);
}

$logFile = $dir . '/stat_calls.log';
if (file_exists($logFile)) {
echo file_get_contents($logFile);
}
?>
--CLEAN--
<?php
$dir = __DIR__ . '/gh25130';
@unlink($dir . '/dir.phar/test.php');
@unlink($dir . '/dir.pharabcd/test.php');
@unlink($dir . '/test.pharma.php');
@unlink($dir . '/test.pharma.report.php');
@unlink($dir . '/test.pharma.phar.php');
@unlink($dir . '/test.phar.php');
@unlink($dir . '/include_test_phar.php');
@unlink($dir . '/test.phar');
@unlink($dir . '/prepend.php');
@unlink($dir . '/stat_calls.log');
@rmdir($dir . '/dir.phar');
@rmdir($dir . '/dir.pharabcd');
@rmdir($dir);
?>
--EXPECT--
test.pharma.phar.php
test.phar.php
test.phar
Loading