www.pudn.com > AntiCrack.zip > APPENDIX


I'd like to thank Chris Samuel and Peter Grandi for all their help in 
beta-testing early versions of Crack, and in Peter's case especially, 
for dropping me into the deep end of troff. Die, you bastard.  As for 
Chris's major contribution, see "Scripts/plaster". 8-> 
 
For the v3.? versions of Crack, I'd like to thank Chris Myers, Randal 
Schwartz, Chris Lewis, and M.Maclaren. Also Brian Tompsett, for 
pointing me at the now infamous v3.2 bug, and for suggestions, patches, 
and enormous amounts of debugging information. To him should go the 
prize for "Most Vociferous Beta Tester Ever". 
 
For Crack v4.1, the greatest help has come from the members of the crack 
beta team, the most vociferous of whom are: 
 
brown@gov.llnl.ocelot, cavanaug@edu.uiuc.cogsci.lees, 
csx040@uk.ac.coventry.cch, dor@acl.lanl.gov, dowling@gov.ncifcrf, 
glad@daimi.aau.dk, kint@engr.washington.edu, korz@edu.columbia.cs.bach, 
morgan@edu.uky.engr, mycroft@edu.mit.ai.gnu, nelsonm@edu.orst.cs.storm, 
nestey@edu.colorado.denver.copper, nigelm@uk.ac.york.ohm, 
pcl@uk.ac.oxford.convex, phil@com.sequent, phill@com.sequent, 
pkh@uk.ac.nott.cs, sck@com.ibm.watson, shabby@edu.purdue.cc.mentor 
 
- especially Fred "Mr Statistics" Korz, Paul Leyland, and shabby@purdue 
for all the debugging info.  Also a bit thanks to Michael Glad for being 
so helpful while we were writing a decent software interface between 
Crack and UFC. 
 
I also wish to acknowledge the help of Kent Landfield (moderator of 
comp.sources.misc) and Dan "COPS" Farmer, both of them for goading me 
into releasing a version of Crack with fcrypt() installed. Without 
them, I probably would have been too timid... 
 
Finally, my gratitude goes to my girlfriend Gilly, for her support 
during the bad times.  You are the everything. 
 
-- 
INET: aem@aber.ac.uk       JANET: aem@uk.ac.aber      BITNET: aem%aber@ukacrl 
UUCP: ...!mcsun!ukc!aber!aem          ARPA: aem%uk.ac.aber@nsfnet-relay.ac.uk 
Alec Muffett, Somewhere in the UK, Probably lying under a tree drinking cider 
 
********************************************************************** 
 
Several people have asked me why I don't write Crack so that it 
distributes dictionaries over the network and hacks the same password 
file on each machine, as opposed to spreading users over the network and 
using the same dictionaries. 
 
There are several reasons for this, which I will outline. 
 
The reasoning that spreading the dictionaries over the network is faster 
is correct in the case of cracking the passwords of ONE user - it is 
most efficient to run different dictionaries on him on several machines, 
and you will break his password eventually. 
 
Scaling this by a factor of 'n' users causes problems.  Firstly, if a 
machine guesses one persons password, it must inform all others on the 
network not to waste time cracking him, but to get on with the other 
users.  This is difficult and nasty. 
 
Secondly, it is not what Crack was designed to do.  The name "Crack" is 
actually a misnomer - Crack really ought to be called "Passwdcheck" or 
something similar, but such names lack sex appeal. 
 
Crack is not a program designed to break the password of every user in 
the file.  Rather, it is designed to find weak passwords in the file, by 
attacking those sorts of bad passwords which are most likely to be used, 
in the order in which they would most easily be found (ie: are most 
likely to be used by a moronic user). 
 
Crack is not designed to break user passwords; it is designed to break 
password files.  This is a subtle but important distinction. 
 
If you want to break into a safe, you do not take a hammer at every bit 
of it in turn; instead, first you try some simple combinations, then you 
try blowing the hinges off, then you get out an acetylene torch and go 
for the bolt.  If that doesnt work, THEN you start on the walls.  You go 
for the bits which are most likely to be weak first. 
 
Consider a password file with 'n' users in it.  Say that your ordinary, 
serial password cracker (eg: the one supplied with COPS) has a 
dictionary of 1000 words, and tries each word 6 ways (upper/lower/mixed 
case, permuted with forwards/backwards) 
 
