What is the optimal length for user password salt?

74,567

Solution 1

Most of these answers are a bit misguided and demonstrate a confusion between salts and cryptographic keys. The purpose of including salts is to modify the function used to hash each user's password so that each stored password hash will have to be attacked individually. The only security requirement is that they are unique per user, there is no benefit in them being unpredictable or difficult to guess.

Salts only need to be long enough so that each user's salt will be unique. Random 64-bit salts are very unlikely to ever repeat even with a billion registered users, so this should be fine. A singly repeated salt is a relatively minor security concern, it allows an attacker to search two accounts at once but in the aggregate won't speed up the search much on the whole database. Even 32-bit salts are acceptable for most purposes, it will in the worst case speed an attacker's search by about 58%. The cost of increasing salts beyond 64 bits isn't high but there is no security reason to do so.

There is some benefit to also using a site-wide salt on top of the per-user salt, this will prevent possible collisions with password hashes stored at other sites, and prevent the use of general-purpose rainbow tables, although even 32 bits of salt is enough to make rainbow tables an impractical attack.

Even simpler-and developers always overlook this-if you have unique user IDs or login names, those serve perfectly fine as a salt. If you do this, you should add a site-wide salt to ensure you don't overlap with users of another system who had the same bright idea.

Solution 2

Currently accepted standards for hashing passwords create a new 16 character long salt for every password and store the salt with the password hash.

Of course proper cryptographic care to create really random salt should be taken.

Solution 3

Edit: My below answer answers the question as asked, but the "real" answer is: just use bcrypt, scrypt, or Argon2. If you're asking questions like this, you're almost certainly using tools at too low a level.

Honestly, there's no defensible reason not to have the salt be the same exact length as the hashed password. If you're using SHA-256, then you have a 256-bit hash. There's no reason not to use a 256-bit salt.

More than 256 bits won't net you any improvement in security, mathematically. But going with a shorter salt may always end up with a situation where a rainbow table catches up to your salt length -- especially with shorter salts.

Solution 4

Wikipedia:

The SHA2-crypt and bcrypt methods—used in Linux, BSD Unixes, and Solaris—have salts of 128 bits. These larger salt values make precomputation attacks for almost any length of password infeasible against these systems for the foreseeable future.

128-bit (16-byte) salt will be enough. You can represent it as a sequence of 128 / 4 = 32 hexadecimal digits.

Solution 5

One answer might be to use as size of salt the value that the hash you are going to use provides in term of security.

E.g. If you are going to use SHA-512 use 256 bit salt since the security provided by SHA-512 is 256 bit.

Share:
74,567
David
Author by

David

loading ...

Updated on September 28, 2020

