如何应对禁用exec函数后的PHP命令执行漏洞及加固措施?

2026-04-29 12:302阅读0评论SEO教程
  • 内容介绍
  • 文章标签
  • 相关推荐

本文共计967个文字,预计阅读时间需要4分钟。

如何应对禁用exec函数后的PHP命令执行漏洞及加固措施?

当Web服务器运行PHP环境时,直接修改主配置文件php.ini可一次性阻止exec及其同类函数被调用,适用于所有PHP进程,无需修改业务代码即可切断多数RCE输入。

1、使用文本编辑器打开php.ini文件,典型路径包括/etc/php/8.2/apache2/php.ini或/usr/local/php/etc/php.ini。

2、搜索disable_functions配置项,若该行以分号开头则删除分号取消注释。

3、在disable_functions = 后追加exec,passthru,shell_exec,system,proc_open,popen,pcntl_exec,多个函数间严格使用英文逗号分隔,注意不可添加空格

立即学习“PHP免费学习笔记(深入)”;

4、保存文件后执行systemctl restart apache2或systemctl restart php8.2-fpm,使配置立即生效。

二、利用open_basedir限制文件操作边界

即使exec等函数已被禁用,攻击者仍可能借助文件包含、临时目录写入或符号链接等方式实现跨目录访问,open_basedir能强制将所有文件类操作约束在指定路径内,形成第二道隔离屏障。

1、在php.ini中定位open_basedir指令,若不存在则新增一行。

2、设置其值为网站根目录与必需临时路径的组合,例如:/var/www/html:/tmp:/var/tmp

3、确保各路径之间使用冒号分隔,且末尾不带斜杠,避免因路径匹配失败导致功能异常。

4、重启PHP服务后,尝试在脚本中执行scandir('/')将返回false或警告,验证限制已生效。

三、检测并拦截动态函数调用行为

攻击者常绕过disable_functions,通过反射、变量函数、array_map等机制间接调用被禁函数,因此需在应用层主动识别并阻断此类调用链,而非仅依赖配置层封堵。

1、在关键执行入口处插入预检逻辑,调用is_callable('exec')判断函数是否可用。

2、进一步读取ini_get('disable_functions')返回值,使用逗号包围法校验exec是否在禁用列表中:stripos(',' . $disabled . ',', ',exec,') !== false

3、若检测到exec被禁但调用意图存在,立即记录日志并终止流程,避免后续反射或回调触发。

4、对用户可控的函数名参数(如$_GET['func'])实施白名单校验,仅允许safe_log、format_date等已知安全函数名通过。

四、屏蔽反引号命令执行操作符

