Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Caffe-Latte attack does not seem to work. #2

Closed
Esser50K opened this issue Aug 10, 2017 · 1 comment
Closed

Caffe-Latte attack does not seem to work. #2

Esser50K opened this issue Aug 10, 2017 · 1 comment

Comments

@Esser50K
Copy link
Owner

Esser50K commented Aug 10, 2017

So I tried to implement the caffe-latte attack in python with the help of scapy.

Fot those who are not familiar with the attack: it is a client side Wi-Fi attack and it is meant to recover WEP keys from clients.

I know WEP is not really used that much anymore but it would be nice to have a clear and readable python implementation of the attack.
In summary the attack goes like this:

  1. An attacker sets up a WEP access point with the same SSID as the network he wants to crack.
  2. Lets all client associate regardless of the wep key (since we dont know the real one)
  3. Once the client is associated it will try to assign itself an IP (after dhcp times out)
    4.The client sends out a gratuitous ARP packet, we catch it.
  4. We flip some of the encrypted bits corresponding to the last byte of the sender MAC and sender IP
  5. Apply crc32 to the bitmask used to flip the last bits
  6. Append that crc32 to the bitmask and XOR it with the contents of the actual packet. A new valid WEP encrypted ARP request packet should have been created.

For more details visit these links:
https://vimeo.com/23207363
https://vimeo.com/23214950

Now I'm finally going to guide you through how I tried implementing this and compare it to how aircrack-ng has this implemented in C.
The identification of the encrypted ARP packet is done correctly, since I know the key I can decrypt the packet and actually check.

First I get the encrypted wepdata and the ICV (which technically is also encrypted) like this:

wepdata = list(packet[Dot11WEP].wepdata)
original_icv = packet[Dot11WEP].icv

Then I create the bitmask and flip the bits at the index of the last byte of the sender MAC and IP.
The position is correct because I can decrypt the packet and check.
The way the crc32 is done could be wrong..

bitmask = list('\x00' * len(wepdata))
Flip bits of the bitmask corresponding to the last byte of sender MAC and IP respectively
bitmask[len(wepdata) - 11] = chr(randint(0, 255))
bitmask[len(wepdata) - 15] = chr(randint(0, 255))
Create crc32 checksum for the bitmask, the logical AND with only Fs turns it into a unsigned crc32
icv_patch = crc32("".join(bitmask)) & 0xffffffff

Then I XOR the results with the original content and put those value in the packet and send it.

flipped_result = [ chr( ord(wepdata[i]) ^ ord(bitmask[i]) ) for i in range(len(wepdata)) ]
patched_icv = icv_patch ^ original_icv
Put the results back in the packet
flipped_packet[Dot11WEP].wepdata = "".join(flipped_result)
flipped_packet[Dot11WEP].icv = patched_icv

What is wrong about this?

I attached 3 .pcap files. The captures encrypted_real_vs_replayed_arp and decrypted_real_vs_replayed_arp contain 2 packets each, one original and another modified packet (in encrypted form and decrypted form). These were from a wireshark capture and performing the caffe-latte attack with airbase-ng (it works and this is how packets should look).
The other capture called valid_vs_invalid shows two packets, one is the original ARP and the other is the modified ARP by the caffe-latte.py plugin. These packets were captured with scapy.
The WEP key is 12345 for simplicity if you want to analyze encrypted packets or so.

It seems that Wireshark can decrypt the modified packets from airbase-ng correctly but "refuses" to decrypt the modified packets from the caffe-latte plugin. Scapy however can decrypt those packets correctly. Clearly something is wrong about the way the packet is sent.
Here is the part of the wireshark code that decides if it is going to decrypt the packet or not:

/*
* Well, this packet should, in theory, have an ICV.
* Do we have the entire packet, and does it have enough data for
* the ICV?
/
if (reported_len < 4) {
/

* The packet is claimed not to even have enough data for a
* 4-byte ICV.
* Pretend it doesn't have an ICV.
/
;
} else if (len < reported_len) {
/

* The packet is claimed to have enough data for a 4-byte ICV,
* but we didn't capture all of the packet.
* Slice off the 4-byte ICV from the reported length, and trim
* the captured length so it's no more than the reported length;
* that will slice off what of the ICV, if any, is in the
* captured length.
/
reported_len -= 4;
if (len > reported_len)
len = reported_len;
} else {
/

* We have the entire packet, and it includes a 4-byte ICV.
* Slice it off, and put it into the tree.
*
* We only support decrypting if we have the the ICV.
*
* XXX - the ICV is encrypted; we're putting the encrypted
* value, not the decrypted value, into the tree.
*/
len -= 4;
reported_len -= 4;
can_decrypt = TRUE;
}

It looks like something is wrong with the size of the packet. But wireshark and scapy both tell me the total size is 86bytes which is the same as the packets from airbase-ng...

So here I reached the dead end.
What is wrong with my implementation of the caffe-latte attack?
captures.zip

@Esser50K
Copy link
Owner Author

I was wrong.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant