Get Matching SHA256 Algorithm - Perl - perl

Hi I'm trying to generate a similar sha256 hex, but I can't seem to get a matching one. I want to generate just about any password using a random key.
In this case, I'm using test123 : ecd71870d1963316a97e3ac3408c9835ad8cf0f3c1bc703527c30265534f75ae
Here is my code:
print "Final Hash: " . generateHash("ecd71870d1963316a97e3ac3408c9835ad8cf0f3c1bc703527c30265534f75ae", "fx4;)#?%") . chr(10);
sub generateHash {
my ($strPass, $strLoginKey) = #_;
my $strHash = encryptPass(uc($strPass), $strLoginKey);
return $strHash;
}
sub encryptPass {
my ($strPassword, $strKey) = #_;
my $strSalt = 'Y(02.>\'H}t":E1';
my $strSwapped = swapSHA($strPassword);
print "First Swap: " . $strSwapped . chr(10);
my $strHash = sha256_hex($strSwapped . $strKey . $strSalt);
print "Hashed Into: " . $strHash . chr(10);
my $strSwappedHash = swapSHA($strHash) . chr(10);
print "Last Swapped: " . $strSwappedHash . chr(10);
return $strSwappedHash;
}
sub swapSHA {
my ($strHash) = #_;
my $strSwapped = substr($strHash, 32, 32);
$strSwapped .= substr($strHash, 0, 32);
return $strSwapped;
}
Any help would be greatly appreciated!
The output I get:
Original Hash: ecd71870d1963316a97e3ac3408c9835ad8cf0f3c1bc703527c30265534f75ae
Hashed Into: 34b6bdd73b3943d7baebf7d0ff54934849a38ee09c387435727e2b88566b4b85
Last Swapped: 49a38ee09c387435727e2b88566b4b8534b6bdd73b3943d7baebf7d0ff549348
Final Hash: 34b6bdd73b3943d7baebf7d0ff54934849a38ee09c387435727e2b88566b4b85
I am trying to make the output have final value same as input
Final Hash: ecd71870d1963316a97e3ac3408c9835ad8cf0f3c1bc703527c30265534f75ae
and I want to do this by reversing the "Hashed Into" value.

SHA, as a hashing algorithm, is designed to prevent collisions. i.e. part of its power, and usefulness, is in limiting the strings which will hash to the same resultant value.
It sounds like you want to find a second string which will hash to the same hashed value as test123 hashes to. This kind of goes the intent of using SHA in the first place.
It is possible to brute force the values with SHA, i.e. given a hashed value, you can brute force the value that was hashed by computing hashes and comparing the hashed value to the target value. This will take some time. Other algorithms, such as bcrypt, are more difficult to brute force, but are more computationally expensive for you also.
Here is another post related to brute forcing SHA-512, which is effectively equivalent in algorithm to SHA-256. The linked post is Java as opposed to Perl, but the concepts are language agnostic. How long to brute force a salted SHA-512 hash? (salt provided)

You're badly misunderstanding what a hash is for. It's a ONE WAY street by design. It's also designed to have a very low probability of 'collision' - two source values that hash to the same result. And by 'very low' I mean 'for practical purposes, it doesn't'. A constrained string - such as a password - simply won't do it.
So what typically happens for passwords - my client takes my password, generates a hash, sends it to the server.
The server compares that against it's list - if the hash matches, we assume that my password was correct. This means at no point is my password sent 'in the clear' nor is possible to work out what it was by grabbing the hash.
To avoid duplicates showing up (e.g. two people with the same password) usually you'll hash some unique values. Simplistically - username + password, when hashed.
The purpose of authenticating against hashes, is to ensure the cleartext password is never required to be held anywhere - and that is all. You still need to secure you communication channel (to avoid replay attacks) and you still need to protect against brute force guessing of password.
But brute forcing hashes is by design an expensive thing to attempt. You will see places where 'rainbow tables' exist, where people have taken every valid password string, and hashed it, so they can rapidly crack retrieved hashes from the server. These are big, and took a long time to generate initially though, and are defeated at least partially by salting or embedding usernames into the hash.
But I cannot re-iterate strongly enough - don't ever hand roll your own security unless you're REALLY sure what's going on. You'll build in weaknesses that you didn't even know existed, and your only 'security' is that no one's bothered to look yet.

You should not do this. It is insecure and vulnerable to dictionary attacks.
The correct way to turn passwords into things you store, is to use a PBKDF like "bcrypt" (password-based-key-derivation-function).
Check out Digest::Bcrypt
Word of caution: if anyone ever tells you (or helps you) to use a "hash" for storing passwords, they do not know anything about security or cryptography. Smile at them, and ignore everything they say next.

