commit c3ff7276a9bf69e33c89036720bb16daafe14f64 Author: Michael Smith Date: Fri Mar 9 14:21:54 2018 +0100 Initial commit diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..dc84959 --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +build/ + diff --git a/Makefile b/Makefile new file mode 100644 index 0000000..61ef537 --- /dev/null +++ b/Makefile @@ -0,0 +1,143 @@ +# Makefile for ESP8266 projects +# +# Thanks to: +# - zarya +# - Jeroen Domburg (Sprite_tm) +# - Christian Klippel (mamalala) +# - Tommie Gannert (tommie) +# +# Changelog: +# - 2014-10-06: Changed the variables to include the header file directory +# - 2014-10-06: Added global var for the Xtensa tool root +# - 2014-11-23: Updated for SDK 0.9.3 +# - 2014-12-25: Replaced esptool by esptool.py + +BUILD_AREA = /Volumes/case-sensitive/esp8266-dev + +# Output directors to store intermediate compiled files +# relative to the project directory +BUILD_BASE = build +FW_BASE = firmware + +# base directory for the compiler +XTENSA_TOOLS_ROOT ?= $(BUILD_AREA)/esp-open-sdk/xtensa-lx106-elf/bin + +# # base directory of the ESP8266 SDK package, absolute +SDK_BASE ?= $(BUILD_AREA)/esp-open-sdk/sdk + +# # esptool.py path and port +ESPTOOL ?= $(BUILD_AREA)/esp-open-sdk/esptool/esptool.py +#ESPTOOL ?= /home/martin/.local/bin/esptool.py +ESPPORT ?= /dev/tty.wchusbserial1420 +ESPTOOLBAUD ?= 115200 +ESPTOOLOPTS = -ff 40m -fm dio -fs 32m + +# name for the target project +TARGET = app + +# which modules (subdirectories) of the project to include in compiling +MODULES = driver user easygpio +EXTRA_INCDIR = include $(BUILD_AREA)/esp-open-sdk/esp-open-lwip/include +#EXTRA_INCDIR = include + +# libraries used in this project, mainly provided by the SDK +LIBS = c gcc hal pp phy net80211 lwip_open_napt wpa main + +# 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 -DLWIP_OPEN_SRC -DUSE_OPTIMIZE_PRINTF + +# linker flags used to generate the main object file +LDFLAGS = -nostdlib -Wl,--no-check-sections -u call_user_start -Wl,-static -L. + +# linker script used for the above linkier step +LD_SCRIPT = eagle.app.v6.ld + +# various paths from the SDK used in this project +SDK_LIBDIR = lib +SDK_LDDIR = ld +SDK_INCDIR = include include/json + +# we create two different files for uploading into the flash +# these are the names and options to generate them +FW_FILE_1_ADDR = 0x00000 +FW_FILE_2_ADDR = 0x10000 + +# select which tools to use as compiler, librarian and linker +CC := $(XTENSA_TOOLS_ROOT)/xtensa-lx106-elf-gcc +AR := $(XTENSA_TOOLS_ROOT)/xtensa-lx106-elf-ar +LD := $(XTENSA_TOOLS_ROOT)/xtensa-lx106-elf-gcc + + + +#### +#### no user configurable options below here +#### +SRC_DIR := $(MODULES) +BUILD_DIR := $(addprefix $(BUILD_BASE)/,$(MODULES)) + +SDK_LIBDIR := $(addprefix $(SDK_BASE)/,$(SDK_LIBDIR)) +SDK_INCDIR := $(addprefix -I$(SDK_BASE)/,$(SDK_INCDIR)) + +SRC := $(foreach sdir,$(SRC_DIR),$(wildcard $(sdir)/*.c)) +OBJ := $(patsubst %.c,$(BUILD_BASE)/%.o,$(SRC)) +LIBS := $(addprefix -l,$(LIBS)) +APP_AR := $(addprefix $(BUILD_BASE)/,$(TARGET)_app.a) +TARGET_OUT := $(addprefix $(BUILD_BASE)/,$(TARGET).out) + +LD_SCRIPT := $(addprefix -T$(SDK_BASE)/$(SDK_LDDIR)/,$(LD_SCRIPT)) + +INCDIR := $(addprefix -I,$(SRC_DIR)) +EXTRA_INCDIR := $(addprefix -I,$(EXTRA_INCDIR)) +MODULE_INCDIR := $(addsuffix /include,$(INCDIR)) + +FW_FILE_1 := $(addprefix $(FW_BASE)/,$(FW_FILE_1_ADDR).bin) +FW_FILE_2 := $(addprefix $(FW_BASE)/,$(FW_FILE_2_ADDR).bin) + +V ?= $(VERBOSE) +ifeq ("$(V)","1") +Q := +vecho := @true +else +Q := @ +vecho := @echo +endif + +vpath %.c $(SRC_DIR) + +define compile-objects +$1/%.o: %.c + $(vecho) "CC $$<" + $(Q) $(CC) $(INCDIR) $(MODULE_INCDIR) $(EXTRA_INCDIR) $(SDK_INCDIR) $(CFLAGS) -c $$< -o $$@ +endef + +.PHONY: all checkdirs flash clean + +all: checkdirs $(TARGET_OUT) $(FW_FILE_1) $(FW_FILE_2) + +$(FW_BASE)/%.bin: $(TARGET_OUT) | $(FW_BASE) + $(vecho) "FW $(FW_BASE)/" + $(Q) $(ESPTOOL) elf2image -o $(FW_BASE)/ $(TARGET_OUT) + +$(TARGET_OUT): $(APP_AR) + $(vecho) "LD $@" + $(Q) $(LD) -L$(SDK_LIBDIR) $(LD_SCRIPT) $(LDFLAGS) -Wl,--start-group $(LIBS) $(APP_AR) -Wl,--end-group -o $@ + +$(APP_AR): $(OBJ) + $(vecho) "AR $@" + $(Q) $(AR) cru $@ $^ + +checkdirs: $(BUILD_DIR) $(FW_BASE) + +$(BUILD_DIR): + $(Q) mkdir -p $@ + +$(FW_BASE): + $(Q) mkdir -p $@ + +flash: $(FW_FILE_1) $(FW_FILE_2) + $(ESPTOOL) --port $(ESPPORT) --baud $(ESPTOOLBAUD) write_flash $(ESPTOOLOPTS) $(FW_FILE_1_ADDR) $(FW_FILE_1) $(FW_FILE_2_ADDR) $(FW_FILE_2) + +clean: + $(Q) rm -rf $(FW_BASE) $(BUILD_BASE) + +$(foreach bdir,$(BUILD_DIR),$(eval $(call compile-objects,$(bdir)))) diff --git a/README.md b/README.md new file mode 100644 index 0000000..85401d2 --- /dev/null +++ b/README.md @@ -0,0 +1,14 @@ +# ESPerPass +A 3DS HomePass implementation for the ESP8266 programmable WiFi chip. +Inspired by [this reddit post](https://www.reddit.com/r/3DS/comments/80k0qb/homepass_for_cheap_using_an_esp8266/) +and largely based on the great work done by [Martin Ger's ESP WiFi Repeater](https://github.com/martin-ger/esp_wifi_repeater). + +## Instructions (need improvement) +1. Flash firmware. +2. Connect ESP8266 to USB and connect with terminal program. +3. Power cycle ESP8266. +3. Follow instructions in terminal program. + +## TODO +* Implement firewall rules to restrict connections to official servers. +* Implement mac address list management through console. diff --git a/driver/new_uart.c b/driver/new_uart.c new file mode 100644 index 0000000..dde2a24 --- /dev/null +++ b/driver/new_uart.c @@ -0,0 +1,471 @@ +/* + * File : uart.c + * Copyright (C) 2013 - 2016, Espressif Systems + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of version 3 of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ +#include "ets_sys.h" +#include "osapi.h" +#include "driver/uart.h" +#include "osapi.h" +#include "driver/uart_register.h" +#include "mem.h" +#include "os_type.h" + +#ifdef _ENABLE_RING_BUFFER + static ringbuf_t rxBuff; + static ringbuf_t txBuff; +#endif + +#ifdef _ENABLE_CONSOLE_INTEGRATION + uint8_t linked_to_console = 0; +#endif + +extern UartDevice UartDev; + +/* Local variables */ +static uint8 uart_recvTaskPrio = 0; + +/* Internal Functions */ +static void ICACHE_FLASH_ATTR uart_config(uint8 uart_no); +static void uart0_rx_intr_handler(void *para); + +/* Public APIs */ +void ICACHE_FLASH_ATTR UART_init(UartBautRate uart0_br, UartBautRate uart1_br, uint8 recv_task_priority); + +#define ENABLE_DEBUG + +#ifdef ENABLE_DEBUG + #define DBG + #define DBG1 os_printf + #define DBG2 os_printf +#else + #define DBG + #define DBG1 + #define DBG2 +#endif + +#if _ENABLE_CONSOLE_INTEGRATION == 1 +void ICACHE_FLASH_ATTR UART_init_console(UartBautRate uart0_br, + uint8 recv_task_priority, + ringbuf_t rxbuffer, + ringbuf_t txBuffer) +{ + /* Set the task which should receive the signals once the data is received */ + uart_recvTaskPrio = recv_task_priority; + + UartDev.baut_rate = uart0_br; + rxBuff = rxbuffer; + txBuff = txBuffer; + linked_to_console = 1; + + uart_config(UART0); + UART_SetPrintPort(UART0); + + UartDev.baut_rate = uart0_br; + uart_config(UART1); + + ETS_UART_INTR_ENABLE(); +} +#endif + +void ICACHE_FLASH_ATTR UART_init(UartBautRate uart0_br, UartBautRate uart1_br, uint8 recv_task_priority) +{ + /* Set the task which should receive the signals once the data is received */ + uart_recvTaskPrio = recv_task_priority; + + UartDev.baut_rate = uart0_br; + uart_config(UART0); + + UART_SetPrintPort(UART0); + + UartDev.baut_rate = uart1_br; + uart_config(UART1); + + ETS_UART_INTR_ENABLE(); + + #if _ENABLE_CONSOLE_INTEGRATION == 0 + #if _ENABLE_RING_BUFFER == 1 + rxBuff = ringbuf_new(RX_RING_BUFFER_SIZE); + #endif + #endif +} + + + +/****************************************************************************** + * FunctionName : uart_config + * Description : Internal used function + * UART0 used for data TX/RX, RX buffer size is 0x100, interrupt enabled + * UART1 just used for debug output + * Parameters : uart_no, use UART0 or UART1 defined ahead + * Returns : NONE +*******************************************************************************/ +LOCAL void ICACHE_FLASH_ATTR uart_config(uint8 uart_no) +{ + if (uart_no == UART1) + { + PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO2_U, FUNC_U1TXD_BK); + } + else + { + /* rcv_buff size if 0x100 */ + ETS_UART_INTR_ATTACH(uart0_rx_intr_handler, &(UartDev.rcv_buff)); + PIN_PULLUP_DIS(PERIPHS_IO_MUX_U0TXD_U); + PIN_FUNC_SELECT(PERIPHS_IO_MUX_U0TXD_U, FUNC_U0TXD); + + #if UART_HW_RTS + PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTDO_U, FUNC_U0RTS); //HW FLOW CONTROL RTS PIN + #endif + + #if UART_HW_CTS + PIN_FUNC_SELECT(PERIPHS_IO_MUX_MTCK_U, FUNC_U0CTS); //HW FLOW CONTROL CTS PIN + #endif + } + uart_div_modify(uart_no, UART_CLK_FREQ / (UartDev.baut_rate));//SET BAUDRATE + + WRITE_PERI_REG(UART_CONF0(uart_no), ((UartDev.exist_parity & UART_PARITY_EN_M) << UART_PARITY_EN_S) //SET BIT AND PARITY MODE + | ((UartDev.parity & UART_PARITY_M) <>UART_RXFIFO_CNT_S)&UART_RXFIFO_CNT; + + if (fifo_len) + { + max_unload = (fifo_len>UART_RXFIFO_CNT_S)&UART_RXFIFO_CNT; + //DBG1("RX FIFO FULL [%d]\r\n", fifo_len ); + + if (fifo_len) + { + //DBG1("Rx Fifo contains %d characters have to unload\r\n", fifo_len); + + for (index=0;index>UART_RXFIFO_CNT_S)& UART_RXFIFO_CNT); + uart_rx_intr_disable(UART0); + WRITE_PERI_REG(UART_INT_CLR(UART0), UART_RXFIFO_FULL_INT_CLR); + system_os_post(uart_recvTaskPrio, SIG_UART0, 0); + #endif + + goto end_int_handler; + } + + if(UART_RXFIFO_TOUT_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_RXFIFO_TOUT_INT_ST)) + { + /* The Time out threshold for Rx/Tx is being execeeded */ + DBG1("Rx Timeout Threshold not being met \r\n"); + uart_rx_intr_disable(UART0); + WRITE_PERI_REG(UART_INT_CLR(UART0), UART_RXFIFO_TOUT_INT_CLR); + + system_os_post(uart_recvTaskPrio, SIG_UART0, 0); + goto end_int_handler; + } + + if(UART_TXFIFO_EMPTY_INT_ST == (READ_PERI_REG(UART_INT_ST(uart_no)) & UART_TXFIFO_EMPTY_INT_ST)) + { + /* The Tx FIFO is empty, the FIFO needs to be fed with new data */ + DBG1("Tx FIFO is empty\r\n"); + CLEAR_PERI_REG_MASK(UART_INT_ENA(UART0), UART_TXFIFO_EMPTY_INT_ENA); + + #if UART_BUFF_EN + tx_start_uart_buffer(UART0); + #endif + //system_os_post(uart_recvTaskPrio, 1, 0); + WRITE_PERI_REG(UART_INT_CLR(uart_no), UART_TXFIFO_EMPTY_INT_CLR); + } + +end_int_handler: + return; +} + +/****************************************************************************** + * FunctionName : uart_tx_one_char_no_wait + * Description : uart tx a single char without waiting for fifo + * Parameters : uint8 uart - uart port + * uint8 TxChar - char to tx + * Returns : STATUS +*******************************************************************************/ +STATUS uart_tx_one_char(uint8 uart, uint8 TxChar) +{ + while (true) + { + uint32 fifo_cnt = READ_PERI_REG(UART_STATUS(uart)) & (UART_TXFIFO_CNT<> UART_TXFIFO_CNT_S & UART_TXFIFO_CNT) < 126) { + break; + } + } + + WRITE_PERI_REG(UART_FIFO(uart) , TxChar); + return OK; +} + +/****************************************************************************** + * FunctionName : uart_tx_one_char_no_wait + * Description : uart tx a single char without waiting for fifo + * Parameters : uint8 uart - uart port + * uint8 TxChar - char to tx + * Returns : STATUS +*******************************************************************************/ +STATUS uart_tx_one_char_no_wait(uint8 uart, uint8 TxChar) +{ + uint8 fifo_cnt = (( READ_PERI_REG(UART_STATUS(uart))>>UART_TXFIFO_CNT_S)& UART_TXFIFO_CNT); + if (fifo_cnt < 126) + { + WRITE_PERI_REG(UART_FIFO(uart) , TxChar); + } + return OK; +} + + +/****************************************************************************** + * FunctionName : uart0_write_char_no_wait + * Description : tx a single char without waiting for uart 0. + helper function for os_printf output to fifo or tx buffer + * Parameters : uint8 uart - uart port + * uint8 TxChar - char to tx + * Returns : STATUS +*******************************************************************************/ +LOCAL void ICACHE_FLASH_ATTR uart0_write_char_no_wait(char c) +{ +#if UART_BUFF_EN //send to uart0 fifo but do not wait + uint8 chr; + if (c == '\n'){ + chr = '\r'; + tx_buff_enq(&chr, 1); + chr = '\n'; + tx_buff_enq(&chr, 1); + }else if (c == '\r'){ + + }else{ + tx_buff_enq(&c,1); + } +#else //send to uart tx buffer + if (c == '\n') + { + uart_tx_one_char(UART0, '\r'); + uart_tx_one_char(UART0, '\n'); + + //uart_tx_one_char_no_wait(UART0, '\r'); + //uart_tx_one_char_no_wait(UART0, '\n'); + } + else + if (c == '\r') + { + uart_tx_one_char(UART0, c); + } + else + { + uart_tx_one_char(UART0, c); + //uart_tx_one_char_no_wait(UART0, c); + } +#endif +} + + +/****************************************************************************** + * FunctionName : UART_SetPrintPort + * Description : + * + * Parameters : + * Returns : NONE +*******************************************************************************/ +void ICACHE_FLASH_ATTR UART_SetPrintPort(uint8 uart_no) +{ + if(uart_no==1) + { + //os_install_putc1(uart1_write_char); + } + else + { + /*option 1: do not wait if uart fifo is full,drop current character*/ + //os_install_putc1(uart0_write_char_no_wait); + /*option 2: wait for a while if uart fifo is full*/ + //os_install_putc1(uart0_write_char); + } +} + diff --git a/easygpio/easygpio.c b/easygpio/easygpio.c new file mode 100644 index 0000000..0d386b1 --- /dev/null +++ b/easygpio/easygpio.c @@ -0,0 +1,343 @@ +/* +* easygpio.c +* +* Copyright (c) 2015, eadf (https://github.com/eadf) +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* +* * Redistributions of source code must retain the above copyright notice, +* this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of Redis nor the names of its contributors may be used +* to endorse or promote products derived from this software without +* specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +* POSSIBILITY OF SUCH DAMAGE. +*/ + +#include "easygpio.h" +#include "gpio.h" +#include "osapi.h" +#include "ets_sys.h" + +#define EASYGPIO_USE_GPIO_INPUT_GET + +static void ICACHE_FLASH_ATTR +gpio16_output_conf(void) { + WRITE_PERI_REG(PAD_XPD_DCDC_CONF, + (READ_PERI_REG(PAD_XPD_DCDC_CONF) & 0xffffffbcUL) | 0x1UL); // mux configuration for XPD_DCDC to output rtc_gpio0 + + WRITE_PERI_REG(RTC_GPIO_CONF, + (READ_PERI_REG(RTC_GPIO_CONF) & 0xfffffffeUL) | 0x0UL); //mux configuration for out enable + + WRITE_PERI_REG(RTC_GPIO_ENABLE, + (READ_PERI_REG(RTC_GPIO_ENABLE) & 0xfffffffeUL) | 0x1UL); //out enable +} + +static void ICACHE_FLASH_ATTR +gpio16_input_conf(void) { + WRITE_PERI_REG(PAD_XPD_DCDC_CONF, + (READ_PERI_REG(PAD_XPD_DCDC_CONF) & 0xffffffbcUL) | 0x1UL); // mux configuration for XPD_DCDC and rtc_gpio0 connection + + WRITE_PERI_REG(RTC_GPIO_CONF, + (READ_PERI_REG(RTC_GPIO_CONF) & 0xfffffffeUL) | 0x0UL); //mux configuration for out enable + + WRITE_PERI_REG(RTC_GPIO_ENABLE, + READ_PERI_REG(RTC_GPIO_ENABLE) & 0xfffffffeUL); //out disable +} + +/** + * Returns the number of active pins in the gpioMask. + */ +uint8_t ICACHE_FLASH_ATTR +easygpio_countBits(uint32_t gpioMask) { + + uint8_t i=0; + uint8_t numberOfPins=0; + for (i=0; i<32; i++){ + numberOfPins += (gpioMask & BIT(i))?1:0; + } + return numberOfPins; +} + +/** + * Returns the gpio name and func for a specific pin. + */ +bool ICACHE_FLASH_ATTR +easygpio_getGPIONameFunc(uint8_t gpio_pin, uint32_t *gpio_name, uint8_t *gpio_func) { + + if (gpio_pin == 6 || gpio_pin == 7 || gpio_pin == 8 || gpio_pin == 11 || gpio_pin >= 17) { + os_printf("easygpio_getGPIONameFunc Error: There is no GPIO%d, check your code\n", gpio_pin); + return false; + } + if (gpio_pin == 16) { + os_printf("easygpio_getGPIONameFunc Error: GPIO16 does not have gpio_name and gpio_func\n"); + return false; + } + switch ( gpio_pin ) { + case 0: + *gpio_func = FUNC_GPIO0; + *gpio_name = PERIPHS_IO_MUX_GPIO0_U; + return true; + case 1: + *gpio_func = FUNC_GPIO1; + *gpio_name = PERIPHS_IO_MUX_U0TXD_U; + return true; + case 2: + *gpio_func = FUNC_GPIO2; + *gpio_name = PERIPHS_IO_MUX_GPIO2_U; + return true; + case 3: + *gpio_func = FUNC_GPIO3; + *gpio_name = PERIPHS_IO_MUX_U0RXD_U; + return true; + case 4: + *gpio_func = FUNC_GPIO4; + *gpio_name = PERIPHS_IO_MUX_GPIO4_U; + return true; + case 5: + *gpio_func = FUNC_GPIO5; + *gpio_name = PERIPHS_IO_MUX_GPIO5_U; + return true; + case 9: + *gpio_func = FUNC_GPIO9; + *gpio_name = PERIPHS_IO_MUX_SD_DATA2_U; + return true; + case 10: + *gpio_func = FUNC_GPIO10; + *gpio_name = PERIPHS_IO_MUX_SD_DATA3_U; + return true; + case 12: + *gpio_func = FUNC_GPIO12; + *gpio_name = PERIPHS_IO_MUX_MTDI_U; + return true; + case 13: + *gpio_func = FUNC_GPIO13; + *gpio_name = PERIPHS_IO_MUX_MTCK_U; + return true; + case 14: + *gpio_func = FUNC_GPIO14; + *gpio_name = PERIPHS_IO_MUX_MTMS_U; + return true; + case 15: + *gpio_func = FUNC_GPIO15; + *gpio_name = PERIPHS_IO_MUX_MTDO_U; + return true; + default: + return false; + } + return true; +} + +/** + * Sets the pull up registers for a pin. + */ +static void ICACHE_FLASH_ATTR +easygpio_setupPullsByName(uint32_t gpio_name, EasyGPIO_PullStatus pullStatus) { + + if (EASYGPIO_PULLUP == pullStatus) { + PIN_PULLUP_EN(gpio_name); + } else { + PIN_PULLUP_DIS(gpio_name); + } +} + +/** + * Sets the pull registers for a pin. + */ +bool ICACHE_FLASH_ATTR +easygpio_pullMode(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus) { + uint32_t gpio_name; + uint8_t gpio_func; + + if (!easygpio_getGPIONameFunc(gpio_pin, &gpio_name, &gpio_func) ) { + return false; + } + + easygpio_setupPullsByName(gpio_name, pullStatus); + return true; +} + +/** + * Sets the 'gpio_pin' pin as a GPIO and sets the pull register for that pin. + * 'pullStatus' has no effect on output pins or GPIO16 + */ +bool ICACHE_FLASH_ATTR +easygpio_pinMode(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus, EasyGPIO_PinMode pinMode) { + uint32_t gpio_name; + uint8_t gpio_func; + + if (16==gpio_pin) { + // ignoring pull status on GPIO16 for now + if (EASYGPIO_OUTPUT == pinMode) { + gpio16_output_conf(); + } else { + gpio16_input_conf(); + } + return true; + } else if (!easygpio_getGPIONameFunc(gpio_pin, &gpio_name, &gpio_func) ) { + return false; + } + + PIN_FUNC_SELECT(gpio_name, gpio_func); + easygpio_setupPullsByName(gpio_name, pullStatus); + + if (EASYGPIO_OUTPUT != pinMode) { + GPIO_DIS_OUTPUT(GPIO_ID_PIN(gpio_pin)); + } else { + // must enable the pin or else the WRITE_PERI_REG won't work + gpio_output_set(0, 0, BIT(GPIO_ID_PIN(gpio_pin)),0); + } + return true; +} + +/** + * Sets the 'gpio_pin' pin as a GPIO and sets the interrupt to trigger on that pin. + * The 'interruptArg' is the function argument that will be sent to your interruptHandler + */ +bool ICACHE_FLASH_ATTR +easygpio_attachInterrupt(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus, void (*interruptHandler)(void *arg), void *interruptArg) { + uint32_t gpio_name; + uint8_t gpio_func; + + if (gpio_pin == 16) { + os_printf("easygpio_setupInterrupt Error: GPIO16 does not have interrupts\n"); + return false; + } + if (!easygpio_getGPIONameFunc(gpio_pin, &gpio_name, &gpio_func) ) { + return false; + } + + ETS_GPIO_INTR_ATTACH(interruptHandler, interruptArg); + ETS_GPIO_INTR_DISABLE(); + + PIN_FUNC_SELECT(gpio_name, gpio_func); + + easygpio_setupPullsByName(gpio_name, pullStatus); + + // disable output + GPIO_DIS_OUTPUT(gpio_pin); + + gpio_register_set(GPIO_PIN_ADDR(gpio_pin), GPIO_PIN_INT_TYPE_SET(GPIO_PIN_INTR_DISABLE) + | GPIO_PIN_PAD_DRIVER_SET(GPIO_PAD_DRIVER_DISABLE) + | GPIO_PIN_SOURCE_SET(GPIO_AS_PIN_SOURCE)); + + //clear gpio14 status + GPIO_REG_WRITE(GPIO_STATUS_W1TC_ADDRESS, BIT(gpio_pin)); + ETS_GPIO_INTR_ENABLE(); + + return true; +} + +/** + * Detach the interrupt handler from the 'gpio_pin' pin. + */ +bool ICACHE_FLASH_ATTR +easygpio_detachInterrupt(uint8_t gpio_pin) { + + if (gpio_pin == 16) { + os_printf("easygpio_setupInterrupt Error: GPIO16 does not have interrupts\n"); + return false; + } + + // Don't know how to detach interrupt, yet. + // Quick and dirty fix - just disable the interrupt + gpio_pin_intr_state_set(GPIO_ID_PIN(gpio_pin), GPIO_PIN_INTR_DISABLE); + return true; +} + +/** + * Uniform way of setting GPIO output value. Handles GPIO 0-16. + * + * You can not rely on that this function will switch the gpio to an output like GPIO_OUTPUT_SET does. + * Use easygpio_outputEnable() to change an input gpio to output mode. + */ +void +easygpio_outputSet(uint8_t gpio_pin, uint8_t value) { + if (16==gpio_pin) { + WRITE_PERI_REG(RTC_GPIO_OUT, + (READ_PERI_REG(RTC_GPIO_OUT) & 0xfffffffeUL) | (0x1UL & value)); + } else { +#ifdef EASYGPIO_USE_GPIO_OUTPUT_SET + GPIO_OUTPUT_SET(GPIO_ID_PIN(gpio_pin), value); +#else + if (value&1){ + WRITE_PERI_REG( PERIPHS_GPIO_BASEADDR, READ_PERI_REG(PERIPHS_GPIO_BASEADDR) | BIT(gpio_pin)); + } else { + WRITE_PERI_REG( PERIPHS_GPIO_BASEADDR, READ_PERI_REG(PERIPHS_GPIO_BASEADDR) & ~BIT(gpio_pin)); + } +#endif + } +} + +/** + * Uniform way of getting GPIO input value. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * If you know that you won't be using GPIO16 then you'd better off by just using GPIO_INPUT_GET(). + */ +uint8_t +easygpio_inputGet(uint8_t gpio_pin) { + if (16==gpio_pin) { + return (READ_PERI_REG(RTC_GPIO_IN_DATA) & 1UL); + } else { +#ifdef EASYGPIO_USE_GPIO_INPUT_GET + return GPIO_INPUT_GET(GPIO_ID_PIN(gpio_pin)); +#else + // this does *not* work, maybe GPIO_IN_ADDRESS is the wrong address + return ((GPIO_REG_READ(GPIO_IN_ADDRESS) > gpio_pin) & 1UL); +#endif + } +} + +/** + * Uniform way of turning an output GPIO pin into input mode. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * This function does the same thing as GPIO_DIS_OUTPUT, but works on GPIO16 too. + */ +void easygpio_outputDisable(uint8_t gpio_pin) { + if (16==gpio_pin) { + WRITE_PERI_REG(RTC_GPIO_ENABLE, + READ_PERI_REG(RTC_GPIO_ENABLE) & 0xfffffffeUL); //out disable + } else { + GPIO_DIS_OUTPUT(GPIO_ID_PIN(gpio_pin)); + } +} + +/** + * Uniform way of turning an input GPIO pin into output mode. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * + * This function: + * - should only be used to convert a input pin into an output pin. + * - is a little bit slower than easygpio_outputSet() so you should use that + * function to just change output value. + * - does the same thing as GPIO_OUTPUT_SET, but works on GPIO16 too. + */ +void easygpio_outputEnable(uint8_t gpio_pin, uint8_t value) { + if (16==gpio_pin) { + // write the value before flipping to output + // - so we don't flash previous value for a few ns. + WRITE_PERI_REG(RTC_GPIO_OUT, + (READ_PERI_REG(RTC_GPIO_OUT) & 0xfffffffeUL) | (0x1UL & value)); + + WRITE_PERI_REG(RTC_GPIO_ENABLE, + (READ_PERI_REG(RTC_GPIO_ENABLE) & 0xfffffffeUL) | 0x1UL); //out enable + + } else { + GPIO_OUTPUT_SET(GPIO_ID_PIN(gpio_pin), value); + } +} diff --git a/easygpio/easygpio.h b/easygpio/easygpio.h new file mode 100644 index 0000000..82c7f26 --- /dev/null +++ b/easygpio/easygpio.h @@ -0,0 +1,114 @@ +/* +* easygpio.h +* +* Copyright (c) 2015, eadf (https://github.com/eadf) +* All rights reserved. +* +* Redistribution and use in source and binary forms, with or without +* modification, are permitted provided that the following conditions are met: +* +* * Redistributions of source code must retain the above copyright notice, +* this list of conditions and the following disclaimer. +* * Redistributions in binary form must reproduce the above copyright +* notice, this list of conditions and the following disclaimer in the +* documentation and/or other materials provided with the distribution. +* * Neither the name of Redis nor the names of its contributors may be used +* to endorse or promote products derived from this software without +* specific prior written permission. +* +* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE +* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR +* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF +* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS +* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN +* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +* POSSIBILITY OF SUCH DAMAGE. +*/ + +#ifndef EASYGPIO_INCLUDE_EASYGPIO_EASYGPIO_H_ +#define EASYGPIO_INCLUDE_EASYGPIO_EASYGPIO_H_ + +#include "c_types.h" + +typedef enum { + EASYGPIO_INPUT=0, + EASYGPIO_OUTPUT=1 +} EasyGPIO_PinMode; + +typedef enum { + EASYGPIO_PULLUP=3, + EASYGPIO_NOPULL=4 +} EasyGPIO_PullStatus; + +/** + * Returns the gpio name and func for a specific pin. + */ +bool easygpio_getGPIONameFunc(uint8_t gpio_pin, uint32_t *gpio_name, uint8_t *gpio_func); + +/** + * Sets the 'gpio_pin' pin as a GPIO and sets the interrupt to trigger on that pin. + * The 'interruptArg' is the function argument that will be sent to your interruptHandler + * (this way you can several interrupts with one interruptHandler) + */ +bool easygpio_attachInterrupt(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus, void (*interruptHandler)(void *arg), void *interruptArg); + +/** + * Deatach the interrupt handler from the 'gpio_pin' pin. + */ +bool easygpio_detachInterrupt(uint8_t gpio_pin); + +/** + * Returns the number of active pins in the gpioMask. + */ +uint8_t easygpio_countBits(uint32_t gpioMask); + +/** + * Sets the 'gpio_pin' pin as a GPIO and enables/disables the pull-up on that pin. + * 'pullStatus' has no effect on output pins or GPIO16 + */ +bool easygpio_pinMode(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus, EasyGPIO_PinMode pinMode); + +/** + * Enable or disable the internal pull up for a pin. + */ +bool easygpio_pullMode(uint8_t gpio_pin, EasyGPIO_PullStatus pullStatus); + +/** + * Uniform way of getting GPIO input value. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * If you know that you won't be using GPIO16 then you'd better off by just using GPIO_INPUT_GET(). + */ +uint8_t easygpio_inputGet(uint8_t gpio_pin); + +/** + * Uniform way of setting GPIO output value. Handles GPIO 0-16. + * + * You can not rely on that this function will switch the gpio to an output like GPIO_OUTPUT_SET does. + * Use easygpio_outputEnable() to change an input gpio to output mode. + */ +void easygpio_outputSet(uint8_t gpio_pin, uint8_t value); + +/** + * Uniform way of turning an output GPIO pin into input mode. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * This function does the same thing as GPIO_DIS_OUTPUT, but works on GPIO16 too. + */ +void easygpio_outputDisable(uint8_t gpio_pin); + +/** + * Uniform way of turning an input GPIO pin into output mode. Handles GPIO 0-16. + * The pin must be initiated with easygpio_pinMode() so that the pin mux is setup as a gpio in the first place. + * + * This function: + * - should only be used to convert a input pin into an output pin. + * - is a little bit slower than easygpio_outputSet() so you should use that + * function to just change output value. + * - does the same thing as GPIO_OUTPUT_SET, but works on GPIO16 too. + */ +void easygpio_outputEnable(uint8_t gpio_pin, uint8_t value); + +#endif /* EASYGPIO_INCLUDE_EASYGPIO_EASYGPIO_H_ */ diff --git a/firewall.txt b/firewall.txt new file mode 100644 index 0000000..6d9ea93 --- /dev/null +++ b/firewall.txt @@ -0,0 +1,14 @@ +# Scrapbook of firewall rules to restrict connections only +# to official servers. + +# Clear outging rules +acl from_sta clear + +# Allow outgoing connections to specified IP +acl from_sta IP any 185.43.124.6 allow + +# Allow outgoing DNS requests +acl from_sta UDP any any any 53 allow + +# Deny everything else +acl from_sta IP any any deny diff --git a/firmware/0x00000.bin b/firmware/0x00000.bin new file mode 100644 index 0000000..a1de31c Binary files /dev/null and b/firmware/0x00000.bin differ diff --git a/firmware/0x10000.bin b/firmware/0x10000.bin new file mode 100644 index 0000000..ccf5807 Binary files /dev/null and b/firmware/0x10000.bin differ diff --git a/include/driver/uart.h b/include/driver/uart.h new file mode 100644 index 0000000..b9bf4ed --- /dev/null +++ b/include/driver/uart.h @@ -0,0 +1,233 @@ +/* + * File : uart.h + * Copyright (C) 2013 - 2016, Espressif Systems + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of version 3 of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ +#ifndef UART_APP_H +#define UART_APP_H + +#include "uart_register.h" +#include "eagle_soc.h" +#include "c_types.h" + +#define UART_TX_BUFFER_SIZE 256 //Ring buffer length of tx buffer +#define UART_RX_BUFFER_SIZE 256 //Ring buffer length of rx buffer + +#define UART_BUFF_EN 0 //use uart buffer , FOR UART0 +#define UART_SELFTEST 0 //set 1:enable the loop test demo for uart buffer, FOR UART0 + +#define UART_HW_RTS 0 //set 1: enable uart hw flow control RTS, PIN MTDO, FOR UART0 +#define UART_HW_CTS 0 //set1: enable uart hw flow contrl CTS , PIN MTCK, FOR UART0 + +#define _ENABLE_CONSOLE_INTEGRATION 1 +#define _ENABLE_RING_BUFFER 1 + +#ifdef _ENABLE_RING_BUFFER + #include "ringbuf.h" + #define RX_RING_BUFFER_SIZE 250 +#endif + + + +#define UART0 0 +#define UART1 1 + + +typedef enum { + FIVE_BITS = 0x0, + SIX_BITS = 0x1, + SEVEN_BITS = 0x2, + EIGHT_BITS = 0x3 +} UartBitsNum4Char; + +typedef enum { + ONE_STOP_BIT = 0x1, + ONE_HALF_STOP_BIT = 0x2, + TWO_STOP_BIT = 0x3 +} UartStopBitsNum; + +typedef enum { + NONE_BITS = 0x2, + ODD_BITS = 1, + EVEN_BITS = 0 +} UartParityMode; + +typedef enum { + STICK_PARITY_DIS = 0, + STICK_PARITY_EN = 1 +} UartExistParity; + +typedef enum { + UART_None_Inverse = 0x0, + UART_Rxd_Inverse = UART_RXD_INV, + UART_CTS_Inverse = UART_CTS_INV, + UART_Txd_Inverse = UART_TXD_INV, + UART_RTS_Inverse = UART_RTS_INV, +} UART_LineLevelInverse; + + +typedef enum { + BIT_RATE_300 = 300, + BIT_RATE_600 = 600, + BIT_RATE_1200 = 1200, + BIT_RATE_2400 = 2400, + BIT_RATE_4800 = 4800, + BIT_RATE_9600 = 9600, + BIT_RATE_19200 = 19200, + BIT_RATE_38400 = 38400, + BIT_RATE_57600 = 57600, + BIT_RATE_74880 = 74880, + BIT_RATE_115200 = 115200, + BIT_RATE_230400 = 230400, + BIT_RATE_460800 = 460800, + BIT_RATE_921600 = 921600, + BIT_RATE_1843200 = 1843200, + BIT_RATE_3686400 = 3686400, +} UartBautRate; + +typedef enum { + NONE_CTRL, + HARDWARE_CTRL, + XON_XOFF_CTRL +} UartFlowCtrl; + +typedef enum { + USART_HardwareFlowControl_None = 0x0, + USART_HardwareFlowControl_RTS = 0x1, + USART_HardwareFlowControl_CTS = 0x2, + USART_HardwareFlowControl_CTS_RTS = 0x3 +} UART_HwFlowCtrl; + +typedef enum { + EMPTY, + UNDER_WRITE, + WRITE_OVER +} RcvMsgBuffState; + +typedef struct { + uint32 RcvBuffSize; + uint8 *pRcvMsgBuff; + uint8 *pWritePos; + uint8 *pReadPos; + uint8 TrigLvl; //JLU: may need to pad + RcvMsgBuffState BuffState; +} RcvMsgBuff; + +typedef struct { + uint32 TrxBuffSize; + uint8 *pTrxBuff; +} TrxMsgBuff; + +typedef enum { + BAUD_RATE_DET, + WAIT_SYNC_FRM, + SRCH_MSG_HEAD, + RCV_MSG_BODY, + RCV_ESC_CHAR, +} RcvMsgState; + +typedef struct { + UartBautRate baut_rate; + UartBitsNum4Char data_bits; + UartExistParity exist_parity; + UartParityMode parity; + UartStopBitsNum stop_bits; + UartFlowCtrl flow_ctrl; + RcvMsgBuff rcv_buff; + TrxMsgBuff trx_buff; + RcvMsgState rcv_state; + int received; + int buff_uart_no; //indicate which uart use tx/rx buffer +} UartDevice; + +void uart_init(UartBautRate uart0_br, UartBautRate uart1_br); +void uart0_sendStr(const char *str); + + +/////////////////////////////////////// +#define UART_FIFO_LEN 128 //define the tx fifo length +#define UART_TX_EMPTY_THRESH_VAL 0x10 + + + struct UartBuffer{ + uint32 UartBuffSize; + uint8 *pUartBuff; + uint8 *pInPos; + uint8 *pOutPos; + STATUS BuffState; + uint16 Space; //remanent space of the buffer + uint8 TcpControl; + struct UartBuffer * nextBuff; +}; + +struct UartRxBuff{ + uint32 UartRxBuffSize; + uint8 *pUartRxBuff; + uint8 *pWritePos; + uint8 *pReadPos; + STATUS RxBuffState; + uint32 Space; //remanent space of the buffer +} ; + +typedef enum { + RUN = 0, + BLOCK = 1, +} TCPState; + +//void ICACHE_FLASH_ATTR uart_test_rx(); +STATUS uart_tx_one_char(uint8 uart, uint8 TxChar); +STATUS uart_tx_one_char_no_wait(uint8 uart, uint8 TxChar); +void uart1_sendStr_no_wait(const char *str); +struct UartBuffer* Uart_Buf_Init(); + + +#if UART_BUFF_EN +LOCAL void Uart_Buf_Cpy(struct UartBuffer* pCur, char* pdata , uint16 data_len); +void uart_buf_free(struct UartBuffer* pBuff); +void tx_buff_enq(char* pdata, uint16 data_len ); +LOCAL void tx_fifo_insert(struct UartBuffer* pTxBuff, uint8 data_len, uint8 uart_no); +void tx_start_uart_buffer(uint8 uart_no); +uint16 rx_buff_deq(char* pdata, uint16 data_len ); +void Uart_rx_buff_enq(); +#endif +void uart_rx_intr_enable(uint8 uart_no); +void uart_rx_intr_disable(uint8 uart_no); +void uart0_tx_buffer(uint8 *buf, uint16 len); + +//============================================== +#define FUNC_UART0_CTS 4 +#define FUNC_U0CTS 4 +#define FUNC_U1TXD_BK 2 +#define UART_LINE_INV_MASK (0x3f<<19) +void UART_SetWordLength(uint8 uart_no, UartBitsNum4Char len); +void UART_SetStopBits(uint8 uart_no, UartStopBitsNum bit_num); +void UART_SetLineInverse(uint8 uart_no, UART_LineLevelInverse inverse_mask); +void UART_SetParity(uint8 uart_no, UartParityMode Parity_mode); +void UART_SetBaudrate(uint8 uart_no,uint32 baud_rate); +void UART_SetFlowCtrl(uint8 uart_no,UART_HwFlowCtrl flow_ctrl,uint8 rx_thresh); +void UART_WaitTxFifoEmpty(uint8 uart_no , uint32 time_out_us); //do not use if tx flow control enabled +void UART_ResetFifo(uint8 uart_no); +void UART_ClearIntrStatus(uint8 uart_no,uint32 clr_mask); +void UART_SetIntrEna(uint8 uart_no,uint32 ena_mask); +void UART_SetPrintPort(uint8 uart_no); +bool UART_CheckOutputFinished(uint8 uart_no, uint32 time_out_us); +//============================================== + +void UART_init_console(UartBautRate uart0_br, + uint8 recv_task_priority, + ringbuf_t rxbuffer, + ringbuf_t txBuffer); + +#endif + diff --git a/include/driver/uart_register.h b/include/driver/uart_register.h new file mode 100644 index 0000000..05f6cea --- /dev/null +++ b/include/driver/uart_register.h @@ -0,0 +1,156 @@ +/* + * File : uart_register.h + * Copyright (C) 2013 - 2016, Espressif Systems + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of version 3 of the GNU General Public License as + * published by the Free Software Foundation. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program. If not, see . + */ +/* + * Copyright (c) 2010 - 2011 Espressif System + * + */ + +#ifndef UART_REGISTER_H_ +#define UART_REGISTER_H_ + +#define REG_UART_BASE(i) (0x60000000 + (i)*0xf00) +//version value:32'h062000 + +#define UART_FIFO(i) (REG_UART_BASE(i) + 0x0) +#define UART_RXFIFO_RD_BYTE 0x000000FF +#define UART_RXFIFO_RD_BYTE_S 0 + +#define UART_INT_RAW(i) (REG_UART_BASE(i) + 0x4) +#define UART_RXFIFO_TOUT_INT_RAW (BIT(8)) +#define UART_BRK_DET_INT_RAW (BIT(7)) +#define UART_CTS_CHG_INT_RAW (BIT(6)) +#define UART_DSR_CHG_INT_RAW (BIT(5)) +#define UART_RXFIFO_OVF_INT_RAW (BIT(4)) +#define UART_FRM_ERR_INT_RAW (BIT(3)) +#define UART_PARITY_ERR_INT_RAW (BIT(2)) +#define UART_TXFIFO_EMPTY_INT_RAW (BIT(1)) +#define UART_RXFIFO_FULL_INT_RAW (BIT(0)) + +#define UART_INT_ST(i) (REG_UART_BASE(i) + 0x8) +#define UART_RXFIFO_TOUT_INT_ST (BIT(8)) +#define UART_BRK_DET_INT_ST (BIT(7)) +#define UART_CTS_CHG_INT_ST (BIT(6)) +#define UART_DSR_CHG_INT_ST (BIT(5)) +#define UART_RXFIFO_OVF_INT_ST (BIT(4)) +#define UART_FRM_ERR_INT_ST (BIT(3)) +#define UART_PARITY_ERR_INT_ST (BIT(2)) +#define UART_TXFIFO_EMPTY_INT_ST (BIT(1)) +#define UART_RXFIFO_FULL_INT_ST (BIT(0)) + +#define UART_INT_ENA(i) (REG_UART_BASE(i) + 0xC) +#define UART_RXFIFO_TOUT_INT_ENA (BIT(8)) +#define UART_BRK_DET_INT_ENA (BIT(7)) +#define UART_CTS_CHG_INT_ENA (BIT(6)) +#define UART_DSR_CHG_INT_ENA (BIT(5)) +#define UART_RXFIFO_OVF_INT_ENA (BIT(4)) +#define UART_FRM_ERR_INT_ENA (BIT(3)) +#define UART_PARITY_ERR_INT_ENA (BIT(2)) +#define UART_TXFIFO_EMPTY_INT_ENA (BIT(1)) +#define UART_RXFIFO_FULL_INT_ENA (BIT(0)) + +#define UART_INT_CLR(i) (REG_UART_BASE(i) + 0x10) +#define UART_RXFIFO_TOUT_INT_CLR (BIT(8)) +#define UART_BRK_DET_INT_CLR (BIT(7)) +#define UART_CTS_CHG_INT_CLR (BIT(6)) +#define UART_DSR_CHG_INT_CLR (BIT(5)) +#define UART_RXFIFO_OVF_INT_CLR (BIT(4)) +#define UART_FRM_ERR_INT_CLR (BIT(3)) +#define UART_PARITY_ERR_INT_CLR (BIT(2)) +#define UART_TXFIFO_EMPTY_INT_CLR (BIT(1)) +#define UART_RXFIFO_FULL_INT_CLR (BIT(0)) + +#define UART_CLKDIV(i) (REG_UART_BASE(i) + 0x14) +#define UART_CLKDIV_CNT 0x000FFFFF +#define UART_CLKDIV_S 0 + +#define UART_AUTOBAUD(i) (REG_UART_BASE(i) + 0x18) +#define UART_GLITCH_FILT 0x000000FF +#define UART_GLITCH_FILT_S 8 +#define UART_AUTOBAUD_EN (BIT(0)) + +#define UART_STATUS(i) (REG_UART_BASE(i) + 0x1C) +#define UART_TXD (BIT(31)) +#define UART_RTSN (BIT(30)) +#define UART_DTRN (BIT(29)) +#define UART_TXFIFO_CNT 0x000000FF +#define UART_TXFIFO_CNT_S 16 +#define UART_RXD (BIT(15)) +#define UART_CTSN (BIT(14)) +#define UART_DSRN (BIT(13)) +#define UART_RXFIFO_CNT 0x000000FF +#define UART_RXFIFO_CNT_S 0 + +#define UART_CONF0(i) (REG_UART_BASE(i) + 0x20) +#define UART_DTR_INV (BIT(24)) +#define UART_RTS_INV (BIT(23)) +#define UART_TXD_INV (BIT(22)) +#define UART_DSR_INV (BIT(21)) +#define UART_CTS_INV (BIT(20)) +#define UART_RXD_INV (BIT(19)) +#define UART_TXFIFO_RST (BIT(18)) +#define UART_RXFIFO_RST (BIT(17)) +#define UART_IRDA_EN (BIT(16)) +#define UART_TX_FLOW_EN (BIT(15)) +#define UART_LOOPBACK (BIT(14)) +#define UART_IRDA_RX_INV (BIT(13)) +#define UART_IRDA_TX_INV (BIT(12)) +#define UART_IRDA_WCTL (BIT(11)) +#define UART_IRDA_TX_EN (BIT(10)) +#define UART_IRDA_DPLX (BIT(9)) +#define UART_TXD_BRK (BIT(8)) +#define UART_SW_DTR (BIT(7)) +#define UART_SW_RTS (BIT(6)) +#define UART_STOP_BIT_NUM 0x00000003 +#define UART_STOP_BIT_NUM_S 4 +#define UART_BIT_NUM 0x00000003 +#define UART_BIT_NUM_S 2 +#define UART_PARITY_EN (BIT(1)) +#define UART_PARITY_EN_M 0x00000001 +#define UART_PARITY_EN_S 1 +#define UART_PARITY (BIT(0)) +#define UART_PARITY_M 0x00000001 +#define UART_PARITY_S 0 + +#define UART_CONF1(i) (REG_UART_BASE(i) + 0x24) +#define UART_RX_TOUT_EN (BIT(31)) +#define UART_RX_TOUT_THRHD 0x0000007F +#define UART_RX_TOUT_THRHD_S 24 +#define UART_RX_FLOW_EN (BIT(23)) +#define UART_RX_FLOW_THRHD 0x0000007F +#define UART_RX_FLOW_THRHD_S 16 +#define UART_TXFIFO_EMPTY_THRHD 0x0000007F +#define UART_TXFIFO_EMPTY_THRHD_S 8 +#define UART_RXFIFO_FULL_THRHD 0x0000007F +#define UART_RXFIFO_FULL_THRHD_S 0 + +#define UART_LOWPULSE(i) (REG_UART_BASE(i) + 0x28) +#define UART_LOWPULSE_MIN_CNT 0x000FFFFF +#define UART_LOWPULSE_MIN_CNT_S 0 + +#define UART_HIGHPULSE(i) (REG_UART_BASE(i) + 0x2C) +#define UART_HIGHPULSE_MIN_CNT 0x000FFFFF +#define UART_HIGHPULSE_MIN_CNT_S 0 + +#define UART_PULSE_NUM(i) (REG_UART_BASE(i) + 0x30) +#define UART_PULSE_NUM_CNT 0x0003FF +#define UART_PULSE_NUM_CNT_S 0 + +#define UART_DATE(i) (REG_UART_BASE(i) + 0x78) +#define UART_ID(i) (REG_UART_BASE(i) + 0x7C) + +#endif // UART_REGISTER_H_INCLUDED + diff --git a/include/lwip/app/dhcpserver.h b/include/lwip/app/dhcpserver.h new file mode 100644 index 0000000..a11f137 --- /dev/null +++ b/include/lwip/app/dhcpserver.h @@ -0,0 +1,106 @@ +#ifndef __DHCPS_H__ +#define __DHCPS_H__ + +#define USE_DNS + +typedef struct dhcps_state{ + sint16_t state; +} dhcps_state; + +// ����dhcpclient�Զ����һ��DHCP msg�ṹ�� +typedef struct dhcps_msg { + uint8_t op, htype, hlen, hops; + uint8_t xid[4]; + uint16_t secs, flags; + uint8_t ciaddr[4]; + uint8_t yiaddr[4]; + uint8_t siaddr[4]; + uint8_t giaddr[4]; + uint8_t chaddr[16]; + uint8_t sname[64]; + uint8_t file[128]; + uint8_t options[312]; +}dhcps_msg; + +#ifndef LWIP_OPEN_SRC +struct dhcps_lease { + bool enable; + struct ip_addr start_ip; + struct ip_addr end_ip; +}; + +enum dhcps_offer_option{ + OFFER_START = 0x00, + OFFER_ROUTER = 0x01, + OFFER_END +}; +#endif + +struct dhcps_pool{ + struct ip_addr ip; + uint8 mac[6]; + uint32 lease_timer; +}; + +typedef struct _list_node{ + void *pnode; + struct _list_node *pnext; +}list_node; + +extern uint32 dhcps_lease_time; +#define DHCPS_LEASE_TIMER dhcps_lease_time //0x05A0 +#define DHCPS_MAX_LEASE 0x64 +#define BOOTP_BROADCAST 0x8000 + +#define DHCP_REQUEST 1 +#define DHCP_REPLY 2 +#define DHCP_HTYPE_ETHERNET 1 +#define DHCP_HLEN_ETHERNET 6 +#define DHCP_MSG_LEN 236 + +#define DHCPS_SERVER_PORT 67 +#define DHCPS_CLIENT_PORT 68 + +#define DHCPDISCOVER 1 +#define DHCPOFFER 2 +#define DHCPREQUEST 3 +#define DHCPDECLINE 4 +#define DHCPACK 5 +#define DHCPNAK 6 +#define DHCPRELEASE 7 + +#define DHCP_OPTION_SUBNET_MASK 1 +#define DHCP_OPTION_ROUTER 3 +#define DHCP_OPTION_DNS_SERVER 6 +#define DHCP_OPTION_REQ_IPADDR 50 +#define DHCP_OPTION_LEASE_TIME 51 +#define DHCP_OPTION_MSG_TYPE 53 +#define DHCP_OPTION_SERVER_ID 54 +#define DHCP_OPTION_INTERFACE_MTU 26 +#define DHCP_OPTION_PERFORM_ROUTER_DISCOVERY 31 +#define DHCP_OPTION_BROADCAST_ADDRESS 28 +#define DHCP_OPTION_REQ_LIST 55 +#define DHCP_OPTION_END 255 + +//#define USE_CLASS_B_NET 1 +#define DHCPS_DEBUG 0 +#define MAX_STATION_NUM 8 + +#define DHCPS_STATE_OFFER 1 +#define DHCPS_STATE_DECLINE 2 +#define DHCPS_STATE_ACK 3 +#define DHCPS_STATE_NAK 4 +#define DHCPS_STATE_IDLE 5 +#define DHCPS_STATE_RELEASE 6 + +#define dhcps_router_enabled(offer) ((offer & OFFER_ROUTER) != 0) + +void dhcps_start(struct ip_info *info); +void dhcps_stop(void); + +void dhcps_set_DNS(struct ip_addr *dns_ip) ICACHE_FLASH_ATTR; +struct dhcps_pool *dhcps_get_mapping(uint16_t no) ICACHE_FLASH_ATTR; +void dhcps_set_mapping(struct ip_addr *addr, uint8 *mac, uint32 lease_time) ICACHE_FLASH_ATTR; + +#endif + diff --git a/include/lwip/lwip_napt.h b/include/lwip/lwip_napt.h new file mode 100644 index 0000000..6784ec9 --- /dev/null +++ b/include/lwip/lwip_napt.h @@ -0,0 +1,115 @@ +#ifndef __LWIP_NAPT_H__ +#define __LWIP_NAPT_H__ + +#include "lwip/opt.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#if IP_FORWARD +#if IP_NAPT + +/* Default size of the tables used for NAPT */ +#define IP_NAPT_MAX 512 +#define IP_PORTMAP_MAX 32 + +/* Timeouts in sec for the various protocol types */ +#define IP_NAPT_TIMEOUT_MS_TCP (30*60*1000) +#define IP_NAPT_TIMEOUT_MS_TCP_DISCON (20*1000) +#define IP_NAPT_TIMEOUT_MS_UDP (2*1000) +#define IP_NAPT_TIMEOUT_MS_ICMP (2*1000) + +#define IP_NAPT_PORT_RANGE_START 49152 +#define IP_NAPT_PORT_RANGE_END 61439 + +struct napt_table { + u32_t last; + u32_t src; + u32_t dest; + u16_t sport; + u16_t dport; + u16_t mport; + u8_t proto; + u8_t fin1 : 1; + u8_t fin2 : 1; + u8_t finack1 : 1; + u8_t finack2 : 1; + u8_t synack : 1; + u8_t rst : 1; + u16_t next, prev; +}; + +struct portmap_table { + u32_t maddr; + u32_t daddr; + u16_t mport; + u16_t dport; + u8_t proto; + u8 valid; +}; + +extern struct portmap_table *ip_portmap_table; + +/** + * Allocates and initializes the NAPT tables. + * + * @param max_nat max number of enties in the NAPT table (use IP_NAPT_MAX if in doubt) + * @param max_portmap max number of enties in the NAPT table (use IP_PORTMAP_MAX if in doubt) + */ +void ICACHE_FLASH_ATTR +ip_napt_init(uint16_t max_nat, uint8_t max_portmap); + + +/** + * Enable/Disable NAPT for a specified interface. + * + * @param addr ip address of the interface + * @param enable non-zero to enable NAPT, or 0 to disable. + */ +void ICACHE_FLASH_ATTR +ip_napt_enable(u32_t addr, int enable); + + +/** + * Enable/Disable NAPT for a specified interface. + * + * @param netif number of the interface + * @param enable non-zero to enable NAPT, or 0 to disable. + */ +void ICACHE_FLASH_ATTR +ip_napt_enable_no(u8_t number, int enable); + + +/** + * Register port mapping on the external interface to internal interface. + * When the same port mapping is registered again, the old mapping is overwritten. + * In this implementation, only 1 unique port mapping can be defined for each target address/port. + * + * @param proto target protocol + * @param maddr ip address of the external interface + * @param mport mapped port on the external interface, in host byte order. + * @param daddr destination ip address + * @param dport destination port, in host byte order. + */ +u8_t ICACHE_FLASH_ATTR +ip_portmap_add(u8_t proto, u32_t maddr, u16_t mport, u32_t daddr, u16_t dport); + + +/** + * Unregister port mapping on the external interface to internal interface. + * + * @param proto target protocol + * @param maddr ip address of the external interface + */ +u8_t ICACHE_FLASH_ATTR +ip_portmap_remove(u8_t proto, u16_t mport); + +#endif /* IP_NAPT */ +#endif /* IP_FORWARD */ + +#ifdef __cplusplus +} +#endif + +#endif /* __LWIP_NAPT_H__ */ diff --git a/include/lwip/netif.h b/include/lwip/netif.h new file mode 100644 index 0000000..c6b85e5 --- /dev/null +++ b/include/lwip/netif.h @@ -0,0 +1,323 @@ +/* + * Copyright (c) 2001-2004 Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT + * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT + * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY + * OF SUCH DAMAGE. + * + * This file is part of the lwIP TCP/IP stack. + * + * Author: Adam Dunkels + * + */ +#ifndef __LWIP_NETIF_H__ +#define __LWIP_NETIF_H__ + +#include "lwip/opt.h" + +#define ENABLE_LOOPBACK (LWIP_NETIF_LOOPBACK || LWIP_HAVE_LOOPIF) + +#include "lwip/err.h" + +#include "lwip/ip_addr.h" + +#include "lwip/def.h" +#include "lwip/pbuf.h" +#if LWIP_DHCP +struct dhcp; +#endif +#if LWIP_AUTOIP +struct autoip; +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/* Throughout this file, IP addresses are expected to be in + * the same byte order as in IP_PCB. */ + +/** must be the maximum of all used hardware address lengths + across all types of interfaces in use */ +#define NETIF_MAX_HWADDR_LEN 6U + +/** Whether the network interface is 'up'. This is + * a software flag used to control whether this network + * interface is enabled and processes traffic. + * It is set by the startup code (for static IP configuration) or + * by dhcp/autoip when an address has been assigned. + */ +#define NETIF_FLAG_UP 0x01U +/** If set, the netif has broadcast capability. + * Set by the netif driver in its init function. */ +#define NETIF_FLAG_BROADCAST 0x02U +/** If set, the netif is one end of a point-to-point connection. + * Set by the netif driver in its init function. */ +#define NETIF_FLAG_POINTTOPOINT 0x04U +/** If set, the interface is configured using DHCP. + * Set by the DHCP code when starting or stopping DHCP. */ +#define NETIF_FLAG_DHCP 0x08U +/** If set, the interface has an active link + * (set by the network interface driver). + * Either set by the netif driver in its init function (if the link + * is up at that time) or at a later point once the link comes up + * (if link detection is supported by the hardware). */ +#define NETIF_FLAG_LINK_UP 0x10U +/** If set, the netif is an ethernet device using ARP. + * Set by the netif driver in its init function. + * Used to check input packet types and use of DHCP. */ +#define NETIF_FLAG_ETHARP 0x20U +/** If set, the netif is an ethernet device. It might not use + * ARP or TCP/IP if it is used for PPPoE only. + */ +#define NETIF_FLAG_ETHERNET 0x40U +/** If set, the netif has IGMP capability. + * Set by the netif driver in its init function. */ +#define NETIF_FLAG_IGMP 0x80U + +/** Function prototype for netif init functions. Set up flags and output/linkoutput + * callback functions in this function. + * + * @param netif The netif to initialize + */ +typedef err_t (*netif_init_fn)(struct netif *netif); +/** Function prototype for netif->input functions. This function is saved as 'input' + * callback function in the netif struct. Call it when a packet has been received. + * + * @param p The received packet, copied into a pbuf + * @param inp The netif which received the packet + */ +typedef err_t (*netif_input_fn)(struct pbuf *p, struct netif *inp); +/** Function prototype for netif->output functions. Called by lwIP when a packet + * shall be sent. For ethernet netif, set this to 'etharp_output' and set + * 'linkoutput'. + * + * @param netif The netif which shall send a packet + * @param p The packet to send (p->payload points to IP header) + * @param ipaddr The IP address to which the packet shall be sent + */ +typedef err_t (*netif_output_fn)(struct netif *netif, struct pbuf *p, + ip_addr_t *ipaddr); +/** Function prototype for netif->linkoutput functions. Only used for ethernet + * netifs. This function is called by ARP when a packet shall be sent. + * + * @param netif The netif which shall send a packet + * @param p The packet to send (raw ethernet packet) + */ +typedef err_t (*netif_linkoutput_fn)(struct netif *netif, struct pbuf *p); +/** Function prototype for netif status- or link-callback functions. */ +typedef void (*netif_status_callback_fn)(struct netif *netif); +/** Function prototype for netif igmp_mac_filter functions */ +typedef err_t (*netif_igmp_mac_filter_fn)(struct netif *netif, + ip_addr_t *group, u8_t action); + +/*add DHCP event processing by LiuHan*/ +typedef void (*dhcp_event_fn)(void); + +/** Generic data structure used for all lwIP network interfaces. + * The following fields should be filled in by the initialization + * function for the device driver: hwaddr_len, hwaddr[], mtu, flags */ +struct netif { + /** pointer to next in linked list */ + struct netif *next; + + /** IP address configuration in network byte order */ + ip_addr_t ip_addr; + ip_addr_t netmask; + ip_addr_t gw; + + /** This function is called by the network device driver + * to pass a packet up the TCP/IP stack. ÏòIP²ãÊäÈëÊý¾Ý°ü*/ + netif_input_fn input; + /** This function is called by the IP module when it wants + * to send a packet on the interface. This function typically + * first resolves the hardware address, then sends the packet. ·¢ËÍIPÊý¾Ý°ü*/ + netif_output_fn output; + /** This function is called by the ARP module when it wants + * to send a packet on the interface. This function outputs + * the pbuf as-is on the link medium. µ×²ãÊý¾Ý°ü·¢ËÍ*/ + netif_linkoutput_fn linkoutput; +#if LWIP_NETIF_STATUS_CALLBACK + /** This function is called when the netif state is set to up or down + */ + netif_status_callback_fn status_callback; +#endif /* LWIP_NETIF_STATUS_CALLBACK */ +#if LWIP_NETIF_LINK_CALLBACK + /** This function is called when the netif link is set to up or down + */ + netif_status_callback_fn link_callback; +#endif /* LWIP_NETIF_LINK_CALLBACK */ + /** This field can be set by the device driver and could point + * to state information for the device. ×ÔÓÉÉèÖÃ×ֶΣ¬±ÈÈçÖ¸Ïòµ×²ãÉ豸Ïà¹ØÐÅÏ¢*/ + void *state; +#if LWIP_DHCP + /** the DHCP client state information for this netif */ + struct dhcp *dhcp; + struct udp_pcb *dhcps_pcb; //dhcps + dhcp_event_fn dhcp_event; +#endif /* LWIP_DHCP */ +#if LWIP_AUTOIP + /** the AutoIP client state information for this netif */ + struct autoip *autoip; +#endif +#if LWIP_NETIF_HOSTNAME + /* the hostname for this netif, NULL is a valid value */ + char* hostname; +#endif /* LWIP_NETIF_HOSTNAME */ + /** maximum transfer unit (in bytes) ¸Ã½Ó¿ÚÔÊÐíµÄ×î´óÊý¾Ý°ü³¤¶È£¬¶àÊÇ1500*/ + u16_t mtu; + /** number of bytes used in hwaddr¸Ã½Ó¿ÚÎïÀíµØÖ·³¤¶È */ + u8_t hwaddr_len; + /** link level hardware address of this interface ¸Ã½Ó¿ÚÎïÀíµØÖ·*/ + u8_t hwaddr[NETIF_MAX_HWADDR_LEN]; + /** flags (see NETIF_FLAG_ above) ¸Ã½Ó¿Ú״̬¡¢ÊôÐÔ×Ö¶Î*/ + u8_t flags; + /** descriptive abbreviation ¸Ã½Ó¿ÚµÄÃû×Ö*/ + char name[2]; + /** number of this interface ¸Ã½Ó¿ÚµÄ±àºÅ*/ + u8_t num; +#if LWIP_SNMP + /** link type (from "snmp_ifType" enum from snmp.h) */ + u8_t link_type; + /** (estimate) link speed */ + u32_t link_speed; + /** timestamp at last change made (up/down) */ + u32_t ts; + /** counters */ + u32_t ifinoctets; + u32_t ifinucastpkts; + u32_t ifinnucastpkts; + u32_t ifindiscards; + u32_t ifoutoctets; + u32_t ifoutucastpkts; + u32_t ifoutnucastpkts; + u32_t ifoutdiscards; +#endif /* LWIP_SNMP */ +#if LWIP_IGMP + /** This function could be called to add or delete a entry in the multicast + filter table of the ethernet MAC.*/ + netif_igmp_mac_filter_fn igmp_mac_filter; +#endif /* LWIP_IGMP */ +#if LWIP_NETIF_HWADDRHINT + u8_t *addr_hint; +#endif /* LWIP_NETIF_HWADDRHINT */ +#if ENABLE_LOOPBACK + /* List of packets to be queued for ourselves. Ö¸Ïò·¢Ë͸ø×Ô¼ºµÄÊý¾Ý°üµÄpbuf*/ + struct pbuf *loop_first;//µÚÒ»¸ö + struct pbuf *loop_last;//×îºóÒ»¸ö +#if LWIP_LOOPBACK_MAX_PBUFS + u16_t loop_cnt_current; +#endif /* LWIP_LOOPBACK_MAX_PBUFS */ +#endif /* ENABLE_LOOPBACK */ +#if IP_NAPT + u8_t napt; +#endif +}; + +#if LWIP_SNMP +#define NETIF_INIT_SNMP(netif, type, speed) \ + /* use "snmp_ifType" enum from snmp.h for "type", snmp_ifType_ethernet_csmacd by example */ \ + (netif)->link_type = (type); \ + /* your link speed here (units: bits per second) */ \ + (netif)->link_speed = (speed); \ + (netif)->ts = 0; \ + (netif)->ifinoctets = 0; \ + (netif)->ifinucastpkts = 0; \ + (netif)->ifinnucastpkts = 0; \ + (netif)->ifindiscards = 0; \ + (netif)->ifoutoctets = 0; \ + (netif)->ifoutucastpkts = 0; \ + (netif)->ifoutnucastpkts = 0; \ + (netif)->ifoutdiscards = 0 +#else /* LWIP_SNMP */ +#define NETIF_INIT_SNMP(netif, type, speed) +#endif /* LWIP_SNMP */ + + +/** The list of network interfaces. */ +extern struct netif *netif_list; +/** The default network interface. */ +extern struct netif *netif_default; + +void netif_init(void)ICACHE_FLASH_ATTR; + +struct netif *netif_add(struct netif *netif, ip_addr_t *ipaddr, ip_addr_t *netmask, + ip_addr_t *gw, void *state, netif_init_fn init, netif_input_fn input)ICACHE_FLASH_ATTR; + +void +netif_set_addr(struct netif *netif, ip_addr_t *ipaddr, ip_addr_t *netmask, + ip_addr_t *gw)ICACHE_FLASH_ATTR; +void netif_remove(struct netif * netif)ICACHE_FLASH_ATTR; + +/* Returns a network interface given its name. The name is of the form + "et0", where the first two letters are the "name" field in the + netif structure, and the digit is in the num field in the same + structure. */ +struct netif *netif_find(char *name)ICACHE_FLASH_ATTR; + +void netif_set_default(struct netif *netif)ICACHE_FLASH_ATTR; + +void netif_set_ipaddr(struct netif *netif, ip_addr_t *ipaddr)ICACHE_FLASH_ATTR; +void netif_set_netmask(struct netif *netif, ip_addr_t *netmask)ICACHE_FLASH_ATTR; +void netif_set_gw(struct netif *netif, ip_addr_t *gw)ICACHE_FLASH_ATTR; + +void netif_set_up(struct netif *netif)ICACHE_FLASH_ATTR; +void netif_set_down(struct netif *netif)ICACHE_FLASH_ATTR; +/** Ask if an interface is up */ +#define netif_is_up(netif) (((netif)->flags & NETIF_FLAG_UP) ? (u8_t)1 : (u8_t)0) + +#if LWIP_NETIF_STATUS_CALLBACK +void netif_set_status_callback(struct netif *netif, netif_status_callback_fn status_callback)ICACHE_FLASH_ATTR; +#endif /* LWIP_NETIF_STATUS_CALLBACK */ + +void netif_set_link_up(struct netif *netif)ICACHE_FLASH_ATTR; +void netif_set_link_down(struct netif *netif)ICACHE_FLASH_ATTR; +/** Ask if a link is up */ +#define netif_is_link_up(netif) (((netif)->flags & NETIF_FLAG_LINK_UP) ? (u8_t)1 : (u8_t)0) + +#if LWIP_NETIF_LINK_CALLBACK +void netif_set_link_callback(struct netif *netif, netif_status_callback_fn link_callback)ICACHE_FLASH_ATTR; +#endif /* LWIP_NETIF_LINK_CALLBACK */ + +#if LWIP_NETIF_HOSTNAME +#define netif_set_hostname(netif, name) do { if((netif) != NULL) { (netif)->hostname = name; }}while(0) +#define netif_get_hostname(netif) (((netif) != NULL) ? ((netif)->hostname) : NULL) +#endif /* LWIP_NETIF_HOSTNAME */ + +#if LWIP_IGMP +#define netif_set_igmp_mac_filter(netif, function) do { if((netif) != NULL) { (netif)->igmp_mac_filter = function; }}while(0) +#define netif_get_igmp_mac_filter(netif) (((netif) != NULL) ? ((netif)->igmp_mac_filter) : NULL) +#endif /* LWIP_IGMP */ + +#if ENABLE_LOOPBACK +err_t netif_loop_output(struct netif *netif, struct pbuf *p, ip_addr_t *dest_ip)ICACHE_FLASH_ATTR; +void netif_poll(struct netif *netif)ICACHE_FLASH_ATTR; +#if !LWIP_NETIF_LOOPBACK_MULTITHREADING +void netif_poll_all(void)ICACHE_FLASH_ATTR; +#endif /* !LWIP_NETIF_LOOPBACK_MULTITHREADING */ +#endif /* ENABLE_LOOPBACK */ + +#ifdef __cplusplus +} +#endif + +#endif /* __LWIP_NETIF_H__ */ diff --git a/include/lwip/opt.h b/include/lwip/opt.h new file mode 100644 index 0000000..91d501f --- /dev/null +++ b/include/lwip/opt.h @@ -0,0 +1,2054 @@ +/** + * @file + * + * lwIP Options Configuration + */ + +/* + * Copyright (c) 2001-2004 Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT + * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT + * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY + * OF SUCH DAMAGE. + * + * This file is part of the lwIP TCP/IP stack. + * + * Author: Adam Dunkels + * + */ +#ifndef __LWIP_OPT_H__ +#define __LWIP_OPT_H__ + +/* + * Include user defined options first. Anything not defined in these files + * will be set to standard values. Override anything you dont like! + */ +#include "lwipopts.h" +#include "lwip/debug.h" + +/* + ----------------------------------------------- + ---------- Platform specific locking ---------- + ----------------------------------------------- +*/ + +/** + * SYS_LIGHTWEIGHT_PROT==1: if you want inter-task protection for certain + * critical regions during buffer allocation, deallocation and memory + * allocation and deallocation. + */ +#ifndef SYS_LIGHTWEIGHT_PROT +#define SYS_LIGHTWEIGHT_PROT 0 +#endif + +/** + * NO_SYS==1: Provides VERY minimal functionality. Otherwise, + * use lwIP facilities. + */ +#ifndef NO_SYS +#define NO_SYS 1 +#endif + +/** + * NO_SYS_NO_TIMERS==1: Drop support for sys_timeout when NO_SYS==1 + * Mainly for compatibility to old versions. + */ +#ifndef NO_SYS_NO_TIMERS +#define NO_SYS_NO_TIMERS 1 +#endif + +/** + * MEMCPY: override this if you have a faster implementation at hand than the + * one included in your C library + */ +#ifndef MEMCPY +#define MEMCPY(dst,src,len) memcpy(dst,src,len) +#endif + +/** + * SMEMCPY: override this with care! Some compilers (e.g. gcc) can inline a + * call to memcpy() if the length is known at compile time and is small. + */ +#ifndef SMEMCPY +#define SMEMCPY(dst,src,len) memcpy(dst,src,len) +#endif + +/* + ------------------------------------ + ---------- Memory options ---------- + ------------------------------------ +*/ +/** + * MEM_LIBC_MALLOC==1: Use malloc/free/realloc provided by your C-library + * instead of the lwip internal allocator. Can save code size if you + * already use it. + */ +#ifndef MEM_LIBC_MALLOC +#define MEM_LIBC_MALLOC 0 +#endif + +/** +* MEMP_MEM_MALLOC==1: Use mem_malloc/mem_free instead of the lwip pool allocator. +* Especially useful with MEM_LIBC_MALLOC but handle with care regarding execution +* speed and usage from interrupts! +*/ +#ifndef MEMP_MEM_MALLOC +#define MEMP_MEM_MALLOC 0 +#endif + +/** + * MEM_ALIGNMENT: should be set to the alignment of the CPU + * 4 byte alignment -> #define MEM_ALIGNMENT 4 + * 2 byte alignment -> #define MEM_ALIGNMENT 2 + */ +#ifndef MEM_ALIGNMENT +#define MEM_ALIGNMENT 1 +#endif + +/** + * MEM_SIZE: the size of the heap memory. If the application will send + * a lot of data that needs to be copied, this should be set high. + */ +#ifndef MEM_SIZE +#define MEM_SIZE 1600 +#endif + +/** + * MEMP_SEPARATE_POOLS: if defined to 1, each pool is placed in its own array. + * This can be used to individually change the location of each pool. + * Default is one big array for all pools + */ +#ifndef MEMP_SEPARATE_POOLS +#define MEMP_SEPARATE_POOLS 0 +#endif + +/** + * MEMP_OVERFLOW_CHECK: memp overflow protection reserves a configurable + * amount of bytes before and after each memp element in every pool and fills + * it with a prominent default value. + * MEMP_OVERFLOW_CHECK == 0 no checking + * MEMP_OVERFLOW_CHECK == 1 checks each element when it is freed + * MEMP_OVERFLOW_CHECK >= 2 checks each element in every pool every time + * memp_malloc() or memp_free() is called (useful but slow!) + */ +#ifndef MEMP_OVERFLOW_CHECK +#define MEMP_OVERFLOW_CHECK 0 +#endif + +/** + * MEMP_SANITY_CHECK==1: run a sanity check after each memp_free() to make + * sure that there are no cycles in the linked lists. + */ +#ifndef MEMP_SANITY_CHECK +#define MEMP_SANITY_CHECK 0 +#endif + +/** + * MEM_USE_POOLS==1: Use an alternative to malloc() by allocating from a set + * of memory pools of various sizes. When mem_malloc is called, an element of + * the smallest pool that can provide the length needed is returned. + * To use this, MEMP_USE_CUSTOM_POOLS also has to be enabled. + */ +#ifndef MEM_USE_POOLS +#define MEM_USE_POOLS 0 +#endif + +/** + * MEM_USE_POOLS_TRY_BIGGER_POOL==1: if one malloc-pool is empty, try the next + * bigger pool - WARNING: THIS MIGHT WASTE MEMORY but it can make a system more + * reliable. */ +#ifndef MEM_USE_POOLS_TRY_BIGGER_POOL +#define MEM_USE_POOLS_TRY_BIGGER_POOL 0 +#endif + +/** + * MEMP_USE_CUSTOM_POOLS==1: whether to include a user file lwippools.h + * that defines additional pools beyond the "standard" ones required + * by lwIP. If you set this to 1, you must have lwippools.h in your + * inlude path somewhere. + */ +#ifndef MEMP_USE_CUSTOM_POOLS +#define MEMP_USE_CUSTOM_POOLS 0 +#endif + +/** + * Set this to 1 if you want to free PBUF_RAM pbufs (or call mem_free()) from + * interrupt context (or another context that doesn't allow waiting for a + * semaphore). + * If set to 1, mem_malloc will be protected by a semaphore and SYS_ARCH_PROTECT, + * while mem_free will only use SYS_ARCH_PROTECT. mem_malloc SYS_ARCH_UNPROTECTs + * with each loop so that mem_free can run. + * + * ATTENTION: As you can see from the above description, this leads to dis-/ + * enabling interrupts often, which can be slow! Also, on low memory, mem_malloc + * can need longer. + * + * If you don't want that, at least for NO_SYS=0, you can still use the following + * functions to enqueue a deallocation call which then runs in the tcpip_thread + * context: + * - pbuf_free_callback(p); + * - mem_free_callback(m); + */ +#ifndef LWIP_ALLOW_MEM_FREE_FROM_OTHER_CONTEXT +#define LWIP_ALLOW_MEM_FREE_FROM_OTHER_CONTEXT 0 +#endif + +/* + ------------------------------------------------ + ---------- Internal Memory Pool Sizes ---------- + ------------------------------------------------ +*/ +/** + * MEMP_NUM_PBUF: the number of memp struct pbufs (used for PBUF_ROM and PBUF_REF). + * If the application sends a lot of data out of ROM (or other static memory), + * this should be set high. + */ +#ifndef MEMP_NUM_PBUF +#define MEMP_NUM_PBUF 16 +#endif + +/** + * MEMP_NUM_RAW_PCB: Number of raw connection PCBs + * (requires the LWIP_RAW option) + */ +#ifndef MEMP_NUM_RAW_PCB +#define MEMP_NUM_RAW_PCB 4 +#endif + +/** + * MEMP_NUM_UDP_PCB: the number of UDP protocol control blocks. One + * per active UDP "connection". + * (requires the LWIP_UDP option) + */ +#ifndef MEMP_NUM_UDP_PCB +#define MEMP_NUM_UDP_PCB 4 +#endif + +/** + * MEMP_NUM_TCP_PCB: the number of simulatenously active TCP connections. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_PCB +#define MEMP_NUM_TCP_PCB 5 +#endif + +/** + * MEMP_NUM_TCP_PCB_LISTEN: the number of listening TCP connections. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_PCB_LISTEN +#define MEMP_NUM_TCP_PCB_LISTEN 8 +#endif + +/** + * MEMP_NUM_TCP_SEG: the number of simultaneously queued TCP segments. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_SEG +#define MEMP_NUM_TCP_SEG 16 +#endif + +/** + * MEMP_NUM_REASSDATA: the number of IP packets simultaneously queued for + * reassembly (whole packets, not fragments!) + */ +#ifndef MEMP_NUM_REASSDATA +#define MEMP_NUM_REASSDATA 5 +#endif + +/** + * MEMP_NUM_FRAG_PBUF: the number of IP fragments simultaneously sent + * (fragments, not whole packets!). + * This is only used with IP_FRAG_USES_STATIC_BUF==0 and + * LWIP_NETIF_TX_SINGLE_PBUF==0 and only has to be > 1 with DMA-enabled MACs + * where the packet is not yet sent when netif->output returns. + */ +#ifndef MEMP_NUM_FRAG_PBUF +#define MEMP_NUM_FRAG_PBUF 15 +#endif + +/** + * MEMP_NUM_ARP_QUEUE: the number of simulateously queued outgoing + * packets (pbufs) that are waiting for an ARP request (to resolve + * their destination address) to finish. + * (requires the ARP_QUEUEING option) + */ +#ifndef MEMP_NUM_ARP_QUEUE +#define MEMP_NUM_ARP_QUEUE 30 +#endif + +/** + * MEMP_NUM_IGMP_GROUP: The number of multicast groups whose network interfaces + * can be members et the same time (one per netif - allsystems group -, plus one + * per netif membership). + * (requires the LWIP_IGMP option) + */ +#ifndef MEMP_NUM_IGMP_GROUP +#define MEMP_NUM_IGMP_GROUP 8 +#endif + +/** + * MEMP_NUM_SYS_TIMEOUT: the number of simulateously active timeouts. + * (requires NO_SYS==0) + */ +#ifndef MEMP_NUM_SYS_TIMEOUT +#define MEMP_NUM_SYS_TIMEOUT 3 +#endif + +/** + * MEMP_NUM_NETBUF: the number of struct netbufs. + * (only needed if you use the sequential API, like api_lib.c) + */ +#ifndef MEMP_NUM_NETBUF +#define MEMP_NUM_NETBUF 2 +#endif + +/** + * MEMP_NUM_NETCONN: the number of struct netconns. + * (only needed if you use the sequential API, like api_lib.c) + */ +#ifndef MEMP_NUM_NETCONN +#define MEMP_NUM_NETCONN 4 +#endif + +/** + * MEMP_NUM_TCPIP_MSG_API: the number of struct tcpip_msg, which are used + * for callback/timeout API communication. + * (only needed if you use tcpip.c) + */ +#ifndef MEMP_NUM_TCPIP_MSG_API +#define MEMP_NUM_TCPIP_MSG_API 8 +#endif + +/** + * MEMP_NUM_TCPIP_MSG_INPKT: the number of struct tcpip_msg, which are used + * for incoming packets. + * (only needed if you use tcpip.c) + */ +#ifndef MEMP_NUM_TCPIP_MSG_INPKT +#define MEMP_NUM_TCPIP_MSG_INPKT 8 +#endif + +/** + * MEMP_NUM_SNMP_NODE: the number of leafs in the SNMP tree. + */ +#ifndef MEMP_NUM_SNMP_NODE +#define MEMP_NUM_SNMP_NODE 50 +#endif + +/** + * MEMP_NUM_SNMP_ROOTNODE: the number of branches in the SNMP tree. + * Every branch has one leaf (MEMP_NUM_SNMP_NODE) at least! + */ +#ifndef MEMP_NUM_SNMP_ROOTNODE +#define MEMP_NUM_SNMP_ROOTNODE 30 +#endif + +/** + * MEMP_NUM_SNMP_VARBIND: the number of concurrent requests (does not have to + * be changed normally) - 2 of these are used per request (1 for input, + * 1 for output) + */ +#ifndef MEMP_NUM_SNMP_VARBIND +#define MEMP_NUM_SNMP_VARBIND 2 +#endif + +/** + * MEMP_NUM_SNMP_VALUE: the number of OID or values concurrently used + * (does not have to be changed normally) - 3 of these are used per request + * (1 for the value read and 2 for OIDs - input and output) + */ +#ifndef MEMP_NUM_SNMP_VALUE +#define MEMP_NUM_SNMP_VALUE 3 +#endif + +/** + * MEMP_NUM_NETDB: the number of concurrently running lwip_addrinfo() calls + * (before freeing the corresponding memory using lwip_freeaddrinfo()). + */ +#ifndef MEMP_NUM_NETDB +#define MEMP_NUM_NETDB 1 +#endif + +/** + * MEMP_NUM_LOCALHOSTLIST: the number of host entries in the local host list + * if DNS_LOCAL_HOSTLIST_IS_DYNAMIC==1. + */ +#ifndef MEMP_NUM_LOCALHOSTLIST +#define MEMP_NUM_LOCALHOSTLIST 1 +#endif + +/** + * MEMP_NUM_PPPOE_INTERFACES: the number of concurrently active PPPoE + * interfaces (only used with PPPOE_SUPPORT==1) + */ +#ifndef MEMP_NUM_PPPOE_INTERFACES +#define MEMP_NUM_PPPOE_INTERFACES 1 +#endif + +/** + * PBUF_POOL_SIZE: the number of buffers in the pbuf pool. + */ +#ifndef PBUF_POOL_SIZE +#define PBUF_POOL_SIZE 16 +#endif + +/* + --------------------------------- + ---------- ARP options ---------- + --------------------------------- +*/ +/** + * LWIP_ARP==1: Enable ARP functionality. + */ +#ifndef LWIP_ARP +#define LWIP_ARP 1 +#endif + +/** + * ARP_TABLE_SIZE: Number of active MAC-IP address pairs cached. + */ +#ifndef ARP_TABLE_SIZE +#define ARP_TABLE_SIZE 10 +#endif + +/** + * ARP_QUEUEING==1: Multiple outgoing packets are queued during hardware address + * resolution. By default, only the most recent packet is queued per IP address. + * This is sufficient for most protocols and mainly reduces TCP connection + * startup time. Set this to 1 if you know your application sends more than one + * packet in a row to an IP address that is not in the ARP cache. + */ +#ifndef ARP_QUEUEING +#define ARP_QUEUEING 0 +#endif + +/** + * ETHARP_TRUST_IP_MAC==1: Incoming IP packets cause the ARP table to be + * updated with the source MAC and IP addresses supplied in the packet. + * You may want to disable this if you do not trust LAN peers to have the + * correct addresses, or as a limited approach to attempt to handle + * spoofing. If disabled, lwIP will need to make a new ARP request if + * the peer is not already in the ARP table, adding a little latency. + * The peer *is* in the ARP table if it requested our address before. + * Also notice that this slows down input processing of every IP packet! + */ +#ifndef ETHARP_TRUST_IP_MAC +#define ETHARP_TRUST_IP_MAC 0 +#endif + +/** + * ETHARP_SUPPORT_VLAN==1: support receiving ethernet packets with VLAN header. + * Additionally, you can define ETHARP_VLAN_CHECK to an u16_t VLAN ID to check. + * If ETHARP_VLAN_CHECK is defined, only VLAN-traffic for this VLAN is accepted. + * If ETHARP_VLAN_CHECK is not defined, all traffic is accepted. + */ +#ifndef ETHARP_SUPPORT_VLAN +#define ETHARP_SUPPORT_VLAN 0 +#endif + +/** LWIP_ETHERNET==1: enable ethernet support for PPPoE even though ARP + * might be disabled + */ +#ifndef LWIP_ETHERNET +#define LWIP_ETHERNET (LWIP_ARP || PPPOE_SUPPORT) +#endif + +/** ETH_PAD_SIZE: number of bytes added before the ethernet header to ensure + * alignment of payload after that header. Since the header is 14 bytes long, + * without this padding e.g. addresses in the IP header will not be aligned + * on a 32-bit boundary, so setting this to 2 can speed up 32-bit-platforms. + */ +#ifndef ETH_PAD_SIZE +#define ETH_PAD_SIZE 0 +#endif + +/** ETHARP_SUPPORT_STATIC_ENTRIES==1: enable code to support static ARP table + * entries (using etharp_add_static_entry/etharp_remove_static_entry). + */ +#ifndef ETHARP_SUPPORT_STATIC_ENTRIES +#define ETHARP_SUPPORT_STATIC_ENTRIES 0 +#endif + + +/* + -------------------------------- + ---------- IP options ---------- + -------------------------------- +*/ +/** + * IP_FORWARD==1: Enables the ability to forward IP packets across network + * interfaces. If you are going to run lwIP on a device with only one network + * interface, define this to 0. + */ +#ifndef IP_FORWARD +#define IP_FORWARD 1 +#endif + +#ifndef IP_NAPT +#define IP_NAPT 1 +#endif + +/** + * IP_OPTIONS_ALLOWED: Defines the behavior for IP options. + * IP_OPTIONS_ALLOWED==0: All packets with IP options are dropped. + * IP_OPTIONS_ALLOWED==1: IP options are allowed (but not parsed). + */ +#ifndef IP_OPTIONS_ALLOWED +#define IP_OPTIONS_ALLOWED 1 +#endif + +/** + * IP_REASSEMBLY==1: Reassemble incoming fragmented IP packets. Note that + * this option does not affect outgoing packet sizes, which can be controlled + * via IP_FRAG. + */ +#ifndef IP_REASSEMBLY +#define IP_REASSEMBLY 0 +#endif + +/** + * IP_FRAG==1: Fragment outgoing IP packets if their size exceeds MTU. Note + * that this option does not affect incoming packet sizes, which can be + * controlled via IP_REASSEMBLY. + */ +#ifndef IP_FRAG +#define IP_FRAG 1 +#endif + +/** + * IP_REASS_MAXAGE: Maximum time (in multiples of IP_TMR_INTERVAL - so seconds, normally) + * a fragmented IP packet waits for all fragments to arrive. If not all fragments arrived + * in this time, the whole packet is discarded. + */ +#ifndef IP_REASS_MAXAGE +#define IP_REASS_MAXAGE 3 +#endif + +/** + * IP_REASS_MAX_PBUFS: Total maximum amount of pbufs waiting to be reassembled. + * Since the received pbufs are enqueued, be sure to configure + * PBUF_POOL_SIZE > IP_REASS_MAX_PBUFS so that the stack is still able to receive + * packets even if the maximum amount of fragments is enqueued for reassembly! + */ +#ifndef IP_REASS_MAX_PBUFS +#define IP_REASS_MAX_PBUFS 10 +#endif + +/** + * IP_FRAG_USES_STATIC_BUF==1: Use a static MTU-sized buffer for IP + * fragmentation. Otherwise pbufs are allocated and reference the original + * packet data to be fragmented (or with LWIP_NETIF_TX_SINGLE_PBUF==1, + * new PBUF_RAM pbufs are used for fragments). + * ATTENTION: IP_FRAG_USES_STATIC_BUF==1 may not be used for DMA-enabled MACs! + */ +#ifndef IP_FRAG_USES_STATIC_BUF +#define IP_FRAG_USES_STATIC_BUF 0 +#endif + +/** + * IP_FRAG_MAX_MTU: Assumed max MTU on any interface for IP frag buffer + * (requires IP_FRAG_USES_STATIC_BUF==1) + */ +#if IP_FRAG_USES_STATIC_BUF && !defined(IP_FRAG_MAX_MTU) +#define IP_FRAG_MAX_MTU 1500 +#endif + +/** + * IP_DEFAULT_TTL: Default value for Time-To-Live used by transport layers. + */ +#ifndef IP_DEFAULT_TTL +#define IP_DEFAULT_TTL 255 +#endif + +/** + * IP_SOF_BROADCAST=1: Use the SOF_BROADCAST field to enable broadcast + * filter per pcb on udp and raw send operations. To enable broadcast filter + * on recv operations, you also have to set IP_SOF_BROADCAST_RECV=1. + */ +#ifndef IP_SOF_BROADCAST +#define IP_SOF_BROADCAST 0 +#endif + +/** + * IP_SOF_BROADCAST_RECV (requires IP_SOF_BROADCAST=1) enable the broadcast + * filter on recv operations. + */ +#ifndef IP_SOF_BROADCAST_RECV +#define IP_SOF_BROADCAST_RECV 0 +#endif + +/* + ---------------------------------- + ---------- ICMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_ICMP==1: Enable ICMP module inside the IP stack. + * Be careful, disable that make your product non-compliant to RFC1122 + */ +#ifndef LWIP_ICMP +#define LWIP_ICMP 1 +#endif + +/** + * ICMP_TTL: Default value for Time-To-Live used by ICMP packets. + */ +#ifndef ICMP_TTL +#define ICMP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * LWIP_BROADCAST_PING==1: respond to broadcast pings (default is unicast only) + */ +#ifndef LWIP_BROADCAST_PING +#define LWIP_BROADCAST_PING 0 +#endif + +/** + * LWIP_MULTICAST_PING==1: respond to multicast pings (default is unicast only) + */ +#ifndef LWIP_MULTICAST_PING +#define LWIP_MULTICAST_PING 0 +#endif + +/* + --------------------------------- + ---------- RAW options ---------- + --------------------------------- +*/ +/** + * LWIP_RAW==1: Enable application layer to hook into the IP layer itself. + */ +#ifndef LWIP_RAW +#define LWIP_RAW 1 +#endif + +/** + * LWIP_RAW==1: Enable application layer to hook into the IP layer itself. + */ +#ifndef RAW_TTL +#define RAW_TTL (IP_DEFAULT_TTL) +#endif + +/* + ---------------------------------- + ---------- DHCP options ---------- + ---------------------------------- +*/ +/** + * LWIP_DHCP==1: Enable DHCP module. + */ +#ifndef LWIP_DHCP +#define LWIP_DHCP 0 +#endif + +/** + * DHCP_DOES_ARP_CHECK==1: Do an ARP check on the offered address. + */ +#ifndef DHCP_DOES_ARP_CHECK +#define DHCP_DOES_ARP_CHECK ((LWIP_DHCP) && (LWIP_ARP)) +#endif + +/* + ------------------------------------ + ---------- AUTOIP options ---------- + ------------------------------------ +*/ +/** + * LWIP_AUTOIP==1: Enable AUTOIP module. + */ +#ifndef LWIP_AUTOIP +#define LWIP_AUTOIP 0 +#endif + +/** + * LWIP_DHCP_AUTOIP_COOP==1: Allow DHCP and AUTOIP to be both enabled on + * the same interface at the same time. + */ +#ifndef LWIP_DHCP_AUTOIP_COOP +#define LWIP_DHCP_AUTOIP_COOP 0 +#endif + +/** + * LWIP_DHCP_AUTOIP_COOP_TRIES: Set to the number of DHCP DISCOVER probes + * that should be sent before falling back on AUTOIP. This can be set + * as low as 1 to get an AutoIP address very quickly, but you should + * be prepared to handle a changing IP address when DHCP overrides + * AutoIP. + */ +#ifndef LWIP_DHCP_AUTOIP_COOP_TRIES +#define LWIP_DHCP_AUTOIP_COOP_TRIES 9 +#endif + +/* + ---------------------------------- + ---------- SNMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_SNMP==1: Turn on SNMP module. UDP must be available for SNMP + * transport. + */ +#ifndef LWIP_SNMP +#define LWIP_SNMP 0 +#endif + +/** + * SNMP_CONCURRENT_REQUESTS: Number of concurrent requests the module will + * allow. At least one request buffer is required. + * Does not have to be changed unless external MIBs answer request asynchronously + */ +#ifndef SNMP_CONCURRENT_REQUESTS +#define SNMP_CONCURRENT_REQUESTS 1 +#endif + +/** + * SNMP_TRAP_DESTINATIONS: Number of trap destinations. At least one trap + * destination is required + */ +#ifndef SNMP_TRAP_DESTINATIONS +#define SNMP_TRAP_DESTINATIONS 1 +#endif + +/** + * SNMP_PRIVATE_MIB: + * When using a private MIB, you have to create a file 'private_mib.h' that contains + * a 'struct mib_array_node mib_private' which contains your MIB. + */ +#ifndef SNMP_PRIVATE_MIB +#define SNMP_PRIVATE_MIB 0 +#endif + +/** + * Only allow SNMP write actions that are 'safe' (e.g. disabeling netifs is not + * a safe action and disabled when SNMP_SAFE_REQUESTS = 1). + * Unsafe requests are disabled by default! + */ +#ifndef SNMP_SAFE_REQUESTS +#define SNMP_SAFE_REQUESTS 1 +#endif + +/** + * The maximum length of strings used. This affects the size of + * MEMP_SNMP_VALUE elements. + */ +#ifndef SNMP_MAX_OCTET_STRING_LEN +#define SNMP_MAX_OCTET_STRING_LEN 127 +#endif + +/** + * The maximum depth of the SNMP tree. + * With private MIBs enabled, this depends on your MIB! + * This affects the size of MEMP_SNMP_VALUE elements. + */ +#ifndef SNMP_MAX_TREE_DEPTH +#define SNMP_MAX_TREE_DEPTH 15 +#endif + +/** + * The size of the MEMP_SNMP_VALUE elements, normally calculated from + * SNMP_MAX_OCTET_STRING_LEN and SNMP_MAX_TREE_DEPTH. + */ +#ifndef SNMP_MAX_VALUE_SIZE +#define SNMP_MAX_VALUE_SIZE LWIP_MAX((SNMP_MAX_OCTET_STRING_LEN)+1, sizeof(s32_t)*(SNMP_MAX_TREE_DEPTH)) +#endif + +/* + ---------------------------------- + ---------- IGMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_IGMP==1: Turn on IGMP module. + */ +#ifndef LWIP_IGMP +#define LWIP_IGMP 0 +#endif + +/* + ---------------------------------- + ---------- DNS options ----------- + ---------------------------------- +*/ +/** + * LWIP_DNS==1: Turn on DNS module. UDP must be available for DNS + * transport. + */ +#ifndef LWIP_DNS +#define LWIP_DNS 0 +#endif + +/** DNS maximum number of entries to maintain locally. */ +#ifndef DNS_TABLE_SIZE +#define DNS_TABLE_SIZE 4 +#endif + +/** DNS maximum host name length supported in the name table. */ +#ifndef DNS_MAX_NAME_LENGTH +#define DNS_MAX_NAME_LENGTH 256 +#endif + +/** The maximum of DNS servers */ +#ifndef DNS_MAX_SERVERS +#define DNS_MAX_SERVERS 2 +#endif + +/** DNS do a name checking between the query and the response. */ +#ifndef DNS_DOES_NAME_CHECK +#define DNS_DOES_NAME_CHECK 1 +#endif + +/** DNS message max. size. Default value is RFC compliant. */ +#ifndef DNS_MSG_SIZE +#define DNS_MSG_SIZE 512 +#endif + +/** DNS_LOCAL_HOSTLIST: Implements a local host-to-address list. If enabled, + * you have to define + * #define DNS_LOCAL_HOSTLIST_INIT {{"host1", 0x123}, {"host2", 0x234}} + * (an array of structs name/address, where address is an u32_t in network + * byte order). + * + * Instead, you can also use an external function: + * #define DNS_LOOKUP_LOCAL_EXTERN(x) extern u32_t my_lookup_function(const char *name) + * that returns the IP address or INADDR_NONE if not found. + */ +#ifndef DNS_LOCAL_HOSTLIST +#define DNS_LOCAL_HOSTLIST 0 +#endif /* DNS_LOCAL_HOSTLIST */ + +/** If this is turned on, the local host-list can be dynamically changed + * at runtime. */ +#ifndef DNS_LOCAL_HOSTLIST_IS_DYNAMIC +#define DNS_LOCAL_HOSTLIST_IS_DYNAMIC 0 +#endif /* DNS_LOCAL_HOSTLIST_IS_DYNAMIC */ + +/* + --------------------------------- + ---------- UDP options ---------- + --------------------------------- +*/ +/** + * LWIP_UDP==1: Turn on UDP. + */ +#ifndef LWIP_UDP +#define LWIP_UDP 1 +#endif + +/** + * LWIP_UDPLITE==1: Turn on UDP-Lite. (Requires LWIP_UDP) + */ +#ifndef LWIP_UDPLITE +#define LWIP_UDPLITE 0 +#endif + +/** + * UDP_TTL: Default Time-To-Live value. + */ +#ifndef UDP_TTL +#define UDP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * LWIP_NETBUF_RECVINFO==1: append destination addr and port to every netbuf. + */ +#ifndef LWIP_NETBUF_RECVINFO +#define LWIP_NETBUF_RECVINFO 0 +#endif + +/* + --------------------------------- + ---------- TCP options ---------- + --------------------------------- +*/ +/** + * LWIP_TCP==1: Turn on TCP. + */ +#ifndef LWIP_TCP +#define LWIP_TCP 1 +#endif + +/** + * TCP_TTL: Default Time-To-Live value. + */ +#ifndef TCP_TTL +#define TCP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * TCP_WND: The size of a TCP window. This must be at least + * (2 * TCP_MSS) for things to work well + */ +#ifndef TCP_WND +#define TCP_WND (4 * TCP_MSS) +#endif + +/** + * TCP_MAXRTX: Maximum number of retransmissions of data segments. + */ +#ifndef TCP_MAXRTX +#define TCP_MAXRTX 12 +#endif + +/** + * TCP_SYNMAXRTX: Maximum number of retransmissions of SYN segments. + */ +#ifndef TCP_SYNMAXRTX +#define TCP_SYNMAXRTX 6 +#endif + +/** + * TCP_QUEUE_OOSEQ==1: TCP will queue segments that arrive out of order. + * Define to 0 if your device is low on memory. + */ +#ifndef TCP_QUEUE_OOSEQ +#define TCP_QUEUE_OOSEQ (LWIP_TCP) +#endif + +/** + * TCP_MSS: TCP Maximum segment size. (default is 536, a conservative default, + * you might want to increase this.) + * For the receive side, this MSS is advertised to the remote side + * when opening a connection. For the transmit size, this MSS sets + * an upper limit on the MSS advertised by the remote host. + */ +#ifndef TCP_MSS +#define TCP_MSS 536 +#endif + +/** + * TCP_CALCULATE_EFF_SEND_MSS: "The maximum size of a segment that TCP really + * sends, the 'effective send MSS,' MUST be the smaller of the send MSS (which + * reflects the available reassembly buffer size at the remote host) and the + * largest size permitted by the IP layer" (RFC 1122) + * Setting this to 1 enables code that checks TCP_MSS against the MTU of the + * netif used for a connection and limits the MSS if it would be too big otherwise. + */ +#ifndef TCP_CALCULATE_EFF_SEND_MSS +#define TCP_CALCULATE_EFF_SEND_MSS 1 +#endif + + +/** + * TCP_SND_BUF: TCP sender buffer space (bytes). + */ +#ifndef TCP_SND_BUF +#define TCP_SND_BUF 256 +#endif + +/** + * TCP_SND_QUEUELEN: TCP sender buffer space (pbufs). This must be at least + * as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work. + */ +#ifndef TCP_SND_QUEUELEN +#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1))/(TCP_MSS)) +#endif + +/** + * TCP_SNDLOWAT: TCP writable space (bytes). This must be less than + * TCP_SND_BUF. It is the amount of space which must be available in the + * TCP snd_buf for select to return writable (combined with TCP_SNDQUEUELOWAT). + */ +#ifndef TCP_SNDLOWAT +#define TCP_SNDLOWAT ((TCP_SND_BUF)/2) +#endif + +/** + * TCP_SNDQUEUELOWAT: TCP writable bufs (pbuf count). This must be grater + * than TCP_SND_QUEUELEN. If the number of pbufs queued on a pcb drops below + * this number, select returns writable (combined with TCP_SNDLOWAT). + */ +#ifndef TCP_SNDQUEUELOWAT +#define TCP_SNDQUEUELOWAT ((TCP_SND_QUEUELEN)/2) +#endif + +/** + * TCP_LISTEN_BACKLOG: Enable the backlog option for tcp listen pcb. + */ +#ifndef TCP_LISTEN_BACKLOG +#define TCP_LISTEN_BACKLOG 0 +#endif + +/** + * The maximum allowed backlog for TCP listen netconns. + * This backlog is used unless another is explicitly specified. + * 0xff is the maximum (u8_t). + */ +#ifndef TCP_DEFAULT_LISTEN_BACKLOG +#define TCP_DEFAULT_LISTEN_BACKLOG 0xff +#endif + +/** + * TCP_OVERSIZE: The maximum number of bytes that tcp_write may + * allocate ahead of time in an attempt to create shorter pbuf chains + * for transmission. The meaningful range is 0 to TCP_MSS. Some + * suggested values are: + * + * 0: Disable oversized allocation. Each tcp_write() allocates a new + pbuf (old behaviour). + * 1: Allocate size-aligned pbufs with minimal excess. Use this if your + * scatter-gather DMA requires aligned fragments. + * 128: Limit the pbuf/memory overhead to 20%. + * TCP_MSS: Try to create unfragmented TCP packets. + * TCP_MSS/4: Try to create 4 fragments or less per TCP packet. + */ +#ifndef TCP_OVERSIZE +#define TCP_OVERSIZE TCP_MSS +#endif + +/** + * LWIP_TCP_TIMESTAMPS==1: support the TCP timestamp option. + */ +#ifndef LWIP_TCP_TIMESTAMPS +#define LWIP_TCP_TIMESTAMPS 0 +#endif + +/** + * TCP_WND_UPDATE_THRESHOLD: difference in window to trigger an + * explicit window update + */ +#ifndef TCP_WND_UPDATE_THRESHOLD +#define TCP_WND_UPDATE_THRESHOLD (TCP_WND / 4) +#endif + +/** + * LWIP_EVENT_API and LWIP_CALLBACK_API: Only one of these should be set to 1. + * LWIP_EVENT_API==1: The user defines lwip_tcp_event() to receive all + * events (accept, sent, etc) that happen in the system. + * LWIP_CALLBACK_API==1: The PCB callback function is called directly + * for the event. + */ +//#ifndef LWIP_EVENT_API +//#define LWIP_EVENT_API 0 +//#define LWIP_CALLBACK_API 1 +//#else +//#define LWIP_EVENT_API 1 +//#define LWIP_CALLBACK_API 0 +//#endif + + +/* + ---------------------------------- + ---------- Pbuf options ---------- + ---------------------------------- +*/ +/** + * PBUF_LINK_HLEN: the number of bytes that should be allocated for a + * link level header. The default is 14, the standard value for + * Ethernet. + */ +#ifndef PBUF_LINK_HLEN +#define PBUF_LINK_HLEN (14 + ETH_PAD_SIZE) +#endif + +/** + * PBUF_POOL_BUFSIZE: the size of each pbuf in the pbuf pool. The default is + * designed to accommodate single full size TCP frame in one pbuf, including + * TCP_MSS, IP header, and link header. + */ +#ifndef PBUF_POOL_BUFSIZE +#define PBUF_POOL_BUFSIZE LWIP_MEM_ALIGN_SIZE(TCP_MSS+40+PBUF_LINK_HLEN) +#endif + +/* + ------------------------------------------------ + ---------- Network Interfaces options ---------- + ------------------------------------------------ +*/ +/** + * LWIP_NETIF_HOSTNAME==1: use DHCP_OPTION_HOSTNAME with netif's hostname + * field. + */ +#ifndef LWIP_NETIF_HOSTNAME +#define LWIP_NETIF_HOSTNAME 0 +#endif + +/** + * LWIP_NETIF_API==1: Support netif api (in netifapi.c) + */ +#ifndef LWIP_NETIF_API +#define LWIP_NETIF_API 0 +#endif + +/** + * LWIP_NETIF_STATUS_CALLBACK==1: Support a callback function whenever an interface + * changes its up/down status (i.e., due to DHCP IP acquistion) + */ +#ifndef LWIP_NETIF_STATUS_CALLBACK +#define LWIP_NETIF_STATUS_CALLBACK 0 +#endif + +/** + * LWIP_NETIF_LINK_CALLBACK==1: Support a callback function from an interface + * whenever the link changes (i.e., link down) + */ +#ifndef LWIP_NETIF_LINK_CALLBACK +#define LWIP_NETIF_LINK_CALLBACK 0 +#endif + +/** + * LWIP_NETIF_HWADDRHINT==1: Cache link-layer-address hints (e.g. table + * indices) in struct netif. TCP and UDP can make use of this to prevent + * scanning the ARP table for every sent packet. While this is faster for big + * ARP tables or many concurrent connections, it might be counterproductive + * if you have a tiny ARP table or if there never are concurrent connections. + */ +#ifndef LWIP_NETIF_HWADDRHINT +#define LWIP_NETIF_HWADDRHINT 0 +#endif + +/** + * LWIP_NETIF_LOOPBACK==1: Support sending packets with a destination IP + * address equal to the netif IP address, looping them back up the stack. + */ +#ifndef LWIP_NETIF_LOOPBACK +#define LWIP_NETIF_LOOPBACK 1 +#endif + +/** + * LWIP_LOOPBACK_MAX_PBUFS: Maximum number of pbufs on queue for loopback + * sending for each netif (0 = disabled) + */ +#ifndef LWIP_LOOPBACK_MAX_PBUFS +#define LWIP_LOOPBACK_MAX_PBUFS 0 +#endif + +/** + * LWIP_NETIF_LOOPBACK_MULTITHREADING: Indicates whether threading is enabled in + * the system, as netifs must change how they behave depending on this setting + * for the LWIP_NETIF_LOOPBACK option to work. + * Setting this is needed to avoid reentering non-reentrant functions like + * tcp_input(). + * LWIP_NETIF_LOOPBACK_MULTITHREADING==1: Indicates that the user is using a + * multithreaded environment like tcpip.c. In this case, netif->input() + * is called directly. + * LWIP_NETIF_LOOPBACK_MULTITHREADING==0: Indicates a polling (or NO_SYS) setup. + * The packets are put on a list and netif_poll() must be called in + * the main application loop. + */ +#ifndef LWIP_NETIF_LOOPBACK_MULTITHREADING +#define LWIP_NETIF_LOOPBACK_MULTITHREADING (!NO_SYS) +#endif + +/** + * LWIP_NETIF_TX_SINGLE_PBUF: if this is set to 1, lwIP tries to put all data + * to be sent into one single pbuf. This is for compatibility with DMA-enabled + * MACs that do not support scatter-gather. + * Beware that this might involve CPU-memcpy before transmitting that would not + * be needed without this flag! Use this only if you need to! + * + * @todo: TCP and IP-frag do not work with this, yet: + */ +#ifndef LWIP_NETIF_TX_SINGLE_PBUF +#define LWIP_NETIF_TX_SINGLE_PBUF 0 +#endif /* LWIP_NETIF_TX_SINGLE_PBUF */ + +/* + ------------------------------------ + ---------- LOOPIF options ---------- + ------------------------------------ +*/ +/** + * LWIP_HAVE_LOOPIF==1: Support loop interface (127.0.0.1) and loopif.c + */ +#ifndef LWIP_HAVE_LOOPIF +#define LWIP_HAVE_LOOPIF 1 +#endif + +/* + ------------------------------------ + ---------- SLIPIF options ---------- + ------------------------------------ +*/ +/** + * LWIP_HAVE_SLIPIF==1: Support slip interface and slipif.c + */ +#ifndef LWIP_HAVE_SLIPIF +#define LWIP_HAVE_SLIPIF 0 +#endif + +/* + ------------------------------------ + ---------- Thread options ---------- + ------------------------------------ +*/ +/** + * TCPIP_THREAD_NAME: The name assigned to the main tcpip thread. + */ +#ifndef TCPIP_THREAD_NAME +#define TCPIP_THREAD_NAME "tcpip_thread" +#endif + +/** + * TCPIP_THREAD_STACKSIZE: The stack size used by the main tcpip thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef TCPIP_THREAD_STACKSIZE +#define TCPIP_THREAD_STACKSIZE 0 +#endif + +/** + * TCPIP_THREAD_PRIO: The priority assigned to the main tcpip thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef TCPIP_THREAD_PRIO +#define TCPIP_THREAD_PRIO 1 +#endif + +/** + * TCPIP_MBOX_SIZE: The mailbox size for the tcpip thread messages + * The queue size value itself is platform-dependent, but is passed to + * sys_mbox_new() when tcpip_init is called. + */ +#ifndef TCPIP_MBOX_SIZE +#define TCPIP_MBOX_SIZE 0 +#endif + +/** + * SLIPIF_THREAD_NAME: The name assigned to the slipif_loop thread. + */ +#ifndef SLIPIF_THREAD_NAME +#define SLIPIF_THREAD_NAME "slipif_loop" +#endif + +/** + * SLIP_THREAD_STACKSIZE: The stack size used by the slipif_loop thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef SLIPIF_THREAD_STACKSIZE +#define SLIPIF_THREAD_STACKSIZE 0 +#endif + +/** + * SLIPIF_THREAD_PRIO: The priority assigned to the slipif_loop thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef SLIPIF_THREAD_PRIO +#define SLIPIF_THREAD_PRIO 1 +#endif + +/** + * PPP_THREAD_NAME: The name assigned to the pppInputThread. + */ +#ifndef PPP_THREAD_NAME +#define PPP_THREAD_NAME "pppInputThread" +#endif + +/** + * PPP_THREAD_STACKSIZE: The stack size used by the pppInputThread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef PPP_THREAD_STACKSIZE +#define PPP_THREAD_STACKSIZE 0 +#endif + +/** + * PPP_THREAD_PRIO: The priority assigned to the pppInputThread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef PPP_THREAD_PRIO +#define PPP_THREAD_PRIO 1 +#endif + +/** + * DEFAULT_THREAD_NAME: The name assigned to any other lwIP thread. + */ +#ifndef DEFAULT_THREAD_NAME +#define DEFAULT_THREAD_NAME "lwIP" +#endif + +/** + * DEFAULT_THREAD_STACKSIZE: The stack size used by any other lwIP thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef DEFAULT_THREAD_STACKSIZE +#define DEFAULT_THREAD_STACKSIZE 0 +#endif + +/** + * DEFAULT_THREAD_PRIO: The priority assigned to any other lwIP thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef DEFAULT_THREAD_PRIO +#define DEFAULT_THREAD_PRIO 1 +#endif + +/** + * DEFAULT_RAW_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_RAW. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_RAW_RECVMBOX_SIZE +#define DEFAULT_RAW_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_UDP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_UDP. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_UDP_RECVMBOX_SIZE +#define DEFAULT_UDP_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_TCP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_TCP. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_TCP_RECVMBOX_SIZE +#define DEFAULT_TCP_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_ACCEPTMBOX_SIZE: The mailbox size for the incoming connections. + * The queue size value itself is platform-dependent, but is passed to + * sys_mbox_new() when the acceptmbox is created. + */ +#ifndef DEFAULT_ACCEPTMBOX_SIZE +#define DEFAULT_ACCEPTMBOX_SIZE 0 +#endif + +/* + ---------------------------------------------- + ---------- Sequential layer options ---------- + ---------------------------------------------- +*/ +/** + * LWIP_TCPIP_CORE_LOCKING: (EXPERIMENTAL!) + * Don't use it if you're not an active lwIP project member + */ +#ifndef LWIP_TCPIP_CORE_LOCKING +#define LWIP_TCPIP_CORE_LOCKING 0 +#endif + +/** + * LWIP_TCPIP_CORE_LOCKING_INPUT: (EXPERIMENTAL!) + * Don't use it if you're not an active lwIP project member + */ +#ifndef LWIP_TCPIP_CORE_LOCKING_INPUT +#define LWIP_TCPIP_CORE_LOCKING_INPUT 0 +#endif + +/** + * LWIP_NETCONN==1: Enable Netconn API (require to use api_lib.c) + */ +#ifndef LWIP_NETCONN +#define LWIP_NETCONN 0 +#endif + +/** LWIP_TCPIP_TIMEOUT==1: Enable tcpip_timeout/tcpip_untimeout tod create + * timers running in tcpip_thread from another thread. + */ +#ifndef LWIP_TCPIP_TIMEOUT +#define LWIP_TCPIP_TIMEOUT 1 +#endif + +/* + ------------------------------------ + ---------- Socket options ---------- + ------------------------------------ +*/ +/** + * LWIP_SOCKET==1: Enable Socket API (require to use sockets.c) + */ +#ifndef LWIP_SOCKET +#define LWIP_SOCKET 0 +#endif + +/** + * LWIP_COMPAT_SOCKETS==1: Enable BSD-style sockets functions names. + * (only used if you use sockets.c) + */ +#ifndef LWIP_COMPAT_SOCKETS +#define LWIP_COMPAT_SOCKETS 1 +#endif + +/** + * LWIP_POSIX_SOCKETS_IO_NAMES==1: Enable POSIX-style sockets functions names. + * Disable this option if you use a POSIX operating system that uses the same + * names (read, write & close). (only used if you use sockets.c) + */ +#ifndef LWIP_POSIX_SOCKETS_IO_NAMES +#define LWIP_POSIX_SOCKETS_IO_NAMES 1 +#endif + +/** + * LWIP_TCP_KEEPALIVE==1: Enable TCP_KEEPIDLE, TCP_KEEPINTVL and TCP_KEEPCNT + * options processing. Note that TCP_KEEPIDLE and TCP_KEEPINTVL have to be set + * in seconds. (does not require sockets.c, and will affect tcp.c) + */ +#ifndef LWIP_TCP_KEEPALIVE +#define LWIP_TCP_KEEPALIVE 0 +#endif + +/** + * LWIP_SO_RCVTIMEO==1: Enable SO_RCVTIMEO processing. + */ +#ifndef LWIP_SO_RCVTIMEO +#define LWIP_SO_RCVTIMEO 0 +#endif + +/** + * LWIP_SO_RCVBUF==1: Enable SO_RCVBUF processing. + */ +#ifndef LWIP_SO_RCVBUF +#define LWIP_SO_RCVBUF 0 +#endif + +/** + * If LWIP_SO_RCVBUF is used, this is the default value for recv_bufsize. + */ +#ifndef RECV_BUFSIZE_DEFAULT +#define RECV_BUFSIZE_DEFAULT INT_MAX +#endif + +/** + * SO_REUSE==1: Enable SO_REUSEADDR option. + */ +#ifndef SO_REUSE +#define SO_REUSE 0 +#endif + +/** + * SO_REUSE_RXTOALL==1: Pass a copy of incoming broadcast/multicast packets + * to all local matches if SO_REUSEADDR is turned on. + * WARNING: Adds a memcpy for every packet if passing to more than one pcb! + */ +#ifndef SO_REUSE_RXTOALL +#define SO_REUSE_RXTOALL 0 +#endif + +/* + ---------------------------------------- + ---------- Statistics options ---------- + ---------------------------------------- +*/ +/** + * LWIP_STATS==1: Enable statistics collection in lwip_stats. + */ +#ifndef LWIP_STATS +#define LWIP_STATS 1 +#endif + +#if LWIP_STATS + +/** + * LWIP_STATS_DISPLAY==1: Compile in the statistics output functions. + */ +#ifndef LWIP_STATS_DISPLAY +#define LWIP_STATS_DISPLAY 0 +#endif + +/** + * LINK_STATS==1: Enable link stats. + */ +#ifndef LINK_STATS +#define LINK_STATS 1 +#endif + +/** + * ETHARP_STATS==1: Enable etharp stats. + */ +#ifndef ETHARP_STATS +#define ETHARP_STATS (LWIP_ARP) +#endif + +/** + * IP_STATS==1: Enable IP stats. + */ +#ifndef IP_STATS +#define IP_STATS 1 +#endif + +/** + * IPFRAG_STATS==1: Enable IP fragmentation stats. Default is + * on if using either frag or reass. + */ +#ifndef IPFRAG_STATS +#define IPFRAG_STATS (IP_REASSEMBLY || IP_FRAG) +#endif + +/** + * ICMP_STATS==1: Enable ICMP stats. + */ +#ifndef ICMP_STATS +#define ICMP_STATS 1 +#endif + +/** + * IGMP_STATS==1: Enable IGMP stats. + */ +#ifndef IGMP_STATS +#define IGMP_STATS (LWIP_IGMP) +#endif + +/** + * UDP_STATS==1: Enable UDP stats. Default is on if + * UDP enabled, otherwise off. + */ +#ifndef UDP_STATS +#define UDP_STATS (LWIP_UDP) +#endif + +/** + * TCP_STATS==1: Enable TCP stats. Default is on if TCP + * enabled, otherwise off. + */ +#ifndef TCP_STATS +#define TCP_STATS (LWIP_TCP) +#endif + +/** + * MEM_STATS==1: Enable mem.c stats. + */ +#ifndef MEM_STATS +#define MEM_STATS ((MEM_LIBC_MALLOC == 0) && (MEM_USE_POOLS == 0)) +#endif + +/** + * MEMP_STATS==1: Enable memp.c pool stats. + */ +#ifndef MEMP_STATS +#define MEMP_STATS (MEMP_MEM_MALLOC == 0) +#endif + +/** + * SYS_STATS==1: Enable system stats (sem and mbox counts, etc). + */ +#ifndef SYS_STATS +#define SYS_STATS (NO_SYS == 0) +#endif + +#else + +#define LINK_STATS 0 +#define IP_STATS 0 +#define IPFRAG_STATS 0 +#define ICMP_STATS 0 +#define IGMP_STATS 0 +#define UDP_STATS 0 +#define TCP_STATS 0 +#define MEM_STATS 0 +#define MEMP_STATS 0 +#define SYS_STATS 0 +#define LWIP_STATS_DISPLAY 0 + +#endif /* LWIP_STATS */ + +/* + --------------------------------- + ---------- PPP options ---------- + --------------------------------- +*/ +/** + * PPP_SUPPORT==1: Enable PPP. + */ +#ifndef PPP_SUPPORT +#define PPP_SUPPORT 0 +#endif + +/** + * PPPOE_SUPPORT==1: Enable PPP Over Ethernet + */ +#ifndef PPPOE_SUPPORT +#define PPPOE_SUPPORT 0 +#endif + +/** + * PPPOS_SUPPORT==1: Enable PPP Over Serial + */ +#ifndef PPPOS_SUPPORT +#define PPPOS_SUPPORT PPP_SUPPORT +#endif + +#if PPP_SUPPORT + +/** + * NUM_PPP: Max PPP sessions. + */ +#ifndef NUM_PPP +#define NUM_PPP 1 +#endif + +/** + * PAP_SUPPORT==1: Support PAP. + */ +#ifndef PAP_SUPPORT +#define PAP_SUPPORT 0 +#endif + +/** + * CHAP_SUPPORT==1: Support CHAP. + */ +#ifndef CHAP_SUPPORT +#define CHAP_SUPPORT 0 +#endif + +/** + * MSCHAP_SUPPORT==1: Support MSCHAP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef MSCHAP_SUPPORT +#define MSCHAP_SUPPORT 0 +#endif + +/** + * CBCP_SUPPORT==1: Support CBCP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef CBCP_SUPPORT +#define CBCP_SUPPORT 0 +#endif + +/** + * CCP_SUPPORT==1: Support CCP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef CCP_SUPPORT +#define CCP_SUPPORT 0 +#endif + +/** + * VJ_SUPPORT==1: Support VJ header compression. + */ +#ifndef VJ_SUPPORT +#define VJ_SUPPORT 0 +#endif + +/** + * MD5_SUPPORT==1: Support MD5 (see also CHAP). + */ +#ifndef MD5_SUPPORT +#define MD5_SUPPORT 0 +#endif + +/* + * Timeouts + */ +#ifndef FSM_DEFTIMEOUT +#define FSM_DEFTIMEOUT 6 /* Timeout time in seconds */ +#endif + +#ifndef FSM_DEFMAXTERMREQS +#define FSM_DEFMAXTERMREQS 2 /* Maximum Terminate-Request transmissions */ +#endif + +#ifndef FSM_DEFMAXCONFREQS +#define FSM_DEFMAXCONFREQS 10 /* Maximum Configure-Request transmissions */ +#endif + +#ifndef FSM_DEFMAXNAKLOOPS +#define FSM_DEFMAXNAKLOOPS 5 /* Maximum number of nak loops */ +#endif + +#ifndef UPAP_DEFTIMEOUT +#define UPAP_DEFTIMEOUT 6 /* Timeout (seconds) for retransmitting req */ +#endif + +#ifndef UPAP_DEFREQTIME +#define UPAP_DEFREQTIME 30 /* Time to wait for auth-req from peer */ +#endif + +#ifndef CHAP_DEFTIMEOUT +#define CHAP_DEFTIMEOUT 6 /* Timeout time in seconds */ +#endif + +#ifndef CHAP_DEFTRANSMITS +#define CHAP_DEFTRANSMITS 10 /* max # times to send challenge */ +#endif + +/* Interval in seconds between keepalive echo requests, 0 to disable. */ +#ifndef LCP_ECHOINTERVAL +#define LCP_ECHOINTERVAL 0 +#endif + +/* Number of unanswered echo requests before failure. */ +#ifndef LCP_MAXECHOFAILS +#define LCP_MAXECHOFAILS 3 +#endif + +/* Max Xmit idle time (in jiffies) before resend flag char. */ +#ifndef PPP_MAXIDLEFLAG +#define PPP_MAXIDLEFLAG 100 +#endif + +/* + * Packet sizes + * + * Note - lcp shouldn't be allowed to negotiate stuff outside these + * limits. See lcp.h in the pppd directory. + * (XXX - these constants should simply be shared by lcp.c instead + * of living in lcp.h) + */ +#define PPP_MTU 1500 /* Default MTU (size of Info field) */ +#ifndef PPP_MAXMTU +/* #define PPP_MAXMTU 65535 - (PPP_HDRLEN + PPP_FCSLEN) */ +#define PPP_MAXMTU 1500 /* Largest MTU we allow */ +#endif +#define PPP_MINMTU 64 +#define PPP_MRU 1500 /* default MRU = max length of info field */ +#define PPP_MAXMRU 1500 /* Largest MRU we allow */ +#ifndef PPP_DEFMRU +#define PPP_DEFMRU 296 /* Try for this */ +#endif +#define PPP_MINMRU 128 /* No MRUs below this */ + +#ifndef MAXNAMELEN +#define MAXNAMELEN 256 /* max length of hostname or name for auth */ +#endif +#ifndef MAXSECRETLEN +#define MAXSECRETLEN 256 /* max length of password or secret */ +#endif + +#endif /* PPP_SUPPORT */ + +/* + -------------------------------------- + ---------- Checksum options ---------- + -------------------------------------- +*/ +/** + * CHECKSUM_GEN_IP==1: Generate checksums in software for outgoing IP packets. + */ +#ifndef CHECKSUM_GEN_IP +#define CHECKSUM_GEN_IP 1 +#endif + +/** + * CHECKSUM_GEN_UDP==1: Generate checksums in software for outgoing UDP packets. + */ +#ifndef CHECKSUM_GEN_UDP +#define CHECKSUM_GEN_UDP 1 +#endif + +/** + * CHECKSUM_GEN_TCP==1: Generate checksums in software for outgoing TCP packets. + */ +#ifndef CHECKSUM_GEN_TCP +#define CHECKSUM_GEN_TCP 1 +#endif + +/** + * CHECKSUM_CHECK_IP==1: Check checksums in software for incoming IP packets. + */ +#ifndef CHECKSUM_CHECK_IP +#define CHECKSUM_CHECK_IP 1 +#endif + +/** + * CHECKSUM_CHECK_UDP==1: Check checksums in software for incoming UDP packets. + */ +#ifndef CHECKSUM_CHECK_UDP +#define CHECKSUM_CHECK_UDP 1 +#endif + +/** + * CHECKSUM_CHECK_TCP==1: Check checksums in software for incoming TCP packets. + */ +#ifndef CHECKSUM_CHECK_TCP +#define CHECKSUM_CHECK_TCP 1 +#endif + +/** + * LWIP_CHECKSUM_ON_COPY==1: Calculate checksum when copying data from + * application buffers to pbufs. + */ +#ifndef LWIP_CHECKSUM_ON_COPY +#define LWIP_CHECKSUM_ON_COPY 0 +#endif + +/* + --------------------------------------- + ---------- Debugging options ---------- + --------------------------------------- +*/ +/** + * LWIP_DBG_MIN_LEVEL: After masking, the value of the debug is + * compared against this value. If it is smaller, then debugging + * messages are written. + */ +#ifndef LWIP_DBG_MIN_LEVEL +#define LWIP_DBG_MIN_LEVEL LWIP_DBG_LEVEL_ALL +#endif + +/** + * LWIP_DBG_TYPES_ON: A mask that can be used to globally enable/disable + * debug messages of certain types. + */ +#ifndef LWIP_DBG_TYPES_ON +#define LWIP_DBG_TYPES_ON LWIP_DBG_ON +#endif + +/** + * ETHARP_DEBUG: Enable debugging in etharp.c. + */ +#ifndef ETHARP_DEBUG +#define ETHARP_DEBUG LWIP_DBG_OFF +#endif + +/** + * NETIF_DEBUG: Enable debugging in netif.c. + */ +#ifndef NETIF_DEBUG +#define NETIF_DEBUG LWIP_DBG_OFF +#endif + +/** + * PBUF_DEBUG: Enable debugging in pbuf.c. + */ +#ifndef PBUF_DEBUG +#define PBUF_DEBUG LWIP_DBG_OFF +#endif + +/** + * API_LIB_DEBUG: Enable debugging in api_lib.c. + */ +#ifndef API_LIB_DEBUG +#define API_LIB_DEBUG LWIP_DBG_OFF +#endif + +/** + * API_MSG_DEBUG: Enable debugging in api_msg.c. + */ +#ifndef API_MSG_DEBUG +#define API_MSG_DEBUG LWIP_DBG_OFF +#endif + +/** + * SOCKETS_DEBUG: Enable debugging in sockets.c. + */ +#ifndef SOCKETS_DEBUG +#define SOCKETS_DEBUG LWIP_DBG_OFF +#endif + +/** + * ICMP_DEBUG: Enable debugging in icmp.c. + */ +#ifndef ICMP_DEBUG +#define ICMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * IGMP_DEBUG: Enable debugging in igmp.c. + */ +#ifndef IGMP_DEBUG +#define IGMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * INET_DEBUG: Enable debugging in inet.c. + */ +#ifndef INET_DEBUG +#define INET_DEBUG LWIP_DBG_OFF +#endif + +/** + * IP_DEBUG: Enable debugging for IP. + */ +#ifndef IP_DEBUG +#define IP_DEBUG LWIP_DBG_OFF +#endif + +/** + * IP_REASS_DEBUG: Enable debugging in ip_frag.c for both frag & reass. + */ +#ifndef IP_REASS_DEBUG +#define IP_REASS_DEBUG LWIP_DBG_OFF +#endif + +/** + * RAW_DEBUG: Enable debugging in raw.c. + */ +#ifndef RAW_DEBUG +#define RAW_DEBUG LWIP_DBG_OFF +#endif + +/** + * MEM_DEBUG: Enable debugging in mem.c. + */ +#ifndef MEM_DEBUG +#define MEM_DEBUG LWIP_DBG_OFF +#endif + +/** + * MEMP_DEBUG: Enable debugging in memp.c. + */ +#ifndef MEMP_DEBUG +#define MEMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SYS_DEBUG: Enable debugging in sys.c. + */ +#ifndef SYS_DEBUG +#define SYS_DEBUG LWIP_DBG_OFF +#endif + +/** + * TIMERS_DEBUG: Enable debugging in timers.c. + */ +#ifndef TIMERS_DEBUG +#define TIMERS_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_DEBUG: Enable debugging for TCP. + */ +#ifndef TCP_DEBUG +#define TCP_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_INPUT_DEBUG: Enable debugging in tcp_in.c for incoming debug. + */ +#ifndef TCP_INPUT_DEBUG +#define TCP_INPUT_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_FR_DEBUG: Enable debugging in tcp_in.c for fast retransmit. + */ +#ifndef TCP_FR_DEBUG +#define TCP_FR_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_RTO_DEBUG: Enable debugging in TCP for retransmit + * timeout. + */ +#ifndef TCP_RTO_DEBUG +#define TCP_RTO_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_CWND_DEBUG: Enable debugging for TCP congestion window. + */ +#ifndef TCP_CWND_DEBUG +#define TCP_CWND_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_WND_DEBUG: Enable debugging in tcp_in.c for window updating. + */ +#ifndef TCP_WND_DEBUG +#define TCP_WND_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_OUTPUT_DEBUG: Enable debugging in tcp_out.c output functions. + */ +#ifndef TCP_OUTPUT_DEBUG +#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_RST_DEBUG: Enable debugging for TCP with the RST message. + */ +#ifndef TCP_RST_DEBUG +#define TCP_RST_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_QLEN_DEBUG: Enable debugging for TCP queue lengths. + */ +#ifndef TCP_QLEN_DEBUG +#define TCP_QLEN_DEBUG LWIP_DBG_OFF +#endif + +/** + * UDP_DEBUG: Enable debugging in UDP. + */ +#ifndef UDP_DEBUG +#define UDP_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCPIP_DEBUG: Enable debugging in tcpip.c. + */ +#ifndef TCPIP_DEBUG +#define TCPIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * PPP_DEBUG: Enable debugging for PPP. + */ +#ifndef PPP_DEBUG +#define PPP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SLIP_DEBUG: Enable debugging in slipif.c. + */ +#ifndef SLIP_DEBUG +#define SLIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * DHCP_DEBUG: Enable debugging in dhcp.c. + */ +#ifndef DHCP_DEBUG +#define DHCP_DEBUG LWIP_DBG_OFF +#endif + +/** + * AUTOIP_DEBUG: Enable debugging in autoip.c. + */ +#ifndef AUTOIP_DEBUG +#define AUTOIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SNMP_MSG_DEBUG: Enable debugging for SNMP messages. + */ +#ifndef SNMP_MSG_DEBUG +#define SNMP_MSG_DEBUG LWIP_DBG_OFF +#endif + +/** + * SNMP_MIB_DEBUG: Enable debugging for SNMP MIBs. + */ +#ifndef SNMP_MIB_DEBUG +#define SNMP_MIB_DEBUG LWIP_DBG_OFF +#endif + +/** + * DNS_DEBUG: Enable debugging for DNS. + */ +#ifndef DNS_DEBUG +#define DNS_DEBUG LWIP_DBG_OFF +#endif + +/** + * NAPT_DEBUG: Enable debugging for NAPT. + */ +#ifndef NAPT_DEBUG +#define NAPT_DEBUG LWIP_DBG_OFF +#endif + +#endif /* __LWIP_OPT_H__ */ diff --git a/include/lwipopts.h b/include/lwipopts.h new file mode 100644 index 0000000..459d0be --- /dev/null +++ b/include/lwipopts.h @@ -0,0 +1,2097 @@ +/** + * @file + * + * lwIP Options Configuration + */ + +/* + * Copyright (c) 2001-2004 Swedish Institute of Computer Science. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without modification, + * are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright notice, + * this list of conditions and the following disclaimer in the documentation + * and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT + * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, + * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT + * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING + * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY + * OF SUCH DAMAGE. + * + * This file is part of the lwIP TCP/IP stack. + * + * Author: Adam Dunkels + * + */ +#ifndef __LWIPOPTS_H__ +#define __LWIPOPTS_H__ + + +/* + ----------------------------------------------- + ---------- Platform specific locking ---------- + ----------------------------------------------- +*/ + +/** + * SYS_LIGHTWEIGHT_PROT==1: if you want inter-task protection for certain + * critical regions during buffer allocation, deallocation and memory + * allocation and deallocation. + */ +#ifndef SYS_LIGHTWEIGHT_PROT +#define SYS_LIGHTWEIGHT_PROT 0 +#endif + +/** + * NO_SYS==1: Provides VERY minimal functionality. Otherwise, + * use lwIP facilities. + */ +#ifndef NO_SYS +#define NO_SYS 1 +#endif + +/** + * NO_SYS_NO_TIMERS==1: Drop support for sys_timeout when NO_SYS==1 + * Mainly for compatibility to old versions. + */ +#ifndef NO_SYS_NO_TIMERS +#define NO_SYS_NO_TIMERS 0 +#endif + +/** + * MEMCPY: override this if you have a faster implementation at hand than the + * one included in your C library + */ +#ifndef MEMCPY +#define MEMCPY(dst,src,len) os_memcpy(dst,src,len) +#endif + +/** + * SMEMCPY: override this with care! Some compilers (e.g. gcc) can inline a + * call to memcpy() if the length is known at compile time and is small. + */ +#ifndef SMEMCPY +#define SMEMCPY(dst,src,len) os_memcpy(dst,src,len) +#endif + +/* + ------------------------------------ + ---------- Memory options ---------- + ------------------------------------ +*/ +/** + * MEM_LIBC_MALLOC==1: Use malloc/free/realloc provided by your C-library + * instead of the lwip internal allocator. Can save code size if you + * already use it. + */ +#ifndef MEM_LIBC_MALLOC +#define MEM_LIBC_MALLOC 1 +#endif + +/** +* MEMP_MEM_MALLOC==1: Use mem_malloc/mem_free instead of the lwip pool allocator. +* Especially useful with MEM_LIBC_MALLOC but handle with care regarding execution +* speed and usage from interrupts! +*/ +#ifndef MEMP_MEM_MALLOC +#define MEMP_MEM_MALLOC 1 +#endif + +/** + * MEM_ALIGNMENT: should be set to the alignment of the CPU + * 4 byte alignment -> #define MEM_ALIGNMENT 4 + * 2 byte alignment -> #define MEM_ALIGNMENT 2 + */ +#ifndef MEM_ALIGNMENT +#define MEM_ALIGNMENT 4 +#endif + +/** + * MEM_SIZE: the size of the heap memory. If the application will send + * a lot of data that needs to be copied, this should be set high. + */ +#ifndef MEM_SIZE +#define MEM_SIZE 16000 +#endif + +/** + * MEMP_SEPARATE_POOLS: if defined to 1, each pool is placed in its own array. + * This can be used to individually change the location of each pool. + * Default is one big array for all pools + */ +#ifndef MEMP_SEPARATE_POOLS +#define MEMP_SEPARATE_POOLS 1 +#endif + +/** + * MEMP_OVERFLOW_CHECK: memp overflow protection reserves a configurable + * amount of bytes before and after each memp element in every pool and fills + * it with a prominent default value. + * MEMP_OVERFLOW_CHECK == 0 no checking + * MEMP_OVERFLOW_CHECK == 1 checks each element when it is freed + * MEMP_OVERFLOW_CHECK >= 2 checks each element in every pool every time + * memp_malloc() or memp_free() is called (useful but slow!) + */ +#ifndef MEMP_OVERFLOW_CHECK +#define MEMP_OVERFLOW_CHECK 0 +#endif + +/** + * MEMP_SANITY_CHECK==1: run a sanity check after each memp_free() to make + * sure that there are no cycles in the linked lists. + */ +#ifndef MEMP_SANITY_CHECK +#define MEMP_SANITY_CHECK 1 +#endif + +/** + * MEM_USE_POOLS==1: Use an alternative to malloc() by allocating from a set + * of memory pools of various sizes. When mem_malloc is called, an element of + * the smallest pool that can provide the length needed is returned. + * To use this, MEMP_USE_CUSTOM_POOLS also has to be enabled. + */ +#ifndef MEM_USE_POOLS +#define MEM_USE_POOLS 0 +#endif + +/** + * MEM_USE_POOLS_TRY_BIGGER_POOL==1: if one malloc-pool is empty, try the next + * bigger pool - WARNING: THIS MIGHT WASTE MEMORY but it can make a system more + * reliable. */ +#ifndef MEM_USE_POOLS_TRY_BIGGER_POOL +#define MEM_USE_POOLS_TRY_BIGGER_POOL 0 +#endif + +/** + * MEMP_USE_CUSTOM_POOLS==1: whether to include a user file lwippools.h + * that defines additional pools beyond the "standard" ones required + * by lwIP. If you set this to 1, you must have lwippools.h in your + * inlude path somewhere. + */ +#ifndef MEMP_USE_CUSTOM_POOLS +#define MEMP_USE_CUSTOM_POOLS 0 +#endif + +/** + * Set this to 1 if you want to free PBUF_RAM pbufs (or call mem_free()) from + * interrupt context (or another context that doesn't allow waiting for a + * semaphore). + * If set to 1, mem_malloc will be protected by a semaphore and SYS_ARCH_PROTECT, + * while mem_free will only use SYS_ARCH_PROTECT. mem_malloc SYS_ARCH_UNPROTECTs + * with each loop so that mem_free can run. + * + * ATTENTION: As you can see from the above description, this leads to dis-/ + * enabling interrupts often, which can be slow! Also, on low memory, mem_malloc + * can need longer. + * + * If you don't want that, at least for NO_SYS=0, you can still use the following + * functions to enqueue a deallocation call which then runs in the tcpip_thread + * context: + * - pbuf_free_callback(p); + * - mem_free_callback(m); + */ +#ifndef LWIP_ALLOW_MEM_FREE_FROM_OTHER_CONTEXT +#define LWIP_ALLOW_MEM_FREE_FROM_OTHER_CONTEXT 0 +#endif + +/* + ------------------------------------------------ + ---------- Internal Memory Pool Sizes ---------- + ------------------------------------------------ +*/ +/** + * MEMP_NUM_PBUF: the number of memp struct pbufs (used for PBUF_ROM and PBUF_REF). + * If the application sends a lot of data out of ROM (or other static memory), + * this should be set high. + */ +#ifndef MEMP_NUM_PBUF +#define MEMP_NUM_PBUF 10 +#endif + +/** + * MEMP_NUM_RAW_PCB: Number of raw connection PCBs + * (requires the LWIP_RAW option) + */ +#ifndef MEMP_NUM_RAW_PCB +#define MEMP_NUM_RAW_PCB 4 +#endif + +/** + * MEMP_NUM_UDP_PCB: the number of UDP protocol control blocks. One + * per active UDP "connection". + * (requires the LWIP_UDP option) + */ +#ifndef MEMP_NUM_UDP_PCB +#define MEMP_NUM_UDP_PCB 4 +#endif + +/** + * MEMP_NUM_TCP_PCB: the number of simulatenously active TCP connections. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_PCB +#define MEMP_NUM_TCP_PCB (*(volatile uint32*)0x600011FC) +#endif + +/** + * MEMP_NUM_TCP_PCB_LISTEN: the number of listening TCP connections. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_PCB_LISTEN +#define MEMP_NUM_TCP_PCB_LISTEN 2 +#endif + +/** + * MEMP_NUM_TCP_SEG: the number of simultaneously queued TCP segments. + * (requires the LWIP_TCP option) + */ +#ifndef MEMP_NUM_TCP_SEG +#define MEMP_NUM_TCP_SEG 16 +#endif + +/** + * MEMP_NUM_REASSDATA: the number of simultaneously IP packets queued for + * reassembly (whole packets, not fragments!) + */ +#ifndef MEMP_NUM_REASSDATA +#define MEMP_NUM_REASSDATA 0 +#endif + +/** + * MEMP_NUM_FRAG_PBUF: the number of IP fragments simultaneously sent + * (fragments, not whole packets!). + * This is only used with IP_FRAG_USES_STATIC_BUF==0 and + * LWIP_NETIF_TX_SINGLE_PBUF==0 and only has to be > 1 with DMA-enabled MACs + * where the packet is not yet sent when netif->output returns. + */ +#ifndef MEMP_NUM_FRAG_PBUF +#define MEMP_NUM_FRAG_PBUF 0 +#endif + +/** + * MEMP_NUM_ARP_QUEUE: the number of simulateously queued outgoing + * packets (pbufs) that are waiting for an ARP request (to resolve + * their destination address) to finish. + * (requires the ARP_QUEUEING option) + */ +#ifndef MEMP_NUM_ARP_QUEUE +#define MEMP_NUM_ARP_QUEUE 10 +#endif + +/** + * MEMP_NUM_IGMP_GROUP: The number of multicast groups whose network interfaces + * can be members et the same time (one per netif - allsystems group -, plus one + * per netif membership). + * (requires the LWIP_IGMP option) + */ +#ifndef MEMP_NUM_IGMP_GROUP +#define MEMP_NUM_IGMP_GROUP 8 +#endif + +/** + * MEMP_NUM_SYS_TIMEOUT: the number of simulateously active timeouts. + * (requires NO_SYS==0) + */ +#ifndef MEMP_NUM_SYS_TIMEOUT +#define MEMP_NUM_SYS_TIMEOUT 8 +#endif + +/** + * MEMP_NUM_NETBUF: the number of struct netbufs. + * (only needed if you use the sequential API, like api_lib.c) + */ +#ifndef MEMP_NUM_NETBUF +#define MEMP_NUM_NETBUF 0 +#endif + +/** + * MEMP_NUM_NETCONN: the number of struct netconns. + * (only needed if you use the sequential API, like api_lib.c) + */ +#ifndef MEMP_NUM_NETCONN +#define MEMP_NUM_NETCONN 0 +#endif + +/** + * MEMP_NUM_TCPIP_MSG_API: the number of struct tcpip_msg, which are used + * for callback/timeout API communication. + * (only needed if you use tcpip.c) + */ +#ifndef MEMP_NUM_TCPIP_MSG_API +#define MEMP_NUM_TCPIP_MSG_API 4 +#endif + +/** + * MEMP_NUM_TCPIP_MSG_INPKT: the number of struct tcpip_msg, which are used + * for incoming packets. + * (only needed if you use tcpip.c) + */ +#ifndef MEMP_NUM_TCPIP_MSG_INPKT +#define MEMP_NUM_TCPIP_MSG_INPKT 4 +#endif + +/** + * MEMP_NUM_SNMP_NODE: the number of leafs in the SNMP tree. + */ +#ifndef MEMP_NUM_SNMP_NODE +#define MEMP_NUM_SNMP_NODE 0 +#endif + +/** + * MEMP_NUM_SNMP_ROOTNODE: the number of branches in the SNMP tree. + * Every branch has one leaf (MEMP_NUM_SNMP_NODE) at least! + */ +#ifndef MEMP_NUM_SNMP_ROOTNODE +#define MEMP_NUM_SNMP_ROOTNODE 0 +#endif + +/** + * MEMP_NUM_SNMP_VARBIND: the number of concurrent requests (does not have to + * be changed normally) - 2 of these are used per request (1 for input, + * 1 for output) + */ +#ifndef MEMP_NUM_SNMP_VARBIND +#define MEMP_NUM_SNMP_VARBIND 0 +#endif + +/** + * MEMP_NUM_SNMP_VALUE: the number of OID or values concurrently used + * (does not have to be changed normally) - 3 of these are used per request + * (1 for the value read and 2 for OIDs - input and output) + */ +#ifndef MEMP_NUM_SNMP_VALUE +#define MEMP_NUM_SNMP_VALUE 0 +#endif + +/** + * MEMP_NUM_NETDB: the number of concurrently running lwip_addrinfo() calls + * (before freeing the corresponding memory using lwip_freeaddrinfo()). + */ +#ifndef MEMP_NUM_NETDB +#define MEMP_NUM_NETDB 0 +#endif + +/** + * MEMP_NUM_LOCALHOSTLIST: the number of host entries in the local host list + * if DNS_LOCAL_HOSTLIST_IS_DYNAMIC==1. + */ +#ifndef MEMP_NUM_LOCALHOSTLIST +#define MEMP_NUM_LOCALHOSTLIST 0 +#endif + +/** + * MEMP_NUM_PPPOE_INTERFACES: the number of concurrently active PPPoE + * interfaces (only used with PPPOE_SUPPORT==1) + */ +#ifndef MEMP_NUM_PPPOE_INTERFACES +#define MEMP_NUM_PPPOE_INTERFACES 0 +#endif + +/** + * PBUF_POOL_SIZE: the number of buffers in the pbuf pool. + */ +#ifndef PBUF_POOL_SIZE +#define PBUF_POOL_SIZE 10 +#endif + +/* + --------------------------------- + ---------- ARP options ---------- + --------------------------------- +*/ +/** + * LWIP_ARP==1: Enable ARP functionality. + */ +#ifndef LWIP_ARP +#define LWIP_ARP 1 +#endif + +/** + * ARP_TABLE_SIZE: Number of active MAC-IP address pairs cached. + */ +#ifndef ARP_TABLE_SIZE +#define ARP_TABLE_SIZE 10 +#endif + +/** + * ARP_QUEUEING==1: Multiple outgoing packets are queued during hardware address + * resolution. By default, only the most recent packet is queued per IP address. + * This is sufficient for most protocols and mainly reduces TCP connection + * startup time. Set this to 1 if you know your application sends more than one + * packet in a row to an IP address that is not in the ARP cache. + */ +#ifndef ARP_QUEUEING +#define ARP_QUEUEING 1 +#endif + +/** + * ETHARP_TRUST_IP_MAC==1: Incoming IP packets cause the ARP table to be + * updated with the source MAC and IP addresses supplied in the packet. + * You may want to disable this if you do not trust LAN peers to have the + * correct addresses, or as a limited approach to attempt to handle + * spoofing. If disabled, lwIP will need to make a new ARP request if + * the peer is not already in the ARP table, adding a little latency. + * The peer *is* in the ARP table if it requested our address before. + * Also notice that this slows down input processing of every IP packet! + */ +#ifndef ETHARP_TRUST_IP_MAC +#define ETHARP_TRUST_IP_MAC 1 +#endif + +/** + * ETHARP_SUPPORT_VLAN==1: support receiving ethernet packets with VLAN header. + * Additionally, you can define ETHARP_VLAN_CHECK to an u16_t VLAN ID to check. + * If ETHARP_VLAN_CHECK is defined, only VLAN-traffic for this VLAN is accepted. + * If ETHARP_VLAN_CHECK is not defined, all traffic is accepted. + */ +#ifndef ETHARP_SUPPORT_VLAN +#define ETHARP_SUPPORT_VLAN 0 +#endif + +/** LWIP_ETHERNET==1: enable ethernet support for PPPoE even though ARP + * might be disabled + */ +#ifndef LWIP_ETHERNET +#define LWIP_ETHERNET (LWIP_ARP || PPPOE_SUPPORT) +#endif + +/** ETH_PAD_SIZE: number of bytes added before the ethernet header to ensure + * alignment of payload after that header. Since the header is 14 bytes long, + * without this padding e.g. addresses in the IP header will not be aligned + * on a 32-bit boundary, so setting this to 2 can speed up 32-bit-platforms. + */ +#ifndef ETH_PAD_SIZE +#define ETH_PAD_SIZE 0 +#endif + +/** ETHARP_SUPPORT_STATIC_ENTRIES==1: enable code to support static ARP table + * entries (using etharp_add_static_entry/etharp_remove_static_entry). + */ +#ifndef ETHARP_SUPPORT_STATIC_ENTRIES +#define ETHARP_SUPPORT_STATIC_ENTRIES 0 +#endif + + +/* + -------------------------------- + ---------- IP options ---------- + -------------------------------- +*/ +/** + * IP_FORWARD==1: Enables the ability to forward IP packets across network + * interfaces. If you are going to run lwIP on a device with only one network + * interface, define this to 0. + */ +#ifndef IP_FORWARD +#define IP_FORWARD 1 +#endif + +/** + * IP_NAPT==1: Enables the ability to do Network Address Port Translation (NAPT) + * on forwarded packets. This only makes sense with IP_FORWARD==1. + */ +#ifndef IP_NAPT +#define IP_NAPT 1 +#endif + +/** + * IP_NAPT_DYNAMIC==1: Saves the memory for the NAPT tables if not required. + * If NAPT is used, ip_napt_init() has to be called explicitly once. + */ +#ifndef IP_NAPT_DYNAMIC +#define IP_NAPT_DYNAMIC 0 +#endif + +/** + * IP_OPTIONS_ALLOWED: Defines the behavior for IP options. + * IP_OPTIONS_ALLOWED==0: All packets with IP options are dropped. + * IP_OPTIONS_ALLOWED==1: IP options are allowed (but not parsed). + */ +#ifndef IP_OPTIONS_ALLOWED +#define IP_OPTIONS_ALLOWED 1 +#endif + +/** + * IP_REASSEMBLY==1: Reassemble incoming fragmented IP packets. Note that + * this option does not affect outgoing packet sizes, which can be controlled + * via IP_FRAG. + */ +#ifndef IP_REASSEMBLY +#define IP_REASSEMBLY 0 +#endif + +/** + * IP_FRAG==1: Fragment outgoing IP packets if their size exceeds MTU. Note + * that this option does not affect incoming packet sizes, which can be + * controlled via IP_REASSEMBLY. + */ +#ifndef IP_FRAG +#define IP_FRAG 0 +#endif + +/** + * IP_REASS_MAXAGE: Maximum time (in multiples of IP_TMR_INTERVAL - so seconds, normally) + * a fragmented IP packet waits for all fragments to arrive. If not all fragments arrived + * in this time, the whole packet is discarded. + */ +#ifndef IP_REASS_MAXAGE +#define IP_REASS_MAXAGE 3 +#endif + +/** + * IP_REASS_MAX_PBUFS: Total maximum amount of pbufs waiting to be reassembled. + * Since the received pbufs are enqueued, be sure to configure + * PBUF_POOL_SIZE > IP_REASS_MAX_PBUFS so that the stack is still able to receive + * packets even if the maximum amount of fragments is enqueued for reassembly! + */ +#ifndef IP_REASS_MAX_PBUFS +#define IP_REASS_MAX_PBUFS 10 +#endif + +/** + * IP_FRAG_USES_STATIC_BUF==1: Use a static MTU-sized buffer for IP + * fragmentation. Otherwise pbufs are allocated and reference the original + * packet data to be fragmented (or with LWIP_NETIF_TX_SINGLE_PBUF==1, + * new PBUF_RAM pbufs are used for fragments). + * ATTENTION: IP_FRAG_USES_STATIC_BUF==1 may not be used for DMA-enabled MACs! + */ +#ifndef IP_FRAG_USES_STATIC_BUF +#define IP_FRAG_USES_STATIC_BUF 1 +#endif + +/** + * IP_FRAG_MAX_MTU: Assumed max MTU on any interface for IP frag buffer + * (requires IP_FRAG_USES_STATIC_BUF==1) + */ +#if IP_FRAG_USES_STATIC_BUF && !defined(IP_FRAG_MAX_MTU) +#define IP_FRAG_MAX_MTU 1500 +#endif + +/** + * IP_DEFAULT_TTL: Default value for Time-To-Live used by transport layers. + */ +#ifndef IP_DEFAULT_TTL +#define IP_DEFAULT_TTL 255 +#endif + +/** + * IP_SOF_BROADCAST=1: Use the SOF_BROADCAST field to enable broadcast + * filter per pcb on udp and raw send operations. To enable broadcast filter + * on recv operations, you also have to set IP_SOF_BROADCAST_RECV=1. + */ +#ifndef IP_SOF_BROADCAST +#define IP_SOF_BROADCAST 0 +#endif + +/** + * IP_SOF_BROADCAST_RECV (requires IP_SOF_BROADCAST=1) enable the broadcast + * filter on recv operations. + */ +#ifndef IP_SOF_BROADCAST_RECV +#define IP_SOF_BROADCAST_RECV 0 +#endif + +/* + ---------------------------------- + ---------- ICMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_ICMP==1: Enable ICMP module inside the IP stack. + * Be careful, disable that make your product non-compliant to RFC1122 + */ +#ifndef LWIP_ICMP +#define LWIP_ICMP 1 +#endif + +/** + * ICMP_TTL: Default value for Time-To-Live used by ICMP packets. + */ +#ifndef ICMP_TTL +#define ICMP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * LWIP_BROADCAST_PING==1: respond to broadcast pings (default is unicast only) + */ +#ifndef LWIP_BROADCAST_PING +#define LWIP_BROADCAST_PING 0 +#endif + +/** + * LWIP_MULTICAST_PING==1: respond to multicast pings (default is unicast only) + */ +#ifndef LWIP_MULTICAST_PING +#define LWIP_MULTICAST_PING 0 +#endif + +/* + --------------------------------- + ---------- RAW options ---------- + --------------------------------- +*/ +/** + * LWIP_RAW==1: Enable application layer to hook into the IP layer itself. + */ +#ifndef LWIP_RAW +#define LWIP_RAW 1 +#endif + +/** + * LWIP_RAW==1: Enable application layer to hook into the IP layer itself. + */ +#ifndef RAW_TTL +#define RAW_TTL (IP_DEFAULT_TTL) +#endif + +/* + ---------------------------------- + ---------- DHCP options ---------- + ---------------------------------- +*/ +/** + * LWIP_DHCP==1: Enable DHCP module. + */ +#ifndef LWIP_DHCP +#define LWIP_DHCP 1 +#endif + +/** + * DHCP_DOES_ARP_CHECK==1: Do an ARP check on the offered address. + */ +#ifndef DHCP_DOES_ARP_CHECK +#define DHCP_DOES_ARP_CHECK ((LWIP_DHCP) && (LWIP_ARP)) +#endif + +/** + * DHCP_MAXRTX: Maximum number of retries of current request. + */ +#ifndef DHCP_MAXRTX +#define DHCP_MAXRTX (*(volatile uint32*)0x600011E0) +#endif + +/* + ------------------------------------ + ---------- AUTOIP options ---------- + ------------------------------------ +*/ +/** + * LWIP_AUTOIP==1: Enable AUTOIP module. + */ +#ifndef LWIP_AUTOIP +#define LWIP_AUTOIP 0 +#endif + +/** + * LWIP_DHCP_AUTOIP_COOP==1: Allow DHCP and AUTOIP to be both enabled on + * the same interface at the same time. + */ +#ifndef LWIP_DHCP_AUTOIP_COOP +#define LWIP_DHCP_AUTOIP_COOP 0 +#endif + +/** + * LWIP_DHCP_AUTOIP_COOP_TRIES: Set to the number of DHCP DISCOVER probes + * that should be sent before falling back on AUTOIP. This can be set + * as low as 1 to get an AutoIP address very quickly, but you should + * be prepared to handle a changing IP address when DHCP overrides + * AutoIP. + */ +#ifndef LWIP_DHCP_AUTOIP_COOP_TRIES +#define LWIP_DHCP_AUTOIP_COOP_TRIES 9 +#endif + +/* + ---------------------------------- + ---------- SNMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_SNMP==1: Turn on SNMP module. UDP must be available for SNMP + * transport. + */ +#ifndef LWIP_SNMP +#define LWIP_SNMP 0 +#endif + +/** + * SNMP_CONCURRENT_REQUESTS: Number of concurrent requests the module will + * allow. At least one request buffer is required. + */ +#ifndef SNMP_CONCURRENT_REQUESTS +#define SNMP_CONCURRENT_REQUESTS 0 +#endif + +/** + * SNMP_TRAP_DESTINATIONS: Number of trap destinations. At least one trap + * destination is required + */ +#ifndef SNMP_TRAP_DESTINATIONS +#define SNMP_TRAP_DESTINATIONS 0 +#endif + +/** + * SNMP_PRIVATE_MIB: + */ +#ifndef SNMP_PRIVATE_MIB +#define SNMP_PRIVATE_MIB 0 +#endif + +/** + * Only allow SNMP write actions that are 'safe' (e.g. disabeling netifs is not + * a safe action and disabled when SNMP_SAFE_REQUESTS = 1). + * Unsafe requests are disabled by default! + */ +#ifndef SNMP_SAFE_REQUESTS +#define SNMP_SAFE_REQUESTS 0 +#endif + +/** + * The maximum length of strings used. This affects the size of + * MEMP_SNMP_VALUE elements. + */ +#ifndef SNMP_MAX_OCTET_STRING_LEN +#define SNMP_MAX_OCTET_STRING_LEN 127 +#endif + +/** + * The maximum depth of the SNMP tree. + * With private MIBs enabled, this depends on your MIB! + * This affects the size of MEMP_SNMP_VALUE elements. + */ +#ifndef SNMP_MAX_TREE_DEPTH +#define SNMP_MAX_TREE_DEPTH 15 +#endif + +/** + * The size of the MEMP_SNMP_VALUE elements, normally calculated from + * SNMP_MAX_OCTET_STRING_LEN and SNMP_MAX_TREE_DEPTH. + */ +#ifndef SNMP_MAX_VALUE_SIZE +#define SNMP_MAX_VALUE_SIZE LWIP_MAX((SNMP_MAX_OCTET_STRING_LEN)+1, sizeof(s32_t)*(SNMP_MAX_TREE_DEPTH)) +#endif + +/* + ---------------------------------- + ---------- IGMP options ---------- + ---------------------------------- +*/ +/** + * LWIP_IGMP==1: Turn on IGMP module. + */ +#ifndef LWIP_IGMP +#define LWIP_IGMP 1 +#endif +/* + ---------------------------------- + ---------- MDNS options ---------- + ---------------------------------- +*/ +/** + * LWIP_MDNS==1: Turn on MDNS module. + */ +#ifndef LWIP_MDNS +#define LWIP_MDNS 1 +#endif +/* +/* + ---------------------------------- + ---------- DNS options ----------- + ---------------------------------- +*/ +/** + * LWIP_DNS==1: Turn on DNS module. UDP must be available for DNS + * transport. + */ +#ifndef LWIP_DNS +#define LWIP_DNS 1 +#endif + +/** DNS maximum number of entries to maintain locally. */ +#ifndef DNS_TABLE_SIZE +#define DNS_TABLE_SIZE 4 +#endif + +/** DNS maximum host name length supported in the name table. */ +#ifndef DNS_MAX_NAME_LENGTH +#define DNS_MAX_NAME_LENGTH 256 +#endif + +/** The maximum of DNS servers */ +#ifndef DNS_MAX_SERVERS +#define DNS_MAX_SERVERS 2 +#endif + +/** DNS do a name checking between the query and the response. */ +#ifndef DNS_DOES_NAME_CHECK +#define DNS_DOES_NAME_CHECK 1 +#endif + +/** DNS message max. size. Default value is RFC compliant. */ +#ifndef DNS_MSG_SIZE +#define DNS_MSG_SIZE 512 +#endif + +/** DNS_LOCAL_HOSTLIST: Implements a local host-to-address list. If enabled, + * you have to define + * #define DNS_LOCAL_HOSTLIST_INIT {{"host1", 0x123}, {"host2", 0x234}} + * (an array of structs name/address, where address is an u32_t in network + * byte order). + * + * Instead, you can also use an external function: + * #define DNS_LOOKUP_LOCAL_EXTERN(x) extern u32_t my_lookup_function(const char *name) + * that returns the IP address or INADDR_NONE if not found. + */ +#ifndef DNS_LOCAL_HOSTLIST +#define DNS_LOCAL_HOSTLIST 0 +#endif /* DNS_LOCAL_HOSTLIST */ + +/** If this is turned on, the local host-list can be dynamically changed + * at runtime. */ +#ifndef DNS_LOCAL_HOSTLIST_IS_DYNAMIC +#define DNS_LOCAL_HOSTLIST_IS_DYNAMIC 0 +#endif /* DNS_LOCAL_HOSTLIST_IS_DYNAMIC */ + +/* + --------------------------------- + ---------- UDP options ---------- + --------------------------------- +*/ +/** + * LWIP_UDP==1: Turn on UDP. + */ +#ifndef LWIP_UDP +#define LWIP_UDP 1 +#endif + +/** + * LWIP_UDPLITE==1: Turn on UDP-Lite. (Requires LWIP_UDP) + */ +#ifndef LWIP_UDPLITE +#define LWIP_UDPLITE 0 +#endif + +/** + * UDP_TTL: Default Time-To-Live value. + */ +#ifndef UDP_TTL +#define UDP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * LWIP_NETBUF_RECVINFO==1: append destination addr and port to every netbuf. + */ +#ifndef LWIP_NETBUF_RECVINFO +#define LWIP_NETBUF_RECVINFO 0 +#endif + +/* + --------------------------------- + ---------- TCP options ---------- + --------------------------------- +*/ +/** + * LWIP_TCP==1: Turn on TCP. + */ +#ifndef LWIP_TCP +#define LWIP_TCP 1 +#endif + +/** + * TCP_TTL: Default Time-To-Live value. + */ +#ifndef TCP_TTL +#define TCP_TTL (IP_DEFAULT_TTL) +#endif + +/** + * TCP_WND: The size of a TCP window. This must be at least + * (2 * TCP_MSS) for things to work well + */ +#ifndef TCP_WND +#define TCP_WND (*(volatile uint32*)0x600011F0) +#endif + +/** + * TCP_MAXRTX: Maximum number of retransmissions of data segments. + */ +#ifndef TCP_MAXRTX +#define TCP_MAXRTX (*(volatile uint32*)0x600011E8) +#endif + +/** + * TCP_SYNMAXRTX: Maximum number of retransmissions of SYN segments. + */ +#ifndef TCP_SYNMAXRTX +#define TCP_SYNMAXRTX (*(volatile uint32*)0x600011E4) +#endif + +/** + * TCP_MAXRTO: Maximum retransmission timeout of data segments. + */ +#ifndef TCP_MAXRTO +#define TCP_MAXRTO 10 +#endif + +/** + * TCP_MINRTO: Minimum retransmission timeout of data segments. + */ +#ifndef TCP_MINRTO +#define TCP_MINRTO 2 +#endif + +/** + * TCP_QUEUE_OOSEQ==1: TCP will queue segments that arrive out of order. + * Define to 0 if your device is low on memory. + */ +#ifndef TCP_QUEUE_OOSEQ +#define TCP_QUEUE_OOSEQ 1 +#endif + +#if 1 +/** + * TCP_MSS: TCP Maximum segment size. (default is 536, a conservative default, + * you might want to increase this.) + * For the receive side, this MSS is advertised to the remote side + * when opening a connection. For the transmit size, this MSS sets + * an upper limit on the MSS advertised by the remote host. + */ +#ifndef TCP_MSS +#define TCP_MSS 536 +#endif +#endif + +/** + * TCP_CALCULATE_EFF_SEND_MSS: "The maximum size of a segment that TCP really + * sends, the 'effective send MSS,' MUST be the smaller of the send MSS (which + * reflects the available reassembly buffer size at the remote host) and the + * largest size permitted by the IP layer" (RFC 1122) + * Setting this to 1 enables code that checks TCP_MSS against the MTU of the + * netif used for a connection and limits the MSS if it would be too big otherwise. + */ +#ifndef TCP_CALCULATE_EFF_SEND_MSS +#define TCP_CALCULATE_EFF_SEND_MSS 1 +#endif + + +/** + * TCP_SND_BUF: TCP sender buffer space (bytes). + */ +#ifndef TCP_SND_BUF +#define TCP_SND_BUF (2 * TCP_MSS) +#endif + +/** + * TCP_SND_QUEUELEN: TCP sender buffer space (pbufs). This must be at least + * as much as (2 * TCP_SND_BUF/TCP_MSS) for things to work. + */ +#ifndef TCP_SND_QUEUELEN +#define TCP_SND_QUEUELEN ((4 * (TCP_SND_BUF) + (TCP_MSS - 1))/(TCP_MSS)) +#endif + +/** + * TCP_SNDLOWAT: TCP writable space (bytes). This must be less than + * TCP_SND_BUF. It is the amount of space which must be available in the + * TCP snd_buf for select to return writable (combined with TCP_SNDQUEUELOWAT). + */ +#ifndef TCP_SNDLOWAT +#define TCP_SNDLOWAT ((TCP_SND_BUF)/2) +#endif + +/** + * TCP_SNDQUEUELOWAT: TCP writable bufs (pbuf count). This must be grater + * than TCP_SND_QUEUELEN. If the number of pbufs queued on a pcb drops below + * this number, select returns writable (combined with TCP_SNDLOWAT). + */ +#ifndef TCP_SNDQUEUELOWAT +#define TCP_SNDQUEUELOWAT LWIP_MAX(((TCP_SND_QUEUELEN)/2), 5) +#endif + +/** + * TCP_LISTEN_BACKLOG: Enable the backlog option for tcp listen pcb. + */ +#ifndef TCP_LISTEN_BACKLOG +#define TCP_LISTEN_BACKLOG 0 +#endif + +/** + * The maximum allowed backlog for TCP listen netconns. + * This backlog is used unless another is explicitly specified. + * 0xff is the maximum (u8_t). + */ +#ifndef TCP_DEFAULT_LISTEN_BACKLOG +#define TCP_DEFAULT_LISTEN_BACKLOG 0xff +#endif + +/** + * TCP_OVERSIZE: The maximum number of bytes that tcp_write may + * allocate ahead of time in an attempt to create shorter pbuf chains + * for transmission. The meaningful range is 0 to TCP_MSS. Some + * suggested values are: + * + * 0: Disable oversized allocation. Each tcp_write() allocates a new + pbuf (old behaviour). + * 1: Allocate size-aligned pbufs with minimal excess. Use this if your + * scatter-gather DMA requires aligned fragments. + * 128: Limit the pbuf/memory overhead to 20%. + * TCP_MSS: Try to create unfragmented TCP packets. + * TCP_MSS/4: Try to create 4 fragments or less per TCP packet. + */ +#ifndef TCP_OVERSIZE +#define TCP_OVERSIZE TCP_MSS +#endif + +/** + * LWIP_TCP_TIMESTAMPS==1: support the TCP timestamp option. + */ +#ifndef LWIP_TCP_TIMESTAMPS +#define LWIP_TCP_TIMESTAMPS 0 +#endif + +/** + * TCP_WND_UPDATE_THRESHOLD: difference in window to trigger an + * explicit window update + */ +#ifndef TCP_WND_UPDATE_THRESHOLD +#define TCP_WND_UPDATE_THRESHOLD (TCP_WND / 4) +#endif + +/** + * 2 * TCP_MSL defines duration of socket TIME-WAIT state in ms. + */ +#define TCP_MSL 2500UL + +/** + * LWIP_EVENT_API and LWIP_CALLBACK_API: Only one of these should be set to 1. + * LWIP_EVENT_API==1: The user defines lwip_tcp_event() to receive all + * events (accept, sent, etc) that happen in the system. + * LWIP_CALLBACK_API==1: The PCB callback function is called directly + * for the event. + */ +#ifndef LWIP_EVENT_API +#define LWIP_EVENT_API 0 +#define LWIP_CALLBACK_API 1 +#else +#define LWIP_EVENT_API 1 +#define LWIP_CALLBACK_API 0 +#endif + + +/* + ---------------------------------- + ---------- Pbuf options ---------- + ---------------------------------- +*/ +/** + * PBUF_LINK_HLEN: the number of bytes that should be allocated for a + * link level header. The default is 14, the standard value for + * Ethernet. + */ +#ifndef PBUF_LINK_HLEN +#define PBUF_LINK_HLEN (14 + ETH_PAD_SIZE) +#endif + +/** + * PBUF_POOL_BUFSIZE: the size of each pbuf in the pbuf pool. The default is + * designed to accommodate single full size TCP frame in one pbuf, including + * TCP_MSS, IP header, and link header. + */ +#ifndef PBUF_POOL_BUFSIZE +#define PBUF_POOL_BUFSIZE LWIP_MEM_ALIGN_SIZE(TCP_MSS+40+PBUF_LINK_HLEN) +#endif + +/* + ------------------------------------------------ + ---------- Network Interfaces options ---------- + ------------------------------------------------ +*/ +/** + * LWIP_NETIF_HOSTNAME==1: use DHCP_OPTION_HOSTNAME with netif's hostname + * field. + */ +#ifndef LWIP_NETIF_HOSTNAME +#define LWIP_NETIF_HOSTNAME 1 +#endif + +/** + * LWIP_NETIF_API==1: Support netif api (in netifapi.c) + */ +#ifndef LWIP_NETIF_API +#define LWIP_NETIF_API 0 +#endif + +/** + * LWIP_NETIF_STATUS_CALLBACK==1: Support a callback function whenever an interface + * changes its up/down status (i.e., due to DHCP IP acquistion) + */ +#ifndef LWIP_NETIF_STATUS_CALLBACK +#define LWIP_NETIF_STATUS_CALLBACK 0 +#endif + +/** + * LWIP_NETIF_LINK_CALLBACK==1: Support a callback function from an interface + * whenever the link changes (i.e., link down) + */ +#ifndef LWIP_NETIF_LINK_CALLBACK +#define LWIP_NETIF_LINK_CALLBACK 0 +#endif + +/** + * LWIP_NETIF_HWADDRHINT==1: Cache link-layer-address hints (e.g. table + * indices) in struct netif. TCP and UDP can make use of this to prevent + * scanning the ARP table for every sent packet. While this is faster for big + * ARP tables or many concurrent connections, it might be counterproductive + * if you have a tiny ARP table or if there never are concurrent connections. + */ +#ifndef LWIP_NETIF_HWADDRHINT +#define LWIP_NETIF_HWADDRHINT 0 +#endif + +/** + * LWIP_NETIF_LOOPBACK==1: Support sending packets with a destination IP + * address equal to the netif IP address, looping them back up the stack. + */ +#ifndef LWIP_NETIF_LOOPBACK +#define LWIP_NETIF_LOOPBACK 0 +#endif + +/** + * LWIP_LOOPBACK_MAX_PBUFS: Maximum number of pbufs on queue for loopback + * sending for each netif (0 = disabled) + */ +#ifndef LWIP_LOOPBACK_MAX_PBUFS +#define LWIP_LOOPBACK_MAX_PBUFS 0 +#endif + +/** + * LWIP_NETIF_LOOPBACK_MULTITHREADING: Indicates whether threading is enabled in + * the system, as netifs must change how they behave depending on this setting + * for the LWIP_NETIF_LOOPBACK option to work. + * Setting this is needed to avoid reentering non-reentrant functions like + * tcp_input(). + * LWIP_NETIF_LOOPBACK_MULTITHREADING==1: Indicates that the user is using a + * multithreaded environment like tcpip.c. In this case, netif->input() + * is called directly. + * LWIP_NETIF_LOOPBACK_MULTITHREADING==0: Indicates a polling (or NO_SYS) setup. + * The packets are put on a list and netif_poll() must be called in + * the main application loop. + */ +#ifndef LWIP_NETIF_LOOPBACK_MULTITHREADING +#define LWIP_NETIF_LOOPBACK_MULTITHREADING (!NO_SYS) +#endif + +/** + * LWIP_NETIF_TX_SINGLE_PBUF: if this is set to 1, lwIP tries to put all data + * to be sent into one single pbuf. This is for compatibility with DMA-enabled + * MACs that do not support scatter-gather. + * Beware that this might involve CPU-memcpy before transmitting that would not + * be needed without this flag! Use this only if you need to! + * + * @todo: TCP and IP-frag do not work with this, yet: + */ +#ifndef LWIP_NETIF_TX_SINGLE_PBUF +#define LWIP_NETIF_TX_SINGLE_PBUF 1 +#endif /* LWIP_NETIF_TX_SINGLE_PBUF */ + +/* + ------------------------------------ + ---------- LOOPIF options ---------- + ------------------------------------ +*/ +/** + * LWIP_HAVE_LOOPIF==1: Support loop interface (127.0.0.1) and loopif.c + */ +#ifndef LWIP_HAVE_LOOPIF +#define LWIP_HAVE_LOOPIF 0 +#endif + +/* + ------------------------------------ + ---------- SLIPIF options ---------- + ------------------------------------ +*/ +/** + * LWIP_HAVE_SLIPIF==1: Support slip interface and slipif.c + */ +#ifndef LWIP_HAVE_SLIPIF +#define LWIP_HAVE_SLIPIF 1 +#endif + +/* + ------------------------------------ + ---------- Thread options ---------- + ------------------------------------ +*/ +/** + * TCPIP_THREAD_NAME: The name assigned to the main tcpip thread. + */ +#ifndef TCPIP_THREAD_NAME +#define TCPIP_THREAD_NAME "tcpip_thread" +#endif + +/** + * TCPIP_THREAD_STACKSIZE: The stack size used by the main tcpip thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef TCPIP_THREAD_STACKSIZE +#define TCPIP_THREAD_STACKSIZE 0 +#endif + +/** + * TCPIP_THREAD_PRIO: The priority assigned to the main tcpip thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef TCPIP_THREAD_PRIO +#define TCPIP_THREAD_PRIO 1 +#endif + +/** + * TCPIP_MBOX_SIZE: The mailbox size for the tcpip thread messages + * The queue size value itself is platform-dependent, but is passed to + * sys_mbox_new() when tcpip_init is called. + */ +#ifndef TCPIP_MBOX_SIZE +#define TCPIP_MBOX_SIZE 0 +#endif + +/** + * SLIPIF_THREAD_NAME: The name assigned to the slipif_loop thread. + */ +#ifndef SLIPIF_THREAD_NAME +#define SLIPIF_THREAD_NAME "slipif_loop" +#endif + +/** + * SLIP_THREAD_STACKSIZE: The stack size used by the slipif_loop thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef SLIPIF_THREAD_STACKSIZE +#define SLIPIF_THREAD_STACKSIZE 0 +#endif + +/** + * SLIPIF_THREAD_PRIO: The priority assigned to the slipif_loop thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef SLIPIF_THREAD_PRIO +#define SLIPIF_THREAD_PRIO 1 +#endif + +/** + * PPP_THREAD_NAME: The name assigned to the pppInputThread. + */ +#ifndef PPP_THREAD_NAME +#define PPP_THREAD_NAME "pppInputThread" +#endif + +/** + * PPP_THREAD_STACKSIZE: The stack size used by the pppInputThread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef PPP_THREAD_STACKSIZE +#define PPP_THREAD_STACKSIZE 0 +#endif + +/** + * PPP_THREAD_PRIO: The priority assigned to the pppInputThread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef PPP_THREAD_PRIO +#define PPP_THREAD_PRIO 1 +#endif + +/** + * DEFAULT_THREAD_NAME: The name assigned to any other lwIP thread. + */ +#ifndef DEFAULT_THREAD_NAME +#define DEFAULT_THREAD_NAME "lwIP" +#endif + +/** + * DEFAULT_THREAD_STACKSIZE: The stack size used by any other lwIP thread. + * The stack size value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef DEFAULT_THREAD_STACKSIZE +#define DEFAULT_THREAD_STACKSIZE 0 +#endif + +/** + * DEFAULT_THREAD_PRIO: The priority assigned to any other lwIP thread. + * The priority value itself is platform-dependent, but is passed to + * sys_thread_new() when the thread is created. + */ +#ifndef DEFAULT_THREAD_PRIO +#define DEFAULT_THREAD_PRIO 1 +#endif + +/** + * DEFAULT_RAW_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_RAW. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_RAW_RECVMBOX_SIZE +#define DEFAULT_RAW_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_UDP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_UDP. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_UDP_RECVMBOX_SIZE +#define DEFAULT_UDP_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_TCP_RECVMBOX_SIZE: The mailbox size for the incoming packets on a + * NETCONN_TCP. The queue size value itself is platform-dependent, but is passed + * to sys_mbox_new() when the recvmbox is created. + */ +#ifndef DEFAULT_TCP_RECVMBOX_SIZE +#define DEFAULT_TCP_RECVMBOX_SIZE 0 +#endif + +/** + * DEFAULT_ACCEPTMBOX_SIZE: The mailbox size for the incoming connections. + * The queue size value itself is platform-dependent, but is passed to + * sys_mbox_new() when the acceptmbox is created. + */ +#ifndef DEFAULT_ACCEPTMBOX_SIZE +#define DEFAULT_ACCEPTMBOX_SIZE 0 +#endif + +/* + ---------------------------------------------- + ---------- Sequential layer options ---------- + ---------------------------------------------- +*/ +/** + * LWIP_TCPIP_CORE_LOCKING: (EXPERIMENTAL!) + * Don't use it if you're not an active lwIP project member + */ +#ifndef LWIP_TCPIP_CORE_LOCKING +#define LWIP_TCPIP_CORE_LOCKING 0 +#endif + +/** + * LWIP_TCPIP_CORE_LOCKING_INPUT: (EXPERIMENTAL!) + * Don't use it if you're not an active lwIP project member + */ +#ifndef LWIP_TCPIP_CORE_LOCKING_INPUT +#define LWIP_TCPIP_CORE_LOCKING_INPUT 0 +#endif + +/** + * LWIP_NETCONN==1: Enable Netconn API (require to use api_lib.c) + */ +#ifndef LWIP_NETCONN +#define LWIP_NETCONN 0 +#endif + +/** LWIP_TCPIP_TIMEOUT==1: Enable tcpip_timeout/tcpip_untimeout tod create + * timers running in tcpip_thread from another thread. + */ +#ifndef LWIP_TCPIP_TIMEOUT +#define LWIP_TCPIP_TIMEOUT 1 +#endif + +/* + ------------------------------------ + ---------- Socket options ---------- + ------------------------------------ +*/ +/** + * LWIP_SOCKET==1: Enable Socket API (require to use sockets.c) + */ +#ifndef LWIP_SOCKET +#define LWIP_SOCKET 0 +#endif + +/** + * LWIP_COMPAT_SOCKETS==1: Enable BSD-style sockets functions names. + * (only used if you use sockets.c) + */ +#ifndef LWIP_COMPAT_SOCKETS +#define LWIP_COMPAT_SOCKETS 0 +#endif + +/** + * LWIP_POSIX_SOCKETS_IO_NAMES==1: Enable POSIX-style sockets functions names. + * Disable this option if you use a POSIX operating system that uses the same + * names (read, write & close). (only used if you use sockets.c) + */ +#ifndef LWIP_POSIX_SOCKETS_IO_NAMES +#define LWIP_POSIX_SOCKETS_IO_NAMES 0 +#endif + +/** + * LWIP_TCP_KEEPALIVE==1: Enable TCP_KEEPIDLE, TCP_KEEPINTVL and TCP_KEEPCNT + * options processing. Note that TCP_KEEPIDLE and TCP_KEEPINTVL have to be set + * in seconds. (does not require sockets.c, and will affect tcp.c) + */ +#ifndef LWIP_TCP_KEEPALIVE +#define LWIP_TCP_KEEPALIVE 1 +#endif + +/** + * LWIP_SO_RCVTIMEO==1: Enable SO_RCVTIMEO processing. + */ +#ifndef LWIP_SO_RCVTIMEO +#define LWIP_SO_RCVTIMEO 0 +#endif + +/** + * LWIP_SO_RCVBUF==1: Enable SO_RCVBUF processing. + */ +#ifndef LWIP_SO_RCVBUF +#define LWIP_SO_RCVBUF 0 +#endif + +/** + * If LWIP_SO_RCVBUF is used, this is the default value for recv_bufsize. + */ +#ifndef RECV_BUFSIZE_DEFAULT +#define RECV_BUFSIZE_DEFAULT INT_MAX +#endif + +/** + * SO_REUSE==1: Enable SO_REUSEADDR option. + */ +#ifndef SO_REUSE +#define SO_REUSE 1 +#endif + +/** + * SO_REUSE_RXTOALL==1: Pass a copy of incoming broadcast/multicast packets + * to all local matches if SO_REUSEADDR is turned on. + * WARNING: Adds a memcpy for every packet if passing to more than one pcb! + */ +#ifndef SO_REUSE_RXTOALL +#define SO_REUSE_RXTOALL 0 +#endif + +/* + ---------------------------------------- + ---------- Statistics options ---------- + ---------------------------------------- +*/ +/** + * LWIP_STATS==1: Enable statistics collection in lwip_stats. + */ +#ifndef LWIP_STATS +#define LWIP_STATS 0 +#endif + +#if LWIP_STATS + +/** + * LWIP_STATS_DISPLAY==1: Compile in the statistics output functions. + */ +#ifndef LWIP_STATS_DISPLAY +#define LWIP_STATS_DISPLAY 1 +#endif + +/** + * LINK_STATS==1: Enable link stats. + */ +#ifndef LINK_STATS +#define LINK_STATS 1 +#endif + +/** + * ETHARP_STATS==1: Enable etharp stats. + */ +#ifndef ETHARP_STATS +#define ETHARP_STATS (LWIP_ARP) +#endif + +/** + * IP_STATS==1: Enable IP stats. + */ +#ifndef IP_STATS +#define IP_STATS 1 +#endif + +/** + * IPFRAG_STATS==1: Enable IP fragmentation stats. Default is + * on if using either frag or reass. + */ +#ifndef IPFRAG_STATS +#define IPFRAG_STATS (IP_REASSEMBLY || IP_FRAG) +#endif + +/** + * ICMP_STATS==1: Enable ICMP stats. + */ +#ifndef ICMP_STATS +#define ICMP_STATS 1 +#endif + +/** + * IGMP_STATS==1: Enable IGMP stats. + */ +#ifndef IGMP_STATS +#define IGMP_STATS (LWIP_IGMP) +#endif + +/** + * UDP_STATS==1: Enable UDP stats. Default is on if + * UDP enabled, otherwise off. + */ +#ifndef UDP_STATS +#define UDP_STATS (LWIP_UDP) +#endif + +/** + * TCP_STATS==1: Enable TCP stats. Default is on if TCP + * enabled, otherwise off. + */ +#ifndef TCP_STATS +#define TCP_STATS (LWIP_TCP) +#endif + +/** + * MEM_STATS==1: Enable mem.c stats. + */ +#ifndef MEM_STATS +#define MEM_STATS ((MEM_LIBC_MALLOC == 0) && (MEM_USE_POOLS == 0)) +#endif + +/** + * MEMP_STATS==1: Enable memp.c pool stats. + */ +#ifndef MEMP_STATS +#define MEMP_STATS (MEMP_MEM_MALLOC == 0) +#endif + +/** + * SYS_STATS==1: Enable system stats (sem and mbox counts, etc). + */ +#ifndef SYS_STATS +#define SYS_STATS (NO_SYS == 0) +#endif + +#else +#define ETHARP_STATS 0 +#define LINK_STATS 0 +#define IP_STATS 0 +#define IPFRAG_STATS 0 +#define ICMP_STATS 0 +#define IGMP_STATS 0 +#define UDP_STATS 0 +#define TCP_STATS 0 +#define MEM_STATS 0 +#define MEMP_STATS 0 +#define SYS_STATS 0 +#define LWIP_STATS_DISPLAY 0 + +#endif /* LWIP_STATS */ + +/* + --------------------------------- + ---------- PPP options ---------- + --------------------------------- +*/ +/** + * PPP_SUPPORT==1: Enable PPP. + */ +#ifndef PPP_SUPPORT +#define PPP_SUPPORT 0 +#endif + +/** + * PPPOE_SUPPORT==1: Enable PPP Over Ethernet + */ +#ifndef PPPOE_SUPPORT +#define PPPOE_SUPPORT 0 +#endif + +/** + * PPPOS_SUPPORT==1: Enable PPP Over Serial + */ +#ifndef PPPOS_SUPPORT +#define PPPOS_SUPPORT PPP_SUPPORT +#endif + +#if PPP_SUPPORT + +/** + * NUM_PPP: Max PPP sessions. + */ +#ifndef NUM_PPP +#define NUM_PPP 1 +#endif + +/** + * PAP_SUPPORT==1: Support PAP. + */ +#ifndef PAP_SUPPORT +#define PAP_SUPPORT 0 +#endif + +/** + * CHAP_SUPPORT==1: Support CHAP. + */ +#ifndef CHAP_SUPPORT +#define CHAP_SUPPORT 0 +#endif + +/** + * MSCHAP_SUPPORT==1: Support MSCHAP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef MSCHAP_SUPPORT +#define MSCHAP_SUPPORT 0 +#endif + +/** + * CBCP_SUPPORT==1: Support CBCP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef CBCP_SUPPORT +#define CBCP_SUPPORT 0 +#endif + +/** + * CCP_SUPPORT==1: Support CCP. CURRENTLY NOT SUPPORTED! DO NOT SET! + */ +#ifndef CCP_SUPPORT +#define CCP_SUPPORT 0 +#endif + +/** + * VJ_SUPPORT==1: Support VJ header compression. + */ +#ifndef VJ_SUPPORT +#define VJ_SUPPORT 0 +#endif + +/** + * MD5_SUPPORT==1: Support MD5 (see also CHAP). + */ +#ifndef MD5_SUPPORT +#define MD5_SUPPORT 0 +#endif + +/* + * Timeouts + */ +#ifndef FSM_DEFTIMEOUT +#define FSM_DEFTIMEOUT 6 /* Timeout time in seconds */ +#endif + +#ifndef FSM_DEFMAXTERMREQS +#define FSM_DEFMAXTERMREQS 2 /* Maximum Terminate-Request transmissions */ +#endif + +#ifndef FSM_DEFMAXCONFREQS +#define FSM_DEFMAXCONFREQS 10 /* Maximum Configure-Request transmissions */ +#endif + +#ifndef FSM_DEFMAXNAKLOOPS +#define FSM_DEFMAXNAKLOOPS 5 /* Maximum number of nak loops */ +#endif + +#ifndef UPAP_DEFTIMEOUT +#define UPAP_DEFTIMEOUT 6 /* Timeout (seconds) for retransmitting req */ +#endif + +#ifndef UPAP_DEFREQTIME +#define UPAP_DEFREQTIME 30 /* Time to wait for auth-req from peer */ +#endif + +#ifndef CHAP_DEFTIMEOUT +#define CHAP_DEFTIMEOUT 6 /* Timeout time in seconds */ +#endif + +#ifndef CHAP_DEFTRANSMITS +#define CHAP_DEFTRANSMITS 10 /* max # times to send challenge */ +#endif + +/* Interval in seconds between keepalive echo requests, 0 to disable. */ +#ifndef LCP_ECHOINTERVAL +#define LCP_ECHOINTERVAL 0 +#endif + +/* Number of unanswered echo requests before failure. */ +#ifndef LCP_MAXECHOFAILS +#define LCP_MAXECHOFAILS 3 +#endif + +/* Max Xmit idle time (in jiffies) before resend flag char. */ +#ifndef PPP_MAXIDLEFLAG +#define PPP_MAXIDLEFLAG 100 +#endif + +/* + * Packet sizes + * + * Note - lcp shouldn't be allowed to negotiate stuff outside these + * limits. See lcp.h in the pppd directory. + * (XXX - these constants should simply be shared by lcp.c instead + * of living in lcp.h) + */ +#define PPP_MTU 1500 /* Default MTU (size of Info field) */ +#ifndef PPP_MAXMTU +/* #define PPP_MAXMTU 65535 - (PPP_HDRLEN + PPP_FCSLEN) */ +#define PPP_MAXMTU 1500 /* Largest MTU we allow */ +#endif +#define PPP_MINMTU 64 +#define PPP_MRU 1500 /* default MRU = max length of info field */ +#define PPP_MAXMRU 1500 /* Largest MRU we allow */ +#ifndef PPP_DEFMRU +#define PPP_DEFMRU 296 /* Try for this */ +#endif +#define PPP_MINMRU 128 /* No MRUs below this */ + +#ifndef MAXNAMELEN +#define MAXNAMELEN 256 /* max length of hostname or name for auth */ +#endif +#ifndef MAXSECRETLEN +#define MAXSECRETLEN 256 /* max length of password or secret */ +#endif + +#endif /* PPP_SUPPORT */ + +/* + -------------------------------------- + ---------- Checksum options ---------- + -------------------------------------- +*/ +/** + * CHECKSUM_GEN_IP==1: Generate checksums in software for outgoing IP packets. + */ +#ifndef CHECKSUM_GEN_IP +#define CHECKSUM_GEN_IP 1 +#endif + +/** + * CHECKSUM_GEN_UDP==1: Generate checksums in software for outgoing UDP packets. + */ +#ifndef CHECKSUM_GEN_UDP +#define CHECKSUM_GEN_UDP 1 +#endif + +/** + * CHECKSUM_GEN_TCP==1: Generate checksums in software for outgoing TCP packets. + */ +#ifndef CHECKSUM_GEN_TCP +#define CHECKSUM_GEN_TCP 1 +#endif + +/** + * CHECKSUM_CHECK_IP==1: Check checksums in software for incoming IP packets. + */ +#ifndef CHECKSUM_CHECK_IP +#define CHECKSUM_CHECK_IP 1 +#endif + +/** + * CHECKSUM_CHECK_UDP==1: Check checksums in software for incoming UDP packets. + */ +#ifndef CHECKSUM_CHECK_UDP +#define CHECKSUM_CHECK_UDP 1 +#endif + +/** + * CHECKSUM_CHECK_TCP==1: Check checksums in software for incoming TCP packets. + */ +#ifndef CHECKSUM_CHECK_TCP +#define CHECKSUM_CHECK_TCP 1 +#endif + +/** + * LWIP_CHECKSUM_ON_COPY==1: Calculate checksum when copying data from + * application buffers to pbufs. + */ +#ifndef LWIP_CHECKSUM_ON_COPY +#define LWIP_CHECKSUM_ON_COPY 0 +#endif + +/* + --------------------------------------- + ---------- Debugging options ---------- + --------------------------------------- +*/ +//#define LWIP_DEBUG 1 +/** + * LWIP_DBG_MIN_LEVEL: After masking, the value of the debug is + * compared against this value. If it is smaller, then debugging + * messages are written. + */ +#ifndef LWIP_DBG_MIN_LEVEL +#define LWIP_DBG_MIN_LEVEL LWIP_DBG_LEVEL_ALL +#endif + +/** + * LWIP_DBG_TYPES_ON: A mask that can be used to globally enable/disable + * debug messages of certain types. + */ +#ifndef LWIP_DBG_TYPES_ON +#define LWIP_DBG_TYPES_ON LWIP_DBG_OFF +#endif + +/** + * ETHARP_DEBUG: Enable debugging in etharp.c. + */ +#ifndef ETHARP_DEBUG +#define ETHARP_DEBUG LWIP_DBG_OFF +#endif + +/** + * NETIF_DEBUG: Enable debugging in netif.c. + */ +#ifndef NETIF_DEBUG +#define NETIF_DEBUG LWIP_DBG_OFF +#endif + +/** + * PBUF_DEBUG: Enable debugging in pbuf.c. + */ +#ifndef PBUF_DEBUG +#define PBUF_DEBUG LWIP_DBG_OFF +#endif + +/** + * API_LIB_DEBUG: Enable debugging in api_lib.c. + */ +#ifndef API_LIB_DEBUG +#define API_LIB_DEBUG LWIP_DBG_OFF +#endif + +/** + * API_MSG_DEBUG: Enable debugging in api_msg.c. + */ +#ifndef API_MSG_DEBUG +#define API_MSG_DEBUG LWIP_DBG_OFF +#endif + +/** + * SOCKETS_DEBUG: Enable debugging in sockets.c. + */ +#ifndef SOCKETS_DEBUG +#define SOCKETS_DEBUG LWIP_DBG_OFF +#endif + +/** + * ICMP_DEBUG: Enable debugging in icmp.c. + */ +#ifndef ICMP_DEBUG +#define ICMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * IGMP_DEBUG: Enable debugging in igmp.c. + */ +#ifndef IGMP_DEBUG +#define IGMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * INET_DEBUG: Enable debugging in inet.c. + */ +#ifndef INET_DEBUG +#define INET_DEBUG LWIP_DBG_OFF +#endif + +/** + * IP_DEBUG: Enable debugging for IP. + */ +#ifndef IP_DEBUG +#define IP_DEBUG LWIP_DBG_OFF +#endif + +/** + * IP_REASS_DEBUG: Enable debugging in ip_frag.c for both frag & reass. + */ +#ifndef IP_REASS_DEBUG +#define IP_REASS_DEBUG LWIP_DBG_OFF +#endif + +/** + * RAW_DEBUG: Enable debugging in raw.c. + */ +#ifndef RAW_DEBUG +#define RAW_DEBUG LWIP_DBG_OFF +#endif + +/** + * MEM_DEBUG: Enable debugging in mem.c. + */ +#ifndef MEM_DEBUG +#define MEM_DEBUG LWIP_DBG_OFF +#endif + +/** + * MEMP_DEBUG: Enable debugging in memp.c. + */ +#ifndef MEMP_DEBUG +#define MEMP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SYS_DEBUG: Enable debugging in sys.c. + */ +#ifndef SYS_DEBUG +#define SYS_DEBUG LWIP_DBG_OFF +#endif + +/** + * TIMERS_DEBUG: Enable debugging in timers.c. + */ +#ifndef TIMERS_DEBUG +#define TIMERS_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_DEBUG: Enable debugging for TCP. + */ +#ifndef TCP_DEBUG +#define TCP_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_INPUT_DEBUG: Enable debugging in tcp_in.c for incoming debug. + */ +#ifndef TCP_INPUT_DEBUG +#define TCP_INPUT_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_FR_DEBUG: Enable debugging in tcp_in.c for fast retransmit. + */ +#ifndef TCP_FR_DEBUG +#define TCP_FR_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_RTO_DEBUG: Enable debugging in TCP for retransmit + * timeout. + */ +#ifndef TCP_RTO_DEBUG +#define TCP_RTO_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_CWND_DEBUG: Enable debugging for TCP congestion window. + */ +#ifndef TCP_CWND_DEBUG +#define TCP_CWND_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_WND_DEBUG: Enable debugging in tcp_in.c for window updating. + */ +#ifndef TCP_WND_DEBUG +#define TCP_WND_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_OUTPUT_DEBUG: Enable debugging in tcp_out.c output functions. + */ +#ifndef TCP_OUTPUT_DEBUG +#define TCP_OUTPUT_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_RST_DEBUG: Enable debugging for TCP with the RST message. + */ +#ifndef TCP_RST_DEBUG +#define TCP_RST_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCP_QLEN_DEBUG: Enable debugging for TCP queue lengths. + */ +#ifndef TCP_QLEN_DEBUG +#define TCP_QLEN_DEBUG LWIP_DBG_OFF +#endif + +/** + * UDP_DEBUG: Enable debugging in UDP. + */ +#ifndef UDP_DEBUG +#define UDP_DEBUG LWIP_DBG_OFF +#endif + +/** + * TCPIP_DEBUG: Enable debugging in tcpip.c. + */ +#ifndef TCPIP_DEBUG +#define TCPIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * PPP_DEBUG: Enable debugging for PPP. + */ +#ifndef PPP_DEBUG +#define PPP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SLIP_DEBUG: Enable debugging in slipif.c. + */ +#ifndef SLIP_DEBUG +#define SLIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * DHCP_DEBUG: Enable debugging in dhcp.c. + */ +#ifndef DHCP_DEBUG +#define DHCP_DEBUG LWIP_DBG_OFF +#endif + +/** + * AUTOIP_DEBUG: Enable debugging in autoip.c. + */ +#ifndef AUTOIP_DEBUG +#define AUTOIP_DEBUG LWIP_DBG_OFF +#endif + +/** + * SNMP_MSG_DEBUG: Enable debugging for SNMP messages. + */ +#ifndef SNMP_MSG_DEBUG +#define SNMP_MSG_DEBUG LWIP_DBG_OFF +#endif + +/** + * SNMP_MIB_DEBUG: Enable debugging for SNMP MIBs. + */ +#ifndef SNMP_MIB_DEBUG +#define SNMP_MIB_DEBUG LWIP_DBG_OFF +#endif + +/** + * DNS_DEBUG: Enable debugging for DNS. + */ +#ifndef DNS_DEBUG +#define DNS_DEBUG LWIP_DBG_OFF +#endif + +/** + * NAPT_DEBUG: Enable debugging for NAPT. + */ +#ifndef NAPT_DEBUG +#define NAPT_DEBUG LWIP_DBG_OFF +#endif + +#endif /* __LWIP_OPT_H__ */ diff --git a/include/string.h b/include/string.h new file mode 100644 index 0000000..bb97dcd --- /dev/null +++ b/include/string.h @@ -0,0 +1 @@ +//Nothing here. diff --git a/liblwip_open_napt.a b/liblwip_open_napt.a new file mode 100644 index 0000000..3ca4da8 Binary files /dev/null and b/liblwip_open_napt.a differ diff --git a/user/acl.c b/user/acl.c new file mode 100644 index 0000000..d4bcd49 --- /dev/null +++ b/user/acl.c @@ -0,0 +1,310 @@ +#include "c_types.h" +#include "mem.h" +#include "ets_sys.h" +#include "osapi.h" +#include "os_type.h" +#include "lwip/ip.h" +#include "lwip/udp.h" +#include "lwip/tcp_impl.h" +#include "netif/etharp.h" + +#include "user_interface.h" +#include "string.h" + +#include "acl.h" + +acl_entry acl[MAX_NO_ACLS][MAX_ACL_ENTRIES]; +uint8_t acl_freep[MAX_NO_ACLS]; +uint32_t acl_allow_count; +uint32_t acl_deny_count; +static packet_deny_cb my_deny_cb; + +void ICACHE_FLASH_ATTR +acl_init() +{ + int i; + acl_allow_count = acl_deny_count = 0; + my_deny_cb = NULL; + for(i=0; i< MAX_NO_ACLS; i++) + { + acl_freep[i] = 0; + acl_clear_stats(i); + } +} + +bool ICACHE_FLASH_ATTR +acl_is_empty(uint8_t acl_no) +{ + if (acl_no >= MAX_NO_ACLS) + { + return true; + } + return acl_freep[acl_no] == 0; +} + +void ICACHE_FLASH_ATTR +acl_clear(uint8_t acl_no) +{ + if (acl_no >= MAX_NO_ACLS) + { + return; + } + acl_freep[acl_no] = 0; + acl_clear_stats(acl_no); +} + +void ICACHE_FLASH_ATTR +acl_clear_stats(uint8_t acl_no) +{ + int i; + + if (acl_no >= MAX_NO_ACLS) + { + return; + } + my_deny_cb = NULL; + for(i=0; i< MAX_ACL_ENTRIES; i++) + acl[acl_no][i].hit_count = 0; +} + +bool ICACHE_FLASH_ATTR +acl_add(uint8_t acl_no, + uint32_t src, + uint32_t s_mask, + uint32_t dest, + uint32_t d_mask, + uint8_t proto, + uint16_t s_port, + uint16_t d_port, + uint8_t allow) +{ + acl_entry *my_entry; + + if (acl_no >= MAX_NO_ACLS || acl_freep[acl_no] >= MAX_ACL_ENTRIES) + { + return false; + } + + my_entry = &acl[acl_no][acl_freep[acl_no]]; + my_entry->src = src & s_mask; + my_entry->s_mask = s_mask; + my_entry->dest = dest & d_mask; + my_entry->d_mask = d_mask; + my_entry->proto = proto; + my_entry->s_port = s_port; + my_entry->d_port = d_port; + my_entry->allow = allow; + my_entry->hit_count = 0; + + acl_freep[acl_no]++; + return true; +} + +uint8_t ICACHE_FLASH_ATTR +acl_check_packet(uint8_t acl_no, struct pbuf *p) +{ + struct eth_hdr *mac_h; + struct ip_hdr *ip_h; + uint8_t proto; + struct udp_hdr *udp_h; + struct tcp_hdr *tcp_h; + uint16_t src_port, dest_port; + uint8_t *packet; + int i; + acl_entry *my_entry; + uint8_t allow; + + if (acl_no >= MAX_NO_ACLS) + { + return ACL_DENY; + } + + if (p->len < sizeof(struct eth_hdr)) + { + return ACL_DENY; + } + + mac_h = (struct eth_hdr *)p->payload; + + // Allow ARP + if (ntohs(mac_h->type) == ETHTYPE_ARP) + { + acl_allow_count++; + return ACL_ALLOW; + } + + // Drop anything else if not IPv4 + if (ntohs(mac_h->type) != ETHTYPE_IP) + { + acl_deny_count++; + return ACL_DENY; + } + + if (p->len < sizeof(struct eth_hdr)+sizeof(struct ip_hdr)) + { + acl_deny_count++; + return ACL_DENY; + } + + allow = ACL_DENY; + packet = (uint8_t*)p->payload; + ip_h = (struct ip_hdr *)&packet[sizeof(struct eth_hdr)]; + proto = IPH_PROTO(ip_h); + + switch (proto) { + case IP_PROTO_UDP: + { + if (p->len < sizeof(struct eth_hdr)+sizeof(struct ip_hdr)+sizeof(struct udp_hdr)) + { + return; + } + udp_h = (struct udp_hdr *)&packet[sizeof(struct eth_hdr)+sizeof(struct ip_hdr)]; + src_port = ntohs(udp_h->src); + dest_port = ntohs(udp_h->dest); + } break; + + case IP_PROTO_TCP: + { + if (p->len < sizeof(struct eth_hdr)+sizeof(struct ip_hdr)+sizeof(struct tcp_hdr)) + { + return; + } + tcp_h = (struct tcp_hdr *)&packet[sizeof(struct eth_hdr)+sizeof(struct ip_hdr)]; + src_port = ntohs(tcp_h->src); + dest_port = ntohs(tcp_h->dest); + } break; + + case IP_PROTO_ICMP: + { + src_port = dest_port = 0; + } break; + + // Drop anything that is not UDP, TCP, or ICMP + default: + { + acl_deny_count++; + return ACL_DENY; + } break; + } + + // os_printf("Src: %d.%d.%d.%d Dst: %d.%d.%d.%d Proto: %s SP:%d DP:%d\n", + // IP2STR(&ip_h->src), IP2STR(&ip_h->dest), + // proto==IP_PROTO_TCP?"TCP":proto==IP_PROTO_UDP?"UDP":"IP4", src_port, dest_port); + + for(i=0; iproto == 0 || proto == my_entry->proto) && + (my_entry->src == 0 || my_entry->src == (ip_h->src.addr&my_entry->s_mask)) && + (my_entry->dest == 0 || my_entry->dest == (ip_h->dest.addr&my_entry->d_mask)) && + (my_entry->s_port == 0 || my_entry->s_port == src_port) && + (my_entry->d_port == 0 || my_entry->d_port == dest_port)) + { + allow = my_entry->allow; + my_entry->hit_count++; + goto done; + } + } + +done: + if (!(allow & ACL_ALLOW) && my_deny_cb != NULL) + { + allow = my_deny_cb(proto, ip_h->src.addr, src_port, + ip_h->dest.addr, dest_port, allow); + } + if (allow & ACL_ALLOW) + { + acl_allow_count++; + } + else + { + acl_deny_count++; + } + + // os_printf(" allow: %d\r\n", allow); + return allow; +} + +void +acl_set_deny_cb(packet_deny_cb cb) +{ + my_deny_cb = cb; +} + +void ICACHE_FLASH_ATTR +addr2str(uint8_t *buf, uint32_t addr, uint32_t mask) +{ + uint8_t clidr; + + if (addr == 0) + { + os_sprintf(buf, "any"); + return; + } + + mask = ntohl(mask); + for (clidr = 0; mask; mask <<= 1,clidr++); + if (clidr < 32) + { + os_sprintf(buf, "%d.%d.%d.%d/%d", IP2STR((ip_addr_t*)&addr), clidr); + } + else + { + os_sprintf(buf, "%d.%d.%d.%d", IP2STR((ip_addr_t*)&addr)); + } +} + +void ICACHE_FLASH_ATTR +port2str(uint8_t *buf, uint16_t port) +{ + if (port == 0) + { + os_sprintf(buf, "any"); + } + else + { + os_sprintf(buf, "%d", port); + } +} + +void ICACHE_FLASH_ATTR +acl_show(uint8_t acl_no, uint8_t *buf) +{ + int i; + acl_entry *my_entry; + uint8_t line[80], addr1[21], addr2[21], port1[6], port2[6]; + + buf[0] = 0; + + if (acl_no >= MAX_NO_ACLS) + { + return; + } + + for(i = 0; i < acl_freep[acl_no]; i++) + { + my_entry = &acl[acl_no][i]; + addr2str(addr1, my_entry->src, my_entry->s_mask); + port2str(port1, my_entry->s_port); + addr2str(addr2, my_entry->dest, my_entry->d_mask); + port2str(port2, my_entry->d_port); + if (my_entry->proto != 0) + { + os_sprintf(line, "%s %s:%s %s:%s %s%s (%d hits)\r\n", + my_entry->proto==IP_PROTO_TCP?"TCP":"UDP", + addr1, port1, addr2, port2, + (my_entry->allow & ACL_ALLOW)?"allow":"deny", + (my_entry->allow & ACL_MONITOR)?"_monitor":"", + my_entry->hit_count); + } + else + { + os_sprintf(line, "IP %s %s %s%s (%d hits)\r\n", + addr1, addr2, + (my_entry->allow & ACL_ALLOW)?"allow":"deny", + (my_entry->allow & ACL_MONITOR)?"_monitor":"", + my_entry->hit_count); + } + os_memcpy(&buf[os_strlen(buf)], line, os_strlen(line)+1); + } +} diff --git a/user/acl.h b/user/acl.h new file mode 100644 index 0000000..1793caf --- /dev/null +++ b/user/acl.h @@ -0,0 +1,51 @@ +#ifndef _ACL_H_ +#define _ACL_H_ + +#include "lwip/ip.h" +#include "lwip/pbuf.h" + +#define MAX_NO_ACLS 4 +#define MAX_ACL_ENTRIES 16 + +#define ACL_DENY 0x0 +#define ACL_ALLOW 0x1 +#define ACL_MONITOR 0x2 + +typedef struct _acl_entry +{ + uint32_t src; + uint32_t s_mask; + uint32_t dest; + uint32_t d_mask; + uint16_t s_port; + uint16_t d_port; + uint8_t proto; + uint8_t allow; + uint32_t hit_count; +} acl_entry; + +extern acl_entry acl[MAX_NO_ACLS][MAX_ACL_ENTRIES]; +extern uint8_t acl_freep[MAX_NO_ACLS]; +extern uint32_t acl_allow_count; +extern uint32_t acl_deny_count; + +typedef uint8_t (*packet_deny_cb)(uint8_t proto, uint32_t saddr, uint16_t s_port, uint32_t daddr, uint16_t d_port, uint8_t allow); + +void acl_init(); +bool acl_is_empty(uint8_t acl_no); +void acl_clear(uint8_t acl_no); +void acl_clear_stats(uint8_t acl_no); +bool acl_add(uint8_t acl_no, + uint32_t src, + uint32_t s_mask, + uint32_t dest, + uint32_t d_mask, + uint8_t proto, + uint16_t s_port, + uint16_t d_port, + uint8_t allow); +uint8_t acl_check_packet(uint8_t acl_no, struct pbuf *p); +void acl_set_deny_cb(packet_deny_cb cb); +void acl_show(uint8_t acl_no, uint8_t *buf); + +#endif /* _ACL_H_ */ diff --git a/user/config_flash.c b/user/config_flash.c new file mode 100644 index 0000000..6e2c1e2 --- /dev/null +++ b/user/config_flash.c @@ -0,0 +1,153 @@ +#include "user_interface.h" +#include "lwip/ip.h" +#include "config_flash.h" + + +/* From the document 99A-SDK-Espressif IOT Flash RW Operation_v0.2 * + * -------------------------------------------------------------------------* + * Flash is erased sector by sector, which means it has to erase 4Kbytes one + * time at least. When you want to change some data in flash, you have to + * erase the whole sector, and then write it back with the new data. + *--------------------------------------------------------------------------*/ +void +config_load_default(sysconfig_p config) +{ + uint8_t mac[6]; + + wifi_get_macaddr(STATION_IF, mac); + + os_memset(config, 0, sizeof(sysconfig_t)); + os_printf("Loading default configuration\r\n"); + config->magic_number = MAGIC_NUMBER; + config->length = sizeof(sysconfig_t); + os_sprintf(config->ssid,"%s", WIFI_SSID); + os_sprintf(config->password,"%s", WIFI_PASSWORD); + config->auto_connect = 0; + os_memset(config->bssid, 0, 6); + os_sprintf(config->sta_hostname, "ESP_%02x%02x%02x", mac[3], mac[4], mac[5]); + os_sprintf(config->ap_ssid,"%s", WIFI_AP_SSID); + + config->first_run = 1; + config->ap_watchdog = -1; + config->client_watchdog = -1; + + IP4_ADDR(&config->network_addr, 192, 168, 4, 1); + config->dns_addr.addr = 0; // use DHCP + config->my_addr.addr = 0; // use DHCP + config->my_netmask.addr = 0; // use DHCP + config->my_gw.addr = 0; // use DHCP +#ifdef PHY_MODE + config->phy_mode = 3; // mode n +#endif + config->clock_speed = 80; + config->status_led = STATUS_LED_GPIO; + + wifi_get_macaddr(STATION_IF, config->STA_MAC_address); + + config->dhcps_entries = 0; +#ifdef ACLS + acl_init(); // initializes the ACLs, written in config during save +#endif + + config->current_mac_address = 0; + // Interval to change mac address in seconds + // Default: 28800 (8 hours) + config->mac_change_interval = 600; + + // list of mac addresses + // from https://docs.google.com/spreadsheets/d/1su5u-vPrQwkTixR6YnOTWSi_Ls9lV-_XNJHaWIJspv4/edit#gid=0 + ets_str2macaddr(config->mac_list[0], "4E:53:50:4F:4F:40"); + ets_str2macaddr(config->mac_list[1], "4E:53:50:4F:4F:41"); + ets_str2macaddr(config->mac_list[2], "4E:53:50:4F:4F:42"); + ets_str2macaddr(config->mac_list[3], "4E:53:50:4F:4F:43"); + ets_str2macaddr(config->mac_list[4], "4E:53:50:4F:4F:44"); + ets_str2macaddr(config->mac_list[5], "4E:53:50:4F:4F:45"); + ets_str2macaddr(config->mac_list[6], "4E:53:50:4F:4F:46"); + ets_str2macaddr(config->mac_list[7], "4E:53:50:4F:4F:47"); + ets_str2macaddr(config->mac_list[8], "4E:53:50:4F:4F:48"); + ets_str2macaddr(config->mac_list[9], "4E:53:50:4F:4F:49"); + ets_str2macaddr(config->mac_list[10], "4E:53:50:4F:4F:4A"); + ets_str2macaddr(config->mac_list[11], "4E:53:50:4F:4F:4B"); + ets_str2macaddr(config->mac_list[12], "4E:53:50:4F:4F:4C"); + ets_str2macaddr(config->mac_list[13], "4E:53:50:4F:4F:4D"); + ets_str2macaddr(config->mac_list[14], "4E:53:50:4F:4F:4E"); + ets_str2macaddr(config->mac_list[15], "4E:53:50:4F:4F:4F"); +} + +int +config_load(sysconfig_p config) +{ + if (config == NULL) + { + return -1; + } + uint16_t base_address = FLASH_BLOCK_NO; + + spi_flash_read(base_address* SPI_FLASH_SEC_SIZE, &config->magic_number, 4); + + if((config->magic_number != MAGIC_NUMBER)) + { + os_printf("\r\nNo config found, saving default in flash\r\n"); + config_load_default(config); + config_save(config); + return -1; + } + + os_printf("\r\nConfig found and loaded\r\n"); + spi_flash_read(base_address * SPI_FLASH_SEC_SIZE, + (uint32 *) config, + sizeof(sysconfig_t)); + if (config->length != sizeof(sysconfig_t)) + { + os_printf("Length Mismatch, probably old version of config, loading defaults\r\n"); + config_load_default(config); + config_save(config); + return -1; + } +#ifdef ACLS + os_memcpy(&acl, &(config->acl), sizeof(acl)); + os_memcpy(&acl_freep, &(config->acl_freep), sizeof(acl_freep)); +#endif + return 0; +} + +void +config_save(sysconfig_p config) +{ + uint16_t base_address = FLASH_BLOCK_NO; +#ifdef ACLS + os_memcpy(&(config->acl), &acl, sizeof(acl)); + os_memcpy(&(config->acl_freep), &acl_freep, sizeof(acl_freep)); +#endif + os_printf("Saving configuration\r\n"); + spi_flash_erase_sector(base_address); + spi_flash_write(base_address * SPI_FLASH_SEC_SIZE, + (uint32 *)config, + sizeof(sysconfig_t)); +} + +void +blob_save(uint8_t blob_no, uint32_t *data, uint16_t len) +{ + uint16_t base_address = FLASH_BLOCK_NO + 1 + blob_no; + spi_flash_erase_sector(base_address); + spi_flash_write(base_address * SPI_FLASH_SEC_SIZE, data, len); +} + +void +blob_load(uint8_t blob_no, uint32_t *data, uint16_t len) +{ + uint16_t base_address = FLASH_BLOCK_NO + 1 + blob_no; + spi_flash_read(base_address * SPI_FLASH_SEC_SIZE, data, len); +} + +void +blob_zero(uint8_t blob_no, uint16_t len) +{ + int i; + uint8_t z[len]; + os_memset(z, 0,len); + uint16_t base_address = FLASH_BLOCK_NO + 1 + blob_no; + spi_flash_erase_sector(base_address); + spi_flash_write(base_address * SPI_FLASH_SEC_SIZE, (uint32_t *)z, len); +} diff --git a/user/config_flash.h b/user/config_flash.h new file mode 100644 index 0000000..bd920aa --- /dev/null +++ b/user/config_flash.h @@ -0,0 +1,81 @@ +#ifndef _CONFIG_FLASH_H_ +#define _CONFIG_FLASH_H_ + +#include "c_types.h" +#include "mem.h" +#include "ets_sys.h" +#include "osapi.h" +#include "gpio.h" +#include "os_type.h" +#include "spi_flash.h" +#include "lwip/app/dhcpserver.h" + +#include "user_config.h" +#include "acl.h" + +#define FLASH_BLOCK_NO 0xc + +#define MAGIC_NUMBER 0x112005fc + +#define MAX_MAC_LIST_LENGTH 15 + +typedef struct +{ + // To check if the structure is initialized or not in flash + uint32_t magic_number; + + // Length of the structure, since this is a evolving library, + // the variant may change hence used for verification + uint16_t length; + + /* Below variables are specific to my code */ + uint8_t ssid[32]; // SSID of the AP to connect to + uint8_t password[64]; // Password of the network + uint8_t auto_connect; // Should we auto connect + uint8_t bssid[6]; // Optional: BSSID the AP + uint8_t sta_hostname[32]; // Name of the station + uint8_t ap_ssid[32]; // SSID of the own AP + uint8_t first_run; // Has ESPerPass been configured yet? + uint8_t current_mac_address; // Holds currently broadcasted HomePass mac address index + int32_t mac_change_interval; // Interval to rotate HomePass mac address (in seconds) + + // Seconds without ap traffic will cause reset (-1 off, default) + int32_t ap_watchdog; + // Seconds without client traffic will cause reset (-1 off, default) + int32_t client_watchdog; + + ip_addr_t network_addr; // Address of the internal network + ip_addr_t dns_addr; // Optional: address of the dns server + + ip_addr_t my_addr; // Optional (if not DHCP): IP address of the uplink side + ip_addr_t my_netmask; // Optional (if not DHCP): IP netmask of the uplink side + ip_addr_t my_gw; // Optional (if not DHCP): Gateway of the uplink side +#ifdef PHY_MODE + uint16_t phy_mode; // WiFi PHY mode +#endif + uint16_t clock_speed; // Freq of the CPU + uint16_t status_led; // GPIO pin os the status LED (>16 disabled) + + uint8_t STA_MAC_address[6]; // MAC address of the STA + + uint16_t dhcps_entries; // number of allocated entries in the following table + struct dhcps_pool dhcps_p[MAX_DHCP]; // DHCP entries +#ifdef ACLS + acl_entry acl[MAX_NO_ACLS][MAX_ACL_ENTRIES]; // ACL entries + uint8_t acl_freep[MAX_NO_ACLS]; // ACL free pointers +#endif + + // HomePass mac list + // Allow 20 slots + uint8_t mac_list[19][6]; + +} sysconfig_t, *sysconfig_p; + +int config_load(sysconfig_p config); +void config_save(sysconfig_p config); + +void blob_save(uint8_t blob_no, uint32_t *data, uint16_t len); +void blob_load(uint8_t blob_no, uint32_t *data, uint16_t len); +void blob_zero(uint8_t blob_no, uint16_t len); + +#endif diff --git a/user/ringbuf.c b/user/ringbuf.c new file mode 100644 index 0000000..7668b5e --- /dev/null +++ b/user/ringbuf.c @@ -0,0 +1,250 @@ +/* + * ringbuf.c - C ring buffer (FIFO) implementation. + * + * Written in 2011 by Drew Hess . + * + * To the extent possible under law, the author(s) have dedicated all + * copyright and related and neighboring rights to this software to + * the public domain worldwide. This software is distributed without + * any warranty. + * + * You should have received a copy of the CC0 Public Domain Dedication + * along with this software. If not, see + * . + */ + +#include "ringbuf.h" + +#include +#include +#include +#include +#include +#include + +#include "osapi.h" +#include "mem.h" + +#define assert(x) + +/* + * The code is written for clarity, not cleverness or performance, and + * contains many assert()s to enforce invariant assumptions and catch + * bugs. Feel free to optimize the code and to remove asserts for use + * in your own projects, once you're comfortable that it functions as + * intended. + */ + +struct ringbuf_t +{ + uint8_t *buf; + uint8_t *head, *tail; + size_t size; +}; + +ringbuf_t +ringbuf_new(size_t capacity) +{ + ringbuf_t rb = (ringbuf_t)os_malloc(sizeof(struct ringbuf_t)); + if (rb) { + + /* One byte is used for detecting the full condition. */ + rb->size = capacity + 1; + rb->buf = (uint8_t *)os_malloc(rb->size); + if (rb->buf) + ringbuf_reset(rb); + else { + os_free(rb); + return 0; + } + } + return rb; +} + +size_t +ringbuf_buffer_size(const struct ringbuf_t *rb) +{ + return rb->size; +} + +void +ringbuf_reset(ringbuf_t rb) +{ + rb->head = rb->tail = rb->buf; +} + +void +ringbuf_free(ringbuf_t *rb) +{ + assert(rb && *rb); + os_free((*rb)->buf); + os_free(*rb); + *rb = 0; +} + +size_t +ringbuf_capacity(const struct ringbuf_t *rb) +{ + return ringbuf_buffer_size(rb) - 1; +} + +/* + * Return a pointer to one-past-the-end of the ring buffer's + * contiguous buffer. You shouldn't normally need to use this function + * unless you're writing a new ringbuf_* function. + */ +static const uint8_t * +ringbuf_end(const struct ringbuf_t *rb) +{ + return rb->buf + ringbuf_buffer_size(rb); +} + +size_t +ringbuf_bytes_free(const struct ringbuf_t *rb) +{ + if (rb->head >= rb->tail) + return ringbuf_capacity(rb) - (rb->head - rb->tail); + else + return rb->tail - rb->head - 1; +} + +size_t +ringbuf_bytes_used(const struct ringbuf_t *rb) +{ + return ringbuf_capacity(rb) - ringbuf_bytes_free(rb); +} + +int +ringbuf_is_full(const struct ringbuf_t *rb) +{ + return ringbuf_bytes_free(rb) == 0; +} + +int +ringbuf_is_empty(const struct ringbuf_t *rb) +{ + return ringbuf_bytes_free(rb) == ringbuf_capacity(rb); +} + +const void * +ringbuf_tail(const struct ringbuf_t *rb) +{ + return rb->tail; +} + +const void * +ringbuf_head(const struct ringbuf_t *rb) +{ + return rb->head; +} + +/* + * Given a ring buffer rb and a pointer to a location within its + * contiguous buffer, return the a pointer to the next logical + * location in the ring buffer. + */ +static uint8_t * +ringbuf_nextp(ringbuf_t rb, const uint8_t *p) +{ + /* + * The assert guarantees the expression (++p - rb->buf) is + * non-negative; therefore, the modulus operation is safe and + * portable. + */ + assert((p >= rb->buf) && (p < ringbuf_end(rb))); + return rb->buf + ((++p - rb->buf) % ringbuf_buffer_size(rb)); +} + +void * +ringbuf_memcpy_into(ringbuf_t dst, const void *src, size_t count) +{ + const uint8_t *u8src = src; + const uint8_t *bufend = ringbuf_end(dst); + int overflow = count > ringbuf_bytes_free(dst); + size_t nread = 0; + + while (nread != count) { + /* don't copy beyond the end of the buffer */ + assert(bufend > dst->head); + size_t n = MIN(bufend - dst->head, count - nread); + os_memcpy(dst->head, u8src + nread, n); + dst->head += n; + nread += n; + + /* wrap? */ + if (dst->head == bufend) + dst->head = dst->buf; + } + + if (overflow) { + dst->tail = ringbuf_nextp(dst, dst->head); + assert(ringbuf_is_full(dst)); + } + + return dst->head; +} + +void * +ringbuf_memcpy_from(void *dst, ringbuf_t src, size_t count) +{ + size_t bytes_used = ringbuf_bytes_used(src); + if (count > bytes_used) + return 0; + + uint8_t *u8dst = dst; + const uint8_t *bufend = ringbuf_end(src); + size_t nwritten = 0; + while (nwritten != count) { + assert(bufend > src->tail); + size_t n = MIN(bufend - src->tail, count - nwritten); + os_memcpy(u8dst + nwritten, src->tail, n); + src->tail += n; + nwritten += n; + + /* wrap ? */ + if (src->tail == bufend) + src->tail = src->buf; + } + + assert(count + ringbuf_bytes_used(src) == bytes_used); + return src->tail; +} + +void * +ringbuf_copy(ringbuf_t dst, ringbuf_t src, size_t count) +{ + size_t src_bytes_used = ringbuf_bytes_used(src); + if (count > src_bytes_used) + return 0; + int overflow = count > ringbuf_bytes_free(dst); + + const uint8_t *src_bufend = ringbuf_end(src); + const uint8_t *dst_bufend = ringbuf_end(dst); + size_t ncopied = 0; + while (ncopied != count) { + assert(src_bufend > src->tail); + size_t nsrc = MIN(src_bufend - src->tail, count - ncopied); + assert(dst_bufend > dst->head); + size_t n = MIN(dst_bufend - dst->head, nsrc); + os_memcpy(dst->head, src->tail, n); + src->tail += n; + dst->head += n; + ncopied += n; + + /* wrap ? */ + if (src->tail == src_bufend) + src->tail = src->buf; + if (dst->head == dst_bufend) + dst->head = dst->buf; + } + + assert(count + ringbuf_bytes_used(src) == src_bytes_used); + + if (overflow) { + dst->tail = ringbuf_nextp(dst, dst->head); + assert(ringbuf_is_full(dst)); + } + + return dst->head; +} + diff --git a/user/ringbuf.h b/user/ringbuf.h new file mode 100644 index 0000000..c032b9e --- /dev/null +++ b/user/ringbuf.h @@ -0,0 +1,167 @@ +#ifndef INCLUDED_RINGBUF_H +#define INCLUDED_RINGBUF_H + +/* + * ringbuf.h - C ring buffer (FIFO) interface. + * + * Written in 2011 by Drew Hess . + * + * To the extent possible under law, the author(s) have dedicated all + * copyright and related and neighboring rights to this software to + * the public domain worldwide. This software is distributed without + * any warranty. + * + * You should have received a copy of the CC0 Public Domain Dedication + * along with this software. If not, see + * . + */ + +/* + * A byte-addressable ring buffer FIFO implementation. + * + * The ring buffer's head pointer points to the starting location + * where data should be written when copying data *into* the buffer + * (e.g., with ringbuf_read). The ring buffer's tail pointer points to + * the starting location where data should be read when copying data + * *from* the buffer (e.g., with ringbuf_write). + */ + +#include +#include + +typedef struct ringbuf_t *ringbuf_t; + +/* + * Create a new ring buffer with the given capacity (usable + * bytes). Note that the actual internal buffer size may be one or + * more bytes larger than the usable capacity, for bookkeeping. + * + * Returns the new ring buffer object, or 0 if there's not enough + * memory to fulfill the request for the given capacity. + */ +ringbuf_t +ringbuf_new(size_t capacity); + +/* + * The size of the internal buffer, in bytes. One or more bytes may be + * unusable in order to distinguish the "buffer full" state from the + * "buffer empty" state. + * + * For the usable capacity of the ring buffer, use the + * ringbuf_capacity function. + */ +size_t +ringbuf_buffer_size(const struct ringbuf_t *rb); + +/* + * Deallocate a ring buffer, and, as a side effect, set the pointer to + * 0. + */ +void +ringbuf_free(ringbuf_t *rb); + +/* + * Reset a ring buffer to its initial state (empty). + */ +void +ringbuf_reset(ringbuf_t rb); + +/* + * The usable capacity of the ring buffer, in bytes. Note that this + * value may be less than the ring buffer's internal buffer size, as + * returned by ringbuf_buffer_size. + */ +size_t +ringbuf_capacity(const struct ringbuf_t *rb); + +/* + * The number of free/available bytes in the ring buffer. This value + * is never larger than the ring buffer's usable capacity. + */ +size_t +ringbuf_bytes_free(const struct ringbuf_t *rb); + +/* + * The number of bytes currently being used in the ring buffer. This + * value is never larger than the ring buffer's usable capacity. + */ +size_t +ringbuf_bytes_used(const struct ringbuf_t *rb); + +int +ringbuf_is_full(const struct ringbuf_t *rb); + +int +ringbuf_is_empty(const struct ringbuf_t *rb); + +/* + * Const access to the head and tail pointers of the ring buffer. + */ +const void * +ringbuf_tail(const struct ringbuf_t *rb); + +const void * +ringbuf_head(const struct ringbuf_t *rb); + +/* + * Copy n bytes from a contiguous memory area src into the ring buffer + * dst. Returns the ring buffer's new head pointer. + * + * It is possible to copy more data from src than is available in the + * buffer; i.e., it's possible to overflow the ring buffer using this + * function. When an overflow occurs, the state of the ring buffer is + * guaranteed to be consistent, including the head and tail pointers; + * old data will simply be overwritten in FIFO fashion, as + * needed. However, note that, if calling the function results in an + * overflow, the value of the ring buffer's tail pointer may be + * different than it was before the function was called. + */ +void * +ringbuf_memcpy_into(ringbuf_t dst, const void *src, size_t count); + +/* + * Copy n bytes from the ring buffer src, starting from its tail + * pointer, into a contiguous memory area dst. Returns the value of + * src's tail pointer after the copy is finished. + * + * Note that this copy is destructive with respect to the ring buffer: + * the n bytes copied from the ring buffer are no longer available in + * the ring buffer after the copy is complete, and the ring buffer + * will have n more free bytes than it did before the function was + * called. + * + * This function will *not* allow the ring buffer to underflow. If + * count is greater than the number of bytes used in the ring buffer, + * no bytes are copied, and the function will return 0. + */ +void * +ringbuf_memcpy_from(void *dst, ringbuf_t src, size_t count); + +/* + * Copy count bytes from ring buffer src, starting from its tail + * pointer, into ring buffer dst. Returns dst's new head pointer after + * the copy is finished. + * + * Note that this copy is destructive with respect to the ring buffer + * src: any bytes copied from src into dst are no longer available in + * src after the copy is complete, and src will have 'count' more free + * bytes than it did before the function was called. + * + * It is possible to copy more data from src than is available in dst; + * i.e., it's possible to overflow dst using this function. When an + * overflow occurs, the state of dst is guaranteed to be consistent, + * including the head and tail pointers; old data will simply be + * overwritten in FIFO fashion, as needed. However, note that, if + * calling the function results in an overflow, the value dst's tail + * pointer may be different than it was before the function was + * called. + * + * It is *not* possible to underflow src; if count is greater than the + * number of bytes used in src, no bytes are copied, and the function + * returns 0. + */ +void * +ringbuf_copy(ringbuf_t dst, ringbuf_t src, size_t count); + +#endif /* INCLUDED_RINGBUF_H */ + diff --git a/user/sys_time.c b/user/sys_time.c new file mode 100644 index 0000000..6748566 --- /dev/null +++ b/user/sys_time.c @@ -0,0 +1,36 @@ +#include "c_types.h" +#include "osapi.h" + +typedef union _timer { + uint32_t time_s[2]; + uint64_t time_l; +} long_time_t; + +static long_time_t time; +static uint32_t old; + +uint64_t ICACHE_FLASH_ATTR +get_long_systime() +{ + uint32_t now = system_get_time(); + if (now < old) + { + time.time_s[1]++; + } + old = now; + time.time_s[0] = now; + return time.time_l; +} + +uint64_t ICACHE_FLASH_ATTR +get_low_systime() +{ + get_long_systime(); + return time.time_s[0]; +} + +void init_long_systime() +{ + old = system_get_time(); + time.time_l = (uint64_t)old; +} diff --git a/user/sys_time.h b/user/sys_time.h new file mode 100644 index 0000000..43c3538 --- /dev/null +++ b/user/sys_time.h @@ -0,0 +1,13 @@ +#include "c_types.h" + +// returns time until boot in us +uint64_t ICACHE_FLASH_ATTR +get_long_systime(); + +// returns lower half of time until boot in us +uint64_t ICACHE_FLASH_ATTR +get_low_systime(); + +// initializes the timer +void +init_long_systime(); diff --git a/user/user_config.h b/user/user_config.h new file mode 100644 index 0000000..f4c5cc8 --- /dev/null +++ b/user/user_config.h @@ -0,0 +1,38 @@ +#ifndef _USER_CONFIG_ +#define _USER_CONFIG_ + +#define ESPERPASS_VERSION "V0.0.1" + +#define WIFI_SSID "ssid" +#define WIFI_PASSWORD "password" + +#define WIFI_AP_SSID "attwifi" + +#define MAX_CLIENTS 8 +#define MAX_DHCP 8 + +// +// Size of the console buffers +// +#define MAX_CON_SEND_SIZE 1024 +#define MAX_CON_CMD_SIZE 80 + +// +// Define this if you have a status LED connected to a GPIO pin +// +#define STATUS_LED_GPIO 2 + +// +// Define this to support the setting of the WiFi PHY mode +// +#define PHY_MODE 1 + +// +// Define this if you want to have ACLs for the SoftAP. +// +#define ACLS 1 + +// Internal +typedef enum {SIG_DO_NOTHING=0, SIG_START_SERVER=1, SIG_SEND_DATA, SIG_UART0, SIG_CONSOLE_RX, SIG_CONSOLE_TX, SIG_CONSOLE_TX_RAW, SIG_GPIO_INT} USER_SIGNALS; + +#endif diff --git a/user/user_main.c b/user/user_main.c new file mode 100644 index 0000000..a8b37b5 --- /dev/null +++ b/user/user_main.c @@ -0,0 +1,1494 @@ +#include "c_types.h" +#include "mem.h" +#include "ets_sys.h" +#include "osapi.h" +#include "gpio.h" +#include "os_type.h" +#include "lwip/ip.h" +#include "lwip/netif.h" +#include "lwip/dns.h" +#include "lwip/lwip_napt.h" +#include "lwip/app/dhcpserver.h" +#include "lwip/app/espconn.h" +#include "lwip/app/espconn_tcp.h" + +#include "user_interface.h" +#include "string.h" +#include "driver/uart.h" + +#include "ringbuf.h" +#include "user_config.h" +#include "config_flash.h" +#include "sys_time.h" + +#include "easygpio.h" + +#ifdef ACLS +#include "acl.h" +#endif + +/* System Task, for signals refer to user_config.h */ +#define user_procTaskPrio 0 +#define user_procTaskQueueLen 1 +os_event_t user_procTaskQueue[user_procTaskQueueLen]; +static void user_procTask(os_event_t *events); + +static os_timer_t ptimer; + +int32_t ap_watchdog_cnt; +int32_t client_watchdog_cnt; +int32_t mac_cnt; + +/* Some stats */ +uint64_t Bytes_in, Bytes_out, Bytes_in_last, Bytes_out_last; +uint32_t Packets_in, Packets_out, Packets_in_last, Packets_out_last; +uint64_t t_old; + +/* Hold the system wide configuration */ +sysconfig_t config; + +static ringbuf_t console_rx_buffer, console_tx_buffer; + +static ip_addr_t my_ip; +static ip_addr_t dns_ip; +bool connected; +uint8_t my_channel; +bool do_ip_config; + +static netif_input_fn orig_input_ap, orig_input_sta; +static netif_linkoutput_fn orig_output_ap, orig_output_sta; + +uint8_t remote_console_disconnect; +struct espconn *currentconn; + +void ICACHE_FLASH_ATTR user_set_softap_wifi_config(void); +void ICACHE_FLASH_ATTR user_set_softap_ip_config(void); +void ICACHE_FLASH_ATTR user_set_station_config(void); + +void +ICACHE_FLASH_ATTR to_console(char *str) +{ + ringbuf_memcpy_into(console_tx_buffer, str, os_strlen(str)); +} + +err_t ICACHE_FLASH_ATTR +my_input_ap(struct pbuf *p, struct netif *inp) +{ + // os_printf("Got packet from STA\r\n"); + + if (config.status_led <= 16) + { + easygpio_outputSet (config.status_led, 1); + } + + client_watchdog_cnt = config.client_watchdog; + +#ifdef ACLS + // Check ACLs - store result + uint8_t acl_check = ACL_ALLOW; + if (!acl_is_empty(0)) + { + acl_check = acl_check_packet(0, p); + } +#endif + +#ifdef ACLS + // If not allowed, drop packet + if (!(acl_check&ACL_ALLOW)) + { + pbuf_free(p); + return; + } +#endif + + Bytes_in += p->tot_len; + Packets_in++; + + orig_input_ap (p, inp); +} + +err_t ICACHE_FLASH_ATTR +my_output_ap(struct netif *outp, struct pbuf *p) +{ + // os_printf("Send packet to STA\r\n"); + + if (config.status_led <= 16) + { + easygpio_outputSet (config.status_led, 0); + } + +#ifdef ACLS + // Check ACLs - store result + uint8_t acl_check = ACL_ALLOW; + if (!acl_is_empty(1)) + { + acl_check = acl_check_packet(1, p); + } +#endif + +#ifdef ACLS + // If not allowed, drop packet + if (!(acl_check&ACL_ALLOW)) + { + pbuf_free(p); + return; + } +#endif + + Bytes_out += p->tot_len; + Packets_out++; + + orig_output_ap (outp, p); +} + +err_t ICACHE_FLASH_ATTR +my_input_sta(struct pbuf *p, struct netif *inp) +{ + ap_watchdog_cnt = config.ap_watchdog; +#ifdef ACLS + if (!acl_is_empty(2) && !(acl_check_packet(2, p) & ACL_ALLOW)) + { + pbuf_free(p); + return; + } +#endif + orig_input_sta (p, inp); +} + +err_t ICACHE_FLASH_ATTR +my_output_sta(struct netif *outp, struct pbuf *p) +{ +#ifdef ACLS + if (!acl_is_empty(3) && !(acl_check_packet(3, p) & ACL_ALLOW)) + { + pbuf_free(p); + return; + } +#endif + orig_output_sta (outp, p); +} + +static void ICACHE_FLASH_ATTR +patch_netif(ip_addr_t netif_ip, + netif_input_fn ifn, + netif_input_fn *orig_ifn, + netif_linkoutput_fn ofn, + netif_linkoutput_fn *orig_ofn, + bool nat) +{ + struct netif *nif; + + for (nif = netif_list; + nif != NULL && nif->ip_addr.addr != netif_ip.addr; + nif = nif->next); + + if (nif == NULL) + { + return; + } + + nif->napt = nat?1:0; + if (ifn != NULL && nif->input != ifn) + { + *orig_ifn = nif->input; + nif->input = ifn; + } + if (ofn != NULL && nif->linkoutput != ofn) + { + *orig_ofn = nif->linkoutput; + nif->linkoutput = ofn; + } +} + +int ICACHE_FLASH_ATTR +parse_str_into_tokens(char *str, char **tokens, int max_tokens) +{ + char *p, *q, *end; + int token_count = 0; + bool in_token = false; + + // preprocessing + for (p = q = str; *p != 0; p++) + { + if (*(p) == '%' && *(p+1) != 0 && *(p+2) != 0) + { + // quoted hex + uint8_t a; + p++; + if (*p <= '9') + a = *p - '0'; + else + a = toupper(*p) - 'A' + 10; + a <<= 4; + p++; + if (*p <= '9') + a += *p - '0'; + else + a += toupper(*p) - 'A' + 10; + *q++ = a; + } + else if (*p == '\\' && *(p+1) != 0) + { + // next char is quoted - just copy it, skip this one + *q++ = *++p; + } + else if (*p == 8) + { + // backspace - delete previous char + if (q != str) + { + q--; + } + } + else if (*p <= ' ') + { + // mark this as whitespace + *q++ = 0; + } + else + { + *q++ = *p; + } + } + + end = q; + *q = 0; + + // cut into tokens + for (p = str; p != end; p++) + { + if (*p == 0) + { + if (in_token) + { + in_token = false; + } + } + else + { + if (!in_token) + { + tokens[token_count++] = p; + if (token_count == max_tokens) + { + return token_count; + } + in_token = true; + } + } + } + return token_count; +} + +void +console_send_response(struct espconn *pespconn, uint8_t do_cmd) +{ + char payload[MAX_CON_SEND_SIZE+4]; + uint16_t len = ringbuf_bytes_used(console_tx_buffer); + + ringbuf_memcpy_from(payload, console_tx_buffer, len); + + if (do_cmd) + { + os_memcpy(&payload[len], "CMD>", 4); + len += 4; + } + + if (pespconn != NULL) + { + espconn_sent(pespconn, payload, len); + } + else + { + UART_Send(0, &payload, len); + } +} + + +#ifdef ACLS +void ICACHE_FLASH_ATTR +parse_IP_addr(uint8_t *str, uint32_t *addr, uint32_t *mask) +{ + int i; + uint32_t net; + if (strcmp(str, "any") == 0) + { + *addr = 0; + *mask = 0; + return; + } + + for(i=0; str[i]!=0 && str[i]!='/'; i++); + + *mask = 0xffffffff; + if (str[i]!=0) + { + str[i]=0; + *mask <<= (32 - atoi(&str[i+1])); + } + *mask = htonl(*mask); + *addr = ipaddr_addr(str); +} + +struct espconn *deny_cb_conn = 0; +uint8_t acl_debug = 0; + +uint8_t +acl_deny_cb(uint8_t proto, + uint32_t saddr, + uint16_t s_port, + uint32_t daddr, + uint16_t d_port, + uint8_t allow) +{ + char response[128]; + + if (!acl_debug) + { + return allow; + } + + os_sprintf(response, + "\rdeny: %s Src: %d.%d.%d.%d:%d Dst: %d.%d.%d.%d:%d\r\n", + proto==IP_PROTO_TCP?"TCP":proto==IP_PROTO_UDP?"UDP":"IP4", + IP2STR((ip_addr_t *)&saddr), + s_port, + IP2STR((ip_addr_t *)&daddr), + d_port); + + if (acl_debug) + { + to_console(response); + system_os_post(0, SIG_CONSOLE_TX, (ETSParam) deny_cb_conn); + } + return allow; +} +#endif /* ACLS */ + +// Use this from ROM instead +int ets_str2macaddr(uint8 *mac, char *str_mac); +#define parse_mac ets_str2macaddr +/*bool parse_mac(uint8_t *mac, uint8_t *inp) +{ +int i; + + if (os_strlen(inp) != 17) return false; + for (i=0; i<17; i++) { + if (inp[i] == ':') continue; + inp[i] = toupper(inp[i]); + inp[i] = inp[i] <= '9'? inp[i]-'0' : (inp[i]-'A')+10; + if (inp[i] >= 16) return false; + } + + for (i=0; i<17; i+=3) { + *mac++ = inp[i]*16+inp[i+1]; + } + return true; +} +*/ +static char INVALID_NUMARGS[] = "Invalid number of arguments\r\n"; +static char INVALID_ARG[] = "Invalid argument\r\n"; + +void ICACHE_FLASH_ATTR +console_handle_command(struct espconn *pespconn) +{ + #define MAX_CMD_TOKENS 9 + + char cmd_line[MAX_CON_CMD_SIZE+1]; + char response[256]; + char *tokens[MAX_CMD_TOKENS]; + + int bytes_count, nTokens; + + bytes_count = ringbuf_bytes_used(console_rx_buffer); + ringbuf_memcpy_from(cmd_line, console_rx_buffer, bytes_count); + + cmd_line[bytes_count] = 0; + response[0] = 0; + + nTokens = parse_str_into_tokens(cmd_line, tokens, MAX_CMD_TOKENS); + + if (nTokens == 0) + { + char c = '\n'; + ringbuf_memcpy_into(console_tx_buffer, &c, 1); + goto command_handled_2; + } + + if (strcmp(tokens[0], "help") == 0) + { + os_sprintf(response, "show [config|stats]\r\n"); + to_console(response); + + os_sprintf(response, "set [ssid|password|auto_connect|ap_ssid] \r\nset [sta_mac|sta_hostname] \r\nset [dns|ip|netmask|gw] \r\n"); + to_console(response); + os_sprintf(response, "set [speed|status_led|config_port] \r\nsave [config|dhcp]\r\nconnect | disconnect| reset [factory] | quit\r\n"); + to_console(response); + os_sprintf(response, "set [client_watchdog|ap_watchdog] \r\n"); + to_console(response); +#ifdef PHY_MODE + os_sprintf(response, "set phy_mode [1|2|3]\r\n"); + to_console(response); +#endif + +#ifdef ACLS + os_sprintf(response, "acl [from_sta|to_sta|from_ap|to_ap] clear\r\nacl [from_sta|to_sta|from_ap|to_ap] [IP|TCP|UDP] [] [] [allow|deny|allow_monitor|deny_monitor]\r\n"); + to_console(response); +#endif + goto command_handled_2; + } + + if (strcmp(tokens[0], "mac_list") == 0) + { + // List stored HomePass mac addresses + int16_t i; + + to_console("HomePass mac list:\r\n"); + for (i = 0; i < MAX_MAC_LIST_LENGTH; i++) + { + os_sprintf(response, "%02x:%02x:%02x:%02x:%02x:%02x\r\n", + config.mac_list[i][0], config.mac_list[i][1], + config.mac_list[i][2], config.mac_list[i][3], + config.mac_list[i][4], config.mac_list[i][5]); + to_console(response); + } + os_sprintf(response, "\r\n"); + to_console(response); + + goto command_handled_2; + } + + if (strcmp(tokens[0], "show") == 0) + { + int16_t i; + ip_addr_t i_ip; + + if (nTokens == 1 || (nTokens == 2 && strcmp(tokens[1], "config") == 0)) + { + os_sprintf(response, + "Version %s (build: %s)\r\n", + ESPERPASS_VERSION, __TIMESTAMP__); + to_console(response); + + os_sprintf(response, "STA: SSID:%s PW:%s%s\r\n", + config.ssid, + (char*)config.password, + config.auto_connect?"":" [AutoConnect:0]"); + to_console(response); + if (*(int*)config.bssid != 0) + { + os_sprintf(response, "BSSID: %02x:%02x:%02x:%02x:%02x:%02x\r\n", + config.bssid[0], config.bssid[1], config.bssid[2], + config.bssid[3], config.bssid[4], config.bssid[5]); + to_console(response); + } + + os_sprintf(response, "AP: SSID:%s IP:%d.%d.%d.%d/24", + config.ap_ssid, + IP2STR(&config.network_addr)); + to_console(response); + + // if static DNS, add it + os_sprintf(response, + config.dns_addr.addr?" DNS: %d.%d.%d.%d\r\n":"\r\n", + IP2STR(&config.dns_addr)); + to_console(response); + + // if static IP, add it + os_sprintf(response, + config.my_addr.addr?"Static IP: %d.%d.%d.%d Netmask: %d.%d.%d.%d Gateway: %d.%d.%d.%d\r\n":"", + IP2STR(&config.my_addr), IP2STR(&config.my_netmask), + IP2STR(&config.my_gw)); + to_console(response); + + os_sprintf(response, + "STA MAC: %02x:%02x:%02x:%02x:%02x:%02x\r\nAP MAC: %02x:%02x:%02x:%02x:%02x:%02x\r\n", + config.STA_MAC_address[0], config.STA_MAC_address[1], + config.STA_MAC_address[2], config.STA_MAC_address[3], + config.STA_MAC_address[4], config.STA_MAC_address[5], + config.mac_list[config.current_mac_address][0], + config.mac_list[config.current_mac_address][1], + config.mac_list[config.current_mac_address][2], + config.mac_list[config.current_mac_address][3], + config.mac_list[config.current_mac_address][4], + config.mac_list[config.current_mac_address][5]); + to_console(response); + os_sprintf(response, "STA hostname: %s\r\n", config.sta_hostname); + to_console(response); + + os_sprintf(response, "Clock speed: %d\r\n", config.clock_speed); + to_console(response); + + goto command_handled_2; + } + + if (nTokens == 2 && strcmp(tokens[1], "stats") == 0) + { + uint32_t time = (uint32_t)(get_long_systime()/1000000); + int16_t i; + enum phy_mode phy; + struct dhcps_pool *p; + os_sprintf(response, "System uptime: %d:%02d:%02d\r\n", + time/3600, (time%3600)/60, time%60); + to_console(response); + os_sprintf(response, + "%d KiB in (%d packets)\r\n%d KiB out (%d packets)\r\n", + (uint32_t)(Bytes_in/1024), Packets_in, + (uint32_t)(Bytes_out/1024), Packets_out); + to_console(response); +#ifdef PHY_MODE + phy = wifi_get_phy_mode(); + os_sprintf(response, "Phy mode: %c\r\n", + phy == PHY_MODE_11B?'b':phy == PHY_MODE_11G?'g':'n'); + to_console(response); +#endif + os_sprintf(response, "Free mem: %d\r\n", system_get_free_heap_size()); + to_console(response); + if (connected) + { + os_sprintf(response, "External IP-address: " IPSTR "\r\n", IP2STR(&my_ip)); + } + else + { + os_sprintf(response, "Not connected to AP\r\n"); + } + to_console(response); + + os_sprintf(response, + "%d Station%s connected to SoftAP\r\n", + wifi_softap_get_station_num(), + wifi_softap_get_station_num()==1?"":"s"); + + to_console(response); + for (i = 0; p = dhcps_get_mapping(i); i++) + { + os_sprintf(response, + "Station: %02x:%02x:%02x:%02x:%02x:%02x - " IPSTR "\r\n", + p->mac[0], p->mac[1], p->mac[2], p->mac[3], p->mac[4], + p->mac[5], IP2STR(&p->ip)); + to_console(response); + } + + if (config.ap_watchdog >= 0 || config.client_watchdog >= 0) + { + os_sprintf(response, "AP watchdog: %d Client watchdog: %d\r\n", + ap_watchdog_cnt, client_watchdog_cnt); + to_console(response); + } + goto command_handled_2; + } +#ifdef ACLS + if (nTokens == 2 && strcmp(tokens[1], "acl") == 0) + { + char *txt[] = {"From STA:\r\n", + "To STA:\r\n", "From AP:\r\n", "To AP:\r\n"}; + for (i = 0; i 1) + { + os_sprintf(response, INVALID_NUMARGS); + goto command_handled; + } + + user_set_station_config(); + os_sprintf(response, "Trying to connect to ssid %s, password: %s\r\n", config.ssid, config.password); + + wifi_station_disconnect(); + wifi_station_connect(); + + goto command_handled; + } + + if (strcmp(tokens[0], "disconnect") == 0) + { + if (nTokens > 1) + { + os_sprintf(response, INVALID_NUMARGS); + goto command_handled; + } + + os_sprintf(response, "Disconnect from ssid\r\n"); + + wifi_station_disconnect(); + + goto command_handled; + } + + if (strcmp(tokens[0], "save") == 0) + { + if (nTokens == 1 || (nTokens == 2 && strcmp(tokens[1], "config") == 0)) + { + config.first_run = 0; + config_save(&config); + os_sprintf(response, "Config saved\r\n"); + goto command_handled; + } + + if (nTokens == 2 && strcmp(tokens[1], "dhcp") == 0) + { + int16_t i; + struct dhcps_pool *p; + + for (i = 0; i 16) + { + os_sprintf(response, "Status led disabled\r\n"); + goto command_handled; + } + if (config.status_led == 1) + { + // Disable output if serial pin is used as status LED + system_set_os_print(0); + } + easygpio_pinMode(config.status_led, EASYGPIO_NOPULL, EASYGPIO_OUTPUT); + easygpio_outputSet (config.status_led, 0); + os_sprintf(response, "Status led set to GPIO %d\r\n", + config.status_led); + goto command_handled; + } + +#ifdef PHY_MODE + if (strcmp(tokens[1], "phy_mode") == 0) + { + uint16_t mode = atoi(tokens[2]); + bool succ = wifi_set_phy_mode(mode); + if (succ) + { + config.phy_mode = mode; + } + os_sprintf(response, "Phy mode setting %s\r\n", + succ?"successful":"failed"); + goto command_handled; + } +#endif + if (strcmp(tokens[1], "network") == 0) + { + config.network_addr.addr = ipaddr_addr(tokens[2]); + ip4_addr4(&config.network_addr) = 0; + os_sprintf(response, "Network set to %d.%d.%d.%d/24\r\n", + IP2STR(&config.network_addr)); + goto command_handled; + } + + if (strcmp(tokens[1], "dns") == 0) + { + if (os_strcmp(tokens[2], "dhcp") == 0) + { + config.dns_addr.addr = 0; + os_sprintf(response, "DNS from DHCP\r\n"); + } + else + { + config.dns_addr.addr = ipaddr_addr(tokens[2]); + os_sprintf(response, "DNS set to %d.%d.%d.%d\r\n", + IP2STR(&config.dns_addr)); + if (config.dns_addr.addr) + { + dns_ip.addr = config.dns_addr.addr; + dhcps_set_DNS(&dns_ip); + } + } + goto command_handled; + } + + if (strcmp(tokens[1], "ip") == 0) + { + if (os_strcmp(tokens[2], "dhcp") == 0) + { + config.my_addr.addr = 0; + os_sprintf(response, "IP from DHCP\r\n"); + } + else + { + config.my_addr.addr = ipaddr_addr(tokens[2]); + os_sprintf(response, "IP address set to %d.%d.%d.%d\r\n", + IP2STR(&config.my_addr)); + } + goto command_handled; + } + + if (strcmp(tokens[1],"netmask") == 0) + { + config.my_netmask.addr = ipaddr_addr(tokens[2]); + os_sprintf(response, "IP netmask set to %d.%d.%d.%d\r\n", + IP2STR(&config.my_netmask)); + goto command_handled; + } + + if (strcmp(tokens[1],"gw") == 0) + { + config.my_gw.addr = ipaddr_addr(tokens[2]); + os_sprintf(response, "Gateway set to %d.%d.%d.%d\r\n", + IP2STR(&config.my_gw)); + goto command_handled; + } + + if (strcmp(tokens[1],"sta_mac") == 0) + { + if (!parse_mac(config.STA_MAC_address, tokens[2])) + { + os_sprintf(response, INVALID_ARG); + } + else + { + os_sprintf(response, "STA MAC set\r\n"); + } + goto command_handled; + } + + if (strcmp(tokens[1],"bssid") == 0) + { + if (!parse_mac(config.bssid, tokens[2])) + { + os_sprintf(response, INVALID_ARG); + } + else + { + os_sprintf(response, "bssid set\r\n"); + } + goto command_handled; + } + } + } + + /* Control comes here only if the tokens[0] command is not handled */ + os_sprintf(response, "\r\nInvalid Command\r\n"); + +command_handled: + to_console(response); + +command_handled_2: + system_os_post(0, SIG_CONSOLE_TX, (ETSParam) pespconn); + + return; +} + +bool toggle; +// Timer cb function +void ICACHE_FLASH_ATTR +timer_func(void *arg) +{ + uint32_t Vcurr; + uint64_t t_new; + uint32_t t_diff; + + toggle = !toggle; + + // Check if watchdogs + if (toggle) + { + // Rotate HomePass mac address if necessary + if (config.auto_connect == 1) + { + if (mac_cnt >= config.mac_change_interval) + { + mac_cnt = 0; + // os_printf("Rotating mac address...\r\n"); + // os_printf("config.current_mac_address = %d\r\n", config.current_mac_address); + + // os_printf("OLD MAC: %02x:%02x:%02x:%02x:%02x:%02x\r\n", + // config.mac_list[config.current_mac_address][0], + // config.mac_list[config.current_mac_address][1], + // config.mac_list[config.current_mac_address][2], + // config.mac_list[config.current_mac_address][3], + // config.mac_list[config.current_mac_address][4], + // config.mac_list[config.current_mac_address][5]); + + if (config.current_mac_address >= (MAX_MAC_LIST_LENGTH - 1)) + { + config.current_mac_address = 0; + } + else + { + config.current_mac_address++; + } + + // os_printf("NEW MAC: %02x:%02x:%02x:%02x:%02x:%02x\r\n\r\n", + // config.mac_list[config.current_mac_address][0], + // config.mac_list[config.current_mac_address][1], + // config.mac_list[config.current_mac_address][2], + // config.mac_list[config.current_mac_address][3], + // config.mac_list[config.current_mac_address][4], + // config.mac_list[config.current_mac_address][5]); + + // Save current mac address config to flash + config_save(&config); + + // Start using new mac address + // wifi_set_macaddr(SOFTAP_IF, config.mac_list[config.current_mac_address]); + system_restart(); + } + else + { + mac_cnt++; + } + } + + if (ap_watchdog_cnt >= 0) + { + if (ap_watchdog_cnt == 0) + { + os_printf("AP watchdog reset\r\n"); + system_restart(); + } + ap_watchdog_cnt--; + } + + if (client_watchdog_cnt >= 0) + { + if (client_watchdog_cnt == 0) + { + os_printf("Client watchdog reset\r\n"); + system_restart(); + } + client_watchdog_cnt--; + } + } + + if (config.status_led <= 16) + { + easygpio_outputSet (config.status_led, toggle && connected); + } + + // Do we still have to configure the AP netif? + if (do_ip_config) + { + user_set_softap_ip_config(); + do_ip_config = false; + } + + t_new = get_long_systime(); + + os_timer_arm(&ptimer, toggle?900:100, 0); +} + +//Priority 0 Task +static void ICACHE_FLASH_ATTR +user_procTask(os_event_t *events) +{ + //os_printf("Sig: %d\r\n", events->sig); + + switch(events->sig) + { + case SIG_START_SERVER: + { + // Anything else to do here, when the repeater has received its IP? + } break; + + case SIG_CONSOLE_TX: + case SIG_CONSOLE_TX_RAW: + { + struct espconn *pespconn = (struct espconn *) events->par; + console_send_response(pespconn, events->sig == SIG_CONSOLE_TX); + + if (pespconn != 0 && remote_console_disconnect) + { + espconn_disconnect(pespconn); + } + remote_console_disconnect = 0; + } break; + + case SIG_CONSOLE_RX: + { + struct espconn *pespconn = (struct espconn *) events->par; + console_handle_command(pespconn); + } break; + + case SIG_DO_NOTHING: + default: + { + // Intentionally ignoring other signals + os_printf("Spurious Signal received\r\n"); + } break; + } +} + +/* Callback called when the connection state of the module with an Access Point changes */ +void +wifi_handle_event_cb(System_Event_t *evt) +{ + uint16_t i; + uint8_t mac_str[20]; + + //os_printf("wifi_handle_event_cb: "); + switch (evt->event) + { + case EVENT_STAMODE_CONNECTED: + { + os_printf("connect to ssid %s, channel %d\r\n", + evt->event_info.connected.ssid, + evt->event_info.connected.channel); + my_channel = evt->event_info.connected.channel; + } break; + + case EVENT_STAMODE_DISCONNECTED: + { + os_printf("disconnect from ssid %s, reason %d\r\n", + evt->event_info.disconnected.ssid, + evt->event_info.disconnected.reason); + connected = false; + } break; + + case EVENT_STAMODE_AUTHMODE_CHANGE: + { + // os_printf("mode: %d -> %d\r\n", + // evt->event_info.auth_change.old_mode, + // evt->event_info.auth_change.new_mode); + } break; + + case EVENT_STAMODE_GOT_IP: + { + if (config.dns_addr.addr == 0) + { + dns_ip = dns_getserver(0); + } + dhcps_set_DNS(&dns_ip); + + os_printf("ip:" IPSTR ",mask:" IPSTR ",gw:" IPSTR ",dns:" IPSTR "\n", + IP2STR(&evt->event_info.got_ip.ip), + IP2STR(&evt->event_info.got_ip.mask), + IP2STR(&evt->event_info.got_ip.gw), + IP2STR(&dns_ip)); + + my_ip = evt->event_info.got_ip.ip; + connected = true; + + patch_netif(my_ip, my_input_sta, &orig_input_sta, my_output_sta, &orig_output_sta, false); + + // Post a Server Start message as the IP has been acquired to Task with priority 0 + system_os_post(user_procTaskPrio, SIG_START_SERVER, 0 ); + } break; + + case EVENT_SOFTAPMODE_STACONNECTED: + { + os_sprintf(mac_str, MACSTR, MAC2STR(evt->event_info.sta_connected.mac)); + os_printf("station: %s join, AID = %d\r\n", + mac_str, evt->event_info.sta_connected.aid); + ip_addr_t ap_ip = config.network_addr; + ip4_addr4(&ap_ip) = 1; + patch_netif(ap_ip, my_input_ap, &orig_input_ap, my_output_ap, + &orig_output_ap, true); + } break; + + case EVENT_SOFTAPMODE_STADISCONNECTED: + { + os_sprintf(mac_str, MACSTR, + MAC2STR(evt->event_info.sta_disconnected.mac)); + os_printf("station: %s leave, AID = %d\r\n", mac_str, + evt->event_info.sta_disconnected.aid); + } break; + + default: + { + // Do nothing + } break; + } +} + +void ICACHE_FLASH_ATTR +user_set_softap_wifi_config(void) +{ + struct softap_config apConfig; + + wifi_softap_get_config(&apConfig); // Get config first. + + os_memset(apConfig.ssid, 0, 32); + os_sprintf(apConfig.ssid, "%s", config.ap_ssid); + apConfig.authmode = AUTH_OPEN; + apConfig.ssid_len = 0;// or its actual length + + // how many stations can connect to ESP8266 softAP at most. + apConfig.max_connection = MAX_CLIENTS; + + // Set ESP8266 softap config + wifi_softap_set_config(&apConfig); +} + +void ICACHE_FLASH_ATTR +user_set_softap_ip_config(void) +{ + struct ip_info info; + struct dhcps_lease dhcp_lease; + struct netif *nif; + int i; + + // Configure the internal network + + // Find the netif of the AP (that with num != 0) + for (nif = netif_list; nif != NULL && nif->num == 0; nif = nif->next); + if (nif == NULL) + { + return; + } + + // If is not 1, set it to 1. + // Kind of a hack, but the Espressif-internals expect it like this (hardcoded 1). + nif->num = 1; + + wifi_softap_dhcps_stop(); + + info.ip = config.network_addr; + ip4_addr4(&info.ip) = 1; + info.gw = info.ip; + IP4_ADDR(&info.netmask, 255, 255, 255, 0); + + wifi_set_ip_info(nif->num, &info); + + dhcp_lease.start_ip = config.network_addr; + ip4_addr4(&dhcp_lease.start_ip) = 2; + dhcp_lease.end_ip = config.network_addr; + ip4_addr4(&dhcp_lease.end_ip) = 128; + wifi_softap_set_dhcps_lease(&dhcp_lease); + + wifi_softap_dhcps_start(); + + // Change the DNS server again + dhcps_set_DNS(&dns_ip); + + // Enter any saved dhcp enties if they are in this network + for (i = 0; i prompt and follow these instructions:\r\n"); + os_printf("Note that the console does not support the backspace key.\r\n"); + os_printf("If you make a mistake, hit return and try the command again.\r\n\r\n"); + os_printf("1. Set your Internet WiFi ssid: set ssid \r\n"); + os_printf("2. Set your Internet WiFi password: set password \r\n"); + os_printf("3. Save the settings: save\r\n"); + os_printf("4. Restart the device: reset\r\n"); + os_printf("\r\n"); + + // Disable any further verbose system output + system_set_os_print(0); + } + else + { + // Now start the STA-Mode + user_set_station_config(); + } + + system_update_cpu_freq(config.clock_speed); + + // Start the timer + os_timer_setfn(&ptimer, timer_func, 0); + os_timer_arm(&ptimer, 500, 0); + + //Start task + system_os_task(user_procTask, user_procTaskPrio, user_procTaskQueue, + user_procTaskQueueLen); +}