PHP_Code_Challenge-6-SQL注入&Union

题目

<?php
if($_POST[user] && $_POST[pass]) {
 $conn = mysql_connect("********", "*****", "********");
 mysql_select_db("challenges") or die("Could not select database");
 if ($conn->connect_error) {
  die("Connection failed: " . mysql_error($conn));
}
$user = $_POST[user];
$pass = md5($_POST[pass]);
$sql = "select pwd from interest where uname='$user'";
$query = mysql_query($sql);
if (!$query) {
 printf("Error: %s
", mysql_error($conn));
 exit();
}
$row = mysql_fetch_array($query, MYSQL_ASSOC);
//echo $row["pwd"];
  if (($row[pwd]) && (!strcasecmp($pass, $row[pwd]))) {
 echo "<p>Logged in! Key:************** </p>";
}
else {
    echo("<p>Log in failure!</p>");
  }
}
?>

分析

$sql直接拼接$user后执行sql语句得到返回结果$query
初步判断存在sql注入
获得flag需满足if (($row[pwd]) && (!strcasecmp($pass, $row[pwd])))

  1. $query中pwd列要有值
  2. pwd列的值与MD5($pass)匹配

可以利用布尔盲注得到interest库中pwd列的值
但也可以利用sql语法union更快得到flag

知识点

Union

UNION用于把来自许多SELECT语句的结果组合到一个结果集合中。 列于每个SELECT语句的对应位置的被选择的列应具有相同的类型。(例如,被第一个语句选择的第一列应和被其它语句选择的第一列具有相同的类型。)在第一个SELECT语句中被使用的列名称也被用于结果的列名称。
其中关键是在第一个SELECT语句中被使用的列名称也被用于结果的列名称

这意味着union后的sql语句执行结果也会被列入pwd列中
我们可以使union前的sql语句无结果,其后的sql语句的结果与MD5($pass)相同,使pwd列的值与MD5($pass)匹配

解法

user=' union select "21232f297a57a5a743894a0e4a801fc3"#&pass=admin

原文地址:https://www.cnblogs.com/Rain99-/p/12604835.html