Skip to main content

Write your passwords down

Here's my advice on password security based on the collected opinions of others:

1. Write them down and keep them in your wallet because you are good at securing your wallet. (ref)

2. Use different passwords on every web site because if you don't one site hacked = all your accounts hacked. (ref)

3. Use passwords of at least 12 characters. (ref)

4. Use mixed-case, numbers and special characters. (ref)

Research says you need 80-bits of entropy in your password so it needs to be long, chosen from a wide range of characters and chosen randomly. My scheme gives me 104 bits of entropy.

My passwords are generated using a little program I wrote that chooses random characters (using a cryptographically secure random number generator) and then printing them out on a tabula recta. If you were to steal my wallet you would find a sheet of paper that looks like this in it (I have a second copy of that sheet left with a friend in an envelope):

I use that sheet as follows. If I'm logging into Amazon I'll find the intersection of column M and column A (the second and third letters of Amazon) and then read off diagonally 16 characters. That would be my Amazon password (in this case, TZ'k}T'p39m-Y>4d); when I hit the edge of the paper I just follow the edge).

The security of this system rests on the randomness of the generated characters and the piece of paper.

PS Yes, it's a total pain to use long, random, different passwords.

PPS If it's not obvious to people you can add a second factor to this (something only you know) in the form of the algorithm for picking the password from the sheet. For example, instead of using the second and third characters from the site name you could pick any combination. And you could change the letters as well (e.g. for Amazon you could use the last two letters moved on one place in the alphabet; you'd have PO as the key). Also you don't have to read diagonally but could use any scheme that works for you (e.g. a spiral pattern, read vertically, read characters at offsets from the start based on the Fibonacci sequence, etc.).


Ruben Berenguel said…
Good approach (I saw a very interesting site that generates cards like yours, by the way, but I don't have the URL at hand). I follow another scheme... I use phrases from some book I know almost to heart. Like a 30 or 40 characters long phrase, with random case changes (far lower entropy than your method, I guess). And I don't write them down, becase I already know them, or can look them up. But I like your approach... I think it is time to upgrade my method.


Latest in my blog: The emacs 30 day challenge: using gnus to read email as a newbie
Unknown said…
I like the table approach. I've always written down passwords - I've believed for some time that having your passwords WITH you is better than having the same/easy passwords that you can remember.

I store a copy of my password list in my fire proof safe at home, and the really common ones (Amazon, my computer, banking, GPG key, etc...) I've memorized the pattern on my keyboard...
Paul Robinson said…
Isn't it better to use a password manager like 1Password (use any length of password) with the encrypted password file stored in Dropbox for cloud recovery?
PaulH said…
I am trying the open source password store Keepass. It seems to do what you recommend regarding password generation, but its printing capabilities are very limited - nothing even close tabula recta. I like the idea of a cryptic hard copy. Portable and no chance of a crash. :-)
J. Aaron Farr said…
I tend to use romanized Mandarin Chinese phrases which I then convert some into leet-speak. It tends to create long, complex passwords that are very easy for me to remember.
jockc said…
I like this idea, but it might be a little inconvenient. I recently saw a blog post somewhere with another good scheme for writing down passwords safely. You have a 3-4 character 'secret part' suffix and a 3-4 letter ID prefix part. The secret part is not written and is the same for all passwords. So let's say my secret part is 'xyz'. To write down my Amazon and Bank of America password I would write something like:


(ID part)

the actual passwords would be xidj3xyz and ie7ixxyz. Of course you could do variations like instead of having a fixed secret part, use the ID part reversed or something.
Unknown said…
Can you explain how the piece of paper is more secure than, for example, KeePassX or a similar cross-platform password storage tool which lets you generate arbitrary length passwords (I use 20+ usually)?

It seems practically easier to steal the password from your wallet than to decrypt password database.
WoJ said…
This is nice for the geeky "do it yourself and forget the wallet at home" section.

