必须显式配置并验证disable_functions与open_basedir等组合策略,因仅禁用函数易被proc_open、反序列化链或文件二次执行绕过;需严格设置路径权限、关闭allow_url_include,并实测执行报错才算生效。

在 Windows 7 上搭建 PHP 环境后,disable_functions 必须显式配置并验证生效,否则 exec、system、proc_open 等函数默认全部可用——攻击者上传一个含 system($_GET['cmd']) 的文件就能直接执行系统命令。
确认并修改正确的 php.ini 路径
Win7 下常见环境(如 WAMP、phpEnv、手工配置的 Apache+PHP)中,PHP 可能加载多个 php.ini,但只有“实际生效”的那个才管用:
- 新建一个
info.php放进 Web 根目录(如C:\wamp64\www\info.php),内容为<?php phpinfo(); ?> - 浏览器访问
http://localhost/info.php,搜索Loaded Configuration File—— 这个路径才是你必须编辑的文件,不是php.ini-development或桌面随便拷贝的副本 - 用记事本或 Notepad++ 打开该文件(避免 WordPad 等插入不可见字符),找到
disable_functions行;若被注释(前面有分号),删掉分号;若整行不存在,就在[PHP]段落里手动添加
disable_functions 的写法必须零容错
这个配置项极其脆弱,一个空格、大小写错误或末尾逗号都会导致整行失效,结果是“写了等于没写”:
- 必须全小写、英文逗号分隔、**逗号后绝对不能有空格**:
disable_functions = exec,passthru,shell_exec,system,proc_open,popen,pcntl_exec,eval,assert,symlink,dl,ini_set,file_put_contents - 禁止写成:
disable_functions = exec, system, shell_exec(空格让system变成" system",匹配失败) - 禁止大写:
SHELL_EXEC不会被识别 - 禁止末尾逗号:
...file_put_contents,会让整个值变为空 - 改完保存后,必须重启 Web 服务(如 Apache 服务或 phpEnv 托盘里的 “Restart Apache”),仅重启浏览器或刷新页面无效
光禁函数远远不够,必须加 open_basedir 隔离
攻击者常绕过 disable_functions:比如用 file_put_contents('shell.php', $_GET['c']) 写入一句话木马,再通过 URL 直接访问执行——这不需要调用 exec,只依赖文件写入+Web 服务器解析能力:
- 在同一个
php.ini文件里,找到或添加open_basedir配置,例如:open_basedir = C:\wamp64\www;C:\wamp64\tmp - 路径之间用英文分号分隔,不能用冒号(Windows);确保包含 Web 根目录和临时目录(如 session、upload_tmp_dir),否则登录、上传会失败
- 同时检查
allow_url_include = Off和expose_php = Off,这两项不设防会暴露版本、允许远程包含 - 对上传目录(如
C:\wamp64\www\uploads)右键 → 属性 → 安全 → 编辑 → 添加IIS_IUSRS或Users组 → 只勾选“写入”,**取消“读取和执行”、“列出文件夹内容”**——这是 Windows 层面的硬隔离,比 PHP 配置更底层
验证是否真被禁用,别信 phpinfo()
phpinfo() 只显示配置值,不反映运行时拦截效果。真正验证必须实测执行行为:
- 在 Web 根目录下建
test.php,内容为:<?php @exec('whoami', $o); print_r($o); ?> - 访问
http://localhost/test.php,如果页面空白且 PHP 错误日志(php_error.log)里出现Warning: exec() has been disabled for security reasons,才算成功 - CLI 下也要验证:
C:\wamp64\bin\php\php8.2.10\php.exe -r "var_dump(exec('whoami'));"—— CLI 有自己的php.ini,路径可通过php --ini查看,漏改就留后门 - 特别注意
proc_open:它常被用来绕过,测试用proc_open('cmd /c echo test', [], $pipes),同样应报 disabled warning
最易被忽略的是:Web 服务器本身是否允许执行上传的 .php 文件。即使 PHP 层禁了函数、锁了路径,如果 Apache 的 httpd.conf 里对 uploads 目录没加 Options -ExecCGI 或 Nginx 没配 fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name,攻击者仍可能靠上传 shell.php 直接触发解析执行。
php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











