World's Largest Wi-Fi Network Keeps Passwords in Plain Text
blog.self.li
blog.self.li
This feels like shaky logic though. Hashing is a good defence against DB harvesting but it doesn't stop a root level admin from listening to inbound unencrypted logins. Prolonged root access is therefore still a viable attack vector. The question is only how quickly you can harvest those passwords.
Other people are arguing that with sufficient decoupling and safeguards between the encryption key and the database there is an acceptable risk associated with storing a password.
Since services like Yodlee clearly do store passwords this is something that companies do address. Could someone who really knows this area well please describe how this is done in a way to minimise risk and how the risk compares to a traditional 1-way hashing?
Forgive my ignorance of web authentication, but aren't passwords hashed in the browser before being sent to the server for authentication?
If not, why? It seems to me that it would be just as easy to hash on the browser side as on the server side, but passwords are less exposed if you do it on the browser side.
(Apologies for hijacking your thread, but I'm interested in the technical details here.)
If you accept the hash from the client, anyone having the hash is able to login, making hashing pointless.
This is not an unusual practice, either. For example, any time you log into a remote computer using an ssh key, your ssh client is performing cryptography to authenticate you with the server. There is no problem in doing this, because the only way to perform the cryptography such that the authentication is successful is to have the right secret key. You could certainly write a custom ssh client that does some different cryptography, but that would be pointless, as the result would be an inability to connect.
There are, I think, two goals at play here. One is what you linked: preventing replay attacks. That is fairly easily solved by doing a double hash with a randomly generated salt. There is no problem in "trusting" the client to do this, because if they don't do it the way you specify, they don't produce the correct result. The only (feasible) way to generate a result that lets you log in is by combining the random salt with the correct password. This is important because otherwise an attacker could sniff your traffic and then impersonate you.
The second goal is in not having your password exposed if the site's database is compromised. Related, it would also be nice to not have your password exposed if the site is compromised and the attacker is watching incoming connections.
SSL solves the first goal, of preventing replay attacks. Not having your password exposed if the database is compromised is solved by hashing passwords. However, if you send the password in plaintext (or encrypted in such a way that the other end can retrieve plaintext, as with SSL) then the last, related goal fails: an attacker with total control can grab your password if you log in during the time he has control.
By doing hashing on the client, you can prevent that, and when implemented properly it can still avoid the rest.
The double hashing scheme doesn't achieve this. Since hash(password) is stored in the server DB, the attacker can just copy that and use it to login later. He just needs the hash, not the plain-text password to compute what the server asks for during authentication.
The above goal can be achieved by public-key cryptography. Its just like SSL working in reverse - server authenticating the client/user based on user's private key. The practicality of assigning a private key to every user is a different matter though :)
How about this for a login solution? For each user, you generate a private key and keep it on the server. But, you encrypt that private key with their password, and you don't keep that password or anything derived from it anywhere.
To log in, the server sends the encrypted private key and an authentication challenge to the client. The client then uses the password to decrypt the private key and respond to the challenge. Replay doesn't work, since the response is only good for that challenge. Watching the traffic on the server doesn't work, since you can only get the encrypted private key and the response. Snarfing the contents of the database doesn't even help, since you only get the encrypted private key.
For bonus points, I don't know if this is actually possible, make it so that it's impossible to tell whether a particular decryption of the private key is valid without using it to respond to an authentication challenge and sending that response to the server. This way it's impossible to brute-force the encrypted key, substantially mitigating problems with weak passwords.
Of course, I may have missed something obvious here....
Something like that is not used probably because the bigger problem is clients getting hijacked, not servers.
Now I really want to implement my scheme using JavaScript crypto. If only I had a web site that needed secure logins.
Enc-Priv-Key = Priv-Key XOR Trun(Hash(password)) where Trunc = Function to truncate to the length of the priv-key.
So, every (Enc-Priv-Key,password) pair combination is valid - it gives you a valid Priv-Key. Also, if you break into the server, you have Enc-Priv-Key and Pub-Key. Enc-Priv-Key is a random number assuming your hash(password) is random (which isn't true if your password is short but let's say it is). So, having Enc-Priv-Key shouldn't give you any information about Priv-Key.
I suppose that even if not every sequence is valid, enough incorrect sequences will still be valid private keys to make a brute force attack impractical without server cooperation.
Hashing on the client does not satisfy the first goal and sending the password in plaintext does not satisfy the second goal. A different solution altogether would be necessary to satisfy both goals.
The first scenario is where the attacker obtained the hash from the wire which is what I think you're assuming to be the case. Then yes, double hashing would protect against replay attacks.
The second scenario is where the attacker obtained the hash from the database which is what I assumed to be the case. Double hashing would not protect against these attacks (which are not, strictly speaking, replay attacks).
I'm not interested in belaboring this point any further, because I think you came up with a better solution to both issues in another post[1].
Glad you liked the other scheme. It's more complex, but seems better. I really have to try it out at some point.
This still has to be done over SSL because otherwise the JS doing this on the client side is subject to MITM.
I guess if you're targeting a single site the difference is small.
Hashing passwords client-side would just provide a false sense of security. Surely if it's worth doing it, it would be worth the cost of an SSL certificate and the overhead of protecting (a minimum of) all pages and requests handling passwords?
How do they actually send the reminder? By email.
But email is not secure, you should always assume that someone is eavesdropping on your email. Far too many users reuse a password from one service on others, so sending a password in email is a huge violation of trust.
I think storing passwords (and not only hashes of passwords) might be a good idea if it is harder for the attacker to recover the passwords than to gain root access to the http/database server, however, I would NEVER send passwords in emails (not even newly generated passwords). A simple solution is to send a one-time login link, and have the password displayed in the browser, over a https:// connection.
There is still a small possibility of stealing the password (someone intercepts the email and clicks on the link before the legitimate user does), but at least the user would become aware of it (his link wouldn't work any more).
One-time links are definitely the right way, though I think it's better to give the user a new password dialog than to tell them a randomly generated password.
What I find interesting about the debate regarding password storage ethics is the question, "What is a website's ethical responsibility in regards to a user's password?"
On the face of it, one could argue that the extent of a site's ethical responsibility ends at their IP address -- i.e. a site is only responsible for protecting one's password to the extent that it reasonably protects the user from harm resulting from someone else using their credentials on the site. For example, under this scenario, HN's responsibility would be to take reasonable steps to protect my password in accordance with the level of harm I would experience should my account be compromised. HN's "reasonable steps" are different from those of Bank of America, and emailing my password in plaintext would not shock me (even if unlikely).
However, there is a tendency for people to argue that the extent of a site's ethical responsibility is to protect the user from harm elsewhere on the internet - the logic of course being that many people use the same password for HN and BOA. In some sense, this argument is premised on websites having some level responsibility for general welfare of their users (i.e. a website's responsibility towards users extends across the entire internet to some degree).
A weakness of that argument is that once general welfare of the user is the standard, plaintext storage of a password may promote the user's general welfare to a greater extent than more secure measures - security is just one criteria in regards to utility. A house with few windows is usually more secure but often less healthy for its occupants.
Although technical considerations are important, the issues surrounding password security methods for most sites are social: trivial passwords, password reuse, and "lost" passwords. Holding all sites to the standards which apply to sites with fiduciary responsibility such as banks or corporate IT centers is, in my opinion, somewhat asinine. Every web service does not need to be locked down, and good architecture will balance security with commodity and delight.
However sometimes you need to store sensitive data. Generally this is done with hardware security modules which rotate encryption keys in a periodic basis. Access to the sensitive data is also audited.
Risk can be minimized. It just comes down to if it is worth if for your business. PCI DSS is just one example of minimizing risk.
The day we move away from simple username password authentication as a whole is the day I can start feeling safe about my online accounts. Until that day there will always be the one crypto 'expert' attempting to dissuade the angry masses with his custom XES scheme which is super secure due to high amount of buzziness.
Consider the case of VPNs. When you have two trusted routers to connect, you use a shared secret. That's because both routers are in the same secured datacenter environment; both are equally trusted. When you have users connecting to your VPN, though, you issue each user a unique certificate (which is a crypto-based identifier). This is because you can't trust individual users the way you can trust a server in your datacenter.
I first reported a similar issue to Rackspace Cloud 2/2/2010:
http://feedback.rackspacecloud.com/forums/71021-product-feed...
They still email new vps ROOT passwords with IP addresses. (At least they said they would fix it about 2 months ago.)
Perhaps there's not enough people that are bothered by this? There is this site: http://plaintextoffenders.com/
Of course, sending passwords in an unencrypted email is bad practice, but that's another story.
It's always (almost) completely unnecessary to store encrypted passwords.
AES-256 symmetric encryption (as one example) is designed to be reversible while a SHA-512 hash is not. What does reversible mean you ask? It means that plaintext can be made into ciphertext and then back to plaintext again. It's designed to be undone/reversed by the party that holds the key/password.
I believe that the parent was simply pointing out that encryption is reversible while hashes are not. This is a point of confusion for many in IT/dev.
And if it's possible to automatically reverse the encryption, then it's not far off plain text.
When each line of code you write is a point of failure, I would rather trust an algorithm (e.g. bcrypt) which is immune to all of them rather than reversible encryption which needs only two.
There should be no feasible way to read the passwords of your users, ever. If you store them 'secure' in a reversible way it doesn't matter much if you use rot13 or state of the art crypto. Anyone getting access to the database can probably get the key as well.
And I didn't even touch problems that aren't related to outside attacks at all (You know, I don't even _want_ you or your customer support guy to be able to look at my password if you browse your customer database).
You do yourself a major disservice if you implicitly take responsibility for knowledge you shouldn't ever need in the first place.
For all I care (and I guess the down-voters in your case think similar) that's just the same thing, really. If you can reproduce the plaintext in any way you're guilty of storing plaintext passwords. Arguing about the terms doesn't change the problem nor the perception in this humble author's opinion. The article is ~correct~, good enough, works for me.
1. plain-text or plain-text equivalent: you can access the original passwords in microseconds
2. lousy hashing: you can't tell what the password is immediately but it's computationally feasible to figure it out
3. good hashing: you can't figure out the password
The only time you ever need to distinguish plaintext from plaintext-equivalent is when you have a partial data breach. Good hashing is safe even under a full data breach.
Although I get your point, this statement is a bit too broad. What about brute force? Get enough parallel hardware running fast enough and you can eventually reproduce the plaintext for any ciphertext or hashtext.
Besides brute force, there's also dictionary and rainbow table attacks to consider. Are you guilty if the plaintext can be reproduced by a table lookup? Are you guilty if you properly salted, but the salt storage was compromised too? Are you guilty if you enforced password-complexity requirements to foil a rainbow table, which led to the user writing down KuteK1tty!123 on her Post-it and a co-worker stole it?
These aren't easy questions, and there's no magic solutions, just a cloud of less-bad options.
Still not the best solution, hashed password (with a salt) are way more secure if your password happens to be 12345.
Everyone here implies that passwords are stored in just another table of the database. There are other more sensible scenarios. For exmaple: authentication servers which talk to the front end using CHAP, well behind internal firewalls and with dedicated hardware which holds the private keys and encrypts/decrypts the data.
This has been discussed before. The ability to recover passwords has bussiness value, so at the end its a tradeoff between risk and money.
Having a stored password in any format except for one way hashing is a massive and _unnecessary_ liability.
Before you take the time to reply with another convoluted shell game of keep the password away from the hacker, consider the actual necessity and value of a recoverable password. Does it really outweigh the massive security problems?
Done correctly, login is an exchange of hashes, not encrypted passwords.
A simple way to do this would be to send a unique, random salt S for every login, and the user would reply with e.g. sha1(password + S). However, to be able to check that the answer is correct, you would need to know the user's password, in plain text, which brings you back to square one.
To securely do this, you would need commutative hashing functions, i.e. hashing functions f(x) and g(x) such that f(g(x)) = g(f(x)). Actually, to be completely safe, you would need to be able to generate a whole (preferably infinite) family of commutative hash functions g(x), a random one for each login. I have no idea if such functions exist, more importantly, if they are known, it's an interesting idea actually.
Since you can't trust the server in this scenario, you can't implement in in (normal) javascript.
Because if you send back passwords in plaintext, they usually are...
If you were in the physical security business and knew of all the violence that occurs in society you would think it's crazy to not own a security system and not use it every day.
Now put yourself in the shoes of a non technical person and you can see how convenience sometimes trumps security.
Sidenote: I love asking people in the computer security business about what kind of physical security system they use at home. Most don't use one.
a) Economies of scale - breaking into houses happens one at a time. Breaking into unsecured computer systems often lets you affect millions of people at once.
b) Jurisdiction - if a thief breaks into your house, he's local, and your cops can find and prosecute him. With computers, this is almost never true.
c) Personal Choice - You can choose whether or not to use an alarm in your home. When you use somebody's service, you have no choice over whether they use a level of security you agree with.
d) Personal Impact - When you choose to use an alarm in your home or not, that is a decision that affects -you-. When a service chooses to be insecure or not, that is a decision that affects -their customers-.
In short, they are nowhere near equivalent. If you want to make decisions for yourself on convenience vs security, that's cool, but don't equate that to a company making decisions on behalf of their customers.
You got a lot of time at work to right 4 points as to why you think my point is wrong ;)
The worst thing that can happen here is that somebody connects to your wifi. If someone can read your email and is in the vicinity to connect to your wifi, the least of your problems is that he or she does connect to your wifi.
Also, as pointed out by others, this doesn't mean it's stored in plain text. Any time you set a password it travels in plain text (typically - and hopefully - via a secure connection) and it arrives to their server in plain text. You are never sure they are immediately storing it properly encrypted in a DB. They can also be doing things like sending it in emails or storing it elsewhere. If you cannot trust your password to whoever is storing it you are basically f*ed. BTW, what do you think they might do whenever you enter the wrong password in the wrong site? (for instance, your email password).
Yes, it's bad if you use the same password everywhere. Yes, it's bad if someone man-in-the-middles you. Yes, it's bad that arbitrary web users can run arbitrary database queries. But the point of robust engineering is to protect a system from many failures. If your passwords are stored in cleartext, your system is less safe overall than one that stores the passwords hashed. And because it's so easy to hash passwords, and because it's so damaging to your users to leak their password, it's generally considered Pretty Fucking Incompetent to keep passwords around in cleartext.
The reality is that most programmers do not call eval("code from the user") but they often call sql_query("code from the user").
Unwarranted paranoia... Any time you set a password it travels in plain text (typically - and hopefully - via a secure connection) and it arrives to their server in plain text.
This is true, but data in motion is less vulnerable to compromise than data at rest (due to how the Internet works and how web applications are programmed), and so the conclusion "unwarranted paranoia" is wrong. The paranoia is warranted.
- not a critical resource : if your email is compromised, the importance of that makes this insignificant. It's also a local resource, cannot be exploited from afar.
- just because they email it to you doesn't mean it's in plain text. It can be symmetrically encrypted, or (not in this case) it can be sent prior to storage.
Not all accounts require draconian password policies. In fact, the abuse of these requirements encourage users to make really bad decisions regarding passwords, like reusing them or having them stored in a central repository.
Unless a negligible amount of the 4 million users accidentally reused the password for other services as well. Which probably makes 3.9 million victims.
Also, as pointed out by others, this doesn't mean it's stored in plain text.
That does not matter much. If FON can extract it, an attacker can extract it as well, thus rendering it insecure.
However, it is still just your wifi connection which has to be locally accessed still and not ultra-secret password. IMO the policy is not problematic and it can save you the need to write it down somewhere, which for a local-only resource might be a worse alternative.
No, the worst thing that can happen is that someone you trust uses the same password for this service and their google account, then the attacker who hates you uses their latitude access to find where your kids are and kidnaps them for money.
Sorry... went to far. A more sane version is: someone uses the same password for their {online retailer} account. Attacker uses that to login and buy themselves a $X000 present using your saved CC details.