For the lazy rest of us there is, thanks God, Lastpass (
Unknown said…
Innovative system for remembering them. For when I'm at a computer I use KeepassX where the database is stored on my dropbox account.
Sullof said…
I think that using password schemes is bad. Because in order to be useful, the method needs to be fast, simple and replicable.
Suppose that someone creates a fake website in order to grab one of your smart passwords. If he understands that you use a method, he will try to deconstruct the method based on the fact that his website surely is included in some manner in the password itself.
Also, since many people who use these methods tend to divulge them to the community, there isn't even a need to create a fake website to understand your passwords.
The only solution that really works is to use a password manager. My favorite obviously is Passpack, because I am a co-founder, but regardless of which software you choose the important thing is that you use it.
My advice is not to relay on any clever schemes because you may be in for a bad surprise.
pat said…
I use the same 6 and 8 character passwords on every site I visit (1000s) and have never had a problem. What a pain to follow those steps. No thanks.
Derek said…
The problem with using the same password for different sites is that your password is only as strong as the weakest security in any one of those sites. See the recent Gawker problems for a perfect example.
max.countryman said…
I was inspired to write a little Python script that generates a tabula recta and finds a password based on a row and col intersection, as described in this post.

The challenge now is finding a better PRNG. Python's random module uses the Mersenne Twister (not suitable for cryptographic uses), however the SystemRandom class makes use of os.urandom, which in some cases (think OS X, FreeBSD, OpenBSD) makes use of the Yarrow algorithm, a well known CSPRNG.
X said…
How does this work in conjunction with sites that have different rules? Some sites only allow passwords of up to 11 characters, and if your approach requires 16 characters, how are you going to remember that a site requires at most 11?
Anonymous said…
Q John, would /dev/random [0] on linux or /dev/urandom accessed via python random.SystemRandom [1] in Python pass your CSPRNG requirement?


[1] via
Unknown said…
I saw your post about your mail Canary and it sent me here.

Your method for managing password seems both not so secure and difficult to use.

Not so secure, because, for example, your password for Amazon and Imazomby is the same.
Furthermore with a sufficient amount of data, I can retrieve you main super password (the sheet of paper).

Of course, your method is far more secure than what most people do. But you should take a look at my method.

Every password is just at one copy/paste. But yes, you need to remember only one strong password (which you might have written somewhere).

You can have 40 character long very easily. I use this method for some years now, and I am really happy with it. While I am certain it is both easier and more secure than your method.

That's very similar to the technique I used in my program called quepasa

I agree with the weakness in my password scheme that some passwords overlap. Note that in your scheme the security will rest on the master password you choose as SHA1 is very fast and it would not be hard to recover your original password given a ( site, password ) combination that got leaked.
Anonymous said…
Thanks for the great post. In case others find this idea interesting, I built a tool called passtab to generate these Tabula Recta's in PDF for printing (with some additional features). Cheers!
jm said…
I am sure other things exist but here is a quick python script for creating your own random tabula recta.
skyriser said…
Cool, reminds of our iPhone app "Password Grid":
Unknown said…
Hi, I stumbled across this post on Do you make your program to generate a tabula recta public?

What does one need to generate a random number?

In essence how do I get this to work for me? How about a step by step for the unwashed masses?
Unknown said…
Lastpass + Yubikey

I still use a long twenty character mix of letters, numbers and special characters that are symbolic to me, but senseless to anyone else.

Yubikey gives it a second factor.
Unknown said…
Good approach. Password generator tools like is another way to generate password.

Popular posts from this blog

Your last name contains invalid characters

My last name is "Graham-Cumming". But here's a typical form response when I enter it:

Does the web site have any idea how rude it is to claim that my last name contains invalid characters? Clearly not. What they actually meant is: our web site will not accept that hyphen in your last name. But do they say that? No, of course not. They decide to shove in my face the claim that there's something wrong with my name.

There's nothing wrong with my name, just as there's nothing wrong with someone whose first name is Jean-Marie, or someone whose last name is O'Reilly.

What is wrong is that way this is being handled. If the system can't cope with non-letters and spaces it needs to say that. How about the following error message:

Our system is unable to process last names that contain non-letters, please replace them with spaces.

Don't blame me for having a last name that your system doesn't like, whose fault is that? Saying "Your last name …

All the symmetrical watch faces (and code to generate them)

If you ever look at pictures of clocks and watches in advertising they are set to roughly 10:10 which is meant to be the most attractive (smiling!) position for the hands. They are actually set to 10:09.14 if the hands are truly symmetrical. CC BY 2.0image by Shinji
I wanted to know what all the possible symmetrical watch faces are and so I wrote some code using Processing. Here's the output (there's one watch face missing, 00:00 or 12:00, because it's very boring):

The key to writing this is to figure out the relationship between the hour and minute hands when the watch face is symmetrical. In an hour the minute hand moves through 360° and the hour hand moves through 30° (12 hours are shown on the watch face and 360/12 = 30).
The core loop inside the program is this:   for (int h = 0; h <= 12; h++) {
    float m = (360-30*float(h))*2/13;
    int s = round(60*(m-floor(m)));
    int col = h%6;
    int row = floor(h/6);
    draw_clock((r+f)*(2*col+1), (r+f)*(row*2+1), r, h, floor(m…

Importing an existing SSL key/certificate pair into a Java keystore

I'm writing this blog post in case anyone else has to Google that. In Java 6 keytool has been improved so that it now becomes possible to import an existing key and certificate (say one you generated outside of the Java world) into a keystore.

You need: Java 6 and openssl.

1. Suppose you have a certificate and key in PEM format. The key is named host.key and the certificate host.crt.

2. The first step is to convert them into a single PKCS12 file using the command: openssl pkcs12 -export -in host.crt -inkey host.key > host.p12. You will be asked for various passwords (the password to access the key (if set) and then the password for the PKCS12 file being created).

3. Then import the PKCS12 file into a keystore using the command: keytool -importkeystore -srckeystore host.p12 -destkeystore host.jks -srcstoretype pkcs12. You now have a keystore named host.jks containing the certificate/key you need.

For the sake of completeness here's the output of a full session I performe…