Related

Is UUID random enought for password recovery link?

Does Data::UUID generates secure and random sequences? Is it ok to use it to generate password recovery link?
For example:
use Data::UUID;
my $u = Data::UUID->new;
my $uuid = $u->create_from_name_str(NameSpace_URL, 'www.example.com');
#then add $uuid to db
#and send email to user
Personally I'd use UUID::Tiny because that's capable of generating version 4 UUIDs, which are more random. However, in either case the modules are just using Perl's rand function which isn't considered random enough for serious crypto work.
Still, this is likely to be random enough for a typical password-recovery e-mail. Especially if the password recovery link is only kept working for, say, 24 hours and stops working after that.
It really depends on what you're securing though. Is it a forum for posting pictures of your pets dressed in superhero costumes, or is it nuclear launch codes? If you think that your website is likely to be a target for criminal elements, then it might be wise to opt for something stronger.
A fairly good random string with low collision probability can be generated using:
use Crypt::PRNG;
my $string = sprintf(
q/%08x%s/,
time(),
Crypt::PRNG->new->bytes_hex(24),
);
Data::UUID can generate either version 1 (create) or version 3 (create_from_name) UUIDs. Neither of those is random. Version 1 is your MAC address plus a timestamp, and version 3 is a MD5 hash of the string you passed in.

How to calculate a 256-bit HMAC_SHA3 hash with CryptoJS?

