盘点PHP中的变量覆盖漏洞

盘点PHP中的变量覆盖漏洞

原创 庆尘qc Daylight庆尘 2024-04-27 00:01

最近在学习PHP代码审计中的变量覆盖问题,所以写了一篇文章简单总结一下,欢迎师傅们指正

一、$$动态变量

1、基本语法

PHP动态变量是指一个变量名的变量名可以动态的设置和使用,一个变量获取另一个变量的值作为这个变量的变量名。

例如下面

所以运行之后结果则为HelloWorld,其实就类似于C语言的指针

2、漏洞案例

分析题目,由于system函数执行的是$a,但现在$a的值是”ping 127.0.0.1″,所以我们需要想办法覆盖$a的值为我们指定的命令,这样才能造成命令执行漏洞,答案如下

这样传参了之后就变为

从而利用变量覆盖漏洞让system函数执行任何我们传入的语句,也就是命令执行漏洞

二、extract()

1、基本语法

PHP extract()函数用于将数组中的变量导入到当前的符号表中。它需要一个关联数组数组,并将键作为变量名和值作为变量值。

例如下面

当以GET方式传入?name=tacoking&age=21&id=123456时,输出的结果就是$name=tacoking;$age=22;$id=123456

也就是name、age、id作为变量名,传进来的值作为了它们的变量值

2、漏洞案例

同理,我们也是需要想法设法覆盖掉$a的值,可以看到这里$
GET[‘1’]和$
GET[‘2’]的值作为键值对会被引入符号表,所以我们只需要进行如下传参

这样就可以得到$a=whoami,从而覆盖掉$a原来的参数值,也就是变量覆盖漏洞

三、list()

1、基本语法

list() 函数用于将数组中的值赋给一组变量

2、漏洞案例

这里的意思也就时$a的值会等于$_GET[‘1’],所以此处我们直接传入$a的值为我们的payload就可以了,传参如下

四、parse_str()

1、基本语法

parse_str() 函数用于解析 URL 查询字符串,并将其中的参数赋值给相应的变量

2、漏洞案例

示例代码,下面附上一段存在变量覆盖导致RCE的漏洞代码案例

payload传参如下

那这里的parse_str就变为了下面这样

所以此时$com[‘cmd’]的值就为whoami,自然也就造成了变量覆盖的任意命令执行

五、mb_parse_str()

mb_parse_str()
PHP 中的函数用于解析 GET、POST 和 COOKIE 数据并设置全局变量。它解析 URL 编码的数据并检测编码。之后,它转换内部编码中的编码并设置全局变量的值。PHP 7 或更高版本支持此功能。

mb_parse_str()函数和parse_str()类似,所以不再做累赘,感兴趣的可自行研究。

六、compact()

1、基本语法

compact() 函数用于将多个变量转换为关联数组,其中变量名将成为数组的键,变量的值将成为数组的值

2、漏洞案例

示例代码

传参如下

如果外部变量和compact参数可控,就可以利用这种方法进行变量覆盖

七、register_globals配置

当register_globals全局变量设置开启时,传递过来的值会被直接注册为全局变量而使用,这会造成全局变量覆盖

在PHP5.3之前 默认开启 PHP5.3默认关闭  PHP5.6及5.7已经被移除

例如下列漏洞代码

这样传入的num=1就会被注册并使用,导致$num不为空,从而获得flag

八、import_request_variables()

(PHP 4 >= 4.1.0, PHP 5 < 5.4.0)

import_request_variables — 将 GET/POST/Cookie 变量导入到全局作用域中

将 GET/POST/Cookie 变量导入到全局作用域中。如果禁止了 register_globals,但又想用全局变量,就可以尝试该函数,简单来说就是用于
手动注册传入的变量

例如下面这个漏洞代码案例