From 5e8ba82e6e11ace6377d82901ce8927ce50bf146 Mon Sep 17 00:00:00 2001 From: kazu Date: Sun, 14 Mar 2021 15:20:44 +0100 Subject: [PATCH] minor changes, added ALL required externals --- Makefile | 10 +- README.md | 1 + user/Buzzer.h | 26 +-- user/ESP8266lib/CompileTime.h | 60 ++++++ user/ESP8266lib/Debug.h | 55 ++++++ user/ESP8266lib/ESP.h | 16 ++ user/ESP8266lib/c++.h | 297 ++++++++++++++++++++++++++++ user/ESP8266lib/data/Bitstream.h | 62 ++++++ user/ESP8266lib/data/Color.h | 116 +++++++++++ user/ESP8266lib/data/DoubleBuffer.h | 70 +++++++ user/ESP8266lib/data/LinearBuffer.h | 59 ++++++ user/ESP8266lib/data/RingBuffer.h | 79 ++++++++ user/ESP8266lib/ext/led/WS2812B.h | 272 +++++++++++++++++++++++++ user/ESP8266lib/io/IO.h | 90 +++++++++ user/ESP8266lib/io/fastGPIO.h | 189 ++++++++++++++++++ user/ESP8266lib/net/IP.h | 27 +++ user/ESP8266lib/net/MAC.h | 78 ++++++++ user/ESP8266lib/net/Promiscuous.h | 52 +++++ user/ESP8266lib/net/UDP.h | 103 ++++++++++ user/ESP8266lib/net/WiFiRaw.h | 195 ++++++++++++++++++ user/Fader.h | 2 +- user/run_Buzzer.h | 24 ++- 22 files changed, 1853 insertions(+), 30 deletions(-) create mode 100644 user/ESP8266lib/CompileTime.h create mode 100644 user/ESP8266lib/Debug.h create mode 100644 user/ESP8266lib/ESP.h create mode 100644 user/ESP8266lib/c++.h create mode 100644 user/ESP8266lib/data/Bitstream.h create mode 100644 user/ESP8266lib/data/Color.h create mode 100644 user/ESP8266lib/data/DoubleBuffer.h create mode 100644 user/ESP8266lib/data/LinearBuffer.h create mode 100644 user/ESP8266lib/data/RingBuffer.h create mode 100644 user/ESP8266lib/ext/led/WS2812B.h create mode 100644 user/ESP8266lib/io/IO.h create mode 100644 user/ESP8266lib/io/fastGPIO.h create mode 100644 user/ESP8266lib/net/IP.h create mode 100644 user/ESP8266lib/net/MAC.h create mode 100644 user/ESP8266lib/net/Promiscuous.h create mode 100644 user/ESP8266lib/net/UDP.h create mode 100644 user/ESP8266lib/net/WiFiRaw.h diff --git a/Makefile b/Makefile index 1e9fd21..c3931bc 100755 --- a/Makefile +++ b/Makefile @@ -17,19 +17,19 @@ SDK_BASE ?= /apps/esp/esp-open-sdk/sdk # esptool.py path and port ESPTOOL ?= esptool.py -ESPPORT ?= /dev/ttyUSB3 +ESPPORT ?= /dev/ttyUSB0 # name for the target project TARGET = app # which modules (subdirectories) of the project to include in compiling MODULES = driver user -EXTRA_INCDIR = include $(ROOT)/include/ $(ROOT)/driver_lib/include/ ../../MilesTag/src +EXTRA_INCDIR = include $(ROOT)/include/ $(ROOT)/driver_lib/include/ /apps/ # libraries used in this project, mainly provided by the SDK #LIBS = c gcc hal pp phy net80211 lwip wpa wpa2 crypto main #LIBS = c gcc pp phy net80211 lwip wpa main -LIBS = c gcc hal phy pp net80211 lwip wpa main wps crypto +LIBS = c gcc hal phy pp net80211 lwip wpa main wps crypto m # compiler flags using during compilation of source files #CFLAGS = -Os -g -O2 -Wpointer-arith -Wundef -Werror -Wl,-EL -fno-inline-functions -nostdlib -mlongcalls -mtext-section-literals -D__ets__ -DICACHE_FLASH @@ -40,8 +40,8 @@ CXXFLAGS = $(CFLAGS) -fno-rtti -fno-exceptions -std=c++11 LDFLAGS = -nostdlib -Wl,--no-check-sections -Wl,--gc-sections -u call_user_start -Wl,-static # linker script used for the above linkier step -#LD_SCRIPT = eagle.app.v6.ld -LD_SCRIPT = eagle.app.v6.modified.ld +LD_SCRIPT = eagle.app.v6.ld +#LD_SCRIPT = eagle.app.v6.modified.ld #http://www.esp8266.com/viewtopic.php?f=9&t=478&start=8 # various paths from the SDK used in this project diff --git a/README.md b/README.md index 7091a1a..13d7c8f 100644 --- a/README.md +++ b/README.md @@ -1,2 +1,3 @@ # buzzer +make clean && make && make flash && stty -F /dev/ttyUSB0 115200 raw -echo && cat /dev/ttyUSB0 diff --git a/user/Buzzer.h b/user/Buzzer.h index a636727..6ad79d5 100755 --- a/user/Buzzer.h +++ b/user/Buzzer.h @@ -13,7 +13,7 @@ #include "Rainbow.h" #include "RainbowBeat.h" -#define FIRMWARE_NR 5 +#define FIRMWARE_NR 10 #define CODE(a, b, c, d) (a << 24 | b << 16 | c << 8 | d) @@ -78,18 +78,18 @@ public: const uint16_t vcc = ADC::getVcc(); os_printf("send: heartbeat, Vcc: %d\n", vcc); - char data[5+12+2+3]; + char data[5+6+2+3]; os_memcpy(&data[0], "*PING", 5); - os_memcpy(&data[5], myMac.asPtr(), 12); + os_memcpy(&data[5], myMac.asPtr(), 6); - data[17] = '_'; - data[18] = FIRMWARE_NR; + data[11] = '_'; + data[12] = FIRMWARE_NR; - data[19] = '_'; - data[20] = (vcc >> 8) & 0xFF; - data[21] = (vcc >> 0) & 0xFF; + data[13] = '_'; + data[14] = (vcc >> 8) & 0xFF; + data[15] = (vcc >> 0) & 0xFF; udp.send(remoteIP, remotePort, data, sizeof(data)); @@ -120,8 +120,8 @@ public: static int cnt = 0; ++cnt; - // every 9 seconds - if (cnt % 9000 == 0) { + // every 3 seconds + if (cnt % 3000 == 0) { buzzer.sendHeartbeat(); } @@ -235,6 +235,7 @@ public: /** disable LED */ void setOff() { + os_printf("setOff()\n"); ledMode = LEDMode::OFF; leds.getColor(0).setRGB(0,0,255); // for testing leds.setEnabled(0, false); @@ -243,7 +244,8 @@ public: /** set a fixed RGB color */ void setRGB(const uint8_t r, const uint8_t g, const uint8_t b) { - debugMod(NAME, "setting LEDS to fixed RGB color"); + //debugMod(NAME, "setting LEDS to fixed RGB color"); + os_printf("setRGB(%d,%d,%d)\n", r, g, b); ledMode = LEDMode::FIXED_COLOR; leds.getColor(0).setRGB(r,g,b); leds.setEnabled(0, true); @@ -260,6 +262,7 @@ public: /** set LED rainbow fading */ void setRainbow() { + os_printf("setRainbow()\n"); rainbow.restart(); ledMode = LEDMode::RAINBOW_COLOR; leds.setEnabled(0, true); @@ -268,6 +271,7 @@ public: /** set LED fading between two colors */ void setFade(const uint8_t r1, const uint8_t g1, const uint8_t b1, const uint8_t r2, const uint8_t g2, const uint8_t b2) { + os_printf("setFade((%d,%d,%d)(%d,%d,%d))\n", r1,g1,b1, r2,g2,b2); fadeBetween.setColor1(Color::fromRGB(r1, g1, b1)); fadeBetween.setColor2(Color::fromRGB(r2, g2, b2)); fadeBetween.restart(); diff --git a/user/ESP8266lib/CompileTime.h b/user/ESP8266lib/CompileTime.h new file mode 100644 index 0000000..7f8d1b2 --- /dev/null +++ b/user/ESP8266lib/CompileTime.h @@ -0,0 +1,60 @@ +#define COMPUTE_BUILD_YEAR ( \ + (__DATE__[ 7] - '0') * 1000 + \ + (__DATE__[ 8] - '0') * 100 + \ + (__DATE__[ 9] - '0') * 10 + \ + (__DATE__[10] - '0') \ +) + + +#define COMPUTE_BUILD_DAY ( \ + ((__DATE__[4] >= '0') ? (__DATE__[4] - '0') * 10 : 0) + \ + (__DATE__[5] - '0') \ +) + + +#define BUILD_MONTH_IS_JAN (__DATE__[0] == 'J' && __DATE__[1] == 'a' && __DATE__[2] == 'n') +#define BUILD_MONTH_IS_FEB (__DATE__[0] == 'F') +#define BUILD_MONTH_IS_MAR (__DATE__[0] == 'M' && __DATE__[1] == 'a' && __DATE__[2] == 'r') +#define BUILD_MONTH_IS_APR (__DATE__[0] == 'A' && __DATE__[1] == 'p') +#define BUILD_MONTH_IS_MAY (__DATE__[0] == 'M' && __DATE__[1] == 'a' && __DATE__[2] == 'y') +#define BUILD_MONTH_IS_JUN (__DATE__[0] == 'J' && __DATE__[1] == 'u' && __DATE__[2] == 'n') +#define BUILD_MONTH_IS_JUL (__DATE__[0] == 'J' && __DATE__[1] == 'u' && __DATE__[2] == 'l') +#define BUILD_MONTH_IS_AUG (__DATE__[0] == 'A' && __DATE__[1] == 'u') +#define BUILD_MONTH_IS_SEP (__DATE__[0] == 'S') +#define BUILD_MONTH_IS_OCT (__DATE__[0] == 'O') +#define BUILD_MONTH_IS_NOV (__DATE__[0] == 'N') +#define BUILD_MONTH_IS_DEC (__DATE__[0] == 'D') + + +#define COMPUTE_BUILD_MONTH ( \ + (BUILD_MONTH_IS_JAN) ? 1 : \ + (BUILD_MONTH_IS_FEB) ? 2 : \ + (BUILD_MONTH_IS_MAR) ? 3 : \ + (BUILD_MONTH_IS_APR) ? 4 : \ + (BUILD_MONTH_IS_MAY) ? 5 : \ + (BUILD_MONTH_IS_JUN) ? 6 : \ + (BUILD_MONTH_IS_JUL) ? 7 : \ + (BUILD_MONTH_IS_AUG) ? 8 : \ + (BUILD_MONTH_IS_SEP) ? 9 : \ + (BUILD_MONTH_IS_OCT) ? 10 : \ + (BUILD_MONTH_IS_NOV) ? 11 : \ + (BUILD_MONTH_IS_DEC) ? 12 : \ + /* error default */ 99 \ +) + +#define COMPUTE_BUILD_HOUR ((__TIME__[0] - '0') * 10 + __TIME__[1] - '0') +#define COMPUTE_BUILD_MIN ((__TIME__[3] - '0') * 10 + __TIME__[4] - '0') +#define COMPUTE_BUILD_SEC ((__TIME__[6] - '0') * 10 + __TIME__[7] - '0') + + +#define BUILD_DATE_IS_BAD (__DATE__[0] == '?') + +#define BUILD_YEAR ((BUILD_DATE_IS_BAD) ? 99 : COMPUTE_BUILD_YEAR) +#define BUILD_MONTH ((BUILD_DATE_IS_BAD) ? 99 : COMPUTE_BUILD_MONTH) +#define BUILD_DAY ((BUILD_DATE_IS_BAD) ? 99 : COMPUTE_BUILD_DAY) + +#define BUILD_TIME_IS_BAD (__TIME__[0] == '?') + +#define BUILD_HOUR ((BUILD_TIME_IS_BAD) ? 99 : COMPUTE_BUILD_HOUR) +#define BUILD_MIN ((BUILD_TIME_IS_BAD) ? 99 : COMPUTE_BUILD_MIN) +#define BUILD_SEC ((BUILD_TIME_IS_BAD) ? 99 : COMPUTE_BUILD_SEC) diff --git a/user/ESP8266lib/Debug.h b/user/ESP8266lib/Debug.h new file mode 100644 index 0000000..d781631 --- /dev/null +++ b/user/ESP8266lib/Debug.h @@ -0,0 +1,55 @@ +#ifndef DEBUG_H +#define DEBUG_H + +#include + +extern "C" { + #include "ets_sys.h" + #include "c_types.h" + #include "osapi.h" + //#include "gpio.h" + + //#include "os_type.h" + //#include "user_config.h" + #include "user_interface.h" + //#include "wpa2_enterprise.h" + //#include "inttypes.h" + #include "mem.h" + #include "espconn.h" + + #include "ESP8266lib/c++.h" + + #include "driver/uart.h" +} + +void hexdump(const uint8_t* buf, uint8_t len) { + for (int i = 0; i < len; ++i) { + os_printf("%02x ", buf[i]); + } + os_printf("\n"); +} + +#ifdef DEBUG + + #define debug(str) os_printf(str) + #define debugMod(module, str) os_printf("[%s] %s\n", module, str) + #define debugMod1(module, str, val) os_printf("[%s] ", module); os_printf(str, val); os_printf("\n"); + #define debugMod2(module, str, v1, v2) os_printf("[%s] ", module); os_printf(str, v1, v2); os_printf("\n"); + #define debugMod3(module, str, v1, v2, v3) os_printf("[%s] ", module); os_printf(str, v1, v2, v3); os_printf("\n"); + #define IF_DEBUG(a) a + #define debugShow(buf, len) hexdump(buf,len) + + +#else + + #define debug(module, str) + #define debugMod(module, str) + #define debugMod1(module, str, val) + #define debugMod2(module, str, v1, v2) + #define debugMod3(module, str, v1, v2, v3) + #define IF_DEBUG(a) + #define debugShow(a, b) + +#endif + +#endif // DEBUG_H diff --git a/user/ESP8266lib/ESP.h b/user/ESP8266lib/ESP.h new file mode 100644 index 0000000..9d7abc4 --- /dev/null +++ b/user/ESP8266lib/ESP.h @@ -0,0 +1,16 @@ +#ifndef ESP_H +#define ESP_H + +class ESP { + +public: + + static inline uint32_t getCycleCount() { + uint32_t ccount; + __asm__ __volatile__("esync; rsr %0,ccount":"=a" (ccount)); + return ccount; + } + +}; + +#endif // ESP_H diff --git a/user/ESP8266lib/c++.h b/user/ESP8266lib/c++.h new file mode 100644 index 0000000..cf8b428 --- /dev/null +++ b/user/ESP8266lib/c++.h @@ -0,0 +1,297 @@ +#pragma once + +#define TRUE true +#define FALSE false + +typedef void (*int_handler_t)(void*); +/* +void *pvPortMalloc(size_t xWantedSize, const char* file, int line) __attribute__((malloc, alloc_size(1))); +void *pvPortRealloc(void* ptr, size_t xWantedSize, const char* file, int line) __attribute__((alloc_size(2))); +void vPortFree(void *ptr, const char* file, int line); +void *ets_memcpy(void *dest, const void *src, size_t n); +void *ets_memset(void *s, int c, size_t n); +void ets_timer_arm_new(ETSTimer *a, int b, int c, int isMstimer); +void ets_timer_setfn(ETSTimer *t, ETSTimerFunc *fn, void *parg); +void ets_timer_disarm(ETSTimer *a); +int atoi(const char *nptr); +int ets_strncmp(const char *s1, const char *s2, int len); +int ets_strcmp(const char *s1, const char *s2); +int ets_strlen(const char *s); +char *ets_strcpy(char *dest, const char *src); +char *ets_strncpy(char *dest, const char *src, size_t n); +char *ets_strstr(const char *haystack, const char *needle); +int ets_sprintf(char *str, const char *format, ...) __attribute__ ((format (printf, 2, 3))); +int os_snprintf(char *str, size_t size, const char *format, ...) __attribute__ ((format (printf, 3, 4))); +int ets_printf(const char *format, ...) __attribute__ ((format (printf, 1, 2))); +void ets_install_putc1(void* routine); + +//#define STATUS int +void uart_div_modify(int no, int freq); +//STATUS uart_tx_one_char(uint8_t uart, uint8_t TxChar); + +void ets_isr_mask(int intr); +void ets_isr_unmask(int intr); +void ets_isr_attach(int intr, int_handler_t handler, void *arg); +void ets_intr_lock(); +void ets_intr_unlock(); +//int ets_vsnprintf(char * s, size_t n, const char * format, va_list arg) __attribute__ ((format (printf, 3, 0))); +//int ets_vprintf(int (*print_function)(int), const char * format, va_list arg) __attribute__ ((format (printf, 2, 0))); +int ets_putc(int); +bool ets_task(ETSTask task, uint8 prio, ETSEvent *queue, uint8 qlen); +bool ets_post(uint8 prio, ETSSignal sig, ETSParam par); + +#define ICACHE_RAM_ATTR __attribute__((section(".iram.text"))) + +typedef void (*int_handler_t)(void*); + +#define ETS_SLC_INUM 1 +#define ETS_SDIO_INUM 1 +#define ETS_SPI_INUM 2 +#define ETS_GPIO_INUM 4 +#define ETS_UART_INUM 5 +#define ETS_UART1_INUM 5 +#define ETS_CCOMPARE0_INUM 6 +#define ETS_SOFT_INUM 7 +#define ETS_WDT_INUM 8 +#define ETS_FRC_TIMER1_INUM 9 // use edge + +#define ETS_INTR_LOCK() \ + ets_intr_lock() + +#define ETS_INTR_UNLOCK() \ + ets_intr_unlock() + +#define ETS_INTR_ENABLE(inum) \ + ets_isr_unmask((1< + +template class Bitstream { + +public: + + inline void reset() { + bitMask = 128; // start with the MSB + curIdx = 0; // start with the first byte + buffer[curIdx] = 0; // initialize all bits with zero + numBitsUsed = 0; // nothing added + } + + inline void addOne() { + buffer[curIdx] |= (0xFF & bitMask); + bitMask >>= 1; + ++numBitsUsed; + checkNextByte(); + } + + inline void addZero() { + bitMask >>= 1; + ++numBitsUsed; + checkNextByte(); + } + + const uint8_t* getData() const { + return buffer; + } + + /** number of used bits */ + inline uint16_t getNumBits() const { + return numBitsUsed; + } + + /** number of used bytes. rounded-up to multiples of 8-bits */ + inline uint8_t getNumBytes() const { + return (numBitsUsed - 1) / 8 + 1; + } + +private: + + /** received 8 bits? byte complete? -> next one */ + inline void checkNextByte() { + if(bitMask == 0) { + bitMask = 128; // start with the MSB + ++curIdx; // next byte + buffer[curIdx] = 0; // initialize all bits with zero + } + } + + uint16_t numBitsUsed = 0; + uint8_t buffer[maxBytes]; //buffer containing received bits + uint8_t curIdx = 0; //index pointing to the byte currently selected within the buffer + uint8_t bitMask = 128; //mask for the next bit to write + +}; + +#endif // BITSTREAM_H diff --git a/user/ESP8266lib/data/Color.h b/user/ESP8266lib/data/Color.h new file mode 100644 index 0000000..2c93f75 --- /dev/null +++ b/user/ESP8266lib/data/Color.h @@ -0,0 +1,116 @@ +#ifndef ESP_COLOR_H +#define ESP_COLOR_H + +#include + + +struct Color { + + uint8_t r; + uint8_t g; + uint8_t b; + + /** no-init */ + Color() { + ; + } + +private: + + /** Hidden ctor. RGB */ + Color(const uint8_t r, const uint8_t g, const uint8_t b) : r(r), g(g), b(b) { + ; + } + +public: + + /** get X-percent [0:100] of this color = darker/brighter */ + Color inline getPercent(const int percent) const { + return Color(r*percent/100, g*percent/100, b*percent/100); + } + + /** mix the two given colors */ + static Color mix(const Color c1, const Color c2, int percentC1) { + return Color( + ((c1.r * percentC1) + (c2.r * (100-percentC1))) / 100, + ((c1.g * percentC1) + (c2.g * (100-percentC1))) / 100, + ((c1.b * percentC1) + (c2.b * (100-percentC1))) / 100 + ); + } + + static inline Color fromRGB(const uint8_t r, const uint8_t g, const uint8_t b) { + return Color(r,g,b); + } + + static inline Color fromHSV(const uint8_t h, const uint8_t s, const uint8_t v) { + Color c; c.setHSV(h,s,v); return c; + } + + /** get color with new brightness (0..255) */ + Color brightness(const uint8_t brightness) const { + return Color( + ((uint16_t)r)*brightness/255, + ((uint16_t)g)*brightness/255, + ((uint16_t)b)*brightness/255 + ); + } + + void setHSV(const uint8_t h, const uint8_t s, const uint8_t v) { + + uint8_t region, remainder, p, q, t; + + region = h / 43; + remainder = (h - (region * 43)) * 6; + + p = (v * (255 - s)) >> 8; + q = (v * (255 - ((s * remainder) >> 8))) >> 8; + t = (v * (255 - ((s * (255 - remainder)) >> 8))) >> 8; + + switch (region) { + case 0: + r = v; g = t; b = p; + break; + case 1: + r = q; g = v; b = p; + break; + case 2: + r = p; g = v; b = t; + break; + case 3: + r = p; g = q; b = v; + break; + case 4: + r = t; g = p; b = v; + break; + default: + r = v; g = p; b = q; + break; + } + + } + + void setRGB(const uint8_t r, const uint8_t g, const uint8_t b) { + this->r = r; + this->g = g; + this->b = b; + } + + void setOff() { + this->r = 0; + this->g = 0; + this->b = 0; + } + + + /** add two colors */ + Color operator + (const Color o) const { + return Color(r+o.r, g+o.g, b+o.g); + } + + Color operator * (const float f) const { + return Color(r*f, g*f, b*f); + } + +}; + +#endif // ESP_COLOR_H diff --git a/user/ESP8266lib/data/DoubleBuffer.h b/user/ESP8266lib/data/DoubleBuffer.h new file mode 100644 index 0000000..6509a3a --- /dev/null +++ b/user/ESP8266lib/data/DoubleBuffer.h @@ -0,0 +1,70 @@ +#ifndef DOUBLEBUFFER_H +#define DOUBLEBUFFER_H + +template class DoubleBuffer { + +private: + + Scalar data[size*2]; + Scalar* ptr1; + Scalar* ptr2; + + volatile uint32_t head; + volatile bool _needsFlush; + +public: + + void init() { + ptr1 = &data[0]; + ptr2 = &data[size]; + head = 0; + _needsFlush = false; + } + + /** add new values to buffer A. swaps A and B if A is full */ + void add(const Scalar value) { + + ptr1[head] = value; // ptr1 + ++head; + + if (head >= size) { + head = 0; + swap(); + _needsFlush = true; + } + + } + + /** get data from buffer B */ + const Scalar* getData() const { + return ptr2; + } + + /** true if the buffer is currently empty */ + bool isEmpty() const { + return head == 0; + } + + bool needsFlush() const { + return _needsFlush; + } + + void markFlushed() { + _needsFlush = false; + } + + uint32_t getSize() const { + return size; + } + +private: + + void swap() { + Scalar* tmp = ptr1; + ptr1 = ptr2; + ptr2 = tmp; + } + +}; + +#endif // DOUBLEBUFFER_H diff --git a/user/ESP8266lib/data/LinearBuffer.h b/user/ESP8266lib/data/LinearBuffer.h new file mode 100644 index 0000000..3844635 --- /dev/null +++ b/user/ESP8266lib/data/LinearBuffer.h @@ -0,0 +1,59 @@ +#ifndef LINEARBUFFER_H +#define LINEARBUFFER_H + +template class LinearBuffer { + +private: + + Scalar _data[_size]; + + uint16_t head = 0; + +public: + + void add(const Scalar value) { + if (head >= _size) {return;} + _data[head] = value; + ++head; + } + + /** get the number of used entries */ + uint16_t getNumUsed() const { + return head; + } + + /** get the number of used bytes */ + uint32_t getBytesUsed() const { + return getNumUsed() * sizeof(Scalar); + } + + uint16_t size() const { + return _size; + } + + /** set the buffer to empty */ + void reset() { + head = 0; + } + + const Scalar* data() const { + return _data; + } + + /** constant array access */ + const Scalar& operator [] (const size_t idx) const { + return _data[idx]; + } + + /** true if the buffer is currently empty */ + bool isEmpty() const { + return head == 0; + } + + bool isFull() const { + return head >= size; + } + +}; + +#endif // LINEARBUFFER_H diff --git a/user/ESP8266lib/data/RingBuffer.h b/user/ESP8266lib/data/RingBuffer.h new file mode 100644 index 0000000..9cd5f95 --- /dev/null +++ b/user/ESP8266lib/data/RingBuffer.h @@ -0,0 +1,79 @@ +#ifndef RINGBUFFER_H +#define RINGBUFFER_H + +template class RingBuffer { + +private: + + Scalar data[size]; + + volatile size_t head; + volatile size_t tail; + volatile size_t used; + +public: + + void init() { + head = 0; + tail = 0; + used = 0; + } + + /** add one value to the buffer */ + void addBlocking(const Scalar value) { + + while (used == size) {os_delay_us(1000);} + + data[head] = value; + head = (head + 1) % size; + ++used; + } + + /** add one value to the buffer */ + void addIgnore(const Scalar value) { + + if (used == size) {return;} + + data[head] = value; + head = (head + 1) % size; + ++used; + } + + /** add multiple values to the buffer */ + void add(const Scalar* value, const size_t len) { + for (size_t i = 0; i < len; ++i) { + add(value[i]); + } + } + + /** anything available? */ + bool hasNext() const { + return used != 0; + } + + Scalar get() { + const Scalar res = data[tail]; + tail = (tail + 1) % size; + --used; + return res; + } + + const Scalar& getConst() { + const uint8_t idx = tail; + tail = (tail + 1) % size; + --used; + return data[idx]; + } + +// /** true if the buffer is currently empty */ +// bool isEmpty() const { +// return head == tail; +// } + + size_t getNumUsed() const { + return used; + } + +}; + +#endif // RINGBUFFER_H diff --git a/user/ESP8266lib/ext/led/WS2812B.h b/user/ESP8266lib/ext/led/WS2812B.h new file mode 100644 index 0000000..640c81e --- /dev/null +++ b/user/ESP8266lib/ext/led/WS2812B.h @@ -0,0 +1,272 @@ +#ifndef WS2812B_H +#define WS2812B_H + +#include "../../data/Color.h" +#include "../../io/fastGPIO.h" +/* +struct Color { + + uint8_t r; + uint8_t g; + uint8_t b; + + Color() : r(0), g(0), b(0) { + ; + } + + Color(const uint8_t r, const uint8_t g, const uint8_t b) : r(r), g(g), b(b) { + ; + } + + void setRGB(const uint8_t r, const uint8_t g, const uint8_t b) { + this->r = r; + this->g = g; + this->b = b; + } + + void setOff() { + this->r = 0; + this->g = 0; + this->b = 0; + } + + void setHSV(const uint8_t h, const uint8_t s, const uint8_t v) { + + uint8_t region, remainder, p, q, t; + + region = h / 43; + remainder = (h - (region * 43)) * 6; + + p = (v * (255 - s)) >> 8; + q = (v * (255 - ((s * remainder) >> 8))) >> 8; + t = (v * (255 - ((s * (255 - remainder)) >> 8))) >> 8; + + switch (region) { + case 0: + r = v; g = t; b = p; + break; + case 1: + r = q; g = v; b = p; + break; + case 2: + r = p; g = v; b = t; + break; + case 3: + r = p; g = q; b = v; + break; + case 4: + r = t; g = p; b = v; + break; + default: + r = v; g = p; b = q; + break; + } + + } + +}; +*/ + +template class WS2812B { + + #define LED_SET_PIN_TO_OUTPUT GPIO5_OUTPUT_SET + #define LED_SET_PIN_H GPIO5_H + #define LED_SET_PIN_L GPIO5_L + + //#define NS_PER_TICK ( (1000ul*1000ul*1000ul) / (80ul*1000ul*1000ul) ) + + /** color-value for each attached LED */ + Color colors[numLEDs]; + + /** enable/disable each led */ + bool enabled[numLEDs] = {true}; + + public: + + /** ctor */ + WS2812B() { + LED_SET_PIN_TO_OUTPUT; + } + + /** set the color for the given LED */ + void setColor(const uint8_t idx, const Color rgb) { + colors[idx] = rgb; + } + + /** enable/disable the given LED */ + void setEnabled(const uint8_t idx, const bool en) { + enabled[idx] = en; + } + + /** is the given LED enabled? */ + bool isEnabled(const uint8_t idx) const { + return enabled[idx]; + } + + Color& getColor(const uint8_t idx) { + return colors[idx]; + } + + /** flush configured changes */ + void flush() { + + LED_SET_PIN_TO_OUTPUT; + + //cli(); + + //reset(); + +/* + send0(); + send1(); + send0(); + send1(); + send0(); + send1(); + send0(); + send1(); + */ + /* + send0(); + send0(); + send0(); + send0(); + send0(); + send0(); + send0(); + send0(); + + send1(); + send1(); + send1(); + send1(); + send1(); + send1(); + send1(); + // send0(); + + // send0(); + */ + + // process each LED + for (uint8_t i = 0; i < numLEDs; ++i) { + + // send each LEDs 24-bit GRB data + if (enabled[i]) { + const Color rgb = colors[i]; + sendByte(rgb.g); + sendByte(rgb.r); + sendByte(rgb.b); + } else { + sendByte(0); + sendByte(0); + sendByte(0); + } + + } + + reset(); + + + // sei(); + + + } + + private: + + inline void sendByte(uint8_t b) { + for (uint8_t i = 0; i < 8; ++i) { + if (b & 0b10000000) { + send1(); + } else { + send0(); + } + b <<= 1; + } + } + + __attribute__((always_inline)) inline void send1() { // 800ns high, 450ns low + LED_SET_PIN_H; + delay800(); + LED_SET_PIN_L; + delay100(); + } + + __attribute__((always_inline)) inline void send0() { // 400ns high, 850ns low + LED_SET_PIN_H; + delay100(); + LED_SET_PIN_L; + delay800(); + } + + __attribute__((always_inline)) inline void reset() { + LED_SET_PIN_L; + os_delay_us(50); + //delayMicroseconds(50); + } + + + //#pragma GCC optimize 0 + + __attribute__((always_inline)) inline void delay50() { + asm volatile("nop"); + asm volatile("nop"); + asm volatile("nop"); + asm volatile("nop"); + } + + + // 100 ns delay. @80 MHz one nop = 12,5ns + __attribute__((always_inline)) inline void delay100() { + delay50(); + delay50(); + } + + __attribute__((always_inline)) inline void delay200() { + delay100(); + delay100(); + } + + __attribute__((always_inline)) inline void delay400() { + delay100(); + delay100(); + delay100(); + delay100(); + } + + __attribute__((always_inline)) inline void delay500() { + delay100(); + delay100(); + delay100(); + delay100(); + delay100(); + } + + __attribute__((always_inline)) inline void delay600() { + delay100(); + delay100(); + delay100(); + delay100(); + delay100(); + delay100(); + } + + __attribute__((always_inline)) inline void delay800() { + delay400(); + delay400(); + } + + + // #pragma GCC reset_options + + + + // inline void delayNS(const uint16_t ns) { + // const uint16_t ticks = ns / NS_PER_TICK / 2; + // for (uint16_t i = 0; i < ticks; ++i) {asm("nop");} + // } + +}; + +#endif // WS2812B_H diff --git a/user/ESP8266lib/io/IO.h b/user/ESP8266lib/io/IO.h new file mode 100644 index 0000000..8813ea4 --- /dev/null +++ b/user/ESP8266lib/io/IO.h @@ -0,0 +1,90 @@ +#ifndef IO_H +#define IO_H + +// http://www.electrodragon.com/w/ESP8266_IoT_Firmware +// https://esp8266.ru/esp8266-pin-register-strapping/ +// http://www.limpkin.fr/index.php?post/2014/12/07/First-Steps-with-the-ESP8266-03-Development-Board + +//extern "C" { +// #include "eagle_soc.h" +// #include "ets_sys.h" +//} + +#include "fastGPIO.h" + +class IO { + +public: + +// // https://esp8266.ru/esp8266-pin-register-strapping/ +// static void setOutput(const uint8_t pin) { +// //PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDI_U, FUNC_GPIO12); +// //PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO0_U, FUNC_GPIO0); +// } + +// // https://esp8266.ru/esp8266-pin-register-strapping/ +// static void setInput(const uint8_t pin) { +// //PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO0_U, FUNC_GPIO0_U); +// //PIN_PULLDWN_DIS(PERIHS_IO_MUX_GPIO0_U); +// //PIN_PULLDWN_EN(PERIHS_IO_MUX_GPIO0_U); +// } + + __attribute__((always_inline)) static inline void setPinHi(const uint8_t pin) { + GPIO_OUTPUT_SET(GPIO_ID_PIN(pin), 1); + //gpio_output_set(pin, 0, pin, 0); + } + + __attribute__((always_inline)) static inline void setPinLo(const uint8_t pin) { + GPIO_OUTPUT_SET(GPIO_ID_PIN(pin), 0); + //gpio_output_set(0, pin, pin, 0); + } + + __attribute__((always_inline)) static inline void setPin(const uint8_t pin, const bool val) { + GPIO_OUTPUT_SET(GPIO_ID_PIN(pin), val); //val ? 1 : 0; + } + + __attribute__((always_inline)) static inline bool getPin(const uint8_t pin) { + return GPIO_INPUT_GET(GPIO_ID_PIN(pin)); + } + + static inline void toggleLED0() { + static bool on = false; + on = !on; + GPIO16_OUTPUT_SET; + if (on) {GPIO16_H;} else {GPIO16_L;} + } + + static inline void toggleLED1() { + static bool on = false; + on = !on; + GPIO5_OUTPUT_SET; + if (on) {GPIO5_H;} else {GPIO5_L;} + } + + /** toggle the onboard LED */ + static inline void toggleBuiltInLED() { + static volatile bool on = false; + on = !on; + +#if PLATFORM == WEMOS_D1_MINI + GPIO2_OUTPUT_SET; + if (on) {GPIO2_H;} else {GPIO2_L;} +#elif PLATFORM == NODE_MCU + GPIO16_OUTPUT_SET; + if (on) {GPIO16_H;} else {GPIO16_L;} + GPIO2_OUTPUT_SET; + if (on) {GPIO2_H;} else {GPIO2_L;} +#else + #error "NO PLATFORM" +#endif + + } + + + + + + +}; + +#endif // IO_H diff --git a/user/ESP8266lib/io/fastGPIO.h b/user/ESP8266lib/io/fastGPIO.h new file mode 100644 index 0000000..1fe9b18 --- /dev/null +++ b/user/ESP8266lib/io/fastGPIO.h @@ -0,0 +1,189 @@ +/* + * fast_gpio.h + * + * Copyright (c) 2016 maowen (https://github.com/maowen) + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to + * deal in the Software without restriction, including without limitation the + * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or + * sell copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in + * all copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING + * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS + * IN THE SOFTWARE. + */ + +#ifndef _ESP8266_FAST_GPIO_H_ +#define _ESP8266_FAST_GPIO_H_ + +#include "eagle_soc.h" +#include "gpio.h" + +/* GPIO0 Macros */ +#define GPIO0_MUX PERIPHS_IO_MUX_GPIO0_U +#define GPIO0_CONF PIN_FUNC_SELECT(GPIO0_MUX, FUNC_GPIO0) +#define GPIO0_OUTPUT_SET do { GPIO0_CONF; GPIO_OUTPUT_SET(0, 0); } while(0) +#define GPIO0_INPUT_SET do { GPIO0_CONF; GPIO_DIS_OUTPUT(0); } while(0) +#define GPIO0_INPUT_PULLUP_SET do { GPIO0_INPUT_SET; PIN_PULLUP_EN(GPIO0_MUX); } while(0) +#define GPIO0_IN (GPIO_INPUT_GET(0)) +#define GPIO0_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT0)) +#define GPIO0_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT0)) +#define GPIO0(x) ((x)?GPIO0_H:GPIO0_L) + +/* GPIO1 Macros */ +#define GPIO1_MUX PERIPHS_IO_MUX_U0TXD_U +#define GPIO1_CONF PIN_FUNC_SELECT(GPIO1_MUX, FUNC_GPIO1) +#define GPIO1_OUTPUT_SET do { GPIO1_CONF; GPIO_OUTPUT_SET(1, 0); } while(0) +#define GPIO1_INPUT_SET do { GPIO1_CONF; GPIO_DIS_OUTPUT(1); } while(0) +#define GPIO1_INPUT_PULLUP_SET do { GPIO1_INPUT_SET; PIN_PULLUP_EN(GPIO1_MUX); } while(0) +#define GPIO1_IN (GPIO_INPUT_GET(1)) +#define GPIO1_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT1)) +#define GPIO1_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT1)) +#define GPIO1(x) ((x)?GPIO1_H:GPIO1_L) + +/* GPIO2 Macros */ +#define GPIO2_MUX PERIPHS_IO_MUX_GPIO2_U +#define GPIO2_CONF PIN_FUNC_SELECT(GPIO2_MUX, FUNC_GPIO2) +#define GPIO2_OUTPUT_SET do { GPIO2_CONF; GPIO_OUTPUT_SET(2, 0); } while(0) +#define GPIO2_INPUT_SET do { GPIO2_CONF; GPIO_DIS_OUTPUT(2); } while(0) +#define GPIO2_INPUT_PULLUP_SET do { GPIO2_INPUT_SET; PIN_PULLUP_EN(GPIO2_MUX); } while(0) +#define GPIO2_IN (GPIO_INPUT_GET(2)) +#define GPIO2_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT2)) +#define GPIO2_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT2)) +#define GPIO2(x) ((x)?GPIO2_H:GPIO2_L) + +/* GPIO3 Macros */ +#define GPIO3_MUX PERIPHS_IO_MUX_U0RXD_U +#define GPIO3_CONF PIN_FUNC_SELECT(GPIO3_MUX, FUNC_GPIO3) +#define GPIO3_OUTPUT_SET do { GPIO3_CONF; GPIO_OUTPUT_SET(3, 0); } while(0) +#define GPIO3_INPUT_SET do { GPIO3_CONF; GPIO_DIS_OUTPUT(3); } while(0) +#define GPIO3_INPUT_PULLUP_SET do { GPIO3_INPUT_SET; PIN_PULLUP_EN(GPIO3_MUX); } while(0) +#define GPIO3_IN (GPIO_INPUT_GET(3)) +#define GPIO3_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT3)) +#define GPIO3_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT3)) +#define GPIO3(x) ((x)?GPIO3_H:GPIO3_L) + +/* GPIO4 Macros */ +#define GPIO4_MUX PERIPHS_IO_MUX_GPIO4_U +#define GPIO4_CONF PIN_FUNC_SELECT(GPIO4_MUX, FUNC_GPIO4) +#define GPIO4_OUTPUT_SET do { GPIO4_CONF; GPIO_OUTPUT_SET(4, 0); } while(0) +#define GPIO4_INPUT_SET do { GPIO4_CONF; GPIO_DIS_OUTPUT(4); } while(0) +#define GPIO4_INPUT_PULLUP_SET do { GPIO4_INPUT_SET; PIN_PULLUP_EN(GPIO4_MUX); } while(0) +#define GPIO4_IN (GPIO_INPUT_GET(4)) +#define GPIO4_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT4)) +#define GPIO4_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT4)) +#define GPIO4(x) ((x)?GPIO4_H:GPIO4_L) + +/* GPIO5 Macros */ +#define GPIO5_MUX PERIPHS_IO_MUX_GPIO5_U +#define GPIO5_CONF PIN_FUNC_SELECT(GPIO5_MUX, FUNC_GPIO5) +#define GPIO5_OUTPUT_SET do { GPIO5_CONF; GPIO_OUTPUT_SET(5, 0); } while(0) +#define GPIO5_INPUT_SET do { GPIO5_CONF; GPIO_DIS_OUTPUT(5); } while(0) +#define GPIO5_INPUT_PULLUP_SET do { GPIO5_INPUT_SET; PIN_PULLUP_EN(GPIO5_MUX); } while(0) +#define GPIO5_IN (GPIO_INPUT_GET(5)) +#define GPIO5_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT5)) +#define GPIO5_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT5)) +#define GPIO5(x) ((x)?GPIO5_H:GPIO5_L) + +/* Pins 6-8 not configurable as for gpio */ + +/* GPIO9 Macros */ +#define GPIO9_MUX PERIPHS_IO_MUX_SD_DATA2_U +#define GPIO9_CONF PIN_FUNC_SELECT(GPIO9_MUX, FUNC_GPIO9) +#define GPIO9_OUTPUT_SET do { GPIO9_CONF; GPIO_OUTPUT_SET(9, 0); } while(0) +#define GPIO9_INPUT_SET do { GPIO9_CONF; GPIO_DIS_OUTPUT(9); } while(0) +#define GPIO9_INPUT_PULLUP_SET do { GPIO9_INPUT_SET; PIN_PULLUP_EN(GPIO9_MUX); } while(0) +#define GPIO9_IN (GPIO_INPUT_GET(9)) +#define GPIO9_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT9)) +#define GPIO9_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT9)) +#define GPIO9(x) ((x)?GPIO9_H:GPIO9_L) + +/* GPIO10 Macros */ +#define GPIO10_MUX PERIPHS_IO_MUX_SD_DATA3_U +#define GPIO10_CONF PIN_FUNC_SELECT(GPIO10_MUX, FUNC_GPIO10) +#define GPIO10_OUTPUT_SET do { GPIO10_CONF; GPIO_OUTPUT_SET(10, 0); } while(0) +#define GPIO10_INPUT_SET do { GPIO10_CONF; GPIO_DIS_OUTPUT(10); } while(0) +#define GPIO10_INPUT_PULLUP_SET do { GPIO10_INPUT_SET; PIN_PULLUP_EN(GPIO10_MUX); } while(0) +#define GPIO10_IN (GPIO_INPUT_GET(10)) +#define GPIO10_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT10)) +#define GPIO10_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT10)) +#define GPIO10(x) ((x)?GPIO10_H:GPIO10_L) + +/* Pin 11 not cofigurable as gpio */ + +/* GPIO12 Macros */ +#define GPIO12_MUX PERIPHS_IO_MUX_MTDI_U +#define GPIO12_CONF PIN_FUNC_SELECT(GPIO12_MUX, FUNC_GPIO12) +#define GPIO12_OUTPUT_SET do { GPIO12_CONF; GPIO_OUTPUT_SET(12, 0); } while(0) +#define GPIO12_INPUT_SET do { GPIO12_CONF; GPIO_DIS_OUTPUT(12); } while(0) +#define GPIO12_INPUT_PULLUP_SET do { GPIO12_INPUT_SET; PIN_PULLUP_EN(GPIO12_MUX); } while(0) +#define GPIO12_INPUT_PULLUP_UNSET do { GPIO12_INPUT_SET; PIN_PULLUP_DIS(GPIO12_MUX); } while(0) +#define GPIO12_IN (GPIO_INPUT_GET(12)) +#define GPIO12_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT12)) +#define GPIO12_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT12)) +#define GPIO12(x) ((x)?GPIO12_H:GPIO12_L) + +/* GPIO13 Macros */ +#define GPIO13_MUX PERIPHS_IO_MUX_MTCK_U +#define GPIO13_CONF PIN_FUNC_SELECT(GPIO13_MUX, FUNC_GPIO13) +#define GPIO13_OUTPUT_SET do { GPIO13_CONF; GPIO_OUTPUT_SET(13, 0); } while(0) +#define GPIO13_INPUT_SET do { GPIO13_CONF; GPIO_DIS_OUTPUT(13); } while(0) +#define GPIO13_INPUT_PULLUP_SET do { GPIO13_INPUT_SET; PIN_PULLUP_EN(GPIO13_MUX); } while(0) +#define GPIO13_IN (GPIO_INPUT_GET(13)) +#define GPIO13_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT13)) +#define GPIO13_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT13)) +#define GPIO13(x) ((x)?GPIO13_H:GPIO13_L) + +/* GPIO14 Macros */ +#define GPIO14_MUX PERIPHS_IO_MUX_MTMS_U +#define GPIO14_CONF PIN_FUNC_SELECT(GPIO14_MUX, FUNC_GPIO14) +#define GPIO14_OUTPUT_SET do { GPIO14_CONF; GPIO_OUTPUT_SET(14, 0); } while(0) +#define GPIO14_INPUT_SET do { GPIO14_CONF; GPIO_DIS_OUTPUT(14); } while(0) +#define GPIO14_INPUT_PULLUP_SET do { GPIO14_INPUT_SET; PIN_PULLUP_EN(GPIO14_MUX); } while(0) +#define GPIO14_IN (GPIO_INPUT_GET(14)) +#define GPIO14_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT14)) +#define GPIO14_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT14)) +#define GPIO14(x) ((x)?GPIO14_H:GPIO14_L) + +/* GPIO15 Macros */ +#define GPIO15_MUX PERIPHS_IO_MUX_MTDO_U +#define GPIO15_CONF PIN_FUNC_SELECT(GPIO15_MUX, FUNC_GPIO15) +#define GPIO15_OUTPUT_SET do { GPIO15_CONF; GPIO_OUTPUT_SET(15, 0); } while(0) +#define GPIO15_INPUT_SET do { GPIO15_CONF; GPIO_DIS_OUTPUT(15); } while(0) +#define GPIO15_INPUT_PULLUP_SET do { GPIO15_INPUT_SET; PIN_PULLUP_EN(GPIO15_MUX); } while(0) +#define GPIO15_IN (GPIO_INPUT_GET(15)) +#define GPIO15_H (GPIO_REG_WRITE(GPIO_OUT_W1TS_ADDRESS, BIT15)) +#define GPIO15_L (GPIO_REG_WRITE(GPIO_OUT_W1TC_ADDRESS, BIT15)) +#define GPIO15(x) ((x)?GPIO15_H:GPIO15_L) + +/* GPIO16 Macros (no pullup enabled) */ +#define GPIO16_CONF \ +do { \ + WRITE_PERI_REG(PAD_XPD_DCDC_CONF, (READ_PERI_REG(PAD_XPD_DCDC_CONF) & (uint32_t)0xffffffbd) | (uint32_t)0x1); \ + WRITE_PERI_REG(RTC_GPIO_CONF, (READ_PERI_REG(RTC_GPIO_CONF) & (uint32_t)0xfffffffe) | (uint32_t)0x0); \ +} while(0) +#define GPIO16_OUTPUT_SET \ +do { \ + GPIO16_CONF; \ + WRITE_PERI_REG(RTC_GPIO_ENABLE, (READ_PERI_REG(RTC_GPIO_ENABLE) & (uint32)0xfffffffe) | (uint32)0x1); \ +} while(0) +#define GPIO16_INPUT_SET \ +do { \ + GPIO16_CONF; \ + WRITE_PERI_REG(RTC_GPIO_ENABLE, (READ_PERI_REG(RTC_GPIO_ENABLE) & (uint32)0xfffffffe)); \ +} while(0) +#define GPIO16_IN (uint8_t)(READ_PERI_REG(RTC_GPIO_IN_DATA) & 1) +#define GPIO16_H WRITE_PERI_REG(RTC_GPIO_OUT, (READ_PERI_REG(RTC_GPIO_OUT) & (uint32_t)0xfffffffe) | (uint32_t)(0x1)); +#define GPIO16_L WRITE_PERI_REG(RTC_GPIO_OUT, (READ_PERI_REG(RTC_GPIO_OUT) & (uint32_t)0xfffffffe) | (uint32_t)(0x0)); +#define GPIO16(x) ((x)?GPIO16_H:GPIO16_L) + +#endif diff --git a/user/ESP8266lib/net/IP.h b/user/ESP8266lib/net/IP.h new file mode 100644 index 0000000..eca1b07 --- /dev/null +++ b/user/ESP8266lib/net/IP.h @@ -0,0 +1,27 @@ +#ifndef IP_H +#define IP_H + +#define Port uint16_t + +struct IP { + + uint32_t val; + + /** empty ctor */ + IP() : val(0) { + ; + } + + /** ctor with IP-string */ + IP(const char* ipStr) { + set(ipStr); + } + + /** set the IP */ + void set(const char* ipStr) { + val = ipaddr_addr(ipStr); + } + +}; + +#endif // IP_H diff --git a/user/ESP8266lib/net/MAC.h b/user/ESP8266lib/net/MAC.h new file mode 100644 index 0000000..7cacc03 --- /dev/null +++ b/user/ESP8266lib/net/MAC.h @@ -0,0 +1,78 @@ +#ifndef MAC_H +#define MAC_H + +#include +#include +#include + +namespace WiFiRaw { + + struct MACAddress { + + uint8_t a; + uint8_t b; + uint8_t c; + uint8_t d; + uint8_t e; + uint8_t f; + + /** empty ctor */ + MACAddress() {;} + + /** ctor from distinct values */ + MACAddress(const uint8_t a, const uint8_t b, const uint8_t c, const uint8_t d, const uint8_t e, const uint8_t f) : + a(a), b(b), c(c), d(d), e(e), f(f) {;} + + /** ctor from memory region */ + MACAddress(const uint8_t* data) { + memcpy(this, data, 6); + } + + /** convert to pointer */ + const uint8_t* asPtr() const { + return (uint8_t*) this; + } + + /** equal to the given mac? */ + bool operator == (const MACAddress& o) const { + return (a == o.a) && (b == o.b) && (c == o.c) && (d == o.d) && (e == o.e) && (f == o.f); + } + + std::string asString() const { + + std::string mac; mac.resize(17); + + mac[0] = toHex(a >> 4); + mac[1] = toHex(a >> 0); + mac[2] = ':'; + mac[3] = toHex(b >> 4); + mac[4] = toHex(b >> 0); + mac[5] = ':'; + mac[6] = toHex(c >> 4); + mac[7] = toHex(c >> 0); + mac[8] = ':'; + mac[9] = toHex(d >> 4); + mac[10] = toHex(d >> 0); + mac[11] = ':'; + mac[12] = toHex(e >> 4); + mac[13] = toHex(e >> 0); + mac[14] = ':'; + mac[15] = toHex(f >> 4); + mac[16] = toHex(f >> 0); + + return mac; + + } + + private: + + inline char toHex(uint8_t c) const { + const uint8_t val = c & 0xF; + return (val >= 10) ? ('A' + val - 10) : ('0' + val); + } + + }; + +} + +#endif // MAC_H diff --git a/user/ESP8266lib/net/Promiscuous.h b/user/ESP8266lib/net/Promiscuous.h new file mode 100644 index 0000000..c318542 --- /dev/null +++ b/user/ESP8266lib/net/Promiscuous.h @@ -0,0 +1,52 @@ +#ifndef PROMISCUOUS_H +#define PROMISCUOUS_H + +struct RxControl { + signed rssi:8; // signal intensity of packet + unsigned rate:4; + unsigned is_group:1; + unsigned:1; + unsigned sig_mode:2; // 0:is 11n packet; 1:is not 11n packet; + unsigned legacy_length:12; // if not 11n packet, shows length of packet. + unsigned damatch0:1; + unsigned damatch1:1; + unsigned bssidmatch0:1; + unsigned bssidmatch1:1; + unsigned MCS:7; // if is 11n packet, shows the modulation // and code used (range from 0 to 76) + unsigned CWB:1; // if is 11n packet, shows if is HT40 packet or not + unsigned HT_length:16;// if is 11n packet, shows length of packet. + unsigned Smoothing:1; + unsigned Not_Sounding:1; + unsigned:1; + unsigned Aggregation:1; + unsigned STBC:2; + unsigned FEC_CODING:1; // if is 11n packet, shows if is LDPC packet or not. + unsigned SGI:1; + unsigned rxend_state:8; + unsigned ampdu_cnt:8; + unsigned channel:4; //which channel this packet in. + unsigned unknown3:12; +}; + +struct LenSeq{ + u16 len; // length of packet + u16 seq; // serial number of packet, the high 12bits are serial number, + // low 14 bits are Fragment number (usually be 0) + u8 addr3[6]; // the third address in packet +}; + +struct sniffer_buf{ + struct RxControl rx_ctrl; + u8 buf[36 ]; // head of ieee80211 packet + u16 cnt; // number count of packet + struct LenSeq lenseq[1]; //length of packet +}; + +struct sniffer_buf2{ + struct RxControl rx_ctrl; + uint8_t buf[112]; + uint16_t cnt; + uint16_t len; +}; + +#endif // PROMISCUOUS_H diff --git a/user/ESP8266lib/net/UDP.h b/user/ESP8266lib/net/UDP.h new file mode 100644 index 0000000..f4b343f --- /dev/null +++ b/user/ESP8266lib/net/UDP.h @@ -0,0 +1,103 @@ +#ifndef UDP_H +#define UDP_H + +extern "C" { + #include "mem.h" + #include "espconn.h" +} + +typedef void (*UDPCallback)(void* arg, char* data, unsigned short len); + +#include "../Debug.h" +#include "IP.h" + +class UDP { + +private: + + static constexpr const char* NAME = "UDP"; + + espconn* con; + +public: + + UDP() { + init(); + } + + /** dtor */ + ~UDP() { + cleanup(); + } + + + + /** bind the socket to the given local port */ + void bind(const Port localPort) { + + debugMod1(NAME, "binding to local port %d", localPort); + + // set the local port to listen on + con->proto.udp->local_port = localPort; + + // todo: check? 0=OK + const int res = espconn_create(con); + os_printf("create: %d\r\n", res); + + } + + bool send(const IP ip, const Port port, const void* data, const uint16_t dataLen) { + + debugMod1(NAME, "sending packet to remote port %d", port); + + // set remote port and IP + con->proto.udp->remote_port = port; + os_memcpy(con->proto.udp->remote_ip, &(ip.val), 4); + + //os_printf("send %d bytes\r\n", dataLen); + //os_printf("IP: %d.%d.%d.%d\n\r", con->proto.udp->remote_ip[0], con->proto.udp->remote_ip[1], con->proto.udp->remote_ip[2], con->proto.udp->remote_ip[3]); + + // send. TODO: check. 0=OK + const int res = espconn_sent(con, (unsigned char*)data, dataLen); + return (res == 0); + + } + + /** set the callback to call whenever a packet is received */ + void setRecvCallback(UDPCallback callback) { + espconn_regist_recvcb(con, callback); + } + +private: + + /** initialize the UDP "connection" */ + void init() { + + debugMod(NAME, "init()"); + + // allocate connection-objects + con = (espconn*) os_zalloc(sizeof(espconn)); + ets_memset( con, 0, sizeof( espconn ) ); + + // configure + con->type = ESPCONN_UDP; + //con->state = ESPCONN_NONE; + + con->proto.udp = (esp_udp*) os_zalloc(sizeof(esp_udp)); + + } + + /** cleanup everything */ + void cleanup() { + + debugMod(NAME, "cleanup()"); + + espconn_delete(con); + os_free(con->proto.udp); + os_free(con); + + } + +}; + +#endif // UDP_H diff --git a/user/ESP8266lib/net/WiFiRaw.h b/user/ESP8266lib/net/WiFiRaw.h new file mode 100644 index 0000000..16b440d --- /dev/null +++ b/user/ESP8266lib/net/WiFiRaw.h @@ -0,0 +1,195 @@ +#ifndef WIFIRAW_H +#define WIFIRAW_H + +#include "MAC.h" + +// ifconfig wlp0s26u1u2u1 down && iw dev wlp0s26u1u2u1 set monitor none && ifconfig wlp0s26u1u2u1 up && iw dev wlp0s26u1u2u1 set channel 3 +// ifconfig wlp0s26u1u2u1 down && iw dev wlp0s26u1u2u1 set monitor none && ifconfig wlp0s26u1u2u1 up iwconfig wlp0s26u1u2u1 channel 3 + +// https://supportforums.cisco.com/document/52391/80211-frames-starter-guide-learn-wireless-sniffer-traces + +namespace WiFiRaw { + + /** frame type */ + enum Type { + MANAGEMENT = 0b00, + CONTROL = 0b01, + DATA = 0b10, + RESERVED = 0b11, + }; + + /** frame sub-type */ + enum SubType { + + DATA_DATA = 0b0000, + DATA_DATA_CF_ACK = 0b0001, + DATA_DATA_CF_POLL = 0b0010, + DATA_DATA_CF_ACK_POLL = 0b0011, + DATA_NULL = 0b0100, + DATA_QOS = 0b1000, + + MGMT_ASSOC_REQUEST = 0b0000, + MGMT_PROBE_REQUEST = 0b0100, + MGMT_BEACON = 0b1000, + MGMT_DISASSOCIATION = 0b1010, + + }; + + /** + * 2 byte segment and fragment number. + * usually set by the ESP itself + */ + struct Fragment { + + uint8_t data[2]; + + /** empty ctor */ + Fragment() : data() {;} + + /** ctor with values */ + Fragment(const uint8_t fragNr, const uint16_t seqNr) { + data[1] = seqNr >> 4; + data[0] = seqNr << 4 | fragNr; + } + }; + +// /** +// * 4 byte checksum. +// * usually set by the ESP itself +// */ +// struct FCS { +// uint8_t data[4]; +// FCS() : data() {;} +// }; + + struct Header { + + uint8_t version : 2; // always 0 + uint8_t type : 2; // see enum + uint8_t subType : 4; // see enum + + struct Flags { + + uint8_t toDS : 1; // always 0 + uint8_t fromDS : 1; // unencrypted: 0 + uint8_t moreFragments : 1; // no more data: 0 , more data: 1 + uint8_t retransmission : 1; // no retransmission: 0, retransmission: 1 + uint8_t powerManagement : 1; // i am fully active: 0, tell AP that i safe power: 1, + uint8_t moreData : 1; // ? + uint8_t protectedPkt : 1; // 1 = encrypted, 0 = unencrypted + uint8_t strictlyOrdered : 1; // 0 = not strictly ordered + + Flags() : + toDS(0), fromDS(0), moreFragments(0), retransmission(0), powerManagement(0), + moreData(0), protectedPkt(0), strictlyOrdered(0) {;} + + } flags; + + uint16_t duration; // ?? + + Header(Type type, SubType subType) : version(0), type(type), subType(subType), duration(0) { + ; + } + + }; + + struct Timestamp { + + uint8_t data[8]; + + Timestamp() : data() {;} + + }; + + struct BeaconInterval { + + uint8_t data[2]; + + BeaconInterval() { + data[0] = 0x64; + data[1] = 0x00; + } + + }; + + struct Capabilities { + + uint8_t isSTA : 1; + uint16_t empty : 15; + + Capabilities() : isSTA(1), empty(0) {;} + }; + + /** base-struct for management frames */ + struct ManagementFrame { + + Timestamp ts; + BeaconInterval interval; + Capabilities capa; + + ManagementFrame() : ts(), interval(), capa() {;} + + }; + + struct UnknownPkt { + Header header; + WiFiRaw::MACAddress destination; + WiFiRaw::MACAddress transmitter; + WiFiRaw::MACAddress bssid; + }; + + + /** beacon packet */ + template struct BeaconPkt { + + Header header; + WiFiRaw::MACAddress destination; // usually broadcast ff:ff:ff:ff:ff:ff + WiFiRaw::MACAddress transmitter; // usually the AP's MAC + WiFiRaw::MACAddress bssid; // the AP's MAC + Fragment frag; + + ManagementFrame mgmt; + + T data; + + //FCS fcs; + + BeaconPkt(const WiFiRaw::MACAddress myMAC) : + header(MANAGEMENT, MGMT_BEACON), destination(0xFF,0xFF,0xFF,0xFF,0xFF,0xFF), transmitter(myMAC), bssid(myMAC) { + ; + } + + }; + + /** data packet */ + template struct DataPkt { + + Header header; + WiFiRaw::MACAddress bssid; // the AP's mac + WiFiRaw::MACAddress transmitter; // my mac + WiFiRaw::MACAddress destination; // the receiver's mac + + Fragment frag; + + uint8_t data[size]; + + //FCS fcs; + + DataPkt(const WiFiRaw::MACAddress& mine, const WiFiRaw::MACAddress& receiver, const WiFiRaw::MACAddress& bssid) : + header(DATA, DATA_DATA_CF_ACK), bssid(bssid), transmitter(mine), destination(receiver) { + header.flags.toDS = 1; + } + + }; + + + WiFiRaw::MACAddress getMyMAC() { + WiFiRaw::MACAddress mine; + wifi_get_macaddr(0x00, (uint8_t*)&mine); + return mine; + } + + +}; + +#endif // WIFIRAW_H diff --git a/user/Fader.h b/user/Fader.h index 56823c1..ba6b386 100755 --- a/user/Fader.h +++ b/user/Fader.h @@ -29,7 +29,7 @@ public: void restart() { pos = 0; - speed = 128; + speed = 64; dir = 0; } diff --git a/user/run_Buzzer.h b/user/run_Buzzer.h index 000b38a..e7ae4d8 100755 --- a/user/run_Buzzer.h +++ b/user/run_Buzzer.h @@ -11,15 +11,13 @@ const uint16_t localPort = 1337; const char* remoteIP = "255.255.255.255"; // BUZZER const uint16_t remotePort = 7331; -//char ssid[32] = "OGWLAN"; -//char password[64] = "LeckereKekse!"; +// TPLink AP +char ssid[32] = "buzzer"; +char password[64] = "RLzW15yWm342Vts2"; -//char ssid[32] = "UGWLAN"; +//char ssid[32] = "Buzzer"; //char password[64] = "LeckereKekse!"; -char ssid[32] = "Buzzer"; -char password[64] = "LeckereKekse!"; - @@ -42,19 +40,19 @@ void onWifiEvent(System_Event_t* evt) { case EVENT_STAMODE_CONNECTED: os_printf("connect to ssid %s, channel %d\n", evt->event_info.connected.ssid, evt->event_info.connected.channel); - buzzer.setRGB(0,0,255); // blue + buzzer.setRGB(0,255,0); // LED green break; case EVENT_STAMODE_GOT_IP: os_printf("got IP\n"); - buzzer.setOff(); + buzzer.setOff(); // LED off connected = true; buzzer.sendHeartbeat(); break; case EVENT_STAMODE_DISCONNECTED: os_printf("disconnect from ssid %s, reason %d\n", evt->event_info.disconnected.ssid, evt->event_info.disconnected.reason); - buzzer.setRGB(255,0,0); + buzzer.setRGB(255,0,0); // LED red break; } @@ -72,8 +70,8 @@ void my_init() { // stty -F /dev/ttyUSB0 115200 raw -echo && cat /dev/ttyUSB0 - // yellow - buzzer.setRGB(255,255,0); + // white 1 + buzzer.setRGB(64,64,64); // register the event handler wifi_set_event_handler_cb(onWifiEvent); @@ -104,8 +102,8 @@ void my_init() { //wifi_set_sleep_type(LIGHT_SLEEP_T); //wifi_set_sleep_type(MODEM_SLEEP_T); - // green - buzzer.setRGB(0,255,0); + // white 2 + buzzer.setRGB(128,128,128); os_delay_us(1000*150);