Leaked list contained passcodes such as "logmein2zoosk" and "zoosk password".

A screenshot from Jeremi Gosney showing passwords cracked by the ocl-Hashcat-plus program.

Jeremi Gosney

Zoosk.com, an online dating service with about 15 million unique visitors each month, is requiring some users to reset their passwords. The move comes after someone published a list cryptographically protected passcodes that may have been used by subscribers to the website.

In the past, the San Francisco-based company has said it has more than 50 million users. With this dump, a small but statistically significant percentage of the 29-million-strong password list contained the word "zoosk," an indication that at least some of the credentials may have originated with the dating site. Jeremi Gosney, a password expert at Stricture Consulting Group, said he cracked more than 90 percent of the passwords and found almost 3,000 had links to Zoosk. The cracked passcodes included phrases such as "logmein2zoosk," "zoosk password," "myzooskpass," "@zoosk," "zoosk4me," "ilovezoosk," "flirtzoosk," "zooskmail."

Other passwords contained strings such as "flirt," "lookingforlove," "lookingforguys," and "lookingforsex," another indication that they were used to access accounts at one or more dating websites. Many users choose passwords containing names, phrases, or topics related to the specific website or generic type of service they're used to access. In December, Ars profiled a 25-GPU cluster system Gosney built that's capable of trying every possible Windows passcode in the typical enterprise in less than six hours..

In a statement issued to Ars on Monday, Zoosk officials wrote: "The company is conducting a thorough forensic analysis of the situation. So far, we have not found evidence of our network being compromised. Additionally we have not received reports of unauthorized access to members' accounts as a result of the information posted to this site. However, and out of an abundance of caution, we are notifying certain users by e-mail with instructions for changing their passwords."

A Zoosk spokeswoman characterized the number of Zoosk users required to reset their passwords as a "small subset." She declined to provide a specific number.

According to someone familiar with the cracked password list, other commonly found words include "apple," "iphone," "linkedin," "yahoo," and "hotmail," an indication the dump may contain account credentials for of a variety of other services. Indeed, the person who posted the passwords said they originated with "various sources" and were "real passwords and not a generated list."

All passwords were protected using MD5, a cryptographic hashing algorithm that is poorly suited for passwords. Because MD5 was designed to be fast and require modest computing resources, attackers with relatively inexpensive computers can try billions of guesses per second when cracking large lists. Making matters worse, none of the hashes on the list contained cryptographic salt, another measure that can slow down the cracking process. By contrast, when passwords are protected using slow, computationally intensive algorithms designed specifically for passwords, the number of guesses can number in the hundreds of thousands per second.

Update: A few hours after this article was published, a Zoosk spokeswoman said that over time the online dating service has moved away from MD5 and today uses the PBKDF2 key derivation function with the SHA-256 algorithm that's been cryptographically salted. That's a vast improvement over unsalted MD5 since PBKDF2 significantly slows the cracking process. It's also a big improvement over the hashing routine the spokeswoman previously described to Ars.

Story updated to correct details in the last paragraph based on an incomplete description previously provided by Zoosk.

Promoted Comments

In this day and age, using md5 for hashing passwords should be punishable by flogging. Even using SHA-256 is just plain lazy.

Seriously, how hard is it to use bcrypt? There are even plenty of free libraries out there for crying out loud.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

Also, getting existing frameworks to work with more advanced hashing algorithms is non-trivial. For example, many websites likely use Microsoft's ASP.NET Membership system because it's available out-of-the-box. They don't want to spend time reinventing the wheel, so they just go with what Microsoft gave them. Problem is, it uses salted SHA1 (on older versions, newer versions use something like SHA256, I think). Reconfiguring the "black box" to use something like PBKDF2 is not easy. That's the downside of using an existing solution rather than writing your own, you lose a bit of control.

Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

In this day and age, using md5 for hashing passwords should be punishable by flogging. Even using SHA-256 is just plain lazy.

Seriously, how hard is it to use bcrypt? There are even plenty of free libraries out there for crying out loud.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

Also, getting existing frameworks to work with more advanced hashing algorithms is non-trivial. For example, many websites likely use Microsoft's ASP.NET Membership system because it's available out-of-the-box. They don't want to spend time reinventing the wheel, so they just go with what Microsoft gave them. Problem is, it uses salted SHA1 (on older versions, newer versions use something like SHA256, I think). Reconfiguring the "black box" to use something like PBKDF2 is not easy. That's the downside of using an existing solution rather than writing your own, you lose a bit of control.

Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

