Skip to content
Draft
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
1 change: 1 addition & 0 deletions ext/opcache/ZendAccelerator.h
Original file line number Diff line number Diff line change
Expand Up @@ -176,6 +176,7 @@ typedef struct _zend_accel_directives {
char *lockfile_path;
#endif
char *file_cache;
mode_t file_cache_permissions;
bool file_cache_read_only;
bool file_cache_only;
bool file_cache_consistency_checks;
Expand Down
70 changes: 70 additions & 0 deletions ext/opcache/tests/file_cache_permissions.phpt
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
--TEST--
opcache.file_cache_permissions
--EXTENSIONS--
opcache
--SKIPIF--
<?php
@mkdir(__DIR__ . '/opcache', 0777, true);
if (substr(PHP_OS, 0, 3) === 'WIN') {
die('skip not for Windows');
}
?>
--INI--
opcache.enable=1
opcache.enable_cli=1
opcache.file_cache="{PWD}/opcache"
opcache.file_cache_only=1
opcache.file_update_protection=0
opcache.file_cache_permissions=0644
--FILE--
<?php
$phpFile = __DIR__ . '/foo.php';
file_put_contents($phpFile, '<?php return 42;');
require $phpFile;
register_shutdown_function(static function () use ($phpFile): void {
@unlink($phpFile);
});

$opcacheDirectory = __DIR__ . '/opcache';
$iterator = new RecursiveIteratorIterator(
new RecursiveDirectoryIterator(
$opcacheDirectory,
FilesystemIterator::SKIP_DOTS,
),
);
foreach ($iterator as $splFileInfo) {
if (!$splFileInfo->isFile()) {
continue;
}
if (str_ends_with($splFileInfo->getPathname(), '/foo.php.bin')) {
var_dump(sprintf('%o', substr(fileperms($splFileInfo->getPathname()), -3)));
break;
}
}
?>
--CLEAN--
<?php
@unlink(__DIR__ . '/foo.php');

$opcacheDirectory = __DIR__ . '/opcache.php';
if (is_dir($opcacheDirectory)) {
$iterator = new RecursiveIteratorIterator(
new RecursiveDirectoryIterator(
$opcacheDirectory,
RecursiveDirectoryIterator::SKIP_DOTS,
),
RecursiveIteratorIterator::CHILD_FIRST,
);
foreach ($iterator as $splFileInfo) {
$path = $splFileInfo->getRealPath();
if ($splFileInfo->isDir()) {
@rmdir($path);
} else {
@unlink($path);
}
}
@rmdir($opcacheDirectory);
}
?>
--EXPECT--
string(6) "644"
20 changes: 20 additions & 0 deletions ext/opcache/zend_accelerator_module.c
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
*/

#include <time.h>
#include <fcntl.h>

#include "php.h"
#include "ZendAccelerator.h"
Expand Down Expand Up @@ -193,6 +194,23 @@ static ZEND_INI_MH(OnUpdateFileCache)
return SUCCESS;
}

static ZEND_INI_MH(OnUpdateFileCachePermissions)
{
mode_t *p = ZEND_INI_GET_ADDR();
char *end;
unsigned long val;

errno = 0;
val = ZEND_STRTOL(ZSTR_VAL(new_value), &end, 8);
if (errno != 0 || end != ZSTR_VAL(new_value) + ZSTR_LEN(new_value) || val > 0777) {
zend_accel_error(ACCEL_LOG_WARNING, "opcache.file_cache_permissions must be a valid octal mode between 0000 and 0777.\n");
return FAILURE;
}

*p = (mode_t) val;
return SUCCESS;
}

#ifdef HAVE_JIT
static ZEND_INI_MH(OnUpdateJit)
{
Expand Down Expand Up @@ -320,6 +338,7 @@ ZEND_INI_BEGIN()
#endif

STD_PHP_INI_ENTRY("opcache.file_cache" , NULL , PHP_INI_SYSTEM, OnUpdateFileCache, accel_directives.file_cache, zend_accel_globals, accel_globals)
STD_PHP_INI_ENTRY("opcache.file_cache_permissions", "0600", PHP_INI_SYSTEM, OnUpdateFileCachePermissions, accel_directives.file_cache_permissions, zend_accel_globals, accel_globals)
STD_PHP_INI_BOOLEAN("opcache.file_cache_read_only" , "0" , PHP_INI_SYSTEM, OnUpdateBool, accel_directives.file_cache_read_only, zend_accel_globals, accel_globals)
STD_PHP_INI_BOOLEAN("opcache.file_cache_only" , "0" , PHP_INI_SYSTEM, OnUpdateBool, accel_directives.file_cache_only, zend_accel_globals, accel_globals)
STD_PHP_INI_BOOLEAN("opcache.file_cache_consistency_checks" , "1" , PHP_INI_SYSTEM, OnUpdateBool, accel_directives.file_cache_consistency_checks, zend_accel_globals, accel_globals)
Expand Down Expand Up @@ -845,6 +864,7 @@ ZEND_FUNCTION(opcache_get_configuration)
#endif

add_assoc_string(&directives, "opcache.file_cache", ZCG(accel_directives).file_cache ? ZCG(accel_directives).file_cache : "");
add_assoc_long(&directives, "opcache.file_cache_permissions", ZCG(accel_directives).file_cache_permissions);
add_assoc_bool(&directives, "opcache.file_cache_read_only", ZCG(accel_directives).file_cache_read_only);
add_assoc_bool(&directives, "opcache.file_cache_only", ZCG(accel_directives).file_cache_only);
add_assoc_bool(&directives, "opcache.file_cache_consistency_checks", ZCG(accel_directives).file_cache_consistency_checks);
Expand Down
2 changes: 1 addition & 1 deletion ext/opcache/zend_file_cache.c
Original file line number Diff line number Diff line change
Expand Up @@ -1171,7 +1171,7 @@ int zend_file_cache_script_store(zend_persistent_script *script, bool in_shm)
return FAILURE;
}

fd = zend_file_cache_open(filename, O_CREAT | O_EXCL | O_RDWR | O_BINARY, S_IRUSR | S_IWUSR);
fd = zend_file_cache_open(filename, O_CREAT | O_EXCL | O_RDWR | O_BINARY, ZCG(accel_directives).file_cache_permissions);
if (fd < 0) {
if (errno != EEXIST) {
zend_accel_error(ACCEL_LOG_WARNING, "opcache cannot create file '%s', %s\n", filename, strerror(errno));
Expand Down
3 changes: 3 additions & 0 deletions php.ini-development
Original file line number Diff line number Diff line change
Expand Up @@ -1777,6 +1777,9 @@ ldap.max_links = -1
; SHM reset. The default "" disables file based caching.
;opcache.file_cache=

; The permissions of the files cached, in octal notation.
;opcache.file_cache_permissions=0600

; Enables or disables read-only mode for the second level cache directory.
; It should improve performance for read-only containers,
; when the cache is pre-warmed and packaged alongside the application.
Expand Down
3 changes: 3 additions & 0 deletions php.ini-production
Original file line number Diff line number Diff line change
Expand Up @@ -1779,6 +1779,9 @@ ldap.max_links = -1
; SHM reset. The default "" disables file based caching.
;opcache.file_cache=

; The permissions of the files cached, in octal notation.
;opcache.file_cache_permissions=0600

; Enables or disables read-only mode for the second level cache directory.
; It should improve performance for read-only containers,
; when the cache is pre-warmed and packaged alongside the application.
Expand Down
Loading