PHP中反引号(`)操作符具有与shell_exec相同的功能,且不受disable_functions控制,是常见绕过点。必须在Web服务器层面或应用输入过滤中显式拦截该语法结构。

1、在Nginx配置的location块中添加rewrite规则,匹配URL中出现反引号的请求并返回403:if ($args ~ "`") { return 403; }

2、Apache环境下,在.htaccess中启用mod_rewrite后添加:RewriteCond %{QUERY_STRING} "`" [NC],RewriteRule ^ - [F]。

3、PHP应用层对所有用户输入执行preg_replace('/[`\\$\{\}]/', '', $input),清除反引号、美元符、花括号及反斜杠。

4、在日志中单独记录含反引号的请求,便于后续分析攻击尝试频率与来源IP。

五、部署PHP沙盒环境隔离高风险操作

对于确需执行外部命令的业务场景(如代码编译、图像处理),不应开放system/exec,而应启用独立沙盒进程,在资源、网络、文件系统维度实施硬性隔离,防止逃逸影响主服务。

1、使用firejail或bubblewrap启动受限子进程,禁止网络访问与文件系统写入,仅挂载只读的必要库路径。

2、通过pcntl_fork()创建子进程后,在子进程中调用posix_setsid()和chroot()构建轻量级隔离环境。

3、设置子进程最大执行时间为3秒,超时后由父进程调用pcntl_kill()强制终止。

4、命令输出统一重定向至内存缓冲区,禁止直接写入磁盘,输出内容须经HTML实体编码后再返回前端

标签:PHP

本文共计967个文字,预计阅读时间需要4分钟。

如何应对禁用exec函数后的PHP命令执行漏洞及加固措施?

当Web服务器运行PHP环境时,直接修改主配置文件php.ini可一次性阻止exec及其同类函数被调用,适用于所有PHP进程,无需修改业务代码即可切断多数RCE输入。

1、使用文本编辑器打开php.ini文件,典型路径包括/etc/php/8.2/apache2/php.ini或/usr/local/php/etc/php.ini。

2、搜索disable_functions配置项,若该行以分号开头则删除分号取消注释。

3、在disable_functions = 后追加exec,passthru,shell_exec,system,proc_open,popen,pcntl_exec,多个函数间严格使用英文逗号分隔,注意不可添加空格

立即学习“PHP免费学习笔记(深入)”;

4、保存文件后执行systemctl restart apache2或systemctl restart php8.2-fpm,使配置立即生效。

二、利用open_basedir限制文件操作边界

即使exec等函数已被禁用,攻击者仍可能借助文件包含、临时目录写入或符号链接等方式实现跨目录访问,open_basedir能强制将所有文件类操作约束在指定路径内,形成第二道隔离屏障。

1、在php.ini中定位open_basedir指令,若不存在则新增一行。

2、设置其值为网站根目录与必需临时路径的组合,例如:/var/www/html:/tmp:/var/tmp

3、确保各路径之间使用冒号分隔,且末尾不带斜杠,避免因路径匹配失败导致功能异常。

4、重启PHP服务后,尝试在脚本中执行scandir('/')将返回false或警告,验证限制已生效。

三、检测并拦截动态函数调用行为

攻击者常绕过disable_functions,通过反射、变量函数、array_map等机制间接调用被禁函数,因此需在应用层主动识别并阻断此类调用链,而非仅依赖配置层封堵。

1、在关键执行入口处插入预检逻辑,调用is_callable('exec')判断函数是否可用。

2、进一步读取ini_get('disable_functions')返回值,使用逗号包围法校验exec是否在禁用列表中:stripos(',' . $disabled . ',', ',exec,') !== false

3、若检测到exec被禁但调用意图存在,立即记录日志并终止流程,避免后续反射或回调触发。

4、对用户可控的函数名参数(如$_GET['func'])实施白名单校验,仅允许safe_log、format_date等已知安全函数名通过。

四、屏蔽反引号命令执行操作符

PHP中反引号(`)操作符具有与shell_exec相同的功能,且不受disable_functions控制,是常见绕过点。必须在Web服务器层面或应用输入过滤中显式拦截该语法结构。

1、在Nginx配置的location块中添加rewrite规则,匹配URL中出现反引号的请求并返回403:if ($args ~ "`") { return 403; }

2、Apache环境下,在.htaccess中启用mod_rewrite后添加:RewriteCond %{QUERY_STRING} "`" [NC],RewriteRule ^ - [F]。

3、PHP应用层对所有用户输入执行preg_replace('/[`\\$\{\}]/', '', $input),清除反引号、美元符、花括号及反斜杠。

4、在日志中单独记录含反引号的请求,便于后续分析攻击尝试频率与来源IP。

五、部署PHP沙盒环境隔离高风险操作

对于确需执行外部命令的业务场景(如代码编译、图像处理),不应开放system/exec,而应启用独立沙盒进程,在资源、网络、文件系统维度实施硬性隔离,防止逃逸影响主服务。

1、使用firejail或bubblewrap启动受限子进程,禁止网络访问与文件系统写入,仅挂载只读的必要库路径。

2、通过pcntl_fork()创建子进程后,在子进程中调用posix_setsid()和chroot()构建轻量级隔离环境。

3、设置子进程最大执行时间为3秒,超时后由父进程调用pcntl_kill()强制终止。

4、命令输出统一重定向至内存缓冲区,禁止直接写入磁盘,输出内容须经HTML实体编码后再返回前端

标签:PHP