Commit 8b28da80 authored by Mohammad Imran Syed's avatar Mohammad Imran Syed
Browse files

Adding WiFi Traffic Generator script

parent ba6efd31
#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Script for generating Wi-Fi traffic using scapy (mainly using a Rapsberry Pi node)
"""
import os
#os.sys.path.append('/home/pi/.local/bin/scapy')
from scapy.all import *
import time
import subprocess
from struct import pack, unpack
interface_name = 'wlan1'
capture_duration = 60*5 # seconds
channel = '1' # channel number
directory = '/home/pi/SentTraces'
if not os.path.exists(directory):
os.makedirs(directory)
os.chmod(directory, 0o777)
class Fake_AP():
def capture(self):
"""
The purpose of this function is to capture the traffic being generated
on the sender node to create relation between the amount of traffic sent
and the amount of traffic actually received.
"""
tSharkCall = ['sudo', 'timeout', str(capture_duration+30),
'tshark', '-i', interface_name, '-Y', 'wlan.sa==11:99:22:88:33:77',
'-T', 'fields', '-e', 'frame.time_epoch', '-e', 'wlan.fc.type',
'-e', 'wlan.fc.type_subtype', '-e', 'wlan.fc.retry', '-e', 'wlan.seq',
'-e', 'wlan.fcs', '-e', 'wlan.sa', '-e', 'wlan_radio.signal_dbm']
print('Starting capturing')
self.capture = subprocess.Popen(tSharkCall, stdout=self.log, close_fds=True)
def set_AP(self, interval):
# Interface to use to send the frames, must be in monitor mode
iface = interface_name
# A random MAC address
sender_mac = "11:99:22:88:33:77"
# SSID (name of access point)
ssid = "HACKER"
# Channel number
channel = chr(1)
# 802.11 frame
"""
Dot11FCS adds an FCS value to each frame but only if it is supported by the Wi-Fi adapter
being used.
Alfa AWUS051NH adapter drops the FCS so it is not appended to packets.
Whereas, TPLink WN722N adds the FCS to the packets.
Having the FCS value improves the quality of the synchronization process.
"""
dot11 = Dot11FCS(type=0, subtype=8, addr1="ff:ff:ff:ff:ff:ff", addr2=sender_mac, addr3=sender_mac)
#dot11 = Dot11(type=0, subtype=8, addr1="ff:ff:ff:ff:ff:ff", addr2=sender_mac, addr3=sender_mac)
# Beacon layer
beacon = Dot11Beacon()
# Putting ssid in the frame
essid = Dot11Elt(ID="SSID", info=ssid, len=len(ssid))
# Putting channel number in the frame
channel = Dot11Elt(ID="DSset", info=channel)
# Stack all the layers and add a RadioTap
frame = RadioTap()/dot11/beacon/essid/channel
start_time = time.time()
while time.time()-start_time <= capture_duration:
frame.SC = self.__fixSC__()
sendp(frame, iface=iface, verbose=False)
time.sleep(interval)
def __fixSC__(self, fragment=0):
"""
This is a reserved method to return the sequence number in a way
that is not skewed by a bug in how the SC field is packed in
Scapy.
"""
if self.sequence >= 0xFFF:
self.sequence = 1
else:
self.sequence += 1
SC = (self.sequence - ((self.sequence >> 4) << 4) << 12) + (fragment << 8) + (self.sequence >> 4)
return unpack('<H', pack('>H', SC))[0]
def main():
p = subprocess.Popen(['sudo', '/sbin/ifconfig', 'wlan1', 'down'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
p.wait()
p.terminate()
stdout, stderr = p.communicate()
if stderr:
print('Bringing wlan1 interface down error: ', stderr)
p = subprocess.Popen(['sudo', '/sbin/iw', 'dev', 'wlan1', 'set', 'type', 'monitor'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
p.wait()
p.terminate()
stdout, stderr = p.communicate()
if stderr:
print('Adding monitor mode error: ', stderr)
time.sleep(2)
p = subprocess.Popen(['sudo', '/sbin/ifconfig', 'wlan0', 'down'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
p.wait()
p.terminate()
p = subprocess.Popen(['sudo', '/sbin/ifconfig', 'wlan1', 'up'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
stdout, stderr = p.communicate()
if stderr:
print('Bringing monitor interface up error: ', stderr)
time.sleep(10)
"""
We use Alfa AWUS051NH Wi-Fi adapter and for some reason the command for changing channel
does not work directly for 2.4 GHz band channels. Therefore, we had to one extra command where
we switch the device to 5 GHz band channel and switch it back to the desired 2.4 GHz band channel
"""
p = subprocess.Popen(['sudo', '/sbin/iw', 'dev', 'wlan1', 'set', 'channel', '52'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
p.wait()
p.terminate()
stdout, stderr = p.communicate()
p = subprocess.Popen(['sudo', '/sbin/iw', 'dev', 'wlan1', 'set', 'channel', channel], stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
p.wait()
p.terminate()
stdout, stderr = p.communicate()
if stderr:
print('Setting channel error: ', stderr)
time.sleep(10)
AP=Fake_AP()
interval = 0.01
#AP.sequence = randint(1200, 2000)
AP.__shutdown__ = False
# 1 test of capture_duration seconds
curr_time = datetime.now().strftime('%Y-%m-%d_%H-%M-%S')
log_name = '/home/pi/SentTraces/log_' + curr_time + '.txt'
AP.log = open(log_name, "wb")
AP.capture()
time.sleep(3)
AP.sequence = 0
AP.set_AP(interval)
time.sleep(60)
AP.capture.terminate()
AP.log.close()
"""
Power off the Raspberry Pi after it is fininshed sending the data.
If we keep disconnecting the power of RPi (after every test) without
shutting it down, then we run into chances of ending up with a corrupted SD card.
Therefore, it import to shut it down.
"""
subprocess.Popen(['sudo', 'poweroff'])
if __name__ == '__main__':
main()
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment