commit
fb759d3e56
4
LICENSE
4
LICENSE
@ -20,9 +20,9 @@ Parts of the source files in this repository are made available under different
|
|||||||
listed below. Refer to each individual source file for more details.
|
listed below. Refer to each individual source file for more details.
|
||||||
|
|
||||||
------------------------------------------------------------------------------------------------
|
------------------------------------------------------------------------------------------------
|
||||||
wifisniffer.cpp
|
wifiscan.cpp
|
||||||
|
|
||||||
Parts of wifisniffer.cpp were derived or taken from
|
Prior art was used for wifiscan.cpp and taken from
|
||||||
|
|
||||||
* Copyright (c) 2017, Łukasz Marcin Podkalicki <lpodkalicki@gmail.com>
|
* Copyright (c) 2017, Łukasz Marcin Podkalicki <lpodkalicki@gmail.com>
|
||||||
* ESP32/016 WiFi Sniffer
|
* ESP32/016 WiFi Sniffer
|
||||||
|
3
build.py
3
build.py
@ -90,5 +90,4 @@ def publish_bintray(source, target, env):
|
|||||||
# put build file name and upload command to platformio environment
|
# put build file name and upload command to platformio environment
|
||||||
env.Replace(
|
env.Replace(
|
||||||
PROGNAME="firmware_" + package + "_v%s" % version,
|
PROGNAME="firmware_" + package + "_v%s" % version,
|
||||||
UPLOADCMD=publish_bintray
|
UPLOADCMD=publish_bintray)
|
||||||
)
|
|
@ -26,7 +26,7 @@ description = Paxcounter is a proof-of-concept ESP32 device for metering passeng
|
|||||||
|
|
||||||
[common]
|
[common]
|
||||||
; for release_version use max. 10 chars total, use any decimal format like "a.b.c"
|
; for release_version use max. 10 chars total, use any decimal format like "a.b.c"
|
||||||
release_version = 1.5.3
|
release_version = 1.5.7
|
||||||
; DEBUG LEVEL: For production run set to 0, otherwise device will leak RAM while running!
|
; DEBUG LEVEL: For production run set to 0, otherwise device will leak RAM while running!
|
||||||
; 0=None, 1=Error, 2=Warn, 3=Info, 4=Debug, 5=Verbose
|
; 0=None, 1=Error, 2=Warn, 3=Info, 4=Debug, 5=Verbose
|
||||||
debug_level = 0
|
debug_level = 0
|
||||||
|
@ -6,10 +6,13 @@
|
|||||||
// Local logging tag
|
// Local logging tag
|
||||||
static const char TAG[] = "main";
|
static const char TAG[] = "main";
|
||||||
|
|
||||||
void IRAM_ATTR ButtonIRQ() { ButtonPressedIRQ++; }
|
void IRAM_ATTR ButtonIRQ() {
|
||||||
|
portENTER_CRITICAL(&timerMux);
|
||||||
|
ButtonPressedIRQ++;
|
||||||
|
portEXIT_CRITICAL(&timerMux);
|
||||||
|
}
|
||||||
|
|
||||||
void readButton() {
|
void readButton() {
|
||||||
if (ButtonPressedIRQ) {
|
|
||||||
portENTER_CRITICAL(&timerMux);
|
portENTER_CRITICAL(&timerMux);
|
||||||
ButtonPressedIRQ = 0;
|
ButtonPressedIRQ = 0;
|
||||||
portEXIT_CRITICAL(&timerMux);
|
portEXIT_CRITICAL(&timerMux);
|
||||||
@ -18,5 +21,4 @@ void readButton() {
|
|||||||
payload.addButton(0x01);
|
payload.addButton(0x01);
|
||||||
SendData(BUTTONPORT);
|
SendData(BUTTONPORT);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
#endif
|
#endif
|
@ -23,6 +23,19 @@ void doHousekeeping() {
|
|||||||
if (cfg.runmode == 1)
|
if (cfg.runmode == 1)
|
||||||
ESP.restart();
|
ESP.restart();
|
||||||
|
|
||||||
|
// task storage debugging //
|
||||||
|
#ifdef HAS_LORA
|
||||||
|
ESP_LOGD(TAG, "Loraloop %d bytes left",
|
||||||
|
uxTaskGetStackHighWaterMark(LoraTask));
|
||||||
|
#endif
|
||||||
|
ESP_LOGD(TAG, "Wifiloop %d bytes left",
|
||||||
|
uxTaskGetStackHighWaterMark(wifiSwitchTask));
|
||||||
|
ESP_LOGD(TAG, "Statemachine %d bytes left",
|
||||||
|
uxTaskGetStackHighWaterMark(stateMachineTask));
|
||||||
|
#ifdef HAS_GPS
|
||||||
|
ESP_LOGD(TAG, "Gpsloop %d bytes left", uxTaskGetStackHighWaterMark(GpsTask));
|
||||||
|
#endif
|
||||||
|
|
||||||
// read battery voltage into global variable
|
// read battery voltage into global variable
|
||||||
#ifdef HAS_BATTERY_PROBE
|
#ifdef HAS_BATTERY_PROBE
|
||||||
batt_voltage = read_voltage();
|
batt_voltage = read_voltage();
|
||||||
@ -48,7 +61,7 @@ void doHousekeeping() {
|
|||||||
esp_get_minimum_free_heap_size(), ESP.getFreeHeap());
|
esp_get_minimum_free_heap_size(), ESP.getFreeHeap());
|
||||||
SendData(COUNTERPORT); // send data before clearing counters
|
SendData(COUNTERPORT); // send data before clearing counters
|
||||||
reset_counters(); // clear macs container and reset all counters
|
reset_counters(); // clear macs container and reset all counters
|
||||||
reset_salt(); // get new salt for salting hashes
|
get_salt(); // get new salt for salting hashes
|
||||||
|
|
||||||
if (esp_get_minimum_free_heap_size() <= MEM_LOW) // check again
|
if (esp_get_minimum_free_heap_size() <= MEM_LOW) // check again
|
||||||
esp_restart(); // memory leak, reset device
|
esp_restart(); // memory leak, reset device
|
||||||
|
@ -13,7 +13,7 @@ const char lora_datarate[] = {"1211100908077BFSNA"};
|
|||||||
const char lora_datarate[] = {"100908078CNA121110090807"};
|
const char lora_datarate[] = {"100908078CNA121110090807"};
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
uint8_t DisplayState = 0;
|
uint8_t volatile DisplayState = 0;
|
||||||
|
|
||||||
// helper function, prints a hex key on display
|
// helper function, prints a hex key on display
|
||||||
void DisplayKey(const uint8_t *key, uint8_t len, bool lsb) {
|
void DisplayKey(const uint8_t *key, uint8_t len, bool lsb) {
|
||||||
@ -91,6 +91,10 @@ void init_display(const char *Productname, const char *Version) {
|
|||||||
|
|
||||||
void refreshtheDisplay() {
|
void refreshtheDisplay() {
|
||||||
|
|
||||||
|
portENTER_CRITICAL(&timerMux);
|
||||||
|
DisplayTimerIRQ = 0;
|
||||||
|
portEXIT_CRITICAL(&timerMux);
|
||||||
|
|
||||||
// set display on/off according to current device configuration
|
// set display on/off according to current device configuration
|
||||||
if (DisplayState != cfg.screenon) {
|
if (DisplayState != cfg.screenon) {
|
||||||
DisplayState = cfg.screenon;
|
DisplayState = cfg.screenon;
|
||||||
@ -114,7 +118,8 @@ void refreshtheDisplay() {
|
|||||||
// update Battery status (line 2)
|
// update Battery status (line 2)
|
||||||
#ifdef HAS_BATTERY_PROBE
|
#ifdef HAS_BATTERY_PROBE
|
||||||
u8x8.setCursor(0, 2);
|
u8x8.setCursor(0, 2);
|
||||||
u8x8.printf(batt_voltage > 4000 ? "B:USB " : "B:%.1fV", batt_voltage / 1000.0);
|
u8x8.printf(batt_voltage > 4000 ? "B:USB " : "B:%.1fV",
|
||||||
|
batt_voltage / 1000.0);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// update GPS status (line 2)
|
// update GPS status (line 2)
|
||||||
@ -191,13 +196,4 @@ void IRAM_ATTR DisplayIRQ() {
|
|||||||
portEXIT_CRITICAL_ISR(&timerMux);
|
portEXIT_CRITICAL_ISR(&timerMux);
|
||||||
}
|
}
|
||||||
|
|
||||||
void updateDisplay() {
|
|
||||||
if (DisplayTimerIRQ) {
|
|
||||||
portENTER_CRITICAL(&timerMux);
|
|
||||||
DisplayTimerIRQ = 0;
|
|
||||||
portEXIT_CRITICAL(&timerMux);
|
|
||||||
refreshtheDisplay();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif // HAS_DISPLAY
|
#endif // HAS_DISPLAY
|
@ -3,13 +3,12 @@
|
|||||||
|
|
||||||
#include <U8x8lib.h>
|
#include <U8x8lib.h>
|
||||||
|
|
||||||
extern uint8_t DisplayState;
|
extern uint8_t volatile DisplayState;
|
||||||
extern HAS_DISPLAY u8x8;
|
extern HAS_DISPLAY u8x8;
|
||||||
|
|
||||||
void init_display(const char *Productname, const char *Version);
|
void init_display(const char *Productname, const char *Version);
|
||||||
void refreshtheDisplay(void);
|
void refreshtheDisplay(void);
|
||||||
void DisplayKey(const uint8_t *key, uint8_t len, bool lsb);
|
void DisplayKey(const uint8_t *key, uint8_t len, bool lsb);
|
||||||
void updateDisplay(void);
|
|
||||||
void DisplayIRQ(void);
|
void DisplayIRQ(void);
|
||||||
|
|
||||||
#endif
|
#endif
|
@ -41,17 +41,21 @@ typedef struct {
|
|||||||
// global variables
|
// global variables
|
||||||
extern configData_t cfg; // current device configuration
|
extern configData_t cfg; // current device configuration
|
||||||
extern char display_line6[], display_line7[]; // screen buffers
|
extern char display_line6[], display_line7[]; // screen buffers
|
||||||
extern uint8_t channel; // wifi channel rotation counter
|
extern uint8_t volatile channel; // wifi channel rotation counter
|
||||||
extern uint16_t macs_total, macs_wifi, macs_ble, batt_voltage; // display values
|
extern uint16_t volatile macs_total, macs_wifi, macs_ble,
|
||||||
|
batt_voltage; // display values
|
||||||
extern std::set<uint16_t> macs; // temp storage for MACs
|
extern std::set<uint16_t> macs; // temp storage for MACs
|
||||||
extern hw_timer_t *channelSwitch, *sendCycle;
|
extern hw_timer_t *channelSwitch, *sendCycle;
|
||||||
extern portMUX_TYPE timerMux;
|
extern portMUX_TYPE timerMux;
|
||||||
extern volatile int SendCycleTimerIRQ, HomeCycleIRQ, DisplayTimerIRQ,
|
extern volatile uint8_t SendCycleTimerIRQ, HomeCycleIRQ, DisplayTimerIRQ,
|
||||||
ChannelTimerIRQ, ButtonPressedIRQ;
|
ChannelTimerIRQ, ButtonPressedIRQ;
|
||||||
|
|
||||||
extern std::array<uint64_t, 0xff>::iterator it;
|
extern std::array<uint64_t, 0xff>::iterator it;
|
||||||
extern std::array<uint64_t, 0xff> beacons;
|
extern std::array<uint64_t, 0xff> beacons;
|
||||||
|
|
||||||
|
extern SemaphoreHandle_t xWifiChannelSwitchSemaphore;
|
||||||
|
extern TaskHandle_t stateMachineTask, wifiSwitchTask;
|
||||||
|
|
||||||
#ifdef HAS_GPS
|
#ifdef HAS_GPS
|
||||||
extern TaskHandle_t GpsTask;
|
extern TaskHandle_t GpsTask;
|
||||||
#include "gps.h"
|
#include "gps.h"
|
||||||
|
@ -3,7 +3,9 @@
|
|||||||
#define HAS_LORA 1 // comment out if device shall not send data via LoRa
|
#define HAS_LORA 1 // comment out if device shall not send data via LoRa
|
||||||
#define HAS_SPI 1 // comment out if device shall not send data via SPI
|
#define HAS_SPI 1 // comment out if device shall not send data via SPI
|
||||||
#define CFG_sx1272_radio 1
|
#define CFG_sx1272_radio 1
|
||||||
#define HAS_LED NOT_A_PIN // LoPy has no on board LED, so we use RGB LED on LoPy
|
//#define HAS_LED NOT_A_PIN // LoPy4 has no on board mono LED, we use on board RGB LED
|
||||||
|
#define HAS_LED GPIO_NUM_12 // use if LoPy is on Expansion Board, this has a user LED
|
||||||
|
#define LED_ACTIVE_LOW 1 // use if LoPy is on Expansion Board, this has a user LED
|
||||||
#define HAS_RGB_LED GPIO_NUM_0 // WS2812B RGB LED on GPIO0
|
#define HAS_RGB_LED GPIO_NUM_0 // WS2812B RGB LED on GPIO0
|
||||||
|
|
||||||
// Hardware pin definitions for Pycom LoPy board
|
// Hardware pin definitions for Pycom LoPy board
|
||||||
@ -28,7 +30,7 @@
|
|||||||
// uncomment this only if your LoPy runs on a expansion board 3.0
|
// uncomment this only if your LoPy runs on a expansion board 3.0
|
||||||
//#define HAS_BATTERY_PROBE ADC1_GPIO39_CHANNEL // battery probe GPIO pin -> ADC1_CHANNEL_7
|
//#define HAS_BATTERY_PROBE ADC1_GPIO39_CHANNEL // battery probe GPIO pin -> ADC1_CHANNEL_7
|
||||||
//#define BATT_FACTOR 2 // voltage divider 1MOhm/1MOhm on board
|
//#define BATT_FACTOR 2 // voltage divider 1MOhm/1MOhm on board
|
||||||
//#define HAS_BUTTON GPIO_NUM_37 // (P14)
|
//#define HAS_BUTTON GPIO_NUM_13 // (P14)
|
||||||
//#define BUTTON_PULLUP 1 // Button need pullup instead of default pulldown
|
//#define BUTTON_PULLUP 1 // Button need pullup instead of default pulldown
|
||||||
|
|
||||||
// uncomment this only if your LoPy runs on a expansion board 2.0
|
// uncomment this only if your LoPy runs on a expansion board 2.0
|
||||||
|
@ -3,7 +3,9 @@
|
|||||||
#define HAS_LORA 1 // comment out if device shall not send data via LoRa
|
#define HAS_LORA 1 // comment out if device shall not send data via LoRa
|
||||||
#define HAS_SPI 1 // comment out if device shall not send data via SPI
|
#define HAS_SPI 1 // comment out if device shall not send data via SPI
|
||||||
#define CFG_sx1276_radio 1
|
#define CFG_sx1276_radio 1
|
||||||
#define HAS_LED NOT_A_PIN // LoPy4 has no on board LED, so we use RGB LED on LoPy4
|
//#define HAS_LED NOT_A_PIN // LoPy4 has no on board mono LED, we use on board RGB LED
|
||||||
|
#define HAS_LED GPIO_NUM_12 // use if LoPy is on Expansion Board, this has a user LED
|
||||||
|
#define LED_ACTIVE_LOW 1 // use if LoPy is on Expansion Board, this has a user LED
|
||||||
#define HAS_RGB_LED GPIO_NUM_0 // WS2812B RGB LED on GPIO0
|
#define HAS_RGB_LED GPIO_NUM_0 // WS2812B RGB LED on GPIO0
|
||||||
#define BOARD_HAS_PSRAM // use extra 4MB extern RAM
|
#define BOARD_HAS_PSRAM // use extra 4MB extern RAM
|
||||||
|
|
||||||
@ -29,7 +31,7 @@
|
|||||||
// uncomment this only if your LoPy runs on a expansion board 3.0
|
// uncomment this only if your LoPy runs on a expansion board 3.0
|
||||||
#define HAS_BATTERY_PROBE ADC1_GPIO39_CHANNEL // battery probe GPIO pin -> ADC1_CHANNEL_7
|
#define HAS_BATTERY_PROBE ADC1_GPIO39_CHANNEL // battery probe GPIO pin -> ADC1_CHANNEL_7
|
||||||
#define BATT_FACTOR 2 // voltage divider 1MOhm/1MOhm on board
|
#define BATT_FACTOR 2 // voltage divider 1MOhm/1MOhm on board
|
||||||
#define HAS_BUTTON GPIO_NUM_37 // (P14)
|
#define HAS_BUTTON GPIO_NUM_13 // (P14)
|
||||||
#define BUTTON_PULLUP 1 // Button need pullup instead of default pulldown
|
#define BUTTON_PULLUP 1 // Button need pullup instead of default pulldown
|
||||||
|
|
||||||
// uncomment this only if your LoPy runs on a expansion board 2.0
|
// uncomment this only if your LoPy runs on a expansion board 2.0
|
||||||
|
@ -247,7 +247,9 @@ void lorawan_loop(void *pvParameters) {
|
|||||||
configASSERT(((uint32_t)pvParameters) == 1); // FreeRTOS check
|
configASSERT(((uint32_t)pvParameters) == 1); // FreeRTOS check
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
|
//vTaskSuspendAll();
|
||||||
os_runloop_once(); // execute LMIC jobs
|
os_runloop_once(); // execute LMIC jobs
|
||||||
|
//xTaskResumeAll();
|
||||||
vTaskDelay(2 / portTICK_PERIOD_MS); // yield to CPU
|
vTaskDelay(2 / portTICK_PERIOD_MS); // yield to CPU
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -11,8 +11,8 @@ static const char TAG[] = "main";
|
|||||||
|
|
||||||
uint16_t salt;
|
uint16_t salt;
|
||||||
|
|
||||||
uint16_t reset_salt(void) {
|
uint16_t get_salt(void) {
|
||||||
salt = random(65536); // get new 16bit random for salting hashes
|
salt = (uint16_t)random(65536); // get new 16bit random for salting hashes
|
||||||
return salt;
|
return salt;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -71,8 +71,8 @@ bool mac_add(uint8_t *paddr, int8_t rssi, bool sniff_type) {
|
|||||||
// https://en.wikipedia.org/wiki/MAC_Address_Anonymization
|
// https://en.wikipedia.org/wiki/MAC_Address_Anonymization
|
||||||
|
|
||||||
snprintf(buff, sizeof(buff), "%08X",
|
snprintf(buff, sizeof(buff), "%08X",
|
||||||
addr2int + (uint32_t)salt); // convert usigned 32-bit salted MAC to
|
addr2int + (uint32_t)salt); // convert usigned 32-bit salted MAC
|
||||||
// 8 digit hex string
|
// to 8 digit hex string
|
||||||
hashedmac = rokkit(&buff[3], 5); // hash MAC last string value, use 5 chars
|
hashedmac = rokkit(&buff[3], 5); // hash MAC last string value, use 5 chars
|
||||||
// to fit hash in uint16_t container
|
// to fit hash in uint16_t container
|
||||||
auto newmac = macs.insert(hashedmac); // add hashed MAC, if new unique
|
auto newmac = macs.insert(hashedmac); // add hashed MAC, if new unique
|
||||||
@ -81,7 +81,6 @@ bool mac_add(uint8_t *paddr, int8_t rssi, bool sniff_type) {
|
|||||||
|
|
||||||
// Count only if MAC was not yet seen
|
// Count only if MAC was not yet seen
|
||||||
if (added) {
|
if (added) {
|
||||||
|
|
||||||
// increment counter and one blink led
|
// increment counter and one blink led
|
||||||
if (sniff_type == MAC_SNIFF_WIFI) {
|
if (sniff_type == MAC_SNIFF_WIFI) {
|
||||||
macs_wifi++; // increment Wifi MACs counter
|
macs_wifi++; // increment Wifi MACs counter
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
#define MAC_SNIFF_WIFI 0
|
#define MAC_SNIFF_WIFI 0
|
||||||
#define MAC_SNIFF_BLE 1
|
#define MAC_SNIFF_BLE 1
|
||||||
|
|
||||||
uint16_t reset_salt(void);
|
uint16_t get_salt(void);
|
||||||
uint64_t macConvert(uint8_t *paddr);
|
uint64_t macConvert(uint8_t *paddr);
|
||||||
bool mac_add(uint8_t *paddr, int8_t rssi, bool sniff_type);
|
bool mac_add(uint8_t *paddr, int8_t rssi, bool sniff_type);
|
||||||
void printKey(const char *name, const uint8_t *key, uint8_t len, bool lsb);
|
void printKey(const char *name, const uint8_t *key, uint8_t len, bool lsb);
|
||||||
|
68
src/main.cpp
68
src/main.cpp
@ -32,6 +32,7 @@ gpsloop 0 2 read data from GPS over serial or i2c
|
|||||||
IDLE 1 0 Arduino loop() -> used for LED switching
|
IDLE 1 0 Arduino loop() -> used for LED switching
|
||||||
loraloop 1 1 runs the LMIC stack
|
loraloop 1 1 runs the LMIC stack
|
||||||
statemachine 1 3 switches application process logic
|
statemachine 1 3 switches application process logic
|
||||||
|
wifiloop 0 4 rotates wifi channels
|
||||||
|
|
||||||
ESP32 hardware timers
|
ESP32 hardware timers
|
||||||
==========================
|
==========================
|
||||||
@ -47,18 +48,20 @@ ESP32 hardware timers
|
|||||||
|
|
||||||
configData_t cfg; // struct holds current device configuration
|
configData_t cfg; // struct holds current device configuration
|
||||||
char display_line6[16], display_line7[16]; // display buffers
|
char display_line6[16], display_line7[16]; // display buffers
|
||||||
uint8_t channel = 0; // channel rotation counter
|
uint8_t volatile channel = 0; // channel rotation counter
|
||||||
uint16_t macs_total = 0, macs_wifi = 0, macs_ble = 0,
|
uint16_t volatile macs_total = 0, macs_wifi = 0, macs_ble = 0,
|
||||||
batt_voltage = 0; // globals for display
|
batt_voltage = 0; // globals for display
|
||||||
|
|
||||||
// hardware timer for cyclic tasks
|
// hardware timer for cyclic tasks
|
||||||
hw_timer_t *channelSwitch, *displaytimer, *sendCycle, *homeCycle;
|
hw_timer_t *channelSwitch, *displaytimer, *sendCycle, *homeCycle;
|
||||||
|
|
||||||
// this variables will be changed in the ISR, and read in main loop
|
// this variables will be changed in the ISR, and read in main loop
|
||||||
volatile int ButtonPressedIRQ = 0, ChannelTimerIRQ = 0, SendCycleTimerIRQ = 0,
|
uint8_t volatile ButtonPressedIRQ = 0, ChannelTimerIRQ = 0,
|
||||||
DisplayTimerIRQ = 0, HomeCycleIRQ = 0;
|
SendCycleTimerIRQ = 0, DisplayTimerIRQ = 0, HomeCycleIRQ = 0;
|
||||||
|
|
||||||
TaskHandle_t StateTask = NULL;
|
TaskHandle_t stateMachineTask, wifiSwitchTask;
|
||||||
|
|
||||||
|
SemaphoreHandle_t xWifiChannelSwitchSemaphore;
|
||||||
|
|
||||||
// RTos send queues for payload transmit
|
// RTos send queues for payload transmit
|
||||||
#ifdef HAS_LORA
|
#ifdef HAS_LORA
|
||||||
@ -96,7 +99,7 @@ void setup() {
|
|||||||
// disable brownout detection
|
// disable brownout detection
|
||||||
#ifdef DISABLE_BROWNOUT
|
#ifdef DISABLE_BROWNOUT
|
||||||
// register with brownout is at address DR_REG_RTCCNTL_BASE + 0xd4
|
// register with brownout is at address DR_REG_RTCCNTL_BASE + 0xd4
|
||||||
(*((volatile uint32_t *)ETS_UNCACHED_ADDR((DR_REG_RTCCNTL_BASE + 0xd4)))) = 0;
|
(*((uint32_t volatile *)ETS_UNCACHED_ADDR((DR_REG_RTCCNTL_BASE + 0xd4)))) = 0;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// setup debug output or silence device
|
// setup debug output or silence device
|
||||||
@ -143,12 +146,15 @@ void setup() {
|
|||||||
batt_voltage = read_voltage();
|
batt_voltage = read_voltage();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#ifdef USE_OTA
|
||||||
|
strcat_P(features, " OTA");
|
||||||
// reboot to firmware update mode if ota trigger switch is set
|
// reboot to firmware update mode if ota trigger switch is set
|
||||||
if (cfg.runmode == 1) {
|
if (cfg.runmode == 1) {
|
||||||
cfg.runmode = 0;
|
cfg.runmode = 0;
|
||||||
saveConfig();
|
saveConfig();
|
||||||
start_ota_update();
|
start_ota_update();
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// initialize button
|
// initialize button
|
||||||
#ifdef HAS_BUTTON
|
#ifdef HAS_BUTTON
|
||||||
@ -242,11 +248,6 @@ void setup() {
|
|||||||
timerAlarmEnable(displaytimer);
|
timerAlarmEnable(displaytimer);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// setup channel rotation trigger IRQ using esp32 hardware timer 1
|
|
||||||
channelSwitch = timerBegin(1, 800, true);
|
|
||||||
timerAttachInterrupt(channelSwitch, &ChannelSwitchIRQ, true);
|
|
||||||
timerAlarmWrite(channelSwitch, cfg.wifichancycle * 1000, true);
|
|
||||||
|
|
||||||
// setup send cycle trigger IRQ using esp32 hardware timer 2
|
// setup send cycle trigger IRQ using esp32 hardware timer 2
|
||||||
sendCycle = timerBegin(2, 8000, true);
|
sendCycle = timerBegin(2, 8000, true);
|
||||||
timerAttachInterrupt(sendCycle, &SendCycleIRQ, true);
|
timerAttachInterrupt(sendCycle, &SendCycleIRQ, true);
|
||||||
@ -257,6 +258,12 @@ void setup() {
|
|||||||
timerAttachInterrupt(homeCycle, &homeCycleIRQ, true);
|
timerAttachInterrupt(homeCycle, &homeCycleIRQ, true);
|
||||||
timerAlarmWrite(homeCycle, HOMECYCLE * 10000, true);
|
timerAlarmWrite(homeCycle, HOMECYCLE * 10000, true);
|
||||||
|
|
||||||
|
// setup channel rotation trigger IRQ using esp32 hardware timer 1
|
||||||
|
xWifiChannelSwitchSemaphore = xSemaphoreCreateBinary();
|
||||||
|
channelSwitch = timerBegin(1, 800, true);
|
||||||
|
timerAttachInterrupt(channelSwitch, &ChannelSwitchIRQ, true);
|
||||||
|
timerAlarmWrite(channelSwitch, cfg.wifichancycle * 1000, true);
|
||||||
|
|
||||||
// enable timers
|
// enable timers
|
||||||
// caution, see: https://github.com/espressif/arduino-esp32/issues/1313
|
// caution, see: https://github.com/espressif/arduino-esp32/issues/1313
|
||||||
yield();
|
yield();
|
||||||
@ -301,8 +308,13 @@ void setup() {
|
|||||||
// https://techtutorialsx.com/2017/05/09/esp32-get-task-execution-core/
|
// https://techtutorialsx.com/2017/05/09/esp32-get-task-execution-core/
|
||||||
|
|
||||||
ESP_LOGI(TAG, "Starting Lora...");
|
ESP_LOGI(TAG, "Starting Lora...");
|
||||||
xTaskCreatePinnedToCore(lorawan_loop, "loraloop", 2048, (void *)1, 1,
|
xTaskCreatePinnedToCore(lorawan_loop, /* task function */
|
||||||
&LoraTask, 1);
|
"loraloop", /* name of task */
|
||||||
|
2560, /* stack size of task */
|
||||||
|
(void *)1, /* parameter of the task */
|
||||||
|
1, /* priority of the task */
|
||||||
|
&LoraTask, /* task handle*/
|
||||||
|
1); /* CPU core */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// if device has GPS and it is enabled, start GPS reader task on core 0 with
|
// if device has GPS and it is enabled, start GPS reader task on core 0 with
|
||||||
@ -310,7 +322,13 @@ void setup() {
|
|||||||
// streaming NMEA data
|
// streaming NMEA data
|
||||||
#ifdef HAS_GPS
|
#ifdef HAS_GPS
|
||||||
ESP_LOGI(TAG, "Starting GPS...");
|
ESP_LOGI(TAG, "Starting GPS...");
|
||||||
xTaskCreatePinnedToCore(gps_loop, "gpsloop", 2048, (void *)1, 2, &GpsTask, 0);
|
xTaskCreatePinnedToCore(gps_loop, /* task function */
|
||||||
|
"gpsloop", /* name of task */
|
||||||
|
1024, /* stack size of task */
|
||||||
|
(void *)1, /* parameter of the task */
|
||||||
|
2, /* priority of the task */
|
||||||
|
&GpsTask, /* task handle*/
|
||||||
|
0); /* CPU core */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// start BLE scan callback if BLE function is enabled in NVRAM configuration
|
// start BLE scan callback if BLE function is enabled in NVRAM configuration
|
||||||
@ -323,18 +341,30 @@ void setup() {
|
|||||||
|
|
||||||
// start wifi in monitor mode and start channel rotation task on core 0
|
// start wifi in monitor mode and start channel rotation task on core 0
|
||||||
ESP_LOGI(TAG, "Starting Wifi...");
|
ESP_LOGI(TAG, "Starting Wifi...");
|
||||||
// esp_event_loop_init(NULL, NULL);
|
|
||||||
// ESP_ERROR_CHECK(esp_event_loop_init(event_handler, NULL));
|
|
||||||
wifi_sniffer_init();
|
wifi_sniffer_init();
|
||||||
// initialize salt value using esp_random() called by random() in
|
// initialize salt value using esp_random() called by random() in
|
||||||
// arduino-esp32 core. Note: do this *after* wifi has started, since
|
// arduino-esp32 core. Note: do this *after* wifi has started, since
|
||||||
// function gets it's seed from RF noise
|
// function gets it's seed from RF noise
|
||||||
reset_salt(); // get new 16bit for salting hashes
|
get_salt(); // get new 16bit for salting hashes
|
||||||
|
|
||||||
|
// start wifi channel rotation task
|
||||||
|
xTaskCreatePinnedToCore(switchWifiChannel, /* task function */
|
||||||
|
"wifiloop", /* name of task */
|
||||||
|
1024, /* stack size of task */
|
||||||
|
NULL, /* parameter of the task */
|
||||||
|
4, /* priority of the task */
|
||||||
|
&wifiSwitchTask, /* task handle*/
|
||||||
|
0); /* CPU core */
|
||||||
|
|
||||||
// start state machine
|
// start state machine
|
||||||
ESP_LOGI(TAG, "Starting Statemachine...");
|
ESP_LOGI(TAG, "Starting Statemachine...");
|
||||||
xTaskCreatePinnedToCore(stateMachine, "stateloop", 2048, (void *)1, 3,
|
xTaskCreatePinnedToCore(stateMachine, /* task function */
|
||||||
&StateTask, 1);
|
"stateloop", /* name of task */
|
||||||
|
2048, /* stack size of task */
|
||||||
|
(void *)1, /* parameter of the task */
|
||||||
|
3, /* priority of the task */
|
||||||
|
&stateMachineTask, /* task handle */
|
||||||
|
1); /* CPU core */
|
||||||
|
|
||||||
} // setup()
|
} // setup()
|
||||||
|
|
||||||
|
85
src/ota.cpp
85
src/ota.cpp
@ -1,3 +1,5 @@
|
|||||||
|
#ifdef USE_OTA
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Parts of this code:
|
Parts of this code:
|
||||||
Copyright (c) 2014-present PlatformIO <contact@platformio.org>
|
Copyright (c) 2014-present PlatformIO <contact@platformio.org>
|
||||||
@ -17,7 +19,6 @@
|
|||||||
|
|
||||||
#include "ota.h"
|
#include "ota.h"
|
||||||
|
|
||||||
#include <string>
|
|
||||||
using namespace std;
|
using namespace std;
|
||||||
|
|
||||||
const BintrayClient bintray(BINTRAY_USER, BINTRAY_REPO, BINTRAY_PACKAGE);
|
const BintrayClient bintray(BINTRAY_USER, BINTRAY_REPO, BINTRAY_PACKAGE);
|
||||||
@ -29,33 +30,27 @@ const int port = 443;
|
|||||||
const uint32_t RESPONSE_TIMEOUT_MS = 5000;
|
const uint32_t RESPONSE_TIMEOUT_MS = 5000;
|
||||||
|
|
||||||
// Variables to validate firmware content
|
// Variables to validate firmware content
|
||||||
volatile int contentLength = 0;
|
int volatile contentLength = 0;
|
||||||
volatile bool isValidContentType = false;
|
bool volatile isValidContentType = false;
|
||||||
|
|
||||||
// Local logging tag
|
// Local logging tag
|
||||||
static const char TAG[] = "main";
|
static const char TAG[] = "main";
|
||||||
|
|
||||||
void display(const uint8_t row, std::string status, std::string msg) {
|
// helper function to extract header value from header
|
||||||
#ifdef HAS_DISPLAY
|
inline String getHeaderValue(String header, String headerName) {
|
||||||
u8x8.setCursor(14, row);
|
return header.substring(strlen(headerName.c_str()));
|
||||||
u8x8.print((status.substr(0, 2)).c_str());
|
|
||||||
if (!msg.empty()) {
|
|
||||||
u8x8.clearLine(7);
|
|
||||||
u8x8.setCursor(0, 7);
|
|
||||||
u8x8.print(msg.substr(0, 16).c_str());
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
}
|
|
||||||
|
|
||||||
// callback function to show download progress while streaming data
|
|
||||||
void show_progress(size_t current, size_t size) {
|
|
||||||
char buf[17];
|
|
||||||
snprintf(buf, 17, "%-9lu (%3lu%%)", current, current*100 / size);
|
|
||||||
display(4, "**", buf);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void start_ota_update() {
|
void start_ota_update() {
|
||||||
|
|
||||||
|
// check battery status if we can before doing ota
|
||||||
|
#ifdef HAS_BATTERY_PROBE
|
||||||
|
if (batt_voltage < OTA_MIN_BATT) {
|
||||||
|
ESP_LOGW(TAG, "Battery voltage %dmV too low for OTA", batt_voltage);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// turn on LED
|
// turn on LED
|
||||||
#if (HAS_LED != NOT_A_PIN)
|
#if (HAS_LED != NOT_A_PIN)
|
||||||
#ifdef LED_ACTIVE_LOW
|
#ifdef LED_ACTIVE_LOW
|
||||||
@ -99,7 +94,7 @@ void start_ota_update() {
|
|||||||
if (i >= 0) {
|
if (i >= 0) {
|
||||||
ESP_LOGI(TAG, "Connected to %s", WIFI_SSID);
|
ESP_LOGI(TAG, "Connected to %s", WIFI_SSID);
|
||||||
display(1, "OK", "WiFi connected");
|
display(1, "OK", "WiFi connected");
|
||||||
checkFirmwareUpdates(); // gets and flashes new firmware
|
do_ota_update(); // gets and flashes new firmware
|
||||||
} else {
|
} else {
|
||||||
ESP_LOGI(TAG, "Could not connect to %s, rebooting.", WIFI_SSID);
|
ESP_LOGI(TAG, "Could not connect to %s, rebooting.", WIFI_SSID);
|
||||||
display(1, " E", "no WiFi connect");
|
display(1, " E", "no WiFi connect");
|
||||||
@ -121,7 +116,9 @@ void start_ota_update() {
|
|||||||
|
|
||||||
} // start_ota_update
|
} // start_ota_update
|
||||||
|
|
||||||
void checkFirmwareUpdates() {
|
void do_ota_update() {
|
||||||
|
char buf[17];
|
||||||
|
|
||||||
// Fetch the latest firmware version
|
// Fetch the latest firmware version
|
||||||
ESP_LOGI(TAG, "Checking latest firmware version on server...");
|
ESP_LOGI(TAG, "Checking latest firmware version on server...");
|
||||||
display(2, "**", "checking version");
|
display(2, "**", "checking version");
|
||||||
@ -140,24 +137,10 @@ void checkFirmwareUpdates() {
|
|||||||
}
|
}
|
||||||
ESP_LOGI(TAG, "New firmware version v%s available. Downloading...",
|
ESP_LOGI(TAG, "New firmware version v%s available. Downloading...",
|
||||||
latest.c_str());
|
latest.c_str());
|
||||||
display(2, "OK", "");
|
display(2, "OK", latest.c_str());
|
||||||
|
|
||||||
processOTAUpdate(latest);
|
display(3, "**", "");
|
||||||
}
|
String firmwarePath = bintray.getBinaryPath(latest);
|
||||||
|
|
||||||
// helper function to extract header value from header
|
|
||||||
inline String getHeaderValue(String header, String headerName) {
|
|
||||||
return header.substring(strlen(headerName.c_str()));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* OTA update processing
|
|
||||||
*/
|
|
||||||
void processOTAUpdate(const String &version) {
|
|
||||||
|
|
||||||
char buf[17];
|
|
||||||
display(3, "**", "requesting file");
|
|
||||||
String firmwarePath = bintray.getBinaryPath(version);
|
|
||||||
if (!firmwarePath.endsWith(".bin")) {
|
if (!firmwarePath.endsWith(".bin")) {
|
||||||
ESP_LOGI(TAG, "Unsupported binary format, OTA update cancelled.");
|
ESP_LOGI(TAG, "Unsupported binary format, OTA update cancelled.");
|
||||||
display(3, " E", "file type error");
|
display(3, " E", "file type error");
|
||||||
@ -268,10 +251,10 @@ void processOTAUpdate(const String &version) {
|
|||||||
size_t written, current, size;
|
size_t written, current, size;
|
||||||
|
|
||||||
if (Update.begin(contentLength)) {
|
if (Update.begin(contentLength)) {
|
||||||
|
#ifdef HAS_DISPLAY
|
||||||
// register callback function for showing progress while streaming data
|
// register callback function for showing progress while streaming data
|
||||||
Update.onProgress(&show_progress);
|
Update.onProgress(&show_progress);
|
||||||
|
#endif
|
||||||
int i = FLASH_MAX_TRY;
|
int i = FLASH_MAX_TRY;
|
||||||
while ((i--) && (written != contentLength)) {
|
while ((i--) && (written != contentLength)) {
|
||||||
|
|
||||||
@ -327,6 +310,25 @@ void processOTAUpdate(const String &version) {
|
|||||||
ESP_LOGI(TAG,
|
ESP_LOGI(TAG,
|
||||||
"OTA update failed. Rebooting to runmode with current version.");
|
"OTA update failed. Rebooting to runmode with current version.");
|
||||||
client.stop();
|
client.stop();
|
||||||
|
} // do_ota_update
|
||||||
|
|
||||||
|
void display(const uint8_t row, const std::string status, const std::string msg) {
|
||||||
|
#ifdef HAS_DISPLAY
|
||||||
|
u8x8.setCursor(14, row);
|
||||||
|
u8x8.print((status.substr(0, 2)).c_str());
|
||||||
|
if (!msg.empty()) {
|
||||||
|
u8x8.clearLine(7);
|
||||||
|
u8x8.setCursor(0, 7);
|
||||||
|
u8x8.print(msg.substr(0, 16).c_str());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// callback function to show download progress while streaming data
|
||||||
|
void show_progress(size_t current, size_t size) {
|
||||||
|
char buf[17];
|
||||||
|
snprintf(buf, 17, "%-9lu (%3lu%%)", current, current * 100 / size);
|
||||||
|
display(4, "**", buf);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
// helper function to compare two versions. Returns 1 if v2 is
|
// helper function to compare two versions. Returns 1 if v2 is
|
||||||
@ -363,3 +365,4 @@ int version_compare(const String v1, const String v2) {
|
|||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
#endif // USE_OTA
|
@ -1,18 +1,21 @@
|
|||||||
#ifndef OTA_H
|
#ifndef OTA_H
|
||||||
#define OTA_H
|
#define OTA_H
|
||||||
|
|
||||||
|
#ifdef USE_OTA
|
||||||
|
|
||||||
#include "globals.h"
|
#include "globals.h"
|
||||||
#include "update.h"
|
#include "update.h"
|
||||||
#include <WiFi.h>
|
#include <WiFi.h>
|
||||||
#include <WiFiClientSecure.h>
|
#include <WiFiClientSecure.h>
|
||||||
//#include <Update.h>
|
|
||||||
#include <BintrayClient.h>
|
#include <BintrayClient.h>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
void checkFirmwareUpdates();
|
void do_ota_update();
|
||||||
void processOTAUpdate(const String &version);
|
|
||||||
void start_ota_update();
|
void start_ota_update();
|
||||||
int version_compare(const String v1, const String v2);
|
int version_compare(const String v1, const String v2);
|
||||||
void show_progress(size_t current, size_t size);
|
void show_progress(size_t current, size_t size);
|
||||||
|
void display(const uint8_t row, const std::string status, const std::string msg);
|
||||||
|
|
||||||
|
#endif // USE_OTA
|
||||||
|
|
||||||
#endif // OTA_H
|
#endif // OTA_H
|
||||||
|
@ -66,8 +66,10 @@
|
|||||||
#define HOMECYCLE 30 // house keeping cycle in seconds [default = 30 secs]
|
#define HOMECYCLE 30 // house keeping cycle in seconds [default = 30 secs]
|
||||||
|
|
||||||
// OTA settings
|
// OTA settings
|
||||||
|
#define USE_OTA 1 // Comment out to disable OTA update
|
||||||
#define WIFI_MAX_TRY 20 // maximum number of wifi connect attempts for OTA update [default = 20]
|
#define WIFI_MAX_TRY 20 // maximum number of wifi connect attempts for OTA update [default = 20]
|
||||||
#define FLASH_MAX_TRY 3 // maximum number of attempts for writing update binary to flash [default = 3]
|
#define FLASH_MAX_TRY 3 // maximum number of attempts for writing update binary to flash [default = 3]
|
||||||
|
#define OTA_MIN_BATT 3700 // minimum battery level vor OTA [millivolt]
|
||||||
|
|
||||||
// LMIC settings
|
// LMIC settings
|
||||||
// define hardware independent LMIC settings here, settings of standard library in /lmic/config.h will be ignored
|
// define hardware independent LMIC settings here, settings of standard library in /lmic/config.h will be ignored
|
||||||
|
@ -18,7 +18,7 @@ void set_reset(uint8_t val[]) {
|
|||||||
case 1: // reset MAC counter
|
case 1: // reset MAC counter
|
||||||
ESP_LOGI(TAG, "Remote command: reset MAC counter");
|
ESP_LOGI(TAG, "Remote command: reset MAC counter");
|
||||||
reset_counters(); // clear macs
|
reset_counters(); // clear macs
|
||||||
reset_salt(); // get new salt
|
get_salt(); // get new salt
|
||||||
sprintf(display_line6, "Reset counter");
|
sprintf(display_line6, "Reset counter");
|
||||||
break;
|
break;
|
||||||
case 2: // reset device to factory settings
|
case 2: // reset device to factory settings
|
||||||
@ -33,9 +33,14 @@ void set_reset(uint8_t val[]) {
|
|||||||
break;
|
break;
|
||||||
case 9: // reset and ask for software update via Wifi OTA
|
case 9: // reset and ask for software update via Wifi OTA
|
||||||
ESP_LOGI(TAG, "Remote command: software update via Wifi");
|
ESP_LOGI(TAG, "Remote command: software update via Wifi");
|
||||||
|
#ifdef USE_OTA
|
||||||
sprintf(display_line6, "Software update");
|
sprintf(display_line6, "Software update");
|
||||||
cfg.runmode = 1;
|
cfg.runmode = 1;
|
||||||
|
#else
|
||||||
|
sprintf(display_line6, "Software update not implemented");
|
||||||
|
#endif // USE_OTA
|
||||||
break;
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
ESP_LOGW(TAG, "Remote command: reset called with invalid parameter(s)");
|
ESP_LOGW(TAG, "Remote command: reset called with invalid parameter(s)");
|
||||||
}
|
}
|
||||||
|
@ -29,7 +29,7 @@ void SendData(uint8_t port) {
|
|||||||
// clear counter if not in cumulative counter mode
|
// clear counter if not in cumulative counter mode
|
||||||
if ((port == COUNTERPORT) && (cfg.countermode != 1)) {
|
if ((port == COUNTERPORT) && (cfg.countermode != 1)) {
|
||||||
reset_counters(); // clear macs container and reset all counters
|
reset_counters(); // clear macs container and reset all counters
|
||||||
reset_salt(); // get new salt for salting hashes
|
get_salt(); // get new salt for salting hashes
|
||||||
ESP_LOGI(TAG, "Counter cleared");
|
ESP_LOGI(TAG, "Counter cleared");
|
||||||
}
|
}
|
||||||
} // SendData
|
} // SendData
|
||||||
|
@ -10,16 +10,15 @@ void stateMachine(void *pvParameters) {
|
|||||||
while (1) {
|
while (1) {
|
||||||
|
|
||||||
#ifdef HAS_BUTTON
|
#ifdef HAS_BUTTON
|
||||||
|
if (ButtonPressedIRQ)
|
||||||
readButton();
|
readButton();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAS_DISPLAY
|
#ifdef HAS_DISPLAY
|
||||||
updateDisplay();
|
if (DisplayTimerIRQ)
|
||||||
|
refreshtheDisplay();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
// check wifi scan cycle and if due rotate channel
|
|
||||||
if (ChannelTimerIRQ)
|
|
||||||
switchWifiChannel(channel);
|
|
||||||
// check housekeeping cycle and if due do the work
|
// check housekeeping cycle and if due do the work
|
||||||
if (HomeCycleIRQ)
|
if (HomeCycleIRQ)
|
||||||
doHousekeeping();
|
doHousekeeping();
|
||||||
|
@ -8,5 +8,6 @@
|
|||||||
#include "cyclic.h"
|
#include "cyclic.h"
|
||||||
|
|
||||||
void stateMachine(void *pvParameters);
|
void stateMachine(void *pvParameters);
|
||||||
|
void stateMachineInit();
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
@ -30,6 +30,10 @@ void wifi_sniffer_init(void) {
|
|||||||
cfg.nvs_enable = 0; // we don't need any wifi settings from NVRAM
|
cfg.nvs_enable = 0; // we don't need any wifi settings from NVRAM
|
||||||
wifi_promiscuous_filter_t filter = {
|
wifi_promiscuous_filter_t filter = {
|
||||||
.filter_mask = WIFI_PROMIS_FILTER_MASK_MGMT}; // we need only MGMT frames
|
.filter_mask = WIFI_PROMIS_FILTER_MASK_MGMT}; // we need only MGMT frames
|
||||||
|
|
||||||
|
// esp_event_loop_init(NULL, NULL);
|
||||||
|
// ESP_ERROR_CHECK(esp_event_loop_init(event_handler, NULL));
|
||||||
|
|
||||||
ESP_ERROR_CHECK(esp_wifi_init(&cfg)); // configure Wifi with cfg
|
ESP_ERROR_CHECK(esp_wifi_init(&cfg)); // configure Wifi with cfg
|
||||||
ESP_ERROR_CHECK(
|
ESP_ERROR_CHECK(
|
||||||
esp_wifi_set_country(&wifi_country)); // set locales for RF and channels
|
esp_wifi_set_country(&wifi_country)); // set locales for RF and channels
|
||||||
@ -43,20 +47,22 @@ void wifi_sniffer_init(void) {
|
|||||||
ESP_ERROR_CHECK(esp_wifi_set_promiscuous(true)); // now switch on monitor mode
|
ESP_ERROR_CHECK(esp_wifi_set_promiscuous(true)); // now switch on monitor mode
|
||||||
}
|
}
|
||||||
|
|
||||||
// Wifi channel rotation
|
// IRQ Handler
|
||||||
void switchWifiChannel(uint8_t &ch) {
|
void ChannelSwitchIRQ() {
|
||||||
portENTER_CRITICAL(&timerMux);
|
BaseType_t xHigherPriorityTaskWoken = pdFALSE;
|
||||||
ChannelTimerIRQ = 0;
|
// unblock wifi channel rotation task
|
||||||
portEXIT_CRITICAL(&timerMux);
|
xSemaphoreGiveFromISR(xWifiChannelSwitchSemaphore, &xHigherPriorityTaskWoken);
|
||||||
// rotates variable channel 1..WIFI_CHANNEL_MAX
|
|
||||||
ch = (ch % WIFI_CHANNEL_MAX) + 1;
|
|
||||||
esp_wifi_set_channel(ch, WIFI_SECOND_CHAN_NONE);
|
|
||||||
ESP_LOGD(TAG, "Wifi set channel %d", &ch);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// IRQ handler
|
// Wifi channel rotation task
|
||||||
void IRAM_ATTR ChannelSwitchIRQ() {
|
void switchWifiChannel(void * parameter) {
|
||||||
portENTER_CRITICAL(&timerMux);
|
while (1) {
|
||||||
ChannelTimerIRQ++;
|
// task is remaining in block state waiting for channel switch timer interrupt event
|
||||||
portEXIT_CRITICAL(&timerMux);
|
xSemaphoreTake(xWifiChannelSwitchSemaphore, portMAX_DELAY);
|
||||||
|
// rotates variable channel 1..WIFI_CHANNEL_MAX
|
||||||
|
channel = (channel % WIFI_CHANNEL_MAX) + 1;
|
||||||
|
esp_wifi_set_channel(channel, WIFI_SECOND_CHAN_NONE);
|
||||||
|
ESP_LOGD(TAG, "Wifi set channel %d", channel);
|
||||||
|
}
|
||||||
|
vTaskDelete(NULL);
|
||||||
}
|
}
|
@ -28,6 +28,6 @@ typedef struct {
|
|||||||
void wifi_sniffer_init(void);
|
void wifi_sniffer_init(void);
|
||||||
void wifi_sniffer_packet_handler(void *buff, wifi_promiscuous_pkt_type_t type);
|
void wifi_sniffer_packet_handler(void *buff, wifi_promiscuous_pkt_type_t type);
|
||||||
void ChannelSwitchIRQ(void);
|
void ChannelSwitchIRQ(void);
|
||||||
void switchWifiChannel(uint8_t &ch);
|
void switchWifiChannel(void * parameter);
|
||||||
|
|
||||||
#endif
|
#endif
|
Loading…
Reference in New Issue
Block a user