Also consider that out of that 1000 users, only one (the last one) has a 
guessable password - "fred". 
 
Also say that it takes time 'T' seconds to encrypt a word. 
 
If you use the "try each user in turn" method, like the COPS password 
cracker, you will have to wait for a time:- 
 
	999 users * 1000 words * 6 ways * T = 5,994,000 T seconds 
 
before you get to that last user.  Spreading this load around on a 
network only alleviates the number of words to be searched (divides them 
by the number of machines you are working on). 
 
Thus, if you use 10 machines, the machine which will guess "fred" will 
get to that last user in:- 
 
	999 * (1000 / 10) * 6 ways = 599,400 T seconds. 
 
Alternatively you can try it the Crack way - "fred" is a word which 
appears in a forwards dictionary.  You will only wait:- 
 
	999 users * 1000 words * 1st way * T = 999,000 T seconds 
 
to get to that user.  Now split the users across 10 machines (for 
simplicity, as outlined above):- 
 
	(999 / 10) users * 1000 words * 1st way = 99,900 T seconds 
 
To get to his password, in ONLY 17% of the time taken by networking 
using the serial cracking method.  This is only a boundary case, but I 
hope I have illustrated the concept. 
 
********************************************************************** 
 
Crack has several other optimisations because of its structured password 
guesses.  The figures below are entirely empirical, but I reckon that 
they're as good as any: 
 
The first pass that Crack makes is over the user data user information 
gleaned from the users' password field.  In my test file, this gets 
about 4% of the passwords (out of a total of 15% guessed).  This pass 
also completes very quickly, working as it does from a very small 
amount of data, but one which is very frequently used for passwords. 
 
The first sweep of the second pass, consisting of lowercase dictionary 
words, gets about another 5% of the passwords. The length of the first 
sweep depends on how much CPU and how many dictionaries I supply, but 
using the Ultrix /usr/dict/words and my bad_pws.dat, over 4 CPUs, it 
doesn't take much more that a few hours. 
 
For the further sweeps, the percentages cracked per sweep tail off, 2%, 
1%, 0.5%...  But they are the people with fairly exotic passwords, and 
it's only common sense that that they will take some time to crack. 
 
********************************************************************** 
 
There is another major optimisation that I haven't mentioned. 
 
Because of the way the UNIX crypt() algorithm works, each encryption is 
"salted" with a two letter sequence which is stored as the first two 
characters of the encrypted password.  This salting means that the word 
"fred" can be encrypted and appear in a password file in (literally) 
thousands of different ways - so long as each encryption has a 
different salt. 
 
Hence, it makes sense to do things in this manner: 
 
1) sort and group the input data by encryption salt. 
2) for each different groups' encryption salt 
	* get a dictionary word 
	* encrypt it using that salt (This is the time consuming bit) 
	* compare the encryption with each member of the group with that salt 
	* if it matches, you have guessed that users password. 
 
This knocks (empirical guesswork time again) up to one third of the 
dictionary encryptions off - thus saving you 0.3 of the time all the 
dictionary sweeps would ordinarily take. 
 
Crack gives this statistic when it says 
 
    pwc: Loaded 'n' password entries into 'm' salted lines. (x%) 
 
where 'x' is the percentage of the total passwords loaded which have 
different salts. 
 
********************************************************************** 
 
Some people have asked me how to generate safe passwords.  This, has 
become a religious issue, and there are now several vociferous 
"password geeks" on USENET, who will say "my method is the best", in 
the same way that some mathematicians will try to compare so-called 
"random number generating algorithms". 
 
Such statements are pointless.  I'm sorry for adding to the confusion, 
but I must say that I think they are wrong. 
 
Okay, so I am a security fatalist and a security philosopher, but I am 
not going to give and hard and fast answers; rather, I'd like to make 
some points and recommendations to the people out there.  Security isn't 
a tangible thing, it is applied psychology. 
 
The whole point of a password is to prevent people accessing your 
system, getting into it from outside.  Once someone is inside your 
system, assuming that they have the relevant knowledge of your O/S, it 
is safest to assume that anyone can get to be 'superuser'.  Your only 
security once someone is on your system is called "security by 
obscurity".  If your user has sufficient knowledge, you've "had it". 
 
The question isn't "How secure can my system be made?". 
 
