常见的题型有4种
1.题目中要求一个字符串与md5后的值相等
<?php
header("Content-Type:text/html;cahrset-utf-8");
show_source(__FILE__);
include('flag.php');
$md5=$_GET['md5'];
if($md5 == md5($md5)){
echo 'GET_FLAG'.$flag;
}else{
echo 'md5校验失败';
}
?>
通过上面PHP 0e漏洞的原理,也就将此题转化成 ->寻找一个字符串(0e开头)加密后(还是0e开头),弱比较相等。?md5=0e215962017
2.
<?php
header("Content-Type:text/html;charset=utf-8");
show_source(__FILE__);
include('flag.php');
$username = $_GET['username'];
$password = $_GET['password'];
if($username != $password){
if(md5($username) == md5($password)){
echo 'GET_FLAG:'.$flag;
}else{
echo 'md5校验出错...';
}
}else{
echo '用户名密码不能相等!';
}
?> 用户名密码不能相等
题目中,要求两个字符串值不能相等,但是两个字符串经过md5加密后的值需要相等,通过上面PHP 0e漏洞的原理,也就将此题转化成 -> 寻找两个值加密后以0e开头,且0e后面是纯数字的字符串即可,在php中0e会被当做科学计数法,就算后面有字母,其结果也都是0,所以if判断结果使true,成功绕过
例子:
240610708
0e462097431906509019562988736854
314282422
0e990995504821699494520356953734
571579406
0e972379832854295224118025748221
QLTHNDT
0e405967825401955372549139051580
QNKCDZO
0e830400451993494058024219903391
EEIZDOI
0e782601363539291779881938479162
TUFEPMC
0e839407194569345277863905212547
UTIPEZQ
0e382098788231234954670291303879
3.
<?php
header("Content-Type:text/html;charset=utf-8");
show_source(__FILE__);
include('flag.php');
$username = $_GET['username'];
$password = $_GET['password'];
if($username != $password){
if(md5($username) === md5($password)){
echo 'GET_FLAG:'.$flag;
}else{
echo 'md5校验出错...';
}
}else{
echo '用户名密码不能相等!';
}
?> 用户名密码不能相等!
全等运算符“===”,既比较值又比较类型,也就是说两个参数值要不相等,两个参数在md5加密后全相等,也就是说两个参数在md5加密后不仅值相等类型也要一致,此时就无法利用PHP 0e漏洞了,需要别的方法绕过。
可以利用md5在加密字符串时会warining,输出结果为NULL,传入两个数组,这样就能使两个参数在md5加密后的类型是一致的。?username[]=1&password[]=2
4.
if((string)$_POST['param1']!==(string)$_POST['param2'] &&md5($_POST['param1'])===md5($_POST['param2'])) { die("success!); }
这里对两个参数都进行了强制类型转换,所以一般的方法(用数组报错绕过肯定是行不通的了)所以我们必须找到两个文件,他们的内容不一样,但是md5值相等
TEXTCOLLBYfGiJUETHQ4hAcKSMd5zYpgqf1YRDhkmxHkhPWptrkoyz28wnI9V0aHeAuaKnak
TEXTCOLLBYfGiJUETHQ4hEcKSMd5zYpgqf1YRDhkmxHkhPWptrkoyz28wnI9V0aHeAuaKnak
这2个字符串md5编码后都是 faad49866e9498fc1719f5289e7a0269