Recent CryptoJS versions support SHA3 hashing.
SHA3 can output different hash sizes, including 512-bit (default) and 256-bit. These two work fine:
var sha3_512_hash = CryptoJS.SHA3( 'test' );
var sha3_256_hash = CryptoJS.SHA3( 'test' , { outputLength:256 } );
Similarly, CryptoJS can also calculate HMAC values. However, I can't figure out how to change the default output size there:
var sha3_512_hmac = CryptoJS.HmacSHA3( 'test' , 'key' );
var sha3_256_hmac = CryptoJS.HmacSHA3( 'test' , 'key' , { outputLength:256 } );
The first works OK (the result is a 512-bit hmac value) but the second is the same (i.e. also 512-bit), as if it ignores the {outputLength:256} parameter!
Here's a live example: http://jsfiddle.net/M8xf3/ (using hmac-sha3.js from CryptoJS 3.1.2)
Does anyone know how to create 256-bit SHA3-based HMAC hashes?
P.S. For the SHA2 family of functions, CryptoJS has separate Hmac functions for each output size (that's HmacSHA256 and HmacSHA512). But this doesn't seem to be the case for SHA3?
This doesn't answer the actual question, but note that with SHA3 you don't really need HMAC hashes. Unlike SHA1 and SHA2 and MD5, SHA3 is not vulnerable to length-extension attacks.
Therefore with SHA3 it would suffice to just prepend or append the secret key to your input.
Or, if you're paranoid of a single hash step becoming compromised (not to be expected in the foreseeable future, especially not with SHA3, but still) you could do something like SHA3(key+SHA3(key+data)) or SHA3(key+SHA3(key+data)+data) (obviously with "+" denoting binary concatenation).
You can just edit hmac-sha3.js and change the outputLength to 256-bit instead of 512-bit.
Open hmac-sha3.js file, using your text editor.
Find "{outputLength:512}" and replace it with "{outputLength:256}"
Then the hash output will be 256-bit in length.
To be sure that you did not messed up things, double check your 256-bit hmac-sha3 output with some test cases available on the internet, for example: http://www.di-mgt.com.au/hmac_sha3_testvectors.html

Password hashing (crackstation.net)

I have a question regarding password hashing. I found a great tutorial on http://crackstation.net/hashing-security.htm. This is how I create a hash from the password using this code:
$hashed_password = create_hash(form_password);
The problem with this code is that it creates a different hash for the same password every time. I guess it's because of adding a random salt to the password:
function create_hash($password)
{
// format: algorithm:iterations:salt:hash
$salt = base64_encode(mcrypt_create_iv(PBKDF2_SALT_BYTES, MCRYPT_DEV_URANDOM));
return PBKDF2_HASH_ALGORITHM . ":" . PBKDF2_ITERATIONS . ":" . $salt . ":" .
base64_encode(pbkdf2(
PBKDF2_HASH_ALGORITHM,
$password,
$salt,
PBKDF2_ITERATIONS,
PBKDF2_HASH_BYTES,
true
));
}
So due to this, I cannot compare the hash created from the password typed by the user at the login with the hash retrieved from the database, because that hash will never be the same with the one stored in the database. The only way I see that it can be done is to store the salt in another column, or am I wrong?
A thing also annoys me. The format of the hast is e.g. sha256:1000:u9p+OqAZgVkIBtlTBkr9ZxhFvtt+zjcA:PvhJY+oesrdBeD5pjeXMQ/3wficCU0EG. A hacker obviously knows this form of hash so the algorythm that created this hash is clear for him. Let's suppose the database has been compromised and thousands of these hash codes were revealed. Doesn't having this form of hash code raise security issues? I guess a simple OqAZgVkIBtlTBkr9ZxhFvtt+zjcA:PvhJY+oesrdBeD5pjeXMQ/3wfic would be better because it reveals nothing about the encryption mechanism.
Read this link to Wikipedia here
It explains more about the use of a random salt. The key information there is that the random salt is stored in the same database as the hashed password. It is only created randomly a few time, when the user creates or changes their password. It is used whenever authentication is required.
Leaving the info about which algorithm it used to create the password hash leaves you the option of changing the algorithm at some time in the future without interrupting your users. If you decide up upgrade the hash algorithm you wait until a user logs in. At that point you have their password in plain text. Once you authenticate against the old algorithm, you rehash and store the new hash in their database row. It may take months or years for all users to log in but once they have they will accrue the benefits of better hashing. So you would then send out an email asking them to login and read your special news about better security (and as a side effect, improve their hashed password).
Here is an interesting discussion of password hashing StackOverflow:Passwords Storage Hash ...
The reason two hashes of the same password don't match for you is because the result of create_hash() includes the salt, which is randomly generated.
To get the same hash, you have to provide the salt as you validate. The code CrackStation.net provides makes this super simple - just store the result of create_hash() in your database, exactly as-is. To confirm a user entered the correct password, use
validate_password('provided-password','hash-from-database');
This will return a boolean of whether the password was correct. Using this method is better than writing your own, because it is specifically designed to prevent certain hints at what the correct password might be based on the time it takes to return an answer. This is a minor weakness, but better to avoid it anyway, especially since the provided function takes care of it for you.
The provided functions give you a solid implementation, so don't mess with it too much. The hash includes those extra details - sha256:1000 - in order to allow future changes to your hashing without affecting the ability of existing users to login; it will simply use the method provided in the hash, no matter what the current method is.
As far as showing a potential attacker how the hash was created: the format does show everything about how, but this doesn't matter very much at all. An attacker can easily figure out the method used from one or two known password:hash pairs. Far more important than this is using a good algorithm. The goal is to make it difficult to impossible to crack the password even with all the details, as security by obscurity is poor security.
Finally, just to reiterate, you do not need to store the salt in a separate column, just leave the big 70-80 character chunk it returns alone as your hash and let the functions take care of everything for you - anything else is a waste of time and resources
To add a bit more to the excellent accepted answer:
The point about salting the hash is to make it impossible for someone to come along with a huge pile of pre-encrypted hashes and try them one by one. Even with the salt in your database, they'd have to hash every possible dictionary entry against that salt to successfully match a hash. And the salt needs to be different every time to prevent duplicate entries (they hack one password, they have that same password that other users have entered).
As for not being able to compare the login hash to the stored hash, that is on purpose: you use a validation function to check the login password against the stored password, not a string comparison function.
Store the salt then add the salt to the password then turn it into a hash then store it.
Then to compare the passwords you retrieve the salt and add it to he password, convert it into a hash and then compare the two hashes.
(python example, the indentation is messed up when I copied the code from my code)
def Createpassword():
import random
import hashlib
username = input("type your username")
newpassword = input("type your new password? ")
#adds some salt
b = random.randint(1, 2000000000000)
randomsalt = str(b)
saltedpassword = (newpassword + randomsalt)
#hashes the newpassword
saltedpassword = saltedpassword.encode('utf-8')
h = hashlib.sha256(saltedpassword)
finsh = h.hexdigest()
#creates file names
saltname = username + "salt.txt"
username = username + ".txt"
#saves the hashedpassword and the salt
text_file = open(username, "w")
text_file.write(finsh)
text_file.close()
text_file = open(saltname, "w")
text_file.write(randomsalt)
text_file.close()
print("your new password has been saved")
def EnterPassword():
trys = 0
while (trys < 3):
username = input("type your username: ")
#takes password input
password = input("type your password: ")
#gets file names
saltname = username + "salt.txt"
username = username + ".txt"
#opens salt file
text_file = open(saltname, "r")
salt1 = text_file.read(50)
text_file.close()
#opens the hashed passwords file
text_file = open(username, "r")
correctpassword = text_file.read(500)
text_file.close()
#adds the salt to the password input
saltedpassword = password + salt1
#hashes the saltedpassword
saltedpassword = saltedpassword.encode('utf-8')
m = hashlib.sha256(saltedpassword)
hashedpassword = m.hexdigest()
#compears hashed passwords
if hashedpassword != correctpassword:
trys += 1
print("your password or username is incorrect")
if trys == 3:
print("you have been locked out for using to many failed trys")
if hashedpassword == correctpassword:
print ("Password Correct ")
#done give access
trys = 0
break
(I'm new to programming so feel free to correct me)

How do you use SHA256 to create a token of key,value pairs and a secret signature?

I want to validate some hidden input fields (to make sure they arent changed on submission) with the help of a sha-encoded string of the key value pairs of these hidden fields. I saw examples of this online but I didnt understand how to encode and
decode the values with a dynamic secret value. Can someone help me understand how to do this in perl?
Also which signature type (MD5, SHA1, SHA256, etc), has a good balance of performance and security?
update
So, how do you decode the string once you get it encoded?
What you really need is not a plain hash function, but a message authentication code such as HMAC. Since you say you'd like to use SHA-256, you might like HMAC_SHA256, which is available in Perl via the Digest::SHA module:
use Digest::SHA qw(hmac_sha256_base64);
my $mac = hmac_sha256_base64( $string, $key );
Here, $key is an arbitrary key, which you should keep secret, and $string contains the data you want to sign. To apply this to a more complex data structure (such as a hash of key–value pairs), you first need to convert it to a string. There are several ways to do that; for example, you could use Storable:
use Storable qw(freeze);
sub pairs_to_string {
local $Storable::canonical = 1;
my %hash = #_;
return freeze( \%hash );
}
You could also URL-encoding, as suggested by David Schwartz. The important thing is that, whatever method you use, it should always return the exact same string when given the same hash as input.
Then, before sending the data to the user, you calculate a MAC for them and include it as an extra field in the data. When you receive the data back, you remove the MAC field (and save its value), recalculate the MAC for the remaining fields and compare it to the value you received. If they don't match, someone (or something) has tampered with the data. Like this:
my $key = "secret";
sub mac { hmac_sha256_base64( pairs_to_string(#_), $key ) }
# before sending data to client:
my %data = (foo => "something", bar => "whatever");
$data{mac} = mac( %data );
# after receiving %data back from client:
my $mac = delete $data{mac};
die "MAC mismatch" if $mac ne mac( %data );
Note that there are some potential tricks this technique doesn't automatically prevent, such as replay attacks: once you send the data and MAC to the user, they'll learn the MAC corresponding to the particular set of data, and could potentially replace the fields in a later form with values saved from an earlier form. To protect yourself against such attacks, you should include enough identifying information in the data protected by the MAC to ensure that you can detect any potentially harmful replays. Ideally, you'd want to include a unique ID in every form and check that no ID is ever submitted twice, but that may not always be practical. Failing that, it may be a good idea to include a user ID (so that a malicious user can't trick someone else into submitting their data) and a form ID (so that a user can't copy data from one form to another) and perhaps a timestamp and/or a session ID (so that you can reject old data) in the form (and in the MAC calculation).
I don't know what you mean by "unpack", but you can't get original string from the hash.
Let's understand the problem: you render some hidden fields and you want to make sure that they're submitted unchanged, right? Here's how you can ensure that.
Let's suppose you have two variables:
first: foo
second: bar
You can hash them together with a secret key:
secret_key = "ysEJbKTuJU6u"
source_string = secret_key + "first" + "foo" + "second" + "bar"
hash = MD5(source_string)
# => "1adfda97d28af6535ef7e8fcb921d3f0"
Now you can render your markup:
<input type="hidden" name="first" value="foo" />
<input type="hidden" name="second" value="bar" />
<input type="hidden" name="hash" value="1adfda97d28af6535ef7e8fcb921d3f0">
Upon form submission, you get values of first and second fields, concat them to your secret key in a similar manner and hash again.
If hashes are equal, your values haven't been changed.
Note: never render secret key to the client. And sort key/value pairs before hashing (to eliminate dependency on order).
( disclaimer: I am not a crypto person, so you may just stop reading now)
As for performance/security, even though MD5 was found to have a weakness, it's still pretty usable, IMHO. SHA1 has a theoretical weakness, although no successful attack has been made yet. There are no known weaknesses in SHA-256.
For this application, any of the encryption algorithms is fine. You can pack the values any way you want, so long as it's repeatable. One common method is to pack the fields into a string the same way you would encode them into a URL for a GET request (name=value).
To compute the hash, create a text secret that can be whatever you want. It should be at least 12 bytes long though. Compute the hash of the secret concatenated with the packed fields and append that onto the end.
So, say you picked MD5, a secret of JS90320ERHe2 and you have these fields:
first_name = Jack
last_name = Smith
other_field = 7=2
First, URL encode it:
first_name=Jack&last_name=Smith&other_field=7%3d=2
Then compute the MD5 hash of
JS90320ERHe2first_name=Jack&last_name=Smith&other_field=7%3d=2
Which is 6d0fa69703935efaa183be57f81d38ea. The final encoded field is:
first_name=Jack&last_name=Smith&other_field=7%3d=2&hash=6d0fa69703935efaa183be57f81d38ea
So that's what you pass to the user. To validate it, remove the hash from the end, compute the MD5 hash by concatenating what's left with the secret, and if the hashes match, the field hasn't been tampered with.
Nobody can compute their own valid MD5 because they don't know to prefix the string with.
Note that an adversary can re-use any old valid value set. They just can't create their own value set from scratch or modify an existing one and have it test valid. So make sure you include something in the information so you can verify that it is suitable for the purpose it has been used.

Which hash function can this be?

I have some strings and some hashes of them, but I don't know which hash function is used. Any idea?
String hash
NN34W f8b46bcdc3b3c92
EM3M3 d8015ca876fd051
HXDKD a740e97464e5dfe
AKREJ aa7aa2dadfcbe53
3bNMK 0f11440639191d9
Edit:
Thank for answers, it's a hash of the captcha.
https://registracia.azet.sk/
If you check URL of captcha image, on the end is HASH value. This
On the server are send in HTTP POST are send TEXT: (P92M4) and HASH (72fec89a2e0ade2) and other values.
I like know how comptute hash of the TEXT P92M4, and control with HASH value, which is send on server.
Because I like make own captcha system for my school project, so I first analyzing situation and weakness.
As I understand your situation, a POST request sends both the "text" and the "hash" to the CAPTCHA server. This then uses whatever hash function they use to hash your text, checks to see if it matches the hash, and decides whether or not you succeeded. Presumably, the server sends you the image, as well as the hash, and then you enter the text.
As such, if you figured out the hashing function, you'd have completely broken this CAPTCHA system: All you would need to do is hash any string using their hashing function, and then when sending your POST request, ignore the hash they sent you and merely send them your computed text and hash pair. Thus, you could very easily automate successfully passing the CAPTCHA challenge.
To illustrate how difficult "reversing" the hash might be, consider the following hash that they very well might use:
Split the TEXT up alternating letters: thus ABCDE becomes ACE and BD
md5 the two halves using salts "fj49w0utw4a" and "r8h3wlsd"
md5("fj49w0utw4a"."ACE") is 115c05f0e5300f958ba01caa64b989f
md5("r8h3wlsd"."BD") is 74eecae86ef46382eb95443a1b1fa8f5
Take every 3rd char of the first string and every 4th char of the second, and alternate them until you have 15 chars
115c05f0e5300f958ba01caa64b989f becomes 55e09b1ab9
74eecae86ef46382eb95443a1b1fa8f5 becomes e8425af5
Final hash value for "ABCDE": 5e58e40295ba1fa
There is really no way you are ever going to reverse engineer that.
UPDATE
Note that CAPTCHAs as described above (and implemented on that site) are extremely insecure, as they only require one valid text/hash combination to be known
To demonstrate, use Firebug or equivalent and navigate to the CAPTCHA area of the form. We will be editing some hidden values.
Change the form[captcha_url] value from https://pokec.azet.sk/sluzby/system/captcha/[somehash] to https://pokec.azet.sk/sluzby/system/captcha/ee2be1f239e5d17
Change the form[captcha_hash] value from [somehash] to ee2be1f239e5d17
Regardless of what the picture says, type "P22KD" for the CAPTCHA
There are several ways to mitigate this vulnerability. As Tangrs suggested, you can store the hash value in a session variable so that it cannot be manipulated by the client. Less elegant but also effective is to store the submitted CAPTCHA in a database and not allow duplicate CAPTCHAs, as is implemented on the link in the question. This is fine, until you start running out of unused CAPTCHAs and end up getting collisions.
Seems smaller than any industry hash... possibly it's propriety?
A bit more info would help though, what language, where did you get it from?