Password generator combining actual words

Solution 1:

Locally installed dictionaries are stored in /usr/share/dict/, for example:

$ ls -1 /usr/share/dict/
american-english
british-english                                                                                                          
cracklib-small                                                                                                             
README.select-wordlist                                                                                                  
words                                                                                                                    
words.pre-dictionaries-common

Here the first two are interesting, those dictionaries are simple word lists with one word per line. We can use shuf to output 4 random lines from one of them (and awk to replace newlines with spaces):

shuf -n4 /usr/share/dict/american-english | awk NF=NF RS= OFS=' '

Here's some example output:

contributions autumn's catalepsy's hemline's
footlights Levi's awfuller rascals
fogies flavoring preregistering requital's
Coleman's cartel halfpennies Williamson
étude's maintainers reviler's dapperest
pizazz Galahads McDowell derby
corroborate bureaucracies anchovy meager
filet Tawney feudalistic backstabbing
Beatriz sitcom surpasses guttural's
warehouse's unfamiliarity's Ashlee's sanguinary

Solution 2:

The computer aspect

Use a method, that provides sufficient randomness alias entropy, often measured in bits.

Accept the first offered choice from the random process. Otherwise the entropy decreases (often more than you would think), and your security level will be lower.

The human aspect

Considering the human aspect it is important that you can

  • accept

  • remember

  • spell

the words in the password/passphrase.

In order to preserve randomness, entropy, it is very important the you accept the first offered choice, and the word list can make a difference.

Using a big word-list provides more entropy per word, but chances are that you or users in the group, whose IT security you are managing, refuse to use the first offered password/passphrase. Your name, city or other personal data might be selected from the word list in an extremely rare case, but more often you might be offended by a political, ethnical, religious, sexual or generally rude word. Of course, if you like such words, you can add them to your own word list ;-) but don't force them onto other people.

It will make it easier to accept, remember and spell the password/passphrase, if you use a list of the most common words, where the words are selected for this particular purpose.

Create a word list yourself

You can create such a list yourself (and in your own language, and remove words with special characters, because they might cause problems with some software).

The following shellscript pruner might help. You get only lowercase words, which makes the typing easier (special characters are removed) and only words in the interval [4,10] letters (not too short, not too long). But there is no sorting of these files according to how easy to accept they are. You need other information to remove uncommon, difficult and potentially offensive words, or you can do it manually.

#!/bin/bash

LANG=C

for wordlist in \
$(find /usr/share/dict/ /usr/lib/python3/dist-packages/xkcdpass/static -type f -size +10k) \
$(ls -1 word-list.txt 2> /dev/null)
do
# prunedlist="${wordlist##*/}"
 prunedlist="${wordlist//\//_}"
 prunedlist="${prunedlist/.txt}-pruned.txt"

 echo "source:  $wordlist"
 echo -n "Total number of words in list:              "
 < "$wordlist" wc -l

 echo "target:  $prunedlist" 
 echo -n "Used lower case words ( 4 < length < 10 ):  "

 < "$wordlist"  tr -d '\015'| \
 grep '^[a-z]\{4,10\}$' | \
 tee "$prunedlist" | \
 wc -l
 echo "-------"
done

The shellscript will find the default word lists and also word lists for xkcdpass and cracklib, if installed.

Now you can run your shuf command line to test the pruned word lists,

$ for i in *pruned*; do echo "$i:";shuf -n4 "$i"| awk NF=NF RS= OFS=' ';echo "-----";done

but I would prefer xkcdpass.

Download a word-list

You can download such a list (check that it consists of unique words and is long enough, at least 2048 words = 2^11 words, which corresponds to 11 bits of entropy).

Downloading, checking and using such a file from the internet should be safe. As usual, you should only use reliable web sites.

The important thing for the security is not the words themselves, but that you let a random process (for example dice) or a good pseudo-random computer process select the words. Do not tamper with the random process by selecting or modifying the password manually.

At this Ubuntu help wiki page: The XKCD method - xkcdpass you can find a

Custom word list - 'word-list.txt'

Useful command-lines with xkcdpass

