php 8.4.27 不修复弱类型比较漏洞,因其是语言固有特性;必须全局用 === 替代 ==,敏感逻辑须配合 hash_equals、类型声明与边界测试。

CVE-2026-109618 和 CVE-2026-109619 是远程代码执行类漏洞,和 == 弱比较无关。所谓“弱类型比较漏洞”,实际是开发者误用 == 导致的逻辑缺陷,比如 "0e12345" == "0e67890" 返回 true,常被用于绕过密码哈希比对或权限校验。
为什么 upgrade 到 8.4.27 不能解决 == 比较问题
PHP 的松散比较(==)规则自 PHP 4 起就已稳定,8.4.27 只是修复了内存越界、Zval 解析异常等底层安全问题,**不会、也不能改变 == 的语义**。官方明确表示:这是语言设计选择,不是 bug。试图靠升级版本来“修复弱比较”,等于指望换轮胎解决刹车失灵——方向错了。
真正有效的修复方式:用 === 替代 ==,且必须全局覆盖
所有涉及身份校验、权限判断、支付金额比对、Token 验证等敏感逻辑的地方,== 必须无条件替换为 ===。这不是建议,是硬性红线。
-
password_verify($input, $hash)已自带时序安全,无需手写比对 - 自定义 token 校验不能写
if ($_GET['token'] == $valid_token),必须用hash_equals($valid_token, $_GET['token']) - 数据库查出的用户角色是字符串
"admin",比对时别写$role == "admin",而要写$role === "admin" - 注意:空数组
[]、字符串"0"、整数0、false在==下全等价,但===严格区分类型和值
静态分析能帮你发现漏网之鱼
光靠人工 grep 很难扫净全部 ==。推荐在 CI 中加入 PHPStan 或 Psalm 的自定义规则:
修复 Core bailout 状态损坏安全问题,以及 BZ2、DOM、PDO、Opcache/JIT 内存与执行错误,改进 Unicode 字素处理、URL 解析、TLS 流状态、信号分发及会话错误处理。
- 用 PHPStan 扩展包
phpstan-phpunit+ 自定义 rule,标记所有非布尔上下文中的==使用 - Psalm 配置中启用
LessSpecificReturnStatement并加注释@psalm-assert ===强化断言 - 简单快速方案:在项目根目录跑
grep -r "== " --include="*.php" . | grep -v "===\|function\|class\|if (.*==.*bool\|return.*==",再人工复核结果
测试必须包含弱类型边界用例
光改代码不写测试,等于没修。每个涉及比较的函数,至少补 3 类用例:
-
"0"vs0vsfalsevs"" -
"123abc"vs123(字符串转数字截断) -
"0e123456"vs"0e789012"(科学计数法解析为 0)
PHPUnit 中直接用 $this->assertSame() 断言,而非 $this->assertEquals()。
getUserById() 返回 array|false,上层用 if ($user == null) 判断,表面看没问题,实则把 ["id" => 0] 也当成了空用户。这种隐式转换,只有靠类型声明 + 严格比较 + 边界测试三者咬合才能兜住。php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!










