php变量覆盖漏洞学习
合上吧,没有新姿势。
全局变量覆盖
1 |
|
当register_globals=Off的时候,下一个程序接收的时候应该用$_GET[‘id’]来接受传递过来的值;
当register_globals=On的时候,下一个程序可以直接使用$id来接受值,也可以用$_GET[‘id’]来接受传递过来的值。
tips:如果上面的代码中,已经对变量$id赋了初始值,比如$id=0,那么即使在URL中有/test.php?id=1,也不会将变量覆盖,id值为0
从 PHP » 4.2.0 版开始配置文件中 PHP 指令 register_globals 的默认值从 on 改为 off 了,自 PHP 5.3.0 起废弃并将自 PHP 5.4.0 起移除。源自Register Globals
$ $导致的变量覆盖问题
这里在url中传值?name=test
会将$name
的值覆盖掉,变成test
举个简单的例子:
1 |
|
extract()变量覆盖
extract()函数的具体用法,函数的定义如下:
int extract ( array &$array [, int $flags = EXTR_OVERWRITE [, string $prefix = NULL ]] )
其中,第二个参数指定函数将变量导入符号表时的行为,最常见的两个值是EXTR_OVERWRITE
和EXTR_SKIP
如果没有指定 flags
,则被假定为 EXTR_OVERWRITE
,也就是默认情况下使用EXTR_OVERWRITE
第二个参数 | 含义 |
---|---|
EXTR_OVERWRITE | 如果有冲突,覆盖已有的变量。 |
EXTR_SKIP | 如果有冲突,不覆盖已有的变量。 |
EXTR_PREFIX_SAME | 如果有冲突,在变量名前加上前缀 prefix 。 |
EXTR_PREFIX_ALL | 给所有变量名加上前缀 prefix 。 |
EXTR_PREFIX_INVALID | 仅在非法/数字的变量名前加上前缀 prefix 。 |
EXTR_IF_EXISTS | 仅在当前符号表中已有同名变量时,覆盖它们的值。其它的都不处理。 举个例子,以下情况非常有用:定义一些有效变量,然后从 $_REQUEST 中仅导入这些已定义的变量。 |
EXTR_PREFIX_IF_EXISTS | 仅在当前符号表中已有同名变量时,建立附加了前缀的变量名,其它的都不处理。 |
EXTR_REFS | 将变量作为引用提取。这有力地表明了导入的变量仍然引用了 array 参数的值。可以单独使用这个标志或者在 flags 中用 OR 与其它任何标志结合使用。 |
举个简单的例子:
1 |
|
当extract()
函数从用户可以控制的数组中导出变量时,可能发生变量覆盖。在这个例子里,extract()
从$_GET
中导出变量,从而可以导致任意变量被覆盖。
这里构造payload:http://127.0.0.2:82/files/not_study_php/test.php?flag=2
impor_request_variables变量覆盖
impor_request_variables函数的具体用法,函数定义如下:
bool import_request_variables ( string $types [, string $prefix ] )
impor_request_variables()
将GET
,POST
,Cookie
中的变量导入到全局,可以用字母‘G’
、‘P’
和‘C’
分别表示 GET
、POST
和Cookie
。这些字母不区分大小写,所以你可以使用‘g’、‘p’和‘c’的任何组合。注意这些字母的顺序,当使用“gp”
时,POST
变量将使用相同的名字覆盖 GET
变量。任何 GPC
以外的字母都将被忽略。
适用php版本:(PHP 4 >= 4.1.0, PHP 5 < 5.4.0)
举个简单的例子:
1 |
|
这里构造payload:http://127.0.0.2:82/files/not_study_php/test.php?flag=1
parse_str()变量覆盖
parse_str函数的具体用法,函数的定义如下:
void parse_str ( string $encoded_string [, array &$result ] )
举个简单的例子:
1 |
|
正常访问
url中参数可控
Reference
- 《白帽子讲Web安全》
- 代码审计|变量覆盖漏洞