last day (16 days later) » 

10:19
8
Q: How to generate short fixed length cryptographic hashes?

ThomasI am trying to implement a kind of email verification system with a node.js server with no state. The strategy User sends his email to the server Server generates a 4 digits code based on the email address and sends it to the user via email. User sends back the received code via email + the e...

Since your code is only 3 hex characters, you have a total of 4096 possibilities. Due to the pigeon hole principal after generating 8293 codes, at least half of them will be duplicates. Is there a reason you're not using a longer (much longer) code?
@AndrolGenhald For UX reason, I want my users to be able to type the code in the app manually.
Security always comes at a cost of convenience. 4 digits is conventient bit provides nearly no security. Perhaps you want a solution with more chars, different representations (e. g. image representation) and/or some method not related to the email contents itself (e. g. TLS for emails, using a single mail system on trusted hardware, DKIM, …)
jww
jww
You might be able to use SipHash. It was designed as a fast and lightweight hash. The rub is, you will probably need to key it. It should not be too difficult to key the hash. I doubt SipHash is worse that the truncated SHA-256 you are using, and it will likely be faster.
@jww No. No. No. There is no "probably". It's designed to use a 128-bit key. It's not optional. Using a known value for the key breaks any security claims regarding SipHash. It's a great algorithm for particular use cases. As a substitute for HMAC, yes, sometimes. As a substitute for a full length collision resistant hash function? No. Definitely not a substitute for plain old untruncated SHA-256.
jww
jww
10:19
@FutureSecurity - I'm not aware of any proof that a truncated SHA-1 or SHA-2 hash retains the collision resistant properties of the full hash. See Kelsey's publications on the NIST website circa 2005. Part of Kelsey's work drove requirements for SHA-3.
@jww That's why I said un-truncated. Using a short digest never allows for collision resistance.
jww
jww
@FutureSecurity - OP requirements are 4 bytes, not 32 bytes.
@jww OP requirements actually are for just under 1.25 bytes... Doesn't change anything I said, though. I'm too tired to engage further for now.
jww
jww
@FutureSecurity - My bad, OP is using 3 bytes, not 4 bytes: "Take the first 3 characters of the digest...".
You wrote: "I want a 4 digit code for UX reasons. The user can read it once, easily memorize it and type it back into the app". Most adults can store between 5 and 9 items in their short-term memory. I think it's safe to use 6 digits, as most verification codes do.
10:19
Why does the user need to memorize the code? Why can't it simply be copy and pasted? Or why can't there be some sort of mechanism to automate the code delivery to the server so a full-length code can be used instead?
Offtopic, but... Is the email really necessary to use your website? If some registration form forces me to provide a "working" email address and I don't want to give mine, I'll just go to any "10 minute mail" service and use that one. No matter how secure your hash generation is, I will provide the correct 4 digits token... proving nothing, because the email address will cease to exist after 10 minutes.
Any particular reason you're reinventing the wheel instead of doing what pretty much every other service that wants email verification does and just provide a unique link for them to visit in the email?
Ray
Ray
If the code has to be 4 characters long, do they have to be digits? If you could use any characters in 0-9A-Z, then you could use the first 4 characters of the base 36 representation of the hash and get 1,679,616 possibilities instead of the 4096 you have now. (But it's still not as good as including the full hash in a link, and AJPerez's objection will still be valid.)
Why not just use hash the e-mail of the user then sign. The user just paste and copy the code and create an e-mail to the server. or better just click replay and send the e-mail. No need to copy-paste, no need to create a new e-mail and nothing is saved on the server to. In this case, even a good keyless hash as SHA-256, etc. can be enough against collisions.
@AJPerez Email is necessary, as it is an email based application.
@Ray Digits are easier to read and memorize.
@8bittree I have this requirement for a particular email based app. I don't want to verify email adresse's once but every time user want to register an email on a new client (eg mutliple phones, devices..). Also with a 4 digits code, the user don't even have to open the email, he just have to read the code from the notification he has received (from its mail client) and tape it directly into the app without never leaving it.
10:19
@Thomas So, send another email with another link when the user registers a new address? Not sure why you would imply that would be any more difficult with a link than with a number. And with the link-based method, you could even have the url open in your app. One click on a notification and a second on a link strikes me as significantly more convenient than anything involving a phone keyboard.

  last day (16 days later) »