Decide what works best for the security level you need in your particular case,

  • lower number of words that are strange and complicated
  • higher number of words that are common and easy

It may be vary between persons (and groups of people, if you are considering how to set a policy or custom tool for an organization).

You can let xkcdpass compute randomness alias entropy in bits by adding the verbosity option -V. These examples use the default word list and the custom word list from the Ubuntu help page word-list.txt,

xkcdpass -V -n 3
xkcdpass -V -n 4 --min 4 --max 10 -d . -w word-list.txt

Using the default word file: lower number of words that are strange and complicated

# Normal security level at home, entropy = 45 bits;

$ xkcdpass -n 3
demeanour basely extrude

# Next security level, entropy = 60 bits:

$ xkcdpass -n 4
metal cottager advocacy soursop

# High security level, entropy = 76 bits:

$ xkcdpass -n 5
hostile impounder Caledonia ramie Goddard

# Very high security level, entropy = 91 bits:

$ xkcdpass
ambrosia Cossack vivify Barbudan royal Campinas

Please notice that this is the default setting. But the security level is very high only if the user

  • can accept the first password/passphrase offered,
  • can remember it without a post-it sticker on the monitor/laptop (or other 'shortcut'),
  • can spell it without a post-it sticker on the monitor/laptop (or other 'shortcut').

Using a custom word file: higher number of words that are common and easy

# Normal security level at home, entropy = 47 bits:

$ xkcdpass -n 4 --min 4 --max 10 -d . -w word-list.txt
sharp.hockey.steal.backyard

# Next security level, entropy = 59 bits:

$ xkcdpass -n 5 --min 4 --max 10 -d . -w word-list.txt
initially.assistant.barely.framework.regional

# Next security level, entropy = 71 bits:

$ xkcdpass -n 6 --min 4 --max 10 -d . -w word-list.txt
snake.food.dress.perception.club.waste

# High security level, entropy = 83 bits:

$ xkcdpass -n 7 --min 4 --max 10 -d . -w word-list.txt
stand.mentor.know.cream.automatic.treatment.effect

Solution 3:

There's probably any number of XKCD password generator implementations out there:

  • xkcdpass, available from the xkcdpass package, Python (doesn't seem to use a CSPRNG)

    $ xkcdpass
    baroque viand blindfold hooch notion ravening
    $ xkcdpass -n4
    useless elated liveable overfly
    
  • xkcd-password, NodeJS module
  • dozens of websites
  • diceware, which follows a similar process, but using websites
  • ...

Pick your poison.

Also see:

  • Is “the oft-cited XKCD scheme […] no longer good advice”? on the Security Stack Exchange

Solution 4:

Please don't do this.

  • Maybe some tools only guess passwords using characters, but some guess multiple common words soon if they don't already.
  • If you're remembering your passwords, you are almost certainly reusing them (maybe with variations) for different sites. If you have 30 accounts on the internet, I bet at least one of your passwords are compromised each year. Someone with your password from one site will try it with variations on your other accounts. So your horseBatteryStapleLinkedIn password allows someone to guess that your gmail password is horseBatteryStapleGoogle, horseBatteryStapleGmail, horseBatteryStapleLiamg (Gmail spelled backwards). If you can think of it, someone else can too.

I know it's a pain, but use a password manager instead. Have it generate unique, random passwords for every site. If you're paranoid like me, you can change a couple characters in the suggested password in case the generator's (pseudo-)random algorithm is ever compromised. I like KeePassX with the database backed up in DropBox, but LastPass is easier for some people to use. There are many paid password managers as well.

Good News

The human brain is good at imposing order, even when there is none. You can remember random characters by staring at them until you perceive order in the chaos. There is no order. This is just what your brain does. For instance:

bJbRpZ2S9

Means something to you. If you type it enough times, you'll come up with something like this to remember it:

black Jack beyond Re post Zaps 2 Surly 9's

You can eventually remember 2 or 3 master passwords that way. One for your OS, and one for your password manager. That's all you need.

P.S. When using a password manager, periodically print out your passwords and put them in a tamper-evident envelope in a safe somewhere so you don't lose them. Ideally where your next-of-kin can get them if something happens to you, like a safe deposit box.