我有两个脚本,一个是verify.php和一个register.php。
在我的注册页面上,我使用了这个..
$salt = hash('sha256', uniqid(mt_rand(), true) . $email);
$storedHash = $salt . $password;
for ( $i = 0; $i < 50000; $i ++ )
{
$storedHash = hash('sha256', $storedHash);
}
$sql = "INSERT INTO authentication (email, password, fname, lname, created_at) VALUES ('$email', '$storedHash', '$fname', '$lname', '$today')";
这是我的用户登录类..
<?php
include 'dbinclude.php';
// Class User
class user {
var $username;
var $password;
var $hashed;
var $salt;
function loginUser() {
require 'dbinclude.php';
$sql = "SELECT * FROM authentication WHERE email='" . $this->username . "';";
$query = mysqli_query($conn,$sql);
$fetch = mysqli_fetch_assoc($query);
$id = $fetch['userid'];
$storedHash = $fetch['password'];
$salt = substr($storedHash, 0, 64);
$validateHash = $salt . $this->password;
$validateHash = hash('sha256', $validateHash);
if ($storedHash == $validateHash)
{
//The entered password is correct.
$user = array(
"status" => "allow",
"email" => $fetch['email'],
"fname" => $fetch['fname'],
"lname" => $fetch['lname'],
"id" => $id,
"setupacc" => $fetch['setupacc'],
"setupleads" => $fetch['setupleads'],
"setupclients" => $fetch['setupclients'],
"hash" => $storedHash,
"salt" => $salt
);
return $user;
}
else
{
//The entered password is incorrect.
$user = array(
"status" => "deny",
"email" => $fetch['email'],
"fname" => $fetch['fname'],
"lname" => $fetch['lname'],
"id" => $id,
"setupacc" => $fetch['setupacc'],
"setupleads" => $fetch['setupleads'],
"setupclients" => $fetch['setupclients'],
"hash" => $storedHash,
"salt" => $salt
);
return $user;
}
}
}
?>
在我的登录页面上,我使用以下代码..
<?php
session_start();
require 'includes/dbinclude.php';
require 'includes/class.user.php';
$email = mysqli_real_escape_string($conn, $_POST['email']);
$password = mysqli_real_escape_string($conn, $_POST['password']);
// New login object? or class..
$login = new user();
$login->username = $email;
$login->password = $password;
$loginstatus = $login->loginUser();
$status = $loginstatus['status'];
$fname = $loginstatus['fname'];
$lname = $loginstatus['lname'];
$id = $loginstatus['id'];
$email = $loginstatus['email'];
$setupacc = $loginstatus['setupacc'];
$setupleads = $loginstatus['setupleads'];
$setupclients = $loginstatus['setupclients'];
// Set User Info in Session
$_SESSION['email'] = $email;
$_SESSION['fname'] = $fname;
$_SESSION['lname'] = $lname;
$_SESSION['id'] = $id;
$_SESSION['setupacc'] = $setupacc;
$_SESSION['setupleads'] = $setupleads;
$_SESSION['setupclients'] = $setupclients;
// Debug Display
echo "Class Pass: " . $login->password;
echo "Salt: " . $loginstatus['salt'];
echo "Hashed: " . $loginstatus['hash'];
if($status == "denied") {
?>
<script>
location.replace("http://hashed.com/?alertstatus=notauthed");
</script>
<?php
} elseif($status == "allow") {
?>
<script>
location.replace("http://hashed.com/app.php");
</script>
<?php
} else {
?>
<script>
location.replace("http://hashed.com/?alertstatus=notauthed");
</script>
<?php
}
?>
出于某种原因,它不会在登录时验证我的哈希值。我可以看到它存储哈希,成功解析盐但它不会验证?
答案 0 :(得分:3)
请记住,散列是一种单向函数,所以没有一种叫做“解密”的概念。哈希。您对密码执行某些操作(哈希)并将其存储在数据库中。接下来,当您需要验证用户提供的密码时,对用户提供的密码执行相同的操作(哈希或执行相同的哈希转换),然后将生成的哈希值与您的密码进行比较。 ;已保存在数据库中。如果匹配,则用户必须提供正确的密码。
在验证例程中,您将获取盐:
$salt = substr($storedHash, 0, 64);
但是在创建$ storedHash时,您已经损坏了并丢失了原始的盐:
$storedHash = $salt . $password;
for ( $i = 0; $i < 50000; $i++ )
{
$storedHash = hash('sha256', $storedHash);
}
在上述for循环之后,无法从$salt
获取原始$storedHash
。
您需要更改存储哈希值和盐的方式(将盐存储在数据库中),或者您需要更改验证用户的方式&#39 ; $validateHash
中的密码。
当您对最初的$salt + $password
进行哈希扫描50,000次时,您还需要在用户提供密码时再次执行相同操作,因此您的$ validateHash应如下所示:
$salt = $this->salt; // salt is also stored in the database
$validateHash = $salt . $this->password;
for ( $i = 0; $i < 50000; $i++ )
{
$validateHash = hash('sha256', $validateHash);
}