我有以下登录脚本,我认为是安全的。但是,有人不断访问网站的管理部分并更改内容。
if(isset($_POST['submit'])) {
$error = false;
$user_login = stripslashes(strip_tags(htmlentities($_POST['user_login'])));
$pass_login = stripslashes(strip_tags(htmlentities($_POST['pass_login'])));
if(!empty($user_login) && !empty($pass_login)) {
$check_details=mysql_query("SELECT * FROM `admin` WHERE email='".$user_login."' AND password='".md5($pass_login)."'");
$status=mysql_num_rows($check_details);
if($status >= "1") {
$error = false;
$_SESSION['wmmadmin_loggedin'] = "1";
$_SESSION['wmmadmin_email'] = "".$user_login."";
header("Location: ./index.php");
}
if(!$status || $status == "0") {
$error = true;
echo "<div id=\"error\"><strong>Error!</strong><br />Login details were incorrect.</div>\n";
}
}
if(empty($user_login) || empty($pass_login)) {
$error = true;
echo "<div id=\"error\"><strong>Error!</strong><br />Enter your username and password.</div>\n";
}
}
在每个脚本的顶部都有一个函数调用:
function checkloggedin() {
if($_SESSION['wmmadmin_loggedin'] == "0" || $_SESSION['wmmadmin_loggedin'] !== "1" || $_SESSION['wmmadmin_email'] == "") {
header("Location: login.php");
exit;
}
}
我错过了什么吗?我需要阻止这些黑客!
由于 皮特
答案 0 :(得分:11)
有人可以发送以下user_login
:
user_login="nobody' OR 1 OR email='nobody"
这将导致查询
… WHERE email='nobody' OR 1 OR email='nobody' AND password='…'
被解释为
… WHERE email='nobody' OR 1 OR (email='nobody' AND password='…')
所以既然中间部分是真的(1
对MySQL来说是真的),一切都是真的并且授予了访问权限。这是一种经典的SQL注入攻击。
答案 1 :(得分:4)
让我们看看你如何违反正确逃避上下文的规则:
$user_login = stripslashes(strip_tags(htmlentities($_POST['user_login'])));
假设用户名DOES包含HTML标记。 <>
首先会转换为实体:<>
。
然后strip_tags()
尝试过滤标签 - 但没有!无用的函数调用。
然后你要删除斜杠。有吗?此函数调用仅在PHP中仍启用魔术引号时才有用,您应该检查它们是否存在,而不是盲目地删除它们。
htmlentities()
只会将双引号转换为实体,而不是单引号。并且您的SQL使用单引号来终止字符串。所以使用的一大堆函数仍然允许SQL注入。
不要自己发明安全功能。在SQL中使用mysql_real_escape_string()
和双引号,即可保存。或者使用mysqli或PDO使用预备语句。
答案 2 :(得分:0)
您需要清理$ user_login和$ pass_login,而不仅仅是检查它们是否为空。有人可以在其中传递SQL代码,并进行SQL注入攻击。
见这里:http://php.net/manual/en/security.database.sql-injection.php