2013-02-24 17:59:30 -07:00
#!/usr/bin/python
#Suppress scapy warnings, but not errors
import logging
logging . getLogger ( " scapy.runtime " ) . setLevel ( logging . ERROR )
#turn off the output for scapy functions with conf.verb
from scapy . all import *
conf . verb = 0
import sys
import time
import os
import smtplib
import re
import subprocess
import commands
bash = commands . getoutput
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
import argparse
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#user_pass contains the email to send from, the password to that email, and the recipient address
try :
from user_pass import user , passwd , rcpt
except ImportError :
print " [?] Error importing user_pass. Are you sure its in this directory? Email won ' t send. "
IPandMAC = { }
prefixIP = " "
essid = " "
interface = " "
routerip = " "
devices = 0
localIP = " "
localMAC = " "
MAC = " "
IPaddr = " "
user = user
passwd = passwd
rcpt = rcpt
#Save a few colors for the print function
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
class colors :
PURPLE = ' \033 [95m '
OKBLUE = ' \033 [94m '
OKGREEN = ' \033 [92m '
WARNING = ' \033 [93m '
FAIL = ' \033 [91m '
ENDC = ' \033 [0m '
def disable ( self ) :
self . PURPLE = ' '
self . OKBLUE = ' '
self . OKGREEN = ' '
self . WARNING = ' '
self . FAIL = ' '
self . ENDC = ' '
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
try :
localIP = [ x [ 4 ] for x in scapy . all . conf . route . routes if x [ 2 ] != ' 0.0.0.0 ' ] [ 0 ]
except Exception :
sys . exit ( colors . WARNING + " [*] " + colors . ENDC + " No local IP found, check network connectivity " )
IPandMAC = { }
MAC = " "
IPaddr = " "
MAClist = [ ]
pktTime = [ ]
detectTimer = 0
prefixIP = re . search ( ' \ d { 2,3} \ . \ d { 1,3} \ . \ d { 1,3} \ . ' , localIP ) . group ( )
parser = argparse . ArgumentParser ( )
parser . add_argument ( " -p " , " --promiscping " , help = " Start with a promiscuous ping scan " , action = " store_true " )
args = parser . parse_args ( )
#Example usage of colors
#print bcolors.OKBLUE + "Check this out" + colors.ENDC
try :
from user_pass import user , passwd , rcpt
except ImportError :
print colors . WARNING + " [?] " + colors . ENDC + " Error importing user_pass. Are you sure its in this directory? Email won ' t send. "
if args . promiscping == True :
print colors . FAIL + " \n [!] " + colors . ENDC + " Possible promisucous mode enabled on the following clients: "
ans , unans = promiscping ( prefixIP + " * " )
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#Example usage of colors
#print bcolors.OKBLUE + "Check this out" + colors.ENDC
localIP = [ x [ 4 ] for x in scapy . all . conf . route . routes if x [ 2 ] != ' 0.0.0.0 ' ] [ 0 ]
prefixIP = re . search ( ' \ d { 2,3} \ . \ d { 1,3} \ . \ d { 1,3} \ . ' , localIP ) . group ( )
print colors . FAIL + " \n ----------------------------------------------------------------------------- "
print " [!] " + colors . ENDC + " Possible promisucous mode enabled on the following clients: \n "
ans , unans = promiscping ( prefixIP + " * " )
print colors . FAIL + " ----------------------------------------------------------------------------- \n " + colors . ENDC
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
#Get the ESSID to match to iwlist scan "(.*?)" searches for all text between quotes
essidcmd = bash ( ' iwgetid ' )
essid = re . search ( ' " (.*?) " ' , essidcmd ) . group ( 1 )
#Define interface in use and router IP
routecmd = bash ( ' ip route ' )
routerinfo = re . search ( ' default via ( %s \ d { 1,3}) \ w+ ( \ w[a-zA-Z0-9] \ w[a-zA-Z0-9][0-9]?) ' % prefixIP , routecmd )
interface = routerinfo . group ( 2 )
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
routerIP = routerinfo . group ( 1 )
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
routerip = routerinfo . group ( 1 )
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
ipalines = bash ( ' ip addr ' ) . splitlines ( )
for l in ipalines :
macsearch = re . search ( interface + " : " , l )
if macsearch != None :
indexof = ipalines . index ( l )
localMAC = re . search ( ' ([a-fA-F0-9] {2} [:| \ -]?) {6} ' , ipalines [ indexof + 1 ] ) . group ( )
#Define router MAC
linelist = bash ( ' iwlist scan ' ) . splitlines ( )
startline = linelist . index ( ' ESSID: " %s " ' % essid )
routermac = re . search ( ' ([a-fA-F0-9] {2} [:| \ -]?) {6} ' , linelist [ startline - 5 ] ) . group ( )
#Populate the IPandMAC table with an arping
if len ( IPandMAC ) == 0 :
ans , unans = arping ( prefixIP + " * " )
devices = len ( ans )
for s , r in ans :
IPandMAC [ r . sprintf ( " % ARP.hwsrc % " ) ] = r . sprintf ( " % ARP.psrc % " )
IPandMAC [ localMAC ] = localIP
#Print the known information
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
print colors . OKBLUE + " \n [+] " + colors . ENDC + " Your device: " + colors . OKBLUE + interface + colors . ENDC + " at " + colors . OKBLUE + localIP + colors . ENDC + " with MAC " + colors . OKBLUE + localMAC + colors . ENDC
print colors . OKBLUE + " [+] " + colors . ENDC + " Router: " + colors . OKBLUE + essid + colors . ENDC + " at " + colors . OKBLUE + routerIP + colors . ENDC + " with MAC " + colors . OKBLUE + routermac
print " [+] " + colors . ENDC + " Number of devices on the local network: " , colors . OKBLUE , devices + 1 , colors . ENDC
ans . show ( )
print localMAC , localIP , " \n "
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
print colors . OKBLUE + " ----------------------------------------------------------------------------- " + colors . ENDC
print colors . OKBLUE + " [+] " + colors . ENDC + " Your device: " + colors . OKBLUE + interface + colors . ENDC + " at " + colors . OKBLUE + localIP + colors . ENDC + " with MAC " + colors . OKBLUE + localMAC + colors . ENDC
print colors . OKBLUE + " [+] " + colors . ENDC + " Router: " + colors . OKBLUE + essid + colors . ENDC + " at " + colors . OKBLUE + routerip + colors . ENDC + " with MAC " + colors . OKBLUE + routermac
print " [+] " + colors . ENDC + " Number of devices on the local network: " , colors . OKBLUE , devices + 1 , colors . ENDC + ' \n '
ans . show ( )
print localMAC , localIP
print colors . OKBLUE + " ----------------------------------------------------------------------------- \n " + colors . ENDC
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
#Send the email
def smtp ( msg ) :
try :
server = smtplib . SMTP ( ' smtp.gmail.com:587 ' )
except Exception :
print colors . PURPLE + " \n [?] " + colors . ENDC + " Contacting Gmail server failed, trying again... "
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
try :
server = smtplib . SMTP ( ' smtp.gmail.com:587 ' )
except Exception :
print colors . PURPLE + " [?] " + colors . ENDC + " Contacting Gmail server failed. Could not send notification. "
return
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
server = smtplib . SMTP ( ' smtp.gmail.com:587 ' )
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
server . starttls ( )
server . login ( user , passwd )
server . sendmail ( user , rcpt , msg )
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
print colors . WARNING + " [*] " + colors . ENDC + " Email sent to " + colors . WARNING + rcpt + colors . ENDC + " \n "
def newdevices ( pkt ) :
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#Print the new device and new device list then email me the device information
def newdevices ( pkt ) :
print colors . WARNING + ' ----------------------------------------------------------------------------- '
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
print colors . WARNING + " [*] " + colors . ENDC + " New device joined the network "
print colors . WARNING + " [*] " + colors . ENDC + " Device IP: " + colors . WARNING + IPaddr + colors . ENDC + " Device MAC: " + colors . WARNING + MAC
print " [*] " + colors . ENDC + " Updated list of current or previously connected devices: \n "
for k , v in IPandMAC . iteritems ( ) :
print k , v
if len ( IPandMAC ) > devices :
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
newdevicemsg = " From: From Me < %s > \n To: < %s > \n Subject: \n \n New device joined network! IP: %s MAC: %s " % ( user , rcpt , IPaddr , MAC )
smtp ( newdevicemsg )
#Launch the deauth packets and send the email
def deauth ( pkt ) :
print colors . FAIL + " [!] " + colors . ENDC + " ARP spoof detected! "
print colors . FAIL + " [!] " + colors . ENDC + " Attacker IP: " + colors . FAIL + IPandMAC [ MAC ] + colors . ENDC + " Attacker MAC: " + colors . FAIL + MAC + colors . ENDC
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#Trigger the email for joining network devices here
newdevicemsg = " From: From Me < %s > \n To: < %s > \n Subject: \n \n New device joined network! IP: %s MAC: %s " % ( user , rcpt , IPaddr , MAC )
smtp ( newdevicemsg )
print colors . WARNING + " \n [*] " + colors . ENDC + " Email sent to " + colors . WARNING + rcpt
print ' ----------------------------------------------------------------------------- \n ' + colors . ENDC
#Launch the deauth packets and send the email
def deauth ( pkt ) :
print colors . FAIL + ' ----------------------------------------------------------------------------- '
print " [!] " + colors . ENDC + " ARP spoof detected! "
print colors . FAIL + " [!] " + colors . ENDC + " Attacker IP: " + colors . FAIL + IPandMAC [ MAC ] + colors . ENDC + " Attacker MAC: " + colors . FAIL + MAC + colors . ENDC + " \n "
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
# Start monitor mode
moncmd = bash ( ' airmon-ng start %s ' % interface )
moniface = re . search ( ' (mon[0-9]) ' , moncmd ) . group ( )
print ' aireplay-ng -0 2 -a %s -c %s %s ' % ( routermac , MAC , moniface )
2013-02-24 18:19:41 -07:00
<< << << < HEAD
== == == =
2012-12-01 17:37:15 -07:00
################## PROBLEM HERE #### causes timeout so errors out timeout to send the email with smtp(arpdetmsg)
# Unfortunately when sending custom packet from scapy, it works, and when
# sending packet from other laptop it makes the variable server timeout!?
# Wireshark stops and says network interface failed whether sending from
# scapy or other laptop
# I wrapped it in try except and it works well, just take a long time on the
# first run
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
deauthcmd = bash ( ' aireplay-ng -0 1 -a %s -c %s %s ' % ( routermac , MAC , moniface ) )
print deauthcmd
monexit = bash ( ' airmon-ng stop %s ' % moniface )
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
#Healing packet function here
print colors . WARNING + " [*] " + colors . ENDC + " Sending healing packets "
send ( ARP ( op = 2 , psrc = localIP , pdst = routerIP , hwdst = " ff:ff:ff:ff:ff " , hwsrc = localMAC ) , count = 10 )
#Send email
arpdetmsg = " From: From Me < %s > \n To: < %s > \n Subject: \n MIME-Version: 1.0 \n Content-type: text/plain \n \n Arp spoof detected! Attacker IP: %s Attacker MAC: %s " % ( user , rcpt , IPandMAC [ MAC ] , MAC )
smtp ( arpdetmsg )
#Reset the IPandMAC table
IPandMAC [ localMAC ] = localIP
def arppingDet ( ) :
global pktTime
global detectTimer
global MAClist
pktTime . append ( time . mktime ( time . gmtime ( ) ) )
pktDif = [ pktTime [ i + 1 ] - pktTime [ i ] for i in range ( len ( pktTime ) - 1 ) ]
MACcounter = 0
timeCounter = 0
if len ( MAClist ) < 8 :
MAClist . append ( MAC )
for a in MAClist :
if a == MAC :
MACcounter + = 1
if MACcounter > 6 :
for b in pktDif :
if b == 0 :
timeCounter + = 1
if timeCounter > 5 :
curTimer = time . mktime ( time . gmtime ( ) )
lastDet = curTimer - detectTimer
if lastDet > 30 :
detectTimer = time . mktime ( time . gmtime ( ) )
print colors . FAIL + " [!] " + colors . ENDC + " ARP ping detected! "
print colors . FAIL + " [!] " + colors . ENDC + " Attacker IP: " + colors . FAIL + IPandMAC [ MAC ] + colors . ENDC + " Attacker MAC: " + colors . FAIL + MAC + colors . ENDC
arpPingmsg = " From: From Me < %s > \n To: < %s > \n Subject: \n \n ARP ping detected! IP: %s MAC: %s " % ( user , rcpt , IPaddr , MAC )
smtp ( arpPingmsg )
MACcounter = 0
timeCounter = 0
else :
MAClist = [ ]
pktDif = [ ]
pktTime = [ ]
def monitor ( pkt ) :
global IPaddr , MAC , detectTimer
#Fill in MAC and IPAddr variables. Sometimes it gets a packet where pkt.getlayer(ARP) is None, that's why MAC is wrapped in try
if pkt . getlayer ( ARP ) . psrc == None :
return
if pkt . getlayer ( ARP ) . psrc == ' 00:00:00:00:00:00 ' :
return
if pkt . getlayer ( ARP ) . psrc == localIP :
return
MAC = pkt . getlayer ( ARP ) . hwsrc
if re . search ( prefixIP , pkt . getlayer ( ARP ) . psrc ) == None :
return
IPaddr = pkt . getlayer ( ARP ) . psrc
arppingDet ( )
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#Send email
#print "after monexit heres what email msg contains", user, rcpt, IPandMAC[MAC], MAC
arpdetmsg = " From: From Me < %s > \n To: < %s > \n Subject: \n MIME-Version: 1.0 \n Content-type: text/plain \n \n Arp spoof detected! Attacker IP: %s Attacker MAC: %s " % ( user , rcpt , IPandMAC [ MAC ] , MAC )
smtp ( arpdetmsg )
print colors . FAIL + " \n [!] " + colors . ENDC + " Email sent to " + colors . FAIL + rcpt
print ' ----------------------------------------------------------------------------- \n ' + colors . ENDC
########################### MAIN LOOP #######################
def monitor ( pkt ) :
global IPandMAC
global IPaddr , MAC
try :
MAC = pkt . getlayer ( ARP ) . hwsrc
except Exception :
print " MAC = NONETYPE "
return
if MAC == None :
return
if MAC == ' 00:00:00:00:00:00 ' :
return
IPaddr = pkt . getlayer ( ARP ) . psrc
if re . search ( prefixIP , IPaddr ) == None :
return
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
#Check for arp spoof
if MAC in IPandMAC :
if IPaddr != IPandMAC [ MAC ] :
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
deauth ( pkt )
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
#Fire the packets
deauth ( pkt )
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447
2013-02-24 17:59:30 -07:00
else :
IPandMAC [ MAC ] = IPaddr
newdevices ( pkt )
2013-02-24 18:19:41 -07:00
<< << << < HEAD
2013-02-24 17:59:30 -07:00
while 1 :
try :
sniff ( store = 0 , filter = ' arp ' , prn = monitor , iface = interface )
except Exception :
print Exception
print colors . WARNING + " [!] " + colors . ENDC + " Network down, trying again in a minute. "
time . sleep ( 60 )
2013-02-24 18:19:41 -07:00
== == == =
2012-12-01 17:37:15 -07:00
sniff ( store = 0 , filter = ' arp ' , prn = monitor , iface = interface )
#NOTES
#check if the transistor's network has DHCP offers and requests when devices join
#Threading for the arp ping or to ping the router to test for connectivity
#<omgimdrunk> fly-tri: time.sleep(5000)
#<omgimdrunk> and threading is stupid simple, hang on i got a one liner
#<pdtpatrick> or use something similar to eventmachine ?
#<jorrit> Threading is not the good solution for this.
#<jorrit> It rarely is.
#<jorrit> Better use some event mechanism like twisted.
#<omgimdrunk> import threading
#<omgimdrunk> t = threadclass ()
#<omgimdrunk> t.start
#Read about Twisted for the regular interval arp ping, as well as inputing commands while script is running?
#Read about curses for user input while the script is running
#Look at pysnort
2013-02-24 18:19:41 -07:00
>> >> >> > 9444156 c44b0621f556b59aac415d6013adf9447