The question really should be, "How much do I care, how much can I trust?". 
 
A system can be perfectly secure without any passwords at all, so long 
as it is in an environment of people who recognise its purpose and 
depend on it.  I say this after having had acounts on several 'public' 
machines, which could have been taken to bits by any competent Unix 
person, but were largely safe - because when someone worked out who did 
anything nasty, the culprit was ostracised from the community.  There 
_is_ a caveat to this, however. 
 
The problem is the sort of people who go around the world 'collecting' 
computer accounts and breaking machines, those who have either a 
childish mentality or an ulterior motive. 
 
The former are like the little boys who go around breaking windows and 
vandalising things 'for kicks'.  They are the ones who see every 
password file as a "NO ENTRY" sign, and therefore, driven by what they 
think is anarchy and fun, they break in and smash the place up.  Tell 
them that they are behaving like children, and they will behave moreso. 
 
The latter are driven by personal motives or money.  Their reasons are 
too complex for me to analyse here. 
 
The 'babyish' hackers need a lesson (which I hope that eventually they 
learn) that true anarchy is for the general good, and is best achieved 
by fiat amongst the community.  USENET is a good example - there is a 
lot of petty bickering and arguing, but an incredible amount of good 
comes out of it.  It is anarchy that the greek philosophers would have 
approved of. 
 
What I am trying to say is that, when I say that if someone gets into 
your system, you've "had it", you should consider whether there is 
anything to have "had" in the first place.  There is no point in getting 
yourself paranoid over security - if you do, you'll lose out.  Don't be 
too paranoid.  Be SENSIBLE instead, and secure your system according to 
it's needs, and not according to some 'holy bible' of absolute security. 
 
If someone gets into your system, you find out how they did it, patch 
the hole, check for back doors, brush yourself off, and start again. 
It's not the end of the world. 
 
What this statement doesn't address (yet) is the needs of system 
managers who have a REAL need for security - be it corporate data or 
research work - on their system.  As I have said before, most O/S's have 
gaping holes in them that cannot be entirely filled, and so the crackers 
must be stopped on the doorstep.  At the password login. 
 
People who say that they have a way of generating safe passwords are 
misinformed, IMHO.  Saying that the password "wyufwqpl" is secure is as 
meaningful as saying that the number "4" is random.  Password security, 
like any other form of computer security, is not absolute, but should 
be taken in context. 
 
You can't say that a certain method will provide secure, random 
passwords, because, in defining an algorithm to create these passwords, 
you will use only a subset of all the possible passwords that could ever 
exist.  You have shrunk the 'search space' for the passwords. 
 
Someone merely has to write a password cracker which will search this 
small subset of passwords, in order to break your system.  Passwords 
generated by any algorithm, human or computer based, are merly 
pseudo-secure, in the same way that numbers can be pseudo-random.  For 
illustration of this aspect of password security, read the document 
"Password Security, A Case History" by Morris and Thompson. 
 
There is an incredibly large set of possible passwords in the world, and 
the best approach toward choosing a password is not to try to find a way 
to generate 'secure' passwords - there are no such things - but rather 
you should learn to choose passwords which are not easily searched for. 
Passwords which are out of the 'search space' of most password crackers 
like 'Crack'. 
 
Read the Crack documentation.  See what sort of things other programs 
like Crack would search for.  Think of some yourself.  I am not going to 
specifically mention methods, you should really work something out for 
yourself. 
 
At the bottom line, the password "fred" is just as secure (random) as 
the password "blurflpox"; the only problem is that "fred" is in a more 
easily searched part of the "password space". 
 
Both of these passwords are more easily found than "Dxk&2+15^N" however. 
Now you must ask yourself if you can cope with remembering "Dxk&2+15^N". 
 
********************************************************************** 
 
Some time ago, I was listening to the REM album 'Green' on the way back 
from the Cropredy folk festival, whilst thinking over things to do to 
Crack, and I was struck (not for the first time) by the words of the 
first verse to 'World Leader Pretend':- 
 
	I sit at my table, and wage war upon myself. 
	It seems like it's all, it's all for nothing. 
	I know the barricades, and I know the mortar in the wall 
	I recognise the weapons, I use them well. 
 
	This is my mistake, let me make it good, 
	I raised the wall, and I will be the one to knock it down... 
 
- writing password cracking programs gets to you after a bit.