Every article on passwords must start by discussing the same subject, so here it is: You’ve chosen a weak password, and deployed it unwisely. This article, however, doesn’t choose password formation as its primary focus. There has been a flurry of activity in the news lately about users who’ve been burned because breached organizations have stored their passwords incorrectly. Here’s how to do it right.
Even if a user of yours chooses the password “123456,” that doesn’t absolve you from the responsibility of storing and protecting it as securely as possible. Many companies don’t do this–according to one hacker, 30 percent of the sites he’s breached store their passwords in plain text.
If you store your passwords correctly, you ensure that even if (when) you are breached, your users enjoy complete protection. If you do not, you may become liable for legal action, and put your users’ names, bank accounts, and online reputations at risk.
Encryption Alone is Not Enough
Encryption is the oldest form of information security there is. The first documented example of cryptography goes back to 1900 BC, when a nameless Egyptian scribe used altered hieroglyphs to encipher a tablet. Modern encryption, such as the government-standard AES encryption algorithm, takes plaintext, loads it into a 4X4 square, and scrambles it using a symmetric key algorithm. Symmetric algorithms use the same key for both encrypting and decrypting data.
Here’s the big weakness inherent in using encryption, by itself, to store passwords. Where do you put the key? You might put it on a separate server, or in a USB key inside of a safe, but that’s clearly sub-optimal. If you possess the means to decrypt and view your users’ passwords, then those means can be taken from you. In order to keep passwords truly secure, you must hide them even from yourself.
Salt and Hash for Maximum Safety
Hiding a piece of information from yourself sounds like something you could accomplish only using electroshock therapy, drugs, or elective brain surgery. Math, however, makes this into a simpler enterprise.
There are a couple of minor weaknesses of encryption that hackers have turned into a major advantage. First of all, your crypto scheme might output ciphered text that’s the same length as the plain text. If I know that your password is definitely just six characters long, then I know that it’s worth trying to break (because a brute-force attack will eat a six-character password for breakfast). What’s more, vanilla encryption might produce the same output using the same input. If I see that both Jock and Tanya have the encrypted password 6qzY13, I could figure out that they’re both using the same plaintext password, and that it is likely to be something simple.
With a hash, all ciphered text, no matter its input length, has the same output length. A good hashing algorithm will also leave no trace of the original message. Instead of storing the plaintext password, you only store the hashed output. When your user logs on, they input their plaintext password. The plaintext is then stored temporarily in memory, hashed, and then checked against the hash that you’ve stored on your site. If the hashes match, they’re good. Again, since you’re only storing the hash, you never can never actually see your user’s plaintext password–thus hiding this information from yourself.
[Note that it is important to choose a good hash. In a recent breach involving the company VTech, which leaked the names of information of 4.8 million people, including children, they were found to be using the MD5 algorithm to hash their passwords. MD5 has been obsolete since the late 90s. Don’t use MD5. SHA-256 is recommended.]
There’s one last step to take. Let’s say that your users all choose dumb passwords, like ‘123456,’ ‘password,’ ‘batman,’ etc. This makes them vulnerable to what’s called a pre-computed dictionary attack. Hackers will determine what kind of hash you’re using, take a list of dumb passwords, and then hash them using that same algorithm. Then they’ll check their output hashes against your list, and your users will have been pwned.
Salting your database is the way to defend against this. This means that you add a bit of random information to each of your users’ passwords prior to hashing. So, if Don’s password is ‘batman,’ salting will turn that password into something like ‘87132458DCU4batman,’ and then scramble it. The salt isn’t crucial information on its own, and can’t be used to break the hash, so it’s okay to store it in your database.
Remember That Hackers Grow More Powerful Every Year
Moore’s law is working against you. The NSA, right now, has a password cracking datacenter that can make one trillion guesses a second. Other nation states aren’t far behind, and even garden-variety criminals can break hashes with a computer that costs less than a new car.
The only way to defend against this, for now, is to use an algorithm, such as HMAC-SHA-256, which takes the first hash, recombines it with new random data, and rehashes it. In order to thwart password-breaking computers, this should be repeated as many as twenty thousand times.
Hashing, salting, and stretching hashes is a process that seems daunting on the face of it. It remains the only method, however, in which your critical user data will remain secure.