Is there a way to compare passwords stored in database after being encrypted in sha2() and the password entered by users during login without encrypting the login-time-password? Actually I want to match the passwords character by character and pass for a match in either of upper case or lower case i.e. in other words is there a function or method to de-crypt the saved password before comparison?
What you want to do sounds fishy.
Anyway no you can't recover a hashed string
You can't "decrypt" a SHA hash. Instead, compare the SHA version of the entered password with the stored passwords in the database (also hashed).
$enteredpass = $_POST['password'];
$enteredpass = sha2($enteredpass);
$realpass = sha2('password123'); //Yup, best password EVAR!! xD
if ($enteredpass == $realpass) {
echo "THE PASSWORD IS CORRECT!! :D";
}
else {
echo "THE PASSWORD IS INCORRECT!!";
}
You probably want to use a database, but this is just a simple example... ;)
Related
I have this code:
$password = vancab123;
password_hash(base64_encode( hash('sha512',$password, true) ), PASSWORD_DEFAULT );
Database stored value:
$password = $2y$10$jUa8ZEFBX5lfsBmySUnJFeSSyKwQ1v/emazJZPh8MwJ0g0lLbmjYC;
My Problem:
I used that on "remember me" function. If the user used that function his/her credentials (email and password) will be saved for 7 days using cookie.
My problem is because the email and password will automatically fill up the email and password text boxes, the password text box characters is too long because it was hashed.
How can I match the length of the hashed password to the original/unhashed password?
And you dont need to jump through all those hoops to use password_hash and this is how to check that an entered password matches the previously hashed password
The point of a HASH is it cannot (within a sensable time frame) be converted back to its original value. Instead you have to compare it using password_verify() to the unhashed value the user enters when they return and attempt to login using the same password.
$password = 'vancab123';
$hashed_pwd = password_hash($password);
// test the hashed password
if ( password_verify($password, $hashed_pwd) ) {
//password entered is OK
} else {
//password entered is WRONG
}
ADDITION after you clarified your question:
Read this for a Remember me functionality What is the best way to implement "remember me" for a website?
A hash is a one way transformation of an arbitrary value. They are by nature irreversible. In your case you will have to hash the password provided by the user, retrieve the value from the db, and do the comparison of both hashed values.
The only alternative would be the paradigm behind a rainbow attack, in which you hash every conceivable possibility and store them as key value pairs, but that is a lot of data.
I want to ask how to save a user's password to the database? I've done it but the result is saved to the database is not the same as the password was entered. and password that instead turned into a strange code that long. even though I've been using the action 'md5'. correction please what is wrong with my syntax controllers.thanks before
function add(){
$data['title']="Add user";
$this->_set_rules();
if($this->form_validation->run()==true){
$kode=$this->input->post('username');
$cek=$this->m_user->cek($kode);
if($cek->num_rows()>0){
$data['message']="<div class='alert alert-danger'>Username is already in use/div>";
$this->template->display('admin/adduser',$data);
}else{
$info=array(
'name'=>$this->input->post('name'),
'addres'=>$this->input->post('addres'),
'dateofbirth'=>$this->input->post('dateof birth'),
'email'=>$this->input->post('email'),
'username'=>$this->input->post('user'),
'password'=>md5($this->input->post('password')),
'level'=>$this->input->post('level')
);
$this->m_user->save($info);
redirect('admin/user/add_success');
}
}else{
$data['message']="";
$this->template->display('admin/adduser',$data);
}
}
md5 is a hashing algorithm which is hashing your password to the string of 32 char length.
that string is the hash of the password you entered.
for ex if your password is abcd then md5(password) will be d41d8cd98f00b204e9800998ecf8427e.
remove that md5() to see your password
If you are applying md5 to the input you have received via form post that means you want to encrypt your password in a secured format. md5() basically applies an encryption to generate a 32 character long text that is secure and not possible to decrypt.
Also this considered a good practice to follow this strategy but you need to be little bit careful before applying the same subject to your requirement and data.
Also if you don't want to apply this encryption then simply omit this method before the post variable:
Before: 'password'=>md5($this->input->post('password')),//Gives encrypted 32 char long text
After : 'password'=>($this->input->post('password'), //Gives plain text
Somebody should pls guide me on how i can fetch out hashed password from database and match the password entered by a user when login in
i used php crypt() function with bcrypt algorithms to hash the password when registrian the user
thank you all in advance
From the documentation:
$hashed_password = crypt('mypassword'); // let the salt be automatically generated
if (crypt($user_input, $hashed_password) == $hashed_password) {
echo "Password verified!";
}
You need to pass in the original hash, otherwise crypt will generate a random salt and the passwords are very unlikely to match. I.e.
//BROKEN - will almost always print "Bugger off!".
$hash = crypt('Hello world');
$attempt = crypt('Hello world');
if($hash === $attempt){
echo "Access granted!";
}else{
echo "Bugger off!";
}
You don't need to "fetch" the hash from the database, you just hash the given password (from a login attempt I assume) and match THAT hash against the password column of a database. if a match is found where the password column matches the hash that you just made AND the username is a match, then the password is valid.
Thank you all, if i really get your explanations you mean i should hash the coming password from a user attempting to login and then compare the hash value with the one in DB
EXAMple
$salt=//the bcrypt algorithms format, cost parameter and the salt goes here, thesame with the one use when registrian
$coming_pass= crypt( $password, $salt)
mysqli_query ( SELECT from user WHERE username= $username AND
password= $coming_pass)
you just send the unencrypted password into the same crypt process as you did with the encrypted password, then they should match.
PHP has built in Options to do that, look at Creating a Hash, and Verifying a Hash
pseudo-code
hashed password = hp
plain text password = p
seed (Random Number generated by server) = s
hash algorithm (md5, sha1, sha256, ...) = hash
Example with Seeded Hash
hp = hash(p + s)
the order you set the seed is not important, as long you do it the same way every time, by Concatenate the password and seed
Example without Seeded Hash
hp = hash(p)
you will need to save the hp and seed, the p should NEVER be saved by the server, as Plain Text Passwords is a security issue.
C# Code Example:
static public bool IsPasswordCorrect(string hp, string seed, string enteredPasword)
{
return (hp == Sha1(String.Concat(enteredPasword, seed)));
}
this way you have no direct way to get the password from the database, and only the actual Client will have the Plaintext Password.
if you want a 2-way encryption algorithm, you will need to look at RSA, but it is way more complicated and requires a lot of knowledge to make secure.
This question already has an answer here:
How to check a mysql encrypt value with a salt in PHP?
(1 answer)
Closed 9 years ago.
I would like to encrypt some passwords and put it in database. How do I keep this stuff in a database so I can retrieve the data if the owner matches.
Example
<?php
// some validations and other staff
$data = $_POST['input'];
$hash = crypt($data);
//then database insert code
?>
If I echo the $hash, it's giving me some encrypted data but when I refresh the page, the numbers are changing from time to time. How do I keep the data static? How will I tell the encrypted password that this was the owner when username and password entered.
Example
<?php
//time of encryption
$name = "someone";
$pass = "p1x6Fui0p>j";
$hash = "$pass"; //outcome of $hash e.g. $1$aD2.bo0.$S93XNfgOFLskhis0qjE.Q/
// $hash and $name inserted in database
?>
When the user tries to login with collect details, how will I refer $hash "$1$aD2.bo0.$S93XNfgOFLskhis0qjE.Q/" was equal to $pass "p1x6Fui0p>j" ?
crypt() has an unfortunate name. It's not an encryption function, but a one-way hashing function.
If you're using PHP 5.5+, just use password_hash and password_verify:
$hash = password_hash($data, PASSWORD_BCRYPT); // Bcrypt is slow, which is good
And to verify the entered password:
if (password_verify($pass, $hash)) {
// The password is correct
}
Now to answer your actual question: the purpose of password hashing is to authenticate users without actually storing their plaintext passwords. If hash(a) == hash(b), then you can be pretty sure that a == b. In your case, you already have hash(a) ($hash), so you just need to hash the inputted password and compare the resulting hashes.
crypt() does this for you:
if (crypt($pass, $hash) === $hash) {
// The password is correct
}
From the php crypt page
if (crypt($user_input, $hashed_password) == $hashed_password) {
echo "Password verified!";
}
You are not using your own salt, so for every call salt is automatically generated, and salted password is hashed. To get the same hash from this password, you need to run crypt with exact salt that was generated during first run.
Generated salt varies depending on algorithm used for hashing, but from your example it's MD5, and salt is delimited by first and third dollar sign inclusively:
$hash = '$1$aD2.bo0.$S93XNfgOFLskhis0qjE.Q/';
// \ salt /
So to get Exact same hash you need to call crypt($pass, '$1$aD2.bo0.$');
Remember that if you want to use your own salt, it needs to be in proper format for given algorithm. For best results use php 5.5+ password_hash mentioned by #Blender, and for older php versions there is password_compat library, with this you don't have to worry about proper salt format.
I am coding a registration system. I decided to encrypt the passwords and let the users use whatever they want in their passwords, including spaces.
The only restrictions would be:
- no spaces at the start or end of password
- min 5 char and max 30 characters
// CHECK PASSWORD
} elseif ((substr($password, 0, 1) == " " || substr($password, -1, 1) == " ")){
$msg = "You cannot have a space in the beginning or end of your password.";
} elseif (strlen($password) > 30)) {
$msg = "Your password cannot be longer than 20 characters.";
} elseif (strlen($password) < 5)) {
$msg = "Your password cannot be shorter than 5 characters.";
Is that enough?
I'll also take this chance to ask how should I treat the password before and after encrypting it. Should I just encrypt it and then escape it?
What you're looking for is not encryption, but hashing. A hash algorythm takes some arbitrary value and tranforms it into a fixed-size string. It's well suited for this becouse a hash algorythm is one-way, i.e. you can hash something but you can't unhash it.
For more security, you can add a 'salt' to avoid rainbow tables. A rainbow table is a table with already-calculated hashes for known words. For example a user has a password of "apple" wich produces the hash "XABC". If a hacker has the hash"XABC", he goes to a rainbow table and looks for a word that produces the hash "XABC". Since apple is a common word, so is it's hash and it will probably be in the table. The salt avoids this since it added before the the hashing occurs. you just concatenate it to the string to be hashed. So if the user uses the password "apple", your script doesn't hash apple, it hashes "saltedapple" wich no loger produces the known hash "XABC". 'saltedapple' is not a known word and its less likely to be in a rainbow table. 'salted' is a pretty simple salt, but using '$ZX?(' would make '$ZX?(apple' wich i can asure you that's not in any rainbow table.
Instead of check for spaces in begin and and of string, you can just trim($password)
You don't need to encrypt password at all. Just encrypt it with something like
function encryptPassword($enteredPassword) {
return md5(sha1($enteredPassword);
}
and validate user entered password, after encryption, with same stored password;
p.s. it is much better to use mcrypt, with more difficult algorithm.