WEB攻防-PHP特性
PHP缺陷函数
强等于与弱等于
在PHP中,=
代表赋值,==
代表弱等于,===
代表强等于,强等于和弱等于区别就在于是否比较类型
===:比较的不仅仅是值相等,而且类型也必须相等,只有当值和类型都相等的时候,才会返回ture |
==:弱比较只要求比较两个值在转化类型之后相等即可,如果两个值的类型不同,会尝试将其中一个值转化为另一个值的类型 |
综上,php比较运算符===
在进行比较时,会先比较两种字符串的类型是否相等,再比较值是否相等,一般md5弱等于比较常考
具体例子可以参考这一篇:PHP强相等&弱相等(附带科学计数法)_php 科学计数法-CSDN博客
intval函数
intval()
函数可以获取变量的整数值,常用于强制类型转换,常见语法int intval($var,$base)
,其中$var
为需要转化的变量,$base
为转换所需要的进制,当base为空时,默认值为0,会根据$var
的格式来调整转化进制,如果$var
以0开头,就使用8进制,如果$var
以0x开头,就使用16进制,否则使用10进制
当intval()
遇上数组的时候,不关系数组的内容,只判断数组内有没有元素,如果是空数组就返回0,如果是非空数组就返回1,但是当传入的$var
是数组中的某个值时,则当作变量来进行转换,而不是当作数组类型
$arr = array(8,6); |
当进行字符串转化时,会先判断字符串是否已数字开头,如果以数字开头,就会返回1个或多个连续的数字,如果以字母开头,就返回0
var_dump(intval('12abc')); int(12) |
另外,intval()
支持算术运算,即intval(5*5)
会返回25
strpos函数
strpos
函数用于查找一个字符串在另一个字符串中首次出现的位置(区分大小写),如果找到了匹配的字符串,strpos
函数就会返回匹配的第一个字符的索引值,否则就返回false
$str1 = "Hello, world!"; |
输出结果
当我们使用strpos
函数的时候,如果被匹配字符串开头就是我们要匹配的目标字符串,那么strpos就会返回0,此时如果采用弱比较,那么0==false
返回的是true,那么就会和没找到相关字符串情况相同,这个时候我们就可以成功绕过strpos函数
同时,如果加上换行符%0a时,strpos是检测不出来的,这也是这种函数的一种绕过思路
in_array
在PHP中,可以使用in_array()
函数直接确定某元素是否在数组中,如果数组中存在该元素,则会返回true,如果不存在,则返回false
语法in_array(search,array,type)
当type设置为strict时,就会判断类型,和强等于一致,但是如果不设置type,就不会判断类型,和弱等于一样,故其绕过方式可以参考强等于和弱等于
preg_match
preg_match
是检查是否匹配的函数,经常用在正则表达式的匹配中,其语法为preg_match($pattern,$subject,$matches,$flags,$offset)
,前两个参数是必须的,后三个参数不填写的话会有自己的默认值
通常preg_match
有以下几种方式绕过
数组绕过
由于preg_match
只能处理字符串,如果不按规定传入一个字符串,通常传入一个数组进去,就会使preg_match
失效,从而进行绕过
|
此时我们通常有三种绕过数组形式,如下所示
$a[] = 'flag.php'; |
str_replace
str_replace
函数的作用是替换字符串中的一些字符(区分大小写),其缺陷在于无法迭代过滤,只过滤一次,所以我们通常通过双写进行绕过
接下来进行双写flag进行绕过,将$a
改成flflagag.php
成功绕过,同时,由于preg_replace
对大小写不敏感,所以我们也可以大写绕过
CMS实例
MetInfo 任意文件读取
考点:str_replace
无法迭代过滤
通过实现../和./
的过滤,防止用户实现路径穿越,由于$dir
是可控的,我们可以通过绕过str_replace
来实现任意文件读取,故对应的payload为../http\..\config\config_db.php
,可以读到数据库配置文件
piwigo SQL注入
考点:使用in_array
函数但未使用第三个参数,导致过滤不严,造成代码的注入,进而引起sql注入
故payload为1,1 and if(ascii(substr((select database(),1,1))=112,1,sleep(3)));