09-29-2020, 03:59 PM
With commit 04d5e5a119ba4c44bedb5bcccd5a42f82463cca3 I have added a new attack-mode called "Association Attack" (a different name could be "Context Attack"), but let's stick to "Association Attack" for reference. This attack is not yet ready to be used in a production environment, it's a very early first version, but I wanted you to play with it.
If you ever used JtR before, the "Association Attack" is somehow of what the "single mode" is in JtR. The attack-mode is strong if you have large -salted- hashlist and at the same time you have some "hint" or "information" for each of the hashes inside the hashlist. Typically the username. The username itself could be seen as a "hint", because some humans tend to use the username as a part of the password. Or the username contains parts of the password because the username is changed for the site the username is used. Then we can extract this information using rules.
The main idea of this attack is to not try all the different (unique) salts with all password candidates from a wordlist, but to only attack each of the hashes in the hashlist with the associated "hint". From a development perspect, we remove the loop in hashcat which iterates through the different salts. To make this attack more efficient, we typically use the "hint" in combination with rules (but that's not a requirement). Using a GPU for this task is not so easy because of the many cores that we have and that we have to give work to. That brings us to an important requirement. Your hashlist needs a large number of unique salts to make this attack efficient (to utilize the GPU fully). Ideally the number of GPU Processors * 64 (or more). You can find out about the GPU Processors of your GPU using hashcat -I. My GTX980 has 16, so I need a hashlist of at least 1024 entries to fully utilize the GPU.
Unrelated Pro-Tip: If you want to attack a slow single hash with a single word but with some rules added to it, then the capitalized -S is what you want.
When I first created this patch I was thinking of how the user could specify what is the "hint" for each of the hashes. In JtR's single mode it simply uses the username from the hashlist. This is very easy to handle, but it's not exactly what I was looking for. In hashcat we specify a hashlist as regular (with or without username) but we also provide a wordlist as regular. However, this wordlist has to have exactly the number of lines as the hashlist. This has both advantages and disadvantages, but I liked the idea to use this even with a folder with many wordlists. This is kind of the opposite of what creates the efficiency of this attack, but I think there are some situations where multiple wordlists make sense. For instance, if you have large portions of substrings which were added to a passwords afterwards, by yubikeys on keypress, by site specific pepper strings or by user using the company name. I can also try to make it 1:1 as in JtR where the username is building some sort of virtual wordlist in memory, but only if I see that you people are really interested in this attack-mode.
One of the problems I was thinking of is if it is possible to have a mixed version of this attack-mode and a regular rule-based straight attack-mode in combination with -S. That could be useful if you have let's say only 10 hashes, because this is not enough to keep the GPU busy and then combine it with rules. This is a more complicated code change and again if I see you people being interested in it.
So here's how you use it. In a first step we will build a demonstration dataset (hashlist) in username:hashlist format as you probably have it and then I show you how to split it so you can use it with the new attack-modes.
1. Build the test dataset, creating a bcrypt hashlist
The resulting "final.txt" looks like this:
2. This is the point where you typically start. You have a hashlist in username:hash format. We need to split them in order to use them with the new attack-mode.
3. Here's a traditional -a 0 attack. This will work fine, but take a look at the time it takes.
In 2+ hours all the 10000 hashes will be cracked. If you know hashcat you know it will finish sooner because as soon as one unique salt has been fully cracked, it does not need to retry that salt, etc. But it will take some time, but you can't beat the -a 9 as you will see next.
4. New attack mode, the syntax is the same just add the -a 9:
So it cracked all 10000 bcrypt in just 2 seconds. This is really not black magic and only worked because we had the right password.
In reality the idea is if you have a large salted hashlist, for instance bcrypt, and you have the usernames for it. Run the -a 9 first with rules. This will crack some of the hashes in a very short time. If you then start your regular -a 0 attack you have already removed a good portion of the unique salts, so it will be a faster.
--
atom
If you ever used JtR before, the "Association Attack" is somehow of what the "single mode" is in JtR. The attack-mode is strong if you have large -salted- hashlist and at the same time you have some "hint" or "information" for each of the hashes inside the hashlist. Typically the username. The username itself could be seen as a "hint", because some humans tend to use the username as a part of the password. Or the username contains parts of the password because the username is changed for the site the username is used. Then we can extract this information using rules.
The main idea of this attack is to not try all the different (unique) salts with all password candidates from a wordlist, but to only attack each of the hashes in the hashlist with the associated "hint". From a development perspect, we remove the loop in hashcat which iterates through the different salts. To make this attack more efficient, we typically use the "hint" in combination with rules (but that's not a requirement). Using a GPU for this task is not so easy because of the many cores that we have and that we have to give work to. That brings us to an important requirement. Your hashlist needs a large number of unique salts to make this attack efficient (to utilize the GPU fully). Ideally the number of GPU Processors * 64 (or more). You can find out about the GPU Processors of your GPU using hashcat -I. My GTX980 has 16, so I need a hashlist of at least 1024 entries to fully utilize the GPU.
Unrelated Pro-Tip: If you want to attack a slow single hash with a single word but with some rules added to it, then the capitalized -S is what you want.
When I first created this patch I was thinking of how the user could specify what is the "hint" for each of the hashes. In JtR's single mode it simply uses the username from the hashlist. This is very easy to handle, but it's not exactly what I was looking for. In hashcat we specify a hashlist as regular (with or without username) but we also provide a wordlist as regular. However, this wordlist has to have exactly the number of lines as the hashlist. This has both advantages and disadvantages, but I liked the idea to use this even with a folder with many wordlists. This is kind of the opposite of what creates the efficiency of this attack, but I think there are some situations where multiple wordlists make sense. For instance, if you have large portions of substrings which were added to a passwords afterwards, by yubikeys on keypress, by site specific pepper strings or by user using the company name. I can also try to make it 1:1 as in JtR where the username is building some sort of virtual wordlist in memory, but only if I see that you people are really interested in this attack-mode.
One of the problems I was thinking of is if it is possible to have a mixed version of this attack-mode and a regular rule-based straight attack-mode in combination with -S. That could be useful if you have let's say only 10 hashes, because this is not enough to keep the GPU busy and then combine it with rules. This is a more complicated code change and again if I see you people being interested in it.
So here's how you use it. In a first step we will build a demonstration dataset (hashlist) in username:hashlist format as you probably have it and then I show you how to split it so you can use it with the new attack-modes.
1. Build the test dataset, creating a bcrypt hashlist
Code:
$ head -10000 example.dict > wordlist.txt
$ shuf wordlist.txt | sponge wordlist.txt
$ tools/test.pl passthrough 3200 < wordlist.txt > hashlist.txt
$ perl -e 'open (IN, "wordlist.txt"); my @a = <IN>; close (IN); open (IN, "hashlist.txt"); my @b = <IN>; close (IN); for (my $i = 0; $i < scalar @a; $i++) { chomp $a[$i]; chomp ($b[$i]); printf ("%s:%s\n", $a[$i], $b[$i]); } print scalar @b' > final.txt
$ rm wordlist.txt hashlist.txt
The resulting "final.txt" looks like this:
Code:
$ more final.txt
001071:$2a$05$KReyKhSyKRi0LBSwLBWyLOj88ZjDCPMD83re/SBNJ9TXJrrPLDbwW
02011511:$2a$05$LBCyKhC1MRGvLxeuLxOxMOilYzVzEnWVFr79uLTj6vTPAPO2y2tbS
01papirus:$2a$05$MB.3MBazLhW0MRKzMBSzKOsHZE77Ou9mGW88yOG2Q5TxF5yvLe48C
010108dh:$2a$05$LBGyLBeuKxavLh.3MRWyLOhOiQVGYyUBYE.rOUiRomCQFGIZfutEK
000123258:$2a$05$LxiwMR.wKhGvKBiyKxeuM.rHYpUIrIOLksCsvo//8YT5J5z28rzBW
...
2. This is the point where you typically start. You have a hashlist in username:hash format. We need to split them in order to use them with the new attack-mode.
Code:
$ cut -d: -f1 < final.txt > wordlist.txt
$ cut -d: -f2 < final.txt > hashlist.txt
3. Here's a traditional -a 0 attack. This will work fine, but take a look at the time it takes.
Code:
$ ./hashcat -m 3200 hashlist.txt wordlist.txt -o result.txt
Code:
...
Time.Started.....: Tue Sep 29 15:38:06 2020 (2 secs)
Time.Estimated...: Tue Sep 29 18:25:37 2020 (2 hours, 47 mins)
...
Recovered........: 6/10000 (0.06%) Digests, 6/10000 (0.06%) Salts
...
In 2+ hours all the 10000 hashes will be cracked. If you know hashcat you know it will finish sooner because as soon as one unique salt has been fully cracked, it does not need to retry that salt, etc. But it will take some time, but you can't beat the -a 9 as you will see next.
4. New attack mode, the syntax is the same just add the -a 9:
Code:
$ ./hashcat -m 3200 hashlist.txt wordlist.txt -o result.txt -a 9
Code:
...
Time.Started.....: Tue Sep 29 15:40:46 2020 (2 secs)
Time.Estimated...: Tue Sep 29 15:40:48 2020 (0 secs)
...
Recovered........: 10000/10000 (100.00%) Digests, 10000/10000 (100.00%) Salts
...
So it cracked all 10000 bcrypt in just 2 seconds. This is really not black magic and only worked because we had the right password.
In reality the idea is if you have a large salted hashlist, for instance bcrypt, and you have the usernames for it. Run the -a 9 first with rules. This will crack some of the hashes in a very short time. If you then start your regular -a 0 attack you have already removed a good portion of the unique salts, so it will be a faster.
--
atom