Skip to content

Instantly share code, notes, and snippets.

@ouoam
Last active October 27, 2025 01:56
Show Gist options
  • Select an option

  • Save ouoam/3462e73fcfc36d063ecd8f9a5ac77f12 to your computer and use it in GitHub Desktop.

Select an option

Save ouoam/3462e73fcfc36d063ecd8f9a5ac77f12 to your computer and use it in GitHub Desktop.
/*
===========================================
Copyright (c) 2017 Stefan Kremser
github.com/spacehuhn
===========================================
*/
/* include all necessary libraries */
#include "freertos/FreeRTOS.h"
#include "esp_wifi.h"
#include "esp_wifi_internal.h"
#include "lwip/err.h"
#include "esp_system.h"
#include "esp_event.h"
#include "esp_event_loop.h"
#include "nvs_flash.h"
#include "driver/gpio.h"
//===== SETTINGS =====//
#define CHANNEL 8
#define BAUD_RATE 460800
#define CHANNEL_HOPPING false //if true it will scan on all channels
#define MAX_CHANNEL 13 //(only necessary if channelHopping is true)
#define HOP_INTERVAL 214 //in ms (only necessary if channelHopping is true)
//===== Run-Time variables =====//
int ch = CHANNEL;
unsigned long lastChannelChange = 0;
//===== FUNCTIONS =====//
/* write packet to Serial */
void newPacketSerial(uint32_t len, uint8_t* buf){
uint8_t _buf[4];
_buf[0] = len;
_buf[1] = len >> 8;
_buf[2] = len >> 16;
_buf[3] = len >> 24;
Serial.write(_buf, 4);
Serial.write(_buf, 4);
Serial.write(buf, len);
}
/* will be executed on every packet the ESP32 gets while beeing in promiscuous mode */
void sniffer(void *buf, wifi_promiscuous_pkt_type_t type){
// if (type == WIFI_PKT_MISC) return; // wrong packet type
// if (type == WIFI_PKT_CTRL) return; // control frame
wifi_promiscuous_pkt_t* pkt = (wifi_promiscuous_pkt_t*)buf;
wifi_pkt_rx_ctrl_t ctrl = (wifi_pkt_rx_ctrl_t)pkt->rx_ctrl;
if (ctrl.sig_len > 293) return; // packet too long if (ctrl.sig_len > SNAP_LEN) return; // 2324 // 293
uint32_t packetLength = ctrl.sig_len;
if (type == WIFI_PKT_MGMT) packetLength -= 4;
// fix for known bug in the IDF
// https://github.com/espressif/esp-idf/issues/886
if (type == WIFI_PKT_MGMT && pkt->payload[0] == 0x80) return; // beacon
if (type == WIFI_PKT_MGMT && (pkt->payload[0] == 0xA0 || pkt->payload[0] == 0xC0 )) {
// deauths++;
}
if (( (pkt->payload[30] == 0x88 && pkt->payload[31] == 0x8e)|| ( pkt->payload[32] == 0x88 && pkt->payload[33] == 0x8e) )){
// eapol++; // new eapol packets :)
}
newPacketSerial(packetLength, pkt->payload);
}
esp_err_t event_handler(void *ctx, system_event_t *event){ return ESP_OK; }
//===== SETUP =====//
void setup() {
/* start Serial */
Serial.begin(BAUD_RATE);
Serial.println();
/* setup wifi */
nvs_flash_init();
tcpip_adapter_init();
ESP_ERROR_CHECK( esp_event_loop_init(event_handler, NULL) );
wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT();
ESP_ERROR_CHECK( esp_wifi_init(&cfg) );
ESP_ERROR_CHECK( esp_wifi_set_storage(WIFI_STORAGE_RAM) );
ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_NULL) );
ESP_ERROR_CHECK( esp_wifi_start() );
Serial.println("<<START>>");
ESP_ERROR_CHECK(esp_wifi_set_promiscuous(true));
ESP_ERROR_CHECK(esp_wifi_set_channel(ch, WIFI_SECOND_CHAN_NONE));
ESP_ERROR_CHECK(esp_wifi_set_promiscuous_rx_cb(sniffer));
}
//===== LOOP =====//
void loop() {
/* Channel Hopping */
if(CHANNEL_HOPPING){
unsigned long currentTime = millis();
if(currentTime - lastChannelChange >= HOP_INTERVAL){
lastChannelChange = currentTime;
ch++; //increase channel
if(ch > MAX_CHANNEL) ch = 1;
esp_wifi_set_channel(ch, WIFI_SECOND_CHAN_NONE);
}
}
}
# Made by @xdavidhu (github.com/xdavidhu, https://xdavidhu.me/)
# Merge with https://github.com/Pinoccio/tool-serial-pcap/blob/master/serial-pcap
# And https://wiki.wireshark.org/CaptureSetup/Pipes
import serial
import io
import os
import subprocess
import signal
import time
import win32pipe, win32file
import struct
import datetime
try:
serialportInput = input("[?] Select a serial port (default '/dev/ttyUSB0'): ")
if serialportInput == "":
serialport = "/dev/ttyUSB0"
else:
serialport = serialportInput
except KeyboardInterrupt:
print("\n[+] Exiting...")
exit()
try:
canBreak = False
while not canBreak:
boardRateInput = input("[?] Select a baudrate (default '921600'): ")
if boardRateInput == "":
boardRate = 921600
canBreak = True
else:
try:
boardRate = int(boardRateInput)
except KeyboardInterrupt:
print("\n[+] Exiting...")
exit()
except Exception as e:
print("[!] Please enter a number!")
continue
canBreak = True
except KeyboardInterrupt:
print("\n[+] Exiting...")
exit()
try:
filenameInput = input("[?] Select a filename (default 'capture.pcap'): ")
if filenameInput == "":
filename = "capture.pcap"
else:
filename = filenameInput
except KeyboardInterrupt:
print("\n[+] Exiting...")
exit()
canBreak = False
while not canBreak:
try:
ser = serial.Serial(serialport, boardRate)
canBreak = True
except KeyboardInterrupt:
print("\n[+] Exiting...")
exit()
except:
print("[!] Serial connection failed... Retrying...")
time.sleep(2)
continue
print("[+] Serial connected. Name: " + ser.name)
counter = 0
check = 0
while check == 0:
line = ser.readline()
if b"<<START>>" in line:
check = 1
print("[+] Stream started...")
#else: print '"'+line+'"'
print("[+] Starting up wireshark...")
#open Wireshark, configure pipe interface and start capture (not mandatory, you can also do this manually)
wireshark_cmd=['C:\Program Files\Wireshark\Wireshark.exe', r'-i\\.\pipe\wireshark','-k']
proc=subprocess.Popen(wireshark_cmd)
#create the named pipe \\.\pipe\wireshark
pipe = win32pipe.CreateNamedPipe(
r'\\.\pipe\wireshark',
win32pipe.PIPE_ACCESS_OUTBOUND,
win32pipe.PIPE_TYPE_MESSAGE | win32pipe.PIPE_WAIT,
1, 65536, 65536,
300,
None)
#connect to pipe
win32pipe.ConnectNamedPipe(pipe, None)
#wait 2 second (not mandatory, but this let watching data coming trough the pipe)
time.sleep(2)
win32file.WriteFile(pipe, struct.pack("=IHHiIII",
0xa1b2c3d4, # magic number
2, # major version number
4, # minor version number
0, # GMT to local correction
0, # accuracy of timestamps
2500, # max length of captured packets, in octets
105, # data link type (DLT) - IEEE 802.11
))
try:
while True:
ch = ser.read(8)
lens, lenr = struct.unpack('<LL', ch)
now = datetime.datetime.now()
timestamp = int(time.mktime(now.timetuple()))
win32file.WriteFile(pipe, struct.pack("=IIII",
timestamp, # timestamp seconds
now.microsecond, # timestamp microseconds
lens, # number of octets of packet saved in file
lenr, # actual length of packet
))
ch = ser.read(lens)
#send pcap data trough the pipe
win32file.WriteFile(pipe, ch)
except KeyboardInterrupt:
print("[+] Stopping...")
# os.killpg(os.getpgid(p.pid), signal.SIGTERM)
f.close()
ser.close()
print("[+] Done.")
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment