-
Notifications
You must be signed in to change notification settings - Fork 2
/
dwcc-sensor.py
executable file
·193 lines (179 loc) · 7.26 KB
/
dwcc-sensor.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
#!/usr/bin/env python
#Need to cleanup the ones we are not using
import sys
import os
import logging
import traceback
import random
import time
import datetime
import multiprocessing
import Queue
import socket
import subprocess
import os.path
import pysftp
from subprocess import Popen
import RPi.GPIO as GPIO
#1 is enabled, 0 is disabled
interface3enable = '1'
interface3 = 'wlan0mon'
monitor_enable3 = 'ifconfig wlan0 down; iw dev wlan0 interface add wlan0mon type monitor; ifconfig wlan0mon down; iw dev wlan0mon set type monitor; ifconfig wlan0mon up'
monitor_disable3 = 'iw dev wlan0mon del; ifconfig wlan0 up'
change_channel3 = 'iw dev wlan0mon set channel %s'
channels3 = [36, 40, 44, 48, 52, 56, 60, 64, 100, 104, 108, 112, 116] #use the linux command "iwlist channel" to get a list of every channel your devices supports)
#At this more than interface has not been tested
#1 is enabled, 0 is disabled
interface1enable = '1'
interface1 = 'wlan1mon'
monitor_enable1 = 'ifconfig wlan1 down; iw dev wlan1 interface add wlan1mon type monitor; ifconfig wlan1mon down; iw dev wlan1mon set type monitor; ifconfig wlan1mon up'
monitor_disable1 = 'iw dev wlan1mon del; ifconfig wlan1 up'
change_channel1 = 'iw dev wlan1mon set channel %s'
channels1 = [120, 124, 128, 132, 136, 140, 149, 153, 157, 161, 165] #use the linux command "iwlist channel" to get a list of every channel your devices supports)
#At this more than interface has not been tested
#1 is enabled, 0 is disabled
interface2enable = '1'
interface2 = 'wlan2mon'
monitor_enable2 = 'ifconfig wlan2 down; iw dev wlan2 interface add wlan2mon type monitor; ifconfig wlan2mon down; iw dev wlan2mon set type monitor; ifconfig wlan2mon up'
monitor_disable2 = 'iw dev wlan2mon del; ifconfig wlan2 up'
change_channel2 = 'iw dev wlan2mon set channel %s'
channels2 = [1, 6, 11] #use the linux command "iwlist channel" to get a list of every channel your devices supports)
#1 is enabled, 0 is disabled
#interface3enable = '1'
#interface3 = 'wlan3mon'
#monitor_enable3 = 'ifconfig wlan3 down; iw dev wlan3 interface add wlan3mon type monitor; ifconfig wlan3mon down; iw dev wlan3mon set type monitor; ifconfig wlan3mon up'
#monitor_disable3 = 'iw dev wlan3mon del; ifconfig wlan3 up'
#change_channel3 = 'iw dev wlan3mon set channel %s'
#channels1 = [6, 48, 1, 11, 36, 40, 44, 10 ] #use the linux command "iwlist channel" to get a list of every channel your devices supports)
#info for sftp server
sshhost = '192.168.15.3' #can be hostname or ip
sshuser = 'zach' #make sure that key auth is working
iamapi = '1' # set this to one if this hardware is a raspberrypi and you want to enable the status LEDs
hostname = socket.gethostname()
queue = multiprocessing.Queue()
incomingpath = '/data/incoming/' #This is the path where new pcaps will be placed
#This is the main function
def start():
try:
os.remove("/root/Distributed-Wifi-Capability-Collector/dwcc.log")
except OSError:
pass
subprocess.call('iw reg set US', shell=True)
logging.basicConfig(filename='/root/Distributed-Wifi-Capability-Collector/dwcc.log', format='%(levelname)s:%(message)s', level=logging.INFO)
if iamapi == '1':
gpinsetup()
stop_networkchecker = networkchecker()
if interface1enable == '1':
os.system(monitor_enable1)
logging.info("starting wlan1")
if interface2enable == '1':
os.system(monitor_enable2)
logging.info("starting wlan2")
if interface3enable == '1':
os.system(monitor_enable3)
logging.info("starting wlan3")
stop_rotating = rotator()
stop_uploading = uploader()
try:sniffer()
except KeyboardInterrupt: sys.exit()
finally:
print "Please wait for everything to stop"
if iamapi == '1':
stop_networkchecker.set()
GPIO.output(6,GPIO.LOW)
GPIO.output(13,GPIO.LOW)
stop_rotating.set()
stop_uploading.set()
if interface1enable == '1':
os.system(monitor_disable1)
if interface2enable == '1':
os.system(monitor_disable2)
if interface3enable == '1':
os.system(monitor_disable3)
def gpinsetup():
#settings up things for the led
GPIO.setmode(GPIO.BCM)
GPIO.setwarnings(False)
GPIO.setup(13,GPIO.OUT)
GPIO.setup(6,GPIO.OUT)
def networkchecker():
def networkcheck(stop):
while not stop.is_set():
try:
response = os.system("ping -c 2 google.com")
if response == 0:
logging.info('network is up!')
logging.info ("port 13 LED on")
GPIO.output(13,GPIO.HIGH)
else:
logging.info('network is down!')
logging.info ("port 13 LED off")
GPIO.output(13,GPIO.LOW)
logging.info ("retesting in 5 min")
time.sleep(300) # seconds
except KeyboardInterrupt: pass
stop = multiprocessing.Event()
multiprocessing.Process(target=networkcheck, args=[stop]).start()
return stop
#This will change the channels every 1 sec to scan all in the range.
def rotator():
def rotate(stop):
while not stop.is_set():
try:
if interface1enable == '1': #This loop is for interface 1
channel1 = str(random.choice(channels1))
logging.info('Changing to channel for interface1 ' + channel1)
os.system(change_channel1 % channel1)
if interface2enable == '1': #This loop is for interface 2
channel2 = str(random.choice(channels2))
logging.info('Changing to channel for interface2 ' + channel2)
os.system(change_channel2 % channel2)
if interface3enable == '1': #This loop is for interface 3
channel3 = str(random.choice(channels3))
logging.info('Changing to channel for interface3 ' + channel3)
os.system(change_channel3 % channel3)
time.sleep(5) # seconds
except KeyboardInterrupt: pass
stop = multiprocessing.Event()
multiprocessing.Process(target=rotate, args=[stop]).start()
return stop
#this is the caputre fuction, It will only caputre the mgt frames.
def sniffer():
logging.info("sniffer started")
if iamapi == '1':
logging.info("port 6 led on")
GPIO.output(6,GPIO.HIGH)
commands = [
'tcpdump -i '+ interface1 +' -G 600 --packet-buffered -W 300 -e -s 1024 type mgt or type ctl -w '+incomingpath +''+ hostname +'-'+ interface1 +'-%Y-%m-%d_%H.%M.%S.pcap;',
'tcpdump -i '+ interface2 +' -G 600 --packet-buffered -W 300 -e -s 1024 type mgt or type ctl -w '+incomingpath +''+ hostname +'-'+ interface2 +'-%Y-%m-%d_%H.%M.%S.pcap;',
'tcpdump -i '+ interface3 +' -G 600 --packet-buffered -W 300 -e -s 1024 type mgt or type ctl -w '+incomingpath +''+ hostname +'-'+ interface3 +'-%Y-%m-%d_%H.%M.%S.pcap;',
]
#
# run in parallel
processes = [Popen(cmd, shell=True) for cmd in commands]
# wait for completion
for p in processes: p.wait()
#the above will rotate the pcap every 10 mins and keeps 24 hours worth
def uploader():
def upload(stop):
while not stop.is_set():
try:
for fname in os.listdir(incomingpath):
if fname.endswith('.pcap'):
try:
with pysftp.Connection(host=sshhost, username=sshuser, private_key='~/.ssh/id_rsa') as sftp:
with sftp.cd(incomingpath):
sftp.put(incomingpath +fname)
logging.info("uploaded pcap")
except pysftp.SSHException:
logging.info("Unable to establish SSH connection will retry in 5 min")
time.sleep(300) #seconds
os.remove(incomingpath +fname)
else:
logging.info("no pcap found, will try again in 5 min")
time.sleep(300) #seconds
except KeyboardInterrupt: pass
stop = multiprocessing.Event()
multiprocessing.Process(target=upload, args=[stop]).start()
return stop
start()