PCC 0.3.0 — PHP Secure Configuration Checker - Big 2026 Update
Release 0.3.0 of the PHP Secure Configuration Checker (pcc) is out: a 2026 update for PHP 8.x with new security checks, bug fixes, and cleanup.
Bug fixes
str_replace arguments reversed — The "GET overrides POST" detection was broken (subject was an empty string). Fixed.
Hardcoded path separator — Replaced
:withPATH_SEPARATORfor correct behavior on Windows.Redundant ini_atol() call — Removed duplicate conversion.
constant() without defined() guard — Prevents
ValueErroron PHP 8+ in two places (including ANSI colors).curl.cainfo Windows path check — Restructured to correctly detect absolute paths on both Unix and Windows.
Version gate and lifecycle
Minimum PHP version is now 8.1 (version gate and documentation updated).
test_old_php_version()reflects the 2026 lifecycle: PHP 8.1 = EOL, 8.2 = security-only, 8.3+ = supported.
Dead code removal
Removed handling and helptext for long-gone directives: magic_quotes_gpc, magic_quotes_runtime, magic_quotes_sybase, register_globals, always_populate_raw_post_data, asp_tags. Dropped assert.quiet_eval and track_errors from the known-safe list. Simplified iconv.*_encoding logic and the update/Snuffleupagus checks.
New security checks
From the 2026 PHP 8.x update:
session.sid_length — Flags short session IDs.
session.sid_bits_per_character — Flags low entropy density.
serialize_precision — Flags non-default values that can cause float serialization issues.
Additional checks added in the follow-up commit (12 directives):
session.serialize_handler — MEDIUM if
php(legacy, pipe-injection risk).session.gc_maxlifetime — COMMENT if > 86400 (24 h sessions).
zend.exception_ignore_args — MAYBE if off (stack traces may leak function arguments).
zend.exception_string_param_max_len — COMMENT if > 0 (stack traces may leak string parameters).
sqlite3.defensive — MEDIUM if off (writable schema enabled).
sqlite3.extension_dir — MEDIUM if set and writable.
unserialize_max_depth — MEDIUM if 0 (depth check disabled, deserialization bombs).
max_multipart_body_parts — MEDIUM if -1 (unlimited, DoS risk per CVE-2023-0662).
openssl.cafile / openssl.capath — MEDIUM if set but file/dir does not exist (MITM risk).
pcre.backtrack_limit / pcre.recursion_limit — COMMENT if 0 (unlimited; ReDoS / stack exhaustion risk).
error_log_mode — LOW if world-writable, COMMENT if world-readable.
register_argc_argv — COMMENT if on in web mode.
Roughly 50 directives were added to the known-safe list (e.g. fiber.stack_size, session.upload_progress.*, zend.enable_gc, zlib.output_compression, and many others), so they are no longer reported as unknown.
Verification
Syntax check, text output, and zero-unknown-directives were confirmed on PHP 8.1.34, 8.2.30, 8.3.30, 8.4.18, and 8.5.3.
Modernization
Replaced
strstr()/strpos() !== FALSEwithstr_contains().Added explicit parentheses for operator precedence where useful and
// fall throughcomments in theini_atol()switch.
Download
Source and releases: https://github.com/sektioneins/pcc
Issues and ideas: https://github.com/sektioneins/pcc/issues
bf