Comments

  • David
    David almost 4 years

    Any salt at all will obviously help when salting and hashing a user's password. Are there any best practices for how long the salt should be? I'll be storing the salt in my user table, so I would like the best tradeoff between storage size and security. Is a random 10 character salt enough? Or do I need something longer?

  • John Czajka
    John Czajka over 13 years
    Remember that the longer your salt and hash algorithm, the bigger the performance hit your site will take
  • Randolpho
    Randolpho over 13 years
    That's not that big a deal; the user will barely notice the difference between a millisecond hash and a half second hash, plus password hashing actually should take longer to slow down brute force attacks -- although typical three strikes locked out for 15 minutes is better. Are you "wasting" CPU cycles to do this? Yeah, whatever. The CPU spends more time idle than not on most websites anyway, so what does it matter? If you're running into performance issues, scale out.
  • mrmcgreg
    mrmcgreg over 13 years
    What do you mean by 'More than 256 bits won't net you any improvement in security'. My belief was that salt defended against
  • Stephen Touset
    Stephen Touset over 13 years
    Salts defend against rainbow tables. A 512-bit salt with a 256-bit hash will still only result in 256 bits of entropy in the final password.
  • Richard Gadsden
    Richard Gadsden almost 13 years
    There is a benefit in salts being unpredictable. A predictable salt could be predicted and used in a hash table attack. For instance, if your salt is just the userID, then a plain alpha hash table that's long enough will include not just all passwords, but all username + password combinations.
  • Richard Gadsden
    Richard Gadsden almost 13 years
    Note in relation to your last paragraph, if you use a site-wide salt, that should be exactly that: site-wide. Not application-wide, ie each new instance you install of your application should generate a new site-wide salt. For instance, if Windows used the same salt on every Windows authentication database, then it would be worthwhile to create a rainbow table for that salt, but if every install of Windows generated a new salt, then it wouldn't.
  • outis
    outis almost 13 years
    Slow hashing is a feature, not a bug.
  • Pacerier
    Pacerier almost 12 years
    @Stephen I beg to differ. Entropy is not the issue here. Let's say we have a 3-bit hash, you are saying having 3-bit salt on a 3-bit hash is as secure as having a 9999-bit salt on a 3-bit hash. This is incorrect, an attacker can simply have a pre-generated full set of rainbow tables for all combinations of your 3-bit salt + 3-bit hash, achieving O(1) time needed to crack each row even when each secret had its own salt....
  • Pacerier
    Pacerier almost 12 years
    ...However, if your salt is 9999-bit long, it is unlikely that there is already a pre-generated rainbow table for that 9999-bit salt. Hence the time needed to crack each row would take O(m) where m is the cost of performing a hash.
  • Stephen Touset
    Stephen Touset almost 12 years
    If you have a 3-bit hash, your 9999-bit salt will still only hash down to 3 possible bits of entropy. A rainbow table would only have to find three salts for each password that result in a different output, which is a constant multiplicative factor and thus discarded from the big-O.
  • Stephen Touset
    Stephen Touset almost 12 years
    To clarify, I don't have to store a rainbow table with 2 ^ 9,999 salts. Just eight (three bits worth) entries for each password in the rainbow table. Again, you have gained nothing.
  • Randolpho
    Randolpho almost 12 years
    @Pacerier if you're on a budget you probably shouldn't be storing credentials at all -- look into OpenID, or Google or Facebook login.
  • Stephen Touset
    Stephen Touset almost 12 years
    Also note that solving for those three bits is exactly equivalent to brute-forcing the entire hash output space.
  • Pacerier
    Pacerier almost 12 years
    @Randolpho Everyone is on a budget, and OpenID has its disadvantages: quora.com/OpenID/What-s-wrong-with-OpenID
  • Randolpho
    Randolpho almost 12 years
    I love how the default login option for the link you provided is Facebook and Twitter login.
  • Pacerier
    Pacerier almost 12 years
    @Randolpho Facebook isn't OpenID btw.
  • Randolpho
    Randolpho almost 12 years
    No, it's a custom flavor of OAuth. But I'm pretty sure I wrote "look into OpenID, or Google or Facebook login". OpenID isn't the only game in town.
  • cjbarth
    cjbarth over 11 years
    It seems to me that an example of what other secure systems use is a great example of what best-practice is.
  • Raven
    Raven almost 11 years
    @JohnCzajka while true the sentence can be turned around, long salts means more cpu time to crack it.
  • CodesInChaos
    CodesInChaos over 10 years
    Character is a bit ill defined. You should say byte.
  • Nate C-K
    Nate C-K over 10 years
    The issue isn't really that the salt needs to be hard to guess. The attacker doesn't need to guess the salt: anyone who has access to the hash already has the salt. The issue is that if your salts are very common (like usernames), they might be the same as those at other sites, and at that point the attacker needs a much smaller set of rainbow tables to make attacks feasible. This is why the per-site salt idea is mentioned, to avoid this kind of collision with other sites.
  • user2864740
    user2864740 over 10 years
    @CodesInChaos I believe you mean octet ;-)
  • Boris Treukhov
    Boris Treukhov about 10 years
    Hi! It seems that wikipedia article is changed - maybe you should refer to en.wikipedia.org/wiki/PBKDF2 or something?
  • Boris Treukhov
    Boris Treukhov about 10 years
  • SilentSteel
    SilentSteel almost 10 years
    Quick note: If using usernames as the salt, this can be an issue if usernames change. Practically, (despite what is said in the customer's design documents) I've found that users often want to change usernames.
  • Pacerier
    Pacerier over 9 years
    @NateC-K, The per-site salt idea you are talking about is called pepper.
  • Pacerier
    Pacerier over 9 years
    @Randolpho, I'm pretty sure I wrote "Facebook isn't OpenID". Also, do read that link.
  • Pacerier
    Pacerier over 9 years
    @StephenTouset, The 9999-bit salt will still only hash down to 3 possible bits of entropy, but let me repeat: entropy is not the issue here. It doesn't matter if you can login as the user in that ................................. ............................................................‌​....................‌​.....
  • Pacerier
    Pacerier over 9 years
    ............................................................‌​....................‌​...... particular system. The purpose of salts is to stop precomputation attacks so that hashes cannot be searched for and immediately reversed into plaintext . With a 9999-bit salt, your password remains a secret, whereas with a 3-bit salt, your password is now known to the whole world (and they can use it to login to your other accounts since many people often reuse passwords). I find it amusing that 5 folks here had actually upvoted your comment due to the word "entropy" in it.
  • Stephen Touset
    Stephen Touset almost 8 years
    Salts are not considered private. If your table of password hashes leaks, then almost certainly your salts have leaked as well.