Reputation: 197
I use the following code to store a password into mysql
if (!$errors) {
// include the connection file
require_once('connection.inc.php');
$conn = dbConnect('write');
// create a salt using the current timestamp
$salt = time();
// encrypt the password and salt
$pwd = sha1($password, $salt);
echo $pwd;
// prepare SQL statement
$sql = 'INSERT INTO users (username, salt, pwd)
VALUES (?, ?, ?)';
$stmt = $conn->stmt_init();
$stmt = $conn->prepare($sql);
// bind parameters and insert the details into the database
$stmt->bind_param('sis', $username, $salt, $pwd);
$stmt->execute();
if ($stmt->affected_rows == 1) {
$success = "$username has been registered. You may now log in.";
} elseif ($stmt->errno == 1062) {
$errors[] = "$username is already in use. Please choose another username.";
} else {
$errors[] = 'Sorry, there was a problem with the database.';
}
}
The password field, pwd, is defined as CHAR 40. When I examine it I see that it contains the following:
ƒ7Ž{9‰ù|EòsŒs”ºþ
no matter what password I enter. Naturally, this doesn't compare to the password when I try to login looking at it with this code:
require_once('connection.inc.php');
$conn = dbConnect('read');
// get the username's details from the database
$sql = 'SELECT salt, pwd FROM users WHERE username = ?';
// initialize and prepare statement
$stmt = $conn->stmt_init();
$stmt->prepare($sql);
// bind the input parameter
$stmt->bind_param('s', $username);
// bind the result, using a new variable for the password
$stmt->bind_result($salt, $storedPwd);
$stmt->execute();
$stmt->fetch();
// encrypt the submitted password with the salt
// and compare with stored password
if (sha1($password . $salt) == $storedPwd) {
$_SESSION['authenticated'] = 'Jethro Tull';
// get the time the session started
$_SESSION['start'] = time();
session_regenerate_id();
header("Location: $redirect");
exit;
} else {
// if no match, prepare error message
echo " pwd " . $password;
echo " salt " . $salt;
echo " sha1 " . sha1($password . $salt);
echo " St. pwd " . $storedPwd;
$error = 'Invalid username or password';
}
Does anyone know why this is happening?
Upvotes: 2
Views: 1617
Reputation: 2264
Not sure if this is your only problem but
$pwd = sha1($password, $salt);
is not how you use the sha1
function. http://php.net/manual/en/function.sha1.php
time()
will always evaluate to TRUE
and thus you're inserting a raw binary format into your char password field. Causing the issue that you're seeing.
What you probably want to do is
$pwd = sha1($password . $salt);
^
Upvotes: 3
Reputation: 63807
You have a simple typo where you have written a comma (,
) instead of a dot (.
) when inserting your data to your database.
// encrypt the password and salt
$pwd = sha1($password, $salt);
Compare this to where you generate the hashsum when validating your password:
// encrypt the submitted password with the salt
// and compare with stored password
if (sha1($password . $salt) == $storedPwd) {
Since the two have very different meanings a mistake that small will have huge consequences overall.
You wanted to form a new string consisting of $password
plus $salt
but instead you are now giving sha1
two arguments instead of one.
The second argument to sha1
controls what kind of data the function will return, plaintext (if false, default) vs raw data (if true).
Upvotes: 0
Reputation: 360702
sha1 returns the binary hash by default, which you're storing in a char field - char fields are subject to charset translation, which means mysql is mangling the hash. Convert the field to a binary/varbinary instead, which are NOT subject to charset translation
Upvotes: 0