8 ms·
Likely the most painful password hashing discussion you'll ever read
- sarciszewski 12y agoWarning: This might ruin your day. Also, don't let tptacek see this or he might get very [angry/existential] (select appropriate).
- opless 12y agowow. just wow. Then I noticed "PHP" and then I was enlightened.
- sarciszewski 12y agoI'm of the opinion that PHP's reputation for being a "bad language" is due to the sheer volume of idiots who can write a script that doesn't parse error.
- pconner 12y agoIt has a low barrier to entry. This tends to welcome really bad developers.
- eli 12y agoIt's a very popular language. It's got a lot of developers at all levels.
- opless 12y agoI got out of web development in general (I still do it now and then) because there's too many idiots writing bad code, and then clients asking me to fix up bad code ... and then expecting to pay the same rates as the cowboy who wrote the original code.
- marcosdumay 12y agoNope. The reputation is due to the number of such kind of developers who post at the offical bug-tracking software as official developers, and with sufficient capability to direct the design of the standard library API.
- sarciszewski 12y agoI'm sorry, maybe I need more coffee, but I'm having trouble grokking your intended meaning.
- Alupis 12y agoI'm floored by the amount of people with "fancy" titles from supposed "consulting" companies in the link discussion. The question was "I want to store password[s] in encrypted form." The answer should have been immediately -- "you don't encrypt passwords, you hash passwords using a well known, established, and tested cryptographic hashing algorithm + a salt, damnit!"
- sarciszewski 12y agoYeah, I attempted to do that (politely) with my first post. Though I made a few mistakes (it's password_hash() not hash_password()). As the discussion grew on, I became less nice.
- Alupis 12y agoI saw that -- but then a bunch of "titles" came in and flooded the discussion with the worst possible advice. I mean, seriously, have these guys been living under a rock? This is (well, should be) common sense by now.
- sarciszewski 12y agoHeh. And they all probably get paid a heck of a lot more than I do too. Oi. :]
- farmdve 12y agoNot to mention that encryption means being able to take some input and generate what appears to be a random sequence of characters,numbers etc, but being able to transform it back to plaintext/original format by using the corresponding decryption key. Indeed too many people there failed.
- owenmarshall 12y ago> The answer should have been immediately -- "you don't encrypt passwords, you hash passwords using a well known, established, and tested cryptographic hashing algorithm + a salt, damnit!" Your answer is as wrong as anything posted on that discussion. The correct answer is that you don't encrypt passwords. You also don't hash passwords with a salt. Instead, you use a key derivation function such as PBKDF2, bcrypt, or scrypt.
- cyphunk 12y agoin general anything coming from a php developer should be ignored. even reading official php documentation when it comes to anything concerning security should scare the shit out of grandmothers everywhere.
- sarciszewski 12y agoThe documentation has actually been going through a clean-up lately. For example, http://php.net/manual/en/function.crypt.php#refsect1-function.crypt-returnvalues http://php.net/manual/en/function.crypt.php#refsect1-functio... Do you have any specific examples of bad security advice in the documentation? I can try to raise hell with the doc maintainers and maybe even suggest an amendment.
- FraaJad 12y agoThe first thing i did after reading the post was to check the official documentation. The docs are explicit about not using MD5 for hashing password. Good on PHP doc maintainers.
- mercurial 12y agoI see that MySQL's documentation [1] recommends SHA2: > Exploits for the MD5 and SHA-1 algorithms have become known. You may wish to consider using one of the other encryption functions described in this section instead, such as SHA2(). Further down: > The PASSWORD() function is used by the authentication system in MySQL Server; you should not use it in your own applications. For that purpose, consider MD5() or SHA2() instead. Also see RFC 2195, section 2 (Challenge-Response Authentication Mechanism (CRAM)), for more information about handling passwords and authentication securely in your applications. 1: http://dev.mysql.com/doc/refman/5.5/en/encryption-functions.html#function_password http://dev.mysql.com/doc/refman/5.5/en/encryption-functions....
- sarciszewski 12y agoI may have voted this comment up, but it makes me feel very :( Related, the only hashing algorithm supported by postgresql for authenticating to the pgsql server is md5.
- deleted 12y ago[deleted]
- orf 12y ago>> "MD5 is fine as long as your database doesn't get leaked and is the subject of offline cracking (like adobe)" Wow. So MD5 is fine as long as it isn't needed to protect the data. Looks like a typical PHP discussion thread: plenty of misconceptions, a mix of of bad and plain stupid advice with a pinch of SQL injectable code. Silly PHP developers.
- danielweber 12y agoTo be fair, there are a class of problems you solve by storing your passwords behind a simple one-way function instead of as plaintext. I was asked earlier this week to audit a system that made the old passwords available to the user on their profile page. Using md5(), for all its shortcomings everyone has mentioned here, would at least make this architecture mistake impossible.
- deleted 12y ago[deleted]
- lttlrck 12y agoI'm disappointed nobody suggested XOR /s
- sarciszewski 12y agoI actually saved this before the grand-daddy of bad advice was posted. http://www.cryptofails.com/post/87697461507/46esab-high-quality-cryptography-direct-from-linkedin http://www.cryptofails.com/post/87697461507/46esab-high-qual...
- mercurial 12y agoWhat about rot13?
- hydrogen18 12y agorot13 is obsolete. You need to move on to rot39.
- CaveTech 12y agoBut someone did suggest Base64!
- mercurial 12y agoMultiple someones, including someones with fancy titles.
- tedunangst 12y agoBase64 does have one use: assume you need to store a plaintext password because you need your service to login to another service. (Use oauth, yada yada. Not everybody has it.) base64 coding passwords prevents support staff from trivially seeing and learning passwords when poking about the database. It's not to protect the password from bad people, it's to keep the good people from accidentally learning something they don't want to know.
- DoggettCK 12y agoI really want to suggest XORing the password with itself, as a goof, but it seems like the type of thing that will bite me in the ass later in life.
- kazinator 12y ago"Do not use MD5" is repeated often in the discussion. But are the weaknesses in MD5 relevant to hashing someone's 17 character password? The problem with MD5 is that it's possible to alter a document such that the forged document still has the same digest. This is a problem for digital signing. That doesn't seem directly relevant to password hashing. Nobody wants to find some 596 character string which has the same MD5 hash as your 17 character password, even if it does work in its place. Your password isn't a document that is being digitally signed by its hash for the sake of certifying its authenticity. Nobody is even supposed to store that document! (Someone tell me where I went wrong, if so.)
- Someone1234 12y agoLet's make the following assumption: That no matter what algorithm we pick we're utilising per-user salts. So you'll always need to search the full keyspace (e.g. 6-9 character length passwords). The reason why MD5, 3DES, and similar algorithms aren't really recommended in 2014 is that they're very fast/efficient on modern hardware. This is due to utilising GPU cores to do the hashing (which wasn't done back when MD5 was popular). This means the "time to crack" is low. Here is benchmarks of different hashing algorithms (faster is WORSE): http://thepasswordproject.com/oclhashcat_benchmarking http://thepasswordproject.com/oclhashcat_benchmarking But the really nice part about things like BCrypt and PBKDF2(Rfc2898) is that they accept "rounds." Which is number of repeated iterations over the password+salt. So every year you can respond to faster hardware by adding more rounds (e.g. 2014, have 10K rounds, in 2020 have 15K rounds, etc). If MD5 had supported rounds, it might still be safe to use today with enough iterations. Even things like BCrypt and PBKDF2 will eventually fall by the wayside (MD5 used to be a more secure alternative to the much faster DES algorithm). But at least rounds (additional iterations to respond to changes in hardware) will keep them relevant for longer.
- sarciszewski 12y agoThe problem is, simply, that cryptographic hashes are very fast and not meant for user-generated passwords. For that, a special sub-class of cryptographically hashes (called Key Derivation Functions) are recommended to make brute-force computation much more difficult. KDFs are meant to require a great deal more computation (e.g. an example of PBKDF2 might iterate HMAC-SHA256 8,000 times).
- higherpurpose 12y agoWhy mention md5 at this point, or even SHA1, when BLAKE2 exists? (assuming the people there don't want SHA2 because of slower performance): https://blake2.net/ https://blake2.net/
- mercurial 12y agoWell, that's kind of the point. You don't want performance here.
- tptacek 12y agoNothing in that thread annoyed me as much as this comment does. Yes, BLAKE2 is trendy, and name-dropping is tempting. But BLAKE2 is also not a password hash, and can't safely be used to store authenticators for passwords.
- peterwwillis 12y agoRight; it's a cryptographic hash. Technically there's no such thing as a 'password hash', only password KDFs and their results, which are composed primarily by cryptographic hashes. I think the guy's point was that if you're going to build a password KDF, you might as well use a hash function that's less shitty than MD5 and SHA1.
- tptacek 12y agoThese people would disagree with you: https://password-hashing.net/ https://password-hashing.net/ I was on your side for awhile, advocating that we just teach people about what a KDF is, but my side lost.
- peterwwillis 12y agoThe only winning move is not to play.
- milesf 12y agoThe title of this post is lost on me. What's so painful about this discussion? It's not that I'm stupid, it's just that I'm ignorant and don't know.
- sarciszewski 12y agoIt's painful because: - Bad advice is posted everywhere. - Good advice is disregarded because nobody reads the preceding posts in the discussion.
- Alupis 12y agoFor the people not understanding why this discussion is a problem, in synopsis: In order for a server to use encrypted passwords for authentication, the server must have access to the decryption key -- which means an attacker has access to your decryption key if they can compromise your box. Furthermore, if they don't get your decryption key, but they get your database dump -- they can then just brute your db and decrypt the passwords. They can do this because encryption is, by design, reversible. Encrypting passwords is almost as bad as storing in plain text. Cryptographically hashing a password is the only way to go. When you cryptographically hash a password, using a known library that has been tested and written by actual cryptographers with passwords/authentication in mind (like bcrypt, etc -- no, sha's and md5's are not safe to use) - you get a one-direction algorithm in that a password goes in, is digested, and a fixed-length hash output comes out. There is no way to reverse this hash back into the original input. Adding salt(s) combats people making rainbow tables against your implementation, as they then would need to know not only which algorithm you are using, how many iterations it does, but also what your salt(s) are (sometimes even varied every so many iterations). This makes it almost impossible for someone to brute your leaked password database.
- sarciszewski 12y agoThank you for posting this. +1
- aerovistae 12y agoI was under the impression SHA256 is valid...it's a cryptographic hash function that hasn't had weaknesses identified yet. 40 iterations of that + salting would suffice, no?
- aerovistae 12y agoI do realize bcrypt is arguably the best option, but why is SHA not valid also?
- tptacek 12y agoBecause it has no work factor. It's uniformly fast, which makes it very easy to brute force. The general-purpose strong cryptographic hashes --- your SHA2s, SHA3s, and BLAKE2s --- are all amenable to fast implementation on GPU. What you need is a password hash, not merely a cryptographic hash.
- aqme28 12y ago"either you can use md5 or base64, there are also many other encryption are there.. md5 is very secure because it cannot be decrypted." I'd say this has to be a joke, but Poe's Law is a tricky thing.
- sarciszewski 12y agoI'm pretty sure a couple of the posts here are tongue-in-cheek, but most of them reek of cluelessness and tl;dr
- blahbl4hblahtoo 12y agoAll of those people need to take down any information they have on their company/personal sites about their customers. Mass pwnge is incoming.
- waitwhatt 12y agoIt's linkedin. As expected.
- mobiuscog 12y agoThe discussion is great - it shows all of the companies you should absolutely avoid doing business with, as they have no sense of security.
- boogerhead 12y agoCould a hacker learn the hash key and salting by opening a bunch of accounts on the site before stealing the database, then comparing his known passwords with the hashed values?
- loumf 12y agoSalts are usually dependent on user details (like the username), so knowing your salt doesn't help you with other passwords.
- squidmccactus 12y agoWhat about this is so bad to begin with? It looks like this is standard industry practice now?