[snip] Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

But, but, but... a hash designed to be fast provides almost no protection. If one can intermix unsalted MD5 with salted SHA-256, then one has stored a hash algorithm identifier someplace. Once that's done, it's no sweat to change over to a real password hash, at least for new accounts and password changes.

In this day and age, using md5 for hashing passwords should be punishable by flogging. Even using SHA-256 is just plain lazy.

Seriously, how hard is it to use bcrypt? There are even plenty of free libraries out there for crying out loud.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

That's very true. I got around this problem for one of my clients by versioning the encryption protocol.

During the login, the app looked at the registration date of the user and picked which version to use. E.G. Originally they were using SHA, but wanted to switch to blowfish. I entered that as #2 in an array set by inception date, so any new passwords were under the new algo. Older users were transparentely moved blowfish if they successfully logged in with the older function.

sigmasirrus wrote:

Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

That site is full of mom & pop like outfits

This proves that the harder it is to do the right thing, the less likely it will be done (or it will be done poorly). My hope is these types of leaks will finally jostle enough people in the hierarchy to get something done right. Maybe more people will educate themselves.

In this day and age, using md5 for hashing passwords should be punishable by flogging. Even using SHA-256 is just plain lazy.

Seriously, how hard is it to use bcrypt? There are even plenty of free libraries out there for crying out loud.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

That's very true. I got around this problem for one of my clients by versioning the encryption protocol.

During the login, the app looked at the registration date of the user and picked which version to use. E.G. Originally they were using SHA, but wanted to switch to blowfish. I entered that as #2 in an array set by inception date, so any new passwords were under the new algo. Older users were transparentely moved blowfish if they successfully logged in with the older function.

sigmasirrus wrote:

Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

That site is full of mom & pop like outfits

This proves that the harder it is to do the right thing, the less likely it will be done (or it will be done poorly). My hope is these types of leaks will finally jostle enough people in the hierarchy to get something done right. Maybe more people will educate themselves.

Edit: I meant "hashing", not "encryption protocol".

That's the way to fix it. But you were able to modify your solution. The Membership system and other frameworks, I'm sure, don't offer much flexibility.

I'm saying that if the "Mom and Pop"s used a framework that did some kind of hashing they'd be a little better off.

[snip] Given that many sites that roll their own membership system use plain text password storage rather than any hashing at all (http://plaintextoffenders.com/) using a prebuilt solution that uses a sub-par hashing algorithm is really the lesser of two evils.

But, but, but... a hash designed to be fast provides almost no protection. If one can intermix unsalted MD5 with salted SHA-256, then one has stored a hash algorithm identifier someplace. Once that's done, it's no sweat to change over to a real password hash, at least for new accounts and password changes.

"No sweat"? For developers with other projects on their plate and management that doesn't understand what a problem insecure password storage can be? ;-P

In the real world, things are not as easy as they seem.

I agree, though, that this should be a much greater focus. It's a shame that it's not important until they get sued.

"No sweat"? For developers with other projects on their plate and management that doesn't understand what a problem insecure password storage can be? ;-P

In the real world, things are not as easy as they seem.

I agree, though, that this should be a much greater focus. It's a shame that it's not important until they get sued.

I spent 30 years in the real world of medical informatics, most of it in a 500 bed general hospital. We've heard from eksith, who has actually implemented such a change, using a date as the versioning variable. It is, as you say, a question of focus and priority.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

Sure you can. Just shove the current salted hash into PBKDF2. Or apply the hash a few ten thousand times more. No one says you have to put the password into PBKDF2 directly.

How would i implement using the username or email address as extra salt?

You should not use the username or email as salt. The salt needs to be random and of a decent length (some say as long as the hash output itself). Very briefly, instead of doing hash(password), you do hash(password + random salt) and save the hash and the salt.

It's not hard to use on an initial design. The problem is, once the design is in place it's (somewhat) difficult to change. You can't change it offline because you can't "decrypt" hashed passwords (of course you shouldn't be able to anyway). You can only change it when the user inputs the password to log in.

Sure you can. Just shove the current salted hash into PBKDF2. Or apply the hash a few ten thousand times more. No one says you have to put the password into PBKDF2 directly.

PBKDF2 does more than just repeat the hash. Please see here for why you wouldn't want to just roll your own password-stretching algorithm: