by James Coglan

Menu

TL;DR: This is something of a rant. The important bit: I’ve built an open-source
storage-free available-anywhere secure password generator called Vault. It’s
available online and for your terminal.

What with recent weeks being a pretty bad time to be a LinkedIn, eHarmony or
Last.fm user, I’ve been putting the final touches on something I hope will
make it much easier for Internet users to keep their accounts safe. But before I
dive into that, let’s review the problems users are facing right now.

Anyone who uses the Web is likely to have signed up for a few, maybe dozens,
maybe hundreds of online services, covering a range of applications from
sharing pictures of kittens to storing all of one’s money and personal
information. Many of these accounts are identified by the user’s email address,
and most people use the same password for every service they sign up for,
because that’s what’s easiest (and often because nobody told them not to). So
while technically all of your data is in nice little silos, a breach of one
service provider’s database can often lead to the attacker gaining access to
accounts on lots of other services. People aren’t attacking eHarmony because
they want to know your ideal date – they want your email password, because
that’s the key to everything else. The money in your bank, the marketable
information Facebook knows about you, your whole identity.

So, the sensible thing to do is use a different password for every service you
use. Then when one site’s database gets stolen, none of your other accounts is
at risk. Well, sort of. How true this is depends on how good you are at picking
passwords. Actually, that’s a lie. It relies on you not picking passwords: the
best way to make sure that one database leak doesn’t lead to others is to use
completely uncorrelated passwords, i.e. get a random number generator to pick
them for you. Passwords chosen by people are highly likely to follow some
predictable pattern, or include affordances for memorability that make them
easier to crack.

But random passwords have a problem: they’re not memorable. This is actually a
good thing for security but it makes them hard to use safely. Advice for dealing
with this ranges from writing your passwords down (a horrible idea) to using a
password manager like 1Password, KeePassX or LastPass to store
your passwords in an encrypted database locked with one master password.
Unfortunately most people still don’t know about these tools and so you end up
with break-ins caused by someone leaving their password on a post-in note stuck
to their monitor.

While these tools are useful, and certainly much better than using the same
password everywhere or writing them down, I think they still suffer from a
number of problems, namely: adoption, security and portability.

All these tools require you to install something on your various devices. They
typically consist of an application that manages storage of passwords, a random
password generator, and maybe a browser plugin and syncing support. Some of them
also require payment. And while I don’t begrudge anyone trying to make money
from software, it must be recognised that all of this creates friction that
makes it less likely any given person will adopt the product. Less adoption
means more unsafe accounts out there, creating more potential for break-ins.
Trading off security against convenience is a very hard problem, but I think we
can make people substantially safer than they currently are, with far less
ceremony than these tools involve.

The second problem is security. While a good password manager will use a
sensible encryption scheme to protect your data, it’s worth questioning whether
storage is necessary at all. Any sensitive stored information requires very
careful treatment when it is stored on disk or transmitted over a network; the
safest data is that which is never stored anywhere and exists only in someone’s
head.

(While I’m on the topic of storage, it’s worth pointing this out to service
providers: because everyone uses the same password everywhere, if you run a site
that requires people to log in, you have their email password. I don’t care if
all your site does is let people rank versions of that one picture of a fishing
boat on the beach at dusk that everyone seems to love – you have people’s
email passwords and you had better take damn good care of them. This means
hashing them using an expensive salted hashing algorithm like PBKDF2,
Bcrypt or scrypt with a tunable work factor. It should take well over
100ms to hash someone’s password, more if you’re using a slow programming
language. It must be computationally expensive for someone to guess a single
password; using hashing algorithms designed for speed makes it easy for anyone
to brute-force your passwords. I have, worryingly, seen several people advocate
rate limiting or IP blocking on your login system for this purpose. This is
completely useless: the most productive thing for an attacker to do is not to
guess username-password pairs through your login form, where a round-trip takes
at least 10ms, but to steal your whole database and analyse it on their own
hardware. Your rate limiting does nothing to stop this, and the expense of
guessing a password must be baked into the hashes themselves.)

Anyway, where was I. Right, password managers, yes. The third problem with
password managers is partly a consequence of the storage problem: portability.
Password managers have two factors conspiring to make them less portable: they
require software installation and so must provide versions for every platform
they wish to target, and they must provide a way to make your password data
available everywhere you need it. I’ve seen too many products (‘too many’ can
mean 'one’ if it’s something you really care about) do an 'experimental’ Linux
release and then abandon it – I don’t trust that it’s going to continue to be
worth any company’s time supporting all the platforms I need to have my
passwords available on. And portability doesn’t just mean availability on all
my devices. What if you’re travelling, or out without your phone and you need
to pop into an Internet café? What if your password manager simply doesn’t work
on your phone? What if your password manager doesn’t provide online retrieval,
or it’s down for maintenance? You’re stuck.

So, you can’t use the same password everywhere, creating good passwords is hard,
bad password policies make it even harder, and password managers suck. But,
back in December I found a good idea in the aforelinked article:

I generate a different password for every service, based on a convoluted
master password and the name of the thing. I do this because it’s what you’re
supposed to do; it’s what security nerds (including myself for the purposes of
this post) tell everyone else to do. “Ho ho!” we all chuckled to ourselves
after the Gawker leak, and the subsequent breakins to various other things
that used the same passwords. “If only these chumps had been generating
different random passwords for every service!”

So my passwords look like 'fC`29ap5w78r3IJ, or Ab3HE4 2Iv5hJk\K, or
mw@\_h< ~o04neHiJ{. Those are actual examples i just generated. I’m eating
my own dogfood, so to speak.

Now remember the qualities we want from our passwords: different for every site,
and uncorrelated. The word 'uncorrelated’ is usually taken to mean 'use a random
number generator and store the result somewhere’. But we can get passwords that
look random (technically, this means there’s no polynomial-time algorithm that
can distinguish them from genuine random noise) in a deterministic way: a
function that produces random-looking output but gives the same result every
time if given the same input. We can just use hashing functions for this: their
output is pseudorandom, deterministic, and changes drastically if the input is
slightly changed. This means we can generate a set of random-looking passwords
from one master passphrase and a string that’s different for each service we
use, and because it’s deterministic we don’t need to store the result anywhere.
This means we can put up a static web page that implements such a function,
never stores or transmits the user’s data, and is available everywhere and
hostable by anybody.

So that’s what I’ve built. A simple page that takes your master passphrase
and service name, and generates a very strong password from them. It lets you
select which characters are required/forbidden, to work around sites with bad
password policies. It has a command-line version based on Node.js. And,
needless to say, it’s open source and anyone can host a copy of it.

The core idea of Vault is that it works without storing anything by default.
This means no installation, no storage to secure and sync, and total
portability: it’s just a static web page instantly accessible from anywhere. You
can host your own copy for when my site’s down, put a copy on your laptop or
internal network, whatever you want. The storage options offered by the
command-line version are simply a convenience: I can get my Gmail password by
typing vault gmail | pbcopy, but if I’m on another machine without my stored
settings I can still get my password from the web version. I am currently
investigating ways of providing similar convenience on the web, but until then
you can do something quite easy: write your character settings down. The
character constraints of websites’ passwords are public knowledge already,
there’s nothing dangerous about keeping a note of them in a text file or in your
wallet.

But, I hear you cry, how does this protect anyone? Can’t an attacker just use
Vault themselves to pre-process my password before trying it? Yes, of course
they can, but they could have just tried your password before, so they’ve not
gained any new power. Vault protects you in two important ways. First, the
passwords it generates with the default settings have about 130 bits of entropy
(20 characters from a uniformly distributed 94-character alphabet). This is far
higher than a dictionary-word password, making it resistant to brute-force
attacks, in fact zxcvbn estimates they will take billions of times the age
of the universe to crack by brute force. Second, the fact that a set of Vault
passwords looks entirely random means that if attacker gets one of your
passwords they cannot predict any others or discover your master passphrase.
This is especially true if you include your username in the the service name
when generating a password so you get a universally unique password. Plus, it
gives you the freedom to choose a good master passphrase rather than being
constrained by the awful password policies affecting many websites.

I’ve been using this system for six months now, and the generator algorithm has
been through several rounds of design improvements to the point where I’m now
happy calling it stable and freezing it. (I’d go into how it works but I’ve
already rambled on for 1700 words so I’ll save that for another post.) Initial
response from the few people I’ve shown it to has been really positive, and I’d
encourage you to try it out if you’re still using one password everywhere.
Read the FAQ first before diving in.

I’ll close by saying that I’m absolutely not trying to compete with the
non-password-based authentication systems that are coming out. I really want
BrowserID to succeed and kill passwords for good, but we’re not there yet.
I’m just trying to do something that works with the web as it is today, that’s
reasonably secure while still being extremely convenient, and is much better
than what the majority of people do with their passwords. It’s a stepping stone
until we have something better.

—

If you’ve enjoyed this article, you might enjoy my recently published book
JavaScript Testing Recipes. It’s
full of simple techniques for writing modular, maintainable JavaScript apps
in the browser and on the server.