PHP代码审计系列基础文章(四)之代码执行漏洞篇
字数 1296 2025-08-11 21:26:21

PHP代码审计:代码执行漏洞详解

1. 代码执行漏洞原理

代码执行漏洞是指攻击者能够通过应用程序的输入点注入恶意代码,并在服务器端执行。PHP中由于提供了多种灵活的函数来执行动态代码,当这些函数的参数可控时,就可能造成严重的安全问题。

核心风险点:

  • 通过代码执行函数可以直接调用PHP任意代码
  • 代码执行可以进一步调用命令执行函数来控制系统
  • 导致RCE(远程代码/命令执行)漏洞

2. 主要代码执行函数及利用方式

2.1 eval()函数

功能:将字符串作为PHP代码执行

危险示例

$arg = $_REQUEST['value'];
eval($arg);

利用方式

  • 传入phpinfo();可查看PHP配置信息
  • 必须用分号结尾,否则会报错
  • 可执行多条语句,用分号分隔

2.2 assert()函数

功能:检查断言是否为false,但也可执行代码

危险示例

$arg = $_REQUEST['value'];
assert($arg);

特点

  • 比eval()更灵活,不需要分号结尾
  • 可拆分调用绕过WAF:
$a='ass'; $b='ert'; $c=$a.$b;
@$c($_REQUEST['value']);

2.3 preg_replace()函数

危险模式:使用/e修正符时

危险示例

@preg_replace("/123/e",$_REQUEST['value'],"1234567");

原理

  • /e模式使替换值被当作PHP代码执行
  • 在字符串"1234567"中匹配"123"并用传入值替换

2.4 create_function()函数

功能:创建匿名函数

危险示例

$a = create_function('$arg',$_REQUEST['x']);

利用方式

  • 第二个参数会在内部执行eval()
  • 需要闭合匿名函数的}使代码独立执行

2.5 array_map()函数

功能:将回调函数作用到数组的每个元素

危险示例

array_map($_REQUEST['arg1'],array($_REQUEST['arg2']));

原理

  • 第一个参数作为回调函数执行
  • 相当于assert(phpinfo())形式

2.6 call_user_func()系列

call_user_func()

call_user_func($_GET['a1'],$_GET['a2']);

call_user_func_array()

call_user_func_array($_GET['arg1'],$_GET['arg2']);
// arg2需为数组形式

2.7 array_filter()函数

危险示例

array_filter(array($_REQUEST['arg1']),$_REQUEST['arg2']);

特点

  • 第一个参数是回调函数的参数
  • 第二个参数是回调函数

2.8 ob_start()函数

危险示例

$cmd = 'system';
ob_start($cmd);
echo "$_REQUEST['arg']";
ob_end_flush();

2.9 usort()函数

危险示例(PHP>=5.6):

usort($_REQUEST,"assert");

功能:使用自定义函数对数组排序

2.10 array_walk()函数

危险示例

array_walk($_GET['arg1'],$_GET['arg2']);

注意:传入参数为数组,形参需加[]

2.11 动态函数

危险示例

$_REQUEST['arg1']($_REQUEST['arg2']);

原理:直接拼接字符串作为函数名调用

3. 代码审计要点

  1. 识别危险函数:熟悉上述所有可能执行代码的函数
  2. 参数追踪:检查这些函数的参数是否用户可控
  3. 输入过滤:查看是否有对用户输入进行有效过滤
  4. 上下文分析:分析代码执行的环境和条件
  5. 利用链构造:考虑如何闭合语句或构造有效payload

4. 防御建议

  1. 避免直接使用eval()等危险函数
  2. 使用白名单限制可执行函数
  3. 对用户输入进行严格过滤和转义
  4. 禁用危险函数(如eval、assert等)
  5. 使用安全的替代方案实现相同功能

5. 总结

代码执行漏洞是PHP应用中最危险的漏洞之一,审计时需要特别关注文中提到的各类函数。掌握这些函数的特性和利用方式,有助于在代码审计中快速发现潜在风险点。实际审计中应结合具体业务场景,分析参数传递路径,判断是否存在可利用的代码执行点。

PHP代码审计:代码执行漏洞详解 1. 代码执行漏洞原理 代码执行漏洞是指攻击者能够通过应用程序的输入点注入恶意代码,并在服务器端执行。PHP中由于提供了多种灵活的函数来执行动态代码,当这些函数的参数可控时,就可能造成严重的安全问题。 核心风险点: 通过代码执行函数可以直接调用PHP任意代码 代码执行可以进一步调用命令执行函数来控制系统 导致RCE(远程代码/命令执行)漏洞 2. 主要代码执行函数及利用方式 2.1 eval()函数 功能 :将字符串作为PHP代码执行 危险示例 : 利用方式 : 传入 phpinfo(); 可查看PHP配置信息 必须用分号结尾,否则会报错 可执行多条语句,用分号分隔 2.2 assert()函数 功能 :检查断言是否为false,但也可执行代码 危险示例 : 特点 : 比eval()更灵活,不需要分号结尾 可拆分调用绕过WAF: 2.3 preg_ replace()函数 危险模式 :使用 /e 修正符时 危险示例 : 原理 : /e 模式使替换值被当作PHP代码执行 在字符串"1234567"中匹配"123"并用传入值替换 2.4 create_ function()函数 功能 :创建匿名函数 危险示例 : 利用方式 : 第二个参数会在内部执行eval() 需要闭合匿名函数的 } 使代码独立执行 2.5 array_ map()函数 功能 :将回调函数作用到数组的每个元素 危险示例 : 原理 : 第一个参数作为回调函数执行 相当于 assert(phpinfo()) 形式 2.6 call_ user_ func()系列 call_ user_ func() : call_ user_ func_ array() : 2.7 array_ filter()函数 危险示例 : 特点 : 第一个参数是回调函数的参数 第二个参数是回调函数 2.8 ob_ start()函数 危险示例 : 2.9 usort()函数 危险示例 (PHP>=5.6): 功能 :使用自定义函数对数组排序 2.10 array_ walk()函数 危险示例 : 注意 :传入参数为数组,形参需加 [] 2.11 动态函数 危险示例 : 原理 :直接拼接字符串作为函数名调用 3. 代码审计要点 识别危险函数 :熟悉上述所有可能执行代码的函数 参数追踪 :检查这些函数的参数是否用户可控 输入过滤 :查看是否有对用户输入进行有效过滤 上下文分析 :分析代码执行的环境和条件 利用链构造 :考虑如何闭合语句或构造有效payload 4. 防御建议 避免直接使用eval()等危险函数 使用白名单限制可执行函数 对用户输入进行严格过滤和转义 禁用危险函数(如eval、assert等) 使用安全的替代方案实现相同功能 5. 总结 代码执行漏洞是PHP应用中最危险的漏洞之一,审计时需要特别关注文中提到的各类函数。掌握这些函数的特性和利用方式,有助于在代码审计中快速发现潜在风险点。实际审计中应结合具体业务场景,分析参数传递路径,判断是否存在可利用的代码执行点。