diff --git a/.github/workflows/test_selfhosted_runner.yml b/.github/workflows/test_selfhosted_runner.yml new file mode 100644 index 00000000000..e7be6a6c4ff --- /dev/null +++ b/.github/workflows/test_selfhosted_runner.yml @@ -0,0 +1,27 @@ +name: Test Github action on self hosted RPI runnes + +on: + push: + branches: + - master + pull_request: + +jobs: + build: + name: Dummy test - self hosted GHR + runs-on: self-hosted + steps: + - name: Check out repo + uses: actions/checkout@v2 + - name: Test message 1 + run: echo "This is test message" + - name: Test message 2 + run: echo "This is test message2" + - name: List directory + run: ls + - name: Create copy of README + run: cp README.md README2.md + - name: Read README2 + run: cat README2.md + - name: Delete README2 + run: rm README2.md diff --git a/README.md b/README.md index d4aeb34a21d..80d8f712627 100644 --- a/README.md +++ b/README.md @@ -43,7 +43,7 @@ You can use [Arduino-ESP32 Online Documentation](https://docs.espressif.com/proj You can use [EspExceptionDecoder](https://github.com/me-no-dev/EspExceptionDecoder) to get meaningful call trace. ### Issue/Bug report template -Before reporting an issue, make sure you've searched for similar one that was already created. Also make sure to go through all the issues labelled as [for reference](https://github.com/espressif/arduino-esp32/issues?utf8=%E2%9C%93&q=is%3Aissue%20label%3A%22for%20reference%22%20). +Before reporting an issue, make sure you've searched for similar one that was already created. Also make sure to go through all the issues labelled as [Type: For reference](https://github.com/espressif/arduino-esp32/issues?q=is%3Aissue+label%3A%22Type%3A+For+reference%22+). Finally, if you are sure no one else had the issue, follow the [issue template](docs/ISSUE_TEMPLATE.md) while reporting any issue. diff --git a/boards.txt b/boards.txt index fb1854d5ec8..b94543c1fdb 100644 --- a/boards.txt +++ b/boards.txt @@ -57,13 +57,6 @@ esp32c3.menu.CDCOnBoot.default.build.cdc_on_boot=0 esp32c3.menu.CDCOnBoot.cdc=Enabled esp32c3.menu.CDCOnBoot.cdc.build.cdc_on_boot=1 -esp32c3.menu.UploadMode.default=UART0 -esp32c3.menu.UploadMode.default.upload.use_1200bps_touch=false -esp32c3.menu.UploadMode.default.upload.wait_for_upload_port=false -esp32c3.menu.UploadMode.cdc=Internal USB -esp32c3.menu.UploadMode.cdc.upload.use_1200bps_touch=true -esp32c3.menu.UploadMode.cdc.upload.wait_for_upload_port=true - esp32c3.menu.PartitionScheme.default=Default 4MB with spiffs (1.2MB APP/1.5MB SPIFFS) esp32c3.menu.PartitionScheme.default.build.partitions=default esp32c3.menu.PartitionScheme.defaultffat=Default 4MB with ffat (1.2MB APP/1.5MB FATFS) @@ -2071,6 +2064,122 @@ ttgo-t7-v14-mini32.menu.DebugLevel.verbose.build.code_debug=5 ############################################################## +ttgo-t-oi-plus.name=TTGO T-OI PLUS RISC-V ESP32-C3 + +ttgo-t-oi-plus.upload.tool=esptool_py +ttgo-t-oi-plus.upload.maximum_size=1310720 +ttgo-t-oi-plus.upload.maximum_data_size=327680 +ttgo-t-oi-plus.upload.flags= +ttgo-t-oi-plus.upload.extra_flags= + +ttgo-t-oi-plus.serial.disableDTR=false +ttgo-t-oi-plus.serial.disableRTS=false + +ttgo-t-oi-plus.build.tarch=riscv32 +ttgo-t-oi-plus.build.target=esp +ttgo-t-oi-plus.build.mcu=esp32c3 +ttgo-t-oi-plus.build.core=esp32 +ttgo-t-oi-plus.build.variant=ttgo-t-oi-plus +ttgo-t-oi-plus.build.board=TTGO-T-OI-PLUS_DEV +ttgo-t-oi-plus.build.bootloader_addr=0x0 + +ttgo-t-oi-plus.build.cdc_on_boot=0 +ttgo-t-oi-plus.build.f_cpu=160000000L +ttgo-t-oi-plus.build.flash_size=4MB +ttgo-t-oi-plus.build.flash_freq=80m +ttgo-t-oi-plus.build.flash_mode=qio +ttgo-t-oi-plus.build.boot=qio +ttgo-t-oi-plus.build.partitions=default +ttgo-t-oi-plus.build.defines= + +ttgo-t-oi-plus.menu.PartitionScheme.default=Default 4MB with spiffs (1.2MB APP/1.5MB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.default.build.partitions=default +ttgo-t-oi-plus.menu.PartitionScheme.defaultffat=Default 4MB with ffat (1.2MB APP/1.5MB FATFS) +ttgo-t-oi-plus.menu.PartitionScheme.defaultffat.build.partitions=default_ffat +ttgo-t-oi-plus.menu.PartitionScheme.minimal=Minimal (1.3MB APP/700KB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.minimal.build.partitions=minimal +ttgo-t-oi-plus.menu.PartitionScheme.no_ota=No OTA (2MB APP/2MB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.no_ota.build.partitions=no_ota +ttgo-t-oi-plus.menu.PartitionScheme.no_ota.upload.maximum_size=2097152 +ttgo-t-oi-plus.menu.PartitionScheme.noota_3g=No OTA (1MB APP/3MB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.noota_3g.build.partitions=noota_3g +ttgo-t-oi-plus.menu.PartitionScheme.noota_3g.upload.maximum_size=1048576 +ttgo-t-oi-plus.menu.PartitionScheme.noota_ffat=No OTA (2MB APP/2MB FATFS) +ttgo-t-oi-plus.menu.PartitionScheme.noota_ffat.build.partitions=noota_ffat +ttgo-t-oi-plus.menu.PartitionScheme.noota_ffat.upload.maximum_size=2097152 +ttgo-t-oi-plus.menu.PartitionScheme.noota_3gffat=No OTA (1MB APP/3MB FATFS) +ttgo-t-oi-plus.menu.PartitionScheme.noota_3gffat.build.partitions=noota_3gffat +ttgo-t-oi-plus.menu.PartitionScheme.noota_3gffat.upload.maximum_size=1048576 +ttgo-t-oi-plus.menu.PartitionScheme.huge_app=Huge APP (3MB No OTA/1MB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.huge_app.build.partitions=huge_app +ttgo-t-oi-plus.menu.PartitionScheme.huge_app.upload.maximum_size=3145728 +ttgo-t-oi-plus.menu.PartitionScheme.min_spiffs=Minimal SPIFFS (1.9MB APP with OTA/190KB SPIFFS) +ttgo-t-oi-plus.menu.PartitionScheme.min_spiffs.build.partitions=min_spiffs +ttgo-t-oi-plus.menu.PartitionScheme.min_spiffs.upload.maximum_size=1966080 + + +ttgo-t-oi-plus.menu.CPUFreq.160=160MHz (WiFi) +ttgo-t-oi-plus.menu.CPUFreq.160.build.f_cpu=160000000L +ttgo-t-oi-plus.menu.CPUFreq.80=80MHz (WiFi) +ttgo-t-oi-plus.menu.CPUFreq.80.build.f_cpu=80000000L +ttgo-t-oi-plus.menu.CPUFreq.40=40MHz +ttgo-t-oi-plus.menu.CPUFreq.40.build.f_cpu=40000000L +ttgo-t-oi-plus.menu.CPUFreq.20=20MHz +ttgo-t-oi-plus.menu.CPUFreq.20.build.f_cpu=20000000L +ttgo-t-oi-plus.menu.CPUFreq.10=10MHz +ttgo-t-oi-plus.menu.CPUFreq.10.build.f_cpu=10000000L + +ttgo-t-oi-plus.menu.FlashMode.qio=QIO +ttgo-t-oi-plus.menu.FlashMode.qio.build.flash_mode=dio +ttgo-t-oi-plus.menu.FlashMode.qio.build.boot=qio +ttgo-t-oi-plus.menu.FlashMode.dio=DIO +ttgo-t-oi-plus.menu.FlashMode.dio.build.flash_mode=dio +ttgo-t-oi-plus.menu.FlashMode.dio.build.boot=dio +ttgo-t-oi-plus.menu.FlashMode.qout=QOUT +ttgo-t-oi-plus.menu.FlashMode.qout.build.flash_mode=dout +ttgo-t-oi-plus.menu.FlashMode.qout.build.boot=qout +ttgo-t-oi-plus.menu.FlashMode.dout=DOUT +ttgo-t-oi-plus.menu.FlashMode.dout.build.flash_mode=dout +ttgo-t-oi-plus.menu.FlashMode.dout.build.boot=dout + +ttgo-t-oi-plus.menu.FlashFreq.80=80MHz +ttgo-t-oi-plus.menu.FlashFreq.80.build.flash_freq=80m +ttgo-t-oi-plus.menu.FlashFreq.40=40MHz +ttgo-t-oi-plus.menu.FlashFreq.40.build.flash_freq=40m + +ttgo-t-oi-plus.menu.FlashSize.4M=4MB (32Mb) +ttgo-t-oi-plus.menu.FlashSize.4M.build.flash_size=4MB + +ttgo-t-oi-plus.menu.UploadSpeed.921600=921600 +ttgo-t-oi-plus.menu.UploadSpeed.921600.upload.speed=921600 +ttgo-t-oi-plus.menu.UploadSpeed.115200=115200 +ttgo-t-oi-plus.menu.UploadSpeed.115200.upload.speed=115200 +ttgo-t-oi-plus.menu.UploadSpeed.256000.windows=256000 +ttgo-t-oi-plus.menu.UploadSpeed.256000.upload.speed=256000 +ttgo-t-oi-plus.menu.UploadSpeed.230400.windows.upload.speed=256000 +ttgo-t-oi-plus.menu.UploadSpeed.230400=230400 +ttgo-t-oi-plus.menu.UploadSpeed.230400.upload.speed=230400 +ttgo-t-oi-plus.menu.UploadSpeed.460800.linux=460800 +ttgo-t-oi-plus.menu.UploadSpeed.460800.macosx=460800 +ttgo-t-oi-plus.menu.UploadSpeed.460800.upload.speed=460800 +ttgo-t-oi-plus.menu.UploadSpeed.512000.windows=512000 +ttgo-t-oi-plus.menu.UploadSpeed.512000.upload.speed=512000 + +ttgo-t-oi-plus.menu.DebugLevel.none=None +ttgo-t-oi-plus.menu.DebugLevel.none.build.code_debug=0 +ttgo-t-oi-plus.menu.DebugLevel.error=Error +ttgo-t-oi-plus.menu.DebugLevel.error.build.code_debug=1 +ttgo-t-oi-plus.menu.DebugLevel.warn=Warn +ttgo-t-oi-plus.menu.DebugLevel.warn.build.code_debug=2 +ttgo-t-oi-plus.menu.DebugLevel.info=Info +ttgo-t-oi-plus.menu.DebugLevel.info.build.code_debug=3 +ttgo-t-oi-plus.menu.DebugLevel.debug=Debug +ttgo-t-oi-plus.menu.DebugLevel.debug.build.code_debug=4 +ttgo-t-oi-plus.menu.DebugLevel.verbose=Verbose +ttgo-t-oi-plus.menu.DebugLevel.verbose.build.code_debug=5 + +############################################################## + cw02.name=XinaBox CW02 cw02.upload.tool=esptool_py @@ -3801,6 +3910,13 @@ adafruit_metro_esp32s2.menu.DFUOnBoot.default.build.dfu_on_boot=0 adafruit_metro_esp32s2.menu.DFUOnBoot.dfu=Enabled adafruit_metro_esp32s2.menu.DFUOnBoot.dfu.build.dfu_on_boot=1 +adafruit_metro_esp32s2.menu.UploadMode.cdc=Internal USB +adafruit_metro_esp32s2.menu.UploadMode.cdc.upload.use_1200bps_touch=true +adafruit_metro_esp32s2.menu.UploadMode.cdc.upload.wait_for_upload_port=true +adafruit_metro_esp32s2.menu.UploadMode.default=UART0 +adafruit_metro_esp32s2.menu.UploadMode.default.upload.use_1200bps_touch=false +adafruit_metro_esp32s2.menu.UploadMode.default.upload.wait_for_upload_port=false + adafruit_metro_esp32s2.menu.PSRAM.enabled=Enabled adafruit_metro_esp32s2.menu.PSRAM.enabled.build.defines=-DBOARD_HAS_PSRAM adafruit_metro_esp32s2.menu.PSRAM.disabled=Disabled @@ -3915,11 +4031,11 @@ adafruit_metro_esp32s2.menu.DebugLevel.verbose.build.code_debug=5 adafruit_magtag29_esp32s2.name=Adafruit MagTag 2.9" adafruit_magtag29_esp32s2.vid.0=0x239A -adafruit_magtag29_esp32s2.pid.0=0x80DF +adafruit_magtag29_esp32s2.pid.0=0x80E5 adafruit_magtag29_esp32s2.vid.1=0x239A -adafruit_magtag29_esp32s2.pid.1=0x00DF +adafruit_magtag29_esp32s2.pid.1=0x00E5 adafruit_magtag29_esp32s2.vid.1=0x239A -adafruit_magtag29_esp32s2.pid.1=0x80E0 +adafruit_magtag29_esp32s2.pid.1=0x80E6 adafruit_magtag29_esp32s2.upload.tool=esptool_py adafruit_magtag29_esp32s2.upload.maximum_size=1310720 @@ -3966,6 +4082,13 @@ adafruit_magtag29_esp32s2.menu.DFUOnBoot.default.build.dfu_on_boot=0 adafruit_magtag29_esp32s2.menu.DFUOnBoot.dfu=Enabled adafruit_magtag29_esp32s2.menu.DFUOnBoot.dfu.build.dfu_on_boot=1 +adafruit_magtag29_esp32s2.menu.UploadMode.cdc=Internal USB +adafruit_magtag29_esp32s2.menu.UploadMode.cdc.upload.use_1200bps_touch=true +adafruit_magtag29_esp32s2.menu.UploadMode.cdc.upload.wait_for_upload_port=true +adafruit_magtag29_esp32s2.menu.UploadMode.default=UART0 +adafruit_magtag29_esp32s2.menu.UploadMode.default.upload.use_1200bps_touch=false +adafruit_magtag29_esp32s2.menu.UploadMode.default.upload.wait_for_upload_port=false + adafruit_magtag29_esp32s2.menu.PSRAM.enabled=Enabled adafruit_magtag29_esp32s2.menu.PSRAM.enabled.build.defines=-DBOARD_HAS_PSRAM adafruit_magtag29_esp32s2.menu.PSRAM.disabled=Disabled @@ -4131,6 +4254,13 @@ adafruit_funhouse_esp32s2.menu.DFUOnBoot.default.build.dfu_on_boot=0 adafruit_funhouse_esp32s2.menu.DFUOnBoot.dfu=Enabled adafruit_funhouse_esp32s2.menu.DFUOnBoot.dfu.build.dfu_on_boot=1 +adafruit_funhouse_esp32s2.menu.UploadMode.cdc=Internal USB +adafruit_funhouse_esp32s2.menu.UploadMode.cdc.upload.use_1200bps_touch=true +adafruit_funhouse_esp32s2.menu.UploadMode.cdc.upload.wait_for_upload_port=true +adafruit_funhouse_esp32s2.menu.UploadMode.default=UART0 +adafruit_funhouse_esp32s2.menu.UploadMode.default.upload.use_1200bps_touch=false +adafruit_funhouse_esp32s2.menu.UploadMode.default.upload.wait_for_upload_port=false + adafruit_funhouse_esp32s2.menu.PSRAM.enabled=Enabled adafruit_funhouse_esp32s2.menu.PSRAM.enabled.build.defines=-DBOARD_HAS_PSRAM adafruit_funhouse_esp32s2.menu.PSRAM.disabled=Disabled @@ -9386,19 +9516,32 @@ atmegazero_esp32s2.build.core=esp32 atmegazero_esp32s2.build.variant=atmegazero_esp32s2 atmegazero_esp32s2.build.board=atmegazero_esp32s2 +atmegazero_esp32s2.build.cdc_on_boot=1 +atmegazero_esp32s2.build.msc_on_boot=0 +atmegazero_esp32s2.build.dfu_on_boot=0 atmegazero_esp32s2.build.serial=0 atmegazero_esp32s2.build.f_cpu=240000000L -atmegazero_esp32s2.build.flash_size=4MB -atmegazero_esp32s2.build.flash_freq=80m +atmegazero_esp32s2.build.flash_size=16MB +atmegazero_esp32s2.build.flash_freq=40m atmegazero_esp32s2.build.flash_mode=qio atmegazero_esp32s2.build.boot=qio atmegazero_esp32s2.build.partitions=default atmegazero_esp32s2.build.defines= -atmegazero_esp32s2.menu.SerialMode.cdc=USB CDC -atmegazero_esp32s2.menu.SerialMode.cdc.build.serial=1 -atmegazero_esp32s2.menu.SerialMode.default=UART0 -atmegazero_esp32s2.menu.SerialMode.default.build.serial=0 +atmegazero_esp32s2.menu.CDCOnBoot.cdc=Enabled +atmegazero_esp32s2.menu.CDCOnBoot.cdc.build.cdc_on_boot=1 +atmegazero_esp32s2.menu.CDCOnBoot.default=Disabled +atmegazero_esp32s2.menu.CDCOnBoot.default.build.cdc_on_boot=0 + +atmegazero_esp32s2.menu.MSCOnBoot.default=Disabled +atmegazero_esp32s2.menu.MSCOnBoot.default.build.msc_on_boot=0 +atmegazero_esp32s2.menu.MSCOnBoot.msc=Enabled +atmegazero_esp32s2.menu.MSCOnBoot.msc.build.msc_on_boot=1 + +atmegazero_esp32s2.menu.DFUOnBoot.default=Disabled +atmegazero_esp32s2.menu.DFUOnBoot.default.build.dfu_on_boot=0 +atmegazero_esp32s2.menu.DFUOnBoot.dfu=Enabled +atmegazero_esp32s2.menu.DFUOnBoot.dfu.build.dfu_on_boot=1 atmegazero_esp32s2.menu.PSRAM.disabled=Disabled atmegazero_esp32s2.menu.PSRAM.disabled.build.defines= diff --git a/cores/esp32/Esp.cpp b/cores/esp32/Esp.cpp index a61fb7d5552..21f86b01565 100644 --- a/cores/esp32/Esp.cpp +++ b/cores/esp32/Esp.cpp @@ -38,6 +38,7 @@ extern "C" { #define ESP_FLASH_IMAGE_BASE 0x1000 // Flash offset containing flash size and spi mode #elif CONFIG_IDF_TARGET_ESP32S2 #include "esp32s2/rom/spi_flash.h" +#include "soc/efuse_reg.h" #define ESP_FLASH_IMAGE_BASE 0x1000 #elif CONFIG_IDF_TARGET_ESP32C3 #include "esp32c3/rom/spi_flash.h" @@ -274,7 +275,17 @@ const char * EspClass::getChipModel(void) return "Unknown"; } #elif CONFIG_IDF_TARGET_ESP32S2 - return "ESP32-S2"; + uint32_t pkg_ver = REG_GET_FIELD(EFUSE_RD_MAC_SPI_SYS_3_REG, EFUSE_PKG_VERSION); + switch (pkg_ver) { + case 0: + return "ESP32-S2"; + case 1: + return "ESP32-S2FH16"; + case 2: + return "ESP32-S2FH32"; + default: + return "ESP32-S2 (Unknown)"; + } #elif CONFIG_IDF_TARGET_ESP32S3 return "ESP32-S3"; #elif CONFIG_IDF_TARGET_ESP32C3 diff --git a/cores/esp32/HWCDC.cpp b/cores/esp32/HWCDC.cpp index 5f79f633f6d..3f6927dda27 100644 --- a/cores/esp32/HWCDC.cpp +++ b/cores/esp32/HWCDC.cpp @@ -24,15 +24,47 @@ #include "soc/periph_defs.h" #include "hal/usb_serial_jtag_ll.h" +ESP_EVENT_DEFINE_BASE(ARDUINO_HW_CDC_EVENTS); + static RingbufHandle_t tx_ring_buf = NULL; static xQueueHandle rx_queue = NULL; static uint8_t rx_data_buf[64]; static intr_handle_t intr_handle = NULL; static volatile bool initial_empty = false; +static xSemaphoreHandle tx_lock = NULL; +static uint32_t tx_timeout_ms = 200; +static esp_event_loop_handle_t arduino_hw_cdc_event_loop_handle = NULL; + +static esp_err_t arduino_hw_cdc_event_post(esp_event_base_t event_base, int32_t event_id, void *event_data, size_t event_data_size, BaseType_t *task_unblocked){ + if(arduino_hw_cdc_event_loop_handle == NULL){ + return ESP_FAIL; + } + return esp_event_isr_post_to(arduino_hw_cdc_event_loop_handle, event_base, event_id, event_data, event_data_size, task_unblocked); +} + +static esp_err_t arduino_hw_cdc_event_handler_register_with(esp_event_base_t event_base, int32_t event_id, esp_event_handler_t event_handler, void *event_handler_arg){ + if (!arduino_hw_cdc_event_loop_handle) { + esp_event_loop_args_t event_task_args = { + .queue_size = 5, + .task_name = "arduino_hw_cdc_events", + .task_priority = 5, + .task_stack_size = 2048, + .task_core_id = tskNO_AFFINITY + }; + if (esp_event_loop_create(&event_task_args, &arduino_hw_cdc_event_loop_handle) != ESP_OK) { + log_e("esp_event_loop_create failed"); + } + } + if(arduino_hw_cdc_event_loop_handle == NULL){ + return ESP_FAIL; + } + return esp_event_handler_register_with(arduino_hw_cdc_event_loop_handle, event_base, event_id, event_handler, event_handler_arg); +} static void hw_cdc_isr_handler(void *arg) { portBASE_TYPE xTaskWoken = 0; uint32_t usbjtag_intr_status = 0; + arduino_hw_cdc_event_data_t event = {0}; usbjtag_intr_status = usb_serial_jtag_ll_get_intsts_mask(); if (usbjtag_intr_status & USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY) { @@ -45,6 +77,7 @@ static void hw_cdc_isr_handler(void *arg) { initial_empty = true; //send event? //ets_printf("CONNECTED\n"); + arduino_hw_cdc_event_post(ARDUINO_HW_CDC_EVENTS, ARDUINO_HW_CDC_CONNECTED_EVENT, &event, sizeof(arduino_hw_cdc_event_data_t), &xTaskWoken); } size_t queued_size; uint8_t *queued_buff = (uint8_t *)xRingbufferReceiveUpToFromISR(tx_ring_buf, &queued_size, 64); @@ -58,6 +91,8 @@ static void hw_cdc_isr_handler(void *arg) { usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); //send event? //ets_printf("TX:%u\n", queued_size); + event.tx.len = queued_size; + arduino_hw_cdc_event_post(ARDUINO_HW_CDC_EVENTS, ARDUINO_HW_CDC_TX_EVENT, &event, sizeof(arduino_hw_cdc_event_data_t), &xTaskWoken); } } else { usb_serial_jtag_ll_clr_intsts_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); @@ -77,6 +112,8 @@ static void hw_cdc_isr_handler(void *arg) { } //send event? //ets_printf("RX:%u/%u\n", i, rx_fifo_len); + event.rx.len = i; + arduino_hw_cdc_event_post(ARDUINO_HW_CDC_EVENTS, ARDUINO_HW_CDC_RX_EVENT, &event, sizeof(arduino_hw_cdc_event_data_t), &xTaskWoken); } if (usbjtag_intr_status & USB_SERIAL_JTAG_INTR_BUS_RESET) { @@ -84,6 +121,7 @@ static void hw_cdc_isr_handler(void *arg) { initial_empty = false; usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); //ets_printf("BUS_RESET\n"); + arduino_hw_cdc_event_post(ARDUINO_HW_CDC_EVENTS, ARDUINO_HW_CDC_BUS_RESET_EVENT, &event, sizeof(arduino_hw_cdc_event_data_t), &xTaskWoken); } if (xTaskWoken == pdTRUE) { @@ -95,13 +133,13 @@ static void ARDUINO_ISR_ATTR cdc0_write_char(char c) { if(xPortInIsrContext()){ xRingbufferSendFromISR(tx_ring_buf, (void*) (&c), 1, NULL); } else { - xRingbufferSend(tx_ring_buf, (void*) (&c), 1, 0); + xRingbufferSend(tx_ring_buf, (void*) (&c), 1, tx_timeout_ms / portTICK_PERIOD_MS); } usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); } HWCDC::HWCDC() { - + } HWCDC::~HWCDC(){ @@ -113,8 +151,19 @@ HWCDC::operator bool() const return initial_empty; } +void HWCDC::onEvent(esp_event_handler_t callback){ + onEvent(ARDUINO_HW_CDC_ANY_EVENT, callback); +} + +void HWCDC::onEvent(arduino_hw_cdc_event_t event, esp_event_handler_t callback){ + arduino_hw_cdc_event_handler_register_with(ARDUINO_HW_CDC_EVENTS, event, callback, this); +} + void HWCDC::begin(unsigned long baud) { + if(tx_lock == NULL) { + tx_lock = xSemaphoreCreateMutex(); + } setRxBufferSize(256);//default if not preset setTxBufferSize(256);//default if not preset @@ -123,6 +172,7 @@ void HWCDC::begin(unsigned long baud) if(!intr_handle && esp_intr_alloc(ETS_USB_SERIAL_JTAG_INTR_SOURCE, 0, hw_cdc_isr_handler, NULL, &intr_handle) != ESP_OK){ isr_log_e("HW USB CDC failed to init interrupts"); end(); + return; } } @@ -132,8 +182,19 @@ void HWCDC::end() usb_serial_jtag_ll_disable_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY | USB_SERIAL_JTAG_INTR_SERIAL_OUT_RECV_PKT | USB_SERIAL_JTAG_INTR_BUS_RESET); esp_intr_free(intr_handle); intr_handle = NULL; + if(tx_lock != NULL) { + vSemaphoreDelete(tx_lock); + } setRxBufferSize(0); setTxBufferSize(0); + if (arduino_hw_cdc_event_loop_handle) { + esp_event_loop_delete(arduino_hw_cdc_event_loop_handle); + arduino_hw_cdc_event_loop_handle = NULL; + } +} + +void HWCDC::setTxTimeoutMs(uint32_t timeout){ + tx_timeout_ms = timeout; } /* @@ -157,21 +218,57 @@ size_t HWCDC::setTxBufferSize(size_t tx_queue_len){ int HWCDC::availableForWrite(void) { - if(tx_ring_buf == NULL){ - return -1; + if(tx_ring_buf == NULL || tx_lock == NULL){ + return 0; + } + if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ + return 0; } - return xRingbufferGetCurFreeSize(tx_ring_buf); + size_t a = xRingbufferGetCurFreeSize(tx_ring_buf); + xSemaphoreGive(tx_lock); + return a; } size_t HWCDC::write(const uint8_t *buffer, size_t size) { - // Blocking method, Sending data to ringbuffer, and handle the data in ISR. - if(xRingbufferSend(tx_ring_buf, (void*) (buffer), size, 200 / portTICK_PERIOD_MS) != pdTRUE){ - log_e("Write Failed"); + if(buffer == NULL || size == 0 || tx_ring_buf == NULL || tx_lock == NULL){ return 0; } - // Now trigger the ISR to read data from the ring buffer. - usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); + if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ + return 0; + } + size_t max_size = xRingbufferGetMaxItemSize(tx_ring_buf); + size_t space = xRingbufferGetCurFreeSize(tx_ring_buf); + size_t to_send = size, so_far = 0; + + if(space > size){ + space = size; + } + // Non-Blocking method, Sending data to ringbuffer, and handle the data in ISR. + if(xRingbufferSend(tx_ring_buf, (void*) (buffer), space, 0) != pdTRUE){ + size = 0; + } else { + to_send -= space; + so_far += space; + // Now trigger the ISR to read data from the ring buffer. + usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); + + while(to_send){ + if(max_size > to_send){ + max_size = to_send; + } + // Blocking method, Sending data to ringbuffer, and handle the data in ISR. + if(xRingbufferSend(tx_ring_buf, (void*) (buffer+so_far), max_size, tx_timeout_ms / portTICK_PERIOD_MS) != pdTRUE){ + size = so_far; + break; + } + so_far += max_size; + to_send -= max_size; + // Now trigger the ISR to read data from the ring buffer. + usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); + } + } + xSemaphoreGive(tx_lock); return size; } @@ -182,15 +279,23 @@ size_t HWCDC::write(uint8_t c) void HWCDC::flush(void) { - if(tx_ring_buf == NULL){ + if(tx_ring_buf == NULL || tx_lock == NULL){ + return; + } + if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ return; } UBaseType_t uxItemsWaiting = 0; vRingbufferGetInfo(tx_ring_buf, NULL, NULL, NULL, NULL, &uxItemsWaiting); + if(uxItemsWaiting){ + // Now trigger the ISR to read data from the ring buffer. + usb_serial_jtag_ll_ena_intr_mask(USB_SERIAL_JTAG_INTR_SERIAL_IN_EMPTY); + } while(uxItemsWaiting){ delay(5); vRingbufferGetInfo(tx_ring_buf, NULL, NULL, NULL, NULL, &uxItemsWaiting); } + xSemaphoreGive(tx_lock); } /* diff --git a/cores/esp32/HWCDC.h b/cores/esp32/HWCDC.h index 6551425d57f..81a334b76b9 100644 --- a/cores/esp32/HWCDC.h +++ b/cores/esp32/HWCDC.h @@ -17,16 +17,41 @@ #if CONFIG_IDF_TARGET_ESP32C3 #include +#include "esp_event.h" #include "Stream.h" +ESP_EVENT_DECLARE_BASE(ARDUINO_HW_CDC_EVENTS); + +typedef enum { + ARDUINO_HW_CDC_ANY_EVENT = ESP_EVENT_ANY_ID, + ARDUINO_HW_CDC_CONNECTED_EVENT = 0, + ARDUINO_HW_CDC_BUS_RESET_EVENT, + ARDUINO_HW_CDC_RX_EVENT, + ARDUINO_HW_CDC_TX_EVENT, + ARDUINO_HW_CDC_MAX_EVENT, +} arduino_hw_cdc_event_t; + +typedef union { + struct { + size_t len; + } rx; + struct { + size_t len; + } tx; +} arduino_hw_cdc_event_data_t; + class HWCDC: public Stream { public: HWCDC(); ~HWCDC(); + void onEvent(esp_event_handler_t callback); + void onEvent(arduino_hw_cdc_event_t event, esp_event_handler_t callback); + size_t setRxBufferSize(size_t); size_t setTxBufferSize(size_t); + void setTxTimeoutMs(uint32_t timeout); void begin(unsigned long baud=0); void end(); diff --git a/cores/esp32/HardwareSerial.cpp b/cores/esp32/HardwareSerial.cpp index 064aef6fb8c..aed14b19c72 100644 --- a/cores/esp32/HardwareSerial.cpp +++ b/cores/esp32/HardwareSerial.cpp @@ -87,7 +87,6 @@ HardwareSerial Serial1(1); #if SOC_UART_NUM > 2 HardwareSerial Serial2(2); #endif -#endif void serialEventRun(void) { @@ -105,6 +104,7 @@ void serialEventRun(void) if(Serial2.available()) serialEvent2(); #endif } +#endif HardwareSerial::HardwareSerial(int uart_nr) : _uart_nr(uart_nr), _uart(NULL), _rxBufferSize(256) {} diff --git a/cores/esp32/USB.cpp b/cores/esp32/USB.cpp index e095c8603a5..5bf78b3bc27 100644 --- a/cores/esp32/USB.cpp +++ b/cores/esp32/USB.cpp @@ -15,6 +15,7 @@ #if CONFIG_TINYUSB_ENABLED +#include "pins_arduino.h" #include "esp32-hal.h" #include "esp32-hal-tinyusb.h" #include "common/tusb_common.h" diff --git a/cores/esp32/USBCDC.cpp b/cores/esp32/USBCDC.cpp index e39b5f1eba4..a7b75eada4f 100644 --- a/cores/esp32/USBCDC.cpp +++ b/cores/esp32/USBCDC.cpp @@ -62,63 +62,40 @@ void tud_cdc_rx_cb(uint8_t itf) // Invoked when received send break void tud_cdc_send_break_cb(uint8_t itf, uint16_t duration_ms){ - //isr_log_v("itf: %u, duration_ms: %u", itf, duration_ms); + //log_v("itf: %u, duration_ms: %u", itf, duration_ms); } // Invoked when space becomes available in TX buffer void tud_cdc_tx_complete_cb(uint8_t itf){ - if(itf < MAX_USB_CDC_DEVICES && devices[itf] != NULL && devices[itf]->tx_sem != NULL){ - xSemaphoreGive(devices[itf]->tx_sem); + if(itf < MAX_USB_CDC_DEVICES && devices[itf] != NULL){ devices[itf]->_onTX(); } } -static size_t tinyusb_cdc_write(uint8_t itf, const uint8_t *buffer, size_t size){ - if(itf >= MAX_USB_CDC_DEVICES || devices[itf] == NULL || devices[itf]->tx_sem == NULL){ - return 0; +static void ARDUINO_ISR_ATTR cdc0_write_char(char c){ + if(devices[0] != NULL){ + devices[0]->write(c); } - if(!tud_cdc_n_connected(itf)){ - return 0; - } - size_t tosend = size, sofar = 0; - while(tosend){ - uint32_t space = tud_cdc_n_write_available(itf); - if(!space){ - //make sure that we do not get previous semaphore - xSemaphoreTake(devices[itf]->tx_sem, 0); - //wait for tx_complete - if(xSemaphoreTake(devices[itf]->tx_sem, 200 / portTICK_PERIOD_MS) == pdTRUE){ - space = tud_cdc_n_write_available(itf); - } - if(!space){ - return sofar; - } - } - if(tosend < space){ - space = tosend; - } - uint32_t sent = tud_cdc_n_write(itf, buffer + sofar, space); - if(!sent){ - return sofar; - } - sofar += sent; - tosend -= sent; - tud_cdc_n_write_flush(itf); - //xSemaphoreTake(devices[itf]->tx_sem, portMAX_DELAY); - } - return sofar; -} - -static void ARDUINO_ISR_ATTR cdc0_write_char(char c) -{ - tinyusb_cdc_write(0, (const uint8_t *)&c, 1); } static void usb_unplugged_cb(void* arg, esp_event_base_t event_base, int32_t event_id, void* event_data){ ((USBCDC*)arg)->_onUnplugged(); } -USBCDC::USBCDC(uint8_t itfn) : tx_sem(NULL), itf(itfn), bit_rate(0), stop_bits(0), parity(0), data_bits(0), dtr(false), rts(false), connected(false), reboot_enable(true), rx_queue(NULL) { +USBCDC::USBCDC(uint8_t itfn) +: itf(itfn) +, bit_rate(0) +, stop_bits(0) +, parity(0) +, data_bits(0) +, dtr(false) +, rts(false) +, connected(false) +, reboot_enable(true) +, rx_queue(NULL) +, tx_lock(NULL) +, tx_timeout_ms(250) +{ tinyusb_enable_interface(USB_INTERFACE_CDC, TUD_CDC_DESC_LEN, load_cdc_descriptor); if(itf < MAX_USB_CDC_DEVICES){ arduino_usb_event_handler_register_with(ARDUINO_USB_EVENTS, ARDUINO_USB_STOPPED_EVENT, usb_unplugged_cb, this); @@ -153,9 +130,8 @@ size_t USBCDC::setRxBufferSize(size_t rx_queue_len){ void USBCDC::begin(unsigned long baud) { - if(tx_sem == NULL){ - tx_sem = xSemaphoreCreateBinary(); - xSemaphoreTake(tx_sem, 0); + if(tx_lock == NULL) { + tx_lock = xSemaphoreCreateMutex(); } setRxBufferSize(256);//default if not preset devices[itf] = this; @@ -166,12 +142,15 @@ void USBCDC::end() connected = false; devices[itf] = NULL; setRxBufferSize(0); - if (tx_sem != NULL) { - vSemaphoreDelete(tx_sem); - tx_sem = NULL; + if(tx_lock != NULL) { + vSemaphoreDelete(tx_lock); } } +void USBCDC::setTxTimeoutMs(uint32_t timeout){ + tx_timeout_ms = timeout; +} + void USBCDC::_onUnplugged(void){ if(connected){ connected = false; @@ -336,23 +315,73 @@ size_t USBCDC::read(uint8_t *buffer, size_t size) void USBCDC::flush(void) { - if(itf >= MAX_USB_CDC_DEVICES || tx_sem == NULL){ + if(itf >= MAX_USB_CDC_DEVICES || tx_lock == NULL || !tud_cdc_n_connected(itf)){ + return; + } + if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ return; } tud_cdc_n_write_flush(itf); + xSemaphoreGive(tx_lock); } int USBCDC::availableForWrite(void) { - if(itf >= MAX_USB_CDC_DEVICES || tx_sem == NULL){ - return -1; + if(itf >= MAX_USB_CDC_DEVICES || tx_lock == NULL || !tud_cdc_n_connected(itf)){ + return 0; } - return tud_cdc_n_write_available(itf); + if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ + return 0; + } + size_t a = tud_cdc_n_write_available(itf); + xSemaphoreGive(tx_lock); + return a; } size_t USBCDC::write(const uint8_t *buffer, size_t size) { - return tinyusb_cdc_write(itf, buffer, size); + if(itf >= MAX_USB_CDC_DEVICES || tx_lock == NULL || buffer == NULL || size == 0 || !tud_cdc_n_connected(itf)){ + return 0; + } + if(xPortInIsrContext()){ + BaseType_t taskWoken = false; + if(xSemaphoreTakeFromISR(tx_lock, &taskWoken) != pdPASS){ + return 0; + } + } else if(xSemaphoreTake(tx_lock, tx_timeout_ms / portTICK_PERIOD_MS) != pdPASS){ + return 0; + } + size_t to_send = size, so_far = 0; + while(to_send){ + if(!tud_cdc_n_connected(itf)){ + size = so_far; + break; + } + size_t space = tud_cdc_n_write_available(itf); + if(!space){ + tud_cdc_n_write_flush(itf); + continue; + } + if(space > to_send){ + space = to_send; + } + size_t sent = tud_cdc_n_write(itf, buffer+so_far, space); + if(sent){ + so_far += sent; + to_send -= sent; + tud_cdc_n_write_flush(itf); + } else { + size = so_far; + break; + } + } + if(xPortInIsrContext()){ + BaseType_t taskWoken = false; + xSemaphoreGiveFromISR(tx_lock, &taskWoken); + } else { + xSemaphoreGive(tx_lock); + } + return size; } size_t USBCDC::write(uint8_t c) diff --git a/cores/esp32/USBCDC.h b/cores/esp32/USBCDC.h index ced588f45f2..3dfe7d9e69c 100644 --- a/cores/esp32/USBCDC.h +++ b/cores/esp32/USBCDC.h @@ -18,6 +18,9 @@ #include #include "esp_event.h" +#include "freertos/FreeRTOS.h" +#include "freertos/queue.h" +#include "freertos/semphr.h" #include "Stream.h" ESP_EVENT_DECLARE_BASE(ARDUINO_USB_CDC_EVENTS); @@ -58,7 +61,8 @@ class USBCDC: public Stream void onEvent(esp_event_handler_t callback); void onEvent(arduino_usb_cdc_event_t event, esp_event_handler_t callback); - size_t setRxBufferSize(size_t); + size_t setRxBufferSize(size_t size); + void setTxTimeoutMs(uint32_t timeout); void begin(unsigned long baud=0); void end(); @@ -113,7 +117,6 @@ class USBCDC: public Stream void _onRX(void); void _onTX(void); void _onUnplugged(void); - xSemaphoreHandle tx_sem; protected: uint8_t itf; @@ -126,6 +129,8 @@ class USBCDC: public Stream bool connected; bool reboot_enable; xQueueHandle rx_queue; + xSemaphoreHandle tx_lock; + uint32_t tx_timeout_ms; }; diff --git a/cores/esp32/esp32-hal-adc.c b/cores/esp32/esp32-hal-adc.c index 0530f1d84fb..9387ec69018 100644 --- a/cores/esp32/esp32-hal-adc.c +++ b/cores/esp32/esp32-hal-adc.c @@ -37,7 +37,7 @@ static uint8_t __analogVRefPin = 0; #include "soc/rtc_io_reg.h" #elif CONFIG_IDF_TARGET_ESP32C3 #include "esp32c3/rom/ets_sys.h" -#else +#else #error Target CONFIG_IDF_TARGET is not supported #endif #else // ESP32 Before IDF 4.0 @@ -46,7 +46,11 @@ static uint8_t __analogVRefPin = 0; #endif static uint8_t __analogAttenuation = 3;//11db -static uint8_t __analogWidth = 3;//12 bits +#if CONFIG_IDF_TARGET_ESP32S2 +static uint8_t __analogWidth = 4; // 13 bits +#else +static uint8_t __analogWidth = 3; // 12 bits +#endif static uint8_t __analogClockDiv = 1; static adc_attenuation_t __pin_attenuation[SOC_GPIO_PIN_COUNT]; diff --git a/cores/esp32/esp32-hal-i2c.c b/cores/esp32/esp32-hal-i2c.c index 1e03627feaa..18ef4c115e7 100644 --- a/cores/esp32/esp32-hal-i2c.c +++ b/cores/esp32/esp32-hal-i2c.c @@ -14,1915 +14,324 @@ #include "esp32-hal-i2c.h" #include "esp32-hal.h" +#if !CONFIG_DISABLE_HAL_LOCKS #include "freertos/FreeRTOS.h" #include "freertos/task.h" #include "freertos/semphr.h" -#include "freertos/event_groups.h" -#include "driver/periph_ctrl.h" -#include "soc/i2c_reg.h" -#include "soc/i2c_struct.h" +#endif #include "esp_attr.h" -#include "esp32-hal-cpu.h" // cpu clock change support 31DEC2018 - #include "esp_system.h" -#ifdef ESP_IDF_VERSION_MAJOR // IDF 4+ -#if CONFIG_IDF_TARGET_ESP32 // ESP32/PICO-D4 -#include "soc/dport_reg.h" -#include "esp32/rom/ets_sys.h" -#elif CONFIG_IDF_TARGET_ESP32S2 -#include "soc/dport_reg.h" -#include "esp32s2/rom/ets_sys.h" -#elif CONFIG_IDF_TARGET_ESP32C3 -#include "esp32c3/rom/ets_sys.h" -#else -#error Target CONFIG_IDF_TARGET is not supported -#endif -#else // ESP32 Before IDF 4.0 -#include "rom/ets_sys.h" -#endif - - -#if CONFIG_IDF_TARGET_ESP32 -//#define I2C_DEV(i) (volatile i2c_dev_t *)((i)?DR_REG_I2C1_EXT_BASE:DR_REG_I2C_EXT_BASE) -//#define I2C_DEV(i) ((i2c_dev_t *)(REG_I2C_BASE(i))) -#define I2C_SCL_IDX(p) ((p==0)?I2CEXT0_SCL_OUT_IDX:((p==1)?I2CEXT1_SCL_OUT_IDX:0)) -#define I2C_SDA_IDX(p) ((p==0)?I2CEXT0_SDA_OUT_IDX:((p==1)?I2CEXT1_SDA_OUT_IDX:0)) - -#define DR_REG_I2C_EXT_BASE_FIXED 0x60013000 -#define DR_REG_I2C1_EXT_BASE_FIXED 0x60027000 - -/* Stickbreaker ISR mode debug support - -ENABLE_I2C_DEBUG_BUFFER - Enable debug interrupt history buffer, fifoTx history buffer. - Setting this define will result in 2570 bytes of RAM being used whenever CORE_DEBUG_LEVEL - is higher than WARNING. Unless you are debugging a problem in the I2C subsystem, - I would recommend you leave it commented out. - */ - -//#define ENABLE_I2C_DEBUG_BUFFER - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) -#define INTBUFFMAX 64 -#define FIFOMAX 512 -static uint32_t intBuff[INTBUFFMAX][3][2]; -static uint32_t intPos[2]= {0,0}; -static uint16_t fifoBuffer[FIFOMAX]; -static uint16_t fifoPos = 0; -#endif - -// start from tools/sdk/include/soc/soc/i2c_struct.h - -typedef union { - struct { - uint32_t byte_num: 8; /*Byte_num represent the number of data need to be send or data need to be received.*/ - uint32_t ack_en: 1; /*ack_check_en ack_exp and ack value are used to control the ack bit.*/ - uint32_t ack_exp: 1; /*ack_check_en ack_exp and ack value are used to control the ack bit.*/ - uint32_t ack_val: 1; /*ack_check_en ack_exp and ack value are used to control the ack bit.*/ - uint32_t op_code: 3; /*op_code is the command 0:RSTART 1:WRITE 2:READ 3:STOP . 4:END.*/ - uint32_t reserved14: 17; - uint32_t done: 1; /*When command0 is done in I2C Master mode this bit changes to high level.*/ - }; - uint32_t val; -} I2C_COMMAND_t; - -typedef union { - struct { - uint32_t rx_fifo_full_thrhd: 5; - uint32_t tx_fifo_empty_thrhd:5; //Config tx_fifo empty threhd value when using apb fifo access * / - uint32_t nonfifo_en: 1; //Set this bit to enble apb nonfifo access. * / - uint32_t fifo_addr_cfg_en: 1; //When this bit is set to 1 then the byte after address represent the offset address of I2C Slave's ram. * / - uint32_t rx_fifo_rst: 1; //Set this bit to reset rx fifo when using apb fifo access. * / - // chuck while this bit is 1, the RX fifo is held in REST, Toggle it * / - uint32_t tx_fifo_rst: 1; //Set this bit to reset tx fifo when using apb fifo access. * / - // chuck while this bit is 1, the TX fifo is held in REST, Toggle it * / - uint32_t nonfifo_rx_thres: 6; //when I2C receives more than nonfifo_rx_thres data it will produce rx_send_full_int_raw interrupt and update the current offset address of the receiving data.* / - uint32_t nonfifo_tx_thres: 6; //when I2C sends more than nonfifo_tx_thres data it will produce tx_send_empty_int_raw interrupt and update the current offset address of the sending data. * / - uint32_t reserved26: 6; - }; - uint32_t val; -} I2C_FIFO_CONF_t; - -typedef union { - struct { - uint32_t rx_fifo_start_addr: 5; /*This is the offset address of the last receiving data as described in nonfifo_rx_thres_register.*/ - uint32_t rx_fifo_end_addr: 5; /*This is the offset address of the first receiving data as described in nonfifo_rx_thres_register.*/ - uint32_t tx_fifo_start_addr: 5; /*This is the offset address of the first sending data as described in nonfifo_tx_thres register.*/ - uint32_t tx_fifo_end_addr: 5; /*This is the offset address of the last sending data as described in nonfifo_tx_thres register.*/ - uint32_t reserved20: 12; - }; - uint32_t val; - } I2C_FIFO_ST_t; - -// end from tools/sdk/include/soc/soc/i2c_struct.h - -// sync between dispatch(i2cProcQueue) and worker(i2c_isr_handler_default) -typedef enum { - //I2C_NONE=0, - I2C_STARTUP=1, - I2C_RUNNING, - I2C_DONE -} I2C_STAGE_t; - -typedef enum { - I2C_NONE=0, - I2C_MASTER, - I2C_SLAVE, - I2C_MASTERSLAVE -} I2C_MODE_t; - -// internal Error condition -typedef enum { - // I2C_NONE=0, - I2C_OK=1, - I2C_ERROR, - I2C_ADDR_NAK, - I2C_DATA_NAK, - I2C_ARBITRATION, - I2C_TIMEOUT -} I2C_ERROR_t; - -// i2c_event bits for EVENTGROUP bits -// needed to minimize change events, FreeRTOS Daemon overload, so ISR will only set values -// on Exit. Dispatcher will set bits for each dq before/after ISR completion -#define EVENT_ERROR_NAK (BIT(0)) -#define EVENT_ERROR (BIT(1)) -#define EVENT_ERROR_BUS_BUSY (BIT(2)) -#define EVENT_RUNNING (BIT(3)) -#define EVENT_DONE (BIT(4)) -#define EVENT_IN_END (BIT(5)) -#define EVENT_ERROR_PREV (BIT(6)) -#define EVENT_ERROR_TIMEOUT (BIT(7)) -#define EVENT_ERROR_ARBITRATION (BIT(8)) -#define EVENT_ERROR_DATA_NAK (BIT(9)) -#define EVENT_MASK 0x3F - -// control record for each dq entry -typedef union { - struct { - uint32_t addr: 16; // I2C address, if 10bit must have 0x7800 mask applied, else 8bit - uint32_t mode: 1; // transaction direction 0 write, 1 read - uint32_t stop: 1; // sendStop 0 no, 1 yes - uint32_t startCmdSent: 1; // START cmd has been added to command[] - uint32_t addrCmdSent: 1; // addr WRITE cmd has been added to command[] - uint32_t dataCmdSent: 1; // all necessary DATA(READ/WRITE) cmds added to command[] - uint32_t stopCmdSent: 1; // completed all necessary commands - uint32_t addrReq: 2; // number of addr bytes need to send address - uint32_t addrSent: 2; // number of addr bytes added to FIFO - uint32_t reserved_31: 6; - }; - uint32_t val; -} I2C_DATA_CTRL_t; - -// individual dq element -typedef struct { - uint8_t *data; // data pointer for read/write buffer - uint16_t length; // size of data buffer - uint16_t position; // current position for next char in buffer (lock, portMAX_DELAY) != pdPASS) -#define I2C_MUTEX_UNLOCK() xSemaphoreGiveRecursive(i2c->lock) - -static i2c_t _i2c_bus_array[2] = { - {(volatile i2c_dev_t *)(DR_REG_I2C_EXT_BASE_FIXED), NULL, 0, -1, -1, I2C_NONE,I2C_NONE,I2C_ERROR_OK,NULL,NULL,NULL,0,0,0,0,0,0}, - {(volatile i2c_dev_t *)(DR_REG_I2C1_EXT_BASE_FIXED), NULL, 1, -1, -1,I2C_NONE,I2C_NONE,I2C_ERROR_OK,NULL,NULL,NULL,0,0,0,0,0,0} -}; -#endif - -/* - * index - command index (0 to 15) - * op_code - is the command - * byte_num - This register is to store the amounts of data that is read and written. byte_num in RSTART, STOP, END is null. - * ack_val - Each data byte is terminated by an ACK bit used to set the bit level. - * ack_exp - This bit is to set an expected ACK value for the transmitter. - * ack_check - This bit is to decide whether the transmitter checks ACK bit. 1 means yes and 0 means no. - * */ +} i2c_bus_t; +static i2c_bus_t bus[SOC_I2C_NUM]; -/* Stickbreaker ISR mode debug support - */ -static void ARDUINO_ISR_ATTR i2cDumpCmdQueue(i2c_t *i2c) -{ -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_ERROR)&&(defined ENABLE_I2C_DEBUG_BUFFER) - static const char * const cmdName[] ={"RSTART","WRITE","READ","STOP","END"}; - uint8_t i=0; - while(i<16) { - I2C_COMMAND_t c; - c.val=i2c->dev->command[i].val; - log_e("[%2d]\t%c\t%s\tval[%d]\texp[%d]\ten[%d]\tbytes[%d]",i,(c.done?'Y':'N'), - cmdName[c.op_code], - c.ack_val, - c.ack_exp, - c.ack_en, - c.byte_num); - i++; +bool i2cIsInit(uint8_t i2c_num){ + if(i2c_num >= SOC_I2C_NUM){ + return false; } -#endif + return bus[i2c_num].initialized; } -/* Stickbreaker ISR mode debug support - */ -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) -static void i2cDumpDqData(i2c_t * i2c) -{ -#if defined (ENABLE_I2C_DEBUG_BUFFER) - uint16_t a=0; - char buff[140]; - I2C_DATA_QUEUE_t *tdq; - int digits=0,lenDigits=0; - a = i2c->queueCount; - while(a>0) { - digits++; - a /= 10; - } - while(aqueueCount) { // find maximum number of len decimal digits for formatting - if (i2c->dq[a].length > lenDigits ) lenDigits = i2c->dq[a].length; - a++; - } - a=0; - while(lenDigits>0){ - a++; - lenDigits /= 10; +esp_err_t i2cInit(uint8_t i2c_num, int8_t sda, int8_t scl, uint32_t frequency){ + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - lenDigits = a; - a = 0; - while(aqueueCount) { - tdq=&i2c->dq[a]; - char buf1[10],buf2[10]; - sprintf(buf1,"%0*d",lenDigits,tdq->length); - sprintf(buf2,"%0*d",lenDigits,tdq->position); - log_i("[%0*d] %sbit %x %c %s buf@=%p, len=%s, pos=%s, ctrl=%d%d%d%d%d",digits,a, - (tdq->ctrl.addr>0x100)?"10":"7", - (tdq->ctrl.addr>0x100)?(((tdq->ctrl.addr&0x600)>>1)|(tdq->ctrl.addr&0xff)):(tdq->ctrl.addr>>1), - (tdq->ctrl.mode)?'R':'W', - (tdq->ctrl.stop)?"STOP":"", - tdq->data, - buf1,buf2, - tdq->ctrl.startCmdSent,tdq->ctrl.addrCmdSent,tdq->ctrl.dataCmdSent,(tdq->ctrl.stop)?tdq->ctrl.stopCmdSent:0,tdq->ctrl.addrSent - ); - uint16_t offset = 0; - while(offsetlength) { - memset(buff,' ',140); - buff[139]='\0'; - uint16_t i = 0,j; - j=sprintf(buff,"0x%04x: ",offset); - while((i<32)&&(offset < tdq->length)) { - char ch = tdq->data[offset]; - sprintf((char*)&buff[(i*3)+41],"%02x ",ch); - if((ch<32)||(ch>126)) { - ch='.'; - } - j+=sprintf((char*)&buff[j],"%c",ch); - buff[j]=' '; - i++; - offset++; - } - log_i("%s",buff); - } - a++; - } -#else - log_i("Debug Buffer not Enabled"); -#endif -} -#endif -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO -static void i2cDumpI2c(i2c_t * i2c) -{ - log_e("i2c=%p",i2c); - log_i("dev=%p date=%p",i2c->dev,i2c->dev->date); #if !CONFIG_DISABLE_HAL_LOCKS - log_i("lock=%p",i2c->lock); -#endif - log_i("num=%d",i2c->num); - log_i("mode=%d",i2c->mode); - log_i("stage=%d",i2c->stage); - log_i("error=%d",i2c->error); - log_i("event=%p bits=%x",i2c->i2c_event,(i2c->i2c_event)?xEventGroupGetBits(i2c->i2c_event):0); - log_i("intr_handle=%p",i2c->intr_handle); - log_i("dq=%p",i2c->dq); - log_i("queueCount=%d",i2c->queueCount); - log_i("queuePos=%d",i2c->queuePos); - log_i("errorByteCnt=%d",i2c->errorByteCnt); - log_i("errorQueue=%d",i2c->errorQueue); - log_i("debugFlags=0x%08X",i2c->debugFlags); - if(i2c->dq) { - i2cDumpDqData(i2c); - } -} -#endif - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) -static void i2cDumpInts(uint8_t num) -{ -#if defined (ENABLE_I2C_DEBUG_BUFFER) - uint32_t b; - log_i("%u row\tcount\tINTR\tTX\tRX\tTick ",num); - for(uint32_t a=1; a<=INTBUFFMAX; a++) { - b=(a+intPos[num])%INTBUFFMAX; - if(intBuff[b][0][num]!=0) { - log_i("[%02d]\t0x%04x\t0x%04x\t0x%04x\t0x%04x\t0x%08x",b,((intBuff[b][0][num]>>16)&0xFFFF),(intBuff[b][0][num]&0xFFFF),((intBuff[b][1][num]>>16)&0xFFFF),(intBuff[b][1][num]&0xFFFF),intBuff[b][2][num]); + if(bus[i2c_num].lock == NULL){ + bus[i2c_num].lock = xSemaphoreCreateMutex(); + if(bus[i2c_num].lock == NULL){ + log_e("xSemaphoreCreateMutex failed"); + return ESP_ERR_NO_MEM; } } -#else - log_i("Debug Buffer not Enabled"); -#endif -} -#endif - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO)&&(defined ENABLE_I2C_DEBUG_BUFFER) -static void ARDUINO_ISR_ATTR i2cDumpStatus(i2c_t * i2c){ - typedef union { - struct { - uint32_t ack_rec: 1; /*This register stores the value of ACK bit.*/ - uint32_t slave_rw: 1; /*when in slave mode 1:master read slave 0: master write slave.*/ - uint32_t time_out: 1; /*when I2C takes more than time_out_reg clocks to receive a data then this register changes to high level.*/ - uint32_t arb_lost: 1; /*when I2C lost control of SDA line this register changes to high level.*/ - uint32_t bus_busy: 1; /*1:I2C bus is busy transferring data. 0:I2C bus is in idle state.*/ - uint32_t slave_addressed: 1; /*when configured as i2c slave and the address send by master is equal to slave's address then this bit will be high level.*/ - uint32_t byte_trans: 1; /*This register changes to high level when one byte is transferred.*/ - uint32_t reserved7: 1; - uint32_t rx_fifo_cnt: 6; /*This register represent the amount of data need to send.*/ - uint32_t reserved14: 4; - uint32_t tx_fifo_cnt: 6; /*This register stores the amount of received data in ram.*/ - uint32_t scl_main_state_last: 3; /*This register stores the value of state machine for i2c module. 3'h0: SCL_MAIN_IDLE 3'h1: SCL_ADDRESS_SHIFT 3'h2: SCL_ACK_ADDRESS 3'h3: SCL_RX_DATA 3'h4 SCL_TX_DATA 3'h5:SCL_SEND_ACK 3'h6:SCL_WAIT_ACK*/ - uint32_t reserved27: 1; - uint32_t scl_state_last: 3; /*This register stores the value of state machine to produce SCL. 3'h0: SCL_IDLE 3'h1:SCL_START 3'h2:SCL_LOW_EDGE 3'h3: SCL_LOW 3'h4:SCL_HIGH_EDGE 3'h5:SCL_HIGH 3'h6:SCL_STOP*/ - uint32_t reserved31: 1; - }; - uint32_t val; - } status_reg; - - status_reg sr; - sr.val= i2c->dev->status_reg.val; - - log_i("ack(%d) sl_rw(%d) to(%d) arb(%d) busy(%d) sl(%d) trans(%d) rx(%d) tx(%d) sclMain(%d) scl(%d)",sr.ack_rec,sr.slave_rw,sr.time_out,sr.arb_lost,sr.bus_busy,sr.slave_addressed,sr.byte_trans, sr.rx_fifo_cnt, sr.tx_fifo_cnt,sr.scl_main_state_last, sr.scl_state_last); -} -#endif - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO)&&(defined ENABLE_I2C_DEBUG_BUFFER) -static void i2cDumpFifo(i2c_t * i2c){ -char buf[64]; -uint16_t k = 0; -uint16_t i = fifoPos+1; - i %=FIFOMAX; -while((fifoBuffer[i]==0)&&(i!=fifoPos)){ - i++; - i %=FIFOMAX; -} -if(i != fifoPos){// actual data - do{ - if(fifoBuffer[i] & 0x8000){ // address byte - if(fifoBuffer[i] & 0x100) { // read - if(fifoBuffer[i] & 0x1) { // valid read dev id - k+= sprintf(&buf[k],"READ 0x%02X",(fifoBuffer[i]&0xff)>>1); - } else { // invalid read dev id - k+= sprintf(&buf[k],"Bad READ 0x%02X",(fifoBuffer[i]&0xff)); - } - } else { // write - if(fifoBuffer[i] & 0x1) { // bad write dev id - k+= sprintf(&buf[k],"bad WRITE 0x%02X",(fifoBuffer[i]&0xff)); - } else { // good Write - k+= sprintf(&buf[k],"WRITE 0x%02X",(fifoBuffer[i]&0xff)>>1); - } - } - } else k += sprintf(&buf[k],"% 4X ",fifoBuffer[i]); - - i++; - i %= FIFOMAX; - bool outBuffer=false; - if( fifoBuffer[i] & 0x8000){ - outBuffer=true; - k=0; - } - if((outBuffer)||(k>50)||(i==fifoPos)) log_i("%s",buf); - outBuffer = false; - if(k>50) { - k=sprintf(buf,"-> "); - } - }while( i!= fifoPos); -} -} -#endif - -static void ARDUINO_ISR_ATTR i2cTriggerDumps(i2c_t * i2c, uint8_t trigger, const char locus[]){ -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO)&&(defined ENABLE_I2C_DEBUG_BUFFER) - if( trigger ){ - log_i("%s",locus); - if(trigger & 1) i2cDumpI2c(i2c); - if(trigger & 2) i2cDumpInts(i2c->num); - if(trigger & 4) i2cDumpCmdQueue(i2c); - if(trigger & 8) i2cDumpStatus(i2c); - if(trigger & 16) i2cDumpFifo(i2c); - } -#endif -} - // end of debug support routines - -/* Start of CPU Clock change Support -*/ - -static void i2cApbChangeCallback(void * arg, apb_change_ev_t ev_type, uint32_t old_apb, uint32_t new_apb){ - i2c_t* i2c = (i2c_t*) arg; // recover data - if(i2c == NULL) { // point to peripheral control block does not exits - return; - } - uint32_t oldFreq=0; - switch(ev_type){ - case APB_BEFORE_CHANGE : - if(new_apb < 3000000) {// too slow - log_e("apb speed %d too slow",new_apb); - break; - } - I2C_MUTEX_LOCK(); // lock will spin until current transaction is completed - break; - case APB_AFTER_CHANGE : - oldFreq = (i2c->dev->scl_low_period.period+i2c->dev->scl_high_period.period); //read old apbCycles - if(oldFreq>0) { // was configured with value - oldFreq = old_apb / oldFreq; - i2cSetFrequency(i2c,oldFreq); - } - I2C_MUTEX_UNLOCK(); - break; - default : - log_e("unk ev %u",ev_type); - I2C_MUTEX_UNLOCK(); - } - return; -} -/* End of CPU Clock change Support -*/ -static void ARDUINO_ISR_ATTR i2cSetCmd(i2c_t * i2c, uint8_t index, uint8_t op_code, uint8_t byte_num, bool ack_val, bool ack_exp, bool ack_check) -{ - I2C_COMMAND_t cmd; - cmd.val=0; - cmd.ack_en = ack_check; - cmd.ack_exp = ack_exp; - cmd.ack_val = ack_val; - cmd.byte_num = byte_num; - cmd.op_code = op_code; - i2c->dev->command[index].val = cmd.val; -} - - -static void ARDUINO_ISR_ATTR fillCmdQueue(i2c_t * i2c, bool INTS) -{ - /* this function is called on initial i2cProcQueue() or when a I2C_END_DETECT_INT occurs - */ - uint16_t cmdIdx = 0; - uint16_t qp = i2c->queuePos; // all queues before queuePos have been completely processed, - // so look start by checking the 'current queue' so see if it needs commands added to - // hardware peripheral command list. walk through each queue entry until all queues have been - // checked - bool done; - bool needMoreCmds = false; - bool ena_rx=false; // if we add a read op, better enable Rx_Fifo IRQ - bool ena_tx=false; // if we add a Write op, better enable TX_Fifo IRQ - - while(!needMoreCmds&&(qp < i2c->queueCount)) { // check if more possible cmds - if(i2c->dq[qp].ctrl.stopCmdSent) {// marks that all required cmds[] have been added to peripheral - qp++; - } else { - needMoreCmds=true; - } - } - //log_e("needMoreCmds=%d",needMoreCmds); - done=(!needMoreCmds)||(cmdIdx>14); - - while(!done) { // fill the command[] until either 0..14 filled or out of cmds and last cmd is STOP - //CMD START - I2C_DATA_QUEUE_t *tdq=&i2c->dq[qp]; // simpler coding - - if((!tdq->ctrl.startCmdSent) && (cmdIdx < 14)) { // has this dq element's START command been added? - // (cmdIdx<14) because a START op cannot directly precede an END op, else a time out cascade occurs - i2cSetCmd(i2c, cmdIdx++, I2C_CMD_RSTART, 0, false, false, false); - tdq->ctrl.startCmdSent=1; - } - - //CMD WRITE ADDRESS - if((!done)&&(tdq->ctrl.startCmdSent)) { // have to leave room for continue(END), and START must have been sent! - if(!tdq->ctrl.addrCmdSent) { - i2cSetCmd(i2c, cmdIdx++, I2C_CMD_WRITE, tdq->ctrl.addrReq, false, false, true); //load address in cmdlist, validate (low) ack - tdq->ctrl.addrCmdSent=1; - done =(cmdIdx>14); - ena_tx=true; // tx Data necessary - } - } - - /* Can I have another Sir? - ALL CMD queues must be terminated with either END or STOP. - - If END is used, when refilling the cmd[] next time, no entries from END to [15] can be used. - AND the cmd[] must be filled starting at [0] with commands. Either fill all 15 [0]..[14] and leave the - END in [15] or include a STOP in one of the positions [0]..[14]. Any entries after a STOP are IGNORED by the StateMachine. - The END operation does not complete until ctr->trans_start=1 has been issued. - - So, only refill from [0]..[14], leave [15] for a continuation(END) if necessary. - As a corollary, once END exists in [15], you do not need to overwrite it for the - next continuation. It is never modified. But, I update it every time because it might - actually be the first time! - - 23NOV17 START cannot proceed END. if START is in[14], END cannot be in [15]. - So, if END is moved to [14], [14] and [15] can no longer be used for anything other than END. - If a START is found in [14] then a prior READ or WRITE must be expanded so that there is no START element in [14]. - */ - - if((!done)&&(tdq->ctrl.addrCmdSent)) { //room in command[] for at least One data (read/Write) cmd - uint8_t blkSize=0; // max is 255 - while(( tdq->cmdBytesNeeded > tdq->ctrl.mode )&&(!done )) { // more bytes needed and room in cmd queue, leave room for END - blkSize = (tdq->cmdBytesNeeded > 255)?255:(tdq->cmdBytesNeeded - tdq->ctrl.mode); // Last read cmd needs different ACK setting, so leave 1 byte remainder on reads - tdq->cmdBytesNeeded -= blkSize; - if(tdq->ctrl.mode==1) { //read mode - i2cSetCmd(i2c, (cmdIdx)++, I2C_CMD_READ, blkSize,false,false,false); // read cmd, this can't be the last read. - ena_rx=true; // need to enable rxFifo IRQ - } else { // write - i2cSetCmd(i2c, cmdIdx++, I2C_CMD_WRITE, blkSize, false, false, true); // check for Nak - ena_tx=true; // need to enable txFifo IRQ - } - done = cmdIdx>14; //have to leave room for END - } - - if(!done) { // buffer is not filled completely - if((tdq->ctrl.mode==1)&&(tdq->cmdBytesNeeded==1)) { //special last read byte NAK - i2cSetCmd(i2c, (cmdIdx)++, I2C_CMD_READ, 1,true,false,false); - // send NAK to mark end of read - tdq->cmdBytesNeeded=0; - done = cmdIdx > 14; - ena_rx=true; - } - } - - tdq->ctrl.dataCmdSent=(tdq->cmdBytesNeeded==0); // enough command[] to send all data - - if((!done)&&(tdq->ctrl.dataCmdSent)) { // possibly add stop - if(!tdq->ctrl.stopCmdSent){ - if(tdq->ctrl.stop) { //send a stop - i2cSetCmd(i2c, (cmdIdx)++,I2C_CMD_STOP,0,false,false,false); - done = cmdIdx > 14; - } - tdq->ctrl.stopCmdSent = 1; - } - } - } - - if((cmdIdx==14)&&(!tdq->ctrl.startCmdSent)) { - // START would have preceded END, causes SM TIMEOUT - // need to stretch out a prior WRITE or READ to two Command[] elements - done = false; // reuse it - uint16_t i = 13; // start working back until a READ/WRITE has >1 numBytes - cmdIdx =15; - while(!done) { - i2c->dev->command[i+1].val = i2c->dev->command[i].val; // push it down - if (((i2c->dev->command[i].op_code == 1)||(i2c->dev->command[i].op_code==2))) { - /* add a dummy read/write cmd[] with num_bytes set to zero,just a place holder in the cmd[]list - */ - i2c->dev->command[i].byte_num = 0; - done = true; - - } else { - if(i > 0) { - i--; - } else { // unable to stretch, fatal - log_e("invalid CMD[] layout Stretch Failed"); - i2cDumpCmdQueue(i2c); - done = true; - } - } - } - - } - - - if(cmdIdx==15) { //need continuation, even if STOP is in 14, it will not matter - // cmd buffer is almost full, Add END as a continuation feature - i2cSetCmd(i2c, (cmdIdx)++,I2C_CMD_END, 0,false,false,false); - i2c->dev->int_ena.end_detect=1; - i2c->dev->int_clr.end_detect=1; - done = true; - } - - if(!done) { - if(tdq->ctrl.stopCmdSent) { // this queue element has been completely added to command[] buffer - qp++; - if(qp < i2c->queueCount) { - tdq = &i2c->dq[qp]; - } else { - done = true; - } - } - } - - }// while(!done) - if(INTS) { // don't want to prematurely enable fifo ints until ISR is ready to handle them. - if(ena_rx) { - i2c->dev->int_ena.rx_fifo_full = 1; - } - if(ena_tx) { - i2c->dev->int_ena.tx_fifo_empty = 1; - } + //acquire lock + if(xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return ESP_FAIL; } -} - -static void ARDUINO_ISR_ATTR fillTxFifo(i2c_t * i2c) -{ - /* - 12/01/2017 The Fifo's are independent, 32 bytes of tx and 32 bytes of Rx. - overlap is not an issue, just keep them full/empty the status_reg.xx_fifo_cnt - tells the truth. And the INT's fire correctly - */ - uint16_t a=i2c->queuePos; // currently executing dq, - bool full=!(i2c->dev->status_reg.tx_fifo_cnt<31); - uint8_t cnt; - bool rxQueueEncountered = false; - while((a < i2c->queueCount) && !full) { - I2C_DATA_QUEUE_t *tdq = &i2c->dq[a]; - cnt=0; - // add to address to fifo ctrl.addr already has R/W bit positioned correctly - if(tdq->ctrl.addrSent < tdq->ctrl.addrReq) { // need to send address bytes - if(tdq->ctrl.addrReq==2) { //10bit - if(tdq->ctrl.addrSent==0) { //10bit highbyte needs sent - if(!full) { // room in fifo - i2c->dev->fifo_data.val = ((tdq->ctrl.addr>>8)&0xFF); - cnt++; - tdq->ctrl.addrSent=1; //10bit highbyte sent - } - } - full=!(i2c->dev->status_reg.tx_fifo_cnt<31); - - if(tdq->ctrl.addrSent==1) { //10bit Lowbyte needs sent - if(!full) { // room in fifo - i2c->dev->fifo_data.val = tdq->ctrl.addr&0xFF; - cnt++; - tdq->ctrl.addrSent=2; //10bit lowbyte sent - } - } - } else { // 7bit} - if(tdq->ctrl.addrSent==0) { // 7bit Lowbyte needs sent - if(!full) { // room in fifo - i2c->dev->fifo_data.val = tdq->ctrl.addr&0xFF; - cnt++; - tdq->ctrl.addrSent=1; // 7bit lowbyte sent -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) - uint16_t a = 0x8000 | tdq->ctrl.addr | (tdq->ctrl.mode<<8); - fifoBuffer[fifoPos++] = a; - fifoPos %= FIFOMAX; #endif - } - } - } - } - // add write data to fifo - if(tdq->ctrl.mode==0) { // write - if(tdq->ctrl.addrSent == tdq->ctrl.addrReq) { //address has been sent, is Write Mode! - uint32_t moveCnt = 32 - i2c->dev->status_reg.tx_fifo_cnt; // how much room in txFifo? - while(( moveCnt>0)&&(tdq->position < tdq->length)) { -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) - fifoBuffer[fifoPos++] = tdq->data[tdq->position]; - fifoPos %= FIFOMAX; -#endif - i2c->dev->fifo_data.val = tdq->data[tdq->position++]; - cnt++; - moveCnt--; - - } - } - } else { // read Queue Encountered, can't update QueuePos past this point, emptyRxfifo will do it - if( ! rxQueueEncountered ) { - rxQueueEncountered = true; - if(a > i2c->queuePos){ - i2c->queuePos = a; - } - } - } -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) - - // update debug buffer tx counts - cnt += intBuff[intPos[i2c->num]][1][i2c->num]>>16; - intBuff[intPos[i2c->num]][1][i2c->num] = (intBuff[intPos[i2c->num]][1][i2c->num]&0xFFFF)|(cnt<<16); - -#endif - full=!(i2c->dev->status_reg.tx_fifo_cnt<31); - if(!full) { - a++; // check next buffer for address tx, or write data - } + if(bus[i2c_num].initialized){ + log_e("bus is already initialized"); + return ESP_FAIL; } - if(a >= i2c->queueCount ) { // disable TX IRQ, all tx Data has been queued - i2c->dev->int_ena.tx_fifo_empty= 0; + if(!frequency){ + frequency = 100000UL; + } else if(frequency > 1000000UL){ + frequency = 1000000UL; } - i2c->dev->int_clr.tx_fifo_empty=1; -} - - -static void ARDUINO_ISR_ATTR emptyRxFifo(i2c_t * i2c) -{ - uint32_t d, cnt=0, moveCnt; - - moveCnt = i2c->dev->status_reg.rx_fifo_cnt;//no need to check the reg until this many are read - - while((moveCnt > 0)&&(i2c->queuePos < i2c->queueCount)){ // data to move - - I2C_DATA_QUEUE_t *tdq =&i2c->dq[i2c->queuePos]; //short cut - - while((tdq->position >= tdq->length)&&( i2c->queuePos < i2c->queueCount)){ // find were to store - i2c->queuePos++; - tdq = &i2c->dq[i2c->queuePos]; - } - - if(i2c->queuePos >= i2c->queueCount){ // bad stuff, rx data but no place to put it! - log_e("no Storage location for %d",moveCnt); - // discard - while(moveCnt>0){ - d = i2c->dev->fifo_data.val; - moveCnt--; - cnt++; - } - break; - } - - if(tdq->ctrl.mode == 1){ // read command - if(moveCnt > (tdq->length - tdq->position)) { //make sure they go in this dq - // part of these reads go into the next dq - moveCnt = (tdq->length - tdq->position); - } - } else {// error - log_e("RxEmpty(%d) call on TxBuffer? dq=%d",moveCnt,i2c->queuePos); - // discard - while(moveCnt>0){ - d = i2c->dev->fifo_data.val; - moveCnt--; - cnt++; - } - break; - } + i2c_config_t conf = { }; + conf.mode = I2C_MODE_MASTER; + conf.scl_io_num = (gpio_num_t)scl; + conf.sda_io_num = (gpio_num_t)sda; + conf.scl_pullup_en = GPIO_PULLUP_ENABLE; + conf.sda_pullup_en = GPIO_PULLUP_ENABLE; + conf.master.clk_speed = frequency; + conf.clk_flags = I2C_SCLK_SRC_FLAG_FOR_NOMAL; //Any one clock source that is available for the specified frequency may be choosen - while(moveCnt > 0) { // store data - d = i2c->dev->fifo_data.val; - moveCnt--; - cnt++; - tdq->data[tdq->position++] = (d&0xFF); + esp_err_t ret = i2c_param_config((i2c_port_t)i2c_num, &conf); + if (ret != ESP_OK) { + log_e("i2c_param_config failed"); + } else { + ret = i2c_driver_install((i2c_port_t)i2c_num, conf.mode, 0, 0, 0); + if (ret != ESP_OK) { + log_e("i2c_driver_install failed"); + } else { + bus[i2c_num].initialized = true; + bus[i2c_num].frequency = frequency; } - - moveCnt = i2c->dev->status_reg.rx_fifo_cnt; //any more out there? } - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO)&& (defined ENABLE_I2C_DEBUG_BUFFER) - // update Debug rxCount - cnt += (intBuff[intPos[i2c->num]][1][i2c->num])&0xffFF; - intBuff[intPos[i2c->num]][1][i2c->num] = (intBuff[intPos[i2c->num]][1][i2c->num]&0xFFFF0000)|cnt; +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); #endif + return ret; } -static void ARDUINO_ISR_ATTR i2cIsrExit(i2c_t * i2c,const uint32_t eventCode,bool Fatal) -{ - - switch(eventCode) { - case EVENT_DONE: - i2c->error = I2C_OK; - break; - case EVENT_ERROR_NAK : - i2c->error =I2C_ADDR_NAK; - break; - case EVENT_ERROR_DATA_NAK : - i2c->error =I2C_DATA_NAK; - break; - case EVENT_ERROR_TIMEOUT : - i2c->error = I2C_TIMEOUT; - break; - case EVENT_ERROR_ARBITRATION: - i2c->error = I2C_ARBITRATION; - break; - default : - i2c->error = I2C_ERROR; - } - uint32_t exitCode = EVENT_DONE | eventCode |(Fatal?EVENT_ERROR:0); - if((i2c->queuePos < i2c->queueCount) && (i2c->dq[i2c->queuePos].ctrl.mode == 1)) { - emptyRxFifo(i2c); // grab last few characters - } - i2c->dev->int_ena.val = 0; // shut down interrupts - i2c->dev->int_clr.val = 0x1FFF; - i2c->stage = I2C_DONE; - i2c->exitCode = exitCode; //true eventcode - - portBASE_TYPE HPTaskAwoken = pdFALSE,xResult; - // try to notify Dispatch we are done, - // else the 50ms time out will recover the APP, just a little slower - HPTaskAwoken = pdFALSE; - xResult = xEventGroupSetBitsFromISR(i2c->i2c_event, exitCode, &HPTaskAwoken); - if(xResult == pdPASS) { - if(HPTaskAwoken==pdTRUE) { - portYIELD_FROM_ISR(); - // log_e("Yield to Higher"); - } - } - -} - -static void ARDUINO_ISR_ATTR i2c_update_error_byte_cnt(i2c_t * i2c) -{ -/* i2c_update_error_byte_cnt 07/18/2018 - Only called after an error has occurred, so, most of the time this function is never used. - This function obliterates the need to interrupt monitor each byte transferred, at high bitrates - the byte interrupts were overwhelming the OS. Spurious Interrupts were being generated. - it updates errorByteCnt, errorQueue. - */ - uint16_t a=0; // start at top of DQ, count how many bytes added to tx fifo, and received from rx_fifo. - int16_t bc = 0; - I2C_DATA_QUEUE_t *tdq; - i2c->errorByteCnt = 0; - while( a < i2c->queueCount){ // add up all bytes loaded into fifo's - tdq = &i2c->dq[a]; - i2c->errorByteCnt += tdq->ctrl.addrSent; - i2c->errorByteCnt += tdq->position; - a++; +esp_err_t i2cDeinit(uint8_t i2c_num){ + esp_err_t err = ESP_FAIL; + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - // now errorByteCnt contains total bytes moved into and out of FIFO's - // but, there may still be bytes waiting in Fifo's - i2c->errorByteCnt -= i2c->dev->status_reg.tx_fifo_cnt; // waiting to go out; - i2c->errorByteCnt += i2c->dev->status_reg.rx_fifo_cnt; // already received -// now walk thru DQ again, find which byte is 'current' - bc = i2c->errorByteCnt; - i2c->errorQueue = 0; - while( i2c->errorQueue < i2c->queueCount ){ - tdq = &i2c->dq[i2c->errorQueue]; - if(bc>0){ // not found yet - if( tdq->ctrl.addrSent >= bc){ // in address - bc = -1; // in address - break; - } else { - bc -= tdq->ctrl.addrSent; - if( tdq->length > bc) { // data nak - break; - } else { // count down - bc -= tdq->length; - } - } - } else break; - - i2c->errorQueue++; - } - - i2c->errorByteCnt = bc; - } - -static void ARDUINO_ISR_ATTR i2c_isr_handler_default(void* arg) -{ - i2c_t* p_i2c = (i2c_t*) arg; // recover data - uint32_t activeInt = p_i2c->dev->int_status.val&0x7FF; - - if(p_i2c->stage==I2C_DONE) { //get Out, can't service, not configured - p_i2c->dev->int_ena.val = 0; - p_i2c->dev->int_clr.val = 0x1FFF; -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_VERBOSE - uint32_t raw = p_i2c->dev->int_raw.val; - log_w("eject raw=%p, int=%p",raw,activeInt); -#endif - return; +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(bus[i2c_num].lock == NULL || xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return err; } - while (activeInt != 0) { // Ordering of 'if(activeInt)' statements is important, don't change - - #if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) - if(activeInt==(intBuff[intPos[p_i2c->num]][0][p_i2c->num]&0x1fff)) { - intBuff[intPos[p_i2c->num]][0][p_i2c->num] = (((intBuff[intPos[p_i2c->num]][0][p_i2c->num]>>16)+1)<<16)|activeInt; - } else { - intPos[p_i2c->num]++; - intPos[p_i2c->num] %= INTBUFFMAX; - intBuff[intPos[p_i2c->num]][0][p_i2c->num] = (1<<16) | activeInt; - intBuff[intPos[p_i2c->num]][1][p_i2c->num] = 0; - } - - intBuff[intPos[p_i2c->num]][2][p_i2c->num] = xTaskGetTickCountFromISR(); // when IRQ fired - #endif - - if (activeInt & I2C_TRANS_START_INT_ST_M) { - if(p_i2c->stage==I2C_STARTUP) { - p_i2c->stage=I2C_RUNNING; - } - - activeInt &=~I2C_TRANS_START_INT_ST_M; - p_i2c->dev->int_ena.trans_start = 1; // already enabled? why Again? - p_i2c->dev->int_clr.trans_start = 1; // so that will trigger after next 'END' - } - - if (activeInt & I2C_TXFIFO_EMPTY_INT_ST) {//should this be before Trans_start? - fillTxFifo(p_i2c); //fillTxFifo will enable/disable/clear interrupt - activeInt&=~I2C_TXFIFO_EMPTY_INT_ST; - } - - if(activeInt & I2C_RXFIFO_FULL_INT_ST) { - emptyRxFifo(p_i2c); - p_i2c->dev->int_clr.rx_fifo_full=1; - p_i2c->dev->int_ena.rx_fifo_full=1; //why? - - activeInt &=~I2C_RXFIFO_FULL_INT_ST; - } - - if(activeInt & I2C_RXFIFO_OVF_INT_ST) { - emptyRxFifo(p_i2c); - p_i2c->dev->int_clr.rx_fifo_full=1; - p_i2c->dev->int_ena.rx_fifo_full=1; //why? - - activeInt &=~I2C_RXFIFO_OVF_INT_ST; - } - - if (activeInt & I2C_ACK_ERR_INT_ST_M) {//fatal error, abort i2c service - if (p_i2c->mode == I2C_MASTER) { - i2c_update_error_byte_cnt(p_i2c); // calc which byte caused ack Error, check if address or data - if(p_i2c->errorByteCnt < 0 ) { // address - i2cIsrExit(p_i2c,EVENT_ERROR_NAK,true); - } else { - i2cIsrExit(p_i2c,EVENT_ERROR_DATA_NAK,true); //data - } - } - return; - } - - if (activeInt & I2C_TIME_OUT_INT_ST_M) { - // let Gross timeout occur, Slave may release SCL before the configured timeout expires - // the Statemachine only has a 13.1ms max timout, some Devices >500ms - p_i2c->dev->int_clr.time_out =1; - activeInt &=~I2C_TIME_OUT_INT_ST; - // since a timeout occurred, capture the rxFifo data - emptyRxFifo(p_i2c); - p_i2c->dev->int_clr.rx_fifo_full=1; - p_i2c->dev->int_ena.rx_fifo_full=1; //why? - - } - - if (activeInt & I2C_TRANS_COMPLETE_INT_ST_M) { - p_i2c->dev->int_clr.trans_complete = 1; - i2cIsrExit(p_i2c,EVENT_DONE,false); - return; // no more work to do - /* - // how does slave mode act? - if (p_i2c->mode == I2C_SLAVE) { // STOP detected - // empty fifo - // dispatch callback - */ - } - - if (activeInt & I2C_ARBITRATION_LOST_INT_ST_M) { //fatal - i2cIsrExit(p_i2c,EVENT_ERROR_ARBITRATION,true); - return; // no more work to do - } - - if (activeInt & I2C_SLAVE_TRAN_COMP_INT_ST_M) { - p_i2c->dev->int_clr.slave_tran_comp = 1; - // need to complete this ! - } - - if (activeInt & I2C_END_DETECT_INT_ST_M) { - p_i2c->dev->int_ena.end_detect = 0; - p_i2c->dev->int_clr.end_detect = 1; - p_i2c->dev->ctr.trans_start=0; - fillCmdQueue(p_i2c,true); // enable interrupts - p_i2c->dev->ctr.trans_start=1; // go for it - activeInt&=~I2C_END_DETECT_INT_ST_M; - } - - if(activeInt) { // clear unhandled if possible? What about Disabling interrupt? - p_i2c->dev->int_clr.val = activeInt; - log_e("unknown int=%x",activeInt); - // disable unhandled IRQ, - p_i2c->dev->int_ena.val = p_i2c->dev->int_ena.val & (~activeInt); - } - -// activeInt = p_i2c->dev->int_status.val; // start all over if another interrupt happened -// 01AUG2018 if another interrupt happened, the OS will schedule another interrupt -// this is the source of spurious interrupts - } -} - -/* Stickbreaker added for ISR 11/2017 -functional with Silicon date=0x16042000 - */ -static i2c_err_t i2cAddQueue(i2c_t * i2c,uint8_t mode, uint16_t i2cDeviceAddr, uint8_t *dataPtr, uint16_t dataLen,bool sendStop, bool dataOnly, EventGroupHandle_t event) -{ - // need to grab a MUTEX for exclusive Queue, - // what about if ISR is running? - - if(i2c==NULL) { - return I2C_ERROR_DEV; - } - - I2C_DATA_QUEUE_t dqx; - dqx.data = dataPtr; - dqx.length = dataLen; - dqx.position = 0; - dqx.cmdBytesNeeded = dataLen; - dqx.ctrl.val = 0; - if( dataOnly) { - /* special case to add a queue data only element. - START and devAddr will not be sent, this dq element can have a STOP. - allows multiple buffers to be used for one transaction. - sequence: normal transaction(sendStop==false), [dataonly(sendStop==false)],dataOnly(sendStop==true) - *** Currently only works with WRITE, final byte NAK an READ will cause a fail between dq buffer elements. (in progress 30JUL2018) - */ - dqx.ctrl.startCmdSent = 1; // mark as already sent - dqx.ctrl.addrCmdSent = 1; + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); } else { - dqx.ctrl.addrReq = ((i2cDeviceAddr&0xFC00)==0x7800)?2:1; // 10bit or 7bit address - } - dqx.ctrl.addr = i2cDeviceAddr; - dqx.ctrl.mode = mode; - dqx.ctrl.stop= sendStop; - dqx.queueEvent = event; - - if(event) { // an eventGroup exist, so, initialize it - xEventGroupClearBits(event, EVENT_MASK); // all of them - } - - if(i2c->dq!=NULL) { // expand - //log_i("expand"); - I2C_DATA_QUEUE_t* tq =(I2C_DATA_QUEUE_t*)realloc(i2c->dq,sizeof(I2C_DATA_QUEUE_t)*(i2c->queueCount +1)); - if(tq!=NULL) { // ok - i2c->dq = tq; - memmove(&i2c->dq[i2c->queueCount++],&dqx,sizeof(I2C_DATA_QUEUE_t)); - } else { // bad stuff, unable to allocate more memory! - log_e("realloc Failure"); - return I2C_ERROR_MEMORY; - } - } else { // first Time - //log_i("new"); - i2c->queueCount=0; - i2c->dq =(I2C_DATA_QUEUE_t*)malloc(sizeof(I2C_DATA_QUEUE_t)); - if(i2c->dq!=NULL) { - memmove(&i2c->dq[i2c->queueCount++],&dqx,sizeof(I2C_DATA_QUEUE_t)); - } else { - log_e("malloc failure"); - return I2C_ERROR_MEMORY; - } - } - return I2C_ERROR_OK; -} - -i2c_err_t i2cAddQueueWrite(i2c_t * i2c, uint16_t i2cDeviceAddr, uint8_t *dataPtr, uint16_t dataLen,bool sendStop,EventGroupHandle_t event) -{ - return i2cAddQueue(i2c,0,i2cDeviceAddr,dataPtr,dataLen,sendStop,false,event); -} - -i2c_err_t i2cAddQueueRead(i2c_t * i2c, uint16_t i2cDeviceAddr, uint8_t *dataPtr, uint16_t dataLen,bool sendStop,EventGroupHandle_t event) -{ - //10bit read is kind of weird, first you do a 0byte Write with 10bit - // address, then a ReSTART then a 7bit Read using the the upper 7bit + - // readBit. - - // this might cause an internal register pointer problem with 10bit - // devices, But, Don't have any to test against. - // this is the Industry Standard specification. - - if((i2cDeviceAddr &0xFC00)==0x7800) { // ten bit read - i2c_err_t err = i2cAddQueue(i2c,0,i2cDeviceAddr,NULL,0,false,false,event); - if(err==I2C_ERROR_OK) { - return i2cAddQueue(i2c,1,(i2cDeviceAddr>>8),dataPtr,dataLen,sendStop,false,event); - } else { - return err; + err = i2c_driver_delete((i2c_port_t)i2c_num); + if(err == ESP_OK){ + bus[i2c_num].initialized = false; } } - return i2cAddQueue(i2c,1,i2cDeviceAddr,dataPtr,dataLen,sendStop,false,event); +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); +#endif + return err; } -i2c_err_t i2cProcQueue(i2c_t * i2c, uint32_t *readCount, uint16_t timeOutMillis) -{ - /* do the hard stuff here - install ISR if necessary - setup EventGroup - handle bus busy? - */ - //log_e("procQueue i2c=%p",&i2c); - if(readCount){ //total reads accomplished in all queue elements - *readCount = 0; - } - if(i2c == NULL) { - return I2C_ERROR_DEV; - } - if(i2c->debugFlags & 0xff000000) i2cTriggerDumps(i2c,(i2c->debugFlags>>24),"before ProcQueue"); - if (i2c->dev->status_reg.bus_busy) { // return error, let TwoWire() handle resetting the hardware. - /* if multi master then this if should be changed to this 03/12/2018 - if(multiMaster){// try to let the bus clear by its self - uint32_t timeOutTick = millis(); - while((i2c->dev->status_reg.bus_busy)&&(millis()-timeOutTickdev->status_reg.bus_busy){ // still busy, so die - */ - log_i("Bus busy, reinit"); - return I2C_ERROR_BUSY; +esp_err_t i2cWrite(uint8_t i2c_num, uint16_t address, const uint8_t* buff, size_t size, uint32_t timeOutMillis){ + esp_err_t ret = ESP_FAIL; + i2c_cmd_handle_t cmd = NULL; + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - - I2C_MUTEX_LOCK(); - /* what about co-existence with SLAVE mode? - Should I check if a slaveMode xfer is in progress and hang - until it completes? - if i2c->stage == I2C_RUNNING or I2C_SLAVE_ACTIVE - */ - i2c->stage = I2C_DONE; // until ready - -#if (ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO) && (defined ENABLE_I2C_DEBUG_BUFFER) - for(uint16_t i=0; inum] = 0; - intBuff[i][1][i2c->num] = 0; - intBuff[i][2][i2c->num] = 0; +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(bus[i2c_num].lock == NULL || xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return ret; } - intPos[i2c->num] = 0; - fifoPos = 0; - memset(fifoBuffer,0,FIFOMAX); #endif - // EventGroup is used to signal transmission completion from ISR - // not always reliable. Sometimes, the FreeRTOS scheduler is maxed out and refuses request - // if that happens, this call hangs until the timeout period expires, then it continues. - if(!i2c->i2c_event) { - i2c->i2c_event = xEventGroupCreate(); - } - if(i2c->i2c_event) { - xEventGroupClearBits(i2c->i2c_event, 0xFF); - } else { // failed to create EventGroup - log_e("eventCreate failed=%p",i2c->i2c_event); - I2C_MUTEX_UNLOCK(); - return I2C_ERROR_MEMORY; - } - - i2c_err_t reason = I2C_ERROR_OK; - i2c->mode = I2C_MASTER; - i2c->dev->ctr.trans_start=0; // Pause Machine - i2c->dev->timeout.tout = 0xFFFFF; // max 13ms - i2c->dev->int_clr.val = 0x1FFF; // kill them All! - - i2c->dev->ctr.ms_mode = 1; // master! - i2c->queuePos=0; - i2c->errorByteCnt=0; - i2c->errorQueue = 0; - uint32_t totalBytes=0; // total number of bytes to be Moved! - // convert address field to required I2C format - while(i2c->queuePos < i2c->queueCount) { // need to push these address modes upstream, to AddQueue - I2C_DATA_QUEUE_t *tdq = &i2c->dq[i2c->queuePos++]; - uint16_t taddr=0; - if(tdq->ctrl.addrReq ==2) { // 10bit address - taddr =((tdq->ctrl.addr >> 7) & 0xFE) - |tdq->ctrl.mode; - taddr = (taddr <<8) | (tdq->ctrl.addr&0xFF); - } else { // 7bit address - taddr = ((tdq->ctrl.addr<<1)&0xFE) - |tdq->ctrl.mode; - } - tdq->ctrl.addr = taddr; // all fixed with R/W bit - totalBytes += tdq->length + tdq->ctrl.addrReq; // total number of byte to be moved! + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); + goto end; } - i2c->queuePos=0; - - fillCmdQueue(i2c,false); // don't enable Tx/RX irq's - // start adding command[], END irq will keep it full - //Data Fifo will be filled after trans_start is issued - i2c->exitCode=0; - - I2C_FIFO_CONF_t f; - f.val = i2c->dev->fifo_conf.val; - f.rx_fifo_rst = 1; // fifo in reset - f.tx_fifo_rst = 1; // fifo in reset - f.nonfifo_en = 0; // use fifo mode - f.nonfifo_tx_thres = 31; - // need to adjust threshold based on I2C clock rate, at 100k, 30 usually works, - // sometimes the emptyRx() actually moves 31 bytes - // it hasn't overflowed yet, I cannot tell if the new byte is added while - // emptyRX() is executing or before? - // let i2cSetFrequency() set thrhds - // f.rx_fifo_full_thrhd = 30; // 30 bytes before INT is issued - // f.tx_fifo_empty_thrhd = 0; - f.fifo_addr_cfg_en = 0; // no directed access - i2c->dev->fifo_conf.val = f.val; // post them all - - f.rx_fifo_rst = 0; // release fifo - f.tx_fifo_rst = 0; - i2c->dev->fifo_conf.val = f.val; // post them all - - i2c->stage = I2C_STARTUP; // everything configured, now start the I2C StateMachine, and - // As soon as interrupts are enabled, the ISR will start handling them. - // it should receive a TXFIFO_EMPTY immediately, even before it - // receives the TRANS_START - - uint32_t interruptsEnabled = - I2C_ACK_ERR_INT_ENA | // (BIT(10)) Causes Fatal Error Exit - I2C_TRANS_START_INT_ENA | // (BIT(9)) Triggered by trans_start=1, initial,END - I2C_TIME_OUT_INT_ENA | //(BIT(8)) Trigger by SLAVE SCL stretching, NOT an ERROR - I2C_TRANS_COMPLETE_INT_ENA | // (BIT(7)) triggered by STOP, successful exit - I2C_ARBITRATION_LOST_INT_ENA | // (BIT(5)) cause fatal error exit - I2C_SLAVE_TRAN_COMP_INT_ENA | // (BIT(4)) unhandled - I2C_END_DETECT_INT_ENA | // (BIT(3)) refills cmd[] list - I2C_RXFIFO_OVF_INT_ENA | //(BIT(2)) unhandled - I2C_TXFIFO_EMPTY_INT_ENA | // (BIT(1)) triggers fillTxFifo() - I2C_RXFIFO_FULL_INT_ENA; // (BIT(0)) trigger emptyRxFifo() - - i2c->dev->int_ena.val = interruptsEnabled; - - if(!i2c->intr_handle) { // create ISR for either peripheral - // log_i("create ISR %d",i2c->num); - uint32_t ret = 0; - uint32_t flags = ARDUINO_ISR_FLAG | //< ISR can be called if cache is disabled - ESP_INTR_FLAG_LOWMED | //< Low and medium prio interrupts. These can be handled in C. - ESP_INTR_FLAG_SHARED; //< Reduce resource requirements, Share interrupts - - if(i2c->num) { - ret = esp_intr_alloc_intrstatus(ETS_I2C_EXT1_INTR_SOURCE, flags, (uint32_t)&i2c->dev->int_status.val, interruptsEnabled, &i2c_isr_handler_default,i2c, &i2c->intr_handle); - } else { - ret = esp_intr_alloc_intrstatus(ETS_I2C_EXT0_INTR_SOURCE, flags, (uint32_t)&i2c->dev->int_status.val, interruptsEnabled, &i2c_isr_handler_default,i2c, &i2c->intr_handle); - } - - if(ret!=ESP_OK) { - log_e("install interrupt handler Failed=%d",ret); - I2C_MUTEX_UNLOCK(); - return I2C_ERROR_MEMORY; - } - if( !addApbChangeCallback( i2c, i2cApbChangeCallback)) { - log_e("install apb Callback failed"); - I2C_MUTEX_UNLOCK(); - return I2C_ERROR_DEV; - } + //short implementation does not support zero size writes (example when scanning) PR in IDF? + //ret = i2c_master_write_to_device((i2c_port_t)i2c_num, address, buff, size, timeOutMillis / portTICK_RATE_MS); + ret = ESP_OK; + uint8_t cmd_buff[I2C_LINK_RECOMMENDED_SIZE(1)] = { 0 }; + cmd = i2c_cmd_link_create_static(cmd_buff, I2C_LINK_RECOMMENDED_SIZE(1)); + ret = i2c_master_start(cmd); + if (ret != ESP_OK) { + goto end; } - //hang until it completes. - - // how many ticks should it take to transfer totalBytes through the I2C hardware, - // add user supplied timeOutMillis to Calculated Value - - portTickType ticksTimeOut = ((totalBytes*10*1000)/(i2cGetFrequency(i2c))+timeOutMillis)/portTICK_PERIOD_MS; - - i2c->dev->ctr.trans_start=1; // go for it - -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_DEBUG - portTickType tBefore=xTaskGetTickCount(); -#endif - - // wait for ISR to complete the transfer, or until timeOut in case of bus fault, hardware problem - - uint32_t eBits = xEventGroupWaitBits(i2c->i2c_event,EVENT_DONE,pdFALSE,pdTRUE,ticksTimeOut); - -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_DEBUG - portTickType tAfter=xTaskGetTickCount(); -#endif - - - // if xEventGroupSetBitsFromISR() failed, the ISR could have succeeded but never been - // able to mark the success - - if(i2c->exitCode!=eBits) { // try to recover from O/S failure - // log_e("EventGroup Failed:%p!=%p",eBits,i2c->exitCode); - eBits=i2c->exitCode; - } - if((eBits&EVENT_ERROR)||(!(eBits & EVENT_DONE))){ // need accurate errorByteCnt for debug - i2c_update_error_byte_cnt(i2c); - } - - if(!(eBits==EVENT_DONE)&&(eBits&~(EVENT_ERROR_NAK|EVENT_ERROR_DATA_NAK|EVENT_ERROR|EVENT_DONE))) { // not only Done, therefore error, exclude ADDR NAK, DATA_NAK -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_INFO - i2cDumpI2c(i2c); - i2cDumpInts(i2c->num); -#endif - } - - if(eBits&EVENT_DONE) { // no gross timeout - switch(i2c->error) { - case I2C_OK : - reason = I2C_ERROR_OK; - break; - case I2C_ERROR : - reason = I2C_ERROR_DEV; - break; - case I2C_ADDR_NAK: - reason = I2C_ERROR_ACK; - break; - case I2C_DATA_NAK: - reason = I2C_ERROR_ACK; - break; - case I2C_ARBITRATION: - reason = I2C_ERROR_BUS; - break; - case I2C_TIMEOUT: - reason = I2C_ERROR_TIMEOUT; - break; - default : - reason = I2C_ERROR_DEV; - } - } else { // GROSS timeout, shutdown ISR , report Timeout - i2c->stage = I2C_DONE; - i2c->dev->int_ena.val =0; - i2c->dev->int_clr.val = 0x1FFF; - i2c_update_error_byte_cnt(i2c); - if((i2c->errorByteCnt == 0)&&(i2c->errorQueue==0)) { // Bus Busy no bytes Moved - reason = I2C_ERROR_BUSY; - eBits = eBits | EVENT_ERROR_BUS_BUSY|EVENT_ERROR|EVENT_DONE; -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_DEBUG - log_d(" Busy Timeout start=0x%x, end=0x%x, =%d, max=%d error=%d",tBefore,tAfter,(tAfter-tBefore),ticksTimeOut,i2c->error); - i2cDumpI2c(i2c); - i2cDumpInts(i2c->num); -#endif - } else { // just a timeout, some data made it out or in. - reason = I2C_ERROR_TIMEOUT; - eBits = eBits | EVENT_ERROR_TIMEOUT|EVENT_ERROR|EVENT_DONE; - -#if ARDUHAL_LOG_LEVEL >= ARDUHAL_LOG_LEVEL_DEBUG - log_d(" Gross Timeout Dead start=0x%x, end=0x%x, =%d, max=%d error=%d",tBefore,tAfter,(tAfter-tBefore),ticksTimeOut,i2c->error); - i2cDumpI2c(i2c); - i2cDumpInts(i2c->num); -#endif - } - } - - /* offloading all EventGroups to dispatch, EventGroups in ISR is not always successful - 11/20/2017 - if error, need to trigger all succeeding dataQueue events with the EVENT_ERROR_PREV - 07/22/2018 - Need to use the queueEvent value to identify transaction blocks, if an error occurs, - all subsequent queue items with the same queueEvent value will receive the EVENT_ERROR_PREV. - But, ProcQue should re-queue queue items that have a different queueEvent value(different transaction) - This change will support multi-thread i2c usage. Use the queueEvent as the transaction event - identifier. - */ - uint32_t b = 0; - - while(b < i2c->queueCount) { - if(i2c->dq[b].ctrl.mode==1 && readCount) { - *readCount += i2c->dq[b].position; // number of data bytes received - } - if(b < i2c->queuePos) { // before any error - if(i2c->dq[b].queueEvent) { // this data queue element has an EventGroup - xEventGroupSetBits(i2c->dq[b].queueEvent,EVENT_DONE); - } - } else if(b == i2c->queuePos) { // last processed queue - if(i2c->dq[b].queueEvent) { // this data queue element has an EventGroup - xEventGroupSetBits(i2c->dq[b].queueEvent,eBits); - } - } else { // never processed queues - if(i2c->dq[b].queueEvent) { // this data queue element has an EventGroup - xEventGroupSetBits(i2c->dq[b].queueEvent,eBits|EVENT_ERROR_PREV); - } - } - b++; - } - if(i2c->debugFlags & 0x00ff0000) i2cTriggerDumps(i2c,(i2c->debugFlags>>16),"after ProcQueue"); - - I2C_MUTEX_UNLOCK(); - return reason; -} - -static void i2cReleaseISR(i2c_t * i2c) -{ - if(i2c->intr_handle) { - esp_intr_free(i2c->intr_handle); - i2c->intr_handle=NULL; - if (!removeApbChangeCallback( i2c, i2cApbChangeCallback)) { - log_e("unable to release apbCallback"); - } - } -} - -static bool i2cCheckLineState(int8_t sda, int8_t scl){ - if(sda < 0 || scl < 0){ - return false;//return false since there is nothing to do + ret = i2c_master_write_byte(cmd, (address << 1) | I2C_MASTER_WRITE, true); + if (ret != ESP_OK) { + goto end; } - // if the bus is not 'clear' try the cycling SCL until SDA goes High or 9 cycles - digitalWrite(sda, HIGH); - digitalWrite(scl, HIGH); - pinMode(sda, PULLUP|OPEN_DRAIN|INPUT); - pinMode(scl, PULLUP|OPEN_DRAIN|OUTPUT); - - if(!digitalRead(sda) || !digitalRead(scl)) { // bus in busy state - log_w("invalid state sda(%d)=%d, scl(%d)=%d", sda, digitalRead(sda), scl, digitalRead(scl)); - digitalWrite(scl, HIGH); - for(uint8_t a=0; a<9; a++) { - delayMicroseconds(5); - digitalWrite(scl, LOW); - delayMicroseconds(5); - digitalWrite(scl, HIGH); - if(digitalRead(sda)){ // bus recovered - log_d("Recovered after %d Cycles",a+1); - break; - } + if(size){ + ret = i2c_master_write(cmd, buff, size, true); + if (ret != ESP_OK) { + goto end; } } - - if(!digitalRead(sda) || !digitalRead(scl)) { // bus in busy state - log_e("Bus Invalid State, TwoWire() Can't init sda=%d, scl=%d",digitalRead(sda),digitalRead(scl)); - return false; // bus is busy - } - return true; -} - -i2c_err_t i2cAttachSCL(i2c_t * i2c, int8_t scl) -{ - if(i2c == NULL) { - return I2C_ERROR_DEV; - } - digitalWrite(scl, HIGH); - pinMode(scl, OPEN_DRAIN | PULLUP | INPUT | OUTPUT); - pinMatrixOutAttach(scl, I2C_SCL_IDX(i2c->num), false, false); - pinMatrixInAttach(scl, I2C_SCL_IDX(i2c->num), false); - return I2C_ERROR_OK; -} - -i2c_err_t i2cDetachSCL(i2c_t * i2c, int8_t scl) -{ - if(i2c == NULL) { - return I2C_ERROR_DEV; - } - pinMatrixOutDetach(scl, false, false); - pinMatrixInDetach(I2C_SCL_IDX(i2c->num), false, false); - pinMode(scl, INPUT | PULLUP); - return I2C_ERROR_OK; -} - -i2c_err_t i2cAttachSDA(i2c_t * i2c, int8_t sda) -{ - if(i2c == NULL) { - return I2C_ERROR_DEV; + ret = i2c_master_stop(cmd); + if (ret != ESP_OK) { + goto end; } - digitalWrite(sda, HIGH); - pinMode(sda, OPEN_DRAIN | PULLUP | INPUT | OUTPUT ); - pinMatrixOutAttach(sda, I2C_SDA_IDX(i2c->num), false, false); - pinMatrixInAttach(sda, I2C_SDA_IDX(i2c->num), false); - return I2C_ERROR_OK; -} + ret = i2c_master_cmd_begin((i2c_port_t)i2c_num, cmd, timeOutMillis / portTICK_RATE_MS); -i2c_err_t i2cDetachSDA(i2c_t * i2c, int8_t sda) -{ - if(i2c == NULL) { - return I2C_ERROR_DEV; +end: + if(cmd != NULL){ + i2c_cmd_link_delete_static(cmd); } - pinMatrixOutDetach(sda, false, false); - pinMatrixInDetach(I2C_SDA_IDX(i2c->num), false, false); - pinMode(sda, INPUT | PULLUP); - return I2C_ERROR_OK; -} - -/* - * PUBLIC API - * */ -// 24Nov17 only supports Master Mode -i2c_t * i2cInit(uint8_t i2c_num, int8_t sda, int8_t scl, uint32_t frequency) { -#ifdef ENABLE_I2C_DEBUG_BUFFER - log_v("num=%d sda=%d scl=%d freq=%d",i2c_num, sda, scl, frequency); +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); #endif - if(i2c_num > 1) { - return NULL; - } - - i2c_t * i2c = &_i2c_bus_array[i2c_num]; + return ret; +} - // pins should be detached, else glitch - if(i2c->sda >= 0){ - i2cDetachSDA(i2c, i2c->sda); - } - if(i2c->scl >= 0){ - i2cDetachSCL(i2c, i2c->scl); +esp_err_t i2cRead(uint8_t i2c_num, uint16_t address, uint8_t* buff, size_t size, uint32_t timeOutMillis, size_t *readCount){ + esp_err_t ret = ESP_FAIL; + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - i2c->sda = sda; - i2c->scl = scl; - #if !CONFIG_DISABLE_HAL_LOCKS - if(i2c->lock == NULL) { - i2c->lock = xSemaphoreCreateRecursiveMutex(); - if(i2c->lock == NULL) { - return NULL; - } + //acquire lock + if(bus[i2c_num].lock == NULL || xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return ret; } #endif - I2C_MUTEX_LOCK(); - - i2cReleaseISR(i2c); // ISR exists, release it before disabling hardware - - if(frequency == 0) {// don't change existing frequency - frequency = i2cGetFrequency(i2c); - if(frequency == 0) { - frequency = 100000L; // default to 100khz - } - } - - if(i2c_num == 0) { - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT0_RST); //reset hardware - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG,DPORT_I2C_EXT0_CLK_EN); - DPORT_CLEAR_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT0_RST);// release reset + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); } else { - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT1_RST); //reset Hardware - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG,DPORT_I2C_EXT1_CLK_EN); - DPORT_CLEAR_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT1_RST); - } - i2c->dev->ctr.val = 0; - i2c->dev->ctr.ms_mode = 1; - i2c->dev->ctr.sda_force_out = 1 ; - i2c->dev->ctr.scl_force_out = 1 ; - i2c->dev->ctr.clk_en = 1; - - //the max clock number of receiving a data - i2c->dev->timeout.tout = 400000;//clocks max=1048575 - //disable apb nonfifo access - i2c->dev->fifo_conf.nonfifo_en = 0; - - i2c->dev->slave_addr.val = 0; - I2C_MUTEX_UNLOCK(); - - i2cSetFrequency(i2c, frequency); // reconfigure - - if(!i2cCheckLineState(i2c->sda, i2c->scl)){ - return NULL; - } - - if(i2c->sda >= 0){ - i2cAttachSDA(i2c, i2c->sda); - } - if(i2c->scl >= 0){ - i2cAttachSCL(i2c, i2c->scl); + ret = i2c_master_read_from_device((i2c_port_t)i2c_num, address, buff, size, timeOutMillis / portTICK_RATE_MS); + if(ret == ESP_OK){ + *readCount = size; + } else { + *readCount = 0; + } } - return i2c; +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); +#endif + return ret; } -void i2cRelease(i2c_t *i2c) // release all resources, power down peripheral -{ - I2C_MUTEX_LOCK(); - - if(i2c->sda >= 0){ - i2cDetachSDA(i2c, i2c->sda); - } - if(i2c->scl >= 0){ - i2cDetachSCL(i2c, i2c->scl); +esp_err_t i2cWriteReadNonStop(uint8_t i2c_num, uint16_t address, const uint8_t* wbuff, size_t wsize, uint8_t* rbuff, size_t rsize, uint32_t timeOutMillis, size_t *readCount){ + esp_err_t ret = ESP_FAIL; + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - - i2cReleaseISR(i2c); - - if(i2c->i2c_event) { - vEventGroupDelete(i2c->i2c_event); - i2c->i2c_event = NULL; +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(bus[i2c_num].lock == NULL || xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return ret; } - - i2cFlush(i2c); - - // reset the I2C hardware and shut off the clock, power it down. - if(i2c->num == 0) { - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT0_RST); //reset hardware - DPORT_CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG,DPORT_I2C_EXT0_CLK_EN); // shutdown hardware +#endif + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); } else { - DPORT_SET_PERI_REG_MASK(DPORT_PERIP_RST_EN_REG,DPORT_I2C_EXT1_RST); //reset Hardware - DPORT_CLEAR_PERI_REG_MASK(DPORT_PERIP_CLK_EN_REG,DPORT_I2C_EXT1_CLK_EN); // shutdown Hardware - } - - I2C_MUTEX_UNLOCK(); -} - -i2c_err_t i2cFlush(i2c_t * i2c) -{ - if(i2c==NULL) { - return I2C_ERROR_DEV; - } - i2cTriggerDumps(i2c,i2c->debugFlags & 0xff, "FLUSH"); - - // need to grab a MUTEX for exclusive Queue, - // what out if ISR is running? - i2c_err_t rc=I2C_ERROR_OK; - if(i2c->dq!=NULL) { - // log_i("free"); - // what about EventHandle? - free(i2c->dq); - i2c->dq = NULL; - } - i2c->queueCount=0; - i2c->queuePos=0; - // release Mutex - return rc; -} - -i2c_err_t i2cWrite(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis){ - if((i2c==NULL)||((size>0)&&(buff==NULL))) { // need to have location to store requested data - return I2C_ERROR_DEV; - } - i2c_err_t last_error = i2cAddQueueWrite(i2c, address, buff, size, sendStop, NULL); - - if(last_error == I2C_ERROR_OK) { //queued - if(sendStop) { //now actually process the queued commands, including READs - last_error = i2cProcQueue(i2c, NULL, timeOutMillis); - if(last_error == I2C_ERROR_BUSY) { // try to clear the bus - if(i2cInit(i2c->num, i2c->sda, i2c->scl, 0)) { - last_error = i2cProcQueue(i2c, NULL, timeOutMillis); - } - } - i2cFlush(i2c); - } else { // stop not received, so wait for I2C stop, - last_error = I2C_ERROR_CONTINUE; - } - } - return last_error; -} - -i2c_err_t i2cRead(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis, uint32_t *readCount){ - if((size == 0)||(i2c == NULL)||(buff==NULL)){ // hardware will hang if no data requested on READ - return I2C_ERROR_DEV; - } - i2c_err_t last_error=i2cAddQueueRead(i2c, address, buff, size, sendStop, NULL); - - if(last_error == I2C_ERROR_OK) { //queued - if(sendStop) { //now actually process the queued commands, including READs - last_error = i2cProcQueue(i2c, readCount, timeOutMillis); - if(last_error == I2C_ERROR_BUSY) { // try to clear the bus - if(i2cInit(i2c->num, i2c->sda, i2c->scl, 0)) { - last_error = i2cProcQueue(i2c, readCount, timeOutMillis); - } - } - i2cFlush(i2c); - } else { // stop not received, so wait for I2C stop, - last_error = I2C_ERROR_CONTINUE; + ret = i2c_master_write_read_device((i2c_port_t)i2c_num, address, wbuff, wsize, rbuff, rsize, timeOutMillis / portTICK_RATE_MS); + if(ret == ESP_OK){ + *readCount = rsize; + } else { + *readCount = 0; } } - return last_error; +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); +#endif + return ret; } -#define MIN_I2C_CLKS 100 // minimum ratio between cpu and i2c Bus clocks -#define INTERRUPT_CYCLE_OVERHEAD 16000 // number of cpu clocks necessary to respond to interrupt -i2c_err_t i2cSetFrequency(i2c_t * i2c, uint32_t clk_speed) -{ - if(i2c == NULL) { - return I2C_ERROR_DEV; - } - uint32_t apb = getApbFrequency(); - uint32_t period = (apb/clk_speed) / 2; - - if((apb/8192 > clk_speed)||(apb/MIN_I2C_CLKS < clk_speed)){ //out of bounds - log_d("i2c freq(%d) out of bounds.vs APB Clock(%d), min=%d, max=%d",clk_speed,apb,(apb/8192),(apb/MIN_I2C_CLKS)); +esp_err_t i2cSetClock(uint8_t i2c_num, uint32_t frequency){ + esp_err_t ret = ESP_FAIL; + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - if(period < (MIN_I2C_CLKS/2) ){ - period = (MIN_I2C_CLKS/2); - clk_speed = apb/(period*2); - log_d("APB Freq too slow, Reducing i2c Freq to %d Hz",clk_speed); - } else if ( period> 4095) { - period = 4095; - clk_speed = apb/(period*2); - log_d("APB Freq too fast, Increasing i2c Freq to %d Hz",clk_speed); +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(bus[i2c_num].lock == NULL || xSemaphoreTake(bus[i2c_num].lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return ret; } -#ifdef ENABLE_I2C_DEBUG_BUFFER - log_v("freq=%dHz",clk_speed); -#endif - uint32_t halfPeriod = period/2; - uint32_t quarterPeriod = period/4; - - I2C_MUTEX_LOCK(); - - I2C_FIFO_CONF_t f; - - f.val = i2c->dev->fifo_conf.val; -/* Adjust Fifo thresholds based on differential between cpu frequency and bus clock. - The fifo_delta is calculated such that at least INTERRUPT_CYCLE_OVERHEAD cpu clocks are - available when a Fifo interrupt is triggered. This allows enough room in the Fifo so that - interrupt latency does not cause a Fifo overflow/underflow event. -*/ -#ifdef ENABLE_I2C_DEBUG_BUFFER - log_v("cpu Freq=%dMhz, i2c Freq=%dHz",getCpuFrequencyMhz(),clk_speed); -#endif - uint32_t fifo_delta = (INTERRUPT_CYCLE_OVERHEAD/((getCpuFrequencyMhz()*1000000 / clk_speed)*10))+1; - if (fifo_delta > 24) fifo_delta=24; - f.rx_fifo_full_thrhd = 32 - fifo_delta; - f.tx_fifo_empty_thrhd = fifo_delta; - i2c->dev->fifo_conf.val = f.val; // set thresholds -#ifdef ENABLE_I2C_DEBUG_BUFFER - log_v("Fifo delta=%d",fifo_delta); #endif - //the clock num during SCL is low level - i2c->dev->scl_low_period.period = period; - //the clock num during SCL is high level - i2c->dev->scl_high_period.period = period; - - //the clock num between the negedge of SDA and negedge of SCL for start mark - i2c->dev->scl_start_hold.time = halfPeriod; - //the clock num between the posedge of SCL and the negedge of SDA for restart mark - i2c->dev->scl_rstart_setup.time = halfPeriod; - - //the clock num after the STOP bit's posedge - i2c->dev->scl_stop_hold.time = halfPeriod; - //the clock num between the posedge of SCL and the posedge of SDA - i2c->dev->scl_stop_setup.time = halfPeriod; - - //the clock num I2C used to hold the data after the negedge of SCL. - i2c->dev->sda_hold.time = quarterPeriod; - //the clock num I2C used to sample data on SDA after the posedge of SCL - i2c->dev->sda_sample.time = quarterPeriod; - I2C_MUTEX_UNLOCK(); - return I2C_ERROR_OK; -} + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); + goto end; + } + if(bus[i2c_num].frequency == frequency){ + ret = ESP_OK; + goto end; + } + if(!frequency){ + frequency = 100000UL; + } else if(frequency > 1000000UL){ + frequency = 1000000UL; + } + // Freq limitation when using different clock sources + #define I2C_CLK_LIMIT_REF_TICK (1 * 1000 * 1000 / 20) /*!< Limited by REF_TICK, no more than REF_TICK/20*/ + #define I2C_CLK_LIMIT_APB (80 * 1000 * 1000 / 20) /*!< Limited by APB, no more than APB/20*/ + #define I2C_CLK_LIMIT_RTC (20 * 1000 * 1000 / 20) /*!< Limited by RTC, no more than RTC/20*/ + #define I2C_CLK_LIMIT_XTAL (40 * 1000 * 1000 / 20) /*!< Limited by RTC, no more than XTAL/20*/ + + typedef struct { + uint8_t character; /*!< I2C source clock characteristic */ + uint32_t clk_freq; /*!< I2C source clock frequency */ + } i2c_clk_alloc_t; + + // i2c clock characteristic, The order is the same as i2c_sclk_t. + static i2c_clk_alloc_t i2c_clk_alloc[I2C_SCLK_MAX] = { + {0, 0}, + #if SOC_I2C_SUPPORT_APB + {0, I2C_CLK_LIMIT_APB}, /*!< I2C APB clock characteristic*/ + #endif + #if SOC_I2C_SUPPORT_XTAL + {0, I2C_CLK_LIMIT_XTAL}, /*!< I2C XTAL characteristic*/ + #endif + #if SOC_I2C_SUPPORT_RTC + {I2C_SCLK_SRC_FLAG_LIGHT_SLEEP | I2C_SCLK_SRC_FLAG_AWARE_DFS, I2C_CLK_LIMIT_RTC}, /*!< I2C 20M RTC characteristic*/ + #endif + #if SOC_I2C_SUPPORT_REF_TICK + {I2C_SCLK_SRC_FLAG_AWARE_DFS, I2C_CLK_LIMIT_REF_TICK}, /*!< I2C REF_TICK characteristic*/ + #endif + }; -uint32_t i2cGetFrequency(i2c_t * i2c) -{ - if(i2c == NULL) { - return 0; + i2c_sclk_t src_clk = I2C_SCLK_DEFAULT; + ret = ESP_OK; + for (i2c_sclk_t clk = I2C_SCLK_DEFAULT + 1; clk < I2C_SCLK_MAX; clk++) { +#if CONFIG_IDF_TARGET_ESP32S3 + if (clk == I2C_SCLK_RTC) { // RTC clock for s3 is unaccessable now. + continue; + } +#endif + if (frequency <= i2c_clk_alloc[clk].clk_freq) { + src_clk = clk; + break; + } } - uint32_t result = 0; - uint32_t old_count = (i2c->dev->scl_low_period.period+i2c->dev->scl_high_period.period); - if(old_count>0) { - result = getApbFrequency() / old_count; + if(src_clk == I2C_SCLK_MAX){ + log_e("clock source could not be selected"); + ret = ESP_FAIL; } else { - result = 0; - } - return result; -} - - -uint32_t i2cDebug(i2c_t * i2c, uint32_t setBits, uint32_t resetBits){ - if(i2c != NULL) { - i2c->debugFlags = ((i2c->debugFlags | setBits) & ~resetBits); - return i2c->debugFlags; - } - return 0; - - } - -uint32_t i2cGetStatus(i2c_t * i2c){ - if(i2c != NULL){ - return i2c->dev->status_reg.val; - } - else return 0; -} -#else -#include "driver/i2c.h" - -#define ACK_CHECK_EN 1 /*!< I2C master will check ack from slave*/ -#define ACK_CHECK_DIS 0 /*!< I2C master will not check ack from slave */ -#define ACK_VAL 0x0 /*!< I2C ack value */ -#define NACK_VAL 0x1 /*!< I2C nack value */ - -struct i2c_struct_t { - i2c_port_t num; -}; - -static i2c_t * i2c_ports[2] = {NULL, NULL}; - -i2c_t * i2cInit(uint8_t i2c_num, int8_t sda, int8_t scl, uint32_t clk_speed){ - if(i2c_num >= SOC_I2C_NUM){ - return NULL; - } - if(!clk_speed){ - //originally does not change the speed, but getFrequency and setFrequency need to be implemented first. - clk_speed = 100000; - } - i2c_t * out = NULL; - if(i2c_ports[i2c_num] == NULL){ - out = (i2c_t*)malloc(sizeof(i2c_t)); - if(out == NULL){ - log_e("malloc failed"); - return NULL; - } - out->num = (i2c_port_t)i2c_num; - i2c_ports[i2c_num] = out; - } else { - out = i2c_ports[i2c_num]; - i2c_driver_delete((i2c_port_t)i2c_num); - } - - i2c_config_t conf = { }; - conf.mode = I2C_MODE_MASTER; - conf.scl_io_num = (gpio_num_t)scl; - conf.sda_io_num = (gpio_num_t)sda; - conf.scl_pullup_en = GPIO_PULLUP_ENABLE; - conf.sda_pullup_en = GPIO_PULLUP_ENABLE; - conf.master.clk_speed = clk_speed; - esp_err_t ret = i2c_param_config(out->num, &conf); - if (ret != ESP_OK) { - log_e("i2c_param_config failed"); - free(out); - i2c_ports[i2c_num] = NULL; - return NULL; - } - ret = i2c_driver_install(out->num, conf.mode, 0, 0, 0); - if (ret != ESP_OK) { - log_e("i2c_driver_install failed"); - free(out); - i2c_ports[i2c_num] = NULL; - return NULL; + i2c_hal_context_t hal; + hal.dev = I2C_LL_GET_HW(i2c_num); + i2c_hal_set_bus_timing(&(hal), frequency, src_clk); + bus[i2c_num].frequency = frequency; } - return out; -} -i2c_err_t i2cWrite(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis){ - esp_err_t ret = ESP_OK; - i2c_cmd_handle_t cmd = i2c_cmd_link_create(); - i2c_master_start(cmd); - i2c_master_write_byte(cmd, (address << 1) | I2C_MASTER_WRITE, ACK_CHECK_EN); - if(size){ - i2c_master_write(cmd, buff, size, ACK_CHECK_EN); - } - //if send stop? - i2c_master_stop(cmd); - ret = i2c_master_cmd_begin(i2c->num, cmd, timeOutMillis / portTICK_RATE_MS); - i2c_cmd_link_delete(cmd); +end: +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(bus[i2c_num].lock); +#endif return ret; } -i2c_err_t i2cRead(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis, uint32_t *readCount){ - esp_err_t ret = ESP_OK; - i2c_cmd_handle_t cmd = i2c_cmd_link_create(); - i2c_master_start(cmd); - i2c_master_write_byte(cmd, (address << 1) | I2C_MASTER_READ, ACK_CHECK_EN); - if (size > 1) { - i2c_master_read(cmd, buff, size - 1, ACK_VAL); +esp_err_t i2cGetClock(uint8_t i2c_num, uint32_t * frequency){ + if(i2c_num >= SOC_I2C_NUM){ + return ESP_ERR_INVALID_ARG; } - i2c_master_read_byte(cmd, buff + size - 1, NACK_VAL); - i2c_master_stop(cmd); - ret = i2c_master_cmd_begin(i2c->num, cmd, timeOutMillis / portTICK_RATE_MS); - i2c_cmd_link_delete(cmd); - if(ret == ESP_OK){ - *readCount = size; + if(!bus[i2c_num].initialized){ + log_e("bus is not initialized"); + return ESP_FAIL; } - return ret; -} - -void i2cRelease(i2c_t *i2c){ - log_w(""); - return; -} -i2c_err_t i2cFlush(i2c_t *i2c){ - esp_err_t ret = i2c_reset_tx_fifo(i2c->num); - if(ret != ESP_OK){ - return ret; - } - return i2c_reset_rx_fifo(i2c->num); -} -i2c_err_t i2cSetFrequency(i2c_t * i2c, uint32_t clk_speed){ - log_w(""); + *frequency = bus[i2c_num].frequency; return ESP_OK; } -uint32_t i2cGetFrequency(i2c_t * i2c){ - log_w(""); - return 0; -} -uint32_t i2cGetStatus(i2c_t * i2c){ - log_w(""); - return 0; -} - -//Functions below should be used only if well understood -//Might be deprecated and removed in future -i2c_err_t i2cAttachSCL(i2c_t * i2c, int8_t scl){ - return ESP_FAIL; -} -i2c_err_t i2cDetachSCL(i2c_t * i2c, int8_t scl){ - return ESP_FAIL; -} -i2c_err_t i2cAttachSDA(i2c_t * i2c, int8_t sda){ - return ESP_FAIL; -} -i2c_err_t i2cDetachSDA(i2c_t * i2c, int8_t sda){ - return ESP_FAIL; -} - -#endif /* CONFIG_IDF_TARGET_ESP32 */ - -/* todo - 22JUL18 - need to add multi-thread capability, use dq.queueEvent as the group marker. When multiple threads - transactions are present in the same queue, and an error occurs, abort all succeeding unserviced transactions - with the same dq.queueEvent value. Succeeding unserviced transactions with different dq.queueEvent values - can be re-queued and processed independently. - 30JUL18 complete data only queue elements, this will allow transfers to use multiple data blocks, - */ - diff --git a/cores/esp32/esp32-hal-i2c.h b/cores/esp32/esp32-hal-i2c.h index 1a696aca7d6..3fa889fbefb 100644 --- a/cores/esp32/esp32-hal-i2c.h +++ b/cores/esp32/esp32-hal-i2c.h @@ -12,6 +12,7 @@ // See the License for the specific language governing permissions and // limitations under the License. // modified Nov 2017 by Chuck Todd to support Interrupt Driven I/O +// modified Nov 2021 by Hristo Gochkov to support ESP-IDF API #ifndef _ESP32_HAL_I2C_H_ #define _ESP32_HAL_I2C_H_ @@ -22,58 +23,16 @@ extern "C" { #include #include -#include "freertos/FreeRTOS.h" -#include "freertos/event_groups.h" - -// External Wire.h equivalent error Codes -typedef enum { - I2C_ERROR_OK=0, - I2C_ERROR_DEV, - I2C_ERROR_ACK, - I2C_ERROR_TIMEOUT, - I2C_ERROR_BUS, - I2C_ERROR_BUSY, - I2C_ERROR_MEMORY, - I2C_ERROR_CONTINUE, - I2C_ERROR_NO_BEGIN -} i2c_err_t; - -struct i2c_struct_t; -typedef struct i2c_struct_t i2c_t; - -i2c_t * i2cInit(uint8_t i2c_num, int8_t sda, int8_t scl, uint32_t clk_speed); -void i2cRelease(i2c_t *i2c); // free ISR, Free DQ, Power off peripheral clock. Must call i2cInit() to recover -i2c_err_t i2cWrite(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis); -i2c_err_t i2cRead(i2c_t * i2c, uint16_t address, uint8_t* buff, uint16_t size, bool sendStop, uint16_t timeOutMillis, uint32_t *readCount); -i2c_err_t i2cFlush(i2c_t *i2c); -i2c_err_t i2cSetFrequency(i2c_t * i2c, uint32_t clk_speed); -uint32_t i2cGetFrequency(i2c_t * i2c); -uint32_t i2cGetStatus(i2c_t * i2c); // Status register of peripheral - -//Functions below should be used only if well understood -//Might be deprecated and removed in future -i2c_err_t i2cAttachSCL(i2c_t * i2c, int8_t scl); -i2c_err_t i2cDetachSCL(i2c_t * i2c, int8_t scl); -i2c_err_t i2cAttachSDA(i2c_t * i2c, int8_t sda); -i2c_err_t i2cDetachSDA(i2c_t * i2c, int8_t sda); - -//Stickbreakers ISR Support -i2c_err_t i2cProcQueue(i2c_t *i2c, uint32_t *readCount, uint16_t timeOutMillis); -i2c_err_t i2cAddQueueWrite(i2c_t *i2c, uint16_t i2cDeviceAddr, uint8_t *dataPtr, uint16_t dataLen, bool SendStop, EventGroupHandle_t event); -i2c_err_t i2cAddQueueRead(i2c_t *i2c, uint16_t i2cDeviceAddr, uint8_t *dataPtr, uint16_t dataLen, bool SendStop, EventGroupHandle_t event); - -//stickbreaker debug support -uint32_t i2cDebug(i2c_t *, uint32_t setBits, uint32_t resetBits); -// Debug actions have 3 currently defined locus -// 0xXX------ : at entry of ProcQueue -// 0x--XX---- : at exit of ProcQueue -// 0x------XX : at entry of Flush -// -// bit 0 causes DumpI2c to execute -// bit 1 causes DumpInts to execute -// bit 2 causes DumpCmdqueue to execute -// bit 3 causes DumpStatus to execute -// bit 4 causes DumpFifo to execute +#include + +esp_err_t i2cInit(uint8_t i2c_num, int8_t sda, int8_t scl, uint32_t clk_speed); +esp_err_t i2cDeinit(uint8_t i2c_num); +esp_err_t i2cSetClock(uint8_t i2c_num, uint32_t frequency); +esp_err_t i2cGetClock(uint8_t i2c_num, uint32_t * frequency); +esp_err_t i2cWrite(uint8_t i2c_num, uint16_t address, const uint8_t* buff, size_t size, uint32_t timeOutMillis); +esp_err_t i2cRead(uint8_t i2c_num, uint16_t address, uint8_t* buff, size_t size, uint32_t timeOutMillis, size_t *readCount); +esp_err_t i2cWriteReadNonStop(uint8_t i2c_num, uint16_t address, const uint8_t* wbuff, size_t wsize, uint8_t* rbuff, size_t rsize, uint32_t timeOutMillis, size_t *readCount); +bool i2cIsInit(uint8_t i2c_num); #ifdef __cplusplus } diff --git a/cores/esp32/esp32-hal-uart.c b/cores/esp32/esp32-hal-uart.c index 1d8c280b687..c3f2df37207 100644 --- a/cores/esp32/esp32-hal-uart.c +++ b/cores/esp32/esp32-hal-uart.c @@ -269,7 +269,7 @@ void uartWrite(uart_t* uart, uint8_t c) void uartWriteBuf(uart_t* uart, const uint8_t * data, size_t len) { - if(uart == NULL) { + if(uart == NULL || data == NULL || !len) { return; } @@ -368,13 +368,9 @@ void uartSetDebug(uart_t* uart) { if(uart == NULL || uart->num >= SOC_UART_NUM) { s_uart_debug_nr = -1; - //ets_install_putc1(NULL); - //return; - } else - if(s_uart_debug_nr == uart->num) { - return; - } else - s_uart_debug_nr = uart->num; + } else { + s_uart_debug_nr = uart->num; + } uart_install_putc(); } diff --git a/cores/esp32/esp32-hal.h b/cores/esp32/esp32-hal.h index 92bb182896d..3efead522dd 100644 --- a/cores/esp32/esp32-hal.h +++ b/cores/esp32/esp32-hal.h @@ -31,6 +31,11 @@ #include "sdkconfig.h" #include "esp_system.h" #include "esp_sleep.h" +#include "freertos/FreeRTOS.h" +#include "freertos/task.h" +#include "freertos/queue.h" +#include "freertos/semphr.h" +#include "freertos/event_groups.h" #ifdef __cplusplus extern "C" { diff --git a/cores/esp32/libb64/cdecode.c b/cores/esp32/libb64/cdecode.c index aa84ef60a8d..47592b02ba8 100755 --- a/cores/esp32/libb64/cdecode.c +++ b/cores/esp32/libb64/cdecode.c @@ -12,7 +12,7 @@ static int base64_decode_value_signed(int8_t value_in){ static const int8_t decoding[] = {62,-1,-1,-1,63,52,53,54,55,56,57,58,59,60,61,-1,-1,-1,-2,-1,-1,-1,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,-1,-1,-1,-1,-1,-1,26,27,28,29,30,31,32,33,34,35,36,37,38,39,40,41,42,43,44,45,46,47,48,49,50,51}; static const int8_t decoding_size = sizeof(decoding); value_in -= 43; - if (value_in < 0 || value_in > decoding_size) return -1; + if (value_in < 0 || value_in >= decoding_size) return -1; return decoding[(int)value_in]; } diff --git a/docs/source/installing.rst b/docs/source/installing.rst index 3ba6a7829e8..56511723eeb 100644 --- a/docs/source/installing.rst +++ b/docs/source/installing.rst @@ -166,9 +166,7 @@ Debian/Ubuntu mkdir -p ~/Arduino/hardware/espressif && \ cd ~/Arduino/hardware/espressif && \ git clone https://github.com/espressif/arduino-esp32.git esp32 && \ - cd esp32 && \ - git submodule update --init --recursive && \ - cd tools && \ + cd esp32/tools && \ python3 get.py - Restart Arduino IDE. @@ -181,9 +179,7 @@ Debian/Ubuntu mkdir -p espressif && \ cd espressif && \ git clone https://github.com/espressif/arduino-esp32.git esp32 && \ - cd esp32 && \ - git submodule update --init --recursive && \ - cd tools && \ + cd esp32/tools && \ python3 get.py Fedora @@ -203,9 +199,7 @@ Fedora mkdir -p ~/Arduino/hardware/espressif && \ cd ~/Arduino/hardware/espressif && \ git clone https://github.com/espressif/arduino-esp32.git esp32 && \ - cd esp32 && \ - git submodule update --init --recursive && \ - cd tools && \ + cd esp32/tools && \ python get.py - Restart Arduino IDE. @@ -228,9 +222,7 @@ openSUSE mkdir -p ~/Arduino/hardware/espressif && \ cd ~/Arduino/hardware/espressif && \ git clone https://github.com/espressif/arduino-esp32.git esp32 && \ - cd esp32 && \ - git submodule update --init --recursive && \ - cd tools && \ + cd esp32/tools && \ python get.py - Restart Arduino IDE. @@ -246,10 +238,8 @@ macOS mkdir -p ~/Documents/Arduino/hardware/espressif && \ cd ~/Documents/Arduino/hardware/espressif && \ - git clone https://github.com/espressif/arduino-esp32.git esp32 --depth 1 && \ - cd esp32 && \ - git submodule update --init --recursive --depth 1 && \ - cd tools && \ + git clone https://github.com/espressif/arduino-esp32.git esp32 && \ + cd esp32/tools && \ python get.py Where ``~/Documents/Arduino`` represents your sketch book location as per "Arduino" > "Preferences" > "Sketchbook location" (in the IDE once started). Adjust the command above accordingly. diff --git a/docs/source/tutorials/blink.rst b/docs/source/tutorials/blink.rst new file mode 100644 index 00000000000..f65af1b3bae --- /dev/null +++ b/docs/source/tutorials/blink.rst @@ -0,0 +1,113 @@ +########################## +Blink Interactive Tutorial +########################## + +Introduction +------------ + +This is the interactive blink tutorial using `Wokwi`_. For this tutorial, you don't need the ESP32 board or the Arduino toolchain. + +.. note:: If you don't want to use this tutorial with the simulation, you can copy and paste the :ref:`blink_example_code` from `Wokwi`_ editor and use it on the `Arduino IDE`_ or `PlatformIO`_. + +About this Tutorial +------------------- + +This tutorial is the most basic for any get started. In this tutorial, we will show how to set a GPIO pin as an output to drive a LED to blink each 1 second. + +Step by step +------------ + +In order to make this simple blink tutorial, you'll need to do the following steps. + +1. **Define the GPIO for the LED.** + +.. code-block:: + + #define LED 2 + +This ``#define LED 2`` will be used to set the GPIO2 as the ``LED`` output pin. + +2. **Setup.** + +Inside the ``setup()`` function, we need to add all things we want to run once during the startup. +Here we'll add the ``pinMode`` function to set the pin as output. + +.. code-block:: + + void setup() { + pinMode(LED, OUTPUT); + } + +The first argument is the GPIO number, already defined and the second is the mode, here defined as an output. + +3. **Main Loop.** + +After the ``setup``, the code runs the ``loop`` function infinitely. Here we will handle the GPIO in order to get the LED blinking. + +.. code-block:: + + void loop() { + digitalWrite(LED, HIGH); + delay(100); + digitalWrite(LED, LOW); + delay(100); + } + +The first function is the ``digitalWrite()`` with two arguments: + +* GPIO: Set the GPIO pin. Here defined by our ``LED`` connected to the GPIO2. +* State: Set the GPIO state as HIGH (ON) or LOW (OFF). + +This first ``digitalWrite`` we will set the LED ON. + +After the ``digitalWrite``, we will set a ``delay`` function in order to wait for some time, defined in milliseconds. + +Now we can set the GPIO to ``LOW`` to turn the LED off and ``delay`` for more few milliseconds to get the LED blinking. + +4. **Run the code.** + +To run this code, you'll need a development board and the Arduino toolchain installed on your computer. If you don't have both, you can use the simulator to test and edit the code. + +Simulation +---------- + +This simulator is provided by `Wokwi`_ and you can test the blink code and play with some modifications to learn more about this example. + +.. raw:: html + + + +Change the parameters, like the delay period, to test the code right on your browser. You can add more LEDs, change the GPIO, and more. + +.. _blink_example_code: + +Example Code +------------ + +Here is the full blink code. + +.. code-block:: + + #define LED 2 + + void setup() { + pinMode(LED, OUTPUT); + } + + void loop() { + digitalWrite(LED, HIGH); + delay(100); + digitalWrite(LED, LOW); + delay(100); + } + +Resources +--------- + +* `ESP32 Datasheet`_ (Datasheet) +* `Wokwi`_ (Wokwi Website) + +.. _ESP32 Datasheet: https://www.espressif.com/sites/default/files/documentation/esp32_datasheet_en.pdf +.. _Wokwi: https://wokwi.com/ +.. _PlatformIO: https://docs.espressif.com/projects/arduino-esp32/en/latest/installing.html#platformio +.. _Arduino IDE: https://docs.espressif.com/projects/arduino-esp32/en/latest/installing.html#installing-using-boards-manager \ No newline at end of file diff --git a/docs/source/tutorials/tutorials.rst b/docs/source/tutorials/tutorials.rst index 15d3f463375..57eead06f31 100644 --- a/docs/source/tutorials/tutorials.rst +++ b/docs/source/tutorials/tutorials.rst @@ -6,6 +6,7 @@ Tutorials :maxdepth: 2 :caption: Tutorials: + Blink Basic DFU GPIO Matrix and Pin Mux diff --git a/libraries/BLE/src/BLECharacteristic.cpp b/libraries/BLE/src/BLECharacteristic.cpp index dd39d8472ec..228c38969f4 100644 --- a/libraries/BLE/src/BLECharacteristic.cpp +++ b/libraries/BLE/src/BLECharacteristic.cpp @@ -191,7 +191,7 @@ uint8_t* BLECharacteristic::getData() { * @brief Retrieve the current length of the data of the characteristic. * @return Amount of databytes of the characteristic. */ -uint8_t BLECharacteristic::getLength() { +size_t BLECharacteristic::getLength() { return m_value.getLength(); } // getLength diff --git a/libraries/BLE/src/BLECharacteristic.h b/libraries/BLE/src/BLECharacteristic.h index 8fdd6213883..9e7c0317faf 100644 --- a/libraries/BLE/src/BLECharacteristic.h +++ b/libraries/BLE/src/BLECharacteristic.h @@ -62,7 +62,7 @@ class BLECharacteristic { BLEUUID getUUID(); std::string getValue(); uint8_t* getData(); - uint8_t getLength(); + size_t getLength(); void indicate(); void notify(bool is_notification = true); diff --git a/libraries/FFat/src/FFat.cpp b/libraries/FFat/src/FFat.cpp index 6441dfca4e4..f58bc444c17 100644 --- a/libraries/FFat/src/FFat.cpp +++ b/libraries/FFat/src/FFat.cpp @@ -168,7 +168,7 @@ size_t F_Fat::freeBytes() bool F_Fat::exists(const char* path) { - File f = open(path, "r"); + File f = open(path, "r",false); return (f == true) && !f.isDirectory(); } diff --git a/libraries/FS/src/FS.cpp b/libraries/FS/src/FS.cpp index 3050ec41fd8..f5e9a8ab2cc 100644 --- a/libraries/FS/src/FS.cpp +++ b/libraries/FS/src/FS.cpp @@ -186,18 +186,18 @@ void File::rewindDirectory(void) _p->rewindDirectory(); } -File FS::open(const String& path, const char* mode) +File FS::open(const String& path, const char* mode, const bool create) { - return open(path.c_str(), mode); + return open(path.c_str(), mode, create); } -File FS::open(const char* path, const char* mode) +File FS::open(const char* path, const char* mode, const bool create) { if (!_impl) { return File(); } - return File(_impl->open(path, mode)); + return File(_impl->open(path, mode, create)); } bool FS::exists(const char* path) diff --git a/libraries/FS/src/FS.h b/libraries/FS/src/FS.h index 2c4aa3011c1..c3a1c51c5ec 100644 --- a/libraries/FS/src/FS.h +++ b/libraries/FS/src/FS.h @@ -89,8 +89,8 @@ class FS public: FS(FSImplPtr impl) : _impl(impl) { } - File open(const char* path, const char* mode = FILE_READ); - File open(const String& path, const char* mode = FILE_READ); + File open(const char* path, const char* mode = FILE_READ, const bool create = false); + File open(const String& path, const char* mode = FILE_READ, const bool create = false); bool exists(const char* path); bool exists(const String& path); diff --git a/libraries/FS/src/FSImpl.h b/libraries/FS/src/FSImpl.h index 51c5915a069..4c5c9786840 100644 --- a/libraries/FS/src/FSImpl.h +++ b/libraries/FS/src/FSImpl.h @@ -53,7 +53,7 @@ class FSImpl public: FSImpl() : _mountpoint(NULL) { } virtual ~FSImpl() { } - virtual FileImplPtr open(const char* path, const char* mode) = 0; + virtual FileImplPtr open(const char* path, const char* mode, const bool create) = 0; virtual bool exists(const char* path) = 0; virtual bool rename(const char* pathFrom, const char* pathTo) = 0; virtual bool remove(const char* path) = 0; diff --git a/libraries/FS/src/vfs_api.cpp b/libraries/FS/src/vfs_api.cpp index aea37b1e3d6..e43b4397452 100644 --- a/libraries/FS/src/vfs_api.cpp +++ b/libraries/FS/src/vfs_api.cpp @@ -16,7 +16,7 @@ using namespace fs; -FileImplPtr VFSImpl::open(const char* fpath, const char* mode) +FileImplPtr VFSImpl::open(const char* fpath, const char* mode, const bool create) { if(!_mountpoint) { log_e("File system is not mounted"); @@ -37,7 +37,7 @@ FileImplPtr VFSImpl::open(const char* fpath, const char* mode) sprintf(temp,"%s%s", _mountpoint, fpath); struct stat st; - //file lound + //file found if(!stat(temp, &st)) { free(temp); if (S_ISREG(st.st_mode) || S_ISDIR(st.st_mode)) { @@ -47,12 +47,6 @@ FileImplPtr VFSImpl::open(const char* fpath, const char* mode) return FileImplPtr(); } - //file not found but mode permits creation - if(mode && mode[0] != 'r') { - free(temp); - return std::make_shared(this, fpath, mode); - } - //try to open this as directory (might be mount point) DIR * d = opendir(temp); if(d) { @@ -61,7 +55,51 @@ FileImplPtr VFSImpl::open(const char* fpath, const char* mode) return std::make_shared(this, fpath, mode); } - log_e("%s does not exist", temp); + //file not found but mode permits file creation without folder creation + if((mode && mode[0] != 'r') && (!create)){ + free(temp); + return std::make_shared(this, fpath, mode); + } + + ////file not found but mode permits file creation and folder creation + if((mode && mode[0] != 'r') && create){ + + char *token; + char *folder = (char *)malloc(strlen(fpath)); + + int start_index = 0; + int end_index = 0; + + token = strchr(fpath+1,'/'); + end_index = (token-fpath); + + while (token != NULL) + { + memcpy(folder,fpath + start_index, end_index-start_index); + folder[end_index-start_index] = '\0'; + + if(!VFSImpl::mkdir(folder)) + { + log_e("Creating folder: %s failed!",folder); + return FileImplPtr(); + } + + token=strchr(token+1,'/'); + if(token != NULL) + { + end_index = (token-fpath); + memset(folder, 0, strlen(folder)); + } + + } + + free(folder); + free(temp); + return std::make_shared(this, fpath, mode); + + } + + log_e("%s does not exist, no permits for creation", temp); free(temp); return FileImplPtr(); } diff --git a/libraries/FS/src/vfs_api.h b/libraries/FS/src/vfs_api.h index 58fd86fdd26..f79852cdcfe 100644 --- a/libraries/FS/src/vfs_api.h +++ b/libraries/FS/src/vfs_api.h @@ -35,7 +35,7 @@ class VFSImpl : public FSImpl friend class VFSFileImpl; public: - FileImplPtr open(const char* path, const char* mode) override; + FileImplPtr open(const char* path, const char* mode, const bool create) override; bool exists(const char* path) override; bool rename(const char* pathFrom, const char* pathTo) override; bool remove(const char* path) override; diff --git a/libraries/HTTPClient/src/HTTPClient.cpp b/libraries/HTTPClient/src/HTTPClient.cpp index e7a8ecb8f4f..cc0a31e2b6b 100644 --- a/libraries/HTTPClient/src/HTTPClient.cpp +++ b/libraries/HTTPClient/src/HTTPClient.cpp @@ -261,6 +261,10 @@ bool HTTPClient::beginInternal(String url, const char* expectedProtocol) url.remove(0, (index + 3)); // remove http:// or https:// index = url.indexOf('/'); + if (index == -1) { + index = url.length(); + url += '/'; + } String host = url.substring(0, index); url.remove(0, index); // remove host part diff --git a/libraries/LittleFS/src/LittleFS.cpp b/libraries/LittleFS/src/LittleFS.cpp index 7989dcb60be..9ea2320ecf9 100644 --- a/libraries/LittleFS/src/LittleFS.cpp +++ b/libraries/LittleFS/src/LittleFS.cpp @@ -45,7 +45,7 @@ LittleFSImpl::LittleFSImpl() bool LittleFSImpl::exists(const char* path) { - File f = open(path, "r"); + File f = open(path, "r",false); return (f == true); } diff --git a/libraries/SD_MMC/src/SD_MMC.cpp b/libraries/SD_MMC/src/SD_MMC.cpp index 16da3c8ead7..450657cfa6f 100644 --- a/libraries/SD_MMC/src/SD_MMC.cpp +++ b/libraries/SD_MMC/src/SD_MMC.cpp @@ -36,7 +36,7 @@ SDMMCFS::SDMMCFS(FSImplPtr impl) : FS(impl), _card(NULL) {} -bool SDMMCFS::begin(const char * mountpoint, bool mode1bit, bool format_if_mount_failed) +bool SDMMCFS::begin(const char * mountpoint, bool mode1bit, bool format_if_mount_failed, int sdmmc_frequency) { if(_card) { return true; @@ -46,7 +46,7 @@ bool SDMMCFS::begin(const char * mountpoint, bool mode1bit, bool format_if_mount sdmmc_host_t host; host.flags = SDMMC_HOST_FLAG_4BIT; host.slot = SDMMC_HOST_SLOT_1; - host.max_freq_khz = SDMMC_FREQ_DEFAULT; + host.max_freq_khz = sdmmc_frequency; host.io_voltage = 3.3f; host.init = &sdmmc_host_init; host.set_bus_width = &sdmmc_host_set_bus_width; @@ -58,7 +58,6 @@ bool SDMMCFS::begin(const char * mountpoint, bool mode1bit, bool format_if_mount host.io_int_enable = &sdmmc_host_io_int_enable; host.io_int_wait = &sdmmc_host_io_int_wait; host.command_timeout_ms = 0; - host.max_freq_khz = SDMMC_FREQ_HIGHSPEED; #ifdef BOARD_HAS_1BIT_SDMMC mode1bit = true; #endif diff --git a/libraries/SD_MMC/src/SD_MMC.h b/libraries/SD_MMC/src/SD_MMC.h index 6e40fd4540c..e8540b32fc4 100644 --- a/libraries/SD_MMC/src/SD_MMC.h +++ b/libraries/SD_MMC/src/SD_MMC.h @@ -21,6 +21,13 @@ #include "driver/sdmmc_types.h" #include "sd_defines.h" +// If reading/writing to the SD card is unstable, +// you can define BOARD_MAX_SDMMC_FREQ with lower value (Ex. SDMMC_FREQ_DEFAULT) +// in pins_arduino.h for your board variant. +#ifndef BOARD_MAX_SDMMC_FREQ +#define BOARD_MAX_SDMMC_FREQ SDMMC_FREQ_HIGHSPEED +#endif + namespace fs { @@ -31,7 +38,7 @@ class SDMMCFS : public FS public: SDMMCFS(FSImplPtr impl); - bool begin(const char * mountpoint="/sdcard", bool mode1bit=false, bool format_if_mount_failed=false); + bool begin(const char * mountpoint="/sdcard", bool mode1bit=false, bool format_if_mount_failed=false, int sdmmc_frequency=BOARD_MAX_SDMMC_FREQ); void end(); sdcard_type_t cardType(); uint64_t cardSize(); diff --git a/libraries/SPIFFS/src/SPIFFS.cpp b/libraries/SPIFFS/src/SPIFFS.cpp index d3e1665491a..0fb2eff08af 100644 --- a/libraries/SPIFFS/src/SPIFFS.cpp +++ b/libraries/SPIFFS/src/SPIFFS.cpp @@ -39,7 +39,7 @@ SPIFFSImpl::SPIFFSImpl() bool SPIFFSImpl::exists(const char* path) { - File f = open(path, "r"); + File f = open(path, "r",false); return (f == true) && !f.isDirectory(); } diff --git a/libraries/WebServer/examples/SDWebServer/SDWebServer.ino b/libraries/WebServer/examples/SDWebServer/SDWebServer.ino index 9e0b8456e28..de01610ecec 100644 --- a/libraries/WebServer/examples/SDWebServer/SDWebServer.ino +++ b/libraries/WebServer/examples/SDWebServer/SDWebServer.ino @@ -25,6 +25,8 @@ index.htm is the default index (works on subfolders as well) upload the contents of SdRoot to the root of the SDcard and access the editor by going to http://esp8266sd.local/edit + To retrieve the contents of SDcard, visit http://esp32sd.local/list?dir=/ + dir is the argument that needs to be passed to the function PrintDirectory via HTTP Get request. */ #include diff --git a/libraries/WiFi/src/ETH.cpp b/libraries/WiFi/src/ETH.cpp index 092d6a3d467..cb5ad7a8c59 100644 --- a/libraries/WiFi/src/ETH.cpp +++ b/libraries/WiFi/src/ETH.cpp @@ -288,7 +288,12 @@ bool ETHClass::begin(uint8_t phy_addr, int power, int mdc, int mdio, eth_phy_typ break; #endif case ETH_PHY_KSZ8081: +#if ESP_IDF_VERSION > ESP_IDF_VERSION_VAL(4,3,0) eth_phy = esp_eth_phy_new_ksz8081(&phy_config); +#else + log_e("unsupported ethernet type 'ETH_PHY_KSZ8081'"); +#endif + break; default: break; } diff --git a/libraries/Wire/doc/i2c_debugging.md b/libraries/Wire/doc/i2c_debugging.md deleted file mode 100644 index 35c6e2e7f17..00000000000 --- a/libraries/Wire/doc/i2c_debugging.md +++ /dev/null @@ -1,276 +0,0 @@ -# Debugging I2C - -With the release of Arduino-ESP32 V1.0.1 the I2C subsystem contains code to exhaustively report communication errors. -* Basic debugging can be enable by setting the *CORE DEBUG LEVEL* at or above *ERROR*. All errors will be directed the the *DEBUG OUTPUT* normally connected to `Serial()`. -* Enhanced debugging can be used to generate specified information at specific positions during the i2c communication sequence. Increase *CORE DEBUG LEVEL* to ***DEBUG*** - -## Enable Debug Buffer -The Enhanced debug features are enabled by uncommenting the `\\#define ENABLE_I2C_DEBUG_BUFFER` at line 45 of `esp32-hal-i2c.c`. -* When Arduino-Esp32 is installed in Windows with Arduino Boards Manager, `esp32-hal-i2c.c` can be found in: -`C:\Users\{user}\AppData\Local\Arduino15\packages\esp32\hardware\esp32\1.0.1\cores\esp32\` -* When Arduino-Esp32 Development version is installed from GitHub, `esp32-hal-i2c.c` can be found in: -`{arduino Sketch}\hardware\espressif\esp32\cores\esp32\` - - -```c++ -//#define ENABLE_I2C_DEBUG_BUFFER -``` -Change it to: -```c++ -#define ENABLE_I2C_DEBUG_BUFFER -``` -and recompile/upload the resulting code to your ESP32. - -Enabling this `#define` will consume an additional 2570 bytes of RAM and include a commensurate amount of code FLASH. If you see the message `"Debug Buffer not Enabled"` in your console log I would suggest you un-comment the line and regenerate the error. Additional information will be supplied on the log console. - -## Manually controlled Debugging -Manual logging of the i2c control data buffers can be accomplished by using the debug control function of `Wire()`: -```c++ - uint32_t setDebugFlags( uint32_t setBits, uint32_t resetBits); -``` -`setBits`, and `resetBits` manually cause output of the control structures to the log console. They are bit fields that enable/disable the reporting of individual control structures during specific phases of the i2c communications sequence. The 32bit values are divided into four 8bit fields. Currently only five bits are defined. ***If an error is detected during normal operations, the relevant control structure will bit added to the log irrespective of the current debug flags.*** - -* **bit 0** causes DumpI2c to execute -header information about current communications event, -and the dataQueue elements showing the logical i2c transaction commands -* **bit 1** causes DumpInts to execute -Actual sequence of interrupts handled during last communications event, cleared on entry into `ProcQueue()`. -* **bit 2** causes DumpCmdqueue to execute -The last block of commands to the i2c peripheral. -* **bit 3** causes DumpStatus to execute -A descriptive display of the 32bit i2c peripheral status word. -* **bit 4** causes DumpFifo to execute -A buffer listing the sequence of data added to the txFifo of the i2c peripheral. - -Of the four division, only three are currently implemented: -* 0xXX - - - - - - : at entry of ProcQueue (`bitFlags << 24`) -* 0x - - XX - - - - : at exit of ProcQueue (`bitFlags << 16`) -* 0x - - - - - - XX : at entry of Flush (`bitFlags`) - -For example, to display the sequence of Interrupts processed during the i2c communication transaction, **bit 1** would be set, and, since this information on Interrupt usage would only be valid after the communications have completed, the locus would be *at exit of ProcQueue*. The following code would be necessary. -### code -```c++ -uint8_t flag = 1 << 1; // turn on bit 1 -uint32_t debugFlag = flag << 16; // correctly position the 8bits of flag as the second byte of setBits. -Wire.setDebugFlags(debugFlag,0);// resetBits=0 says leave all current setBits as is. - -Wire.requestFrom(id,byteCount); // read byteCount bytes from slave at id - -Wire.setDebugFlags(0,debugFlag); // don't add any new debug, remove debugFlag -``` -### output of log console -``` -[I][esp32-hal-i2c.c:437] i2cTriggerDumps(): after ProcQueue -[I][esp32-hal-i2c.c:346] i2cDumpInts(): 0 row count INTR TX RX Tick -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [01] 0x0001 0x0002 0x0003 0x0000 0x005baac5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [02] 0x0001 0x0200 0x0000 0x0000 0x005baac5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [03] 0x0001 0x0080 0x0000 0x0008 0x005baac6 -``` -# Debug Log example -### Code -To read eight bytes of data from a DS1307 RTCC -``` - uint32_t debugFlag = 0x001F0000; - uint8_t ID = 0x68; - uint8_t block=8; - - if(debugFlag >0){ - Wire.setDebugFlags(debugFlag,0); - } - - Wire.beginTransmission(ID); - Wire.write(lowByte(addr)); - if((err=Wire.endTransmission(false))!=0) { - Serial.printf(" EndTransmission=%d(%s)",Wire.lastError(),Wire.getErrorText(Wire.lastError())); - - if(err!=2) { - Serial.printf(", resetting\n"); - if( !Wire.begin()) Serial.printf(" Reset Failed\n"); - if(debugFlag >0) Wire.setDebugFlags(0,debugFlag); - return; - } else { - Serial.printf(", No Device present, aborting\n"); - currentCommand= NO_COMMAND; - return; - } - } - err = Wire.requestFrom(ID,block,true); - if(debugFlag >0){ - Wire.setDebugFlags(0,debugFlag); - } -``` -### output of log console -``` -[I][esp32-hal-i2c.c:437] i2cTriggerDumps(): after ProcQueue -[E][esp32-hal-i2c.c:318] i2cDumpI2c(): i2c=0x3ffbdc78 -[I][esp32-hal-i2c.c:319] i2cDumpI2c(): dev=0x60013000 date=0x16042000 -[I][esp32-hal-i2c.c:321] i2cDumpI2c(): lock=0x3ffb843c -[I][esp32-hal-i2c.c:323] i2cDumpI2c(): num=0 -[I][esp32-hal-i2c.c:324] i2cDumpI2c(): mode=1 -[I][esp32-hal-i2c.c:325] i2cDumpI2c(): stage=3 -[I][esp32-hal-i2c.c:326] i2cDumpI2c(): error=1 -[I][esp32-hal-i2c.c:327] i2cDumpI2c(): event=0x3ffb85c4 bits=10 -[I][esp32-hal-i2c.c:328] i2cDumpI2c(): intr_handle=0x3ffb85f4 -[I][esp32-hal-i2c.c:329] i2cDumpI2c(): dq=0x3ffb858c -[I][esp32-hal-i2c.c:330] i2cDumpI2c(): queueCount=2 -[I][esp32-hal-i2c.c:331] i2cDumpI2c(): queuePos=1 -[I][esp32-hal-i2c.c:332] i2cDumpI2c(): errorByteCnt=0 -[I][esp32-hal-i2c.c:333] i2cDumpI2c(): errorQueue=0 -[I][esp32-hal-i2c.c:334] i2cDumpI2c(): debugFlags=0x001F0000 -[I][esp32-hal-i2c.c:288] i2cDumpDqData(): [0] 7bit 68 W buf@=0x3ffc04b2, len=1, pos=1, ctrl=11101 -[I][esp32-hal-i2c.c:306] i2cDumpDqData(): 0x0000: . 00 -[I][esp32-hal-i2c.c:288] i2cDumpDqData(): [1] 7bit 68 R STOP buf@=0x3ffc042c, len=8, pos=8, ctrl=11111 -[I][esp32-hal-i2c.c:306] i2cDumpDqData(): 0x0000: 5P...... 35 50 07 06 13 09 18 00 -[I][esp32-hal-i2c.c:346] i2cDumpInts(): 0 row count INTR TX RX Tick -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [01] 0x0001 0x0002 0x0003 0x0000 0x000073d5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [02] 0x0001 0x0200 0x0000 0x0000 0x000073d5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [03] 0x0001 0x0080 0x0000 0x0008 0x000073d6 -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 0] Y RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 1] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 2] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 3] Y RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 4] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 5] Y READ val[0] exp[0] en[0] bytes[7] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 6] Y READ val[1] exp[0] en[0] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 7] Y STOP val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 8] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 9] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [10] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [11] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [12] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [13] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [14] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [15] N RSTART val[0] exp[0] en[0] bytes[0] -[I][esp32-hal-i2c.c:385] i2cDumpStatus(): ack(0) sl_rw(0) to(0) arb(0) busy(0) sl(1) trans(0) rx(0) tx(0) sclMain(5) scl(6) -[I][esp32-hal-i2c.c:424] i2cDumpFifo(): WRITE 0x68 0 -[I][esp32-hal-i2c.c:424] i2cDumpFifo(): READ 0x68 -``` -## Explaination of log output -### DumpI2c -``` -[I][esp32-hal-i2c.c:437] i2cTriggerDumps(): after ProcQueue -[E][esp32-hal-i2c.c:318] i2cDumpI2c(): i2c=0x3ffbdc78 -[I][esp32-hal-i2c.c:319] i2cDumpI2c(): dev=0x60013000 date=0x16042000 -[I][esp32-hal-i2c.c:321] i2cDumpI2c(): lock=0x3ffb843c -[I][esp32-hal-i2c.c:323] i2cDumpI2c(): num=0 -[I][esp32-hal-i2c.c:324] i2cDumpI2c(): mode=1 -[I][esp32-hal-i2c.c:325] i2cDumpI2c(): stage=3 -[I][esp32-hal-i2c.c:326] i2cDumpI2c(): error=1 -[I][esp32-hal-i2c.c:327] i2cDumpI2c(): event=0x3ffb85c4 bits=10 -[I][esp32-hal-i2c.c:328] i2cDumpI2c(): intr_handle=0x3ffb85f4 -[I][esp32-hal-i2c.c:329] i2cDumpI2c(): dq=0x3ffb858c -[I][esp32-hal-i2c.c:330] i2cDumpI2c(): queueCount=2 -[I][esp32-hal-i2c.c:331] i2cDumpI2c(): queuePos=1 -[I][esp32-hal-i2c.c:332] i2cDumpI2c(): errorByteCnt=0 -[I][esp32-hal-i2c.c:333] i2cDumpI2c(): errorQueue=0 -[I][esp32-hal-i2c.c:334] i2cDumpI2c(): debugFlags=0x001F0000 -``` -variable | description ----- | ---- -**i2c** | *memory address for control block* -**dev** | *memory address for access to i2c peripheral registers* -**date** | *revision date of peripheral silicon 2016, 42 week* -**lock** | *hal lock handle* -**num** | *0,1 which peripheral is being controlled* -**mode** | *configuration of driver 0=none, 1=MASTER, 2=SLAVE, 3=MASTER and SLAVE* -**stage** | *internal STATE of driver 0=not configured, 1=startup, 2=running, 3=done* -**error** | *internal ERROR status 0=not configured, 1=ok, 2=error, 3=address NAK, 4=data NAK, 5=arbitration loss, 6=timeout* -**event** | *handle for interprocess FreeRTOS eventSemaphore for communication between ISR and APP* -**intr_handle** | *FreeRTOS handle for allocated interrupt* -**dq** | *memory address for data queue control block* -**queueCount** | *number of data operations in queue control block* -**queuePos** | *last executed data block* -**errorByteCnt** | *position in current data block when error occured -1=address byte* -**errorQueue** | *queue that was executing when error occurred* -**debugFlags** | *current specified error bits* - -### DQ data -``` -[I][esp32-hal-i2c.c:288] i2cDumpDqData(): [0] 7bit 68 W buf@=0x3ffc04b2, len=1, pos=1, ctrl=11101 -[I][esp32-hal-i2c.c:306] i2cDumpDqData(): 0x0000: . 00 -[I][esp32-hal-i2c.c:288] i2cDumpDqData(): [1] 7bit 68 R STOP buf@=0x3ffc042c, len=8, pos=8, ctrl=11111 -[I][esp32-hal-i2c.c:306] i2cDumpDqData(): 0x0000: 5P...... 35 50 07 06 13 09 18 00 -``` -variable | description ---- | --- -**[n]** | *index of data queue element* -**i2c address** | *7bit= 7bit i2c slave address, 10bit= 10bit i2c slave address* -**direction** | *W=Write, R=READ* -**STOP** | *command issued a I2C STOP, else if blank, a RESTART was issued by next dq element.* -**buf@** | *pointer to data buffer* -**len** | *length of data buffer* -**pos** | *last position used in buffer* -**ctrl** | *bit field for data queue control, this bits describe if all necessary commands have been added to peripheral command buffer. in order(START,ADDRESS_Write,DATA,STOP,ADDRESS_value* -**0xnnnn** | *data buffer content, displayable followed by HEX, 32 bytes on a line.* - -### DumpInts -``` -[I][esp32-hal-i2c.c:346] i2cDumpInts(): 0 row count INTR TX RX Tick -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [01] 0x0001 0x0002 0x0003 0x0000 0x000073d5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [02] 0x0001 0x0200 0x0000 0x0000 0x000073d5 -[I][esp32-hal-i2c.c:350] i2cDumpInts(): [03] 0x0001 0x0080 0x0000 0x0008 0x000073d6 -``` -variable | description ----- | ---- -**row** | *array index* -**count** | *number of consecutive, duplicate interrupts* -**INTR** | *bit value of active interrupt (from ..\esp32\tools\sdk\include\soc\soc\i2c_struct.h)* -**TX** | *number of bytes added to txFifo* -**RX** | *number of bytes read from rxFifo* -**Tick** | *current tick counter from xTaskGetTickCountFromISR()* - -### DumpCmdQueue -``` -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 0] Y RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 1] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 2] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 3] Y RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 4] Y WRITE val[0] exp[0] en[1] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 5] Y READ val[0] exp[0] en[0] bytes[7] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 6] Y READ val[1] exp[0] en[0] bytes[1] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 7] Y STOP val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 8] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [ 9] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [10] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [11] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [12] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [13] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [14] N RSTART val[0] exp[0] en[0] bytes[0] -[E][esp32-hal-i2c.c:243] i2cDumpCmdQueue(): [15] N RSTART val[0] exp[0] en[0] bytes[0] -``` -Column | description ----- | ---- -**command** | *RSTART= generate i2c START sequence, WRITE= output byte(s), READ= input byte(s), STOP= generate i2c STOP sequence, END= continuation flag for peripheral to pause execution waiting for a refilled command list* -**val** | *value for ACK bit, 0 = LOW, 1= HIGH* -**exp** | *test of ACK bit 0=no, 1=yes* -**en** | *output of val, 0=no, 1=yes* -**bytes** | *number of byte to send(WRITE) or receive(READ) 1..255* - -### DumpStatus -``` -[I][esp32-hal-i2c.c:385] i2cDumpStatus(): ack(0) sl_rw(0) to(0) arb(0) busy(0) sl(1) trans(0) rx(0) tx(0) sclMain(5) scl(6) -``` -variable | description ----- | ---- -**ack** | *last value for ACK bit* -**sl_rw** | *mode for SLAVE operation 0=write, 1=read* -**to** | *timeout* -**arb** | *arbitration loss* -**busy** | *bus is inuse by other Master, or SLAVE is holding SCL,SDA* -**sl** | *last address on bus was equal to slave_addr* -**trans** | *a byte has moved though peripheral* -**rx** | *count of bytes in rxFifo* -**tx** | *count of bytes in txFifo* -**sclMain** | *state machine for i2c module. 0: SCL_MAIN_IDLE, 1: SCL_ADDRESS_SHIFT, 2: SCL_ACK_ADDRESS, 3: SCL_RX_DATA, 4: SCL_TX_DATA, 5: SCL_SEND_ACK, 6 :SCL_WAIT_ACK* -**scl** | *SCL clock state. 0: SCL_IDLE, 1: SCL_START, 2: SCL_LOW_EDGE, 3: SCL_LOW, 4: SCL_HIGH_EDGE, 5: SCL_HIGH, 6:SCL_STOP* - -### DumpFifo -``` -[I][esp32-hal-i2c.c:424] i2cDumpFifo(): WRITE 0x68 0 -[I][esp32-hal-i2c.c:424] i2cDumpFifo(): READ 0x68 -``` -Mode | datavalues ---- | --- -**WRITE** | the following bytes added to the txFifo are in response to a WRITE command -**READ** | the following bytes added to the txFifo are in response to a READ command - diff --git a/libraries/Wire/keywords.txt b/libraries/Wire/keywords.txt index 3344011d406..a2fbf317e95 100644 --- a/libraries/Wire/keywords.txt +++ b/libraries/Wire/keywords.txt @@ -11,13 +11,14 @@ ####################################### begin KEYWORD2 +end KEYWORD2 setClock KEYWORD2 -setClockStretchLimit KEYWORD2 +getClock KEYWORD2 +setTimeOut KEYWORD2 +getTimeOut KEYWORD2 beginTransmission KEYWORD2 endTransmission KEYWORD2 requestFrom KEYWORD2 -send KEYWORD2 -receive KEYWORD2 onReceive KEYWORD2 onRequest KEYWORD2 @@ -26,6 +27,7 @@ onRequest KEYWORD2 ####################################### Wire KEYWORD2 +TwoWire KEYWORD2 ####################################### # Constants (LITERAL1) diff --git a/libraries/Wire/src/Wire.cpp b/libraries/Wire/src/Wire.cpp index 3acea70ac58..7000e7013bb 100644 --- a/libraries/Wire/src/Wire.cpp +++ b/libraries/Wire/src/Wire.cpp @@ -20,6 +20,7 @@ Modified December 2014 by Ivan Grokhotkov (ivan@esp8266.com) - esp8266 support Modified April 2015 by Hrsto Gochkov (ficeto@ficeto.com) - alternative esp8266 support Modified Nov 2017 by Chuck Todd (ctodd@cableone.net) - ESP32 ISR Support + Modified Nov 2021 by Hristo Gochkov to support ESP-IDF API */ extern "C" { @@ -36,41 +37,79 @@ TwoWire::TwoWire(uint8_t bus_num) :num(bus_num & 1) ,sda(-1) ,scl(-1) - ,i2c(NULL) ,rxIndex(0) ,rxLength(0) - ,rxQueued(0) - ,txIndex(0) ,txLength(0) ,txAddress(0) - ,txQueued(0) - ,transmitting(0) - ,last_error(I2C_ERROR_OK) ,_timeOutMillis(50) + ,nonStop(false) +#if !CONFIG_DISABLE_HAL_LOCKS + ,nonStopTask(NULL) + ,lock(NULL) +#endif {} TwoWire::~TwoWire() { - flush(); - if(i2c) { - i2cRelease(i2c); - i2c=NULL; + end(); +#if !CONFIG_DISABLE_HAL_LOCKS + if(lock != NULL){ + vSemaphoreDelete(lock); } +#endif } bool TwoWire::setPins(int sdaPin, int sclPin) { - if(i2c) { - log_e("can not set pins if begin was already called"); +#if !CONFIG_DISABLE_HAL_LOCKS + if(lock == NULL){ + lock = xSemaphoreCreateMutex(); + if(lock == NULL){ + log_e("xSemaphoreCreateMutex failed"); + return false; + } + } + //acquire lock + if(xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); return false; } - sda = sdaPin; - scl = sclPin; - return true; +#endif + if(!i2cIsInit(num)){ + sda = sdaPin; + scl = sclPin; + } else { + log_e("bus already initialized. change pins only when not."); + } +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); +#endif + return !i2cIsInit(num); } bool TwoWire::begin(int sdaPin, int sclPin, uint32_t frequency) { + bool started = false; + esp_err_t err = ESP_OK; +#if !CONFIG_DISABLE_HAL_LOCKS + if(lock == NULL){ + lock = xSemaphoreCreateMutex(); + if(lock == NULL){ + log_e("xSemaphoreCreateMutex failed"); + return false; + } + } + //acquire lock + if(xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return false; + } +#endif + if(i2cIsInit(num)){ + started = true; + goto end; + } if(sdaPin < 0) { // default param passed if(num == 0) { if(sda==-1) { @@ -81,7 +120,7 @@ bool TwoWire::begin(int sdaPin, int sclPin, uint32_t frequency) } else { if(sda==-1) { log_e("no Default SDA Pin for Second Peripheral"); - return false; //no Default pin for Second Peripheral + goto end; //no Default pin for Second Peripheral } else { sdaPin = sda; // reuse prior pin } @@ -98,7 +137,7 @@ bool TwoWire::begin(int sdaPin, int sclPin, uint32_t frequency) } else { if(scl == -1) { log_e("no Default SCL Pin for Second Peripheral"); - return false; //no Default pin for Second Peripheral + goto end; //no Default pin for Second Peripheral } else { sclPin = scl; // reuse prior pin } @@ -107,138 +146,172 @@ bool TwoWire::begin(int sdaPin, int sclPin, uint32_t frequency) sda = sdaPin; scl = sclPin; - i2c = i2cInit(num, sda, scl, frequency); - if(!i2c) { - return false; - } - - flush(); - return true; + err = i2cInit(num, sda, scl, frequency); + started = (err == ESP_OK); -} +end: +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); +#endif + return started; -void TwoWire::setTimeOut(uint16_t timeOutMillis) -{ - _timeOutMillis = timeOutMillis; } -uint16_t TwoWire::getTimeOut() +bool TwoWire::end() { - return _timeOutMillis; + esp_err_t err = ESP_OK; +#if !CONFIG_DISABLE_HAL_LOCKS + if(lock != NULL){ + //acquire lock + if(xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return false; + } +#endif + if(i2cIsInit(num)){ + err = i2cDeinit(num); + } +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); + } +#endif + return (err == ESP_OK); } -void TwoWire::setClock(uint32_t frequency) +uint32_t TwoWire::getClock() { -#if CONFIG_IDF_TARGET_ESP32S2 - i2c = i2cInit(num, sda, scl, frequency); - if(!i2c) { - return; + uint32_t frequency = 0; +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(lock == NULL || xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + } else { +#endif + i2cGetClock(num, &frequency); +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); } #endif - i2cSetFrequency(i2c, frequency); + return frequency; } -size_t TwoWire::getClock() +bool TwoWire::setClock(uint32_t frequency) { - return i2cGetFrequency(i2c); + esp_err_t err = ESP_OK; +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(lock == NULL || xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return false; + } +#endif + err = i2cSetClock(num, frequency); +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); +#endif + return (err == ESP_OK); } -/* stickBreaker Nov 2017 ISR, and bigblock 64k-1 - */ -i2c_err_t TwoWire::writeTransmission(uint16_t address, uint8_t *buff, uint16_t size, bool sendStop) +void TwoWire::setTimeOut(uint16_t timeOutMillis) { - last_error = i2cWrite(i2c, address, buff, size, sendStop, _timeOutMillis); - return last_error; + _timeOutMillis = timeOutMillis; } -i2c_err_t TwoWire::readTransmission(uint16_t address, uint8_t *buff, uint16_t size, bool sendStop, uint32_t *readCount) +uint16_t TwoWire::getTimeOut() { - last_error = i2cRead(i2c, address, buff, size, sendStop, _timeOutMillis, readCount); - return last_error; + return _timeOutMillis; } void TwoWire::beginTransmission(uint16_t address) { - transmitting = 1; +#if !CONFIG_DISABLE_HAL_LOCKS + if(nonStop && nonStopTask == xTaskGetCurrentTaskHandle()){ + log_e("Unfinished Repeated Start transaction! Expected requestFrom, not beginTransmission! Clearing..."); + //release lock + xSemaphoreGive(lock); + } + //acquire lock + if(lock == NULL || xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return; + } +#endif + nonStop = false; txAddress = address; - txIndex = txQueued; // allow multiple beginTransmission(),write(),endTransmission(false) until endTransmission(true) - txLength = txQueued; - last_error = I2C_ERROR_OK; + txLength = 0; } -/*stickbreaker isr - */ -uint8_t TwoWire::endTransmission(bool sendStop) // Assumes Wire.beginTransaction(), Wire.write() +uint8_t TwoWire::endTransmission(bool sendStop) { - if(transmitting == 1) { - // txlength is howmany bytes in txbuffer have been use - last_error = writeTransmission(txAddress, &txBuffer[txQueued], txLength - txQueued, sendStop); - if(last_error == I2C_ERROR_CONTINUE){ - txQueued = txLength; - } else if( last_error == I2C_ERROR_OK){ - rxIndex = 0; - rxLength = rxQueued; - rxQueued = 0; - txQueued = 0; // the SendStop=true will restart all Queueing - } + esp_err_t err = ESP_OK; + if(sendStop){ + err = i2cWrite(num, txAddress, txBuffer, txLength, _timeOutMillis); +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); +#endif } else { - last_error = I2C_ERROR_NO_BEGIN; - flush(); + //mark as non-stop + nonStop = true; +#if !CONFIG_DISABLE_HAL_LOCKS + nonStopTask = xTaskGetCurrentTaskHandle(); +#endif } - txIndex = 0; - txLength = 0; - transmitting = 0; - return (last_error == I2C_ERROR_CONTINUE)?I2C_ERROR_OK:last_error; // Don't return Continue for compatibility. + switch(err){ + case ESP_OK: return 0; + case ESP_FAIL: return 2; + case ESP_ERR_TIMEOUT: return 5; + default: break; + } + return 4; } -/* @stickBreaker 11/2017 fix for ReSTART timeout, ISR - */ uint8_t TwoWire::requestFrom(uint16_t address, uint8_t size, bool sendStop) { - //use internal Wire rxBuffer, multiple requestFrom()'s may be pending, try to share rxBuffer - uint32_t cnt = rxQueued; // currently queued reads, next available position in rxBuffer - if(cnt < (I2C_BUFFER_LENGTH-1) && (size + cnt) <= I2C_BUFFER_LENGTH) { // any room left in rxBuffer - rxQueued += size; - } else { // no room to receive more! - log_e("rxBuff overflow %d", cnt + size); - cnt = 0; - last_error = I2C_ERROR_MEMORY; - flush(); - return cnt; - } - - last_error = readTransmission(address, &rxBuffer[cnt], size, sendStop, &cnt); - rxIndex = 0; - - rxLength = cnt; - - if( last_error != I2C_ERROR_CONTINUE){ // not a buffered ReSTART operation - // so this operation actually moved data, queuing is done. - rxQueued = 0; - txQueued = 0; // the SendStop=true will restart all Queueing or error condition - } - - if(last_error != I2C_ERROR_OK){ // ReSTART on read does not return any data - cnt = 0; + esp_err_t err = ESP_OK; + if(nonStop +#if !CONFIG_DISABLE_HAL_LOCKS + && nonStopTask == xTaskGetCurrentTaskHandle() +#endif + ){ + if(address != txAddress){ + log_e("Unfinished Repeated Start transaction! Expected address do not match! %u != %u", address, txAddress); + return 0; + } + nonStop = false; + rxIndex = 0; + rxLength = 0; + err = i2cWriteReadNonStop(num, address, txBuffer, txLength, rxBuffer, size, _timeOutMillis, &rxLength); + } else { +#if !CONFIG_DISABLE_HAL_LOCKS + //acquire lock + if(lock == NULL || xSemaphoreTake(lock, portMAX_DELAY) != pdTRUE){ + log_e("could not acquire lock"); + return 0; + } +#endif + rxIndex = 0; + rxLength = 0; + err = i2cRead(num, address, rxBuffer, size, _timeOutMillis, &rxLength); } - - return cnt; +#if !CONFIG_DISABLE_HAL_LOCKS + //release lock + xSemaphoreGive(lock); +#endif + return rxLength; } size_t TwoWire::write(uint8_t data) { - if(transmitting) { - if(txLength >= I2C_BUFFER_LENGTH) { - last_error = I2C_ERROR_MEMORY; - return 0; - } - txBuffer[txIndex] = data; - ++txIndex; - txLength = txIndex; - return 1; + if(txLength >= I2C_BUFFER_LENGTH) { + return 0; } - last_error = I2C_ERROR_NO_BEGIN; // no begin, not transmitting - return 0; + txBuffer[txLength++] = data; + return 1; } size_t TwoWire::write(const uint8_t *data, size_t quantity) @@ -262,8 +335,7 @@ int TwoWire::read(void) { int value = -1; if(rxIndex < rxLength) { - value = rxBuffer[rxIndex]; - ++rxIndex; + value = rxBuffer[rxIndex++]; } return value; } @@ -281,11 +353,8 @@ void TwoWire::flush(void) { rxIndex = 0; rxLength = 0; - txIndex = 0; txLength = 0; - rxQueued = 0; - txQueued = 0; - i2cFlush(i2c); // cleanup + //i2cFlush(num); // cleanup } uint8_t TwoWire::requestFrom(uint8_t address, uint8_t quantity, uint8_t sendStop) @@ -333,56 +402,5 @@ uint8_t TwoWire::endTransmission(void) return endTransmission(true); } -/* stickbreaker Nov2017 better error reporting - */ -uint8_t TwoWire::lastError() -{ - return (uint8_t)last_error; -} - -const char ERRORTEXT[] = - "OK\0" - "DEVICE\0" - "ACK\0" - "TIMEOUT\0" - "BUS\0" - "BUSY\0" - "MEMORY\0" - "CONTINUE\0" - "NO_BEGIN\0" - "\0"; - - -char * TwoWire::getErrorText(uint8_t err) -{ - uint8_t t = 0; - bool found = false; - char * message = (char*)&ERRORTEXT; - - while(!found && message[0]) { - found = t == err; - if(!found) { - message = message + strlen(message) + 1; - t++; - } - } - if(!found) { - return NULL; - } else { - return message; - } -} - -/*stickbreaker Dump i2c Interrupt buffer, i2c isr Debugging - */ - -uint32_t TwoWire::setDebugFlags( uint32_t setBits, uint32_t resetBits){ - return i2cDebug(i2c,setBits,resetBits); -} - -bool TwoWire::busy(void){ - return ((i2cGetStatus(i2c) & 16 )==16); -} - TwoWire Wire = TwoWire(0); TwoWire Wire1 = TwoWire(1); diff --git a/libraries/Wire/src/Wire.h b/libraries/Wire/src/Wire.h index 3cee73104bd..08e52f5d011 100644 --- a/libraries/Wire/src/Wire.h +++ b/libraries/Wire/src/Wire.h @@ -20,17 +20,20 @@ Modified December 2014 by Ivan Grokhotkov (ivan@esp8266.com) - esp8266 support Modified April 2015 by Hrsto Gochkov (ficeto@ficeto.com) - alternative esp8266 support Modified November 2017 by Chuck Todd to use ISR and increase stability. + Modified Nov 2021 by Hristo Gochkov to support ESP-IDF API */ #ifndef TwoWire_h #define TwoWire_h #include +#if !CONFIG_DISABLE_HAL_LOCKS #include "freertos/FreeRTOS.h" -#include "freertos/queue.h" +#include "freertos/task.h" +#include "freertos/semphr.h" +#endif #include "Stream.h" -#define STICKBREAKER 'V1.1.0' #ifndef I2C_BUFFER_LENGTH #define I2C_BUFFER_LENGTH 128 #endif @@ -43,28 +46,21 @@ class TwoWire: public Stream uint8_t num; int8_t sda; int8_t scl; - i2c_t * i2c; uint8_t rxBuffer[I2C_BUFFER_LENGTH]; - uint16_t rxIndex; - uint16_t rxLength; - uint16_t rxQueued; //@stickBreaker + size_t rxIndex; + size_t rxLength; uint8_t txBuffer[I2C_BUFFER_LENGTH]; - uint16_t txIndex; - uint16_t txLength; + size_t txLength; uint16_t txAddress; - uint16_t txQueued; //@stickbreaker - - uint8_t transmitting; - /* slave Mode, not yet Stickbreaker - static user_onRequest uReq[2]; - static user_onReceive uRcv[2]; - void onRequestService(void); - void onReceiveService(uint8_t*, int); - */ - i2c_err_t last_error; // @stickBreaker from esp32-hal-i2c.h - uint16_t _timeOutMillis; + + uint32_t _timeOutMillis; + bool nonStop; +#if !CONFIG_DISABLE_HAL_LOCKS + TaskHandle_t nonStopTask; + SemaphoreHandle_t lock; +#endif public: TwoWire(uint8_t bus_num); @@ -74,20 +70,13 @@ class TwoWire: public Stream bool setPins(int sda, int scl); bool begin(int sda=-1, int scl=-1, uint32_t frequency=0); // returns true, if successful init of i2c bus - // calling will attemp to recover hung bus - - void setClock(uint32_t frequency); // change bus clock without initing hardware - size_t getClock(); // current bus clock rate in hz + bool end(); void setTimeOut(uint16_t timeOutMillis); // default timeout of i2c transactions is 50ms uint16_t getTimeOut(); - uint8_t lastError(); - char * getErrorText(uint8_t err); - - //@stickBreaker for big blocks and ISR model - i2c_err_t writeTransmission(uint16_t address, uint8_t* buff, uint16_t size, bool sendStop=true); - i2c_err_t readTransmission(uint16_t address, uint8_t* buff, uint16_t size, bool sendStop=true, uint32_t *readCount=NULL); + bool setClock(uint32_t); + uint32_t getClock(); void beginTransmission(uint16_t address); void beginTransmission(uint8_t address); @@ -134,22 +123,9 @@ class TwoWire: public Stream void onReceive( void (*)(int) ); void onRequest( void (*)(void) ); - - uint32_t setDebugFlags( uint32_t setBits, uint32_t resetBits); - bool busy(); }; extern TwoWire Wire; extern TwoWire Wire1; - -/* -V1.1.0 08JAN2019 Support CPU Clock frequency changes -V1.0.2 30NOV2018 stop returning I2C_ERROR_CONTINUE on ReSTART operations, regain compatibility with Arduino libs -V1.0.1 02AUG2018 First Fix after release, Correct ReSTART handling, change Debug control, change begin() - to a function, this allow reporting if bus cannot be initialized, Wire.begin() can be used to recover - a hung bus busy condition. -V0.2.2 13APR2018 preserve custom SCL,SDA,Frequency when no parameters passed to begin() -V0.2.1 15MAR2018 Hardware reset, Glitch prevention, adding destructor for second i2c testing -*/ #endif diff --git a/platform.txt b/platform.txt index 65df452ad62..1b92b64efa8 100644 --- a/platform.txt +++ b/platform.txt @@ -10,8 +10,8 @@ tools.esptool_py.cmd=esptool tools.esptool_py.cmd.linux=esptool.py tools.esptool_py.cmd.windows=esptool.exe -tools.esptool_py.network_cmd=python "{runtime.platform.path}/tools/espota.py" -tools.esptool_py.network_cmd.windows="{runtime.platform.path}/tools/espota.exe" +tools.esptool_py.network_cmd=python "{runtime.platform.path}/tools/espota.py" -r +tools.esptool_py.network_cmd.windows="{runtime.platform.path}/tools/espota.exe" -r tools.gen_esp32part.cmd=python "{runtime.platform.path}/tools/gen_esp32part.py" tools.gen_esp32part.cmd.windows="{runtime.platform.path}/tools/gen_esp32part.exe" @@ -23,12 +23,12 @@ compiler.prefix={build.tarch}-{build.target}-elf- # # ESP32 Support Start # -compiler.cpreprocessor.flags.esp32=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-2897-g61299f879e" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/port/xtensa/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32" "-I{compiler.sdk.path}/include/soc/esp32/include" "-I{compiler.sdk.path}/include/hal/esp32/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32" "-I{compiler.sdk.path}/include/esp_rom/esp32" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/esp32/include" "-I{compiler.sdk.path}/include/xtensa/include" "-I{compiler.sdk.path}/include/xtensa/esp32/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/xtensa" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/xtensa" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/bt/common/osi/include" "-I{compiler.sdk.path}/include/bt/include/esp32/include" "-I{compiler.sdk.path}/include/bt/common/api/include/api" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/blufi/include" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/include" "-I{compiler.sdk.path}/include/bt/host/bluedroid/api/include/api" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/perfmon/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/ulp/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/button/button/include" "-I{compiler.sdk.path}/include/json_parser" "-I{compiler.sdk.path}/include/json_parser/jsmn/include" "-I{compiler.sdk.path}/include/json_generator" "-I{compiler.sdk.path}/include/esp_schedule/include" "-I{compiler.sdk.path}/include/esp_rainmaker/include" "-I{compiler.sdk.path}/include/qrcode/include" "-I{compiler.sdk.path}/include/ws2812_led" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dotprod/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/support/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/hann/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_harris/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/flat_top/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/iir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/add/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sub/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mul/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/addc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mulc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sqrt/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/matrix/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fft/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dct/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/conv/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/common/include" "-I{compiler.sdk.path}/include/esp-face/include" "-I{compiler.sdk.path}/include/esp-face/include/tool" "-I{compiler.sdk.path}/include/esp-face/include/typedef" "-I{compiler.sdk.path}/include/esp-face/include/image" "-I{compiler.sdk.path}/include/esp-face/include/math" "-I{compiler.sdk.path}/include/esp-face/include/nn" "-I{compiler.sdk.path}/include/esp-face/include/layer" "-I{compiler.sdk.path}/include/esp-face/include/detect" "-I{compiler.sdk.path}/include/esp-face/include/model_zoo" "-I{compiler.sdk.path}/include/esp32-camera/driver/include" "-I{compiler.sdk.path}/include/esp32-camera/conversions/include" "-I{compiler.sdk.path}/include/fb_gfx/include" -compiler.c.elf.libs.esp32=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lbt -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lperfmon -lspiffs -lulp -lwifi_provisioning -lbutton -ljson_parser -ljson_generator -lesp_schedule -lesp_rainmaker -lqrcode -lws2812_led -lesp-dsp -lesp32-camera -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lperfmon -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lesp_rainmaker -lmqtt -lwifi_provisioning -lprotocomm -lbt -lbtdm_app -lprotobuf-c -lmdns -lconsole -ljson -ljson_parser -ljson_generator -lesp_schedule -lqrcode -lcat_face_detect -lhuman_face_detect -ldl -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lesp_phy -lphy -lesp_phy -lphy -lrtc -lxt_hal -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc +compiler.cpreprocessor.flags.esp32=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-3235-g3e370c4296" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions/freertos" "-I{compiler.sdk.path}/include/freertos/port/xtensa/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32" "-I{compiler.sdk.path}/include/soc/esp32/include" "-I{compiler.sdk.path}/include/hal/esp32/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32" "-I{compiler.sdk.path}/include/esp_rom/esp32" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/esp32/include" "-I{compiler.sdk.path}/include/xtensa/include" "-I{compiler.sdk.path}/include/xtensa/esp32/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/xtensa" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/xtensa" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/bt/common/osi/include" "-I{compiler.sdk.path}/include/bt/include/esp32/include" "-I{compiler.sdk.path}/include/bt/common/api/include/api" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/blufi/include" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/include" "-I{compiler.sdk.path}/include/bt/host/bluedroid/api/include/api" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/perfmon/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/ulp/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/button/button/include" "-I{compiler.sdk.path}/include/json_parser" "-I{compiler.sdk.path}/include/json_parser/jsmn/include" "-I{compiler.sdk.path}/include/json_generator" "-I{compiler.sdk.path}/include/esp_schedule/include" "-I{compiler.sdk.path}/include/esp_rainmaker/include" "-I{compiler.sdk.path}/include/qrcode/include" "-I{compiler.sdk.path}/include/ws2812_led" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dotprod/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/support/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/hann/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_harris/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/flat_top/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/iir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/add/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sub/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mul/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/addc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mulc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sqrt/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/matrix/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fft/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dct/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/conv/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/common/include" "-I{compiler.sdk.path}/include/esp-face/include" "-I{compiler.sdk.path}/include/esp-face/include/tool" "-I{compiler.sdk.path}/include/esp-face/include/typedef" "-I{compiler.sdk.path}/include/esp-face/include/image" "-I{compiler.sdk.path}/include/esp-face/include/math" "-I{compiler.sdk.path}/include/esp-face/include/nn" "-I{compiler.sdk.path}/include/esp-face/include/layer" "-I{compiler.sdk.path}/include/esp-face/include/detect" "-I{compiler.sdk.path}/include/esp-face/include/model_zoo" "-I{compiler.sdk.path}/include/esp32-camera/driver/include" "-I{compiler.sdk.path}/include/esp32-camera/conversions/include" "-I{compiler.sdk.path}/include/fb_gfx/include" +compiler.c.elf.libs.esp32=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lbt -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lperfmon -lspiffs -lulp -lwifi_provisioning -lbutton -ljson_parser -ljson_generator -lesp_schedule -lesp_rainmaker -lqrcode -lws2812_led -lesp-dsp -lesp32-camera -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lperfmon -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lesp_rainmaker -lmqtt -lwifi_provisioning -lprotocomm -lbt -lbtdm_app -lprotobuf-c -lmdns -lconsole -ljson -ljson_parser -ljson_generator -lesp_schedule -lqrcode -lcat_face_detect -lhuman_face_detect -ldl -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lrtc -lesp_phy -lphy -lrtc -lesp_phy -lphy -lrtc -lxt_hal -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc compiler.c.flags.esp32=-mlongcalls -Wno-frame-address -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu99 -Wno-old-style-declaration -MMD -c compiler.cpp.flags.esp32=-mlongcalls -Wno-frame-address -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu++11 -fexceptions -fno-rtti -MMD -c compiler.S.flags.esp32=-ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -x assembler-with-cpp -MMD -c -compiler.c.elf.flags.esp32=-T esp32.rom.redefined.ld -T memory.ld -T sections.ld -T esp32.rom.ld -T esp32.rom.api.ld -T esp32.rom.libgcc.ld -T esp32.rom.newlib-data.ld -T esp32.rom.syscalls.ld -T esp32.peripherals.ld -mlongcalls -Wno-frame-address -Wl,--cref -Wl,--gc-sections -fno-rtti -fno-lto -u _Z5setupv -u _Z4loopv -Wl,--wrap=mbedtls_mpi_exp_mod -u esp_app_desc -u pthread_include_pthread_impl -u pthread_include_pthread_cond_impl -u pthread_include_pthread_local_storage_impl -u ld_include_highint_hdl -u start_app -u start_app_other_cores -u __ubsan_include -Wl,--wrap=longjmp -u __assert_func -u vfs_include_syscalls_impl -Wl,--undefined=uxTopUsedPriority -u app_main -u newlib_include_heap_impl -u newlib_include_syscalls_impl -u newlib_include_pthread_impl -u newlib_include_assert_impl -u __cxa_guard_dummy +compiler.c.elf.flags.esp32=-T esp32.rom.redefined.ld -T memory.ld -T sections.ld -T esp32.rom.ld -T esp32.rom.api.ld -T esp32.rom.libgcc.ld -T esp32.rom.newlib-data.ld -T esp32.rom.syscalls.ld -T esp32.peripherals.ld -mlongcalls -Wno-frame-address -Wl,--cref -Wl,--gc-sections -fno-rtti -fno-lto -u ld_include_hli_vectors_bt -u _Z5setupv -u _Z4loopv -Wl,--wrap=mbedtls_mpi_exp_mod -u esp_app_desc -u pthread_include_pthread_impl -u pthread_include_pthread_cond_impl -u pthread_include_pthread_local_storage_impl -u ld_include_highint_hdl -u start_app -u start_app_other_cores -u __ubsan_include -Wl,--wrap=longjmp -u __assert_func -u vfs_include_syscalls_impl -Wl,--undefined=uxTopUsedPriority -u app_main -u newlib_include_heap_impl -u newlib_include_syscalls_impl -u newlib_include_pthread_impl -u newlib_include_assert_impl -u __cxa_guard_dummy compiler.ar.flags.esp32=cr build.extra_flags.esp32=-DARDUINO_USB_CDC_ON_BOOT=0 # @@ -38,8 +38,8 @@ build.extra_flags.esp32=-DARDUINO_USB_CDC_ON_BOOT=0 # # ESP32S2 Support Start # -compiler.cpreprocessor.flags.esp32s2=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-2897-g61299f879e" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/port/xtensa/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32s2" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32s2" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32s2/private_include" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32s2" "-I{compiler.sdk.path}/include/soc/esp32s2/include" "-I{compiler.sdk.path}/include/hal/esp32s2/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32s2" "-I{compiler.sdk.path}/include/esp_rom/esp32s2" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/xtensa/include" "-I{compiler.sdk.path}/include/xtensa/esp32s2/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32s2/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32s2/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32s2/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/xtensa" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32s2" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/xtensa" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_https_server/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32s2" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/perfmon/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/touch_element/include" "-I{compiler.sdk.path}/include/ulp/include" "-I{compiler.sdk.path}/include/usb/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/freertos/include/freertos" "-I{compiler.sdk.path}/include/arduino_tinyusb/tinyusb/src" "-I{compiler.sdk.path}/include/arduino_tinyusb/include" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dotprod/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/support/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/hann/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_harris/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/flat_top/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/iir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/add/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sub/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mul/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/addc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mulc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sqrt/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/matrix/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fft/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dct/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/conv/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/common/include" "-I{compiler.sdk.path}/include/esp-face/include" "-I{compiler.sdk.path}/include/esp-face/include/tool" "-I{compiler.sdk.path}/include/esp-face/include/typedef" "-I{compiler.sdk.path}/include/esp-face/include/image" "-I{compiler.sdk.path}/include/esp-face/include/math" "-I{compiler.sdk.path}/include/esp-face/include/nn" "-I{compiler.sdk.path}/include/esp-face/include/layer" "-I{compiler.sdk.path}/include/esp-face/include/detect" "-I{compiler.sdk.path}/include/esp-face/include/model_zoo" "-I{compiler.sdk.path}/include/esp32-camera/driver/include" "-I{compiler.sdk.path}/include/esp32-camera/conversions/include" "-I{compiler.sdk.path}/include/fb_gfx/include" -compiler.c.elf.libs.esp32s2=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_https_server -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lperfmon -lspiffs -ltouch_element -lulp -lusb -lwifi_provisioning -lesp-dsp -lesp32-camera -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_https_server -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lmqtt -lperfmon -ltouch_element -lusb -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lwifi_provisioning -lprotocomm -lprotobuf-c -lmdns -lconsole -ljson -larduino_tinyusb -lcat_face_detect -lhuman_face_detect -ldl -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lesp_phy -lphy -lesp_phy -lphy -lxt_hal -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc +compiler.cpreprocessor.flags.esp32s2=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-3235-g3e370c4296" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions/freertos" "-I{compiler.sdk.path}/include/freertos/port/xtensa/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32s2" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32s2" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32s2/private_include" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32s2" "-I{compiler.sdk.path}/include/soc/esp32s2/include" "-I{compiler.sdk.path}/include/hal/esp32s2/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32s2" "-I{compiler.sdk.path}/include/esp_rom/esp32s2" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/xtensa/include" "-I{compiler.sdk.path}/include/xtensa/esp32s2/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32s2/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32s2/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32s2/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/xtensa" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32s2" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/xtensa" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_https_server/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32s2" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/perfmon/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/usb/include" "-I{compiler.sdk.path}/include/touch_element/include" "-I{compiler.sdk.path}/include/ulp/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/freertos/include/freertos" "-I{compiler.sdk.path}/include/arduino_tinyusb/tinyusb/src" "-I{compiler.sdk.path}/include/arduino_tinyusb/include" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dotprod/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/support/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/hann/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_harris/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/blackman_nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/nuttall/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/windows/flat_top/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/iir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fir/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/add/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sub/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mul/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/addc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/mulc/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/math/sqrt/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/matrix/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/fft/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/dct/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/conv/include" "-I{compiler.sdk.path}/include/esp-dsp/modules/common/include" "-I{compiler.sdk.path}/include/esp-face/include" "-I{compiler.sdk.path}/include/esp-face/include/tool" "-I{compiler.sdk.path}/include/esp-face/include/typedef" "-I{compiler.sdk.path}/include/esp-face/include/image" "-I{compiler.sdk.path}/include/esp-face/include/math" "-I{compiler.sdk.path}/include/esp-face/include/nn" "-I{compiler.sdk.path}/include/esp-face/include/layer" "-I{compiler.sdk.path}/include/esp-face/include/detect" "-I{compiler.sdk.path}/include/esp-face/include/model_zoo" "-I{compiler.sdk.path}/include/esp32-camera/driver/include" "-I{compiler.sdk.path}/include/esp32-camera/conversions/include" "-I{compiler.sdk.path}/include/fb_gfx/include" +compiler.c.elf.libs.esp32s2=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_https_server -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lperfmon -lspiffs -lusb -ltouch_element -lulp -lwifi_provisioning -lesp-dsp -lesp32-camera -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_https_server -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lmqtt -lperfmon -lusb -ltouch_element -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lwifi_provisioning -lprotocomm -lprotobuf-c -lmdns -lconsole -ljson -larduino_tinyusb -lcat_face_detect -lhuman_face_detect -ldl -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lxtensa -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lulp -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lesp_phy -lphy -lesp_phy -lphy -lxt_hal -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc compiler.c.flags.esp32s2=-mlongcalls -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu99 -Wno-old-style-declaration -MMD -c compiler.cpp.flags.esp32s2=-mlongcalls -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu++11 -fexceptions -fno-rtti -MMD -c compiler.S.flags.esp32s2=-ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -O2 -Wwrite-strings -fstack-protector -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -x assembler-with-cpp -MMD -c @@ -53,8 +53,8 @@ build.extra_flags.esp32s2=-DARDUINO_USB_CDC_ON_BOOT={build.cdc_on_boot} -DARDUIN # # ESP32C3 Support Start # -compiler.cpreprocessor.flags.esp32c3=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-2897-g61299f879e" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/port/riscv/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32c3" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32c3" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32c3/private_include" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32c3" "-I{compiler.sdk.path}/include/soc/esp32c3/include" "-I{compiler.sdk.path}/include/hal/esp32c3/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32c3" "-I{compiler.sdk.path}/include/esp_rom/esp32c3" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/include/riscv" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/riscv/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32c3/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32c3/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32c3/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/riscv" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32c3" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/riscv" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/bt/common/osi/include" "-I{compiler.sdk.path}/include/bt/include/esp32c3/include" "-I{compiler.sdk.path}/include/bt/common/api/include/api" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/blufi/include" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/include" "-I{compiler.sdk.path}/include/bt/host/bluedroid/api/include/api" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_https_server/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32c3" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/fb_gfx/include" -compiler.c.elf.libs.esp32c3=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lbt -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_https_server -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lspiffs -lwifi_provisioning -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_https_server -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lmqtt -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lwifi_provisioning -lprotocomm -lbt -lbtdm_app -lprotobuf-c -lmdns -lconsole -ljson -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lesp_phy -lphy -lesp_phy -lphy -lbtbb -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc +compiler.cpreprocessor.flags.esp32c3=-DHAVE_CONFIG_H -DMBEDTLS_CONFIG_FILE="mbedtls/esp_config.h" -DUNITY_INCLUDE_CONFIG_H -DWITH_POSIX -D_GNU_SOURCE -DIDF_VER="v4.4-dev-3235-g3e370c4296" -DESP_PLATFORM "-I{compiler.sdk.path}/include/config" "-I{compiler.sdk.path}/include/newlib/platform_include" "-I{compiler.sdk.path}/include/freertos/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions/freertos" "-I{compiler.sdk.path}/include/freertos/port/riscv/include" "-I{compiler.sdk.path}/include/freertos/include/esp_additions" "-I{compiler.sdk.path}/include/esp_hw_support/include" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc" "-I{compiler.sdk.path}/include/esp_hw_support/include/soc/esp32c3" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32c3" "-I{compiler.sdk.path}/include/esp_hw_support/port/esp32c3/private_include" "-I{compiler.sdk.path}/include/heap/include" "-I{compiler.sdk.path}/include/log/include" "-I{compiler.sdk.path}/include/lwip/include/apps" "-I{compiler.sdk.path}/include/lwip/include/apps/sntp" "-I{compiler.sdk.path}/include/lwip/lwip/src/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include" "-I{compiler.sdk.path}/include/lwip/port/esp32/include/arch" "-I{compiler.sdk.path}/include/soc/include" "-I{compiler.sdk.path}/include/soc/esp32c3" "-I{compiler.sdk.path}/include/soc/esp32c3/include" "-I{compiler.sdk.path}/include/hal/esp32c3/include" "-I{compiler.sdk.path}/include/hal/include" "-I{compiler.sdk.path}/include/hal/platform_port/include" "-I{compiler.sdk.path}/include/esp_rom/include" "-I{compiler.sdk.path}/include/esp_rom/include/esp32c3" "-I{compiler.sdk.path}/include/esp_rom/esp32c3" "-I{compiler.sdk.path}/include/esp_common/include" "-I{compiler.sdk.path}/include/esp_system/include" "-I{compiler.sdk.path}/include/esp_system/port/soc" "-I{compiler.sdk.path}/include/esp_system/port/include/riscv" "-I{compiler.sdk.path}/include/esp_system/port/public_compat" "-I{compiler.sdk.path}/include/riscv/include" "-I{compiler.sdk.path}/include/driver/include" "-I{compiler.sdk.path}/include/driver/esp32c3/include" "-I{compiler.sdk.path}/include/esp_pm/include" "-I{compiler.sdk.path}/include/esp_ringbuf/include" "-I{compiler.sdk.path}/include/efuse/include" "-I{compiler.sdk.path}/include/efuse/esp32c3/include" "-I{compiler.sdk.path}/include/vfs/include" "-I{compiler.sdk.path}/include/esp_wifi/include" "-I{compiler.sdk.path}/include/esp_event/include" "-I{compiler.sdk.path}/include/esp_netif/include" "-I{compiler.sdk.path}/include/esp_eth/include" "-I{compiler.sdk.path}/include/tcpip_adapter/include" "-I{compiler.sdk.path}/include/esp_phy/include" "-I{compiler.sdk.path}/include/esp_phy/esp32c3/include" "-I{compiler.sdk.path}/include/esp_ipc/include" "-I{compiler.sdk.path}/include/app_trace/include" "-I{compiler.sdk.path}/include/esp_timer/include" "-I{compiler.sdk.path}/include/mbedtls/port/include" "-I{compiler.sdk.path}/include/mbedtls/mbedtls/include" "-I{compiler.sdk.path}/include/mbedtls/esp_crt_bundle/include" "-I{compiler.sdk.path}/include/app_update/include" "-I{compiler.sdk.path}/include/spi_flash/include" "-I{compiler.sdk.path}/include/bootloader_support/include" "-I{compiler.sdk.path}/include/nvs_flash/include" "-I{compiler.sdk.path}/include/pthread/include" "-I{compiler.sdk.path}/include/esp_gdbstub/include" "-I{compiler.sdk.path}/include/esp_gdbstub/riscv" "-I{compiler.sdk.path}/include/esp_gdbstub/esp32c3" "-I{compiler.sdk.path}/include/espcoredump/include" "-I{compiler.sdk.path}/include/espcoredump/include/port/riscv" "-I{compiler.sdk.path}/include/wpa_supplicant/include" "-I{compiler.sdk.path}/include/wpa_supplicant/port/include" "-I{compiler.sdk.path}/include/wpa_supplicant/esp_supplicant/include" "-I{compiler.sdk.path}/include/ieee802154/include" "-I{compiler.sdk.path}/include/asio/asio/asio/include" "-I{compiler.sdk.path}/include/asio/port/include" "-I{compiler.sdk.path}/include/bt/common/osi/include" "-I{compiler.sdk.path}/include/bt/include/esp32c3/include" "-I{compiler.sdk.path}/include/bt/common/api/include/api" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/blufi/include" "-I{compiler.sdk.path}/include/bt/common/btc/profile/esp/include" "-I{compiler.sdk.path}/include/bt/host/bluedroid/api/include/api" "-I{compiler.sdk.path}/include/cbor/port/include" "-I{compiler.sdk.path}/include/unity/include" "-I{compiler.sdk.path}/include/unity/unity/src" "-I{compiler.sdk.path}/include/cmock/CMock/src" "-I{compiler.sdk.path}/include/coap/port/include" "-I{compiler.sdk.path}/include/coap/libcoap/include" "-I{compiler.sdk.path}/include/console" "-I{compiler.sdk.path}/include/nghttp/port/include" "-I{compiler.sdk.path}/include/nghttp/nghttp2/lib/includes" "-I{compiler.sdk.path}/include/esp-tls" "-I{compiler.sdk.path}/include/esp-tls/esp-tls-crypto" "-I{compiler.sdk.path}/include/esp_adc_cal/include" "-I{compiler.sdk.path}/include/esp_hid/include" "-I{compiler.sdk.path}/include/tcp_transport/include" "-I{compiler.sdk.path}/include/esp_http_client/include" "-I{compiler.sdk.path}/include/esp_http_server/include" "-I{compiler.sdk.path}/include/esp_https_ota/include" "-I{compiler.sdk.path}/include/esp_https_server/include" "-I{compiler.sdk.path}/include/esp_lcd/include" "-I{compiler.sdk.path}/include/esp_lcd/interface" "-I{compiler.sdk.path}/include/protobuf-c/protobuf-c" "-I{compiler.sdk.path}/include/protocomm/include/common" "-I{compiler.sdk.path}/include/protocomm/include/security" "-I{compiler.sdk.path}/include/protocomm/include/transports" "-I{compiler.sdk.path}/include/mdns/include" "-I{compiler.sdk.path}/include/esp_local_ctrl/include" "-I{compiler.sdk.path}/include/sdmmc/include" "-I{compiler.sdk.path}/include/esp_serial_slave_link/include" "-I{compiler.sdk.path}/include/esp_websocket_client/include" "-I{compiler.sdk.path}/include/expat/expat/expat/lib" "-I{compiler.sdk.path}/include/expat/port/include" "-I{compiler.sdk.path}/include/wear_levelling/include" "-I{compiler.sdk.path}/include/fatfs/diskio" "-I{compiler.sdk.path}/include/fatfs/vfs" "-I{compiler.sdk.path}/include/fatfs/src" "-I{compiler.sdk.path}/include/freemodbus/common/include" "-I{compiler.sdk.path}/include/idf_test/include" "-I{compiler.sdk.path}/include/idf_test/include/esp32c3" "-I{compiler.sdk.path}/include/jsmn/include" "-I{compiler.sdk.path}/include/json/cJSON" "-I{compiler.sdk.path}/include/libsodium/libsodium/src/libsodium/include" "-I{compiler.sdk.path}/include/libsodium/port_include" "-I{compiler.sdk.path}/include/mqtt/esp-mqtt/include" "-I{compiler.sdk.path}/include/openssl/include" "-I{compiler.sdk.path}/include/spiffs/include" "-I{compiler.sdk.path}/include/wifi_provisioning/include" "-I{compiler.sdk.path}/include/esp_littlefs/src" "-I{compiler.sdk.path}/include/esp_littlefs/include" "-I{compiler.sdk.path}/include/fb_gfx/include" +compiler.c.elf.libs.esp32c3=-lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lasio -lbt -lcbor -lunity -lcmock -lcoap -lconsole -lnghttp -lesp-tls -lesp_adc_cal -lesp_hid -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lesp_https_server -lesp_lcd -lprotobuf-c -lprotocomm -lmdns -lesp_local_ctrl -lsdmmc -lesp_serial_slave_link -lesp_websocket_client -lexpat -lwear_levelling -lfatfs -lfreemodbus -ljsmn -ljson -llibsodium -lmqtt -lopenssl -lspiffs -lwifi_provisioning -lesp_littlefs -lfb_gfx -lasio -lcbor -lcmock -lunity -lcoap -lesp_lcd -lesp_local_ctrl -lesp_https_server -lesp_websocket_client -lexpat -lfreemodbus -ljsmn -llibsodium -lmqtt -lesp_adc_cal -lesp_hid -lfatfs -lwear_levelling -lopenssl -lspiffs -lwifi_provisioning -lprotocomm -lbt -lbtdm_app -lprotobuf-c -lmdns -lconsole -ljson -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lesp_ringbuf -lefuse -lesp_ipc -ldriver -lesp_pm -lmbedtls -lapp_update -lbootloader_support -lspi_flash -lnvs_flash -lpthread -lesp_gdbstub -lespcoredump -lesp_phy -lesp_system -lesp_rom -lhal -lvfs -lesp_eth -ltcpip_adapter -lesp_netif -lesp_event -lwpa_supplicant -lesp_wifi -llwip -llog -lheap -lsoc -lesp_hw_support -lriscv -lesp_common -lesp_timer -lfreertos -lnewlib -lcxx -lapp_trace -lnghttp -lesp-tls -ltcp_transport -lesp_http_client -lesp_http_server -lesp_https_ota -lsdmmc -lesp_serial_slave_link -lmbedtls -lmbedcrypto -lmbedx509 -lcoexist -lcore -lespnow -lmesh -lnet80211 -lpp -lsmartconfig -lwapi -lphy -lbtbb -lesp_phy -lphy -lbtbb -lesp_phy -lphy -lbtbb -lm -lnewlib -lstdc++ -lpthread -lgcc -lcxx -lapp_trace -lgcov -lapp_trace -lgcov -lc compiler.c.flags.esp32c3=-march=rv32imc -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -Wno-error=format= -nostartfiles -Wno-format -Og -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu99 -Wno-old-style-declaration -MMD -c compiler.cpp.flags.esp32c3=-march=rv32imc -ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -Wno-error=format= -nostartfiles -Wno-format -Og -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -std=gnu++11 -fno-exceptions -fno-rtti -MMD -c compiler.S.flags.esp32c3=-ffunction-sections -fdata-sections -Wno-error=unused-function -Wno-error=unused-variable -Wno-error=deprecated-declarations -Wno-unused-parameter -Wno-sign-compare -ggdb -Wno-error=format= -nostartfiles -Wno-format -Og -fstrict-volatile-bitfields -Wno-error=unused-but-set-variable -fno-jump-tables -fno-tree-switch-conversion -x assembler-with-cpp -MMD -c @@ -172,7 +172,7 @@ recipe.size.regex.data=^(?:\.dram0\.data|\.dram0\.bss|\.noinit)\s+([0-9]+).* tools.esptool_py.upload.protocol=esp32 tools.esptool_py.upload.params.verbose= tools.esptool_py.upload.params.quiet= -tools.esptool_py.upload.pattern_args=--chip {build.mcu} --port "{serial.port}" --baud {upload.speed} {upload.flags} --before default_reset --after hard_reset write_flash -z --flash_mode {build.flash_mode} --flash_freq {build.flash_freq} --flash_size detect 0xe000 "{runtime.platform.path}/tools/partitions/boot_app0.bin" {build.bootloader_addr} "{build.path}/{build.project_name}.bootloader.bin" 0x10000 "{build.path}/{build.project_name}.bin" 0x8000 "{build.path}/{build.project_name}.partitions.bin" {upload.extra_flags} +tools.esptool_py.upload.pattern_args=--chip {build.mcu} --port "{serial.port}" --baud {upload.speed} {upload.flags} --before default_reset --after hard_reset write_flash -z --flash_mode {build.flash_mode} --flash_freq {build.flash_freq} --flash_size {build.flash_size} 0xe000 "{runtime.platform.path}/tools/partitions/boot_app0.bin" {build.bootloader_addr} "{build.path}/{build.project_name}.bootloader.bin" 0x10000 "{build.path}/{build.project_name}.bin" 0x8000 "{build.path}/{build.project_name}.partitions.bin" {upload.extra_flags} tools.esptool_py.upload.pattern="{path}/{cmd}" {upload.pattern_args} tools.esptool_py.upload.pattern.linux=python "{path}/{cmd}" {upload.pattern_args} tools.esptool_py.upload.network_pattern={network_cmd} -i "{serial.port}" -p "{network.port}" "--auth={network.password}" -f "{build.path}/{build.project_name}.bin" diff --git a/tools/esptool.py b/tools/esptool.py index d108fc3d9a6..7b8a32fc8d3 100755 --- a/tools/esptool.py +++ b/tools/esptool.py @@ -27,6 +27,7 @@ import io import itertools import os +import re import shlex import string import struct @@ -355,38 +356,53 @@ def detect_chip(port=DEFAULT_PORT, baud=ESP_ROM_BAUD, connect_mode='default_rese connect_attempts=DEFAULT_CONNECT_ATTEMPTS): """ Use serial access to detect the chip type. - We use the UART's datecode register for this, it's mapped at - the same address on ESP8266 & ESP32 so we can use one - memory read and compare to the datecode register for each chip - type. + First, get_security_info command is sent to detect the ID of the chip + (supported only by ESP32-C3 and later, works even in the Secure Download Mode). + If this fails, we reconnect and fall-back to reading the magic number. + It's mapped at a specific ROM address and has a different value on each chip model. + This way we can use one memory read and compare it to the magic number for each chip type. This routine automatically performs ESPLoader.connect() (passing connect_mode parameter) as part of querying the chip. """ + inst = None detect_port = ESPLoader(port, baud, trace_enabled=trace_enabled) detect_port.connect(connect_mode, connect_attempts, detecting=True) try: print('Detecting chip type...', end='') - sys.stdout.flush() - chip_magic_value = detect_port.read_reg(ESPLoader.CHIP_DETECT_MAGIC_REG_ADDR) + res = detect_port.check_command('get security info', ESPLoader.ESP_GET_SECURITY_INFO, b'') + res = struct.unpack(" 0 else itertools.count(): - last_error = self._connect_attempt(mode=mode, usb_jtag_serial=usb_jtag_serial) + for _, extra_delay in zip(range(attempts) if attempts > 0 else itertools.count(), itertools.cycle((False, True))): + last_error = self._connect_attempt(mode=mode, usb_jtag_serial=usb_jtag_serial, extra_delay=extra_delay) if last_error is None: break finally: print('') # end 'Connecting...' line if last_error is not None: - raise FatalError('Failed to connect to %s: %s' % (self.CHIP_NAME, last_error)) + raise FatalError('Failed to connect to %s: %s' + '\nFor troubleshooting steps visit: https://github.com/espressif/esptool#troubleshooting' % (self.CHIP_NAME, last_error)) if not detecting: try: @@ -646,7 +677,7 @@ def connect(self, mode='default_reset', attempts=DEFAULT_CONNECT_ATTEMPTS, detec if chip_magic_value in cls.CHIP_DETECT_MAGIC_VALUE: actually = cls break - if actually is None: + if warnings and actually is None: print(("WARNING: This chip doesn't appear to be a %s (chip magic value 0x%08x). " "Probably it is unsupported by this version of esptool.") % (self.CHIP_NAME, chip_magic_value)) else: @@ -797,20 +828,23 @@ def flash_id(self): return self.run_spiflash_command(SPIFLASH_RDID, b"", 24) def get_security_info(self): - # TODO: this only works on the ESP32S2 ROM code loader and needs to work in stub loader also res = self.check_command('get security info', self.ESP_GET_SECURITY_INFO, b'') - res = struct.unpack("LOW if self.uses_usb(): # Give the chip some time to come out of reset, to be able to handle further DTR/RTS transitions @@ -2037,6 +2072,7 @@ def hard_reset(self): if self.uses_usb(): self._check_if_can_reset() + print('Hard resetting via RTS pin...') self._setRTS(True) # EN->LOW if self.uses_usb(): # Give the chip some time to come out of reset, to be able to handle further DTR/RTS transitions @@ -3260,13 +3296,17 @@ def slip_reader(port, trace_function): """ partial_packet = None in_escape = False + successful_slip = False while True: waiting = port.inWaiting() read_bytes = port.read(1 if waiting == 0 else waiting) if read_bytes == b'': - waiting_for = "header" if partial_packet is None else "content" - trace_function("Timed out waiting for packet %s", waiting_for) - raise FatalError("Timed out waiting for packet %s" % waiting_for) + if partial_packet is None: # fail due to no data + msg = "Serial data stream stopped: Possible serial noise or corruption." if successful_slip else "No serial data received." + else: # fail during packet transfer + msg = "Packet content transfer stopped (received {} bytes)".format(len(partial_packet)) + trace_function(msg) + raise FatalError(msg) trace_function("Read %d bytes: %s", len(read_bytes), HexFormatter(read_bytes)) for b in read_bytes: if type(b) is int: @@ -3278,7 +3318,7 @@ def slip_reader(port, trace_function): else: trace_function("Read invalid data: %s", HexFormatter(read_bytes)) trace_function("Remaining data in serial buffer: %s", HexFormatter(port.read(port.inWaiting()))) - raise FatalError('Invalid head of packet (0x%s)' % hexify(b)) + raise FatalError('Invalid head of packet (0x%s): Possible serial noise or corruption.' % hexify(b)) elif in_escape: # part-way through escape sequence in_escape = False if b == b'\xdc': @@ -3295,6 +3335,7 @@ def slip_reader(port, trace_function): trace_function("Received full packet: %s", HexFormatter(partial_packet)) yield partial_packet partial_packet = None + successful_slip = True else: # normal byte in packet partial_packet += b @@ -3968,11 +4009,14 @@ def write_flash_status(esp, args): def get_security_info(esp, args): - (flags, flash_crypt_cnt, key_purposes) = esp.get_security_info() - # TODO: better display - print('Flags: 0x%08x (%s)' % (flags, bin(flags))) - print('Flash_Crypt_Cnt: 0x%x' % flash_crypt_cnt) - print('Key_Purposes: %s' % (key_purposes,)) + si = esp.get_security_info() + # TODO: better display and tests + print('Flags: {:#010x} ({})'.format(si["flags"], bin(si["flags"]))) + print('Flash_Crypt_Cnt: {:#x}'.format(si["flash_crypt_cnt"])) + print('Key_Purposes: {}'.format(si["key_purposes"])) + if si["chip_id"] is not None and si["api_version"] is not None: + print('Chip_ID: {}'.format(si["chip_id"])) + print('Api_Version: {}'.format(si["api_version"])) def merge_bin(args): @@ -4642,230 +4686,235 @@ def __call__(self, parser, namespace, values, option_string=None): Kk+niVdi6p/UV6vbT+2gnurMD1bFqoi+LuWzjT1+EhOaZGo6TdMv/wXshTKs\ """))) ESP32S2ROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ ++rqe/Hebvj3Y4S8jQkWaGpP//j8geRE3\ """))) ESP32S3BETA2ROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ -6LmFj5VbO/6/2uSC94Bb0olUVtg8Nx//B/8OvP0=\ +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\ """))) ESP32S3ROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ """))) ESP32C3ROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ +xp4M93cxNksKk1z9D2WAtrU=\ """))) ESP32C6BETAROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ """))) ESP32H2ROM.STUB_CODE = eval(zlib.decompress(base64.b64decode(b""" -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\ """))) diff --git a/tools/platformio-build-esp32.py b/tools/platformio-build-esp32.py index 21d8bfe74be..083169f60d9 100644 --- a/tools/platformio-build-esp32.py +++ b/tools/platformio-build-esp32.py @@ -92,6 +92,7 @@ "-T", "esp32.rom.newlib-data.ld", "-T", "esp32.rom.syscalls.ld", "-T", "esp32.peripherals.ld", + "-u", "ld_include_hli_vectors_bt", "-u", "_Z5setupv", "-u", "_Z4loopv", "-u", "esp_app_desc", @@ -117,6 +118,7 @@ join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "config"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "newlib", "platform_include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "freertos", "include"), + join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "freertos", "include", "esp_additions", "freertos"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "freertos", "port", "xtensa", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "freertos", "include", "esp_additions"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32", "include", "esp_hw_support", "include"), @@ -289,7 +291,7 @@ ], LIBS=[ - "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lbt", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lperfmon", "-lspiffs", "-lulp", "-lwifi_provisioning", "-lbutton", "-ljson_parser", "-ljson_generator", "-lesp_schedule", "-lesp_rainmaker", "-lqrcode", "-lws2812_led", "-lesp-dsp", "-lesp32-camera", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lperfmon", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lesp_rainmaker", "-lmqtt", "-lwifi_provisioning", "-lprotocomm", "-lbt", "-lbtdm_app", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-ljson_parser", "-ljson_generator", "-lesp_schedule", "-lqrcode", "-lcat_face_detect", "-lhuman_face_detect", "-ldl", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lesp_phy", "-lphy", "-lesp_phy", "-lphy", "-lrtc", "-lxt_hal", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" + "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lbt", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lperfmon", "-lspiffs", "-lulp", "-lwifi_provisioning", "-lbutton", "-ljson_parser", "-ljson_generator", "-lesp_schedule", "-lesp_rainmaker", "-lqrcode", "-lws2812_led", "-lesp-dsp", "-lesp32-camera", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lperfmon", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lesp_rainmaker", "-lmqtt", "-lwifi_provisioning", "-lprotocomm", "-lbt", "-lbtdm_app", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-ljson_parser", "-ljson_generator", "-lesp_schedule", "-lqrcode", "-lcat_face_detect", "-lhuman_face_detect", "-ldl", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lrtc", "-lesp_phy", "-lphy", "-lrtc", "-lesp_phy", "-lphy", "-lrtc", "-lxt_hal", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" ], CPPDEFINES=[ @@ -298,7 +300,7 @@ "UNITY_INCLUDE_CONFIG_H", "WITH_POSIX", "_GNU_SOURCE", - ("IDF_VER", '\\"v4.4-dev-2897-g61299f879e\\"'), + ("IDF_VER", '\\"v4.4-dev-3235-g3e370c4296\\"'), "ESP_PLATFORM", "ARDUINO_ARCH_ESP32", "ESP32", diff --git a/tools/platformio-build-esp32c3.py b/tools/platformio-build-esp32c3.py index d6468700134..63680ad42a9 100644 --- a/tools/platformio-build-esp32c3.py +++ b/tools/platformio-build-esp32c3.py @@ -143,6 +143,7 @@ join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "config"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "newlib", "platform_include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "freertos", "include"), + join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "freertos", "include", "esp_additions", "freertos"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "freertos", "port", "riscv", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "freertos", "include", "esp_additions"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32c3", "include", "esp_hw_support", "include"), @@ -272,7 +273,7 @@ ], LIBS=[ - "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lbt", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_https_server", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_https_server", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lmqtt", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lprotocomm", "-lbt", "-lbtdm_app", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lesp_phy", "-lphy", "-lesp_phy", "-lphy", "-lbtbb", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" + "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lbt", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_https_server", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_https_server", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lmqtt", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lprotocomm", "-lbt", "-lbtdm_app", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lriscv", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lbtbb", "-lesp_phy", "-lphy", "-lbtbb", "-lesp_phy", "-lphy", "-lbtbb", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" ], CPPDEFINES=[ @@ -281,7 +282,7 @@ "UNITY_INCLUDE_CONFIG_H", "WITH_POSIX", "_GNU_SOURCE", - ("IDF_VER", '\\"v4.4-dev-2897-g61299f879e\\"'), + ("IDF_VER", '\\"v4.4-dev-3235-g3e370c4296\\"'), "ESP_PLATFORM", "ARDUINO_ARCH_ESP32", "ESP32", diff --git a/tools/platformio-build-esp32s2.py b/tools/platformio-build-esp32s2.py index c9801f06a2e..dac966a52b0 100644 --- a/tools/platformio-build-esp32s2.py +++ b/tools/platformio-build-esp32s2.py @@ -112,6 +112,7 @@ join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "config"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "newlib", "platform_include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "freertos", "include"), + join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "freertos", "include", "esp_additions", "freertos"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "freertos", "port", "xtensa", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "freertos", "include", "esp_additions"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "esp_hw_support", "include"), @@ -223,9 +224,9 @@ join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "openssl", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "perfmon", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "spiffs", "include"), + join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "usb", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "touch_element", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "ulp", "include"), - join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "usb", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "wifi_provisioning", "include"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "freertos", "include", "freertos"), join(FRAMEWORK_DIR, "tools", "sdk", "esp32s2", "include", "arduino_tinyusb", "tinyusb", "src"), @@ -276,7 +277,7 @@ ], LIBS=[ - "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_https_server", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lperfmon", "-lspiffs", "-ltouch_element", "-lulp", "-lusb", "-lwifi_provisioning", "-lesp-dsp", "-lesp32-camera", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_https_server", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lmqtt", "-lperfmon", "-ltouch_element", "-lusb", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lprotocomm", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-larduino_tinyusb", "-lcat_face_detect", "-lhuman_face_detect", "-ldl", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lesp_phy", "-lphy", "-lesp_phy", "-lphy", "-lxt_hal", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" + "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lasio", "-lcbor", "-lunity", "-lcmock", "-lcoap", "-lconsole", "-lnghttp", "-lesp-tls", "-lesp_adc_cal", "-lesp_hid", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lesp_https_server", "-lesp_lcd", "-lprotobuf-c", "-lprotocomm", "-lmdns", "-lesp_local_ctrl", "-lsdmmc", "-lesp_serial_slave_link", "-lesp_websocket_client", "-lexpat", "-lwear_levelling", "-lfatfs", "-lfreemodbus", "-ljsmn", "-ljson", "-llibsodium", "-lmqtt", "-lopenssl", "-lperfmon", "-lspiffs", "-lusb", "-ltouch_element", "-lulp", "-lwifi_provisioning", "-lesp-dsp", "-lesp32-camera", "-lesp_littlefs", "-lfb_gfx", "-lasio", "-lcbor", "-lcmock", "-lunity", "-lcoap", "-lesp_lcd", "-lesp_local_ctrl", "-lesp_https_server", "-lesp_websocket_client", "-lexpat", "-lfreemodbus", "-ljsmn", "-llibsodium", "-lmqtt", "-lperfmon", "-lusb", "-ltouch_element", "-lesp_adc_cal", "-lesp_hid", "-lfatfs", "-lwear_levelling", "-lopenssl", "-lspiffs", "-lwifi_provisioning", "-lprotocomm", "-lprotobuf-c", "-lmdns", "-lconsole", "-ljson", "-larduino_tinyusb", "-lcat_face_detect", "-lhuman_face_detect", "-ldl", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lesp_ringbuf", "-lefuse", "-lesp_ipc", "-ldriver", "-lesp_pm", "-lmbedtls", "-lapp_update", "-lbootloader_support", "-lspi_flash", "-lnvs_flash", "-lpthread", "-lesp_gdbstub", "-lespcoredump", "-lesp_phy", "-lesp_system", "-lesp_rom", "-lhal", "-lvfs", "-lesp_eth", "-ltcpip_adapter", "-lesp_netif", "-lesp_event", "-lwpa_supplicant", "-lesp_wifi", "-llwip", "-llog", "-lheap", "-lsoc", "-lesp_hw_support", "-lxtensa", "-lesp_common", "-lesp_timer", "-lfreertos", "-lnewlib", "-lcxx", "-lapp_trace", "-lnghttp", "-lesp-tls", "-ltcp_transport", "-lesp_http_client", "-lesp_http_server", "-lesp_https_ota", "-lsdmmc", "-lesp_serial_slave_link", "-lulp", "-lmbedtls", "-lmbedcrypto", "-lmbedx509", "-lcoexist", "-lcore", "-lespnow", "-lmesh", "-lnet80211", "-lpp", "-lsmartconfig", "-lwapi", "-lphy", "-lesp_phy", "-lphy", "-lesp_phy", "-lphy", "-lxt_hal", "-lm", "-lnewlib", "-lstdc++", "-lpthread", "-lgcc", "-lcxx", "-lapp_trace", "-lgcov", "-lapp_trace", "-lgcov", "-lc" ], CPPDEFINES=[ @@ -285,7 +286,7 @@ "UNITY_INCLUDE_CONFIG_H", "WITH_POSIX", "_GNU_SOURCE", - ("IDF_VER", '\\"v4.4-dev-2897-g61299f879e\\"'), + ("IDF_VER", '\\"v4.4-dev-3235-g3e370c4296\\"'), "ESP_PLATFORM", "ARDUINO_ARCH_ESP32", "ESP32", diff --git a/tools/sdk/esp32/bin/bootloader_dio_40m.bin b/tools/sdk/esp32/bin/bootloader_dio_40m.bin index 8ee6e0cd289..97c4c99695b 100644 Binary files a/tools/sdk/esp32/bin/bootloader_dio_40m.bin and b/tools/sdk/esp32/bin/bootloader_dio_40m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_dio_80m.bin b/tools/sdk/esp32/bin/bootloader_dio_80m.bin index 4c53b9f48ff..30a2681f021 100644 Binary files a/tools/sdk/esp32/bin/bootloader_dio_80m.bin and b/tools/sdk/esp32/bin/bootloader_dio_80m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_dout_40m.bin b/tools/sdk/esp32/bin/bootloader_dout_40m.bin index 3600f0cc84e..bd7c316fcd2 100644 Binary files a/tools/sdk/esp32/bin/bootloader_dout_40m.bin and b/tools/sdk/esp32/bin/bootloader_dout_40m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_dout_80m.bin b/tools/sdk/esp32/bin/bootloader_dout_80m.bin index d0e64c30af8..44ee9d6cfc9 100644 Binary files a/tools/sdk/esp32/bin/bootloader_dout_80m.bin and b/tools/sdk/esp32/bin/bootloader_dout_80m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_qio_40m.bin b/tools/sdk/esp32/bin/bootloader_qio_40m.bin index 1bf41b8c57d..958ddfe8135 100644 Binary files a/tools/sdk/esp32/bin/bootloader_qio_40m.bin and b/tools/sdk/esp32/bin/bootloader_qio_40m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_qio_80m.bin b/tools/sdk/esp32/bin/bootloader_qio_80m.bin index ee3e21efd17..bf18af59925 100644 Binary files a/tools/sdk/esp32/bin/bootloader_qio_80m.bin and b/tools/sdk/esp32/bin/bootloader_qio_80m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_qout_40m.bin b/tools/sdk/esp32/bin/bootloader_qout_40m.bin index fda760ab1c1..93d6ff461aa 100644 Binary files a/tools/sdk/esp32/bin/bootloader_qout_40m.bin and b/tools/sdk/esp32/bin/bootloader_qout_40m.bin differ diff --git a/tools/sdk/esp32/bin/bootloader_qout_80m.bin b/tools/sdk/esp32/bin/bootloader_qout_80m.bin index 934858035f5..1edaf34822d 100644 Binary files a/tools/sdk/esp32/bin/bootloader_qout_80m.bin and b/tools/sdk/esp32/bin/bootloader_qout_80m.bin differ diff --git a/tools/sdk/esp32/include/bootloader_support/include/bootloader_common.h b/tools/sdk/esp32/include/bootloader_support/include/bootloader_common.h index 2ff0e595a27..2f4e9062200 100644 --- a/tools/sdk/esp32/include/bootloader_support/include/bootloader_common.h +++ b/tools/sdk/esp32/include/bootloader_support/include/bootloader_common.h @@ -119,6 +119,15 @@ bool bootloader_common_label_search(const char *list, char *label); */ void bootloader_configure_spi_pins(int drv); +/** + * @brief Get flash CS IO + * + * Can be determined by eFuse values, or the default value + * + * @return Flash CS IO + */ +uint8_t bootloader_flash_get_cs_io(void); + /** * @brief Calculates a sha-256 for a given partition or returns a appended digest. * diff --git a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h index ce309935853..dd48ab982dd 100644 --- a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h +++ b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gap_ble_api.h @@ -467,7 +467,7 @@ typedef struct { uint16_t rx_len; /*!< pkt rx data length value */ uint16_t tx_len; /*!< pkt tx data length value */ -}esp_ble_pkt_data_length_params_t; +} esp_ble_pkt_data_length_params_t; /** * @brief BLE encryption keys @@ -648,7 +648,7 @@ typedef enum { typedef enum{ ESP_BLE_WHITELIST_REMOVE = 0X00, /*!< remove mac from whitelist */ ESP_BLE_WHITELIST_ADD = 0X01, /*!< add address to whitelist */ -}esp_ble_wl_opration_t; +} esp_ble_wl_opration_t; #if (BLE_42_FEATURE_SUPPORT == TRUE) typedef enum { ESP_BLE_DUPLICATE_EXCEPTIONAL_LIST_ADD = 0, /*!< Add device info into duplicate scan exceptional list */ @@ -998,7 +998,7 @@ typedef union { uint16_t conn_int; /*!< Current connection interval */ uint16_t timeout; /*!< Supervision timeout for the LE Link. Range: 0x000A to 0x0C80. Mandatory Range: 0x000A to 0x0C80 Time = N * 10 msec */ - }update_conn_params; /*!< Event parameter of ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT */ + } update_conn_params; /*!< Event parameter of ESP_GAP_BLE_UPDATE_CONN_PARAMS_EVT */ /** * @brief ESP_GAP_BLE_SET_PKT_LENGTH_COMPLETE_EVT */ @@ -1018,13 +1018,13 @@ typedef union { struct ble_remove_bond_dev_cmpl_evt_param { esp_bt_status_t status; /*!< Indicate the remove bond device operation success status */ esp_bd_addr_t bd_addr; /*!< The device address which has been remove from the bond list */ - }remove_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_REMOVE_BOND_DEV_COMPLETE_EVT */ + } remove_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_REMOVE_BOND_DEV_COMPLETE_EVT */ /** * @brief ESP_GAP_BLE_CLEAR_BOND_DEV_COMPLETE_EVT */ struct ble_clear_bond_dev_cmpl_evt_param { esp_bt_status_t status; /*!< Indicate the clear bond device operation success status */ - }clear_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_CLEAR_BOND_DEV_COMPLETE_EVT */ + } clear_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_CLEAR_BOND_DEV_COMPLETE_EVT */ /** * @brief ESP_GAP_BLE_GET_BOND_DEV_COMPLETE_EVT */ @@ -1032,7 +1032,7 @@ typedef union { esp_bt_status_t status; /*!< Indicate the get bond device operation success status */ uint8_t dev_num; /*!< Indicate the get number device in the bond list */ esp_ble_bond_dev_t *bond_dev; /*!< the pointer to the bond device Structure */ - }get_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_GET_BOND_DEV_COMPLETE_EVT */ + } get_bond_dev_cmpl; /*!< Event parameter of ESP_GAP_BLE_GET_BOND_DEV_COMPLETE_EVT */ /** * @brief ESP_GAP_BLE_READ_RSSI_COMPLETE_EVT */ diff --git a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gattc_api.h b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gattc_api.h index 077cca38507..40719096345 100644 --- a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gattc_api.h +++ b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_gattc_api.h @@ -380,7 +380,7 @@ esp_err_t esp_ble_gattc_search_service(esp_gatt_if_t gattc_if, uint16_t conn_id, /** * @brief Find all the service with the given service uuid in the gattc cache, if the svc_uuid is NULL, find all the service. * Note: It just get service from local cache, won't get from remote devices. If want to get it from remote device, need - * to used the esp_ble_gattc_search_service. + * to used the esp_ble_gattc_cache_refresh, then call esp_ble_gattc_get_service again. * * @param[in] gattc_if: Gatt client access interface. * @param[in] conn_id: connection ID which identify the server. diff --git a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidd_api.h b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidd_api.h new file mode 100644 index 00000000000..de90ff8efc6 --- /dev/null +++ b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidd_api.h @@ -0,0 +1,379 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// Copyright 2019 Blake Felt +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef __ESP_HIDD_API_H__ +#define __ESP_HIDD_API_H__ + +#include "esp_bt_defs.h" +#include "esp_err.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* sub_class of hid device */ +#define ESP_HID_CLASS_UNKNOWN (0x00<<2) +#define ESP_HID_CLASS_JOS (0x01<<2) /* joy stick */ +#define ESP_HID_CLASS_GPD (0x02<<2) /* game pad */ +#define ESP_HID_CLASS_RMC (0x03<<2) /* remote control */ +#define ESP_HID_CLASS_SED (0x04<<2) /* sensing device */ +#define ESP_HID_CLASS_DGT (0x05<<2) /* Digitizer tablet */ +#define ESP_HID_CLASS_CDR (0x06<<2) /* card reader */ +#define ESP_HID_CLASS_KBD (0x10<<2) /* keyboard */ +#define ESP_HID_CLASS_MIC (0x20<<2) /* pointing device */ +#define ESP_HID_CLASS_COM (0x30<<2) /* Combo keyboard/pointing */ + +/** + * @brief HIDD handshake error + */ +typedef enum { + ESP_HID_PAR_HANDSHAKE_RSP_SUCCESS = 0, + ESP_HID_PAR_HANDSHAKE_RSP_NOT_READY = 1, + ESP_HID_PAR_HANDSHAKE_RSP_ERR_INVALID_REP_ID = 2, + ESP_HID_PAR_HANDSHAKE_RSP_ERR_UNSUPPORTED_REQ = 3, + ESP_HID_PAR_HANDSHAKE_RSP_ERR_INVALID_PARAM = 4, + ESP_HID_PAR_HANDSHAKE_RSP_ERR_UNKNOWN = 14, + ESP_HID_PAR_HANDSHAKE_RSP_ERR_FATAL = 15 +} esp_hidd_handshake_error_t; + +/** + * @brief HIDD report types + */ +typedef enum { + ESP_HIDD_REPORT_TYPE_OTHER = 0, + ESP_HIDD_REPORT_TYPE_INPUT, + ESP_HIDD_REPORT_TYPE_OUTPUT, + ESP_HIDD_REPORT_TYPE_FEATURE, + // special value for reports to be sent on INTR(INPUT is assumed) + ESP_HIDD_REPORT_TYPE_INTRDATA +} esp_hidd_report_type_t; + +/** + * @brief HIDD connection state + */ +typedef enum { + ESP_HIDD_CONN_STATE_CONNECTED, + ESP_HIDD_CONN_STATE_CONNECTING, + ESP_HIDD_CONN_STATE_DISCONNECTED, + ESP_HIDD_CONN_STATE_DISCONNECTING, + ESP_HIDD_CONN_STATE_UNKNOWN +} esp_hidd_connection_state_t; + +/** + * @brief HID device protocol modes + */ +typedef enum { + ESP_HIDD_REPORT_MODE = 0x00, + ESP_HIDD_BOOT_MODE = 0x01, + ESP_HIDD_UNSUPPORTED_MODE = 0xff +} esp_hidd_protocol_mode_t; + + +/** + * @brief HIDD characteristics for SDP report + */ +typedef struct { + const char *name; + const char *description; + const char *provider; + uint8_t subclass; + uint8_t *desc_list; + int desc_list_len; +} esp_hidd_app_param_t; + +/** + * @brief HIDD Quality of Service parameters + */ +typedef struct { + uint8_t service_type; + uint32_t token_rate; + uint32_t token_bucket_size; + uint32_t peak_bandwidth; + uint32_t access_latency; + uint32_t delay_variation; +} esp_hidd_qos_param_t; + +/** + * @brief HID device callback function events + */ +typedef enum { + ESP_HIDD_INIT_EVT = 0, /*!< When HID device is inited, the event comes */ + ESP_HIDD_DEINIT_EVT, /*!< When HID device is deinited, the event comes */ + ESP_HIDD_REGISTER_APP_EVT, /*!< When HID device application registered, the event comes */ + ESP_HIDD_UNREGISTER_APP_EVT, /*!< When HID device application unregistered, the event comes */ + ESP_HIDD_OPEN_EVT, /*!< When HID device connection to host opened, the event comes */ + ESP_HIDD_CLOSE_EVT, /*!< When HID device connection to host closed, the event comes */ + ESP_HIDD_SEND_REPORT_EVT, /*!< When HID device send report to lower layer, the event comes */ + ESP_HIDD_REPORT_ERR_EVT, /*!< When HID device report handshanke error to lower layer, the event comes */ + ESP_HIDD_GET_REPORT_EVT, /*!< When HID device receives GET_REPORT request from host, the event comes */ + ESP_HIDD_SET_REPORT_EVT, /*!< When HID device receives SET_REPORT request from host, the event comes */ + ESP_HIDD_SET_PROTOCOL_EVT, /*!< When HID device receives SET_PROTOCOL request from host, the event comes */ + ESP_HIDD_INTR_DATA_EVT, /*!< When HID device receives DATA from host on intr, the event comes */ + ESP_HIDD_VC_UNPLUG_EVT, /*!< When HID device initiates Virtual Cable Unplug, the event comes */ + ESP_HIDD_API_ERR_EVT /*!< When HID device has API error, the event comes */ +} esp_hidd_cb_event_t; + +typedef enum { + ESP_HIDD_SUCCESS, + ESP_HIDD_ERROR, /*!< general ESP HD error */ + ESP_HIDD_NO_RES, /*!< out of system resources */ + ESP_HIDD_BUSY, /*!< Temporarily can not handle this request. */ + ESP_HIDD_NO_DATA, /*!< No data. */ + ESP_HIDD_NEED_INIT, /*!< HIDD module shall init first */ + ESP_HIDD_NEED_DEINIT, /*!< HIDD module shall deinit first */ + ESP_HIDD_NEED_REG, /*!< HIDD module shall register first */ + ESP_HIDD_NEED_DEREG, /*!< HIDD module shall deregister first */ + ESP_HIDD_NO_CONNECTION, /*!< connection may have been closed */ +} esp_hidd_status_t; + +/** + * @brief HID device callback parameters union + */ +typedef union { + /** + * @brief ESP_HIDD_INIT_EVT + */ + struct hidd_init_evt_param { + esp_hidd_status_t status; /*!< operation status */ + } init; /*!< HIDD callback param of ESP_HIDD_INIT_EVT */ + + /** + * @brief ESP_HIDD_DEINIT_EVT + */ + struct hidd_deinit_evt_param { + esp_hidd_status_t status; /*!< operation status */ + } deinit; /*!< HIDD callback param of ESP_HIDD_DEINIT_EVT */ + + /** + * @brief ESP_HIDD_REGISTER_APP_EVT + */ + struct hidd_register_app_evt_param { + esp_hidd_status_t status; /*!< operation status */ + bool in_use; /*!< indicate whether use virtual cable plug host address */ + esp_bd_addr_t bd_addr; /*!< host address */ + } register_app; /*!< HIDD callback param of ESP_HIDD_REGISTER_APP_EVT */ + + /** + * @brief ESP_HIDD_UNREGISTER_APP_EVT + */ + struct hidd_unregister_app_evt_param { + esp_hidd_status_t status; /*!< operation status */ + } unregister_app; /*!< HIDD callback param of ESP_HIDD_UNREGISTER_APP_EVT */ + + /** + * @brief ESP_HIDD_OPEN_EVT + */ + struct hidd_open_evt_param { + esp_hidd_status_t status; /*!< operation status */ + esp_hidd_connection_state_t conn_status; /*!< connection status */ + esp_bd_addr_t bd_addr; /*!< host address */ + } open; /*!< HIDD callback param of ESP_HIDD_OPEN_EVT */ + + /** + * @brief ESP_HIDD_CLOSE_EVT + */ + struct hidd_close_evt_param { + esp_hidd_status_t status; /*!< operation status */ + esp_hidd_connection_state_t conn_status; /*!< connection status */ + } close; /*!< HIDD callback param of ESP_HIDD_CLOSE_EVT */ + + /** + * @brief ESP_HIDD_SEND_REPORT_EVT + */ + struct hidd_send_report_evt_param { + esp_hidd_status_t status; /*!< operation status */ + uint8_t reason; /*!< lower layer failed reason(ref hiddefs.h) */ + esp_hidd_report_type_t report_type; /*!< report type */ + uint8_t report_id; /*!< report id */ + } send_report; /*!< HIDD callback param of ESP_HIDD_SEND_REPORT_EVT */ + + /** + * @brief ESP_HIDD_REPORT_ERR_EVT + */ + struct hidd_report_err_evt_param { + esp_hidd_status_t status; /*!< operation status */ + uint8_t reason; /*!< lower layer failed reason(ref hiddefs.h) */ + } report_err; /*!< HIDD callback param of ESP_HIDD_REPORT_ERR_EVT */ + + /** + * @brief ESP_HIDD_GET_REPORT_EVT + */ + struct hidd_get_report_evt_param { + esp_hidd_report_type_t report_type; /*!< report type */ + uint8_t report_id; /*!< report id */ + uint16_t buffer_size; /*!< buffer size */ + } get_report; /*!< HIDD callback param of ESP_HIDD_GET_REPORT_EVT */ + + /** + * @brief ESP_HIDD_SET_REPORT_EVT + */ + struct hidd_set_report_evt_param { + esp_hidd_report_type_t report_type; /*!< report type */ + uint8_t report_id; /*!< report id */ + uint16_t len; /*!< set_report data length */ + uint8_t *data; /*!< set_report data pointer */ + } set_report; /*!< HIDD callback param of ESP_HIDD_SET_REPORT_EVT */ + + /** + * @brief ESP_HIDD_SET_PROTOCOL_EVT + */ + struct hidd_set_protocol_evt_param { + esp_hidd_protocol_mode_t protocol_mode; /*!< protocol mode */ + } set_protocol; /*!< HIDD callback param of ESP_HIDD_SET_PROTOCOL_EVT */ + + /** + * @brief ESP_HIDD_INTR_DATA_EVT + */ + struct hidd_intr_data_evt_param { + uint8_t report_id; /*!< interrupt channel report id */ + uint16_t len; /*!< interrupt channel report data length */ + uint8_t *data; /*!< interrupt channel report data pointer */ + } intr_data; /*!< HIDD callback param of ESP_HIDD_INTR_DATA_EVT */ + + /** + * @brief ESP_HIDD_VC_UNPLUG_EVT + */ + struct hidd_vc_unplug_param { + esp_hidd_status_t status; /*!< operation status */ + esp_hidd_connection_state_t conn_status; /*!< connection status */ + } vc_unplug; /*!< HIDD callback param of ESP_HIDD_VC_UNPLUG_EVT */ +} esp_hidd_cb_param_t; + +/** + * @brief HID device callback function type. + * @param event: Event type + * @param param: Point to callback parameter, currently is union type + */ +typedef void (esp_hd_cb_t)(esp_hidd_cb_event_t event, esp_hidd_cb_param_t *param); + +/** + * @brief This function is called to init callbacks with HID device module. + * + * @param[in] callback: pointer to the init callback function. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_register_callback(esp_hd_cb_t callback); + +/** + * @brief This function initializes HIDD. This function should be called after esp_bluedroid_enable and + * esp_blueroid_init success, and should be called after esp_bt_hid_device_register_callback. + * When the operation is complete the callback function will be called with ESP_HIDD_INIT_EVT. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_init(void); + +/** + * @brief This function de-initializes HIDD interface. This function should be called after esp_bluedroid_enable() and + * esp_blueroid_init() success, and should be called after esp_bt_hid_device_init(). When the operation is complete the callback + * function will be called with ESP_HIDD_DEINIT_EVT. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_deinit(void); + +/** + * @brief Registers HIDD parameters with SDP and sets l2cap Quality of Service. This function should be called after + * esp_bluedroid_enable and esp_blueroid_init success, and must be done after esp_bt_hid_device_init. When the operation is complete the callback + * function will be called with ESP_HIDD_REGISTER_APP_EVT. + * + * @param[in] app_param: HIDD parameters + * @param[in] in_qos: incoming QoS parameters + * @param[in] out_qos: outgoing QoS parameters + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_register_app(esp_hidd_app_param_t *app_param, esp_hidd_qos_param_t *in_qos, + esp_hidd_qos_param_t *out_qos); + +/** + * @brief Removes HIDD parameters from SDP and resets l2cap Quality of Service. This function should be called after esp_bluedroid_enable and + * esp_blueroid_init success, and should be called after esp_bt_hid_device_init. When the operation is complete the callback + * function will be called with ESP_HIDD_UNREGISTER_APP_EVT. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_unregister_app(void); + +/** + * @brief This function connects HIDD interface to connected bluetooth device, if not done already. When the operation is complete the callback + * function will be called with ESP_HIDD_OPEN_EVT. + * + * @param[in] bd_addr: Remote host bluetooth device address. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_connect(esp_bd_addr_t bd_addr); + +/** + * @brief This function disconnects HIDD interface. When the operation is complete the callback + * function will be called with ESP_HIDD_CLOSE_EVT. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_disconnect(void); + +/** + * @brief Send HIDD report. When the operation is complete the callback + * function will be called with ESP_HIDD_SEND_REPORT_EVT. + * + * @param[in] type: type of report + * @param[in] id: report id as defined by descriptor + * @param[in] len: length of report + * @param[in] data: report data + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_send_report(esp_hidd_report_type_t type, uint8_t id, uint16_t len, uint8_t *data); + +/** + * @brief Sends HIDD handshake with error info for invalid set_report. When the operation is complete the callback + * function will be called with ESP_HIDD_REPORT_ERR_EVT. + * + * @param[in] error: type of error + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_report_error(esp_hidd_handshake_error_t error); + +/** + * @brief Unplug virtual cable of HIDD. When the operation is complete the callback + * function will be called with ESP_HIDD_VC_UNPLUG_EVT. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_device_virtual_cable_unplug(void); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidh_api.h b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidh_api.h new file mode 100644 index 00000000000..07abdece2d0 --- /dev/null +++ b/tools/sdk/esp32/include/bt/host/bluedroid/api/include/api/esp_hidh_api.h @@ -0,0 +1,465 @@ +// Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD +// Copyright 2019 Blake Felt +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#ifndef __ESP_HIDH_API_H__ +#define __ESP_HIDH_API_H__ + +#include "esp_bt_defs.h" +#include "esp_err.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define BTHH_MAX_DSC_LEN 884 + +/** + * @brief HID host connection state + */ +typedef enum { + ESP_HIDH_CONN_STATE_CONNECTED = 0, /*!< connected state */ + ESP_HIDH_CONN_STATE_CONNECTING, /*!< connecting state */ + ESP_HIDH_CONN_STATE_DISCONNECTED, /*!< disconnected state */ + ESP_HIDH_CONN_STATE_DISCONNECTING, /*!< disconnecting state */ + ESP_HIDH_CONN_STATE_UNKNOWN /*!< unknown state(initial state) */ +} esp_hidh_connection_state_t; + +typedef enum { + ESP_HIDH_OK, + ESP_HIDH_HS_HID_NOT_READY, /*!< handshake error : device not ready */ + ESP_HIDH_HS_INVALID_RPT_ID, /*!< handshake error : invalid report ID */ + ESP_HIDH_HS_TRANS_NOT_SPT, /*!< handshake error : transaction not spt */ + ESP_HIDH_HS_INVALID_PARAM, /*!< handshake error : invalid paremter */ + ESP_HIDH_HS_ERROR, /*!< handshake error : unspecified HS error */ + ESP_HIDH_ERR, /*!< general ESP HH error */ + ESP_HIDH_ERR_SDP, /*!< SDP error */ + ESP_HIDH_ERR_PROTO, /*!< SET_Protocol error, + only used in ESP_HIDH_OPEN_EVT callback */ + + ESP_HIDH_ERR_DB_FULL, /*!< device database full error, used in + ESP_HIDH_OPEN_EVT/ESP_HIDH_ADD_DEV_EVT */ + ESP_HIDH_ERR_TOD_UNSPT, /*!< type of device not supported */ + ESP_HIDH_ERR_NO_RES, /*!< out of system resources */ + ESP_HIDH_ERR_AUTH_FAILED, /*!< authentication fail */ + ESP_HIDH_ERR_HDL, /*!< connection handle error */ + ESP_HIDH_ERR_SEC, /*!< encryption error */ + // self_defined + ESP_HIDH_BUSY, /*!< Temporarily can not handle this request. */ + ESP_HIDH_NO_DATA, /*!< No data. */ + ESP_HIDH_NEED_INIT, /*!< HIDH module shall init first */ + ESP_HIDH_NEED_DEINIT, /*!< HIDH module shall deinit first */ + ESP_HIDH_NO_CONNECTION, /*!< connection may have been closed */ +} esp_hidh_status_t; + +/** + * @brief HID host protocol modes + */ +typedef enum { + ESP_HIDH_BOOT_MODE = 0x00, /*!< boot protocol mode */ + ESP_HIDH_REPORT_MODE = 0x01, /*!< report protocol mode */ + ESP_HIDH_UNSUPPORTED_MODE = 0xff /*!< unsupported protocol mode */ +} esp_hidh_protocol_mode_t; + +/** + * @brief HID host report types + */ +typedef enum { + ESP_HIDH_REPORT_TYPE_OTHER = 0, /*!< unsupported report type */ + ESP_HIDH_REPORT_TYPE_INPUT, /*!< input report type */ + ESP_HIDH_REPORT_TYPE_OUTPUT, /*!< output report type */ + ESP_HIDH_REPORT_TYPE_FEATURE, /*!< feature report type */ +} esp_hidh_report_type_t; + +/** + * @brief HID host callback function events + */ +typedef enum { + ESP_HIDH_INIT_EVT = 0, /*!< When HID host is inited, the event comes */ + ESP_HIDH_DEINIT_EVT, /*!< When HID host is deinited, the event comes */ + ESP_HIDH_OPEN_EVT, /*!< When HID host connection opened, the event comes */ + ESP_HIDH_CLOSE_EVT, /*!< When HID host connection closed, the event comes */ + ESP_HIDH_GET_RPT_EVT, /*!< When Get_Report command is called, the event comes */ + ESP_HIDH_SET_RPT_EVT, /*!< When Set_Report command is called, the event comes */ + ESP_HIDH_GET_PROTO_EVT, /*!< When Get_Protocol command is called, the event comes */ + ESP_HIDH_SET_PROTO_EVT, /*!< When Set_Protocol command is called, the event comes */ + ESP_HIDH_GET_IDLE_EVT, /*!< When Get_Idle command is called, the event comes */ + ESP_HIDH_SET_IDLE_EVT, /*!< When Set_Idle command is called, the event comes */ + ESP_HIDH_GET_DSCP_EVT, /*!< When HIDH is inited, the event comes */ + ESP_HIDH_ADD_DEV_EVT, /*!< When a device is added, the event comes */ + ESP_HIDH_RMV_DEV_EVT, /*!< When a device is removed, the event comes */ + ESP_HIDH_VC_UNPLUG_EVT, /*!< When virtually unplugged, the event comes */ + ESP_HIDH_DATA_EVT, /*!< When send data on interrupt channel, the event comes */ + ESP_HIDH_DATA_IND_EVT, /*!< When receive data on interrupt channel, the event comes */ + ESP_HIDH_SET_INFO_EVT /*!< When set the HID device descriptor, the event comes */ +} esp_hidh_cb_event_t; + +typedef struct { + int attr_mask; + uint8_t sub_class; + uint8_t app_id; + int vendor_id; + int product_id; + int version; + uint8_t ctry_code; + int dl_len; + uint8_t dsc_list[BTHH_MAX_DSC_LEN]; +} esp_hidh_hid_info_t; + +/** + * @brief HID host callback parameters union + */ +typedef union { + /** + * @brief ESP_HIDH_INIT_EVT + */ + struct hidh_init_evt_param { + esp_hidh_status_t status; /*!< status */ + } init; /*!< HIDH callback param of ESP_HIDH_INIT_EVT */ + + /** + * @brief ESP_HIDH_DEINIT_EVT + */ + struct hidh_uninit_evt_param { + esp_hidh_status_t status; /*!< status */ + } deinit; /*!< HIDH callback param of ESP_HIDH_DEINIT_EVT */ + + /** + * @brief ESP_HIDH_OPEN_EVT + */ + struct hidh_open_evt_param { + esp_hidh_status_t status; /*!< operation status */ + esp_hidh_connection_state_t conn_status; /*!< connection status */ + bool is_orig; /*!< indicate if host intiate the connection */ + uint8_t handle; /*!< device handle */ + esp_bd_addr_t bd_addr; /*!< device address */ + } open; /*!< HIDH callback param of ESP_HIDH_OPEN_EVT */ + + /** + * @brief ESP_HIDH_CLOSE_EVT + */ + struct hidh_close_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t reason; /*!< lower layer failed reason(ref hiddefs.h) */ + esp_hidh_connection_state_t conn_status; /*!< connection status */ + uint8_t handle; /*!< device handle */ + } close; /*!< HIDH callback param of ESP_HIDH_CLOSE_EVT */ + + /** + * @brief ESP_HIDH_VC_UNPLUG_EVT + */ + struct hidh_unplug_evt_param { + esp_hidh_status_t status; /*!< operation status */ + esp_hidh_connection_state_t conn_status; /*!< connection status */ + uint8_t handle; /*!< device handle */ + } unplug; /*!< HIDH callback param of ESP_HIDH_VC_UNPLUG_EVT */ + + /** + * @brief ESP_HIDH_GET_PROTO_EVT + */ + struct hidh_get_proto_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + esp_hidh_protocol_mode_t proto_mode; /*!< protocol mode */ + } get_proto; /*!< HIDH callback param of ESP_HIDH_GET_PROTO_EVT */ + + /** + * @brief ESP_HIDH_SET_PROTO_EVT + */ + struct hidh_set_proto_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + } set_proto; /*!< HIDH callback param of ESP_HIDH_SET_PROTO_EVT */ + + /** + * @brief ESP_HIDH_GET_RPT_EVT + */ + struct hidh_get_rpt_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + uint16_t len; /*!< data length */ + uint8_t *data; /*!< data pointer */ + } get_rpt; /*!< HIDH callback param of ESP_HIDH_GET_RPT_EVT */ + + /** + * @brief ESP_HIDH_SET_RPT_EVT + */ + struct hidh_set_rpt_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + } set_rpt; /*!< HIDH callback param of ESP_HIDH_SET_RPT_EVT */ + + /** + * @brief ESP_HIDH_DATA_EVT + */ + struct hidh_send_data_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + uint8_t reason; /*!< lower layer failed reason(ref hiddefs.h) */ + } send_data; /*!< HIDH callback param of ESP_HIDH_DATA_EVT */ + + /** + * @brief ESP_HIDH_GET_IDLE_EVT + */ + struct hidh_get_idle_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + uint8_t idle_rate; /*!< idle rate */ + } get_idle; /*!< HIDH callback param of ESP_HIDH_GET_IDLE_EVT */ + + /** + * @brief ESP_HIDH_SET_IDLE_EVT + */ + struct hidh_set_idle_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + } set_idle; /*!< HIDH callback param of ESP_HIDH_SET_IDLE_EVT */ + + /** + * @brief ESP_HIDH_DATA_IND_EVT + */ + struct hidh_data_ind_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + esp_hidh_protocol_mode_t proto_mode; /*!< protocol mode */ + uint16_t len; /*!< data length */ + uint8_t *data; /*!< data pointer */ + } data_ind; /*!< HIDH callback param of ESP_HIDH_DATA_IND_EVT */ + + /** + * @brief ESP_HIDH_ADD_DEV_EVT + */ + struct hidh_add_dev_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + esp_bd_addr_t bd_addr; /*!< device address */ + } add_dev; /*!< HIDH callback param of ESP_HIDH_ADD_DEV_EVT */ + + /** + * @brief ESP_HIDH_RMV_DEV_EVT + */ + struct hidh_rmv_dev_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + esp_bd_addr_t bd_addr; /*!< device address */ + } rmv_dev; /*!< HIDH callback param of ESP_HIDH_RMV_DEV_EVT */ + + /** + * @brief ESP_HIDH_GET_DSCP_EVT + */ + struct hidh_get_dscp_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + bool added; /*!< Indicate if added */ + uint16_t vendor_id; /*!< Vendor ID */ + uint16_t product_id; /*!< Product ID */ + uint16_t version; /*!< Version */ + uint16_t ssr_max_latency; /*!< SSR max latency */ + uint16_t ssr_min_tout; /*!< SSR min timeout */ + uint8_t ctry_code; /*!< Country Code */ + uint16_t dl_len; /*!< Device descriptor length */ + uint8_t *dsc_list; /*!< Device descriptor pointer */ + } dscp; /*!< HIDH callback param of ESP_HIDH_GET_DSCP_EVT */ + + /** + * @brief ESP_HIDH_SET_INFO_EVT + */ + struct hidh_set_info_evt_param { + esp_hidh_status_t status; /*!< operation status */ + uint8_t handle; /*!< device handle */ + esp_bd_addr_t bd_addr; /*!< device address */ + } set_info; /*!< HIDH callback param of ESP_HIDH_SET_INFO_EVT */ +} esp_hidh_cb_param_t; + +/** + * @brief HID host callback function type + * @param event: Event type + * @param param: Point to callback parameter, currently is union type + */ +typedef void (esp_hh_cb_t)(esp_hidh_cb_event_t event, esp_hidh_cb_param_t *param); + +/** + * @brief This function is called to init callbacks with HID host module. + * + * @param[in] callback: pointer to the init callback function. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_register_callback(esp_hh_cb_t callback); + +/** + * @brief This function initializes HID host. This function should be called after esp_bluedroid_enable() and + * esp_blueroid_init() success, and should be called after esp_bt_hid_host_register_callback(). + * When the operation is complete the callback function will be called with ESP_HIDH_INIT_EVT. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_init(void); + +/** + * @brief Closes the interface. This function should be called after esp_bluedroid_enable() and + * esp_blueroid_init() success, and should be called after esp_bt_hid_host_init(). + * When the operation is complete the callback function will be called with ESP_HIDH_DEINIT_EVT. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_deinit(void); + +/** + * @brief Connect to hid device. When the operation is complete the callback + * function will be called with ESP_HIDH_OPEN_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_connect(esp_bd_addr_t bd_addr); + +/** + * @brief Disconnect from hid device. When the operation is complete the callback + * function will be called with ESP_HIDH_CLOSE_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_disconnect(esp_bd_addr_t bd_addr); + +/** + * @brief Virtual UnPlug (VUP) the specified HID device. When the operation is complete the callback + * function will be called with ESP_HIDH_VC_UNPLUG_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_virtual_cable_unplug(esp_bd_addr_t bd_addr); + +/** + * @brief Set the HID device descriptor for the specified HID device. When the operation is complete the callback + * function will be called with ESP_HIDH_SET_INFO_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] hid_info: HID device descriptor structure. + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_set_info(esp_bd_addr_t bd_addr, esp_hidh_hid_info_t *hid_info); + +/** + * @brief Get the HID proto mode. When the operation is complete the callback + * function will be called with ESP_HIDH_GET_PROTO_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_get_protocol(esp_bd_addr_t bd_addr); + +/** + * @brief Set the HID proto mode. When the operation is complete the callback + * function will be called with ESP_HIDH_SET_PROTO_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] protocol_mode: Protocol mode type. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_set_protocol(esp_bd_addr_t bd_addr, esp_hidh_protocol_mode_t protocol_mode); + +/** + * @brief Get the HID Idle Time. When the operation is complete the callback + * function will be called with ESP_HIDH_GET_IDLE_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * + * @return + * - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_get_idle(esp_bd_addr_t bd_addr); + +/** + * @brief Set the HID Idle Time. When the operation is complete the callback + * function will be called with ESP_HIDH_SET_IDLE_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] idle_time: Idle time rate + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_set_idle(esp_bd_addr_t bd_addr, uint16_t idle_time); + +/** + * @brief Send a GET_REPORT to HID device. When the operation is complete the callback + * function will be called with ESP_HIDH_GET_RPT_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] report_type: Report type + * @param[in] report_id: Report id + * @param[in] buffer_size: Buffer size + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_get_report(esp_bd_addr_t bd_addr, esp_hidh_report_type_t report_type, uint8_t report_id, + int buffer_size); + +/** + * @brief Send a SET_REPORT to HID device. When the operation is complete the callback + * function will be called with ESP_HIDH_SET_RPT_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] report_type: Report type + * @param[in] report: Report data pointer + * @param[in] len: Report data length + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_set_report(esp_bd_addr_t bd_addr, esp_hidh_report_type_t report_type, uint8_t *report, + size_t len); + +/** + * @brief Send data to HID device. When the operation is complete the callback + * function will be called with ESP_HIDH_DATA_EVT. + * + * @param[in] bd_addr: Remote device bluetooth device address. + * @param[in] data: Data pointer + * @param[in] len: Data length + * + * @return - ESP_OK: success + * - other: failed + */ +esp_err_t esp_bt_hid_host_send_data(esp_bd_addr_t bd_addr, uint8_t *data, size_t len); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/tools/sdk/esp32/include/bt/include/esp32/include/esp_bt.h b/tools/sdk/esp32/include/bt/include/esp32/include/esp_bt.h index 020b48bcf34..7c8f2ea744d 100644 --- a/tools/sdk/esp32/include/bt/include/esp32/include/esp_bt.h +++ b/tools/sdk/esp32/include/bt/include/esp32/include/esp_bt.h @@ -149,6 +149,12 @@ the adv packet will be discarded until the memory is restored. */ #define BTDM_CTRL_AUTO_LATENCY_EFF false #endif +#ifdef CONFIG_BTDM_CTRL_HLI +#define BTDM_CTRL_HLI CONFIG_BTDM_CTRL_HLI +#else +#define BTDM_CTRL_HLI false +#endif + #ifdef CONFIG_BTDM_CTRL_LEGACY_AUTH_VENDOR_EVT_EFF #define BTDM_CTRL_LEGACY_AUTH_VENDOR_EVT_EFF CONFIG_BTDM_CTRL_LEGACY_AUTH_VENDOR_EVT_EFF #else @@ -183,6 +189,7 @@ the adv packet will be discarded until the memory is restored. */ .ble_sca = CONFIG_BTDM_BLE_SLEEP_CLOCK_ACCURACY_INDEX_EFF, \ .pcm_role = CONFIG_BTDM_CTRL_PCM_ROLE_EFF, \ .pcm_polar = CONFIG_BTDM_CTRL_PCM_POLAR_EFF, \ + .hli = BTDM_CTRL_HLI, \ .magic = ESP_BT_CONTROLLER_CONFIG_MAGIC_VAL, \ }; @@ -224,6 +231,7 @@ typedef struct { uint8_t ble_sca; /*!< BLE low power crystal accuracy index */ uint8_t pcm_role; /*!< PCM role (master & slave)*/ uint8_t pcm_polar; /*!< PCM polar trig (falling clk edge & rising clk edge) */ + bool hli; /*!< Using high level interrupt or not */ uint32_t magic; /*!< Magic number */ } esp_bt_controller_config_t; diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/address.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/address.h new file mode 100644 index 00000000000..8b8d9a24fae --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/address.h @@ -0,0 +1,213 @@ +/* + * address.h -- representation of network addresses + * + * Copyright (C) 2010-2011,2015-2016 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file address.h + * @brief Representation of network addresses + */ + +#ifndef COAP_ADDRESS_H_ +#define COAP_ADDRESS_H_ + +#include +#include +#include +#include +#include "libcoap.h" + +#if defined(WITH_LWIP) + +#include + +typedef struct coap_address_t { + uint16_t port; + ip_addr_t addr; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +COAP_STATIC_INLINE uint16_t +coap_address_get_port(const coap_address_t *addr) { + return ntohs(addr->port); +} + +/** + * Sets the port field of @p addr to @p port (in host byte order). + */ +COAP_STATIC_INLINE void +coap_address_set_port(coap_address_t *addr, uint16_t port) { + addr->port = htons(port); +} + +#define _coap_address_equals_impl(A, B) \ + ((A)->port == (B)->port \ + && (!!ip_addr_cmp(&(A)->addr,&(B)->addr))) + +#define _coap_address_isany_impl(A) ip_addr_isany(&(A)->addr) + +#define _coap_is_mcast_impl(Address) ip_addr_ismulticast(&(Address)->addr) + +#elif defined(WITH_CONTIKI) + +#include "uip.h" + +typedef struct coap_address_t { + uip_ipaddr_t addr; + uint16_t port; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +COAP_STATIC_INLINE uint16_t +coap_address_get_port(const coap_address_t *addr) { + return uip_ntohs(addr->port); +} + +/** + * Sets the port field of @p addr to @p port (in host byte order). + */ +COAP_STATIC_INLINE void +coap_address_set_port(coap_address_t *addr, uint16_t port) { + addr->port = uip_htons(port); +} + +#define _coap_address_equals_impl(A,B) \ + ((A)->port == (B)->port \ + && uip_ipaddr_cmp(&((A)->addr),&((B)->addr))) + +/** @todo implementation of _coap_address_isany_impl() for Contiki */ +#define _coap_address_isany_impl(A) 0 + +#define _coap_is_mcast_impl(Address) uip_is_addr_mcast(&((Address)->addr)) + +#else /* WITH_LWIP || WITH_CONTIKI */ + + /** multi-purpose address abstraction */ +typedef struct coap_address_t { + socklen_t size; /**< size of addr */ + union { + struct sockaddr sa; + struct sockaddr_in sin; + struct sockaddr_in6 sin6; + } addr; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +uint16_t coap_address_get_port(const coap_address_t *addr); + +/** + * Set the port field of @p addr to @p port (in host byte order). + */ +void coap_address_set_port(coap_address_t *addr, uint16_t port); + +/** + * Compares given address objects @p a and @p b. This function returns @c 1 if + * addresses are equal, @c 0 otherwise. The parameters @p a and @p b must not be + * @c NULL; + */ +int coap_address_equals(const coap_address_t *a, const coap_address_t *b); + +COAP_STATIC_INLINE int +_coap_address_isany_impl(const coap_address_t *a) { + /* need to compare only relevant parts of sockaddr_in6 */ + switch (a->addr.sa.sa_family) { + case AF_INET: + return a->addr.sin.sin_addr.s_addr == INADDR_ANY; + case AF_INET6: + return memcmp(&in6addr_any, + &a->addr.sin6.sin6_addr, + sizeof(in6addr_any)) == 0; + default: + ; + } + + return 0; +} +#endif /* WITH_LWIP || WITH_CONTIKI */ + +/** + * Resets the given coap_address_t object @p addr to its default values. In + * particular, the member size must be initialized to the available size for + * storing addresses. + * + * @param addr The coap_address_t object to initialize. + */ +void coap_address_init(coap_address_t *addr); + +/* Convenience function to copy IPv6 addresses without garbage. */ + +COAP_STATIC_INLINE void +coap_address_copy( coap_address_t *dst, const coap_address_t *src ) { +#if defined(WITH_LWIP) || defined(WITH_CONTIKI) + memcpy( dst, src, sizeof( coap_address_t ) ); +#else + memset( dst, 0, sizeof( coap_address_t ) ); + dst->size = src->size; + if ( src->addr.sa.sa_family == AF_INET6 ) { + dst->addr.sin6.sin6_family = src->addr.sin6.sin6_family; + dst->addr.sin6.sin6_addr = src->addr.sin6.sin6_addr; + dst->addr.sin6.sin6_port = src->addr.sin6.sin6_port; + dst->addr.sin6.sin6_scope_id = src->addr.sin6.sin6_scope_id; + } else if ( src->addr.sa.sa_family == AF_INET ) { + dst->addr.sin = src->addr.sin; + } else { + memcpy( &dst->addr, &src->addr, src->size ); + } +#endif +} + +#if defined(WITH_LWIP) || defined(WITH_CONTIKI) +/** + * Compares given address objects @p a and @p b. This function returns @c 1 if + * addresses are equal, @c 0 otherwise. The parameters @p a and @p b must not be + * @c NULL; + */ +COAP_STATIC_INLINE int +coap_address_equals(const coap_address_t *a, const coap_address_t *b) { + assert(a); assert(b); + return _coap_address_equals_impl(a, b); +} +#endif + +/** + * Checks if given address object @p a denotes the wildcard address. This + * function returns @c 1 if this is the case, @c 0 otherwise. The parameters @p + * a must not be @c NULL; + */ +COAP_STATIC_INLINE int +coap_address_isany(const coap_address_t *a) { + assert(a); + return _coap_address_isany_impl(a); +} + +#if !defined(WITH_LWIP) && !defined(WITH_CONTIKI) + +/** + * Checks if given address @p a denotes a multicast address. This function + * returns @c 1 if @p a is multicast, @c 0 otherwise. + */ +int coap_is_mcast(const coap_address_t *a); +#else /* !WITH_LWIP && !WITH_CONTIKI */ +/** + * Checks if given address @p a denotes a multicast address. This function + * returns @c 1 if @p a is multicast, @c 0 otherwise. + */ +COAP_STATIC_INLINE int +coap_is_mcast(const coap_address_t *a) { + return a && _coap_is_mcast_impl(a); +} +#endif /* !WITH_LWIP && !WITH_CONTIKI */ + +#endif /* COAP_ADDRESS_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/async.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/async.h new file mode 100644 index 00000000000..a61e0c09828 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/async.h @@ -0,0 +1,116 @@ +/* + * async.h -- state management for asynchronous messages + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file async.h + * @brief State management for asynchronous messages + */ + +#ifndef COAP_ASYNC_H_ +#define COAP_ASYNC_H_ + +#include "net.h" + +/** + * @defgroup coap_async Asynchronous Messaging + * @{ + * API functions for Async "separate" messages. + * A coap_context_t object holds a list of coap_async_t objects that can + * be used to generate a separate response in the case a result of a request + * cannot be delivered immediately. + */ + +/** + * Returns @c 1 if libcoap was built with separate messages enabled, + * @c 0 otherwise. + */ +int coap_async_is_supported(void); + +/** + * Allocates a new coap_async_t object and fills its fields according to + * the given @p request. This function returns a pointer to the registered + * coap_async_t object or @c NULL on error. Note that this function will + * return @c NULL in case that an object with the same identifier is already + * registered. + * + * When the delay expires, a copy of the @p request will get sent to the + * appropriate request handler. + * + * @param session The session that is used for asynchronous transmissions. + * @param request The request that is handled asynchronously. + * @param delay The amount of time to delay before sending response, 0 means + * wait forever. + * + * @return A pointer to the registered coap_async_t object or @c + * NULL in case of an error. + */ +coap_async_t * +coap_register_async(coap_session_t *session, + const coap_pdu_t *request, + coap_tick_t delay); + +/** + * Update the delay timeout, so changing when the registered @p async triggers. + * + * When the new delay expires, a copy of the original request will get sent to + * the appropriate request handler. + * + * @param async The object to update. + * @param delay The amount of time to delay before sending response, 0 means + * wait forever. + */ +void +coap_async_set_delay(coap_async_t *async, coap_tick_t delay); + +/** + * Releases the memory that was allocated by coap_register_async() for the + * object @p async. + * + * @param session The session to use. + * @param async The object to delete. + */ +void +coap_free_async(coap_session_t *session, coap_async_t *async); + +/** + * Retrieves the object identified by @p token from the list of asynchronous + * transactions that are registered with @p context. This function returns a + * pointer to that object or @c NULL if not found. + * + * @param session The session that is used for asynchronous transmissions. + * @param token The PDU's token of the object to retrieve. + * + * @return A pointer to the object identified by @p token or @c NULL if + * not found. + */ +coap_async_t *coap_find_async(coap_session_t *session, coap_bin_const_t token); + +/** + * Set the application data pointer held in @p async. This overwrites any + * existing data pointer. + * + * @param async The async state object. + * @param app_data The pointer to the data. + */ +void coap_async_set_app_data(coap_async_t *async, void *app_data); + +/** + * Gets the application data pointer held in @p async. + * + * @param async The async state object. + * + * @return The applicaton data pointer. + */ +void *coap_async_get_app_data(const coap_async_t *async); + +/** @} */ + +#endif /* COAP_ASYNC_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/block.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/block.h new file mode 100644 index 00000000000..a2aac00fdc6 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/block.h @@ -0,0 +1,348 @@ +/* + * block.h -- block transfer + * + * Copyright (C) 2010-2012,2014-2015 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_BLOCK_H_ +#define COAP_BLOCK_H_ + +#include "encode.h" +#include "option.h" +#include "pdu.h" + +/** + * @defgroup block Block Transfer + * API functions for handling PDUs using CoAP BLOCK options + * @{ + */ + +#ifndef COAP_MAX_BLOCK_SZX +/** + * The largest value for the SZX component in a Block option. + */ +#define COAP_MAX_BLOCK_SZX 6 +#endif /* COAP_MAX_BLOCK_SZX */ + +/** + * Structure of Block options. + */ +typedef struct { + unsigned int num; /**< block number */ + unsigned int m:1; /**< 1 if more blocks follow, 0 otherwise */ + unsigned int szx:3; /**< block size */ +} coap_block_t; + +#define COAP_BLOCK_USE_LIBCOAP 0x01 /* Use libcoap to do block requests */ +#define COAP_BLOCK_SINGLE_BODY 0x02 /* Deliver the data as a single body */ + +/** + * Returns the value of the least significant byte of a Block option @p opt. + * For zero-length options (i.e. num == m == szx == 0), COAP_OPT_BLOCK_LAST + * returns @c NULL. + */ +#define COAP_OPT_BLOCK_LAST(opt) \ + (coap_opt_length(opt) ? (coap_opt_value(opt) + (coap_opt_length(opt)-1)) : 0) + +/** Returns the value of the More-bit of a Block option @p opt. */ +#define COAP_OPT_BLOCK_MORE(opt) \ + (coap_opt_length(opt) ? (*COAP_OPT_BLOCK_LAST(opt) & 0x08) : 0) + +/** Returns the value of the SZX-field of a Block option @p opt. */ +#define COAP_OPT_BLOCK_SZX(opt) \ + (coap_opt_length(opt) ? (*COAP_OPT_BLOCK_LAST(opt) & 0x07) : 0) + +/** + * Returns the value of field @c num in the given block option @p block_opt. + */ +unsigned int coap_opt_block_num(const coap_opt_t *block_opt); + +/** + * Checks if more than @p num blocks are required to deliver @p data_len + * bytes of data for a block size of 1 << (@p szx + 4). + */ +COAP_STATIC_INLINE int +coap_more_blocks(size_t data_len, unsigned int num, uint16_t szx) { + return ((num+1) << (szx + 4)) < data_len; +} + +#if 0 +/** Sets the More-bit in @p block_opt */ +COAP_STATIC_INLINE void +coap_opt_block_set_m(coap_opt_t *block_opt, int m) { + if (m) + *(coap_opt_value(block_opt) + (coap_opt_length(block_opt) - 1)) |= 0x08; + else + *(coap_opt_value(block_opt) + (coap_opt_length(block_opt) - 1)) &= ~0x08; +} +#endif + +/** + * Initializes @p block from @p pdu. @p number must be either COAP_OPTION_BLOCK1 + * or COAP_OPTION_BLOCK2. When option @p number was found in @p pdu, @p block is + * initialized with values from this option and the function returns the value + * @c 1. Otherwise, @c 0 is returned. + * + * @param pdu The pdu to search for option @p number. + * @param number The option number to search for (must be COAP_OPTION_BLOCK1 or + * COAP_OPTION_BLOCK2). + * @param block The block structure to initilize. + * + * @return @c 1 on success, @c 0 otherwise. + */ +int coap_get_block(const coap_pdu_t *pdu, coap_option_num_t number, + coap_block_t *block); + +/** + * Writes a block option of type @p number to message @p pdu. If the requested + * block size is too large to fit in @p pdu, it is reduced accordingly. An + * exception is made for the final block when less space is required. The actual + * length of the resource is specified in @p data_length. + * + * This function may change *block to reflect the values written to @p pdu. As + * the function takes into consideration the remaining space @p pdu, no more + * options should be added after coap_write_block_opt() has returned. + * + * @param block The block structure to use. On return, this object is + * updated according to the values that have been written to + * @p pdu. + * @param number COAP_OPTION_BLOCK1 or COAP_OPTION_BLOCK2. + * @param pdu The message where the block option should be written. + * @param data_length The length of the actual data that will be added the @p + * pdu by calling coap_add_block(). + * + * @return @c 1 on success, or a negative value on error. + */ +int coap_write_block_opt(coap_block_t *block, + coap_option_num_t number, + coap_pdu_t *pdu, + size_t data_length); + +/** + * Adds the @p block_num block of size 1 << (@p block_szx + 4) from source @p + * data to @p pdu. + * + * @param pdu The message to add the block. + * @param len The length of @p data. + * @param data The source data to fill the block with. + * @param block_num The actual block number. + * @param block_szx Encoded size of block @p block_number. + * + * @return @c 1 on success, @c 0 otherwise. + */ +int coap_add_block(coap_pdu_t *pdu, + size_t len, + const uint8_t *data, + unsigned int block_num, + unsigned char block_szx); + +/** + * Re-assemble payloads into a body + * + * @param body_data The pointer to the data for the body holding the + * representation so far or NULL if the first time. + * @param length The length of @p data. + * @param data The payload data to update the body with. + * @param offset The offset of the @p data into the body. + * @param total The estimated total size of the body. + * + * @return The current representation of the body or @c NULL if error. + * If NULL, @p body_data will have been de-allocated. + */ +coap_binary_t * +coap_block_build_body(coap_binary_t *body_data, size_t length, + const uint8_t *data, size_t offset, size_t total); + +/** + * Adds the appropriate part of @p data to the @p response pdu. If blocks are + * required, then the appropriate block will be added to the PDU and sent. + * Adds a ETAG option that is the hash of the entire data if the data is to be + * split into blocks + * Used by a request handler. + * + * Note: The application will get called for every packet of a large body to + * process. Consider using coap_add_data_response_large() instead. + * + * @param request The requesting pdu. + * @param response The response pdu. + * @param media_type The format of the data. + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage. + * @param length The total length of the data. + * @param data The entire data block to transmit. + * + */ +void +coap_add_data_blocked_response(const coap_pdu_t *request, + coap_pdu_t *response, + uint16_t media_type, + int maxage, + size_t length, + const uint8_t* data); + +/** + * Callback handler for de-allocating the data based on @p app_ptr provided to + * coap_add_data_large_*() functions following transmission of the supplied + * data. + * + * @param session The session that this data is associated with + * @param app_ptr The application provided pointer provided to the + * coap_add_data_large_* functions. + */ +typedef void (*coap_release_large_data_t)(coap_session_t *session, + void *app_ptr); + +/** + * Associates given data with the @p pdu that is passed as second parameter. + * + * If all the data can be transmitted in a single PDU, this is functionally + * the same as coap_add_data() except @p release_func (if not NULL) will get + * invoked after data transmission. + * + * Used for a client request. + * + * If the data spans multiple PDUs, then the data will get transmitted using + * BLOCK1 option with the addition of the SIZE1 option. + * The underlying library will handle the transmission of the individual blocks. + * Once the body of data has been transmitted (or a failure occurred), then + * @p release_func (if not NULL) will get called so the application can + * de-allocate the @p data based on @p app_data. It is the responsibility of + * the application not to change the contents of @p data until the data + * transfer has completed. + * + * There is no need for the application to include the BLOCK1 option in the + * @p pdu. + * + * coap_add_data_large_request() (or the alternative coap_add_data_large_*() + * functions) must be called only once per PDU and must be the last PDU update + * before the PDU is transmitted. The (potentially) initial data will get + * transmitted when coap_send() is invoked. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set by coap_context_set_block_mode() + * for libcoap to work correctly when using this function. + * + * @param session The session to associate the data with. + * @param pdu The PDU to associate the data with. + * @param length The length of data to transmit. + * @param data The data to transmit. + * @param release_func The function to call to de-allocate @p data or @c NULL + * if the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if addition is successful, else @c 0. + */ +int coap_add_data_large_request(coap_session_t *session, + coap_pdu_t *pdu, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * Associates given data with the @p response pdu that is passed as fourth + * parameter. + * + * If all the data can be transmitted in a single PDU, this is functionally + * the same as coap_add_data() except @p release_func (if not NULL) will get + * invoked after data transmission. The MEDIA_TYPE, MAXAGE and ETAG options may + * be added in as appropriate. + * + * Used by a server request handler to create the response. + * + * If the data spans multiple PDUs, then the data will get transmitted using + * BLOCK2 (response) option with the addition of the SIZE2 and ETAG + * options. The underlying library will handle the transmission of the + * individual blocks. Once the body of data has been transmitted (or a + * failure occurred), then @p release_func (if not NULL) will get called so the + * application can de-allocate the @p data based on @p app_data. It is the + * responsibility of the application not to change the contents of @p data + * until the data transfer has completed. + * + * There is no need for the application to include the BLOCK2 option in the + * @p pdu. + * + * coap_add_data_large_response() (or the alternative coap_add_data_large*() + * functions) must be called only once per PDU and must be the last PDU update + * before returning from the request handler function. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set by coap_context_set_block_mode() + * for libcoap to work correctly when using this function. + * + * @param resource The resource the data is associated with. + * @param session The coap session. + * @param request The requesting pdu. + * @param response The response pdu. + * @param query The query taken from the (original) requesting pdu. + * @param media_type The format of the data. + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage. + * @param etag ETag to use if not 0. + * @param length The total length of the data. + * @param data The entire data block to transmit. + * @param release_func The function to call to de-allocate @p data or NULL if + * the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if addition is successful, else @c 0. + */ +int +coap_add_data_large_response(coap_resource_t *resource, + coap_session_t *session, + const coap_pdu_t *request, + coap_pdu_t *response, + const coap_string_t *query, + uint16_t media_type, + int maxage, + uint64_t etag, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * Set the context level CoAP block handling bits for handling RFC7959. + * These bits flow down to a session when a session is created and if the peer + * does not support something, an appropriate bit may get disabled in the + * session block_mode. + * The session block_mode then flows down into coap_crcv_t or coap_srcv_t where + * again an appropriate bit may get disabled. + * + * Note: This function must be called before the session is set up. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set if libcoap is to do all the + * block tracking and requesting, otherwise the application will have to do + * all of this work (the default if coap_context_set_block_mode() is not + * called). + * + * @param context The coap_context_t object. + * @param block_mode Zero or more COAP_BLOCK_ or'd options + */ +void coap_context_set_block_mode(coap_context_t *context, + uint8_t block_mode); + +/** + * Cancel an observe that is being tracked by the client large receive logic. + * (coap_context_set_block_mode() has to be called) + * This will trigger the sending of an observe cancel pdu to the server. + * + * @param session The session that is being used for the observe. + * @param token The original token used to initiate the observation. + * @param message_type The COAP_MESSAGE_ type (NON or CON) to send the observe + * cancel pdu as. + * + * @return @c 1 if observe cancel transmission initiation is successful, + * else @c 0. + */ +int coap_cancel_observe(coap_session_t *session, coap_binary_t *token, + coap_pdu_type_t message_type); + +/**@}*/ + +#endif /* COAP_BLOCK_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_asn1_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_asn1_internal.h new file mode 100644 index 00000000000..5bb4e2a8dbe --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_asn1_internal.h @@ -0,0 +1,89 @@ +/* + * coap_asn1_internal.h -- ASN.1 functions for libcoap + * + * Copyright (C) 2020 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_asn1_internal.h + * @brief COAP ASN.1 internal information + */ + +#ifndef COAP_ASN1_INTERNAL_H_ +#define COAP_ASN1_INTERNAL_H_ + + +/** + * @defgroup asn1 ASN.1 Support (Internal) + * CoAP ASN.1 Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +typedef enum { + COAP_ASN1_NONE = 0, + COAP_ASN1_INTEGER = 2, + COAP_ASN1_BITSTRING = 3, + COAP_ASN1_OCTETSTRING = 4, + COAP_ASN1_IDENTIFIER = 6, +} coap_asn1_tag_t; + +/** + * Callback to validate the asn1 tag and data. + * + * Internal function. + * + * @param data The start of the tag and data + * @param size The size of the tag and data + * + * @return @c 1 if pass, else @c 0 if fail + */ +typedef int (*asn1_validate)(const uint8_t *data, size_t size); + +/** + * Get the asn1 length from the current @p ptr. + * + * Internal function. + * + * @param ptr The current asn.1 object length pointer + * + * @return The length of the asn.1 object. @p ptr is updated to be after the length. + */ +size_t asn1_len(const uint8_t **ptr); + +/** + * Get the asn1 tag from the current @p ptr. + * + * Internal function. + * + * @param ptr The current asn.1 object tag pointer + * @param constructed 1 if current tag is constructed + * @param class The current class of the tag + * + * @return The tag value.@p ptr is updated to be after the tag. + */ +coap_asn1_tag_t asn1_tag_c(const uint8_t **ptr, int *constructed, int *class); + +/** + * Get the asn1 tag and data from the current @p ptr. + * + * Internal function. + * + * @param ltag The tag to look for + * @param ptr The current asn.1 object pointer + * @param tlen The remaining size oof the asn.1 data + * @param validate Call validate to verify tag data or @c NULL + * + * @return The asn.1 tag and data or @c NULL if not found + */ +coap_binary_t *get_asn1_tag(coap_asn1_tag_t ltag, const uint8_t *ptr, + size_t tlen, asn1_validate validate); + +/** @} */ + +#endif /* COAP_ASN1_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_async_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_async_internal.h new file mode 100644 index 00000000000..a23b1c8e697 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_async_internal.h @@ -0,0 +1,67 @@ +/* + * coap_async_internal.h -- state management for asynchronous messages + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_async_internal.h + * @brief CoAP async internal information + */ + +#ifndef COAP_ASYNC_INTERNAL_H_ +#define COAP_ASYNC_INTERNAL_H_ + +#include "coap3/net.h" + +#ifndef WITHOUT_ASYNC + +/** + * @defgroup coap_async_internal Asynchronous Messaging (Internal) + * @{ + * CoAP Async Structures, Enums and Functions that are not exposed to + * applications. + * A coap_context_t object holds a list of coap_async_t objects that can be + * used to generate a separate response in the case a result of a request cannot + * be delivered immediately. + */ +struct coap_async_t { + struct coap_async_t *next; /**< internally used for linking */ + coap_tick_t delay; /**< When to delay to before triggering the response + 0 indicates never trigger */ + coap_session_t *session; /**< transaction session */ + coap_pdu_t *pdu; /**< copy of request pdu */ + void* appdata; /** User definable data pointer */ +}; + +/** + * Checks if there are any pending Async requests - if so, send them off. + * Otherewise return the time remaining for the next Async to be triggered + * or 0 if nothing to do. + * + * @param context The current context. + * @param now The current time in ticks. + * + * @return The tick time before the next Async needs to go, else 0 if + * nothing to do. + */ +coap_tick_t coap_check_async(coap_context_t *context, coap_tick_t now); + +/** + * Removes and frees off all of the async entries for the given context. + * + * @param context The context to remove all async entries from. + */ +void +coap_delete_all_async(coap_context_t *context); + +/** @} */ + +#endif /* WITHOUT_ASYNC */ + +#endif /* COAP_ASYNC_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_block_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_block_internal.h new file mode 100644 index 00000000000..9abe81557fa --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_block_internal.h @@ -0,0 +1,239 @@ +/* + * coap_block_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * Copyright (C) 2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_block_internal.h + * @brief COAP block internal information + */ + +#ifndef COAP_BLOCK_INTERNAL_H_ +#define COAP_BLOCK_INTERNAL_H_ + +#include "coap_pdu_internal.h" +#include "resource.h" + +/** + * @defgroup block_internal Block (Internal) + * Structures, Enums and Functions that are not exposed to applications + * @{ + */ + +typedef enum { + COAP_RECURSE_OK, + COAP_RECURSE_NO +} coap_recurse_t; + +struct coap_lg_range { + uint32_t begin; + uint32_t end; +}; + +#define COAP_RBLOCK_CNT 4 +/** + * Structure to keep track of received blocks + */ +typedef struct coap_rblock_t { + uint32_t used; + uint32_t retry; + struct coap_lg_range range[COAP_RBLOCK_CNT]; + coap_tick_t last_seen; +} coap_rblock_t; + +/** + * Structure to keep track of block1 specific information + * (Requests) + */ +typedef struct coap_l_block1_t { + coap_binary_t *app_token; /**< original PDU token */ + uint8_t token[8]; /**< last used token */ + size_t token_length; /**< length of token */ + uint32_t count; /**< the number of packets sent for payload */ +} coap_l_block1_t; + +/** + * Structure to keep track of block2 specific information + * (Responses) + */ +typedef struct coap_l_block2_t { + coap_resource_t *resource; /**< associated resource */ + coap_string_t *query; /**< Associated query for the resource */ + uint64_t etag; /**< ETag value */ + coap_time_t maxage_expire; /**< When this entry expires */ +} coap_l_block2_t; + +/** + * Structure to hold large body (many blocks) transmission information + */ +struct coap_lg_xmit_t { + struct coap_lg_xmit_t *next; + uint8_t blk_size; /**< large block transmission size */ + uint16_t option; /**< large block transmisson CoAP option */ + int last_block; /**< last acknowledged block number */ + const uint8_t *data; /**< large data ptr */ + size_t length; /**< large data length */ + size_t offset; /**< large data next offset to transmit */ + union { + coap_l_block1_t b1; + coap_l_block2_t b2; + } b; + coap_pdu_t pdu; /**< skeletal PDU */ + coap_tick_t last_payload; /**< Last time MAX_PAYLOAD was sent or 0 */ + coap_tick_t last_used; /**< Last time all data sent or 0 */ + coap_release_large_data_t release_func; /**< large data de-alloc function */ + void *app_ptr; /**< applicaton provided ptr for de-alloc function */ +}; + +/** + * Structure to hold large body (many blocks) client receive information + */ +struct coap_lg_crcv_t { + struct coap_lg_crcv_t *next; + uint8_t observe[3]; /**< Observe data (if set) (only 24 bits) */ + uint8_t observe_length;/**< Length of observe data */ + uint8_t observe_set; /**< Set if this is an observe receive PDU */ + uint8_t etag_set; /**< Set if ETag is in receive PDU */ + uint8_t etag_length; /**< ETag length */ + uint8_t etag[8]; /**< ETag for block checking */ + uint16_t content_format; /**< Content format for the set of blocks */ + uint8_t last_type; /**< Last request type (CON/NON) */ + uint8_t initial; /**< If set, has not been used yet */ + uint8_t szx; /**< size of individual blocks */ + size_t total_len; /**< Length as indicated by SIZE2 option */ + coap_binary_t *body_data; /**< Used for re-assembling entire body */ + coap_binary_t *app_token; /**< app requesting PDU token */ + uint8_t base_token[8]; /**< established base PDU token */ + size_t base_token_length; /**< length of token */ + uint8_t token[8]; /**< last used token */ + size_t token_length; /**< length of token */ + coap_pdu_t pdu; /**< skeletal PDU */ + coap_rblock_t rec_blocks; /** < list of received blocks */ + coap_tick_t last_used; /**< Last time all data sent or 0 */ + uint16_t block_option; /**< Block option in use */ +}; + +/** + * Structure to hold large body (many blocks) server receive information + */ +struct coap_lg_srcv_t { + struct coap_lg_srcv_t *next; + uint8_t observe[3]; /**< Observe data (if set) (only 24 bits) */ + uint8_t observe_length;/**< Length of observe data */ + uint8_t observe_set; /**< Set if this is an observe receive PDU */ + uint8_t rtag_set; /**< Set if RTag is in receive PDU */ + uint8_t rtag_length; /**< RTag length */ + uint8_t rtag[8]; /**< RTag for block checking */ + uint16_t content_format; /**< Content format for the set of blocks */ + uint8_t last_type; /**< Last request type (CON/NON) */ + uint8_t szx; /**< size of individual blocks */ + size_t total_len; /**< Length as indicated by SIZE1 option */ + coap_binary_t *body_data; /**< Used for re-assembling entire body */ + size_t amount_so_far; /**< Amount of data seen so far */ + coap_resource_t *resource; /**< associated resource */ + coap_str_const_t *uri_path; /** set to uri_path if unknown resource */ + coap_rblock_t rec_blocks; /** < list of received blocks */ + uint8_t last_token[8]; /**< last used token */ + size_t last_token_length; /**< length of token */ + coap_mid_t last_mid; /**< Last received mid for this set of packets */ + coap_tick_t last_used; /**< Last time data sent or 0 */ + uint16_t block_option; /**< Block option in use */ +}; + +coap_lg_crcv_t * coap_block_new_lg_crcv(coap_session_t *session, + coap_pdu_t *pdu); + +void coap_block_delete_lg_crcv(coap_session_t *session, + coap_lg_crcv_t *lg_crcv); + +coap_tick_t coap_block_check_lg_crcv_timeouts(coap_session_t *session, + coap_tick_t now); + +void coap_block_delete_lg_srcv(coap_session_t *session, + coap_lg_srcv_t *lg_srcv); + +coap_tick_t coap_block_check_lg_srcv_timeouts(coap_session_t *session, + coap_tick_t now); + +int coap_handle_request_send_block(coap_session_t *session, + coap_pdu_t *pdu, + coap_pdu_t *response, + coap_resource_t *resource, + coap_string_t *query); + +int coap_handle_request_put_block(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *pdu, + coap_pdu_t *response, + coap_resource_t *resource, + coap_string_t *uri_path, + coap_opt_t *observe, + coap_string_t *query, + coap_method_handler_t h, + int *added_block); + +int coap_handle_response_send_block(coap_session_t *session, coap_pdu_t *rcvd); + +int coap_handle_response_get_block(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *sent, + coap_pdu_t *rcvd, + coap_recurse_t recursive); + +void coap_block_delete_lg_xmit(coap_session_t *session, + coap_lg_xmit_t *lg_xmit); + +/** + * The function that does all the work for the coap_add_data_large*() + * functions. + * + * @param session The session to associate the data with. + * @param pdu The PDU to associate the data with. + * @param resource The resource to associate the data with (BLOCK2). + * @param query The query to associate the data with (BLOCK2). + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage (BLOCK2). + * @param etag ETag to use if not 0 (BLOCK2). + * @param length The length of data to transmit. + * @param data The data to transmit. + * @param release_func The function to call to de-allocate @p data or NULL if + * the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if transmission initiation is successful, else @c 0. + */ +int coap_add_data_large_internal(coap_session_t *session, + coap_pdu_t *pdu, + coap_resource_t *resource, + const coap_string_t *query, + int maxage, + uint64_t etag, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * The function checks that the code in a newly formed lg_xmit created by + * coap_add_data_large_response() is updated. + * + * @param session The session + * @param response The response PDU to to check + * @param resource The requested resource + * @param query The requested query + */ +void coap_check_code_lg_xmit(coap_session_t *session, coap_pdu_t *response, + coap_resource_t *resource, coap_string_t *query); + +/** @} */ + +#endif /* COAP_BLOCK_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache.h new file mode 100644 index 00000000000..a8d2fd7a84e --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache.h @@ -0,0 +1,232 @@ +/* coap_cache.h -- Caching of CoAP requests +* +* Copyright (C) 2020 Olaf Bergmann +* + * SPDX-License-Identifier: BSD-2-Clause + * +* This file is part of the CoAP library libcoap. Please see +* README for terms of use. +*/ + +/** + * @file coap_cache.h + * @brief Provides a simple cache request storage for CoAP requests + */ + +#ifndef COAP_CACHE_H_ +#define COAP_CACHE_H_ + +#include "coap_forward_decls.h" + +/** + * @defgroup cache Cache Support + * API functions for CoAP Caching + * @{ + */ + +/** + * Callback to free off the app data when the cache-entry is + * being deleted / freed off. + * + * @param data The app data to be freed off. + */ +typedef void (*coap_cache_app_data_free_callback_t)(void *data); + +typedef enum coap_cache_session_based_t { + COAP_CACHE_NOT_SESSION_BASED, + COAP_CACHE_IS_SESSION_BASED +} coap_cache_session_based_t; + +typedef enum coap_cache_record_pdu_t { + COAP_CACHE_NOT_RECORD_PDU, + COAP_CACHE_RECORD_PDU +} coap_cache_record_pdu_t; + +/** + * Calculates a cache-key for the given CoAP PDU. See + * https://tools.ietf.org/html/rfc7252#section-5.6 + * for an explanation of CoAP cache keys. + * + * Specific CoAP options can be removed from the cache-key. Examples of + * this are the BLOCK1 and BLOCK2 options - which make no real sense including + * them in a client or server environment, but should be included in a proxy + * caching environment where things are cached on a per block basis. + * This is done globally by calling the coap_cache_ignore_options() + * function. + * + * NOTE: The returned cache-key needs to be freed off by the caller by + * calling coap_cache_delete_key(). + * + * @param session The session to add into cache-key if @p session_based + * is set. + * @param pdu The CoAP PDU for which a cache-key is to be + * calculated. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key, else COAP_CACHE_NOT_SESSION_BASED. + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_key_t *coap_cache_derive_key(const coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based); + +/** + * Calculates a cache-key for the given CoAP PDU. See + * https://tools.ietf.org/html/rfc7252#section-5.6 + * for an explanation of CoAP cache keys. + * + * Specific CoAP options can be removed from the cache-key. Examples of + * this are the BLOCK1 and BLOCK2 options - which make no real sense including + * them in a client or server environment, but should be included in a proxy + * caching environment where things are cached on a per block basis. + * This is done individually by specifying @p cache_ignore_count and + * @p cache_ignore_options . + * + * NOTE: The returned cache-key needs to be freed off by the caller by + * calling coap_cache_delete_key(). + * + * @param session The session to add into cache-key if @p session_based + * is set. + * @param pdu The CoAP PDU for which a cache-key is to be + * calculated. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key, else COAP_CACHE_NOT_SESSION_BASED. + * @param ignore_options The array of options to ignore. + * @param ignore_count The number of options to ignore. + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_key_t *coap_cache_derive_key_w_ignore(const coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based, + const uint16_t *ignore_options, + size_t ignore_count); + +/** + * Delete the cache-key. + * + * @param cache_key The cache-key to delete. + */ +void coap_delete_cache_key(coap_cache_key_t *cache_key); + +/** + * Define the CoAP options that are not to be included when calculating + * the cache-key. Options that are defined as Non-Cache and the Observe + * option are always ignored. + * + * @param context The context to save the ignored options information in. + * @param options The array of options to ignore. + * @param count The number of options to ignore. Use 0 to reset the + * options matching. + * + * @return @return @c 1 if successful, else @c 0. + */ +int coap_cache_ignore_options(coap_context_t *context, + const uint16_t *options, size_t count); + +/** + * Create a new cache-entry hash keyed by cache-key derived from the PDU. + * + * If @p session_based is set, then this cache-entry will get deleted when + * the session is freed off. + * If @p record_pdu is set, then the copied PDU will get freed off when + * this cache-entry is deleted. + * + * The cache-entry is maintained on a context hash list. + * + * @param session The session to use to derive the context from. + * @param pdu The pdu to use to generate the cache-key. + * @param record_pdu COAP_CACHE_RECORD_PDU if to take a copy of the PDU for + * later use, else COAP_CACHE_NOT_RECORD_PDU. + * @param session_based COAP_CACHE_IS_SESSION_BASED if to associate this + * cache-entry with the the session (which is embedded + * in the cache-entry), else COAP_CACHE_NOT_SESSION_BASED. + * @param idle_time Idle time in seconds before cache-entry is expired. + * If set to 0, it does not expire (but will get + * deleted if the session is deleted and it is session_based). + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_entry_t *coap_new_cache_entry(coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_record_pdu_t record_pdu, + coap_cache_session_based_t session_based, + unsigned int idle_time); + +/** + * Remove a cache-entry from the hash list and free off all the appropriate + * contents apart from app_data. + * + * @param context The context to use. + * @param cache_entry The cache-entry to remove. + */ +void coap_delete_cache_entry(coap_context_t *context, + coap_cache_entry_t *cache_entry); + +/** + * Searches for a cache-entry identified by @p cache_key. This + * function returns the corresponding cache-entry or @c NULL + * if not found. + * + * @param context The context to use. + * @param cache_key The cache-key to get the hashed coap-entry. + * + * @return The cache-entry for @p cache_key or @c NULL if not found. + */ +coap_cache_entry_t *coap_cache_get_by_key(coap_context_t *context, + const coap_cache_key_t *cache_key); + +/** + * Searches for a cache-entry corresponding to @p pdu. This + * function returns the corresponding cache-entry or @c NULL if not + * found. + * + * @param session The session to use. + * @param pdu The CoAP request to search for. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key to be used, else COAP_CACHE_NOT_SESSION_BASED. + * + * @return The cache-entry for @p request or @c NULL if not found. + */ +coap_cache_entry_t *coap_cache_get_by_pdu(coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based); + +/** + * Returns the PDU information stored in the @p coap_cache entry. + * + * @param cache_entry The CoAP cache entry. + * + * @return The PDU information stored in the cache_entry or NULL + * if the PDU was not initially copied. + */ +const coap_pdu_t *coap_cache_get_pdu(const coap_cache_entry_t *cache_entry); + +/** + * Stores @p data with the given cache entry. This function + * overwrites any value that has previously been stored with @p + * cache_entry. + * + * @param cache_entry The CoAP cache entry. + * @param data The data pointer to store with wih the cache entry. Note that + * this data must be valid during the lifetime of @p cache_entry. + * @param callback The callback to call to free off this data when the + * cache-entry is deleted, or @c NULL if not required. + */ +void coap_cache_set_app_data(coap_cache_entry_t *cache_entry, void *data, + coap_cache_app_data_free_callback_t callback); + +/** + * Returns any application-specific data that has been stored with @p + * cache_entry using the function coap_cache_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param cache_entry The CoAP cache entry. + * + * @return The data pointer previously stored or @c NULL if no data stored. + */ +void *coap_cache_get_app_data(const coap_cache_entry_t *cache_entry); + +/** @} */ + +#endif /* COAP_CACHE_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache_internal.h new file mode 100644 index 00000000000..29c0756875c --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_cache_internal.h @@ -0,0 +1,111 @@ +/* + * coap_cache_internal.h -- Cache functions for libcoap + * + * Copyright (C) 2019--2020 Olaf Bergmann and others + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_cache_internal.h + * @brief COAP cache internal information + */ + +#ifndef COAP_CACHE_INTERNAL_H_ +#define COAP_CACHE_INTERNAL_H_ + +#include "coap_io.h" + +/** + * @defgroup cache_internal Cache Support (Internal) + * CoAP Cache Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/* Holds a digest in binary typically sha256 except for notls */ +typedef struct coap_digest_t { + uint8_t key[32]; +} coap_digest_t; + +struct coap_cache_key_t { + uint8_t key[32]; +}; + +struct coap_cache_entry_t { + UT_hash_handle hh; + coap_cache_key_t *cache_key; + coap_session_t *session; + coap_pdu_t *pdu; + void* app_data; + coap_tick_t expire_ticks; + unsigned int idle_timeout; + coap_cache_app_data_free_callback_t callback; +}; + +/** + * Expire coap_cache_entry_t entries + * + * Internal function. + * + * @param context The context holding the coap-entries to exire + */ +void coap_expire_cache_entries(coap_context_t *context); + +typedef void coap_digest_ctx_t; + +/** + * Initialize a coap_digest + * + * Internal function. + * + * @return The digest context or @c NULL if failure. + */ +coap_digest_ctx_t *coap_digest_setup(void); + +/** + * Free off coap_digest_ctx_t. Always done by + * coap_digest_final() + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + */ +void coap_digest_free(coap_digest_ctx_t *digest_ctx); + +/** + * Update the coap_digest information with the next chunk of data + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + * @param data Pointer to data. + * @param data_len Number of bytes. + * + * @return @c 1 success, @c 0 failure. + */ +int coap_digest_update(coap_digest_ctx_t *digest_ctx, + const uint8_t *data, + size_t data_len + ); + +/** + * Finalize the coap_digest information into the provided + * @p digest_buffer. + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + * @param digest_buffer Pointer to digest buffer to update + * + * @return @c 1 success, @c 0 failure. + */ +int coap_digest_final(coap_digest_ctx_t *digest_ctx, + coap_digest_t *digest_buffer); + +/** @} */ + +#endif /* COAP_CACHE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_debug.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_debug.h new file mode 100644 index 00000000000..f8f70f64495 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_debug.h @@ -0,0 +1,247 @@ +/* + * coap_debug.h -- debug utilities + * + * Copyright (C) 2010-2011,2014 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DEBUG_H_ +#define COAP_DEBUG_H_ + +/** + * @defgroup logging Logging Support + * API functions for logging support + * @{ + */ + +#ifndef COAP_DEBUG_FD +/** + * Used for output for @c LOG_DEBUG to @c LOG_ERR. + */ +#define COAP_DEBUG_FD stdout +#endif + +#ifndef COAP_ERR_FD +/** + * Used for output for @c LOG_CRIT to @c LOG_EMERG. + */ +#define COAP_ERR_FD stderr +#endif + +#ifdef HAVE_SYSLOG_H +#include +/** + * Logging type. One of LOG_* from @b syslog. + */ +typedef short coap_log_t; +/* + LOG_DEBUG+2 gives ciphers in GnuTLS + Use COAP_LOG_CIPHERS to output Cipher Info in OpenSSL etc. + */ +#define COAP_LOG_CIPHERS (LOG_DEBUG+2) +#else /* !HAVE_SYSLOG_H */ +/** Pre-defined log levels akin to what is used in \b syslog + with LOG_CIPHERS added. */ + +#if !defined(RIOT_VERSION) +typedef enum { + LOG_EMERG=0, /**< Emergency */ + LOG_ALERT, /**< Alert */ + LOG_CRIT, /**< Critical */ + LOG_ERR, /**< Error */ + LOG_WARNING, /**< Warning */ + LOG_NOTICE, /**< Notice */ + LOG_INFO, /**< Information */ + LOG_DEBUG, /**< Debug */ + COAP_LOG_CIPHERS=LOG_DEBUG+2 /**< CipherInfo */ +} coap_log_t; +#else /* RIOT_VERSION */ +/* RIOT defines a subset of the syslog levels in log.h with different + * numeric values. The remaining levels are defined here. Note that + * output granularity differs from what would be expected when + * adhering to the syslog levels. + */ +#include +typedef short coap_log_t; +#define LOG_EMERG (0) +#define LOG_ALERT (1) +#define LOG_CRIT (2) +#define LOG_ERR (3) +/* LOG_WARNING (4) */ +#define LOG_NOTICE (5) +/* LOG_INFO (6) */ +/* LOG_DEBUG (7) */ +#define COAP_LOG_CIPHERS (9) +#endif /* RIOT_VERSION */ + +#endif /* !HAVE_SYSLOG_H */ + +/** + * Get the current logging level. + * + * @return One of the LOG_* values. + */ +coap_log_t coap_get_log_level(void); + +/** + * Sets the log level to the specified value. + * + * @param level One of the LOG_* values. + */ +void coap_set_log_level(coap_log_t level); + +/** + * Logging callback handler definition. + * + * @param level One of the LOG_* values. + * @param message Zero-terminated string message to log. + */ +typedef void (*coap_log_handler_t) (coap_log_t level, const char *message); + +/** + * Add a custom log callback handler. + * + * @param handler The logging handler to use or @p NULL to use default handler. + */ +void coap_set_log_handler(coap_log_handler_t handler); + +/** + * Get the library package name. + * + * @return Zero-terminated string with the name of this library. + */ +const char *coap_package_name(void); + +/** + * Get the library package version. + * + * @return Zero-terminated string with the library version. + */ +const char *coap_package_version(void); + +/** + * Writes the given text to @c COAP_ERR_FD (for @p level <= @c LOG_CRIT) or @c + * COAP_DEBUG_FD (for @p level >= @c LOG_ERR). The text is output only when + * @p level is below or equal to the log level that set by coap_set_log_level(). + * + * Internal function. + * + * @param level One of the LOG_* values. + & @param format The format string to use. + */ +#if (defined(__GNUC__)) +void coap_log_impl(coap_log_t level, + const char *format, ...) __attribute__ ((format(printf, 2, 3))); +#else +void coap_log_impl(coap_log_t level, const char *format, ...); +#endif + +#ifndef coap_log +/** + * Logging function. + * Writes the given text to @c COAP_ERR_FD (for @p level <= @c LOG_CRIT) or @c + * COAP_DEBUG_FD (for @p level >= @c LOG_ERR). The text is output only when + * @p level is below or equal to the log level that set by coap_set_log_level(). + * + * @param level One of the LOG_* values. + */ +#define coap_log(level, ...) do { \ + if ((int)((level))<=(int)coap_get_log_level()) \ + coap_log_impl((level), __VA_ARGS__); \ +} while(0) +#endif + +#include "pdu.h" + +/** + * Defines the output mode for the coap_show_pdu() function. + * + * @param use_fprintf @p 1 if the output is to use fprintf() (the default) + * @p 0 if the output is to use coap_log(). + */ +void coap_set_show_pdu_output(int use_fprintf); + +/** + * Display the contents of the specified @p pdu. + * Note: The output method of coap_show_pdu() is dependent on the setting of + * coap_set_show_pdu_output(). + * + * @param level The required minimum logging level. + * @param pdu The PDU to decode. + */ +void coap_show_pdu(coap_log_t level, const coap_pdu_t *pdu); + +/** + * Display the current (D)TLS library linked with and built for version. + * + * @param level The required minimum logging level. + */ +void coap_show_tls_version(coap_log_t level); + +/** + * Build a string containing the current (D)TLS library linked with and + * built for version. + * + * @param buffer The buffer to put the string into. + * @param bufsize The size of the buffer to put the string into. + * + * @return A pointer to the provided buffer. + */ +char *coap_string_tls_version(char *buffer, size_t bufsize); + +/** + * Build a string containing the current (D)TLS library support + * + * @param buffer The buffer to put the string into. + * @param bufsize The size of the buffer to put the string into. + * + * @return A pointer to the provided buffer. + */ +char *coap_string_tls_support(char *buffer, size_t bufsize); + +/** + * Print the address into the defined buffer. + * + * Internal Function. + * + * @param address The address to print. + * @param buffer The buffer to print into. + * @param size The size of the buffer to print into. + * + * @return The amount written into the buffer. + */ +size_t coap_print_addr(const coap_address_t *address, + unsigned char *buffer, size_t size); + +/** @} */ + +/** + * Set the packet loss level for testing. This can be in one of two forms. + * + * Percentage : 0% to 100%. Use the specified probability. + * 0% is send all packets, 100% is drop all packets. + * + * List: A comma separated list of numbers or number ranges that are the + * packets to drop. + * + * @param loss_level The defined loss level (percentage or list). + * + * @return @c 1 If loss level set, @c 0 if there is an error. + */ +int coap_debug_set_packet_loss(const char *loss_level); + +/** + * Check to see whether a packet should be sent or not. + * + * Internal function + * + * @return @c 1 if packet is to be sent, @c 0 if packet is to be dropped. + */ +int coap_debug_send_packet(void); + + +#endif /* COAP_DEBUG_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls.h new file mode 100644 index 00000000000..cbd369dfce6 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls.h @@ -0,0 +1,479 @@ +/* + * coap_dtls.h -- (Datagram) Transport Layer Support for libcoap + * + * Copyright (C) 2016 Olaf Bergmann + * Copyright (C) 2017 Jean-Claude Michelou + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DTLS_H_ +#define COAP_DTLS_H_ + +#include "coap_time.h" +#include "str.h" + +/** + * @defgroup dtls DTLS Support + * API functions for interfacing with DTLS libraries. + * @{ + */ + +typedef struct coap_dtls_pki_t coap_dtls_pki_t; + +#ifndef COAP_DTLS_HINT_LENGTH +#define COAP_DTLS_HINT_LENGTH 128 +#endif + +typedef enum coap_dtls_role_t { + COAP_DTLS_ROLE_CLIENT, /**< Internal function invoked for client */ + COAP_DTLS_ROLE_SERVER /**< Internal function invoked for server */ +} coap_dtls_role_t; + +#define COAP_DTLS_RPK_CERT_CN "RPK" + +/** + * Check whether DTLS is available. + * + * @return @c 1 if support for DTLS is enabled, or @c 0 otherwise. + */ +int coap_dtls_is_supported(void); + +/** + * Check whether TLS is available. + * + * @return @c 1 if support for TLS is enabled, or @c 0 otherwise. + */ +int coap_tls_is_supported(void); + +typedef enum coap_tls_library_t { + COAP_TLS_LIBRARY_NOTLS = 0, /**< No DTLS library */ + COAP_TLS_LIBRARY_TINYDTLS, /**< Using TinyDTLS library */ + COAP_TLS_LIBRARY_OPENSSL, /**< Using OpenSSL library */ + COAP_TLS_LIBRARY_GNUTLS, /**< Using GnuTLS library */ + COAP_TLS_LIBRARY_MBEDTLS, /**< Using Mbed TLS library */ +} coap_tls_library_t; + +/** + * The structure used for returning the underlying (D)TLS library + * information. + */ +typedef struct coap_tls_version_t { + uint64_t version; /**< (D)TLS runtime Library Version */ + coap_tls_library_t type; /**< Library type. One of COAP_TLS_LIBRARY_* */ + uint64_t built_version; /**< (D)TLS Built against Library Version */ +} coap_tls_version_t; + +/** + * Determine the type and version of the underlying (D)TLS library. + * + * @return The version and type of library libcoap was compiled against. + */ +coap_tls_version_t *coap_get_tls_library_version(void); + +/** + * Additional Security setup handler that can be set up by + * coap_context_set_pki(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to do some additional checks/changes/updates. + * + * @param tls_session The security session definition - e.g. SSL * for OpenSSL. + * NULL if server callback. + * This will be dependent on the underlying TLS library - + * see coap_get_tls_library_version() + * @param setup_data A structure containing setup data originally passed into + * coap_context_set_pki() or coap_new_client_session_pki(). + * + * @return @c 1 if successful, else @c 0. + */ +typedef int (*coap_dtls_security_setup_t)(void* tls_session, + coap_dtls_pki_t *setup_data); + +/** + * CN Validation callback that can be set up by coap_context_set_pki(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the CN is allowed. + * CN is the SubjectAltName in the cert, if not present, then the leftmost + * Common Name (CN) component of the subject name. + * NOTE: If using RPK, then the Public Key does not contain a CN, but the + * content of COAP_DTLS_RPK_CERT_CN is presented for the @p cn parameter. + * + * @param cn The determined CN from the certificate + * @param asn1_public_cert The ASN.1 DER encoded X.509 certificate + * @param asn1_length The ASN.1 length + * @param coap_session The CoAP session associated with the certificate update + * @param depth Depth in cert chain. If 0, then client cert, else a CA + * @param validated TLS layer can find no issues if 1 + * @param arg The same as was passed into coap_context_set_pki() + * in setup_data->cn_call_back_arg + * + * @return @c 1 if accepted, else @c 0 if to be rejected. + */ +typedef int (*coap_dtls_cn_callback_t)(const char *cn, + const uint8_t *asn1_public_cert, + size_t asn1_length, + coap_session_t *coap_session, + unsigned int depth, + int validated, + void *arg); + +/** + * The enum used for determining the provided PKI ASN.1 (DER) Private Key + * formats. + */ +typedef enum coap_asn1_privatekey_type_t { + COAP_ASN1_PKEY_NONE, /**< NONE */ + COAP_ASN1_PKEY_RSA, /**< RSA type */ + COAP_ASN1_PKEY_RSA2, /**< RSA2 type */ + COAP_ASN1_PKEY_DSA, /**< DSA type */ + COAP_ASN1_PKEY_DSA1, /**< DSA1 type */ + COAP_ASN1_PKEY_DSA2, /**< DSA2 type */ + COAP_ASN1_PKEY_DSA3, /**< DSA3 type */ + COAP_ASN1_PKEY_DSA4, /**< DSA4 type */ + COAP_ASN1_PKEY_DH, /**< DH type */ + COAP_ASN1_PKEY_DHX, /**< DHX type */ + COAP_ASN1_PKEY_EC, /**< EC type */ + COAP_ASN1_PKEY_HMAC, /**< HMAC type */ + COAP_ASN1_PKEY_CMAC, /**< CMAC type */ + COAP_ASN1_PKEY_TLS1_PRF, /**< TLS1_PRF type */ + COAP_ASN1_PKEY_HKDF /**< HKDF type */ +} coap_asn1_privatekey_type_t; + +/** + * The enum used for determining the PKI key formats. + */ +typedef enum coap_pki_key_t { + COAP_PKI_KEY_PEM = 0, /**< The PKI key type is PEM file */ + COAP_PKI_KEY_ASN1, /**< The PKI key type is ASN.1 (DER) buffer */ + COAP_PKI_KEY_PEM_BUF, /**< The PKI key type is PEM buffer */ + COAP_PKI_KEY_PKCS11, /**< The PKI key type is PKCS11 (DER) */ +} coap_pki_key_t; + +/** + * The structure that holds the PKI PEM definitions. + */ +typedef struct coap_pki_key_pem_t { + const char *ca_file; /**< File location of Common CA in PEM format */ + const char *public_cert; /**< File location of Public Cert */ + const char *private_key; /**< File location of Private Key in PEM format */ +} coap_pki_key_pem_t; + +/** + * The structure that holds the PKI PEM buffer definitions. + * The certificates and private key data must be in PEM format. + * + * Note: The Certs and Key should be NULL terminated strings for + * performance reasons (to save a potential buffer copy) and the length include + * this NULL terminator. It is not a requirement to have the NULL terminator + * though and the length must then reflect the actual data size. + */ +typedef struct coap_pki_key_pem_buf_t { + const uint8_t *ca_cert; /**< PEM buffer Common CA Cert */ + const uint8_t *public_cert; /**< PEM buffer Public Cert, or Public Key if RPK */ + const uint8_t *private_key; /**< PEM buffer Private Key + If RPK and 'EC PRIVATE KEY' this can be used + for both the public_cert and private_key */ + size_t ca_cert_len; /**< PEM buffer CA Cert length */ + size_t public_cert_len; /**< PEM buffer Public Cert length */ + size_t private_key_len; /**< PEM buffer Private Key length */ +} coap_pki_key_pem_buf_t; + +/** + * The structure that holds the PKI ASN.1 (DER) definitions. + */ +typedef struct coap_pki_key_asn1_t { + const uint8_t *ca_cert; /**< ASN1 (DER) Common CA Cert */ + const uint8_t *public_cert; /**< ASN1 (DER) Public Cert, or Public Key if RPK */ + const uint8_t *private_key; /**< ASN1 (DER) Private Key */ + size_t ca_cert_len; /**< ASN1 CA Cert length */ + size_t public_cert_len; /**< ASN1 Public Cert length */ + size_t private_key_len; /**< ASN1 Private Key length */ + coap_asn1_privatekey_type_t private_key_type; /**< Private Key Type */ +} coap_pki_key_asn1_t; + +/** + * The structure that holds the PKI PKCS11 definitions. + */ +typedef struct coap_pki_key_pkcs11_t { + const char *ca; /**< pkcs11: URI for Common CA Certificate */ + const char *public_cert; /**< pkcs11: URI for Public Cert */ + const char *private_key; /**< pkcs11: URI for Private Key */ + const char *user_pin; /**< User pin to access PKCS11. If NULL, then + pin-value= parameter must be set in + pkcs11: URI as a query. */ +} coap_pki_key_pkcs11_t; + +/** + * The structure that holds the PKI key information. + */ +typedef struct coap_dtls_key_t { + coap_pki_key_t key_type; /**< key format type */ + union { + coap_pki_key_pem_t pem; /**< for PEM file keys */ + coap_pki_key_pem_buf_t pem_buf; /**< for PEM memory keys */ + coap_pki_key_asn1_t asn1; /**< for ASN.1 (DER) memory keys */ + coap_pki_key_pkcs11_t pkcs11; /**< for PKCS11 keys */ + } key; +} coap_dtls_key_t; + +/** + * Server Name Indication (SNI) Validation callback that can be set up by + * coap_context_set_pki(). + * Invoked if the SNI is not previously seen and prior to sending a certificate + * set back to the client so that the appropriate certificate set can be used + * based on the requesting SNI. + * + * @param sni The requested SNI + * @param arg The same as was passed into coap_context_set_pki() + * in setup_data->sni_call_back_arg + * + * @return New set of certificates to use, or @c NULL if SNI is to be rejected. + */ +typedef coap_dtls_key_t *(*coap_dtls_pki_sni_callback_t)(const char *sni, + void* arg); + + +#define COAP_DTLS_PKI_SETUP_VERSION 1 /**< Latest PKI setup version */ + +/** + * The structure used for defining the PKI setup data to be used. + */ +struct coap_dtls_pki_t { + uint8_t version; /** Set to COAP_DTLS_PKI_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t verify_peer_cert; /**< 1 if peer cert is to be verified */ + uint8_t check_common_ca; /**< 1 if peer cert is to be signed by + * the same CA as the local cert */ + uint8_t allow_self_signed; /**< 1 if self-signed certs are allowed. + * Ignored if check_common_ca set */ + uint8_t allow_expired_certs; /**< 1 if expired certs are allowed */ + uint8_t cert_chain_validation; /**< 1 if to check cert_chain_verify_depth */ + uint8_t cert_chain_verify_depth; /**< recommended depth is 3 */ + uint8_t check_cert_revocation; /**< 1 if revocation checks wanted */ + uint8_t allow_no_crl; /**< 1 ignore if CRL not there */ + uint8_t allow_expired_crl; /**< 1 if expired crl is allowed */ + uint8_t allow_bad_md_hash; /**< 1 if unsupported MD hashes are allowed */ + uint8_t allow_short_rsa_length; /**< 1 if small RSA keysizes are allowed */ + uint8_t is_rpk_not_cert; /**< 1 is RPK instead of Public Certificate. + * If set, PKI key format type cannot be + * COAP_PKI_KEY_PEM */ + uint8_t reserved[3]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 3 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_PKI_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** CN check callback function. + * If not NULL, is called when the TLS connection has passed the configured + * TLS options above for the application to verify if the CN is valid. + */ + coap_dtls_cn_callback_t validate_cn_call_back; + void *cn_call_back_arg; /**< Passed in to the CN callback function */ + + /** SNI check callback function. + * If not @p NULL, called if the SNI is not previously seen and prior to + * sending a certificate set back to the client so that the appropriate + * certificate set can be used based on the requesting SNI. + */ + coap_dtls_pki_sni_callback_t validate_sni_call_back; + void *sni_call_back_arg; /**< Passed in to the sni callback function */ + + /** Additional Security callback handler that is invoked when libcoap has + * done the standard, defined validation checks at the TLS level, + * If not @p NULL, called from within the TLS Client Hello connection + * setup. + */ + coap_dtls_security_setup_t additional_tls_setup_call_back; + + char* client_sni; /**< If not NULL, SNI to use in client TLS setup. + Owned by the client app and must remain valid + during the call to coap_new_client_session_pki() */ + + coap_dtls_key_t pki_key; /**< PKI key definition */ +}; + +/** + * The structure that holds the Client PSK information. + */ +typedef struct coap_dtls_cpsk_info_t { + coap_bin_const_t identity; + coap_bin_const_t key; +} coap_dtls_cpsk_info_t; + +/** + * Identity Hint Validation callback that can be set up by + * coap_new_client_session_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the Identity Hint is allowed, + * and thus needs to use the appropriate PSK information for the Identity + * Hint for the (D)TLS session. + * Note: Identity Hint is not supported in (D)TLS1.3. + * + * @param hint The server provided Identity Hint + * @param coap_session The CoAP session associated with the Identity Hint + * @param arg The same as was passed into coap_new_client_session_psk2() + * in setup_data->ih_call_back_arg + * + * @return New coap_dtls_cpsk_info_t object or @c NULL on error. + */ +typedef const coap_dtls_cpsk_info_t *(*coap_dtls_ih_callback_t)( + coap_str_const_t *hint, + coap_session_t *coap_session, + void *arg); + +#define COAP_DTLS_CPSK_SETUP_VERSION 1 /**< Latest CPSK setup version */ + +/** + * The structure used for defining the Client PSK setup data to be used. + */ +typedef struct coap_dtls_cpsk_t { + uint8_t version; /** Set to COAP_DTLS_CPSK_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t reserved[7]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 7 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_CPSK_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** Identity Hint check callback function. + * If not NULL, is called when the Identity Hint (TLS1.2 or earlier) is + * provided by the server. + * The appropriate Identity and Pre-shared Key to use can then be returned. + */ + coap_dtls_ih_callback_t validate_ih_call_back; + void *ih_call_back_arg; /**< Passed in to the Identity Hint callback + function */ + + char* client_sni; /**< If not NULL, SNI to use in client TLS setup. + Owned by the client app and must remain valid + during the call to coap_new_client_session_psk2() + Note: Not supported by TinyDTLS. */ + + coap_dtls_cpsk_info_t psk_info; /**< Client PSK definition */ +} coap_dtls_cpsk_t; + +/** + * The structure that holds the Server Pre-Shared Key and Identity + * Hint information. + */ +typedef struct coap_dtls_spsk_info_t { + coap_bin_const_t hint; + coap_bin_const_t key; +} coap_dtls_spsk_info_t; + + +/** + * Identity Validation callback that can be set up by + * coap_context_set_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the Identity is allowed, + * and needs to use the appropriate Pre-Shared Key for the (D)TLS session. + * + * @param identity The client provided Identity + * @param coap_session The CoAP session associated with the Identity Hint + * @param arg The value as passed into coap_context_set_psk2() + * in setup_data->id_call_back_arg + * + * @return New coap_bin_const_t object containing the Pre-Shared Key or + @c NULL on error. + * Note: This information will be duplicated into an internal + * structure. + */ +typedef const coap_bin_const_t *(*coap_dtls_id_callback_t)( + coap_bin_const_t *identity, + coap_session_t *coap_session, + void *arg); +/** + * PSK SNI callback that can be set up by coap_context_set_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level + * and the application needs to:- + * a) check that the SNI is allowed + * b) provide the appropriate PSK information for the (D)TLS session. + * + * @param sni The client provided SNI + * @param coap_session The CoAP session associated with the SNI + * @param arg The same as was passed into coap_context_set_psk2() + * in setup_data->sni_call_back_arg + * + * @return New coap_dtls_spsk_info_t object or @c NULL on error. + */ +typedef const coap_dtls_spsk_info_t *(*coap_dtls_psk_sni_callback_t)( + const char *sni, + coap_session_t *coap_session, + void *arg); + +#define COAP_DTLS_SPSK_SETUP_VERSION 1 /**< Latest SPSK setup version */ + +/** + * The structure used for defining the Server PSK setup data to be used. + */ +typedef struct coap_dtls_spsk_t { + uint8_t version; /** Set to COAP_DTLS_SPSK_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t reserved[7]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 7 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_SPSK_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** Identity check callback function. + * If not @p NULL, is called when the Identity is provided by the client. + * The appropriate Pre-Shared Key to use can then be returned. + */ + coap_dtls_id_callback_t validate_id_call_back; + void *id_call_back_arg; /**< Passed in to the Identity callback function */ + + /** SNI check callback function. + * If not @p NULL, called if the SNI is not previously seen and prior to + * sending PSK information back to the client so that the appropriate + * PSK information can be used based on the requesting SNI. + */ + coap_dtls_psk_sni_callback_t validate_sni_call_back; + void *sni_call_back_arg; /**< Passed in to the SNI callback function */ + + coap_dtls_spsk_info_t psk_info; /**< Server PSK definition */ +} coap_dtls_spsk_t; + + +/** @} */ + +/** + * @ingroup logging + * Sets the (D)TLS logging level to the specified @p level. + * Note: coap_log_level() will influence output if at a specified level. + * + * @param level The logging level to use - LOG_* + */ +void coap_dtls_set_log_level(int level); + +/** + * @ingroup logging + * Get the current (D)TLS logging. + * + * @return The current log level (one of LOG_*). + */ +int coap_dtls_get_log_level(void); + + +#endif /* COAP_DTLS_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls_internal.h new file mode 100644 index 00000000000..8ea09a4eb3e --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_dtls_internal.h @@ -0,0 +1,345 @@ +/* + * coap_dtls_internal.h -- (Datagram) Transport Layer Support for libcoap + * + * Copyright (C) 2016 Olaf Bergmann + * Copyright (C) 2017 Jean-Claude Michelou + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DTLS_INTERNAL_H_ +#define COAP_DTLS_INTERNAL_H_ + +/** + * @defgroup dtls_internal DTLS Support (Internal) + * CoAP DTLS Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/* https://tools.ietf.org/html/rfc6347#section-4.2.4.1 */ +#ifndef COAP_DTLS_RETRANSMIT_MS +#define COAP_DTLS_RETRANSMIT_MS 1000 +#endif +#ifndef COAP_DTLS_RETRANSMIT_TOTAL_MS +#define COAP_DTLS_RETRANSMIT_TOTAL_MS 60000 +#endif + +#define COAP_DTLS_RETRANSMIT_COAP_TICKS (COAP_DTLS_RETRANSMIT_MS * COAP_TICKS_PER_SECOND / 1000) + +/** + * Creates a new DTLS context for the given @p coap_context. This function + * returns a pointer to a new DTLS context object or @c NULL on error. + * + * @param coap_context The CoAP context where the DTLS object shall be used. + * + * @return A DTLS context object or @c NULL on error. + */ +void * +coap_dtls_new_context(coap_context_t *coap_context); + +/** + * Set the DTLS context's default server PSK information. + * This does the PSK specifics following coap_dtls_new_context(). + * + * @param coap_context The CoAP context. + * @param setup_data A structure containing setup data originally passed into + * coap_context_set_psk2(). + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_spsk(coap_context_t *coap_context, + coap_dtls_spsk_t *setup_data); + +/** + * Set the DTLS context's default client PSK information. + * This does the PSK specifics following coap_dtls_new_context(). + * + * @param coap_context The CoAP context. + * @param setup_data A structure containing setup data originally passed into + * coap_new_client_session_psk2(). + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_cpsk(coap_context_t *coap_context, + coap_dtls_cpsk_t *setup_data); + +/** + * Set the DTLS context's default server PKI information. + * This does the PKI specifics following coap_dtls_new_context(). + * If @p COAP_DTLS_ROLE_SERVER, then the information will get put into the + * TLS library's context (from which sessions are derived). + * If @p COAP_DTLS_ROLE_CLIENT, then the information will get put into the + * TLS library's session. + * + * @param coap_context The CoAP context. + * @param setup_data Setup information defining how PKI is to be setup. + * Required parameter. If @p NULL, PKI will not be + * set up. + * @param role One of @p COAP_DTLS_ROLE_CLIENT or @p COAP_DTLS_ROLE_SERVER + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_pki(coap_context_t *coap_context, + const coap_dtls_pki_t *setup_data, + const coap_dtls_role_t role); + +/** + * Set the dtls context's default Root CA information for a client or server. + * + * @param coap_context The current coap_context_t object. + * @param ca_file If not @p NULL, is the full path name of a PEM encoded + * file containing all the Root CAs to be used. + * @param ca_dir If not @p NULL, points to a directory containing PEM + * encoded files containing all the Root CAs to be used. + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_pki_root_cas(coap_context_t *coap_context, + const char *ca_file, + const char *ca_dir); + +/** + * Check whether one of the coap_dtls_context_set_{psk|pki}() functions have + * been called. + * + * @param coap_context The current coap_context_t object. + * + * @return @c 1 if coap_dtls_context_set_{psk|pki}() called, else @c 0. + */ + +int coap_dtls_context_check_keys_enabled(coap_context_t *coap_context); + +/** + * Releases the storage allocated for @p dtls_context. + * + * @param dtls_context The DTLS context as returned by coap_dtls_new_context(). + */ +void coap_dtls_free_context(void *dtls_context); + +/** + * Create a new client-side session. This should send a HELLO to the server. + * + * @param coap_session The CoAP session. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. +*/ +void *coap_dtls_new_client_session(coap_session_t *coap_session); + +/** + * Create a new DTLS server-side session. + * Called after coap_dtls_hello() has returned @c 1, signalling that a validated + * HELLO was received from a client. + * This should send a HELLO to the server. + * + * @param coap_session The CoAP session. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the DTLS session. + */ +void *coap_dtls_new_server_session(coap_session_t *coap_session); + +/** + * Terminates the DTLS session (may send an ALERT if necessary) then frees the + * underlying TLS library object containing security parameters for the session. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_free_session(coap_session_t *coap_session); + +/** + * Notify of a change in the CoAP session's MTU, for example after + * a PMTU update. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_session_update_mtu(coap_session_t *coap_session); + +/** + * Send data to a DTLS peer. + * + * @param coap_session The CoAP session. + * @param data pointer to data. + * @param data_len Number of bytes to send. + * + * @return @c 0 if this would be blocking, @c -1 if there is an error or the + * number of cleartext bytes sent. + */ +int coap_dtls_send(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Check if timeout is handled per CoAP session or per CoAP context. + * + * @return @c 1 of timeout and retransmit is per context, @c 0 if it is + * per session. + */ +int coap_dtls_is_context_timeout(void); + +/** + * Do all pending retransmits and get next timeout + * + * @param dtls_context The DTLS context. + * + * @return @c 0 if no event is pending or date of the next retransmit. + */ +coap_tick_t coap_dtls_get_context_timeout(void *dtls_context); + +/** + * Get next timeout for this session. + * + * @param coap_session The CoAP session. + * @param now The current time in ticks. + * + * @return @c 0 If no event is pending or ticks time of the next retransmit. + */ +coap_tick_t coap_dtls_get_timeout(coap_session_t *coap_session, + coap_tick_t now); + +/** + * Handle a DTLS timeout expiration. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_handle_timeout(coap_session_t *coap_session); + +/** + * Handling incoming data from a DTLS peer. + * + * @param coap_session The CoAP session. + * @param data Encrypted datagram. + * @param data_len Encrypted datagram size. + * + * @return Result of coap_handle_dgram on the decrypted CoAP PDU + * or @c -1 for error. + */ +int coap_dtls_receive(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Handling client HELLO messages from a new candiate peer. + * Note that session->tls is empty. + * + * @param coap_session The CoAP session. + * @param data Encrypted datagram. + * @param data_len Encrypted datagram size. + * + * @return @c 0 if a cookie verification message has been sent, @c 1 if the + * HELLO contains a valid cookie and a server session should be created, + * @c -1 if the message is invalid. + */ +int coap_dtls_hello(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Get DTLS overhead over cleartext PDUs. + * + * @param coap_session The CoAP session. + * + * @return Maximum number of bytes added by DTLS layer. + */ +unsigned int coap_dtls_get_overhead(coap_session_t *coap_session); + +/** + * Create a new TLS client-side session. + * + * @param coap_session The CoAP session. + * @param connected Updated with whether the connection is connected yet or not. + * @c 0 is not connected, @c 1 is connected. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. +*/ +void *coap_tls_new_client_session(coap_session_t *coap_session, int *connected); + +/** + * Create a TLS new server-side session. + * + * @param coap_session The CoAP session. + * @param connected Updated with whether the connection is connected yet or not. + * @c 0 is not connected, @c 1 is connected. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. + */ +void *coap_tls_new_server_session(coap_session_t *coap_session, int *connected); + +/** + * Terminates the TLS session (may send an ALERT if necessary) then frees the + * underlying TLS library object containing security parameters for the session. + * + * @param coap_session The CoAP session. + */ +void coap_tls_free_session( coap_session_t *coap_session ); + +/** + * Send data to a TLS peer, with implicit flush. + * + * @param coap_session The CoAP session. + * @param data Pointer to data. + * @param data_len Number of bytes to send. + * + * @return @c 0 if this should be retried, @c -1 if there is an error + * or the number of cleartext bytes sent. + */ +ssize_t coap_tls_write(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len + ); + +/** + * Read some data from a TLS peer. + * + * @param coap_session The CoAP session. + * @param data Pointer to data. + * @param data_len Maximum number of bytes to read. + * + * @return @c 0 if this should be retried, @c -1 if there is an error + * or the number of cleartext bytes read. + */ +ssize_t coap_tls_read(coap_session_t *coap_session, + uint8_t *data, + size_t data_len + ); + +/** + * Initialize the underlying (D)TLS Library layer. + * + */ +void coap_dtls_startup(void); + +/** + * Close down the underlying (D)TLS Library layer. + * + */ +void coap_dtls_shutdown(void); + +/** + * Get the actual (D)TLS object for the session. + * + * @param session The session. + * @param tls_lib Updated with the library type. + * + * @return The TLS information. + */ +void *coap_dtls_get_tls(const coap_session_t *session, + coap_tls_library_t *tls_lib); + +/** @} */ + +#endif /* COAP_DTLS_INTERNAL_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_event.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_event.h new file mode 100644 index 00000000000..89b2a63967c --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_event.h @@ -0,0 +1,104 @@ +/* + * coap_event.h -- libcoap Event API + * + * Copyright (C) 2016 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_EVENT_H_ +#define COAP_EVENT_H_ + +#include "libcoap.h" + +/** + * @defgroup events Event API + * API functions for event delivery from lower-layer library functions. + * @{ + */ + +/** + * Scalar type to represent different events, e.g. DTLS events or + * retransmission timeouts. + */ + typedef unsigned int coap_event_t; + +/** + * (D)TLS events for COAP_PROTO_DTLS and COAP_PROTO_TLS + */ +#define COAP_EVENT_DTLS_CLOSED 0x0000 +#define COAP_EVENT_DTLS_CONNECTED 0x01DE +#define COAP_EVENT_DTLS_RENEGOTIATE 0x01DF +#define COAP_EVENT_DTLS_ERROR 0x0200 + +/** + * TCP events for COAP_PROTO_TCP and COAP_PROTO_TLS + */ +#define COAP_EVENT_TCP_CONNECTED 0x1001 +#define COAP_EVENT_TCP_CLOSED 0x1002 +#define COAP_EVENT_TCP_FAILED 0x1003 + +/** + * CSM exchange events for reliable protocols only + */ +#define COAP_EVENT_SESSION_CONNECTED 0x2001 +#define COAP_EVENT_SESSION_CLOSED 0x2002 +#define COAP_EVENT_SESSION_FAILED 0x2003 + +/** + * BLOCK2 receive errors + */ +#define COAP_EVENT_PARTIAL_BLOCK 0x3001 + +/** + * Type for event handler functions that can be registered with a CoAP + * context using the unction coap_set_event_handler(). When called by + * the library, the first argument will be the current coap_session_t object + * which is associated with the original CoAP context. The second parameter + * is the event type. + */ +typedef int (*coap_event_handler_t)(coap_session_t *session, + const coap_event_t event); + +/** + * Registers the function @p hnd as callback for events from the given + * CoAP context @p context. Any event handler that has previously been + * registered with @p context will be overwritten by this operation. + * + * @param context The CoAP context to register the event handler with. + * @param hnd The event handler to be registered. @c NULL if to be + * de-registered. + */ +void coap_register_event_handler(coap_context_t *context, + coap_event_handler_t hnd); + +/** @} */ + +/** + * Registers the function @p hnd as callback for events from the given + * CoAP context @p context. Any event handler that has previously been + * registered with @p context will be overwritten by this operation. + * + * @deprecated Use coap_register_event_handler() instead. + * + * @param context The CoAP context to register the event handler with. + * @param hnd The event handler to be registered. + */ +COAP_DEPRECATED +void coap_set_event_handler(coap_context_t *context, + coap_event_handler_t hnd); + +/** + * Clears the event handler registered with @p context. + * + * @deprecated Use coap_register_event_handler() instead with NULL for hnd. + * + * @param context The CoAP context whose event handler is to be removed. + */ +COAP_DEPRECATED +void coap_clear_event_handler(coap_context_t *context); + +#endif /* COAP_EVENT_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_forward_decls.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_forward_decls.h new file mode 100644 index 00000000000..3bedbf7899a --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_forward_decls.h @@ -0,0 +1,107 @@ +/* + * coap_forward_decls.h -- Forward declarations of structures that are + * opaque to application programming that use libcoap. + * + * Copyright (C) 2019-2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_forward_decls.h + * @brief COAP forward definitions + */ + +#ifndef COAP_FORWARD_DECLS_H_ +#define COAP_FORWARD_DECLS_H_ + +/* + * Define the forward declations for the structures (even non-opaque) + * so that applications (using coap.h) as well as libcoap builds + * can reference them (and makes .h file dependencies a lot simpler). + */ +struct coap_address_t; +struct coap_bin_const_t; +struct coap_dtls_pki_t; +struct coap_str_const_t; +struct coap_string_t; + +/* + * typedef all the opaque structures that are defined in coap_*_internal.h + */ + +/* ************* coap_async_internal.h ***************** */ + +/** + * Async Entry information. + */ +typedef struct coap_async_t coap_async_t; + +/* ************* coap_block_internal.h ***************** */ + +/* + * Block handling information. + */ +typedef struct coap_lg_xmit_t coap_lg_xmit_t; +typedef struct coap_lg_crcv_t coap_lg_crcv_t; +typedef struct coap_lg_srcv_t coap_lg_srcv_t; + +/* ************* coap_cache_internal.h ***************** */ + +/* + * Cache Entry information. + */ +typedef struct coap_cache_entry_t coap_cache_entry_t; +typedef struct coap_cache_key_t coap_cache_key_t; + +/* ************* coap_io_internal.h ***************** */ + +/** + * coap_socket_t and coap_packet_t information. + */ +typedef struct coap_packet_t coap_packet_t; +typedef struct coap_socket_t coap_socket_t; + +/* ************* coap_net_internal.h ***************** */ + +/* + * Net information. + */ +typedef struct coap_context_t coap_context_t; +typedef struct coap_queue_t coap_queue_t; + +/* ************* coap_pdu_internal.h ***************** */ + +/** + * PDU information. + */ +typedef struct coap_pdu_t coap_pdu_t; + +/* ************* coap_resource_internal.h ***************** */ + +/* + * Resource information. + */ +typedef struct coap_attr_t coap_attr_t; +typedef struct coap_resource_t coap_resource_t; + +/* ************* coap_session_internal.h ***************** */ + +/* + * Session information. + */ +typedef struct coap_addr_hash_t coap_addr_hash_t; +typedef struct coap_endpoint_t coap_endpoint_t; +typedef struct coap_session_t coap_session_t; + +/* ************* coap_subscribe_internal.h ***************** */ + +/* + * Observe subscriber information. + */ +typedef struct coap_subscription_t coap_subscription_t; + +#endif /* COAP_FORWARD_DECLS_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_hashkey.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_hashkey.h new file mode 100644 index 00000000000..11a797bde7a --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_hashkey.h @@ -0,0 +1,61 @@ +/* + * coap_hashkey.h -- definition of hash key type and helper functions + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_hashkey.h + * @brief definition of hash key type and helper functions + */ + +#ifndef COAP_HASHKEY_H_ +#define COAP_HASHKEY_H_ + +#include "libcoap.h" +#include "uthash.h" +#include "str.h" + +typedef unsigned char coap_key_t[4]; + +#ifndef coap_hash +/** + * Calculates a fast hash over the given string @p s of length @p len and stores + * the result into @p h. Depending on the exact implementation, this function + * cannot be used as one-way function to check message integrity or simlar. + * + * @param s The string used for hash calculation. + * @param len The length of @p s. + * @param h The result buffer to store the calculated hash key. + */ +void coap_hash_impl(const unsigned char *s, size_t len, coap_key_t h); + +#define coap_hash(String,Length,Result) \ + coap_hash_impl((String),(Length),(Result)) + +/* This is used to control the pre-set hash-keys for resources. */ +#define COAP_DEFAULT_HASH +#else +#undef COAP_DEFAULT_HASH +#endif /* coap_hash */ + +/** + * Calls coap_hash() with given @c coap_string_t object as parameter. + * + * @param Str Must contain a pointer to a coap string object. + * @param H A coap_key_t object to store the result. + * + * @hideinitializer + */ +#define coap_str_hash(Str,H) { \ + assert(Str); \ + memset((H), 0, sizeof(coap_key_t)); \ + coap_hash((Str)->s, (Str)->length, (H)); \ + } + +#endif /* COAP_HASHKEY_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_internal.h new file mode 100644 index 00000000000..5eee5c12867 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_internal.h @@ -0,0 +1,65 @@ +/* + * coap_internal.h -- Structures, Enums & Functions that are not exposed to + * application programming + * + * Copyright (C) 2019-2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/* + * All libcoap library files should include this file which then pulls in all + * of the other appropriate header files. + * + * Note: This file should never be included in application code (with the + * possible exception of internal test suites). + */ + +/** + * @file coap_internal.h + * @brief Pulls together all the internal only header files + */ + +#ifndef COAP_INTERNAL_H_ +#define COAP_INTERNAL_H_ + +#include "coap_config.h" + +/* + * Correctly set up assert() based on NDEBUG for libcoap + */ +#if defined(HAVE_ASSERT_H) && !defined(assert) +# include +#endif + +#include "coap3/coap.h" + +/* + * Include all the header files that are for internal use only. + */ + +/* Not defined in coap.h - internal usage .h files */ +#include "utlist.h" +#include "uthash.h" +#include "coap_hashkey.h" +#include "coap_mutex.h" + +/* Specifically defined internal .h files */ +#include "coap_asn1_internal.h" +#include "coap_async_internal.h" +#include "coap_block_internal.h" +#include "coap_cache_internal.h" +#include "coap_dtls_internal.h" +#include "coap_io_internal.h" +#include "coap_net_internal.h" +#include "coap_pdu_internal.h" +#include "coap_session_internal.h" +#include "coap_resource_internal.h" +#include "coap_session_internal.h" +#include "coap_subscribe_internal.h" +#include "coap_tcp_internal.h" + +#endif /* COAP_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io.h new file mode 100644 index 00000000000..b27921f8be1 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io.h @@ -0,0 +1,72 @@ +/* + * coap_io.h -- Default network I/O functions for libcoap + * + * Copyright (C) 2012-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_IO_H_ +#define COAP_IO_H_ + +#include + +#include "address.h" + +#ifdef RIOT_VERSION +#include "net/gnrc.h" +#endif /* RIOT_VERSION */ + +#ifndef COAP_RXBUFFER_SIZE +#define COAP_RXBUFFER_SIZE 1472 +#endif /* COAP_RXBUFFER_SIZE */ + +/* + * It may may make sense to define this larger on busy systems + * (lots of sessions, large number of which are active), by using + * -DCOAP_MAX_EPOLL_EVENTS=nn at compile time. + */ +#ifndef COAP_MAX_EPOLL_EVENTS +#define COAP_MAX_EPOLL_EVENTS 10 +#endif /* COAP_MAX_EPOLL_EVENTS */ + +#ifdef _WIN32 +typedef SOCKET coap_fd_t; +#define coap_closesocket closesocket +#define COAP_SOCKET_ERROR SOCKET_ERROR +#define COAP_INVALID_SOCKET INVALID_SOCKET +#else +typedef int coap_fd_t; +#define coap_closesocket close +#define COAP_SOCKET_ERROR (-1) +#define COAP_INVALID_SOCKET (-1) +#endif + +typedef uint16_t coap_socket_flags_t; + +typedef struct coap_addr_tuple_t { + coap_address_t remote; /**< remote address and port */ + coap_address_t local; /**< local address and port */ +} coap_addr_tuple_t; + +const char *coap_socket_strerror( void ); + +/** + * Check whether TCP is available. + * + * @return @c 1 if support for TCP is enabled, or @c 0 otherwise. + */ +int coap_tcp_is_supported(void); + +typedef enum { + COAP_NACK_TOO_MANY_RETRIES, + COAP_NACK_NOT_DELIVERABLE, + COAP_NACK_RST, + COAP_NACK_TLS_FAILED, + COAP_NACK_ICMP_ISSUE +} coap_nack_reason_t; + +#endif /* COAP_IO_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io_internal.h new file mode 100644 index 00000000000..241ef7f9955 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_io_internal.h @@ -0,0 +1,168 @@ +/* + * coap_io.h -- Default network I/O functions for libcoap + * + * Copyright (C) 2012-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_IO_INTERNAL_H_ +#define COAP_IO_INTERNAL_H_ + +#include + +#include "address.h" + +#ifdef RIOT_VERSION +#include "net/gnrc.h" +#endif /* RIOT_VERSION */ + +struct coap_socket_t { +#if defined(WITH_LWIP) + struct udp_pcb *pcb; +#elif defined(WITH_CONTIKI) + void *conn; +#else + coap_fd_t fd; +#endif /* WITH_LWIP */ +#if defined(RIOT_VERSION) + gnrc_pktsnip_t *pkt; /* pointer to received packet for processing */ +#endif /* RIOT_VERSION */ + coap_socket_flags_t flags; + coap_session_t *session; /* Used by the epoll logic for an active session. */ + coap_endpoint_t *endpoint; /* Used by the epoll logic for a listening + endpoint. */ +}; + +/** + * coap_socket_flags_t values + */ +#define COAP_SOCKET_EMPTY 0x0000 /**< the socket is not used */ +#define COAP_SOCKET_NOT_EMPTY 0x0001 /**< the socket is not empty */ +#define COAP_SOCKET_BOUND 0x0002 /**< the socket is bound */ +#define COAP_SOCKET_CONNECTED 0x0004 /**< the socket is connected */ +#define COAP_SOCKET_WANT_READ 0x0010 /**< non blocking socket is waiting for reading */ +#define COAP_SOCKET_WANT_WRITE 0x0020 /**< non blocking socket is waiting for writing */ +#define COAP_SOCKET_WANT_ACCEPT 0x0040 /**< non blocking server socket is waiting for accept */ +#define COAP_SOCKET_WANT_CONNECT 0x0080 /**< non blocking client socket is waiting for connect */ +#define COAP_SOCKET_CAN_READ 0x0100 /**< non blocking socket can now read without blocking */ +#define COAP_SOCKET_CAN_WRITE 0x0200 /**< non blocking socket can now write without blocking */ +#define COAP_SOCKET_CAN_ACCEPT 0x0400 /**< non blocking server socket can now accept without blocking */ +#define COAP_SOCKET_CAN_CONNECT 0x0800 /**< non blocking client socket can now connect without blocking */ +#define COAP_SOCKET_MULTICAST 0x1000 /**< socket is used for multicast communication */ + +coap_endpoint_t *coap_malloc_endpoint( void ); +void coap_mfree_endpoint( coap_endpoint_t *ep ); + +const char *coap_socket_format_errno(int error); + +int +coap_socket_connect_udp(coap_socket_t *sock, + const coap_address_t *local_if, + const coap_address_t *server, + int default_port, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +int +coap_socket_bind_udp(coap_socket_t *sock, + const coap_address_t *listen_addr, + coap_address_t *bound_addr ); + +void coap_socket_close(coap_socket_t *sock); + +ssize_t +coap_socket_send( coap_socket_t *sock, coap_session_t *session, + const uint8_t *data, size_t data_len ); + +ssize_t +coap_socket_write(coap_socket_t *sock, const uint8_t *data, size_t data_len); + +ssize_t +coap_socket_read(coap_socket_t *sock, uint8_t *data, size_t data_len); + +void +coap_epoll_ctl_mod(coap_socket_t *sock, uint32_t events, const char *func); + +#ifdef WITH_LWIP +ssize_t +coap_socket_send_pdu( coap_socket_t *sock, coap_session_t *session, + coap_pdu_t *pdu ); +#endif + +/** + * Function interface for data transmission. This function returns the number of + * bytes that have been transmitted, or a value less than zero on error. + * + * @param sock Socket to send data with + * @param session Addressing information for unconnected sockets, or NULL + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_network_send( coap_socket_t *sock, const coap_session_t *session, const uint8_t *data, size_t datalen ); + +/** + * Function interface for reading data. This function returns the number of + * bytes that have been read, or a value less than zero on error. In case of an + * error, @p *packet is set to NULL. + * + * @param sock Socket to read data from + * @param packet Received packet metadata and payload. src and dst should be preset. + * + * @return The number of bytes received on success, or a value less than + * zero on error. + */ +ssize_t coap_network_read( coap_socket_t *sock, coap_packet_t *packet ); + +#ifndef coap_mcast_interface +# define coap_mcast_interface(Local) 0 +#endif + +/** + * Given a packet, set msg and msg_len to an address and length of the packet's + * data in memory. + * */ +void coap_packet_get_memmapped(coap_packet_t *packet, + unsigned char **address, + size_t *length); + +#ifdef WITH_LWIP +/** + * Get the pbuf of a packet. The caller takes over responsibility for freeing + * the pbuf. + */ +struct pbuf *coap_packet_extract_pbuf(coap_packet_t *packet); +#endif + +#if defined(WITH_LWIP) +/* + * This is only included in coap_io.h instead of .c in order to be available for + * sizeof in lwippools.h. + * Simple carry-over of the incoming pbuf that is later turned into a node. + * + * Source address data is currently side-banded via ip_current_dest_addr & co + * as the packets have limited lifetime anyway. + */ +struct coap_packet_t { + struct pbuf *pbuf; + const coap_endpoint_t *local_interface; + coap_addr_tuple_t addr_info; /**< local and remote addresses */ + int ifindex; /**< the interface index */ +// uint16_t srcport; +}; +#else +struct coap_packet_t { + coap_addr_tuple_t addr_info; /**< local and remote addresses */ + int ifindex; /**< the interface index */ + size_t length; /**< length of payload */ + unsigned char payload[COAP_RXBUFFER_SIZE]; /**< payload */ +}; +#endif + +#endif /* COAP_IO_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_mutex.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_mutex.h new file mode 100644 index 00000000000..44084fecb1c --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_mutex.h @@ -0,0 +1,59 @@ +/* + * coap_mutex.h -- mutex utilities + * + * Copyright (C) 2019 Jon Shallow + * 2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_mutex.h + * @brief COAP mutex mechanism wrapper + */ + +#ifndef COAP_MUTEX_H_ +#define COAP_MUTEX_H_ + +/* + * Mutexes are currently only used if there is a constrained stack, + * and large static variables (instead of the large variable being on + * the stack) need to be protected. + */ +#if COAP_CONSTRAINED_STACK + +#if defined(HAVE_PTHREAD_H) && defined(HAVE_PTHREAD_MUTEX_LOCK) +#include + +typedef pthread_mutex_t coap_mutex_t; +#define COAP_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER +#define coap_mutex_lock(a) pthread_mutex_lock(a) +#define coap_mutex_trylock(a) pthread_mutex_trylock(a) +#define coap_mutex_unlock(a) pthread_mutex_unlock(a) + +#elif defined(RIOT_VERSION) +/* use RIOT's mutex API */ +#include + +typedef mutex_t coap_mutex_t; +#define COAP_MUTEX_INITIALIZER MUTEX_INIT +#define coap_mutex_lock(a) mutex_lock(a) +#define coap_mutex_trylock(a) mutex_trylock(a) +#define coap_mutex_unlock(a) mutex_unlock(a) + +#else +/* define stub mutex functions */ +typedef int coap_mutex_t; +#define COAP_MUTEX_INITIALIZER 0 +#define coap_mutex_lock(a) *(a) = 1 +#define coap_mutex_trylock(a) *(a) = 1 +#define coap_mutex_unlock(a) *(a) = 0 + +#endif /* !RIOT_VERSION && !HAVE_PTHREAD_H && !HAVE_PTHREAD_MUTEX_LOCK */ + +#endif /* COAP_CONSTRAINED_STACK */ + +#endif /* COAP_MUTEX_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_net_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_net_internal.h new file mode 100644 index 00000000000..bf243f3d022 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_net_internal.h @@ -0,0 +1,366 @@ +/* + * coap_context_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_net_internal.h + * @brief COAP net internal information + */ + +#ifndef COAP_NET_INTERNAL_H_ +#define COAP_NET_INTERNAL_H_ + +/** + * @defgroup context_internal Context Handling (Internal) + * CoAP Context Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/** + * Queue entry + */ +struct coap_queue_t { + struct coap_queue_t *next; + coap_tick_t t; /**< when to send PDU for the next time */ + unsigned char retransmit_cnt; /**< retransmission counter, will be removed + * when zero */ + unsigned int timeout; /**< the randomized timeout value */ + coap_session_t *session; /**< the CoAP session */ + coap_mid_t id; /**< CoAP message id */ + coap_pdu_t *pdu; /**< the CoAP PDU to send */ +}; + +/** + * The CoAP stack's global state is stored in a coap_context_t object. + */ +struct coap_context_t { + coap_opt_filter_t known_options; + coap_resource_t *resources; /**< hash table or list of known + resources */ + coap_resource_t *unknown_resource; /**< can be used for handling + unknown resources */ + coap_resource_t *proxy_uri_resource; /**< can be used for handling + proxy URI resources */ + coap_resource_release_userdata_handler_t release_userdata; + /**< function to release user_data + when resource is deleted */ + +#ifndef WITHOUT_ASYNC + /** + * list of asynchronous message ids */ + coap_async_t *async_state; +#endif /* WITHOUT_ASYNC */ + + /** + * The time stamp in the first element of the sendqeue is relative + * to sendqueue_basetime. */ + coap_tick_t sendqueue_basetime; + coap_queue_t *sendqueue; + coap_endpoint_t *endpoint; /**< the endpoints used for listening */ + coap_session_t *sessions; /**< client sessions */ + +#ifdef WITH_CONTIKI + struct uip_udp_conn *conn; /**< uIP connection object */ + struct etimer retransmit_timer; /**< fires when the next packet must be + sent */ + struct etimer notify_timer; /**< used to check resources periodically */ +#endif /* WITH_CONTIKI */ + +#ifdef WITH_LWIP + uint8_t timer_configured; /**< Set to 1 when a retransmission is + * scheduled using lwIP timers for this + * context, otherwise 0. */ +#endif /* WITH_LWIP */ + + coap_response_handler_t response_handler; + coap_nack_handler_t nack_handler; + coap_ping_handler_t ping_handler; + coap_pong_handler_t pong_handler; + + /** + * Callback function that is used to signal events to the + * application. This field is set by coap_set_event_handler(). + */ + coap_event_handler_t handle_event; + + ssize_t (*network_send)(coap_socket_t *sock, const coap_session_t *session, + const uint8_t *data, size_t datalen); + + ssize_t (*network_read)(coap_socket_t *sock, coap_packet_t *packet); + + size_t(*get_client_psk)(const coap_session_t *session, const uint8_t *hint, + size_t hint_len, uint8_t *identity, + size_t *identity_len, size_t max_identity_len, + uint8_t *psk, size_t max_psk_len); + size_t(*get_server_psk)(const coap_session_t *session, + const uint8_t *identity, size_t identity_len, + uint8_t *psk, size_t max_psk_len); + size_t(*get_server_hint)(const coap_session_t *session, uint8_t *hint, + size_t max_hint_len); + + void *dtls_context; + + coap_dtls_spsk_t spsk_setup_data; /**< Contains the initial PSK server setup + data */ + + unsigned int session_timeout; /**< Number of seconds of inactivity after + which an unused session will be closed. + 0 means use default. */ + unsigned int max_idle_sessions; /**< Maximum number of simultaneous unused + sessions per endpoint. 0 means no + maximum. */ + unsigned int max_handshake_sessions; /**< Maximum number of simultaneous + negotating sessions per endpoint. 0 + means use default. */ + unsigned int ping_timeout; /**< Minimum inactivity time before + sending a ping message. 0 means + disabled. */ + unsigned int csm_timeout; /**< Timeout for waiting for a CSM from + the remote side. 0 means disabled. */ + uint8_t observe_pending; /**< Observe response pending */ + uint8_t block_mode; /**< Zero or more COAP_BLOCK_ or'd options */ + uint64_t etag; /**< Next ETag to use */ + + coap_cache_entry_t *cache; /**< CoAP cache-entry cache */ + uint16_t *cache_ignore_options; /**< CoAP options to ignore when creating a + cache-key */ + size_t cache_ignore_count; /**< The number of CoAP options to ignore + when creating a cache-key */ + void *app; /**< application-specific data */ +#ifdef COAP_EPOLL_SUPPORT + int epfd; /**< External FD for epoll */ + int eptimerfd; /**< Internal FD for timeout */ + coap_tick_t next_timeout; /**< When the next timeout is to occur */ +#endif /* COAP_EPOLL_SUPPORT */ +}; + +/** + * Adds @p node to given @p queue, ordered by variable t in @p node. + * + * @param queue Queue to add to. + * @param node Node entry to add to Queue. + * + * @return @c 1 added to queue, @c 0 failure. + */ +int coap_insert_node(coap_queue_t **queue, coap_queue_t *node); + +/** + * Destroys specified @p node. + * + * @param node Node entry to remove. + * + * @return @c 1 node deleted from queue, @c 0 failure. + */ +int coap_delete_node(coap_queue_t *node); + +/** + * Removes all items from given @p queue and frees the allocated storage. + * + * Internal function. + * + * @param queue The queue to delete. + */ +void coap_delete_all(coap_queue_t *queue); + +/** + * Creates a new node suitable for adding to the CoAP sendqueue. + * + * @return New node entry, or @c NULL if failure. + */ +coap_queue_t *coap_new_node(void); + +/** + * Set sendqueue_basetime in the given context object @p ctx to @p now. This + * function returns the number of elements in the queue head that have timed + * out. + */ +unsigned int coap_adjust_basetime(coap_context_t *ctx, coap_tick_t now); + +/** + * Returns the next pdu to send without removing from sendqeue. + */ +coap_queue_t *coap_peek_next( coap_context_t *context ); + +/** + * Returns the next pdu to send and removes it from the sendqeue. + */ +coap_queue_t *coap_pop_next( coap_context_t *context ); + +/** + * Handles retransmissions of confirmable messages + * + * @param context The CoAP context. + * @param node The node to retransmit. + * + * @return The message id of the sent message or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_retransmit(coap_context_t *context, coap_queue_t *node); + +/** + * Parses and interprets a CoAP datagram with context @p ctx. This function + * returns @c 0 if the datagram was handled, or a value less than zero on + * error. + * + * @param ctx The current CoAP context. + * @param session The current CoAP session. + * @param data The received packet'd data. + * @param data_len The received packet'd data length. + * + * @return @c 0 if message was handled successfully, or less than zero on + * error. + */ +int coap_handle_dgram(coap_context_t *ctx, coap_session_t *session, uint8_t *data, size_t data_len); + +/** + * This function removes the element with given @p id from the list given list. + * If @p id was found, @p node is updated to point to the removed element. Note + * that the storage allocated by @p node is @b not released. The caller must do + * this manually using coap_delete_node(). This function returns @c 1 if the + * element with id @p id was found, @c 0 otherwise. For a return value of @c 0, + * the contents of @p node is undefined. + * + * @param queue The queue to search for @p id. + * @param session The session to look for. + * @param id The message id to look for. + * @param node If found, @p node is updated to point to the removed node. You + * must release the storage pointed to by @p node manually. + * + * @return @c 1 if @p id was found, @c 0 otherwise. + */ +int coap_remove_from_queue(coap_queue_t **queue, + coap_session_t *session, + coap_mid_t id, + coap_queue_t **node); + +coap_mid_t +coap_wait_ack( coap_context_t *context, coap_session_t *session, + coap_queue_t *node); + +/** + * Cancels all outstanding messages for session @p session that have the specified + * token. + * + * @param context The context in use. + * @param session Session of the messages to remove. + * @param token Message token. + * @param token_length Actual length of @p token. + */ +void coap_cancel_all_messages(coap_context_t *context, + coap_session_t *session, + const uint8_t *token, + size_t token_length); + +/** +* Cancels all outstanding messages for session @p session. +* +* @param context The context in use. +* @param session Session of the messages to remove. +* @param reason The reasion for the session cancellation +*/ +void +coap_cancel_session_messages(coap_context_t *context, + coap_session_t *session, + coap_nack_reason_t reason); + +/** + * Dispatches the PDUs from the receive queue in given context. + */ +void coap_dispatch(coap_context_t *context, coap_session_t *session, + coap_pdu_t *pdu); + +/** + * Verifies that @p pdu contains no unknown critical options. Options must be + * registered at @p ctx, using the function coap_register_option(). A basic set + * of options is registered automatically by coap_new_context(). This function + * returns @c 1 if @p pdu is ok, @c 0 otherwise. The given filter object @p + * unknown will be updated with the unknown options. As only @c COAP_MAX_OPT + * options can be signalled this way, remaining options must be examined + * manually. + * + * @code + coap_opt_filter_t f = COAP_OPT_NONE; + coap_opt_iterator_t opt_iter; + + if (coap_option_check_critical(ctx, pdu, f) == 0) { + coap_option_iterator_init(pdu, &opt_iter, f); + + while (coap_option_next(&opt_iter)) { + if (opt_iter.type & 0x01) { + ... handle unknown critical option in opt_iter ... + } + } + } + @endcode + * + * @param ctx The context where all known options are registered. + * @param pdu The PDU to check. + * @param unknown The output filter that will be updated to indicate the + * unknown critical options found in @p pdu. + * + * @return @c 1 if everything was ok, @c 0 otherwise. + */ +int coap_option_check_critical(coap_context_t *ctx, + coap_pdu_t *pdu, + coap_opt_filter_t *unknown); + +/** + * Creates a new response for given @p request with the contents of @c + * .well-known/core. The result is NULL on error or a newly allocated PDU that + * must be either sent with coap_sent() or released by coap_delete_pdu(). + * + * @param context The current coap context to use. + * @param session The CoAP session. + * @param request The request for @c .well-known/core . + * + * @return A new 2.05 response for @c .well-known/core or NULL on error. + */ +coap_pdu_t *coap_wellknown_response(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *request); + +/** + * Calculates the initial timeout based on the session CoAP transmission + * parameters 'ack_timeout', 'ack_random_factor', and COAP_TICKS_PER_SECOND. + * The calculation requires 'ack_timeout' and 'ack_random_factor' to be in + * Qx.FRAC_BITS fixed point notation, whereas the passed parameter @p r + * is interpreted as the fractional part of a Q0.MAX_BITS random value. + * + * @param session session timeout is associated with + * @param r random value as fractional part of a Q0.MAX_BITS fixed point + * value + * @return COAP_TICKS_PER_SECOND * 'ack_timeout' * + * (1 + ('ack_random_factor' - 1) * r) + */ +unsigned int coap_calc_timeout(coap_session_t *session, unsigned char r); + +/** + * Sends a CoAP message to given peer. The memory that is + * allocated for the pdu will be released by coap_send_internal(). + * The caller must not use the pdu after calling coap_send_internal(). + * + * If the response body is split into multiple payloads using blocks, libcoap + * will handle asking for the subsequent blocks and any necessary recovery + * needed. + * + * @param session The CoAP session. + * @param pdu The CoAP PDU to send. + * + * @return The message id of the sent message or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_send_internal(coap_session_t *session, coap_pdu_t *pdu); + +/** @} */ + +#endif /* COAP_NET_INTERNAL_H_ */ + diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_pdu_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_pdu_internal.h new file mode 100644 index 00000000000..0d8446c0d4c --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_pdu_internal.h @@ -0,0 +1,300 @@ +/* + * coap_pdu_internal.h -- CoAP PDU structure + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_pdu_internal.h + * @brief CoAP PDU internal information + */ + +#ifndef COAP_COAP_PDU_INTERNAL_H_ +#define COAP_COAP_PDU_INTERNAL_H_ + +#ifdef WITH_LWIP +#include +#endif + +#include + +/** + * @defgroup pdu_internal PDU (Internal) + * CoAP PDU Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +#define COAP_DEFAULT_VERSION 1 /* version of CoAP supported */ + +/* TCP Message format constants, do not modify */ +#define COAP_MESSAGE_SIZE_OFFSET_TCP8 13 +#define COAP_MESSAGE_SIZE_OFFSET_TCP16 269 /* 13 + 256 */ +#define COAP_MESSAGE_SIZE_OFFSET_TCP32 65805 /* 269 + 65536 */ + +/* Derived message size limits */ +#define COAP_MAX_MESSAGE_SIZE_TCP0 (COAP_MESSAGE_SIZE_OFFSET_TCP8-1) /* 12 */ +#define COAP_MAX_MESSAGE_SIZE_TCP8 (COAP_MESSAGE_SIZE_OFFSET_TCP16-1) /* 268 */ +#define COAP_MAX_MESSAGE_SIZE_TCP16 (COAP_MESSAGE_SIZE_OFFSET_TCP32-1) /* 65804 */ +#define COAP_MAX_MESSAGE_SIZE_TCP32 (COAP_MESSAGE_SIZE_OFFSET_TCP32+0xFFFFFFFF) + +#ifndef COAP_DEBUG_BUF_SIZE +#if defined(WITH_CONTIKI) || defined(WITH_LWIP) +#define COAP_DEBUG_BUF_SIZE 128 +#else /* defined(WITH_CONTIKI) || defined(WITH_LWIP) */ +/* 1024 derived from RFC7252 4.6. Message Size max payload */ +#define COAP_DEBUG_BUF_SIZE (8 + 1024 * 2) +#endif /* defined(WITH_CONTIKI) || defined(WITH_LWIP) */ +#endif /* COAP_DEBUG_BUF_SIZE */ + +#ifndef COAP_DEFAULT_MAX_PDU_RX_SIZE +#if defined(WITH_CONTIKI) || defined(WITH_LWIP) +#define COAP_DEFAULT_MAX_PDU_RX_SIZE (COAP_MAX_MESSAGE_SIZE_TCP16+4UL) +#else +/* 8 MiB max-message-size plus some space for options */ +#define COAP_DEFAULT_MAX_PDU_RX_SIZE (8UL*1024*1024+256) +#endif +#endif /* COAP_DEFAULT_MAX_PDU_RX_SIZE */ + +/** + * Indicates that a response is suppressed. This will occur for error + * responses if the request was received via IP multicast. + */ +#define COAP_DROPPED_RESPONSE -2 + +#define COAP_PDU_DELAYED -3 + +#define COAP_PAYLOAD_START 0xFF /* payload marker */ + +#define COAP_PDU_IS_EMPTY(pdu) ((pdu)->code == 0) +#define COAP_PDU_IS_REQUEST(pdu) (!COAP_PDU_IS_EMPTY(pdu) && (pdu)->code < 32) +#define COAP_PDU_IS_RESPONSE(pdu) ((pdu)->code >= 64 && (pdu)->code < 224) +#define COAP_PDU_IS_SIGNALING(pdu) ((pdu)->code >= 224) + +#define COAP_PDU_MAX_UDP_HEADER_SIZE 4 +#define COAP_PDU_MAX_TCP_HEADER_SIZE 6 + +/** + * structure for CoAP PDUs + * token, if any, follows the fixed size header, then options until + * payload marker (0xff), then the payload if stored inline. + * Memory layout is: + * <---header--->|<---token---><---options--->0xff<---payload---> + * header is addressed with a negative offset to token, its maximum size is + * max_hdr_size. + * options starts at token + token_length + * payload starts at data, its length is used_size - (data - token) + */ + +struct coap_pdu_t { + coap_pdu_type_t type; /**< message type */ + coap_pdu_code_t code; /**< request method (value 1--31) or response code + (value 64-255) */ + coap_mid_t mid; /**< message id, if any, in regular host byte + order */ + uint8_t max_hdr_size; /**< space reserved for protocol-specific header */ + uint8_t hdr_size; /**< actual size used for protocol-specific + header */ + uint8_t token_length; /**< length of Token */ + uint16_t max_opt; /**< highest option number in PDU */ + size_t alloc_size; /**< allocated storage for token, options and + payload */ + size_t used_size; /**< used bytes of storage for token, options and + payload */ + size_t max_size; /**< maximum size for token, options and payload, + or zero for variable size pdu */ + uint8_t *token; /**< first byte of token, if any, or options */ + uint8_t *data; /**< first byte of payload, if any */ +#ifdef WITH_LWIP + struct pbuf *pbuf; /**< lwIP PBUF. The package data will always reside + * inside the pbuf's payload, but this pointer + * has to be kept because no exact offset can be + * given. This field must not be accessed from + * outside, because the pbuf's reference count + * is checked to be 1 when the pbuf is assigned + * to the pdu, and the pbuf stays exclusive to + * this pdu. */ +#endif + const uint8_t *body_data; /**< Holds ptr to re-assembled data or NULL */ + size_t body_length; /**< Holds body data length */ + size_t body_offset; /**< Holds body data offset */ + size_t body_total; /**< Holds body data total size */ + coap_lg_xmit_t *lg_xmit; /**< Holds ptr to lg_xmit if sending a set of + blocks */ +}; + +/** + * Dynamically grows the size of @p pdu to @p new_size. The new size + * must not exceed the PDU's configure maximum size. On success, this + * function returns 1, otherwise 0. + * + * @param pdu The PDU to resize. + * @param new_size The new size in bytes. + * @return 1 if the operation succeeded, 0 otherwise. + */ +int coap_pdu_resize(coap_pdu_t *pdu, size_t new_size); + +/** + * Dynamically grows the size of @p pdu to @p new_size if needed. The new size + * must not exceed the PDU's configured maximum size. On success, this + * function returns 1, otherwise 0. + * + * @param pdu The PDU to resize. + * @param new_size The new size in bytes. + * @return 1 if the operation succeeded, 0 otherwise. + */ +int coap_pdu_check_resize(coap_pdu_t *pdu, size_t new_size); + +/** +* Interprets @p data to determine the number of bytes in the header. +* This function returns @c 0 on error or a number greater than zero on success. +* +* @param proto Session's protocol +* @param data The first byte of raw data to parse as CoAP PDU. +* +* @return A value greater than zero on success or @c 0 on error. +*/ +size_t coap_pdu_parse_header_size(coap_proto_t proto, + const uint8_t *data); + +/** + * Parses @p data to extract the message size. + * @p length must be at least coap_pdu_parse_header_size(proto, data). + * This function returns @c 0 on error or a number greater than zero on success. + * + * @param proto Session's protocol + * @param data The raw data to parse as CoAP PDU. + * @param length The actual size of @p data. + * + * @return A value greater than zero on success or @c 0 on error. + */ +size_t coap_pdu_parse_size(coap_proto_t proto, + const uint8_t *data, + size_t length); + +/** + * Decode the protocol specific header for the specified PDU. + * @param pdu A newly received PDU. + * @param proto The target wire protocol. + * @return 1 for success or 0 on error. + */ + +int coap_pdu_parse_header(coap_pdu_t *pdu, coap_proto_t proto); + +/** + * Verify consistency in the given CoAP PDU structure and locate the data. + * This function returns @c 0 on error or a number greater than zero on + * success. + * This function only parses the token and options, up to the payload start + * marker. + * + * @param pdu The PDU structure to check. + * + * @return 1 on success or @c 0 on error. + */ +int coap_pdu_parse_opt(coap_pdu_t *pdu); + +/** +* Parses @p data into the CoAP PDU structure given in @p result. +* The target pdu must be large enough to +* This function returns @c 0 on error or a number greater than zero on success. +* +* @param proto Session's protocol +* @param data The raw data to parse as CoAP PDU. +* @param length The actual size of @p data. +* @param pdu The PDU structure to fill. Note that the structure must +* provide space to hold at least the token and options +* part of the message. +* +* @return 1 on success or @c 0 on error. +*/ +int coap_pdu_parse(coap_proto_t proto, + const uint8_t *data, + size_t length, + coap_pdu_t *pdu); + +/** + * Clears any contents from @p pdu and resets @c used_size, + * and @c data pointers. @c max_size is set to @p size, any + * other field is set to @c 0. Note that @p pdu must be a valid + * pointer to a coap_pdu_t object created e.g. by coap_pdu_init(). + * + * @param pdu The PDU to clear. + * @param size The maximum size of the PDU. + */ +void coap_pdu_clear(coap_pdu_t *pdu, size_t size); + +/** + * Removes (first) option of given number from the @p pdu. + * + * @param pdu The PDU to remove the option from. + * @param number The number of the CoAP option to remove (first only removed). + * + * @return @c 1 if success else @c 0 if error. + */ +int coap_remove_option(coap_pdu_t *pdu, coap_option_num_t number); + +/** + * Inserts option of given number in the @p pdu with the appropriate data. + * The option will be inserted in the appropriate place in the options in + * the pdu. + * + * @param pdu The PDU where the option is to be inserted. + * @param number The number of the new option. + * @param len The length of the new option. + * @param data The data of the new option. + * + * @return The overall length of the option or @c 0 on failure. + */ +size_t coap_insert_option(coap_pdu_t *pdu, coap_option_num_t number, + size_t len, const uint8_t *data); + +/** + * Updates existing first option of given number in the @p pdu with the new + * data. + * + * @param pdu The PDU where the option is to be updated. + * @param number The number of the option to update (first only updated). + * @param len The length of the updated option. + * @param data The data of the updated option. + * + * @return The overall length of the updated option or @c 0 on failure. + */ +size_t coap_update_option(coap_pdu_t *pdu, + coap_option_num_t number, + size_t len, + const uint8_t *data); + +/** + * Compose the protocol specific header for the specified PDU. + * + * @param pdu A newly composed PDU. + * @param proto The target wire protocol. + * + * @return Number of header bytes prepended before pdu->token or 0 on error. + */ + +size_t coap_pdu_encode_header(coap_pdu_t *pdu, coap_proto_t proto); + + /** + * Updates token in @p pdu with length @p len and @p data. + * This function returns @c 0 on error or a value greater than zero on success. + * + * @param pdu The PDU where the token is to be updated. + * @param len The length of the new token. + * @param data The token to add. + * + * @return A value greater than zero on success, or @c 0 on error. + */ +int coap_update_token(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** @} */ + +#endif /* COAP_COAP_PDU_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_prng.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_prng.h new file mode 100644 index 00000000000..6d297afaec3 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_prng.h @@ -0,0 +1,113 @@ +/* + * coap_prng.h -- Pseudo Random Numbers + * + * Copyright (C) 2010-2020 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_prng.h + * @brief Pseudo Random Numbers + */ + +#ifndef COAP_PRNG_H_ +#define COAP_PRNG_H_ + +/** + * @defgroup coap_prng Pseudo Random Numbers + * API functions for gerating pseudo random numbers + * @{ + */ + +#if defined(WITH_CONTIKI) +#include + +/** + * Fills \p buf with \p len random bytes. This is the default implementation for + * coap_prng(). You might want to change contiki_prng_impl() to use a better + * PRNG on your specific platform. + */ +COAP_STATIC_INLINE int +contiki_prng_impl(unsigned char *buf, size_t len) { + uint16_t v = random_rand(); + while (len > sizeof(v)) { + memcpy(buf, &v, sizeof(v)); + len -= sizeof(v); + buf += sizeof(v); + v = random_rand(); + } + + memcpy(buf, &v, len); + return 1; +} + +#define coap_prng(Buf,Length) contiki_prng_impl((Buf), (Length)) +#define coap_prng_init(Value) random_init((uint16_t)(Value)) + +#elif defined(WITH_LWIP) && defined(LWIP_RAND) + +COAP_STATIC_INLINE int +lwip_prng_impl(unsigned char *buf, size_t len) { + u32_t v = LWIP_RAND(); + while (len > sizeof(v)) { + memcpy(buf, &v, sizeof(v)); + len -= sizeof(v); + buf += sizeof(v); + v = LWIP_RAND(); + } + + memcpy(buf, &v, len); + return 1; +} + +#define coap_prng(Buf,Length) lwip_prng_impl((Buf), (Length)) +#define coap_prng_init(Value) (void)Value + +#else + +/** + * Data type for random number generator function. The function must + * fill @p len bytes of random data into the buffer starting at @p + * out. On success, the function should return 1, zero otherwise. + */ +typedef int (*coap_rand_func_t)(void *out, size_t len); + +/** + * Replaces the current random number generation function with the + * default function @p rng. + * + * @param rng The random number generation function to use. + */ +void coap_set_prng(coap_rand_func_t rng); + +/** + * Seeds the default random number generation function with the given + * @p seed. The default random number generation function will use + * getrandom() if available, ignoring the seed. + * + * @param seed The seed for the pseudo random number generator. + */ +void coap_prng_init(unsigned int seed); + +/** + * Fills @p buf with @p len random bytes using the default pseudo + * random number generator. The default PRNG can be changed with + * coap_set_prng(). This function returns 1 when @p len random bytes + * have been written to @p buf, zero otherwise. + * + * @param buf The buffer to fill with random bytes. + * @param len The number of random bytes to write into @p buf. + * + * @return 1 on success, 0 otherwise. + */ +int coap_prng(void *buf, size_t len); + +#endif /* POSIX */ + +/** @} */ + +#endif /* COAP_PRNG_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_resource_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_resource_internal.h new file mode 100644 index 00000000000..cbcc36a664c --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_resource_internal.h @@ -0,0 +1,141 @@ +/* + * coap_resource_internal.h -- generic resource handling + * + * Copyright (C) 2010,2011,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_resource_internal.h + * @brief Generic resource internal handling + */ + +#ifndef COAP_RESOURCE_INTERNAL_H_ +#define COAP_RESOURCE_INTERNAL_H_ + +#include "uthash.h" + +/** + * @defgroup coap_resource_internal Resources (Internal) + * Structures, Enums and Functions that are not exposed to applications + * @{ + */ + +/** +* Abstraction of attribute associated with a resource. +*/ +struct coap_attr_t { + struct coap_attr_t *next; /**< Pointer to next in chain or NULL */ + coap_str_const_t *name; /**< Name of the attribute */ + coap_str_const_t *value; /**< Value of the attribute (can be NULL) */ + int flags; +}; + +/** +* Abstraction of resource that can be attached to coap_context_t. +* The key is uri_path. +*/ +struct coap_resource_t { + unsigned int dirty:1; /**< set to 1 if resource has changed */ + unsigned int partiallydirty:1; /**< set to 1 if some subscribers have not yet + * been notified of the last change */ + unsigned int observable:1; /**< can be observed */ + unsigned int cacheable:1; /**< can be cached */ + unsigned int is_unknown:1; /**< resource created for unknown handler */ + unsigned int is_proxy_uri:1; /**< resource created for proxy URI handler */ + + /** + * Used to store handlers for the seven coap methods @c GET, @c POST, @c PUT, + * @c DELETE, @c FETCH, @c PATCH and @c IPATCH. + * coap_dispatch() will pass incoming requests to handle_request() and then + * to the handler that corresponds to its request method or generate a 4.05 + * response if no handler is available. + */ + coap_method_handler_t handler[7]; + + UT_hash_handle hh; + + coap_attr_t *link_attr; /**< attributes to be included with the link format */ + coap_subscription_t *subscribers; /**< list of observers for this resource */ + + /** + * Request URI Path for this resource. This field will point into static + * or allocated memory which must remain there for the duration of the + * resource. + */ + coap_str_const_t *uri_path; /**< the key used for hash lookup for this + resource */ + int flags; /**< zero or more COAP_RESOURCE_FLAGS_* or'd together */ + + /** + * The next value for the Observe option. This field must be increased each + * time the resource changes. Only the lower 24 bits are sent. + */ + unsigned int observe; + + /** + * Pointer back to the context that 'owns' this resource. + */ + coap_context_t *context; + + /** + * Count of valid names this host is known by (proxy support) + */ + size_t proxy_name_count; + + /** + * Array valid names this host is known by (proxy support) + */ + coap_str_const_t ** proxy_name_list; + + /** + * This pointer is under user control. It can be used to store context for + * the coap handler. + */ + void *user_data; + +}; + +/** + * Deletes all resources from given @p context and frees their storage. + * + * @param context The CoAP context with the resources to be deleted. + */ +void coap_delete_all_resources(coap_context_t *context); + +#define RESOURCES_ADD(r, obj) \ + HASH_ADD(hh, (r), uri_path->s[0], (obj)->uri_path->length, (obj)) + +#define RESOURCES_DELETE(r, obj) \ + HASH_DELETE(hh, (r), (obj)) + +#define RESOURCES_ITER(r,tmp) \ + coap_resource_t *tmp, *rtmp; \ + HASH_ITER(hh, (r), tmp, rtmp) + +#define RESOURCES_FIND(r, k, res) { \ + HASH_FIND(hh, (r), (k)->s, (k)->length, (res)); \ + } + +/** + * Deletes an attribute. + * Note: This is for internal use only, as it is not deleted from its chain. + * + * @param attr Pointer to a previously created attribute. + * + */ +void coap_delete_attr(coap_attr_t *attr); + +coap_print_status_t coap_print_wellknown(coap_context_t *, + unsigned char *, + size_t *, size_t, + coap_opt_t *); + + +/** @} */ + +#endif /* COAP_RESOURCE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_riot.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_riot.h new file mode 100644 index 00000000000..fc4bfa2e655 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_riot.h @@ -0,0 +1,34 @@ +/* coap_riot.h -- RIOT-specific definitions for libcoap + * + * Copyright (C) 2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see + * README for terms of use. + */ + +#ifndef COAP_RIOT_H_ +#define COAP_RIOT_H_ + +#ifndef LIBCOAP_MSG_QUEUE_SIZE +/** + * Size of the queue for passing messages between the network + * interface and the coap stack. */ +#define LIBCOAP_MSG_QUEUE_SIZE (32U) +#endif /* LIBCOAP_MSG_QUEUE_SIZE */ + +#ifndef LIBCOAP_MAX_SOCKETS +/** + * Maximum number of sockets that are simultaneously considered for + * reading or writing. */ +#define LIBCOAP_MAX_SOCKETS (16U) +#endif /* LIBCOAP_MAX_SOCKETS */ + +/** + * This function must be called in the RIOT CoAP thread for + * RIOT-specific initialization. + */ +void coap_riot_startup(void); + +#endif /* COAP_RIOT_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session.h new file mode 100644 index 00000000000..6c49b78e97d --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session.h @@ -0,0 +1,591 @@ +/* coap_session.h -- Session management for libcoap +* +* Copyright (C) 2017 Jean-Claue Michelou +* + * SPDX-License-Identifier: BSD-2-Clause + * +* This file is part of the CoAP library libcoap. Please see +* README for terms of use. +*/ + +/** + * @file coap_session.h + * @brief Defines the application visible session information + */ + +#ifndef COAP_SESSION_H_ +#define COAP_SESSION_H_ + +/** + * @defgroup session Sessions + * API functions for CoAP Sessions + * @{ + */ + +/** +* Abstraction of a fixed point number that can be used where necessary instead +* of a float. 1,000 fractional bits equals one integer +*/ +typedef struct coap_fixed_point_t { + uint16_t integer_part; /**< Integer part of fixed point variable */ + uint16_t fractional_part; /**< Fractional part of fixed point variable + 1/1000 (3 points) precision */ +} coap_fixed_point_t; + +#define COAP_PROTO_NOT_RELIABLE(p) ((p)==COAP_PROTO_UDP || (p)==COAP_PROTO_DTLS) +#define COAP_PROTO_RELIABLE(p) ((p)==COAP_PROTO_TCP || (p)==COAP_PROTO_TLS) + +/** + * coap_session_type_t values + */ +typedef enum coap_session_type_t { + COAP_SESSION_TYPE_NONE = 0, /**< Not defined */ + COAP_SESSION_TYPE_CLIENT, /**< client-side */ + COAP_SESSION_TYPE_SERVER, /**< server-side */ + COAP_SESSION_TYPE_HELLO, /**< server-side ephemeral session for + responding to a client hello */ +} coap_session_type_t; + +/** + * coap_session_state_t values + */ +typedef enum coap_session_state_t { + COAP_SESSION_STATE_NONE = 0, + COAP_SESSION_STATE_CONNECTING, + COAP_SESSION_STATE_HANDSHAKE, + COAP_SESSION_STATE_CSM, + COAP_SESSION_STATE_ESTABLISHED, +} coap_session_state_t; + +/** + * Increment reference counter on a session. + * + * @param session The CoAP session. + * @return same as session + */ +coap_session_t *coap_session_reference(coap_session_t *session); + +/** + * Decrement reference counter on a session. + * Note that the session may be deleted as a result and should not be used + * after this call. + * + * @param session The CoAP session. + */ +void coap_session_release(coap_session_t *session); + +/** + * Notify session that it has failed. This cleans up any outstanding / queued + * transmissions, observations etc.. + * + * @param session The CoAP session. + * @param reason The reason why the session was disconnected. + */ +void coap_session_disconnected(coap_session_t *session, + coap_nack_reason_t reason); + +/** + * Stores @p data with the given session. This function overwrites any value + * that has previously been stored with @p session. + * + * @param session The CoAP session. + * @param data The pointer to the data to store. + */ +void coap_session_set_app_data(coap_session_t *session, void *data); + +/** + * Returns any application-specific data that has been stored with @p + * session using the function coap_session_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param session The CoAP session. + * + * @return Pointer to the stored data or @c NULL. + */ +void *coap_session_get_app_data(const coap_session_t *session); + +/** + * Get the remote IP address from the session. + * + * @param session The CoAP session. + * + * @return The session's remote address or @c NULL on failure. + */ +const coap_address_t *coap_session_get_addr_remote( + const coap_session_t *session); + +/** + * Get the local IP address from the session. + * + * @param session The CoAP session. + * + * @return The session's local address or @c NULL on failure. + */ +const coap_address_t *coap_session_get_addr_local( + const coap_session_t *session); + +/** + * Get the session protocol type + * + * @param session The CoAP session. + * + * @return The session's protocol type + */ +coap_proto_t coap_session_get_proto(const coap_session_t *session); + +/** + * Get the session type + * + * @param session The CoAP session. + * + * @return The session's type + */ +coap_session_type_t coap_session_get_type(const coap_session_t *session); + +/** + * Get the session state + * + * @param session The CoAP session. + * + * @return The session's state + */ +coap_session_state_t coap_session_get_state(const coap_session_t *session); + +/** + * Get the session if index + * + * @param session The CoAP session. + * + * @return The session's if index, or @c -1 on error. + */ +int coap_session_get_ifindex(const coap_session_t *session); + +/** + * Get the session TLS security ptr (TLS type dependent) + * + * OpenSSL: SSL* + * GnuTLS: gnutls_session_t (implicit *) + * Mbed TLS: mbedtls_ssl_context* + * TinyDTLS: struct dtls_context* + * + * @param session The CoAP session. + * @param tls_lib Updated with the library type. + * + * @return The session TLS ptr or @c NULL if not set up + */ +void *coap_session_get_tls(const coap_session_t *session, + coap_tls_library_t *tls_lib); + +/** + * Get the session context + * + * @param session The CoAP session. + * + * @return The session's context + */ +coap_context_t *coap_session_get_context(const coap_session_t *session); + +/** + * Set the session type to client. Typically used in a call-home server. + * The session needs to be of type COAP_SESSION_TYPE_SERVER. + * Note: If this function is successful, the session reference count is + * incremented and a subsequent coap_session_release() taking the + * reference count to 0 will cause the session to be freed off. + * + * @param session The CoAP session. + * + * @return @c 1 if updated, @c 0 on failure. + */ +int coap_session_set_type_client(coap_session_t *session); + +/** + * Set the session MTU. This is the maximum message size that can be sent, + * excluding IP and UDP overhead. + * + * @param session The CoAP session. + * @param mtu maximum message size + */ +void coap_session_set_mtu(coap_session_t *session, unsigned mtu); + +/** + * Get maximum acceptable PDU size + * + * @param session The CoAP session. + * @return maximum PDU size, not including header (but including token). + */ +size_t coap_session_max_pdu_size(const coap_session_t *session); + +/** +* Creates a new client session to the designated server. +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to let the operating system choose a suitable local interface. If an address is specified, the port number should be zero, which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default port for the protocol will be used. +* @param proto Protocol. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release to free. +*/ +coap_session_t *coap_new_client_session( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto +); + +/** +* Creates a new client session to the designated server with PSK credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to let the operating system choose a suitable local interface. If an address is specified, the port number should be zero, which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default port for the protocol will be used. +* @param proto Protocol. +* @param identity PSK client identity +* @param key PSK shared key +* @param key_len PSK shared key length +* +* @return A new CoAP session or NULL if failed. Call coap_session_release to free. +*/ +coap_session_t *coap_new_client_session_psk( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + const char *identity, + const uint8_t *key, + unsigned key_len +); + +/** +* Creates a new client session to the designated server with PSK credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to +* let the operating system choose a suitable local interface. +* If an address is specified, the port number should be zero, +* which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default +* port for the protocol will be used. +* @param proto CoAP Protocol. +* @param setup_data PSK parameters. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release() +* to free. +*/ +coap_session_t *coap_new_client_session_psk2( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *setup_data +); + +/** + * Get the server session's current Identity Hint (PSK). + * + * @param session The current coap_session_t object. + * + * @return @c hint if successful, else @c NULL. + */ +const coap_bin_const_t * coap_session_get_psk_hint( + const coap_session_t *session); + +/** + * Get the session's current pre-shared key (PSK). + * + * @param session The current coap_session_t object. + * + * @return @c psk_key if successful, else @c NULL. + */ +const coap_bin_const_t * coap_session_get_psk_key( + const coap_session_t *session); + +/** +* Creates a new client session to the designated server with PKI credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to +* let the operating system choose a suitable local interface. +* If an address is specified, the port number should be zero, +* which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default +* port for the protocol will be used. +* @param proto CoAP Protocol. +* @param setup_data PKI parameters. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release() +* to free. +*/ +coap_session_t *coap_new_client_session_pki( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data +); + +/** + * Initializes the token value to use as a starting point. + * + * @param session The current coap_session_t object. + * @param length The length of the token (0 - 8 bytes). + * @param token The token data. + * + */ +void coap_session_init_token(coap_session_t *session, size_t length, + const uint8_t *token); + +/** + * Creates a new token for use. + * + * @param session The current coap_session_t object. + * @param length Updated with the length of the new token. + * @param token Updated with the new token data (must be 8 bytes long). + * + */ +void coap_session_new_token(coap_session_t *session, size_t *length, + uint8_t *token); + +/** + * @ingroup logging + * Get session description. + * + * @param session The CoAP session. + * @return description string. + */ +const char *coap_session_str(const coap_session_t *session); + +/** +* Create a new endpoint for communicating with peers. +* +* @param context The coap context that will own the new endpoint +* @param listen_addr Address the endpoint will listen for incoming requests on or originate outgoing requests from. Use NULL to specify that no incoming request will be accepted and use a random endpoint. +* @param proto Protocol used on this endpoint +*/ + +coap_endpoint_t *coap_new_endpoint(coap_context_t *context, const coap_address_t *listen_addr, coap_proto_t proto); + +/** +* Set the endpoint's default MTU. This is the maximum message size that can be +* sent, excluding IP and UDP overhead. +* +* @param endpoint The CoAP endpoint. +* @param mtu maximum message size +*/ +void coap_endpoint_set_default_mtu(coap_endpoint_t *endpoint, unsigned mtu); + +void coap_free_endpoint(coap_endpoint_t *ep); + +/** @} */ + +/** + * @ingroup logging +* Get endpoint description. +* +* @param endpoint The CoAP endpoint. +* @return description string. +*/ +const char *coap_endpoint_str(const coap_endpoint_t *endpoint); + +coap_session_t *coap_session_get_by_peer(const coap_context_t *ctx, + const coap_address_t *remote_addr, int ifindex); + + /** + * @defgroup cc Rate Control + * The transmission parameters for CoAP rate control ("Congestion + * Control" in stream-oriented protocols) are defined in + * https://tools.ietf.org/html/rfc7252#section-4.8 + * @{ + */ + + /** + * Number of seconds when to expect an ACK or a response to an + * outstanding CON message. + * RFC 7252, Section 4.8 Default value of ACK_TIMEOUT is 2 + * + * Configurable using coap_session_set_ack_timeout() + */ +#define COAP_DEFAULT_ACK_TIMEOUT ((coap_fixed_point_t){2,0}) + + /** + * A factor that is used to randomize the wait time before a message + * is retransmitted to prevent synchronization effects. + * RFC 7252, Section 4.8 Default value of ACK_RANDOM_FACTOR is 1.5 + * + * Configurable using coap_session_set_ack_random_factor() + */ +#define COAP_DEFAULT_ACK_RANDOM_FACTOR ((coap_fixed_point_t){1,500}) + + /** + * Number of message retransmissions before message sending is stopped + * RFC 7252, Section 4.8 Default value of MAX_RETRANSMIT is 4 + * + * Configurable using coap_session_set_max_retransmit() + */ +#define COAP_DEFAULT_MAX_RETRANSMIT 4 + + /** + * The number of simultaneous outstanding interactions that a client + * maintains to a given server. + * RFC 7252, Section 4.8 Default value of NSTART is 1 + */ +#define COAP_DEFAULT_NSTART 1 + + /** + * The maximum number of seconds before sending back a response to a + * multicast request. + * RFC 7252, Section 4.8 DEFAULT_LEISURE is 5. + */ +#ifndef COAP_DEFAULT_LEISURE +#define COAP_DEFAULT_LEISURE (5U) +#endif /* COAP_DEFAULT_LEISURE */ + + /** + * The MAX_TRANSMIT_SPAN definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_TRAMSMIT_SPAN + * ACK_TIMEOUT * ((2 ** (MAX_RETRANSMIT)) - 1) * ACK_RANDOM_FACTOR + */ +#define COAP_MAX_TRANSMIT_SPAN(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part) * \ + ((1 << (s->max_retransmit)) -1) * \ + (s->ack_random_factor.integer_part * 1000 + \ + s->ack_random_factor.fractional_part) \ + / 1000000) + + /** + * The MAX_TRANSMIT_WAIT definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_TRAMSMIT_WAIT + * ACK_TIMEOUT * ((2 ** (MAX_RETRANSMIT + 1)) - 1) * ACK_RANDOM_FACTOR + */ +#define COAP_MAX_TRANSMIT_WAIT(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part) * \ + ((1 << (s->max_retransmit + 1)) -1) * \ + (s->ack_random_factor.integer_part * 1000 + \ + s->ack_random_factor.fractional_part) \ + / 1000000) + + /** + * The MAX_LATENCY definition. + * RFC 7252, Section 4.8.2 MAX_LATENCY is 100. + */ +#define COAP_MAX_LATENCY 100 + + /** + * The PROCESSING_DELAY definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of PROCESSING_DELAY + * PROCESSING_DELAY set to ACK_TIMEOUT + */ +#define COAP_PROCESSING_DELAY(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part + 500) \ + / 1000) + + /** + * The MAX_RTT definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_RTT + * (2 * MAX_LATENCY) + PROCESSING_DELAY + */ +#define COAP_MAX_RTT(s) \ + ((2 * COAP_MAX_LATENCY) + COAP_PROCESSING_DELAY(s)) + + /** + * The EXCHANGE_LIFETIME definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of EXCHANGE_LIFETIME + * MAX_TRANSMIT_SPAN + (2 * MAX_LATENCY) + PROCESSING_DELAY + */ +#define COAP_EXCHANGE_LIFETIME(s) \ + (COAP_MAX_TRANSMIT_SPAN(s) + (2 * COAP_MAX_LATENCY) + COAP_PROCESSING_DELAY(s)) + + /** + * The NON_LIFETIME definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of NON_LIFETIME + * MAX_TRANSMIT_SPAN + MAX_LATENCY + */ +#define COAP_NON_LIFETIME(s) \ + (COAP_MAX_TRANSMIT_SPAN(s) + COAP_MAX_LATENCY) + + /** @} */ + +/** +* Set the CoAP maximum retransmit count before failure +* +* Number of message retransmissions before message sending is stopped +* +* @param session The CoAP session. +* @param value The value to set to. The default is 4 and should not normally +* get changed. +*/ +void coap_session_set_max_retransmit(coap_session_t *session, + unsigned int value); + +/** +* Set the CoAP initial ack response timeout before the next re-transmit +* +* Number of seconds when to expect an ACK or a response to an +* outstanding CON message. +* +* @param session The CoAP session. +* @param value The value to set to. The default is 2 and should not normally +* get changed. +*/ +void coap_session_set_ack_timeout(coap_session_t *session, + coap_fixed_point_t value); + +/** +* Set the CoAP ack randomize factor +* +* A factor that is used to randomize the wait time before a message +* is retransmitted to prevent synchronization effects. +* +* @param session The CoAP session. +* @param value The value to set to. The default is 1.5 and should not normally +* get changed. +*/ +void coap_session_set_ack_random_factor(coap_session_t *session, + coap_fixed_point_t value); + +/** +* Get the CoAP maximum retransmit before failure +* +* Number of message retransmissions before message sending is stopped +* +* @param session The CoAP session. +* +* @return Current maximum retransmit value +*/ +unsigned int coap_session_get_max_retransmit(const coap_session_t *session); + +/** +* Get the CoAP initial ack response timeout before the next re-transmit +* +* Number of seconds when to expect an ACK or a response to an +* outstanding CON message. +* +* @param session The CoAP session. +* +* @return Current ack response timeout value +*/ +coap_fixed_point_t coap_session_get_ack_timeout(const coap_session_t *session); + +/** +* Get the CoAP ack randomize factor +* +* A factor that is used to randomize the wait time before a message +* is retransmitted to prevent synchronization effects. +* +* @param session The CoAP session. +* +* @return Current ack randomize value +*/ +coap_fixed_point_t coap_session_get_ack_random_factor( + const coap_session_t *session); + +/** + * Send a ping message for the session. + * @param session The CoAP session. + * + * @return COAP_INVALID_MID if there is an error + */ +coap_mid_t coap_session_send_ping(coap_session_t *session); + +#endif /* COAP_SESSION_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session_internal.h new file mode 100644 index 00000000000..1fd2de9ecf1 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_session_internal.h @@ -0,0 +1,295 @@ +/* + * coap_session_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_session_internal.h + * @brief COAP session internal information + */ + +#ifndef COAP_SESSION_INTERNAL_H_ +#define COAP_SESSION_INTERNAL_H_ + +#include "coap_io_internal.h" + +#define COAP_DEFAULT_SESSION_TIMEOUT 300 +#define COAP_PARTIAL_SESSION_TIMEOUT_TICKS (30 * COAP_TICKS_PER_SECOND) +#define COAP_DEFAULT_MAX_HANDSHAKE_SESSIONS 100 + +/** + * @defgroup session_internal Sessions (Internal) + * CoAP Session Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/** + * Only used for servers for hashing incoming packets. Cannot have local IP + * address as this may be an initial multicast and subsequent unicast address + */ +struct coap_addr_hash_t { + coap_address_t remote; /**< remote address and port */ + uint16_t lport; /**< local port */ + coap_proto_t proto; /**< CoAP protocol */ +}; + +/** + * Abstraction of virtual session that can be attached to coap_context_t + * (client) or coap_endpoint_t (server). + */ +struct coap_session_t { + coap_proto_t proto; /**< protocol used */ + coap_session_type_t type; /**< client or server side socket */ + coap_session_state_t state; /**< current state of relationaship with + peer */ + unsigned ref; /**< reference count from queues */ + size_t tls_overhead; /**< overhead of TLS layer */ + size_t mtu; /**< path or CSM mtu */ + coap_addr_hash_t addr_hash; /**< Address hash for server incoming packets */ + UT_hash_handle hh; + coap_addr_tuple_t addr_info; /**< key: remote/local address info */ + int ifindex; /**< interface index */ + coap_socket_t sock; /**< socket object for the session, if + any */ + coap_endpoint_t *endpoint; /**< session's endpoint */ + coap_context_t *context; /**< session's context */ + void *tls; /**< security parameters */ + uint16_t tx_mid; /**< the last message id that was used in + this session */ + uint8_t con_active; /**< Active CON request sent */ + uint8_t csm_block_supported; /**< CSM TCP blocks supported */ + coap_mid_t last_ping_mid; /**< the last keepalive message id that was + used in this session */ + coap_queue_t *delayqueue; /**< list of delayed messages waiting to + be sent */ + coap_lg_xmit_t *lg_xmit; /**< list of large transmissions */ + coap_lg_crcv_t *lg_crcv; /**< Client list of expected large receives */ + coap_lg_srcv_t *lg_srcv; /**< Server list of expected large receives */ + size_t partial_write; /**< if > 0 indicates number of bytes + already written from the pdu at the + head of sendqueue */ + uint8_t read_header[8]; /**< storage space for header of incoming + message header */ + size_t partial_read; /**< if > 0 indicates number of bytes + already read for an incoming message */ + coap_pdu_t *partial_pdu; /**< incomplete incoming pdu */ + coap_tick_t last_rx_tx; + coap_tick_t last_tx_rst; + coap_tick_t last_ping; + coap_tick_t last_pong; + coap_tick_t csm_tx; + coap_dtls_cpsk_t cpsk_setup_data; /**< client provided PSK initial setup + data */ + coap_bin_const_t *psk_identity; /**< If client, this field contains the + current identity for server; When this + field is NULL, the current identity is + contained in cpsk_setup_data + + If server, this field contains the client + provided identity. + + Value maintained internally */ + coap_bin_const_t *psk_key; /**< If client, this field contains the + current pre-shared key for server; + When this field is NULL, the current + key is contained in cpsk_setup_data + + If server, this field contains the + client's current key. + + Value maintained internally */ + coap_bin_const_t *psk_hint; /**< If client, this field contains the + server provided identity hint. + + If server, this field contains the + current hint for the client; When this + field is NULL, the current hint is + contained in context->spsk_setup_data + + Value maintained internally */ + void *app; /**< application-specific data */ + unsigned int max_retransmit; /**< maximum re-transmit count (default + 4) */ + coap_fixed_point_t ack_timeout; /**< timeout waiting for ack (default 2 + secs) */ + coap_fixed_point_t ack_random_factor; /**< ack random factor backoff (default + 1.5) */ + unsigned int dtls_timeout_count; /**< dtls setup retry counter */ + int dtls_event; /**< Tracking any (D)TLS events on this + sesison */ + uint8_t block_mode; /**< Zero or more COAP_BLOCK_ or'd options */ + uint64_t tx_token; /**< Next token number to use */ +}; + +/** + * Abstraction of virtual endpoint that can be attached to coap_context_t. The + * keys (port, bind_addr) must uniquely identify this endpoint. + */ +struct coap_endpoint_t { + struct coap_endpoint_t *next; + coap_context_t *context; /**< endpoint's context */ + coap_proto_t proto; /**< protocol used on this interface */ + uint16_t default_mtu; /**< default mtu for this interface */ + coap_socket_t sock; /**< socket object for the interface, if + any */ + coap_address_t bind_addr; /**< local interface address */ + coap_session_t *sessions; /**< hash table or list of active sessions */ +}; + +/** + * Notify session transport has just connected and CSM exchange can now start. + * + * @param session The CoAP session. + */ +void coap_session_send_csm(coap_session_t *session); + +/** + * Notify session that it has just connected or reconnected. + * + * @param session The CoAP session. + */ +void coap_session_connected(coap_session_t *session); + +/** + * Refresh the session's current Identity Hint (PSK). + * Note: A copy of @p psk_hint is maintained in the session by libcoap. + * + * @param session The current coap_session_t object. + * @param psk_hint If NULL, the Identity Hint will revert to the + * initial Identity Hint used at session setup. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_session_refresh_psk_hint(coap_session_t *session, + const coap_bin_const_t *psk_hint); + +/** + * Refresh the session's current pre-shared key (PSK). + * Note: A copy of @p psk_key is maintained in the session by libcoap. + * + * @param session The current coap_session_t object. + * @param psk_key If NULL, the pre-shared key will revert to the + * initial pre-shared key used as session setup. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_session_refresh_psk_key(coap_session_t *session, + const coap_bin_const_t *psk_key); + +/** + * Creates a new server session for the specified endpoint. + * @param ctx The CoAP context. + * @param ep An endpoint where an incoming connection request is pending. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release to + * add to unused queue. + */ +coap_session_t *coap_new_server_session( + coap_context_t *ctx, + coap_endpoint_t *ep +); + +/** + * Function interface for datagram data transmission. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. + * + * @param session Session to send data on. + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_send(coap_session_t *session, + const uint8_t *data, size_t datalen); + +/** + * Function interface for stream data transmission. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. The number of bytes written may be less than datalen because of + * congestion control. + * + * @param session Session to send data on. + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_write(coap_session_t *session, + const uint8_t *data, size_t datalen); + +/** + * Send a pdu according to the session's protocol. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. + * + * @param session Session to send pdu on. + * @param pdu The pdu to send. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_send_pdu(coap_session_t *session, coap_pdu_t *pdu); + +ssize_t +coap_session_delay_pdu(coap_session_t *session, coap_pdu_t *pdu, + coap_queue_t *node); + +/** + * Lookup the server session for the packet received on an endpoint, or create + * a new one. + * + * @param endpoint Active endpoint the packet was received on. + * @param packet Received packet. + * @param now The current time in ticks. + * @return The CoAP session or @c NULL if error. + */ +coap_session_t *coap_endpoint_get_session(coap_endpoint_t *endpoint, + const coap_packet_t *packet, coap_tick_t now); + +/** + * Create a new DTLS session for the @p session. + * Note: the @p session is released if no DTLS server session can be created. + * + * @ingroup dtls_internal + * + * @param session Session to add DTLS session to + * @param now The current time in ticks. + * + * @return CoAP session or @c NULL if error. + */ +coap_session_t *coap_session_new_dtls_session(coap_session_t *session, + coap_tick_t now); + +void coap_session_free(coap_session_t *session); +void coap_session_mfree(coap_session_t *session); + +/** @} */ + +#define SESSIONS_ADD(e, obj) \ + HASH_ADD(hh, (e), addr_hash, sizeof((obj)->addr_hash), (obj)) + +#define SESSIONS_DELETE(e, obj) \ + HASH_DELETE(hh, (e), (obj)) + +#define SESSIONS_ITER(e, el, rtmp) \ + HASH_ITER(hh, (e), el, rtmp) + +#define SESSIONS_ITER_SAFE(e, el, rtmp) \ +for ((el) = (e); (el) && ((rtmp) = (el)->hh.next, 1); (el) = (rtmp)) + +#define SESSIONS_FIND(e, k, res) { \ + HASH_FIND(hh, (e), &(k), sizeof(k), (res)); \ + } + +#endif /* COAP_SESSION_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_subscribe_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_subscribe_internal.h new file mode 100644 index 00000000000..b7702362bee --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_subscribe_internal.h @@ -0,0 +1,151 @@ +/* + * coap_subscribe_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_subscribe_internal.h + * @brief COAP subscribe internal information + */ + +#ifndef COAP_SUBSCRIBE_INTERNAL_H_ +#define COAP_SUBSCRIBE_INTERNAL_H_ + +/** + * @defgroup subscribe_internal Observe Subscription (Internal) + * CoAP Observe Subscription Structures, Enums and Functions that are not + * exposed to applications + * @{ + */ + +#ifndef COAP_OBS_MAX_NON +/** + * Number of notifications that may be sent non-confirmable before a confirmable + * message is sent to detect if observers are alive. The maximum allowed value + * here is @c 15. + */ +#define COAP_OBS_MAX_NON 5 +#endif /* COAP_OBS_MAX_NON */ + +#ifndef COAP_OBS_MAX_FAIL +/** + * Number of confirmable notifications that may fail (i.e. time out without + * being ACKed) before an observer is removed. The maximum value for + * COAP_OBS_MAX_FAIL is @c 3. + */ +#define COAP_OBS_MAX_FAIL 3 +#endif /* COAP_OBS_MAX_FAIL */ + +/** Subscriber information */ +struct coap_subscription_t { + struct coap_subscription_t *next; /**< next element in linked list */ + struct coap_session_t *session; /**< subscriber session */ + + unsigned int non_cnt:4; /**< up to 15 non-confirmable notifies allowed */ + unsigned int fail_cnt:2; /**< up to 3 confirmable notifies can fail */ + unsigned int dirty:1; /**< set if the notification temporarily could not be + * sent (in that case, the resource's partially + * dirty flag is set too) */ + coap_cache_key_t *cache_key; /** cache_key to identify requester */ + coap_pdu_t *pdu; /**< PDU to use for additional requests */ +}; + +void coap_subscription_init(coap_subscription_t *); + +/** + * Handles a failed observe notify. + * + * @param context The context holding the resource. + * @param session The session that the observe notify failed on. + * @param token The token used when the observe notify failed. + */ +void +coap_handle_failed_notify(coap_context_t *context, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Checks all known resources to see if they are dirty and then notifies + * subscribed observers. + * + * @param context The context to check for dirty resources. + */ +void coap_check_notify(coap_context_t *context); + +/** + * Adds the specified peer as observer for @p resource. The subscription is + * identified by the given @p token. This function returns the registered + * subscription information if the @p observer has been added, or @c NULL on + * error. + * + * @param resource The observed resource. + * @param session The observer's session + * @param token The token that identifies this subscription. + * @param pdu The requesting pdu. + * + * @return A pointer to the added/updated subscription + * information or @c NULL on error. + */ +coap_subscription_t *coap_add_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token, + const coap_pdu_t *pdu); + +/** + * Returns a subscription object for given @p peer. + * + * @param resource The observed resource. + * @param session The observer's session + * @param token The token that identifies this subscription or @c NULL for + * any token. + * @return A valid subscription if exists or @c NULL otherwise. + */ +coap_subscription_t *coap_find_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Flags that data is ready to be sent to observers. + * + * @param context The CoAP context to use. + * @param session The observer's session + * @param token The corresponding token that has been used for the + * subscription. + */ +void coap_touch_observer(coap_context_t *context, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Removes any subscription for @p observer from @p resource and releases the + * allocated storage. The result is @c 1 if an observation relationship with @p + * observer and @p token existed, @c 0 otherwise. + * + * @param resource The observed resource. + * @param session The observer's session. + * @param token The token that identifies this subscription or @c NULL for + * any token. + * @return @c 1 if the observer has been deleted, @c 0 otherwise. + */ +int coap_delete_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Removes any subscription for @p session and releases the allocated storage. + * + * @param context The CoAP context to use. + * @param session The observer's session. + */ +void coap_delete_observers(coap_context_t *context, coap_session_t *session); + +/** @} */ + +#endif /* COAP_SUBSCRIBE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_tcp_internal.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_tcp_internal.h new file mode 100644 index 00000000000..4fd31b38d01 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_tcp_internal.h @@ -0,0 +1,111 @@ +/* + * coap_tcp_internal.h -- TCP functions for libcoap + * + * Copyright (C) 2019--2020 Olaf Bergmann and others + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_tcp_internal.h + * @brief COAP tcp internal information + */ + +#ifndef COAP_TCP_INTERNAL_H_ +#define COAP_TCP_INTERNAL_H_ + +#include "coap_io.h" + +/** + * @defgroup tcp TCP Support (Internal) + * CoAP TCP Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +#if !COAP_DISABLE_TCP + +/** + * Create a new TCP socket and initiate the connection + * + * Internal function. + * + * @param sock Where socket information is to be filled in + * @param local_if The local address to use or NULL + * @param server The address to connect to + * @param default_port The port to use if not set in @p server + * @param local_addr Filled in after connection initiation with + * the local address + * @param remote_addr Filled in after connection initiation with + * the remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_connect_tcp1(coap_socket_t *sock, + const coap_address_t *local_if, + const coap_address_t *server, + int default_port, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +/** + * Complete the TCP Connection + * + * Internal function. + * + * @param sock The socket information to use + * @param local_addr Filled in with the final local address + * @param remote_addr Filled in with the final remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_connect_tcp2(coap_socket_t *sock, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +/** + * Create a new TCP socket and then listen for new incoming TCP sessions + * + * Internal function. + * + * @param sock Where socket information is to be filled in + * @param listen_addr The address to be listening for new incoming sessions + * @param bound_addr Filled in with the address that the TCP layer + * is listening on for new incoming TCP sessions + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_bind_tcp(coap_socket_t *sock, + const coap_address_t *listen_addr, + coap_address_t *bound_addr); + +/** + * Accept a new incoming TCP session + * + * Internal function. + * + * @param server The socket information to use to accept the TCP connection + * @param new_client Filled in socket information with the new incoming + * session information + * @param local_addr Filled in with the local address + * @param remote_addr Filled in with the remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_accept_tcp(coap_socket_t *server, + coap_socket_t *new_client, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +#endif /* !COAP_DISABLE_TCP */ + +/** @} */ + +#endif /* COAP_TCP_INTERNAL_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_time.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_time.h new file mode 100644 index 00000000000..baa8650eaff --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/coap_time.h @@ -0,0 +1,199 @@ +/* + * coap_time.h -- Clock Handling + * + * Copyright (C) 2010-2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_time.h + * @brief Clock Handling + */ + +#ifndef COAP_TIME_H_ +#define COAP_TIME_H_ + +/** + * @defgroup clock Clock Handling + * Default implementation of internal clock. + * @{ + */ + +#if defined(WITH_LWIP) + +#include +#include + +/* lwIP provides ms in sys_now */ +#define COAP_TICKS_PER_SECOND 1000 + +typedef uint32_t coap_tick_t; +typedef uint32_t coap_time_t; +typedef int32_t coap_tick_diff_t; + +COAP_STATIC_INLINE void coap_ticks_impl(coap_tick_t *t) { + *t = sys_now(); +} + +COAP_STATIC_INLINE void coap_clock_init_impl(void) { +} + +#define coap_clock_init coap_clock_init_impl +#define coap_ticks coap_ticks_impl + +COAP_STATIC_INLINE coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / COAP_TICKS_PER_SECOND; +} + +COAP_STATIC_INLINE uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND; +} + +#elif defined(WITH_CONTIKI) + +#include "clock.h" + +typedef clock_time_t coap_tick_t; +typedef clock_time_t coap_time_t; + +/** + * This data type is used to represent the difference between two clock_tick_t + * values. This data type must have the same size in memory as coap_tick_t to + * allow wrapping. + */ +typedef int coap_tick_diff_t; + +#define COAP_TICKS_PER_SECOND CLOCK_SECOND + +COAP_STATIC_INLINE void coap_clock_init(void) { + clock_init(); +} + +COAP_STATIC_INLINE void coap_ticks(coap_tick_t *t) { + *t = clock_time(); +} + +COAP_STATIC_INLINE coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / COAP_TICKS_PER_SECOND; +} + +COAP_STATIC_INLINE uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND; +} + +#elif defined(RIOT_VERSION) +#include + +#define COAP_TICKS_PER_SECOND (XTIMER_HZ) + +typedef uint64_t coap_tick_t; +typedef int64_t coap_tick_diff_t; +typedef uint32_t coap_time_t; + +static inline void coap_clock_init(void) {} + +static inline void coap_ticks(coap_tick_t *t) { + *t = xtimer_now_usec64(); +} + +static inline coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / 1000000UL; +} + +static inline uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return t; +} + +static inline coap_tick_t coap_ticks_from_rt_us(uint64_t t) { + return t / 1000000UL; +} +#else /* !WITH_LWIP && !WITH_CONTIKI && !RIOT_VERSION */ + +#include + +/** + * This data type represents internal timer ticks with COAP_TICKS_PER_SECOND + * resolution. + */ +typedef uint64_t coap_tick_t; + +/** + * CoAP time in seconds since epoch. + */ +typedef time_t coap_time_t; + +/** + * This data type is used to represent the difference between two clock_tick_t + * values. This data type must have the same size in memory as coap_tick_t to + * allow wrapping. + */ +typedef int64_t coap_tick_diff_t; + +/** Use ms resolution on POSIX systems */ +#define COAP_TICKS_PER_SECOND ((coap_tick_t)(1000U)) + +/** + * Initializes the internal clock. + */ +void coap_clock_init(void); + +/** + * Sets @p t to the internal time with COAP_TICKS_PER_SECOND resolution. + */ +void coap_ticks(coap_tick_t *t); + +/** + * Helper function that converts coap ticks to wallclock time. On POSIX, this + * function returns the number of seconds since the epoch. On other systems, it + * may be the calculated number of seconds since last reboot or so. + * + * @param t Internal system ticks. + * + * @return The number of seconds that has passed since a specific reference + * point (seconds since epoch on POSIX). + */ +coap_time_t coap_ticks_to_rt(coap_tick_t t); + +/** +* Helper function that converts coap ticks to POSIX wallclock time in us. +* +* @param t Internal system ticks. +* +* @return The number of seconds that has passed since a specific reference +* point (seconds since epoch on POSIX). +*/ +uint64_t coap_ticks_to_rt_us(coap_tick_t t); + +/** +* Helper function that converts POSIX wallclock time in us to coap ticks. +* +* @param t POSIX time is us +* +* @return coap ticks +*/ +coap_tick_t coap_ticks_from_rt_us(uint64_t t); +#endif + +/** + * Returns @c 1 if and only if @p a is less than @p b where less is defined on a + * signed data type. + */ +COAP_STATIC_INLINE int coap_time_lt(coap_tick_t a, coap_tick_t b) { + return ((coap_tick_diff_t)(a - b)) < 0; +} + +/** + * Returns @c 1 if and only if @p a is less than or equal @p b where less is + * defined on a signed data type. + */ +COAP_STATIC_INLINE int coap_time_le(coap_tick_t a, coap_tick_t b) { + return a == b || coap_time_lt(a,b); +} + +/** @} */ + +#endif /* COAP_TIME_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/encode.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/encode.h new file mode 100644 index 00000000000..a79146fc862 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/encode.h @@ -0,0 +1,120 @@ +/* + * encode.h -- encoding and decoding of CoAP data types + * + * Copyright (C) 2010-2012 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_ENCODE_H_ +#define COAP_ENCODE_H_ + +#if (BSD >= 199103) || defined(WITH_CONTIKI) || defined(_WIN32) +# include +#else +# include +#endif + +#include + +#ifndef HAVE_FLS +/* include this only if fls() is not available */ +extern int coap_fls(unsigned int i); +#else +#define coap_fls(i) fls(i) +#endif + +#ifndef HAVE_FLSLL + /* include this only if flsll() is not available */ +extern int coap_flsll(long long i); +#else +#define coap_flsll(i) flsll(i) +#endif + +/** + * @defgroup encode Encode / Decode API + * API functions for endoding/decoding CoAP options. + * @{ + */ + +/** + * Decodes multiple-length byte sequences. @p buf points to an input byte + * sequence of length @p length. Returns the up to 4 byte decoded value. + * + * @param buf The input byte sequence to decode from + * @param length The length of the input byte sequence + * + * @return The decoded value + */ +unsigned int coap_decode_var_bytes(const uint8_t *buf, size_t length); + +/** + * Decodes multiple-length byte sequences. @p buf points to an input byte + * sequence of length @p length. Returns the up to 8 byte decoded value. + * + * @param buf The input byte sequence to decode from + * @param length The length of the input byte sequence + * + * @return The decoded value + */ +uint64_t coap_decode_var_bytes8(const uint8_t *buf, size_t length); + +/** + * Encodes multiple-length byte sequences. @p buf points to an output buffer of + * sufficient length to store the encoded bytes. @p value is the 4 byte value + * to encode. + * Returns the number of bytes used to encode @p value or 0 on error. + * + * @param buf The output buffer to encode into + * @param length The output buffer size to encode into (must be sufficient) + * @param value The value to encode into the buffer + * + * @return The number of bytes used to encode @p value or @c 0 on error. + */ +unsigned int coap_encode_var_safe(uint8_t *buf, + size_t length, + unsigned int value); + +/** + * Encodes multiple-length byte sequences. @p buf points to an output buffer of + * sufficient length to store the encoded bytes. @p value is the 8 byte value + * to encode. + * Returns the number of bytes used to encode @p value or 0 on error. + * + * @param buf The output buffer to encode into + * @param length The output buffer size to encode into (must be sufficient) + * @param value The value to encode into the buffer + * + * @return The number of bytes used to encode @p value or @c 0 on error. + */ +unsigned int coap_encode_var_safe8(uint8_t *buf, + size_t length, + uint64_t value); + +/** @} */ + +/** + * @deprecated Use coap_encode_var_safe() instead. + * Provided for backward compatibility. As @p value has a + * maximum value of 0xffffffff, and buf is usually defined as an array, it + * is unsafe to continue to use this variant if buf[] is less than buf[4]. + * + * For example + * char buf[1],oops; + * .. + * coap_encode_var_bytes(buf, 0xfff); + * would cause oops to get overwritten. This error can only be found by code + * inspection. + * coap_encode_var_safe(buf, sizeof(buf), 0xfff); + * would catch this error at run-time and should be used instead. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_encode_var_bytes(uint8_t *buf, unsigned int value +) { + return (int)coap_encode_var_safe(buf, sizeof(value), value); +} + +#endif /* COAP_ENCODE_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/libcoap.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/libcoap.h new file mode 100644 index 00000000000..60ca3b64b90 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/libcoap.h @@ -0,0 +1,63 @@ +/* + * libcoap.h -- platform specific header file for CoAP stack + * + * Copyright (C) 2015 Carsten Schoenert + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_LIBCOAP_H_ +#define COAP_LIBCOAP_H_ + +/* The non posix embedded platforms like Contiki, TinyOS, RIOT, ... doesn't have + * a POSIX compatible header structure so we have to slightly do some platform + * related things. Currently there is only Contiki available so we check for a + * CONTIKI environment and do *not* include the POSIX related network stuff. If + * there are other platforms in future there need to be analogous environments. + * + * The CONTIKI variable is within the Contiki build environment! */ + +#if defined(_WIN32) +#pragma comment(lib,"Ws2_32.lib") +#include +typedef SSIZE_T ssize_t; +typedef USHORT in_port_t; +#elif !defined (CONTIKI) +#include +#include +#endif /* CONTIKI */ + +#ifndef COAP_STATIC_INLINE +# if defined(__cplusplus) +# define COAP_STATIC_INLINE inline +# else +# if defined(_MSC_VER) +# define COAP_STATIC_INLINE static __inline +# else +# define COAP_STATIC_INLINE static inline +# endif +# endif +#endif +#ifndef COAP_DEPRECATED +# if defined(_MSC_VER) +# define COAP_DEPRECATED __declspec(deprecated) +# else +# define COAP_DEPRECATED __attribute__ ((deprecated)) +# endif +#endif +#ifndef COAP_UNUSED +# ifdef __GNUC__ +# define COAP_UNUSED __attribute__((unused)) +# else /* __GNUC__ */ +# define COAP_UNUSED +# endif /* __GNUC__ */ +#endif /* COAP_UNUSED */ + +void coap_startup(void); + +void coap_cleanup(void); + +#endif /* COAP_LIBCOAP_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/lwippools.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/lwippools.h new file mode 100644 index 00000000000..445bce4a94a --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/lwippools.h @@ -0,0 +1,117 @@ +/* + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/* Memory pool definitions for the libcoap when used with lwIP (which has its + * own mechanism for quickly allocating chunks of data with known sizes). Has + * to be findable by lwIP (ie. an #include must either directly + * include this or include something more generic which includes this), and + * MEMP_USE_CUSTOM_POOLS has to be set in lwipopts.h. */ + +#include "coap_internal.h" +#include "net.h" +#include "resource.h" +#include "subscribe.h" + +#ifndef MEMP_NUM_COAPCONTEXT +#define MEMP_NUM_COAPCONTEXT 1 +#endif + +#ifndef MEMP_NUM_COAPENDPOINT +#define MEMP_NUM_COAPENDPOINT 1 +#endif + +/* 1 is sufficient as this is very short-lived */ +#ifndef MEMP_NUM_COAPPACKET +#define MEMP_NUM_COAPPACKET 1 +#endif + +#ifndef MEMP_NUM_COAPNODE +#define MEMP_NUM_COAPNODE 4 +#endif + +#ifndef MEMP_NUM_COAPPDU +#define MEMP_NUM_COAPPDU MEMP_NUM_COAPNODE +#endif + +#ifndef MEMP_NUM_COAPSESSION +#define MEMP_NUM_COAPSESSION 2 +#endif + +#ifndef MEMP_NUM_COAP_SUBSCRIPTION +#define MEMP_NUM_COAP_SUBSCRIPTION 4 +#endif + +#ifndef MEMP_NUM_COAPRESOURCE +#define MEMP_NUM_COAPRESOURCE 10 +#endif + +#ifndef MEMP_NUM_COAPRESOURCEATTR +#define MEMP_NUM_COAPRESOURCEATTR 20 +#endif + +#ifndef MEMP_NUM_COAPOPTLIST +#define MEMP_NUM_COAPOPTLIST 1 +#endif + +#ifndef MEMP_LEN_COAPOPTLIST +#define MEMP_LEN_COAPOPTLIST 12 +#endif + +#ifndef MEMP_NUM_COAPSTRING +#define MEMP_NUM_COAPSTRING 10 +#endif + +#ifndef MEMP_LEN_COAPSTRING +#define MEMP_LEN_COAPSTRING 32 +#endif + +#ifndef MEMP_NUM_COAPCACHE_KEYS +#define MEMP_NUM_COAPCACHE_KEYS (2U) +#endif /* MEMP_NUM_COAPCACHE_KEYS */ + +#ifndef MEMP_NUM_COAPCACHE_ENTRIES +#define MEMP_NUM_COAPCACHE_ENTRIES (2U) +#endif /* MEMP_NUM_COAPCACHE_ENTRIES */ + +#ifndef MEMP_NUM_COAPPDUBUF +#define MEMP_NUM_COAPPDUBUF 2 +#endif + +#ifndef MEMP_LEN_COAPPDUBUF +#define MEMP_LEN_COAPPDUBUF 32 +#endif + +#ifndef MEMP_NUM_COAPLGXMIT +#define MEMP_NUM_COAPLGXMIT 2 +#endif + +#ifndef MEMP_NUM_COAPLGCRCV +#define MEMP_NUM_COAPLGCRCV 2 +#endif + +#ifndef MEMP_NUM_COAPLGSRCV +#define MEMP_NUM_COAPLGSRCV 2 +#endif + +LWIP_MEMPOOL(COAP_CONTEXT, MEMP_NUM_COAPCONTEXT, sizeof(coap_context_t), "COAP_CONTEXT") +LWIP_MEMPOOL(COAP_ENDPOINT, MEMP_NUM_COAPENDPOINT, sizeof(coap_endpoint_t), "COAP_ENDPOINT") +LWIP_MEMPOOL(COAP_PACKET, MEMP_NUM_COAPPACKET, sizeof(coap_packet_t), "COAP_PACKET") +LWIP_MEMPOOL(COAP_NODE, MEMP_NUM_COAPNODE, sizeof(coap_queue_t), "COAP_NODE") +LWIP_MEMPOOL(COAP_PDU, MEMP_NUM_COAPPDU, sizeof(coap_pdu_t), "COAP_PDU") +LWIP_MEMPOOL(COAP_SESSION, MEMP_NUM_COAPSESSION, sizeof(coap_session_t), "COAP_SESSION") +LWIP_MEMPOOL(COAP_subscription, MEMP_NUM_COAP_SUBSCRIPTION, sizeof(coap_subscription_t), "COAP_subscription") +LWIP_MEMPOOL(COAP_RESOURCE, MEMP_NUM_COAPRESOURCE, sizeof(coap_resource_t), "COAP_RESOURCE") +LWIP_MEMPOOL(COAP_RESOURCEATTR, MEMP_NUM_COAPRESOURCEATTR, sizeof(coap_attr_t), "COAP_RESOURCEATTR") +LWIP_MEMPOOL(COAP_OPTLIST, MEMP_NUM_COAPOPTLIST, sizeof(coap_optlist_t)+MEMP_LEN_COAPOPTLIST, "COAP_OPTLIST") +LWIP_MEMPOOL(COAP_STRING, MEMP_NUM_COAPSTRING, sizeof(coap_string_t)+MEMP_LEN_COAPSTRING, "COAP_STRING") +LWIP_MEMPOOL(COAP_CACHE_KEY, MEMP_NUM_COAPCACHE_KEYS, sizeof(coap_cache_key_t), "COAP_CACHE_KEY") +LWIP_MEMPOOL(COAP_CACHE_ENTRY, MEMP_NUM_COAPCACHE_ENTRIES, sizeof(coap_cache_entry_t), "COAP_CACHE_ENTRY") +LWIP_MEMPOOL(COAP_PDU_BUF, MEMP_NUM_COAPPDUBUF, MEMP_LEN_COAPPDUBUF, "COAP_PDU_BUF") +LWIP_MEMPOOL(COAP_LG_XMIT, MEMP_NUM_COAPLGXMIT, sizeof(coap_lg_xmit_t), "COAP_LG_XMIT") +LWIP_MEMPOOL(COAP_LG_CRCV, MEMP_NUM_COAPLGCRCV, sizeof(coap_lg_crcv_t), "COAP_LG_CRCV") +LWIP_MEMPOOL(COAP_LG_SRCV, MEMP_NUM_COAPLGSRCV, sizeof(coap_lg_srcv_t), "COAP_LG_SRCV") + diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/mem.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/mem.h new file mode 100644 index 00000000000..c42008963da --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/mem.h @@ -0,0 +1,139 @@ +/* + * mem.h -- CoAP memory handling + * + * Copyright (C) 2010-2011,2014-2015 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_MEM_H_ +#define COAP_MEM_H_ + +#include + +#ifndef WITH_LWIP +/** + * Initializes libcoap's memory management. + * This function must be called once before coap_malloc() can be used on + * constrained devices. + */ +void coap_memory_init(void); +#endif /* WITH_LWIP */ + +/** + * Type specifiers for coap_malloc_type(). Memory objects can be typed to + * facilitate arrays of type objects to be used instead of dynamic memory + * management on constrained devices. + */ +typedef enum { + COAP_STRING, + COAP_ATTRIBUTE_NAME, + COAP_ATTRIBUTE_VALUE, + COAP_PACKET, + COAP_NODE, + COAP_CONTEXT, + COAP_ENDPOINT, + COAP_PDU, + COAP_PDU_BUF, + COAP_RESOURCE, + COAP_RESOURCEATTR, +#ifdef HAVE_LIBTINYDTLS + COAP_DTLS_SESSION, +#endif + COAP_SESSION, + COAP_OPTLIST, + COAP_CACHE_KEY, + COAP_CACHE_ENTRY, + COAP_LG_XMIT, + COAP_LG_CRCV, + COAP_LG_SRCV, +} coap_memory_tag_t; + +#ifndef WITH_LWIP + +/** + * Allocates a chunk of @p size bytes and returns a pointer to the newly + * allocated memory. The @p type is used to select the appropriate storage + * container on constrained devices. The storage allocated by coap_malloc_type() + * must be released with coap_free_type(). + * + * @param type The type of object to be stored. + * @param size The number of bytes requested. + * @return A pointer to the allocated storage or @c NULL on error. + */ +void *coap_malloc_type(coap_memory_tag_t type, size_t size); + +/** + * Reallocates a chunk @p p of bytes created by coap_malloc_type() or + * coap_realloc_type() and returns a pointer to the newly allocated memory of + * @p size. + * Only COAP_STRING type is supported. + * + * Note: If there is an error, @p p will separately need to be released by + * coap_free_type(). + * + * @param type The type of object to be stored. + * @param p A pointer to memory that was allocated by coap_malloc_type(). + * @param size The number of bytes requested. + * @return A pointer to the allocated storage or @c NULL on error. + */ +void *coap_realloc_type(coap_memory_tag_t type, void *p, size_t size); + +/** + * Releases the memory that was allocated by coap_malloc_type(). The type tag @p + * type must be the same that was used for allocating the object pointed to by + * @p . + * + * @param type The type of the object to release. + * @param p A pointer to memory that was allocated by coap_malloc_type(). + */ +void coap_free_type(coap_memory_tag_t type, void *p); + +/** + * Wrapper function to coap_malloc_type() for backwards compatibility. + */ +COAP_STATIC_INLINE void *coap_malloc(size_t size) { + return coap_malloc_type(COAP_STRING, size); +} + +/** + * Wrapper function to coap_free_type() for backwards compatibility. + */ +COAP_STATIC_INLINE void coap_free(void *object) { + coap_free_type(COAP_STRING, object); +} + +#endif /* not WITH_LWIP */ + +#ifdef WITH_LWIP + +#include + +/* no initialization needed with lwip (or, more precisely: lwip must be + * completely initialized anyway by the time coap gets active) */ +COAP_STATIC_INLINE void coap_memory_init(void) {} + +/* It would be nice to check that size equals the size given at the memp + * declaration, but i currently don't see a standard way to check that without + * sourcing the custom memp pools and becoming dependent of its syntax + */ +#define coap_malloc_type(type, size) memp_malloc(MEMP_ ## type) +#define coap_free_type(type, p) memp_free(MEMP_ ## type, p) + +/* Those are just here to make uri.c happy where string allocation has not been + * made conditional. + */ +COAP_STATIC_INLINE void *coap_malloc(size_t size) { + LWIP_ASSERT("coap_malloc must not be used in lwIP", 0); +} + +COAP_STATIC_INLINE void coap_free(void *pointer) { + LWIP_ASSERT("coap_free must not be used in lwIP", 0); +} + +#endif /* WITH_LWIP */ + +#endif /* COAP_MEM_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/net.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/net.h new file mode 100644 index 00000000000..577a0b5d5a5 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/net.h @@ -0,0 +1,779 @@ +/* + * net.h -- CoAP network interface + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_NET_H_ +#define COAP_NET_H_ + +#include +#include +#ifndef _WIN32 +#include +#endif +#include + +#ifdef WITH_LWIP +#include +#endif + +#include "coap_io.h" +#include "coap_dtls.h" +#include "coap_event.h" +#include "pdu.h" +#include "coap_session.h" + +/** + * @defgroup context Context Handling + * API functions for handling PDUs using CoAP Contexts + * @{ + */ + +typedef enum coap_response_t { + COAP_RESPONSE_FAIL, /**< Response not liked - send CoAP RST packet */ + COAP_RESPONSE_OK /**< Response is fine */ +} coap_response_t; + +/** + * Response handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param sent The PDU that was transmitted. + * @param received The PDU that was received. + * @param mid CoAP transaction ID. + + * @return @c COAP_RESPONSE_OK if successful, else @c COAP_RESPONSE_FAIL which + * triggers sending a RST packet. + */ +typedef coap_response_t (*coap_response_handler_t)(coap_session_t *session, + const coap_pdu_t *sent, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Negative Acknowedge handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param sent The PDU that was transmitted. + * @param reason The reason for the NACK. + * @param mid CoAP message ID. + */ +typedef void (*coap_nack_handler_t)(coap_session_t *session, + const coap_pdu_t *sent, + const coap_nack_reason_t reason, + const coap_mid_t mid); + +/** + * Received Ping handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param received The PDU that was received. + * @param mid CoAP message ID. + */ +typedef void (*coap_ping_handler_t)(coap_session_t *session, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Received Pong handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param received The PDU that was received. + * @param mid CoAP message ID. + */ +typedef void (*coap_pong_handler_t)(coap_session_t *session, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Registers a new message handler that is called whenever a response is + * received. + * + * @param context The context to register the handler for. + * @param handler The response handler to register. + */ +void +coap_register_response_handler(coap_context_t *context, + coap_response_handler_t handler); + +/** + * Registers a new message handler that is called whenever a confirmable + * message (request or response) is dropped after all retries have been + * exhausted, or a rst message was received, or a network or TLS level + * event was received that indicates delivering the message is not possible. + * + * @param context The context to register the handler for. + * @param handler The nack handler to register. + */ +void +coap_register_nack_handler(coap_context_t *context, + coap_nack_handler_t handler); + +/** + * Registers a new message handler that is called whenever a CoAP Ping + * message is received. + * + * @param context The context to register the handler for. + * @param handler The ping handler to register. + */ +void +coap_register_ping_handler(coap_context_t *context, + coap_ping_handler_t handler); + +/** + * Registers a new message handler that is called whenever a CoAP Pong + * message is received. + * + * @param context The context to register the handler for. + * @param handler The pong handler to register. + */ +void +coap_register_pong_handler(coap_context_t *context, + coap_pong_handler_t handler); + +/** + * Registers the option type @p type with the given context object @p ctx. + * + * @param ctx The context to use. + * @param type The option type to register. + */ +void +coap_register_option(coap_context_t *ctx, uint16_t type); + +/** + * Creates a new coap_context_t object that will hold the CoAP stack status. + */ +coap_context_t *coap_new_context(const coap_address_t *listen_addr); + +/** + * Set the context's default PSK hint and/or key for a server. + * + * @param context The current coap_context_t object. + * @param hint The default PSK server hint sent to a client. If NULL, PSK + * authentication is disabled. Empty string is a valid hint. + * @param key The default PSK key. If NULL, PSK authentication will fail. + * @param key_len The default PSK key's length. If @p 0, PSK authentication will + * fail. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_context_set_psk( coap_context_t *context, const char *hint, + const uint8_t *key, size_t key_len ); + +/** + * Set the context's default PSK hint and/or key for a server. + * + * @param context The current coap_context_t object. + * @param setup_data If NULL, PSK authentication will fail. PSK + * information required. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_context_set_psk2(coap_context_t *context, + coap_dtls_spsk_t *setup_data); + +/** + * Set the context's default PKI information for a server. + * + * @param context The current coap_context_t object. + * @param setup_data If NULL, PKI authentication will fail. Certificate + * information required. + * + * @return @c 1 if successful, else @c 0. + */ +int +coap_context_set_pki(coap_context_t *context, + const coap_dtls_pki_t *setup_data); + +/** + * Set the context's default Root CA information for a client or server. + * + * @param context The current coap_context_t object. + * @param ca_file If not NULL, is the full path name of a PEM encoded + * file containing all the Root CAs to be used. + * @param ca_dir If not NULL, points to a directory containing PEM + * encoded files containing all the Root CAs to be used. + * + * @return @c 1 if successful, else @c 0. + */ +int +coap_context_set_pki_root_cas(coap_context_t *context, + const char *ca_file, + const char *ca_dir); + +/** + * Set the context keepalive timer for sessions. + * A keepalive message will be sent after if a session has been inactive, + * i.e. no packet sent or received, for the given number of seconds. + * For unreliable protocols, a CoAP Empty message will be sent. If a + * CoAP RST is not received, the CoAP Empty messages will get resent based + * on the Confirmable retry parameters until there is a failure timeout, + * at which point the session will be considered as disconnected. + * For reliable protocols, a CoAP PING message will be sent. If a CoAP PONG + * has not been received before the next PING is due to be sent, the session + * will be considered as disconnected. + * + * @param context The coap_context_t object. + * @param seconds Number of seconds for the inactivity timer, or zero + * to disable CoAP-level keepalive messages. + */ +void coap_context_set_keepalive(coap_context_t *context, unsigned int seconds); + +/** + * Get the libcoap internal file descriptor for using in an application's + * select() or returned as an event in an application's epoll_wait() call. + * + * @param context The coap_context_t object. + * + * @return The libcoap file descriptor or @c -1 if epoll is not available. + */ +int coap_context_get_coap_fd(const coap_context_t *context); + +/** + * Set the maximum idle sessions count. The number of server sessions that + * are currently not in use. If this number is exceeded, the least recently + * used server session is completely removed. + * 0 (the default) means that the number is not monitored. + * + * @param context The coap_context_t object. + * @param max_idle_sessions The maximum idle session count. + */ +void +coap_context_set_max_idle_sessions(coap_context_t *context, + unsigned int max_idle_sessions); + +/** + * Get the maximum idle sessions count. + * + * @param context The coap_context_t object. + * + * @return The count of max idle sessions. + */ +unsigned int +coap_context_get_max_idle_sessions(const coap_context_t *context); + +/** + * Set the session timeout value. The number of seconds of inactivity after + * which an unused server session will be closed. + * 0 means use default (300 secs). + * + * @param context The coap_context_t object. + * @param session_timeout The session timeout value. + */ +void +coap_context_set_session_timeout(coap_context_t *context, + unsigned int session_timeout); + +/** + * Get the session timeout value + * + * @param context The coap_context_t object. + * + * @return The session timeout value. + */ +unsigned int +coap_context_get_session_timeout(const coap_context_t *context); + +/** + * Set the CSM timeout value. The number of seconds to wait for a (TCP) CSM + * negotiation response from the peer. + * 0 (the default) means use wait forever. + * + * @param context The coap_context_t object. + * @param csm_tmeout The CSM timeout value. + */ +void +coap_context_set_csm_timeout(coap_context_t *context, + unsigned int csm_tmeout); + +/** + * Get the CSM timeout value + * + * @param context The coap_context_t object. + * + * @return The CSM timeout value. + */ +unsigned int +coap_context_get_csm_timeout(const coap_context_t *context); + +/** + * Set the maximum number of sessions in (D)TLS handshake value. If this number + * is exceeded, the least recently used server session in handshake is + * completely removed. + * 0 (the default) means that the number is not monitored. + * + * @param context The coap_context_t object. + * @param max_handshake_sessions The maximum number of sessions in handshake. + */ +void +coap_context_set_max_handshake_sessions(coap_context_t *context, + unsigned int max_handshake_sessions); + +/** + * Get the session timeout value + * + * @param context The coap_context_t object. + * + * @return The maximim number of sessions in (D)TLS handshake value. + */ +unsigned int +coap_context_get_max_handshake_sessions(const coap_context_t *context); + +/** + * Returns a new message id and updates @p session->tx_mid accordingly. The + * message id is returned in network byte order to make it easier to read in + * tracing tools. + * + * @param session The current coap_session_t object. + * + * @return Incremented message id in network byte order. + */ +uint16_t coap_new_message_id(coap_session_t *session); + +/** + * CoAP stack context must be released with coap_free_context(). This function + * clears all entries from the receive queue and send queue and deletes the + * resources that have been registered with @p context, and frees the attached + * endpoints. + * + * @param context The current coap_context_t object to free off. + */ +void coap_free_context(coap_context_t *context); + +/** + * Stores @p data with the given CoAP context. This function + * overwrites any value that has previously been stored with @p + * context. + * + * @param context The CoAP context. + * @param data The data to store with wih the context. Note that this data + * must be valid during the lifetime of @p context. + */ +void coap_set_app_data(coap_context_t *context, void *data); + +/** + * Returns any application-specific data that has been stored with @p + * context using the function coap_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param context The CoAP context. + * + * @return The data previously stored or @c NULL if not data stored. + */ +void *coap_get_app_data(const coap_context_t *context); + +/** + * Creates a new ACK PDU with specified error @p code. The options specified by + * the filter expression @p opts will be copied from the original request + * contained in @p request. Unless @c SHORT_ERROR_RESPONSE was defined at build + * time, the textual reason phrase for @p code will be added as payload, with + * Content-Type @c 0. + * This function returns a pointer to the new response message, or @c NULL on + * error. The storage allocated for the new message must be released with + * coap_free(). + * + * @param request Specification of the received (confirmable) request. + * @param code The error code to set. + * @param opts An option filter that specifies which options to copy from + * the original request in @p node. + * + * @return A pointer to the new message or @c NULL on error. + */ +coap_pdu_t *coap_new_error_response(const coap_pdu_t *request, + coap_pdu_code_t code, + coap_opt_filter_t *opts); + +/** + * Sends an error response with code @p code for request @p request to @p dst. + * @p opts will be passed to coap_new_error_response() to copy marked options + * from the request. This function returns the message id if the message was + * sent, or @c COAP_INVALID_MID otherwise. + * + * @param session The CoAP session. + * @param request The original request to respond to. + * @param code The response code. + * @param opts A filter that specifies the options to copy from the + * @p request. + * + * @return The message id if the message was sent, or @c + * COAP_INVALID_MID otherwise. + */ +coap_mid_t coap_send_error(coap_session_t *session, + const coap_pdu_t *request, + coap_pdu_code_t code, + coap_opt_filter_t *opts); + +/** + * Helper function to create and send a message with @p type (usually ACK or + * RST). This function returns @c COAP_INVALID_MID when the message was not + * sent, a valid transaction id otherwise. + * + * @param session The CoAP session. + * @param request The request that should be responded to. + * @param type Which type to set. + * @return message id on success or @c COAP_INVALID_MID + * otherwise. + */ +coap_mid_t +coap_send_message_type(coap_session_t *session, const coap_pdu_t *request, + coap_pdu_type_t type); + +/** + * Sends an ACK message with code @c 0 for the specified @p request to @p dst. + * This function returns the corresponding message id if the message was + * sent or @c COAP_INVALID_MID on error. + * + * @param session The CoAP session. + * @param request The request to be acknowledged. + * + * @return The message id if ACK was sent or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_send_ack(coap_session_t *session, const coap_pdu_t *request); + +/** + * Sends an RST message with code @c 0 for the specified @p request to @p dst. + * This function returns the corresponding message id if the message was + * sent or @c COAP_INVALID_MID on error. + * + * @param session The CoAP session. + * @param request The request to be reset. + * + * @return The message id if RST was sent or @c + * COAP_INVALID_MID on error. + */ +COAP_STATIC_INLINE coap_mid_t +coap_send_rst(coap_session_t *session, const coap_pdu_t *request) { + return coap_send_message_type(session, request, COAP_MESSAGE_RST); +} + +/** +* Sends a CoAP message to given peer. The memory that is +* allocated for the pdu will be released by coap_send(). +* The caller must not use the pdu after calling coap_send(). +* +* @param session The CoAP session. +* @param pdu The CoAP PDU to send. +* +* @return The message id of the sent message or @c +* COAP_INVALID_MID on error. +*/ +coap_mid_t coap_send( coap_session_t *session, coap_pdu_t *pdu ); + +#define coap_send_large(session, pdu) coap_send(session, pdu) + +/** + * Invokes the event handler of @p context for the given @p event and + * @p data. + * + * @param context The CoAP context whose event handler is to be called. + * @param event The event to deliver. + * @param session The session related to @p event. + * @return The result from the associated event handler or 0 if none was + * registered. + */ +int coap_handle_event(coap_context_t *context, + coap_event_t event, + coap_session_t *session); +/** + * Returns 1 if there are no messages to send or to dispatch in the context's + * queues. */ +int coap_can_exit(coap_context_t *context); + +/** + * Returns the current value of an internal tick counter. The counter counts \c + * COAP_TICKS_PER_SECOND ticks every second. + */ +void coap_ticks(coap_tick_t *); + +/** + * Function interface for joining a multicast group for listening for the + * currently defined endpoints that are UDP. + * + * @param ctx The current context. + * @param groupname The name of the group that is to be joined for listening. + * @param ifname Network interface to join the group on, or NULL if first + * appropriate interface is to be chosen by the O/S. + * + * @return 0 on success, -1 on error + */ +int +coap_join_mcast_group_intf(coap_context_t *ctx, const char *groupname, + const char *ifname); + +#define coap_join_mcast_group(ctx, groupname) \ + (coap_join_mcast_group_intf(ctx, groupname, NULL)) + +/** + * Function interface for defining the hop count (ttl) for sending + * multicast traffic + * + * @param session The current contexsion. + * @param hops The number of hops (ttl) to use before the multicast + * packet expires. + * + * @return 1 on success, 0 on error + */ +int +coap_mcast_set_hops(coap_session_t *session, size_t hops); + +/**@}*/ + +/** + * @defgroup app_io Application I/O Handling + * API functions for Application Input / Output + * @{ + */ + +#define COAP_IO_WAIT 0 +#define COAP_IO_NO_WAIT ((uint32_t)-1) + +/** + * The main I/O processing function. All pending network I/O is completed, + * and then optionally waits for the next input packet. + * + * This internally calls coap_io_prepare_io(), then select() for the appropriate + * sockets, updates COAP_SOCKET_CAN_xxx where appropriate and then calls + * coap_io_do_io() before returning with the time spent in the function. + * + * Alternatively, if libcoap is compiled with epoll support, this internally + * calls coap_io_prepare_epoll(), then epoll_wait() for waiting for any file + * descriptors that have (internally) been set up with epoll_ctl() and + * finally coap_io_do_epoll() before returning with the time spent in the + * function. + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * + * @return Number of milliseconds spent in function or @c -1 if there was + * an error + */ +int coap_io_process(coap_context_t *ctx, uint32_t timeout_ms); + +#ifndef RIOT_VERSION +/** + * The main message processing loop with additional fds for internal select. + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * @param nfds The maximum FD set in readfds, writefds or exceptfds + * plus one, + * @param readfds Read FDs to additionally check for in internal select() + * or NULL if not required. + * @param writefds Write FDs to additionally check for in internal select() + * or NULL if not required. + * @param exceptfds Except FDs to additionally check for in internal select() + * or NULL if not required. + * + * + * @return Number of milliseconds spent in coap_io_process_with_fds, or @c -1 + * if there was an error. If defined, readfds, writefds, exceptfds + * are updated as returned by the internal select() call. + */ +int coap_io_process_with_fds(coap_context_t *ctx, uint32_t timeout_ms, + int nfds, fd_set *readfds, fd_set *writefds, + fd_set *exceptfds); +#endif /* !RIOT_VERSION */ + +/**@}*/ + +/** + * @defgroup app_io_internal Application I/O Handling (Internal) + * Internal API functions for Application Input / Output + * @{ + */ + +/** +* Iterates through all the coap_socket_t structures embedded in endpoints or +* sessions associated with the @p ctx to determine which are wanting any +* read, write, accept or connect I/O (COAP_SOCKET_WANT_xxx is set). If set, +* the coap_socket_t is added to the @p sockets. +* +* Any now timed out delayed packet is transmitted, along with any packets +* associated with requested observable response. +* +* In addition, it returns when the next expected I/O is expected to take place +* (e.g. a packet retransmit). +* +* Prior to calling coap_io_do_io(), the @p sockets must be tested to see +* if any of the COAP_SOCKET_WANT_xxx have the appropriate information and if +* so, COAP_SOCKET_CAN_xxx is set. This typically will be done after using a +* select() call. +* +* Note: If epoll support is compiled into libcoap, coap_io_prepare_epoll() must +* be used instead of coap_io_prepare_io(). +* +* Internal function. +* +* @param ctx The CoAP context +* @param sockets Array of socket descriptors, filled on output +* @param max_sockets Size of socket array. +* @param num_sockets Pointer to the number of valid entries in the socket +* arrays on output. +* @param now Current time. +* +* @return timeout Maxmimum number of milliseconds that can be used by a +* select() to wait for network events or 0 if wait should be +* forever. +*/ +unsigned int +coap_io_prepare_io(coap_context_t *ctx, + coap_socket_t *sockets[], + unsigned int max_sockets, + unsigned int *num_sockets, + coap_tick_t now +); + +/** + * Processes any outstanding read, write, accept or connect I/O as indicated + * in the coap_socket_t structures (COAP_SOCKET_CAN_xxx set) embedded in + * endpoints or sessions associated with @p ctx. + * + * Note: If epoll support is compiled into libcoap, coap_io_do_epoll() must + * be used instead of coap_io_do_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time + */ +void coap_io_do_io(coap_context_t *ctx, coap_tick_t now); + +/** + * Any now timed out delayed packet is transmitted, along with any packets + * associated with requested observable response. + * + * In addition, it returns when the next expected I/O is expected to take place + * (e.g. a packet retransmit). + * + * Note: If epoll support is compiled into libcoap, coap_io_prepare_epoll() must + * be used instead of coap_io_prepare_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time. + * + * @return timeout Maxmimum number of milliseconds that can be used by a + * epoll_wait() to wait for network events or 0 if wait should be + * forever. + */ +unsigned int +coap_io_prepare_epoll(coap_context_t *ctx, coap_tick_t now); + +struct epoll_event; + +/** + * Process all the epoll events + * + * Note: If epoll support is compiled into libcoap, coap_io_do_epoll() must + * be used instead of coap_io_do_io(). + * + * Internal function + * + * @param ctx The current CoAP context. + * @param events The list of events returned from an epoll_wait() call. + * @param nevents The number of events. + * + */ +void coap_io_do_epoll(coap_context_t *ctx, struct epoll_event* events, + size_t nevents); + +/**@}*/ + +/** + * @deprecated Use coap_io_process() instead. + * + * This function just calls coap_io_process(). + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * + * @return Number of milliseconds spent in function or @c -1 if there was + * an error + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_run_once(coap_context_t *ctx, uint32_t timeout_ms) +{ + return coap_io_process(ctx, timeout_ms); +} + +/** +* @deprecated Use coap_io_prepare_io() instead. +* +* This function just calls coap_io_prepare_io(). +* +* Internal function. +* +* @param ctx The CoAP context +* @param sockets Array of socket descriptors, filled on output +* @param max_sockets Size of socket array. +* @param num_sockets Pointer to the number of valid entries in the socket +* arrays on output. +* @param now Current time. +* +* @return timeout Maxmimum number of milliseconds that can be used by a +* select() to wait for network events or 0 if wait should be +* forever. +*/ +COAP_STATIC_INLINE COAP_DEPRECATED unsigned int +coap_write(coap_context_t *ctx, + coap_socket_t *sockets[], + unsigned int max_sockets, + unsigned int *num_sockets, + coap_tick_t now +) { + return coap_io_prepare_io(ctx, sockets, max_sockets, num_sockets, now); +} + +/** + * @deprecated Use coap_io_do_io() instead. + * + * This function just calls coap_io_do_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time + */ +COAP_STATIC_INLINE COAP_DEPRECATED void +coap_read(coap_context_t *ctx, coap_tick_t now +) { + coap_io_do_io(ctx, now); +} + +/* Old definitions which may be hanging around in old code - be helpful! */ +#define COAP_RUN_NONBLOCK COAP_RUN_NONBLOCK_deprecated_use_COAP_IO_NO_WAIT +#define COAP_RUN_BLOCK COAP_RUN_BLOCK_deprecated_use_COAP_IO_WAIT + +#endif /* COAP_NET_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/option.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/option.h new file mode 100644 index 00000000000..c01e8f6688b --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/option.h @@ -0,0 +1,439 @@ +/* + * option.h -- helpers for handling options in CoAP PDUs + * + * Copyright (C) 2010-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file option.h + * @brief Helpers for handling options in CoAP PDUs + */ + +#ifndef COAP_OPTION_H_ +#define COAP_OPTION_H_ + +typedef uint16_t coap_option_num_t; + +/** + * Use byte-oriented access methods here because sliding a complex struct + * coap_opt_t over the data buffer may cause bus error on certain platforms. + */ +typedef uint8_t coap_opt_t; +#define PCHAR(p) ((coap_opt_t *)(p)) + +/** + * Representation of CoAP options. + */ +typedef struct { + uint16_t delta; + size_t length; + const uint8_t *value; +} coap_option_t; + +/** + * Parses the option pointed to by @p opt into @p result. This function returns + * the number of bytes that have been parsed, or @c 0 on error. An error is + * signaled when illegal delta or length values are encountered or when option + * parsing would result in reading past the option (i.e. beyond opt + length). + * + * @param opt The beginning of the option to parse. + * @param length The maximum length of @p opt. + * @param result A pointer to the coap_option_t structure that is filled with + * actual values iff coap_opt_parse() > 0. + * @return The number of bytes parsed or @c 0 on error. + */ +size_t coap_opt_parse(const coap_opt_t *opt, + size_t length, + coap_option_t *result); + +/** + * Returns the size of the given option, taking into account a possible option + * jump. + * + * @param opt An option jump or the beginning of the option. + * @return The number of bytes between @p opt and the end of the option + * starting at @p opt. In case of an error, this function returns + * @c 0 as options need at least one byte storage space. + */ +size_t coap_opt_size(const coap_opt_t *opt); + +/** + * @defgroup opt_filter Option Filters + * API functions for access option filters + * @{ + */ + +/** + * The number of option types below 256 that can be stored in an + * option filter. COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be + * at most 16. Each coap_option_filter_t object reserves + * ((COAP_OPT_FILTER_SHORT + 1) / 2) * 2 bytes for short options. + */ +#define COAP_OPT_FILTER_SHORT 6 + +/** + * The number of option types above 255 that can be stored in an + * option filter. COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be + * at most 16. Each coap_option_filter_t object reserves + * COAP_OPT_FILTER_LONG * 2 bytes for short options. + */ +#define COAP_OPT_FILTER_LONG 2 + +/* Ensure that COAP_OPT_FILTER_SHORT and COAP_OPT_FILTER_LONG are set + * correctly. */ +#if (COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG > 16) +#error COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be less or equal 16 +#endif /* (COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG > 16) */ + +/* + * mask contains a bit vector that indicates which fields in the long_opts[] + * and subsequent short_opts[] are used. The first COAP_OPT_FILTER_LONG bits + * correspond to the long option types that are stored in long_opts[] + * elements. The next COAP_OPT_FILTER_SHORT bits correspond to the short + * option types that are stored in short_opts[]. + */ +typedef struct coap_opt_filter_t { + uint16_t mask; + uint16_t long_opts[COAP_OPT_FILTER_LONG]; + uint8_t short_opts[COAP_OPT_FILTER_SHORT]; +} coap_opt_filter_t; + +/** Pre-defined filter that includes all options. */ +#define COAP_OPT_ALL NULL + +/** + * Clears filter @p filter. + * + * @param filter The filter to clear. + */ +void +coap_option_filter_clear(coap_opt_filter_t *filter); + +/** + * Sets the corresponding entry for @p number in @p filter. This + * function returns @c 1 if bit was set or @c 0 on error (i.e. when + * the given number does not fit in the filter). + * + * @param filter The filter object to change. + * @param number The option number for which the bit should be set. + * + * @return @c 1 if bit was set, @c 0 otherwise. + */ +int coap_option_filter_set(coap_opt_filter_t *filter, coap_option_num_t number); + +/** + * Clears the corresponding entry for @p number in @p filter. This + * function returns @c 1 if bit was set or @c 0 on error (i.e. when + * the given number does not fit in the filter). + * + * @param filter The filter object to change. + * @param number The option number that should be cleared from the filter. + * + * @return @c 1 if bit was set, @c 0 otherwise. + */ +int coap_option_filter_unset(coap_opt_filter_t *filter, + coap_option_num_t number); + +/** + * Checks if @p number is contained in @p filter. This function returns + * @c 1 if found, @c 0 if not, or @c -1 on error (i.e. when the given + * number does not fit in the filter). + * + * @param filter The filter object to search. + * @param number The option number to search for. + * + * @return @c 1 if @p number was found, @c 0 otherwise, or @c -1 on error. + */ +int coap_option_filter_get(coap_opt_filter_t *filter, coap_option_num_t number); + +/** + * Iterator to run through PDU options. This object must be + * initialized with coap_option_iterator_init(). Call + * coap_option_next() to walk through the list of options until + * coap_option_next() returns @c NULL. + * + * @code + * coap_opt_t *option; + * coap_opt_iterator_t opt_iter; + * coap_option_iterator_init(pdu, &opt_iter, COAP_OPT_ALL); + * + * while ((option = coap_option_next(&opt_iter))) { + * ... do something with option ... + * } + * @endcode + */ +typedef struct { + size_t length; /**< remaining length of PDU */ + coap_option_num_t number; /**< decoded option number */ + unsigned int bad:1; /**< iterator object is ok if not set */ + unsigned int filtered:1; /**< denotes whether or not filter is used */ + coap_opt_t *next_option; /**< pointer to the unparsed next option */ + coap_opt_filter_t filter; /**< option filter */ +} coap_opt_iterator_t; + +/** + * Initializes the given option iterator @p oi to point to the beginning of the + * @p pdu's option list. This function returns @p oi on success, @c NULL + * otherwise (i.e. when no options exist). Note that a length check on the + * option list must be performed before coap_option_iterator_init() is called. + * + * @param pdu The PDU the options of which should be walked through. + * @param oi An iterator object that will be initilized. + * @param filter An optional option number filter. + * With @p number != @c COAP_OPT_ALL, coap_option_next() + * will return only options matching this bitmask. + * Fence-post options @c 14, @c 28, @c 42, ... are always + * skipped. + * + * @return The iterator object @p oi on success, @c NULL otherwise. + */ +coap_opt_iterator_t *coap_option_iterator_init(const coap_pdu_t *pdu, + coap_opt_iterator_t *oi, + const coap_opt_filter_t *filter); + +/** + * Updates the iterator @p oi to point to the next option. This function returns + * a pointer to that option or @c NULL if no more options exist. The contents of + * @p oi will be updated. In particular, @c oi->n specifies the current option's + * ordinal number (counted from @c 1), @c oi->number is the option's number + * value, and @c oi->option points to the beginning of the current option + * itself. When * advanced past the last option, @c oi->option will be @c NULL. + * + * Note that options are skipped whose corresponding bits in the filter + * specified with coap_option_iterator_init() are @c 0. Options with numbers + * that do not fit in this filter hence will always be returned. + * + * @param oi The option iterator to update. + * + * @return The next option or @c NULL if no more options exist. + */ +coap_opt_t *coap_option_next(coap_opt_iterator_t *oi); + +/** + * Retrieves the first option of number @p number from @p pdu. @p oi must + * point to a coap_opt_iterator_t object that will be initialized by this + * function to filter only options with number @p number. This function returns + * the first option with this number, or @c NULL if not found. + * + * @param pdu The PDU to parse for options. + * @param number The option number to search for. + * @param oi An iterator object to use. + * + * @return A pointer to the first option of number @p number, or @c NULL if + * not found. + */ +coap_opt_t *coap_check_option(const coap_pdu_t *pdu, + coap_option_num_t number, + coap_opt_iterator_t *oi); + +/** + * Encodes the given delta and length values into @p opt. This function returns + * the number of bytes that were required to encode @p delta and @p length or @c + * 0 on error. Note that the result indicates by how many bytes @p opt must be + * advanced to encode the option value. + * + * @param opt The option buffer space where @p delta and @p length are + * written. + * @param maxlen The maximum length of @p opt. + * @param delta The actual delta value to encode. + * @param length The actual length value to encode. + * + * @return The number of bytes used or @c 0 on error. + */ +size_t coap_opt_setheader(coap_opt_t *opt, + size_t maxlen, + uint16_t delta, + size_t length); + +/** + * Compute storage bytes needed for an option with given @p delta and + * @p length + * + * @param delta The option delta. + * @param length The option length. + * + * @return The number of bytes required to encode this option. + */ +size_t coap_opt_encode_size(uint16_t delta, size_t length); + +/** + * Encodes option with given @p delta into @p opt. This function returns the + * number of bytes written to @p opt or @c 0 on error. This happens especially + * when @p opt does not provide sufficient space to store the option value, + * delta, and option jumps when required. + * + * @param opt The option buffer space where @p val is written. + * @param n Maximum length of @p opt. + * @param delta The option delta. + * @param val The option value to copy into @p opt. + * @param length The actual length of @p val. + * + * @return The number of bytes that have been written to @p opt or @c 0 on + * error. The return value will always be less than @p n. + */ +size_t coap_opt_encode(coap_opt_t *opt, + size_t n, + uint16_t delta, + const uint8_t *val, + size_t length); + +/** + * Returns the length of the given option. @p opt must point to an option jump + * or the beginning of the option. This function returns @c 0 when @p opt is not + * an option or the actual length of @p opt (which can be @c 0 as well). + * + * @note {The rationale for using @c 0 in case of an error is that in most + * contexts, the result of this function is used to skip the next + * coap_opt_length() bytes.} + * + * @param opt The option whose length should be returned. + * + * @return The option's length or @c 0 when undefined. + */ +uint32_t coap_opt_length(const coap_opt_t *opt); + +/** + * Returns a pointer to the value of the given option. @p opt must point to an + * option jump or the beginning of the option. This function returns @c NULL if + * @p opt is not a valid option. + * + * @param opt The option whose value should be returned. + * + * @return A pointer to the option value or @c NULL on error. + */ +const uint8_t *coap_opt_value(const coap_opt_t *opt); + +/** + * Representation of chained list of CoAP options to install. + * + * @code + * coap_optlist_t *optlist_chain = NULL; + * coap_pdu_t *pdu = coap_new_pdu(session); + * + * ... other set up code ... + * coap_insert_optlist(&optlist_chain, coap_new_optlist(COAP_OPTION_OBSERVE, + * COAP_OBSERVE_ESTABLISH, NULL)); + * + * coap_add_optlist_pdu(pdu, &optlist_chain); + * ... other code ... + * coap_delete_optlist(optlist_chain); + * @endcode + */ +typedef struct coap_optlist_t { + struct coap_optlist_t *next; /**< next entry in the optlist chain */ + uint16_t number; /**< the option number (no delta coding) */ + size_t length; /**< the option value length */ + uint8_t *data; /**< the option data */ +} coap_optlist_t; + +/** + * Create a new optlist entry. + * + * Note: Where possible, the option data needs to be stripped of leading zeros + * (big endian) to reduce the amount of data needed in the PDU, as well as in + * some cases the maximum data size of an opton can be exceeded if not stripped + * and hence be illegal. This is done by using coap_encode_var_safe() or + * coap_encode_var_safe8(). + * + * @param number The option number (COAP_OPTION_*) + * @param length The option length + * @param data The option value data + * + * @return A pointer to the new optlist entry, or @c NULL if error + */ +coap_optlist_t *coap_new_optlist(uint16_t number, + size_t length, + const uint8_t *data); + +/** + * The current optlist of @p optlist_chain is first sorted (as per RFC7272 + * ordering requirements) and then added to the @p pdu. + * + * @param pdu The pdu to add the options to from the chain list + * @param optlist_chain The chained list of optlist to add to the pdu + * + * @return @c 1 if succesful or @c 0 if failure; + */ +int coap_add_optlist_pdu(coap_pdu_t *pdu, coap_optlist_t** optlist_chain); + +/** + * Adds @p optlist to the given @p optlist_chain. The optlist_chain variable + * be set to NULL before the initial call to coap_insert_optlist(). + * The optlist_chain will need to be deleted using coap_delete_optlist() + * when no longer required. + * + * @param optlist_chain The chain to add optlist to + * @param optlist The optlist to add to the queue + * + * @return @c 1 if successful, @c 0 otherwise. + */ +int coap_insert_optlist(coap_optlist_t **optlist_chain, + coap_optlist_t *optlist); + +/** + * Removes all entries from the @p optlist_chain, freeing off their + * memory usage. + * + * @param optlist_chain The optlist chain to remove all the entries from + */ +void coap_delete_optlist(coap_optlist_t *optlist_chain); + +/** @} */ + +/** + * Sets the corresponding bit for @p type in @p filter. This function returns @c + * 1 if bit was set or @c -1 on error (i.e. when the given type does not fit in + * the filter). + * + * @deprecated Use coap_option_filter_set() instead. + * + * @param filter The filter object to change. + * @param type The type for which the bit should be set. + * + * @return @c 1 if bit was set, @c -1 otherwise. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_setb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_set(filter, type) ? 1 : -1; +} + +/** + * Clears the corresponding bit for @p type in @p filter. This function returns + * @c 1 if bit was cleared or @c -1 on error (i.e. when the given type does not + * fit in the filter). + * + * @deprecated Use coap_option_filter_unset() instead. + * + * @param filter The filter object to change. + * @param type The type for which the bit should be cleared. + * + * @return @c 1 if bit was set, @c -1 otherwise. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_clrb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_unset(filter, type) ? 1 : -1; +} + +/** + * Gets the corresponding bit for @p type in @p filter. This function returns @c + * 1 if the bit is set @c 0 if not, or @c -1 on error (i.e. when the given type + * does not fit in the filter). + * + * @deprecated Use coap_option_filter_get() instead. + * + * @param filter The filter object to read bit from. + * @param type The type for which the bit should be read. + * + * @return @c 1 if bit was set, @c 0 if not, @c -1 on error. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_getb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_get(filter, type); +} + +#endif /* COAP_OPTION_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/pdu.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/pdu.h new file mode 100644 index 00000000000..a22869b69ed --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/pdu.h @@ -0,0 +1,572 @@ +/* + * pdu.h -- CoAP message structure + * + * Copyright (C) 2010-2014 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file pdu.h + * @brief Pre-defined constants that reflect defaults for CoAP + */ + +#ifndef COAP_PDU_H_ +#define COAP_PDU_H_ + +#include "uri.h" +#include "option.h" + +#ifdef WITH_LWIP +#include +#endif + +#include + +/** + * @defgroup pdu PDU + * API functions for PDUs + * @{ + */ + +#define COAP_DEFAULT_PORT 5683 /* CoAP default UDP/TCP port */ +#define COAPS_DEFAULT_PORT 5684 /* CoAP default UDP/TCP port for secure transmission */ +#define COAP_DEFAULT_MAX_AGE 60 /* default maximum object lifetime in seconds */ +#ifndef COAP_DEFAULT_MTU +#define COAP_DEFAULT_MTU 1152 +#endif /* COAP_DEFAULT_MTU */ + +#ifndef COAP_DEFAULT_HOP_LIMIT +#define COAP_DEFAULT_HOP_LIMIT 16 +#endif /* COAP_DEFAULT_HOP_LIMIT */ + +#define COAP_DEFAULT_SCHEME "coap" /* the default scheme for CoAP URIs */ + +/** well-known resources URI */ +#define COAP_DEFAULT_URI_WELLKNOWN ".well-known/core" + +/* CoAP message types */ + +/** + * CoAP PDU message type definitions + */ +typedef enum coap_pdu_type_t { + COAP_MESSAGE_CON, /* 0 confirmable message (requires ACK/RST) */ + COAP_MESSAGE_NON, /* 1 non-confirmable message (one-shot message) */ + COAP_MESSAGE_ACK, /* 2 used to acknowledge confirmable messages */ + COAP_MESSAGE_RST /* 3 indicates error in received messages */ +} coap_pdu_type_t; + +/** + * CoAP PDU Request methods + */ +typedef enum coap_request_t { + COAP_REQUEST_GET = 1, + COAP_REQUEST_POST, /* 2 */ + COAP_REQUEST_PUT, /* 3 */ + COAP_REQUEST_DELETE, /* 4 */ + COAP_REQUEST_FETCH, /* 5 RFC 8132 */ + COAP_REQUEST_PATCH, /* 6 RFC 8132 */ + COAP_REQUEST_IPATCH, /* 7 RFC 8132 */ +} coap_request_t; + +/* + * CoAP option numbers (be sure to update coap_option_check_critical() and + * coap_add_option() when adding options + */ + +/* + * The C, U, and N flags indicate the properties + * Critical, Unsafe, and NoCacheKey, respectively. + * If U is set, then N has no meaning as per + * https://tools.ietf.org/html/rfc7252#section-5.10 + * and is set to a -. + * + * Separately, R is for the options that can be repeated + * + * The least significant byte of the option is set as followed + * as per https://tools.ietf.org/html/rfc7252#section-5.4.6 + * + * 0 1 2 3 4 5 6 7 + * --+---+---+---+---+---+---+---+ + * | NoCacheKey| U | C | + * --+---+---+---+---+---+---+---+ + * + * https://tools.ietf.org/html/rfc8613#section-4 goes on to define E, I and U + * properties Encrypted and Integrity Protected, Integrity Protected Only, and + * Unprotected respectively. Integrity Protected Only is not currently used. + * + * An Option is tagged with CUNREIU with any of the letters replaced with _ if + * not set, or - for N if U is set (see above) for aiding understanding of the + * Option. + */ + +#define COAP_OPTION_IF_MATCH 1 /* C__RE__, opaque, 0-8 B, RFC7252 */ +#define COAP_OPTION_URI_HOST 3 /* CU-___U, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_ETAG 4 /* ___RE__, opaque, 1-8 B, RFC7252 */ +#define COAP_OPTION_IF_NONE_MATCH 5 /* C___E__, empty, 0 B, RFC7252 */ +#define COAP_OPTION_OBSERVE 6 /* _U-_E_U, empty/uint,0/0-3 B, RFC7641 */ +#define COAP_OPTION_URI_PORT 7 /* CU-___U, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_LOCATION_PATH 8 /* ___RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_OSCORE 9 /* C_____U, *, 0-255 B, RFC8613 */ +#define COAP_OPTION_URI_PATH 11 /* CU-RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_CONTENT_FORMAT 12 /* ____E__, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_CONTENT_TYPE COAP_OPTION_CONTENT_FORMAT +/* COAP_OPTION_MAXAGE default 60 seconds if not set */ +#define COAP_OPTION_MAXAGE 14 /* _U-_E_U, uint, 0-4 B, RFC7252 */ +#define COAP_OPTION_URI_QUERY 15 /* CU-RE__, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_HOP_LIMIT 16 /* ______U, uint, 1 B, RFC8768 */ +#define COAP_OPTION_ACCEPT 17 /* C___E__, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_LOCATION_QUERY 20 /* ___RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_BLOCK2 23 /* CU-_E_U, uint, 0-3 B, RFC7959 */ +#define COAP_OPTION_BLOCK1 27 /* CU-_E_U, uint, 0-3 B, RFC7959 */ +#define COAP_OPTION_SIZE2 28 /* __N_E_U, uint, 0-4 B, RFC7959 */ +#define COAP_OPTION_PROXY_URI 35 /* CU-___U, String, 1-1034 B, RFC7252 */ +#define COAP_OPTION_PROXY_SCHEME 39 /* CU-___U, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_SIZE1 60 /* __N_E_U, uint, 0-4 B, RFC7252 */ +#define COAP_OPTION_NORESPONSE 258 /* _U-_E_U, uint, 0-1 B, RFC7967 */ + +#define COAP_MAX_OPT 65535 /**< the highest option number we know */ + +/* CoAP result codes (HTTP-Code / 100 * 40 + HTTP-Code % 100) */ + +/* As of draft-ietf-core-coap-04, response codes are encoded to base + * 32, i.e. the three upper bits determine the response class while + * the remaining five fine-grained information specific to that class. + */ +#define COAP_RESPONSE_CODE(N) (((N)/100 << 5) | (N)%100) + +/* Determines the class of response code C */ +#define COAP_RESPONSE_CLASS(C) (((C) >> 5) & 0xFF) + +#ifndef SHORT_ERROR_RESPONSE +/** + * Returns a human-readable response phrase for the specified CoAP response @p + * code. This function returns @c NULL if not found. + * + * @param code The response code for which the literal phrase should be + * retrieved. + * + * @return A zero-terminated string describing the error, or @c NULL if not + * found. + */ +const char *coap_response_phrase(unsigned char code); + +#define COAP_ERROR_PHRASE_LENGTH 32 /**< maximum length of error phrase */ + +#else +#define coap_response_phrase(x) ((char *)NULL) + +#define COAP_ERROR_PHRASE_LENGTH 0 /**< maximum length of error phrase */ +#endif /* SHORT_ERROR_RESPONSE */ + +#define COAP_SIGNALING_CODE(N) (((N)/100 << 5) | (N)%100) + +typedef enum coap_pdu_signaling_proto_t { + COAP_SIGNALING_CSM = COAP_SIGNALING_CODE(701), + COAP_SIGNALING_PING = COAP_SIGNALING_CODE(702), + COAP_SIGNALING_PONG = COAP_SIGNALING_CODE(703), + COAP_SIGNALING_RELEASE = COAP_SIGNALING_CODE(704), + COAP_SIGNALING_ABORT = COAP_SIGNALING_CODE(705), +} coap_pdu_signaling_proto_t; + +/* Applies to COAP_SIGNALING_CSM */ +#define COAP_SIGNALING_OPTION_MAX_MESSAGE_SIZE 2 +#define COAP_SIGNALING_OPTION_BLOCK_WISE_TRANSFER 4 +/* Applies to COAP_SIGNALING_PING / COAP_SIGNALING_PONG */ +#define COAP_SIGNALING_OPTION_CUSTODY 2 +/* Applies to COAP_SIGNALING_RELEASE */ +#define COAP_SIGNALING_OPTION_ALTERNATIVE_ADDRESS 2 +#define COAP_SIGNALING_OPTION_HOLD_OFF 4 +/* Applies to COAP_SIGNALING_ABORT */ +#define COAP_SIGNALING_OPTION_BAD_CSM_OPTION 2 + +/* CoAP media type encoding */ + +#define COAP_MEDIATYPE_TEXT_PLAIN 0 /* text/plain (UTF-8) */ +#define COAP_MEDIATYPE_APPLICATION_LINK_FORMAT 40 /* application/link-format */ +#define COAP_MEDIATYPE_APPLICATION_XML 41 /* application/xml */ +#define COAP_MEDIATYPE_APPLICATION_OCTET_STREAM 42 /* application/octet-stream */ +#define COAP_MEDIATYPE_APPLICATION_RDF_XML 43 /* application/rdf+xml */ +#define COAP_MEDIATYPE_APPLICATION_EXI 47 /* application/exi */ +#define COAP_MEDIATYPE_APPLICATION_JSON 50 /* application/json */ +#define COAP_MEDIATYPE_APPLICATION_CBOR 60 /* application/cbor */ +#define COAP_MEDIATYPE_APPLICATION_CWT 61 /* application/cwt, RFC 8392 */ + +/* Content formats from RFC 8152 */ +#define COAP_MEDIATYPE_APPLICATION_COSE_SIGN 98 /* application/cose; cose-type="cose-sign" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_SIGN1 18 /* application/cose; cose-type="cose-sign1" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_ENCRYPT 96 /* application/cose; cose-type="cose-encrypt" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_ENCRYPT0 16 /* application/cose; cose-type="cose-encrypt0" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_MAC 97 /* application/cose; cose-type="cose-mac" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_MAC0 17 /* application/cose; cose-type="cose-mac0" */ + +#define COAP_MEDIATYPE_APPLICATION_COSE_KEY 101 /* application/cose-key */ +#define COAP_MEDIATYPE_APPLICATION_COSE_KEY_SET 102 /* application/cose-key-set */ + +/* Content formats from RFC 8428 */ +#define COAP_MEDIATYPE_APPLICATION_SENML_JSON 110 /* application/senml+json */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_JSON 111 /* application/sensml+json */ +#define COAP_MEDIATYPE_APPLICATION_SENML_CBOR 112 /* application/senml+cbor */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_CBOR 113 /* application/sensml+cbor */ +#define COAP_MEDIATYPE_APPLICATION_SENML_EXI 114 /* application/senml-exi */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_EXI 115 /* application/sensml-exi */ +#define COAP_MEDIATYPE_APPLICATION_SENML_XML 310 /* application/senml+xml */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_XML 311 /* application/sensml+xml */ + +/* Content formats from RFC 8782 */ +#define COAP_MEDIATYPE_APPLICATION_DOTS_CBOR 271 /* application/dots+cbor */ + +/* Note that identifiers for registered media types are in the range 0-65535. We + * use an unallocated type here and hope for the best. */ +#define COAP_MEDIATYPE_ANY 0xff /* any media type */ + +/** + * coap_mid_t is used to store the CoAP Message ID of a CoAP PDU. + * Valid message ids are 0 to 2^16. Negative values are error codes. + */ +typedef int coap_mid_t; + +/** Indicates an invalid message id. */ +#define COAP_INVALID_MID -1 + +/** + * Indicates an invalid message id. + * @deprecated Use COAP_INVALID_MID instead. + */ +#define COAP_INVALID_TID COAP_INVALID_MID + +/** + * @deprecated Use coap_optlist_t instead. + * + * Structures for more convenient handling of options. (To be used with ordered + * coap_list_t.) The option's data will be added to the end of the coap_option + * structure (see macro COAP_OPTION_DATA). + */ +COAP_DEPRECATED typedef struct { + uint16_t key; /* the option key (no delta coding) */ + unsigned int length; +} coap_option; + +#define COAP_OPTION_KEY(option) (option).key +#define COAP_OPTION_LENGTH(option) (option).length +#define COAP_OPTION_DATA(option) ((unsigned char *)&(option) + sizeof(coap_option)) + +#ifdef WITH_LWIP +/** + * Creates a CoAP PDU from an lwIP @p pbuf, whose reference is passed on to this + * function. + * + * The pbuf is checked for being contiguous, and for having only one reference. + * The reference is stored in the PDU and will be freed when the PDU is freed. + * + * (For now, these are fatal errors; in future, a new pbuf might be allocated, + * the data copied and the passed pbuf freed). + * + * This behaves like coap_pdu_init(0, 0, 0, pbuf->tot_len), and afterwards + * copying the contents of the pbuf to the pdu. + * + * @return A pointer to the new PDU object or @c NULL on error. + */ +coap_pdu_t * coap_pdu_from_pbuf(struct pbuf *pbuf); +#endif + +/** +* CoAP protocol types +*/ +typedef enum coap_proto_t { + COAP_PROTO_NONE = 0, + COAP_PROTO_UDP, + COAP_PROTO_DTLS, + COAP_PROTO_TCP, + COAP_PROTO_TLS, +} coap_proto_t; + +/** + * Set of codes available for a PDU. + */ +typedef enum coap_pdu_code_t { + COAP_EMPTY_CODE = 0, + + COAP_REQUEST_CODE_GET = COAP_REQUEST_GET, + COAP_REQUEST_CODE_POST = COAP_REQUEST_POST, + COAP_REQUEST_CODE_PUT = COAP_REQUEST_PUT, + COAP_REQUEST_CODE_DELETE = COAP_REQUEST_DELETE, + COAP_REQUEST_CODE_FETCH = COAP_REQUEST_FETCH, + COAP_REQUEST_CODE_PATCH = COAP_REQUEST_PATCH, + COAP_REQUEST_CODE_IPATCH = COAP_REQUEST_IPATCH, + + COAP_RESPONSE_CODE_OK = COAP_RESPONSE_CODE(200), + COAP_RESPONSE_CODE_CREATED = COAP_RESPONSE_CODE(201), + COAP_RESPONSE_CODE_DELETED = COAP_RESPONSE_CODE(202), + COAP_RESPONSE_CODE_VALID = COAP_RESPONSE_CODE(203), + COAP_RESPONSE_CODE_CHANGED = COAP_RESPONSE_CODE(204), + COAP_RESPONSE_CODE_CONTENT = COAP_RESPONSE_CODE(205), + COAP_RESPONSE_CODE_CONTINUE = COAP_RESPONSE_CODE(231), + COAP_RESPONSE_CODE_BAD_REQUEST = COAP_RESPONSE_CODE(400), + COAP_RESPONSE_CODE_UNAUTHORIZED = COAP_RESPONSE_CODE(401), + COAP_RESPONSE_CODE_BAD_OPTION = COAP_RESPONSE_CODE(402), + COAP_RESPONSE_CODE_FORBIDDEN = COAP_RESPONSE_CODE(403), + COAP_RESPONSE_CODE_NOT_FOUND = COAP_RESPONSE_CODE(404), + COAP_RESPONSE_CODE_NOT_ALLOWED = COAP_RESPONSE_CODE(405), + COAP_RESPONSE_CODE_NOT_ACCEPTABLE = COAP_RESPONSE_CODE(406), + COAP_RESPONSE_CODE_INCOMPLETE = COAP_RESPONSE_CODE(408), + COAP_RESPONSE_CODE_CONFLICT = COAP_RESPONSE_CODE(409), + COAP_RESPONSE_CODE_PRECONDITION_FAILED = COAP_RESPONSE_CODE(412), + COAP_RESPONSE_CODE_REQUEST_TOO_LARGE = COAP_RESPONSE_CODE(413), + COAP_RESPONSE_CODE_UNSUPPORTED_CONTENT_FORMAT = COAP_RESPONSE_CODE(415), + COAP_RESPONSE_CODE_UNPROCESSABLE = COAP_RESPONSE_CODE(422), + COAP_RESPONSE_CODE_TOO_MANY_REQUESTS = COAP_RESPONSE_CODE(429), + COAP_RESPONSE_CODE_INTERNAL_ERROR = COAP_RESPONSE_CODE(500), + COAP_RESPONSE_CODE_NOT_IMPLEMENTED = COAP_RESPONSE_CODE(501), + COAP_RESPONSE_CODE_BAD_GATEWAY = COAP_RESPONSE_CODE(502), + COAP_RESPONSE_CODE_SERVICE_UNAVAILABLE = COAP_RESPONSE_CODE(503), + COAP_RESPONSE_CODE_GATEWAY_TIMEOUT = COAP_RESPONSE_CODE(504), + COAP_RESPONSE_CODE_PROXYING_NOT_SUPPORTED = COAP_RESPONSE_CODE(505), + COAP_RESPONSE_CODE_HOP_LIMIT_REACHED = COAP_RESPONSE_CODE(508), + + COAP_SIGNALING_CODE_CSM = COAP_SIGNALING_CSM, + COAP_SIGNALING_CODE_PING = COAP_SIGNALING_PING, + COAP_SIGNALING_CODE_PONG = COAP_SIGNALING_PONG, + COAP_SIGNALING_CODE_RELEASE = COAP_SIGNALING_RELEASE, + COAP_SIGNALING_CODE_ABORT = COAP_SIGNALING_ABORT +} coap_pdu_code_t; + +/** + * Creates a new CoAP PDU with at least enough storage space for the given + * @p size maximum message size. The function returns a pointer to the + * node coap_pdu_t object on success, or @c NULL on error. The storage allocated + * for the result must be released with coap_delete_pdu() if coap_send() + * is not called. + * + * @param type The type of the PDU (one of COAP_MESSAGE_CON, COAP_MESSAGE_NON, + * COAP_MESSAGE_ACK, COAP_MESSAGE_RST). + * @param code The message code of the PDU. + * @param mid The message id to set or 0 if unknown / not applicable. + * @param size The maximum allowed number of byte for the message. + * @return A pointer to the new PDU object or @c NULL on error. + */ +coap_pdu_t *coap_pdu_init(coap_pdu_type_t type, coap_pdu_code_t code, + coap_mid_t mid, size_t size); + +/** + * Creates a new CoAP PDU. + * + * @param type The type of the PDU (one of COAP_MESSAGE_CON, COAP_MESSAGE_NON, + * COAP_MESSAGE_ACK, COAP_MESSAGE_RST). + * @param code The message code of the PDU. + * @param session The session that will be using this PDU + * + * @return The skeletal PDU or @c NULL if failure. + */ +coap_pdu_t *coap_new_pdu(coap_pdu_type_t type, coap_pdu_code_t code, + coap_session_t *session); + +/** + * Dispose of an CoAP PDU and frees associated storage. + * Not that in general you should not call this function directly. + * When a PDU is sent with coap_send(), coap_delete_pdu() will be called + * automatically for you. + * + * @param pdu The PDU for free off. + */ +void coap_delete_pdu(coap_pdu_t *pdu); + +/** + * Duplicate an existing PDU. Specific options can be ignored and not copied + * across. The PDU data payload is not copied across. + * + * @param old_pdu The PDU to duplicate + * @param session The session that will be using this PDU. + * @param token_length The length of the token to use in this duplicated PDU. + * @param token The token to use in this duplicated PDU. + * @param drop_options A list of options not to copy into the duplicated PDU. + * If @c NULL, then all options are copied across. + * + * @return The duplicated PDU or @c NULL if failure. + */ +coap_pdu_t * +coap_pdu_duplicate(const coap_pdu_t *old_pdu, + coap_session_t *session, + size_t token_length, + const uint8_t *token, + coap_opt_filter_t *drop_options); + +/** + * Adds token of length @p len to @p pdu. + * Adding the token destroys any following contents of the pdu. Hence options + * and data must be added after coap_add_token() has been called. In @p pdu, + * length is set to @p len + @c 4, and max_delta is set to @c 0. This function + * returns @c 0 on error or a value greater than zero on success. + * + * @param pdu The PDU where the token is to be added. + * @param len The length of the new token. + * @param data The token to add. + * + * @return A value greater than zero on success, or @c 0 on error. + */ +int coap_add_token(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** + * Adds option of given number to pdu that is passed as first + * parameter. + * coap_add_option() destroys the PDU's data, so coap_add_data() must be called + * after all options have been added. As coap_add_token() destroys the options + * following the token, the token must be added before coap_add_option() is + * called. This function returns the number of bytes written or @c 0 on error. + * + * Note: Where possible, the option data needs to be stripped of leading zeros + * (big endian) to reduce the amount of data needed in the PDU, as well as in + * some cases the maximum data size of an opton can be exceeded if not stripped + * and hence be illegal. This is done by using coap_encode_var_safe() or + * coap_encode_var_safe8(). + * + * @param pdu The PDU where the option is to be added. + * @param number The number of the new option. + * @param len The length of the new option. + * @param data The data of the new option. + * + * @return The overall length of the option or @c 0 on failure. + */ +size_t coap_add_option(coap_pdu_t *pdu, + coap_option_num_t number, + size_t len, + const uint8_t *data); + +/** + * Adds given data to the pdu that is passed as first parameter. Note that the + * PDU's data is destroyed by coap_add_option(). coap_add_data() must be called + * only once per PDU, otherwise the result is undefined. + * + * @param pdu The PDU where the data is to be added. + * @param len The length of the data. + * @param data The data to add. + * + * @return @c 1 if success, else @c 0 if failure. + */ +int coap_add_data(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** + * Adds given data to the pdu that is passed as first parameter but does not + * copy it. Note that the PDU's data is destroyed by coap_add_option(). + * coap_add_data() must be have been called once for this PDU, otherwise the + * result is undefined. + * The actual data must be copied at the returned location. + * + * @param pdu The PDU where the data is to be added. + * @param len The length of the data. + * + * @return Where to copy the data of len to, or @c NULL is error. + */ +uint8_t *coap_add_data_after(coap_pdu_t *pdu, size_t len); + +/** + * Retrieves the length and data pointer of specified PDU. Returns 0 on error or + * 1 if *len and *data have correct values. Note that these values are destroyed + * with the pdu. + * + * @param pdu The specified PDU. + * @param len Returns the length of the current data + * @param data Returns the ptr to the current data + * + * @return @c 1 if len and data are correctly filled in, else + * @c 0 if there is no data. + */ +int coap_get_data(const coap_pdu_t *pdu, + size_t *len, + const uint8_t **data); + +/** + * Retrieves the data from a PDU, with support for large bodies of data that + * spans multiple PDUs. + * + * Note: The data pointed to on return is destroyed when the PDU is destroyed. + * + * @param pdu The specified PDU. + * @param len Returns the length of the current data + * @param data Returns the ptr to the current data + * @param offset Returns the offset of the current data from the start of the + * body comprising of many blocks (RFC7959) + * @param total Returns the total size of the body. + * If offset + length < total, then there is more data to follow. + * + * @return @c 1 if len, data, offset and total are correctly filled in, else + * @c 0 if there is no data. + */ +int coap_get_data_large(const coap_pdu_t *pdu, + size_t *len, + const uint8_t **data, + size_t *offset, + size_t *total); + +/** + * Gets the PDU code associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The PDU code. + */ +coap_pdu_code_t coap_pdu_get_code(const coap_pdu_t *pdu); + +/** + * Sets the PDU code in the @p pdu. + * + * @param pdu The PDU object. + * @param code The code to set in the PDU. + */ +void coap_pdu_set_code(coap_pdu_t *pdu, coap_pdu_code_t code); + +/** + * Gets the PDU type associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The PDU type. + */ +coap_pdu_type_t coap_pdu_get_type(const coap_pdu_t *pdu); + +/** + * Sets the PDU type in the @p pdu. + * + * @param pdu The PDU object. + * @param type The type to set for the PDU. + */ +void coap_pdu_set_type(coap_pdu_t *pdu, coap_pdu_type_t type); + +/** + * Gets the token associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The token information. + */ +coap_bin_const_t coap_pdu_get_token(const coap_pdu_t *pdu); + +/** + * Gets the message id associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The message id. + */ +coap_mid_t coap_pdu_get_mid(const coap_pdu_t *pdu); + +/** + * Sets the message id in the @p pdu. + * + * @param pdu The PDU object. + * @param mid The message id value to set in the PDU. + * + */ +void coap_pdu_set_mid(coap_pdu_t *pdu, coap_mid_t mid); + +/** @} */ + +#endif /* COAP_PDU_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/resource.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/resource.h new file mode 100644 index 00000000000..2cd9aea48fa --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/resource.h @@ -0,0 +1,378 @@ +/* + * resource.h -- generic resource handling + * + * Copyright (C) 2010,2011,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file resource.h + * @brief Generic resource handling + */ + +#ifndef COAP_RESOURCE_H_ +#define COAP_RESOURCE_H_ + +#ifndef COAP_RESOURCE_CHECK_TIME +/** The interval in seconds to check if resources have changed. */ +#define COAP_RESOURCE_CHECK_TIME 2 +#endif /* COAP_RESOURCE_CHECK_TIME */ + +#include "async.h" +#include "block.h" +#include "str.h" +#include "pdu.h" +#include "net.h" +#include "subscribe.h" + +/** + * @defgroup coap_resource Resource Configuraton + * API functions for setting up resources + * @{ + */ + +/** + * Definition of message handler function + */ +typedef void (*coap_method_handler_t) + (coap_resource_t *, + coap_session_t *, + const coap_pdu_t * /* request */, + const coap_string_t * /* query string */, + coap_pdu_t * /* response */); + +#define COAP_ATTR_FLAGS_RELEASE_NAME 0x1 +#define COAP_ATTR_FLAGS_RELEASE_VALUE 0x2 + +/** The URI passed to coap_resource_init() is free'd by coap_delete_resource(). */ +#define COAP_RESOURCE_FLAGS_RELEASE_URI 0x1 + +/** + * Notifications will be sent non-confirmable by default. RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + * Libcoap will always send every fifth packet as confirmable. + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_NON 0x0 + +/** + * Notifications will be sent confirmable. RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_CON 0x2 + +/** + * Notifications will always be sent non-confirmable. This is in + * violation of RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + * but required by the DOTS signal channel protocol which needs to operate in + * lossy DDoS attack environments. + * https://tools.ietf.org/html/rfc8782#section-4.4.2.1 + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_NON_ALWAYS 0x4 + +/** + * Creates a new resource object and initializes the link field to the string + * @p uri_path. This function returns the new coap_resource_t object. + * + * If the string is going to be freed off by coap_delete_resource() when + * COAP_RESOURCE_FLAGS_RELEASE_URI is set in @p flags, then either the 's' + * variable of coap_str_const_t has to point to constant text, or point to data + * within the allocated coap_str_const_t parameter. + * + * @param uri_path The string URI path of the new resource. + * @param flags Flags for memory management (in particular release of + * memory). Possible values:@n + * + * COAP_RESOURCE_FLAGS_RELEASE_URI + * If this flag is set, the URI passed to + * coap_resource_init() is free'd by + * coap_delete_resource()@n + * + * COAP_RESOURCE_FLAGS_NOTIFY_CON + * If this flag is set, coap-observe notifications + * will be sent confirmable by default.@n + * + * COAP_RESOURCE_FLAGS_NOTIFY_NON (default) + * If this flag is set, coap-observe notifications + * will be sent non-confirmable by default.@n + * + * If flags is set to 0 then the + * COAP_RESOURCE_FLAGS_NOTIFY_NON is considered. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_init(coap_str_const_t *uri_path, + int flags); + + +/** + * Creates a new resource object for the unknown resource handler with support + * for PUT. + * + * In the same way that additional handlers can be added to the resource + * created by coap_resource_init() by using coap_register_handler(), POST, + * GET, DELETE etc. handlers can be added to this resource. It is the + * responsibility of the application to manage the unknown resources by either + * creating new resources with coap_resource_init() (which should have a + * DELETE handler specified for the resource removal) or by maintaining an + * active resource list. + * + * Note: There can only be one unknown resource handler per context - attaching + * a new one overrides the previous definition. + * + * Note: It is not possible to observe the unknown resource with a GET request + * - a separate resource needs to be reated by the PUT (or POST) handler, + * and make that resource observable. + * + * This function returns the new coap_resource_t object. + * + * @param put_handler The PUT handler to register with @p resource for + * unknown Uri-Path. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_unknown_init(coap_method_handler_t put_handler); + +/** + * Creates a new resource object for handling proxy URIs. + * This function returns the new coap_resource_t object. + * + * Note: There can only be one proxy resource handler per context - attaching + * a new one overrides the previous definition. + * + * @param handler The PUT/POST/GET etc. handler that handles all request types. + * @param host_name_count The number of provided host_name_list entries. A + * minimum of 1 must be provided. + * @param host_name_list Array of depth host_name_count names that this proxy + * is known by. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_proxy_uri_init(coap_method_handler_t handler, + size_t host_name_count, const char *host_name_list[]); + +/** + * Returns the resource identified by the unique string @p uri_path. If no + * resource was found, this function returns @c NULL. + * + * @param context The context to look for this resource. + * @param uri_path The unique string uri of the resource. + * + * @return A pointer to the resource or @c NULL if not found. + */ +coap_resource_t *coap_get_resource_from_uri_path(coap_context_t *context, + coap_str_const_t *uri_path); + +/** + * Get the uri_path from a @p resource. + * + * @param resource The CoAP resource to check. + * + * @return The uri_path if it exists or @c NULL otherwise. + */ +coap_str_const_t* coap_resource_get_uri_path(coap_resource_t *resource); + +/** + * Sets the notification message type of resource @p resource to given + * @p mode + + * @param resource The resource to update. + * @param mode Must be one of @c COAP_RESOURCE_FLAGS_NOTIFY_NON + * or @c COAP_RESOURCE_FLAGS_NOTIFY_CON. + */ +void coap_resource_set_mode(coap_resource_t *resource, int mode); + +/** + * Sets the user_data. The user_data is exclusively used by the library-user + * and can be used as user defined context in the handler functions. + * + * @param resource Resource to attach the data to + * @param data Data to attach to the user_data field. This pointer is + * only used for storage, the data remains under user control + */ +void coap_resource_set_userdata(coap_resource_t *resource, void *data); + +/** + * Gets the user_data. The user_data is exclusively used by the library-user + * and can be used as context in the handler functions. + * + * @param resource Resource to retrieve the user_data from + * + * @return The user_data pointer + */ +void *coap_resource_get_userdata(coap_resource_t *resource); + +/** + * Definition of release resource user_data callback function + */ +typedef void (*coap_resource_release_userdata_handler_t)(void *user_data); + +/** + * Defines the context wide callback to use to when the resource is deleted + * to release the data held in the resource's user_data. + * + * @param context The context to associate the release callback with + * @param callback The callback to invoke when the resource is deleted or NULL + * + */ +void coap_resource_release_userdata_handler(coap_context_t *context, + coap_resource_release_userdata_handler_t callback); + +/** + * Registers the given @p resource for @p context. The resource must have been + * created by coap_resource_init() or coap_resource_unknown_init(), the + * storage allocated for the resource will be released by coap_delete_resource(). + * + * @param context The context to use. + * @param resource The resource to store. + */ +void coap_add_resource(coap_context_t *context, coap_resource_t *resource); + +/** + * Deletes a resource identified by @p resource. The storage allocated for that + * resource is freed, and removed from the context. + * + * @param context The context where the resources are stored. + * @param resource The resource to delete. + * + * @return @c 1 if the resource was found (and destroyed), + * @c 0 otherwise. + */ +int coap_delete_resource(coap_context_t *context, coap_resource_t *resource); + +/** + * Registers the specified @p handler as message handler for the request type @p + * method + * + * @param resource The resource for which the handler shall be registered. + * @param method The CoAP request method to handle. + * @param handler The handler to register with @p resource. + */ +void coap_register_handler(coap_resource_t *resource, + coap_request_t method, + coap_method_handler_t handler); + +/** + * Registers a new attribute with the given @p resource. As the + * attribute's coap_str_const_ fields will point to @p name and @p value the + * caller must ensure that these pointers are valid during the + * attribute's lifetime. + + * If the @p name and/or @p value string is going to be freed off at attribute + * removal time by the setting of COAP_ATTR_FLAGS_RELEASE_NAME or + * COAP_ATTR_FLAGS_RELEASE_VALUE in @p flags, then either the 's' + * variable of coap_str_const_t has to point to constant text, or point to data + * within the allocated coap_str_const_t parameter. + * + * @param resource The resource to register the attribute with. + * @param name The attribute's name as a string. + * @param value The attribute's value as a string or @c NULL if none. + * @param flags Flags for memory management (in particular release of + * memory). Possible values:@n + * + * COAP_ATTR_FLAGS_RELEASE_NAME + * If this flag is set, the name passed to + * coap_add_attr_release() is free'd + * when the attribute is deleted@n + * + * COAP_ATTR_FLAGS_RELEASE_VALUE + * If this flag is set, the value passed to + * coap_add_attr_release() is free'd + * when the attribute is deleted@n + * + * @return A pointer to the new attribute or @c NULL on error. + */ +coap_attr_t *coap_add_attr(coap_resource_t *resource, + coap_str_const_t *name, + coap_str_const_t *value, + int flags); + +/** + * Returns @p resource's coap_attr_t object with given @p name if found, @c NULL + * otherwise. + * + * @param resource The resource to search for attribute @p name. + * @param name Name of the requested attribute as a string. + * @return The first attribute with specified @p name or @c NULL if none + * was found. + */ +coap_attr_t *coap_find_attr(coap_resource_t *resource, + coap_str_const_t *name); + +/** + * Returns @p attribute's value. + * + * @param attribute Pointer to attribute. + * + * @return Attribute's value or @c NULL. + */ +coap_str_const_t *coap_attr_get_value(coap_attr_t *attribute); + +/** + * Status word to encode the result of conditional print or copy operations such + * as coap_print_link(). The lower 28 bits of coap_print_status_t are used to + * encode the number of characters that has actually been printed, bits 28 to 31 + * encode the status. When COAP_PRINT_STATUS_ERROR is set, an error occurred + * during output. In this case, the other bits are undefined. + * COAP_PRINT_STATUS_TRUNC indicates that the output is truncated, i.e. the + * printing would have exceeded the current buffer. + */ +typedef unsigned int coap_print_status_t; + +#define COAP_PRINT_STATUS_MASK 0xF0000000u +#define COAP_PRINT_OUTPUT_LENGTH(v) ((v) & ~COAP_PRINT_STATUS_MASK) +#define COAP_PRINT_STATUS_ERROR 0x80000000u +#define COAP_PRINT_STATUS_TRUNC 0x40000000u + +/** + * Writes a description of this resource in link-format to given text buffer. @p + * len must be initialized to the maximum length of @p buf and will be set to + * the number of characters actually written if successful. This function + * returns @c 1 on success or @c 0 on error. + * + * @param resource The resource to describe. + * @param buf The output buffer to write the description to. + * @param len Must be initialized to the length of @p buf and + * will be set to the length of the printed link description. + * @param offset The offset within the resource description where to + * start writing into @p buf. This is useful for dealing + * with the Block2 option. @p offset is updated during + * output as it is consumed. + * + * @return If COAP_PRINT_STATUS_ERROR is set, an error occured. Otherwise, + * the lower 28 bits will indicate the number of characters that + * have actually been output into @p buffer. The flag + * COAP_PRINT_STATUS_TRUNC indicates that the output has been + * truncated. + */ +coap_print_status_t coap_print_link(const coap_resource_t *resource, + unsigned char *buf, + size_t *len, + size_t *offset); + +/** @} */ + +/** + * Returns the resource identified by the unique string @p uri_path. If no + * resource was found, this function returns @c NULL. + * + * @param context The context to look for this resource. + * @param uri_path The unique string uri of the resource. + * + * @return A pointer to the resource or @c NULL if not found. + */ +coap_resource_t *coap_get_resource_from_uri_path(coap_context_t *context, + coap_str_const_t *uri_path); + +/** + * @deprecated use coap_resource_notify_observers() instead. + */ +COAP_DEPRECATED int +coap_resource_set_dirty(coap_resource_t *r, + const coap_string_t *query); + +#endif /* COAP_RESOURCE_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/str.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/str.h new file mode 100644 index 00000000000..dbf53d0c475 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/str.h @@ -0,0 +1,204 @@ +/* + * str.h -- strings to be used in the CoAP library + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_STR_H_ +#define COAP_STR_H_ + +#include + + +/** + * @defgroup string String handling support + * API functions for handling strings and binary data + * @{ + */ + +/* + * Note: string and binary use equivalent objects. + * string is likely to contain readable textual information, binary will not. + */ + +/** + * CoAP string data definition + */ +typedef struct coap_string_t { + size_t length; /**< length of string */ + uint8_t *s; /**< string data */ +} coap_string_t; + +/** + * CoAP string data definition with const data + */ +typedef struct coap_str_const_t { + size_t length; /**< length of string */ + const uint8_t *s; /**< read-only string data */ +} coap_str_const_t; + +#define COAP_SET_STR(st,l,v) { (st)->length = (l), (st)->s = (v); } + +/** + * CoAP binary data definition + */ +typedef struct coap_binary_t { + size_t length; /**< length of binary data */ + uint8_t *s; /**< binary data */ +} coap_binary_t; + +/** + * CoAP binary data definition with const data + */ +typedef struct coap_bin_const_t { + size_t length; /**< length of binary data */ + const uint8_t *s; /**< read-only binary data */ +} coap_bin_const_t; + +/** + * Returns a new string object with at least size+1 bytes storage allocated. + * It is the responsibility of the caller to fill in all the appropriate + * information. + * The string must be released using coap_delete_string(). + * + * @param size The size to allocate for the string data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_string_t *coap_new_string(size_t size); + +/** + * Deletes the given string and releases any memory allocated. + * + * @param string The string to free off. + */ +void coap_delete_string(coap_string_t *string); + +/** + * Returns a new const string object with at least size+1 bytes storage + * allocated, and the provided data copied into the string object. + * The string must be released using coap_delete_str_const(). + * + * @param data The data to put in the new string object. + * @param size The size to allocate for the binary string data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_str_const_t *coap_new_str_const(const uint8_t *data, size_t size); + +/** + * Deletes the given const string and releases any memory allocated. + * + * @param string The string to free off. + */ +void coap_delete_str_const(coap_str_const_t *string); + +/** + * Returns a new binary object with at least size bytes storage allocated. + * It is the responsibility of the caller to fill in all the appropriate + * information. + * The coap_binary_t object must be released using coap_delete_binary(). + * + * @param size The size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_binary_t *coap_new_binary(size_t size); + +/** + * Deletes the given coap_binary_t object and releases any memory allocated. + * + * @param binary The coap_binary_t object to free off. + */ +void coap_delete_binary(coap_binary_t *binary); + +/** + * Resizes the given coap_binary_t object. + * It is the responsibility of the caller to fill in all the appropriate + * additional information. + * + * Note: If there is an error, @p binary will separately need to be released by + * coap_delete_binary(). + * + * @param binary The coap_binary_t object to resize. + * @param new_size The new size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_binary_t *coap_resize_binary(coap_binary_t *binary, size_t new_size); + +/** + * Take the specified byte array (text) and create a coap_bin_const_t * + * Returns a new const binary object with at least size bytes storage + * allocated, and the provided data copied into the binary object. + * The binary data must be released using coap_delete_bin_const(). + * + * @param data The data to put in the new string object. + * @param size The size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_bin_const_t *coap_new_bin_const(const uint8_t *data, size_t size); + +/** + * Deletes the given const binary data and releases any memory allocated. + * + * @param binary The binary data to free off. + */ +void coap_delete_bin_const(coap_bin_const_t *binary); + +#ifndef COAP_MAX_STR_CONST_FUNC +#define COAP_MAX_STR_CONST_FUNC 2 +#endif /* COAP_MAX_STR_CONST_FUNC */ + +/** + * Take the specified byte array (text) and create a coap_str_const_t * + * + * Note: the array is 2 deep as there are up to two callings of + * coap_make_str_const in a function call. e.g. coap_add_attr(). + * Caution: If there are local variable assignments, these will cycle around + * the var[COAP_MAX_STR_CONST_FUNC] set. No current examples do this. + * + * @param string The const string to convert to a coap_str_const_t * + * + * @return A pointer to one of two static variables containing the + * coap_str_const_t * result + */ +coap_str_const_t *coap_make_str_const(const char *string); + +/** + * Compares the two strings for equality + * + * @param string1 The first string. + * @param string2 The second string. + * + * @return @c 1 if the strings are equal + * @c 0 otherwise. + */ +#define coap_string_equal(string1,string2) \ + ((string1)->length == (string2)->length && ((string1)->length == 0 || \ + ((string1)->s && (string2)->s && \ + memcmp((string1)->s, (string2)->s, (string1)->length) == 0))) + +/** + * Compares the two binary data for equality + * + * @param binary1 The first binary data. + * @param binary2 The second binary data. + * + * @return @c 1 if the binary data is equal + * @c 0 otherwise. + */ +#define coap_binary_equal(binary1,binary2) \ + ((binary1)->length == (binary2)->length && ((binary1)->length == 0 || \ + ((binary1)->s && (binary2)->s && \ + memcmp((binary1)->s, (binary2)->s, (binary1)->length) == 0))) + +/** @} */ + +#endif /* COAP_STR_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/subscribe.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/subscribe.h new file mode 100644 index 00000000000..c3aabc2db04 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/subscribe.h @@ -0,0 +1,68 @@ +/* + * subscribe.h -- subscription handling for CoAP + * see RFC7641 + * + * Copyright (C) 2010-2012,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file subscribe.h + * @brief Defines the application visible subscribe information + */ + +#ifndef COAP_SUBSCRIBE_H_ +#define COAP_SUBSCRIBE_H_ + +/** + * @defgroup observe Resource Observation + * API functions for interfacing with the observe handling (RFC7641) + * @{ + */ + +/** + * The value COAP_OBSERVE_ESTABLISH in a GET/FETCH request option + * COAP_OPTION_OBSERVE indicates a new observe relationship for (sender + * address, token) is requested. + */ +#define COAP_OBSERVE_ESTABLISH 0 + +/** + * The value COAP_OBSERVE_CANCEL in a GET/FETCH request option + * COAP_OPTION_OBSERVE indicates that the observe relationship for (sender + * address, token) must be cancelled. + */ +#define COAP_OBSERVE_CANCEL 1 + +/** + * Set whether a @p resource is observable. If the resource is observable + * and the client has set the COAP_OPTION_OBSERVE in a request packet, then + * whenever the state of the resource changes (a call to + * coap_resource_trigger_observe()), an Observer response will get sent. + * + * @param resource The CoAP resource to use. + * @param mode @c 1 if Observable is to be set, @c 0 otherwise. + * + */ +void coap_resource_set_get_observable(coap_resource_t *resource, int mode); + +/** + * Initiate the sending of an Observe packet for all observers of @p resource, + * optionally matching @p query if not NULL + * + * @param resource The CoAP resource to use. + * @param query The Query to match against or NULL + * + * @return @c 1 if the Observe has been triggered, @c 0 otherwise. + */ +int +coap_resource_notify_observers(coap_resource_t *resource, + const coap_string_t *query); + +/** @} */ + +#endif /* COAP_SUBSCRIBE_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/uri.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/uri.h new file mode 100644 index 00000000000..8084483b500 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/uri.h @@ -0,0 +1,176 @@ +/* + * uri.h -- helper functions for URI treatment + * + * Copyright (C) 2010-2020 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_URI_H_ +#define COAP_URI_H_ + +#include + +#include "str.h" + +/** + * The scheme specifiers. Secure schemes have an odd numeric value, + * others are even. + */ +typedef enum coap_uri_scheme_t { + COAP_URI_SCHEME_COAP = 0, + COAP_URI_SCHEME_COAPS, /* 1 */ + COAP_URI_SCHEME_COAP_TCP, /* 2 */ + COAP_URI_SCHEME_COAPS_TCP, /* 3 */ + COAP_URI_SCHEME_HTTP, /* 4 Proxy-Uri only */ + COAP_URI_SCHEME_HTTPS /* 5 Proxy-Uri only */ +} coap_uri_scheme_t; + +/** This mask can be used to check if a parsed URI scheme is secure. */ +#define COAP_URI_SCHEME_SECURE_MASK 0x01 + +/** + * Representation of parsed URI. Components may be filled from a string with + * coap_split_uri() or coap_split_proxy_uri() and can be used as input for + * option-creation functions. + */ +typedef struct { + coap_str_const_t host; /**< host part of the URI */ + uint16_t port; /**< The port in host byte order */ + coap_str_const_t path; /**< Beginning of the first path segment. + Use coap_split_path() to create Uri-Path options */ + coap_str_const_t query; /**< The query part if present */ + + /** The parsed scheme specifier. */ + enum coap_uri_scheme_t scheme; +} coap_uri_t; + +static inline int +coap_uri_scheme_is_secure(const coap_uri_t *uri) { + return uri && ((uri->scheme & COAP_URI_SCHEME_SECURE_MASK) != 0); +} + +/** + * Creates a new coap_uri_t object from the specified URI. Returns the new + * object or NULL on error. The memory allocated by the new coap_uri_t + * must be released using coap_free(). + * + * @param uri The URI path to copy. + * @param length The length of uri. + * + * @return New URI object or NULL on error. + */ +coap_uri_t *coap_new_uri(const uint8_t *uri, unsigned int length); + +/** + * Clones the specified coap_uri_t object. Thie function allocates sufficient + * memory to hold the coap_uri_t structure and its contents. The object must + * be released with coap_free(). */ +coap_uri_t *coap_clone_uri(const coap_uri_t *uri); + +/** + * @defgroup uri_parse URI Parsing Functions + * + * CoAP PDUs contain normalized URIs with their path and query split into + * multiple segments. The functions in this module help splitting strings. + * @{ + */ + +/** + * Parses a given string into URI components. The identified syntactic + * components are stored in the result parameter @p uri. Optional URI + * components that are not specified will be set to { 0, 0 }, except for the + * port which is set to the default port for the protocol. This function + * returns @p 0 if parsing succeeded, a value less than zero otherwise. + * + * @param str_var The string to split up. + * @param len The actual length of @p str_var + * @param uri The coap_uri_t object to store the result. + * + * @return @c 0 on success, or < 0 on error. + * + */ +int coap_split_uri(const uint8_t *str_var, size_t len, coap_uri_t *uri); + +/** + * Parses a given string into URI components. The identified syntactic + * components are stored in the result parameter @p uri. Optional URI + * components that are not specified will be set to { 0, 0 }, except for the + * port which is set to default port for the protocol. This function returns + * @p 0 if parsing succeeded, a value less than zero otherwise. + * Note: This function enforces that the given string is in Proxy-Uri format + * as well as supports different schema such as http. + * + * @param str_var The string to split up. + * @param len The actual length of @p str_var + * @param uri The coap_uri_t object to store the result. + * + * @return @c 0 on success, or < 0 on error. + * + */ +int coap_split_proxy_uri(const uint8_t *str_var, size_t len, coap_uri_t *uri); + +/** + * Splits the given URI path into segments. Each segment is preceded + * by an option pseudo-header with delta-value 0 and the actual length + * of the respective segment after percent-decoding. + * + * @param s The path string to split. + * @param length The actual length of @p s. + * @param buf Result buffer for parsed segments. + * @param buflen Maximum length of @p buf. Will be set to the actual number + * of bytes written into buf on success. + * + * @return The number of segments created or @c -1 on error. + */ +int coap_split_path(const uint8_t *s, + size_t length, + unsigned char *buf, + size_t *buflen); + +/** + * Splits the given URI query into segments. Each segment is preceded + * by an option pseudo-header with delta-value 0 and the actual length + * of the respective query term. + * + * @param s The query string to split. + * @param length The actual length of @p s. + * @param buf Result buffer for parsed segments. + * @param buflen Maximum length of @p buf. Will be set to the actual number + * of bytes written into buf on success. + * + * @return The number of segments created or @c -1 on error. + * + * @bug This function does not reserve additional space for delta > 12. + */ +int coap_split_query(const uint8_t *s, + size_t length, + unsigned char *buf, + size_t *buflen); + +/** + * Extract query string from request PDU according to escape rules in 6.5.8. + * @param request Request PDU. + * @return Reconstructed and escaped query string part or @c NULL if + * no query was contained in @p request. The coap_string_t + * object returned by this function must be released with + * coap_delete_string. + */ +coap_string_t *coap_get_query(const coap_pdu_t *request); + +/** + * Extract uri_path string from request PDU + * @param request Request PDU. + * @return Reconstructed and escaped uri path string part or @c NULL + * if no URI-Path was contained in @p request. The + * coap_string_t object returned by this function must be + * released with coap_delete_string. + */ +coap_string_t *coap_get_uri_path(const coap_pdu_t *request); + +/** @} */ + +#endif /* COAP_URI_H_ */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/uthash.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/uthash.h new file mode 100644 index 00000000000..9a396b6179f --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/uthash.h @@ -0,0 +1,1136 @@ +/* +Copyright (c) 2003-2021, Troy D. Hanson http://troydhanson.github.io/uthash/ +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. + +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 UTHASH_H +#define UTHASH_H + +#define UTHASH_VERSION 2.3.0 + +#include /* memcmp, memset, strlen */ +#include /* ptrdiff_t */ +#include /* exit */ + +#if defined(HASH_DEFINE_OWN_STDINT) && HASH_DEFINE_OWN_STDINT +/* This codepath is provided for backward compatibility, but I plan to remove it. */ +#warning "HASH_DEFINE_OWN_STDINT is deprecated; please use HASH_NO_STDINT instead" +typedef unsigned int uint32_t; +typedef unsigned char uint8_t; +#elif defined(HASH_NO_STDINT) && HASH_NO_STDINT +#else +#include /* uint8_t, uint32_t */ +#endif + +/* These macros use decltype or the earlier __typeof GNU extension. + As decltype is only available in newer compilers (VS2010 or gcc 4.3+ + when compiling c++ source) this code uses whatever method is needed + or, for VS2008 where neither is available, uses casting workarounds. */ +#if !defined(DECLTYPE) && !defined(NO_DECLTYPE) +#if defined(_MSC_VER) /* MS compiler */ +#if _MSC_VER >= 1600 && defined(__cplusplus) /* VS2010 or newer in C++ mode */ +#define DECLTYPE(x) (decltype(x)) +#else /* VS2008 or older (or VS2010 in C mode) */ +#define NO_DECLTYPE +#endif +#elif defined(__BORLANDC__) || defined(__ICCARM__) || defined(__LCC__) || defined(__WATCOMC__) +#define NO_DECLTYPE +#else /* GNU, Sun and other compilers */ +#define DECLTYPE(x) (__typeof(x)) +#endif +#endif + +#ifdef NO_DECLTYPE +#define DECLTYPE(x) +#define DECLTYPE_ASSIGN(dst,src) \ +do { \ + char **_da_dst = (char**)(&(dst)); \ + *_da_dst = (char*)(src); \ +} while (0) +#else +#define DECLTYPE_ASSIGN(dst,src) \ +do { \ + (dst) = DECLTYPE(dst)(src); \ +} while (0) +#endif + +#ifndef uthash_malloc +#define uthash_malloc(sz) malloc(sz) /* malloc fcn */ +#endif +#ifndef uthash_free +#define uthash_free(ptr,sz) free(ptr) /* free fcn */ +#endif +#ifndef uthash_bzero +#define uthash_bzero(a,n) memset(a,'\0',n) +#endif +#ifndef uthash_strlen +#define uthash_strlen(s) strlen(s) +#endif + +#ifndef HASH_FUNCTION +#define HASH_FUNCTION(keyptr,keylen,hashv) HASH_JEN(keyptr, keylen, hashv) +#endif + +#ifndef HASH_KEYCMP +#define HASH_KEYCMP(a,b,n) memcmp(a,b,n) +#endif + +#ifndef uthash_noexpand_fyi +#define uthash_noexpand_fyi(tbl) /* can be defined to log noexpand */ +#endif +#ifndef uthash_expand_fyi +#define uthash_expand_fyi(tbl) /* can be defined to log expands */ +#endif + +#ifndef HASH_NONFATAL_OOM +#define HASH_NONFATAL_OOM 0 +#endif + +#if HASH_NONFATAL_OOM +/* malloc failures can be recovered from */ + +#ifndef uthash_nonfatal_oom +#define uthash_nonfatal_oom(obj) do {} while (0) /* non-fatal OOM error */ +#endif + +#define HASH_RECORD_OOM(oomed) do { (oomed) = 1; } while (0) +#define IF_HASH_NONFATAL_OOM(x) x + +#else +/* malloc failures result in lost memory, hash tables are unusable */ + +#ifndef uthash_fatal +#define uthash_fatal(msg) exit(-1) /* fatal OOM error */ +#endif + +#define HASH_RECORD_OOM(oomed) uthash_fatal("out of memory") +#define IF_HASH_NONFATAL_OOM(x) + +#endif + +/* initial number of buckets */ +#define HASH_INITIAL_NUM_BUCKETS 32U /* initial number of buckets */ +#define HASH_INITIAL_NUM_BUCKETS_LOG2 5U /* lg2 of initial number of buckets */ +#define HASH_BKT_CAPACITY_THRESH 10U /* expand when bucket count reaches */ + +/* calculate the element whose hash handle address is hhp */ +#define ELMT_FROM_HH(tbl,hhp) ((void*)(((char*)(hhp)) - ((tbl)->hho))) +/* calculate the hash handle from element address elp */ +#define HH_FROM_ELMT(tbl,elp) ((UT_hash_handle*)(void*)(((char*)(elp)) + ((tbl)->hho))) + +#define HASH_ROLLBACK_BKT(hh, head, itemptrhh) \ +do { \ + struct UT_hash_handle *_hd_hh_item = (itemptrhh); \ + unsigned _hd_bkt; \ + HASH_TO_BKT(_hd_hh_item->hashv, (head)->hh.tbl->num_buckets, _hd_bkt); \ + (head)->hh.tbl->buckets[_hd_bkt].count++; \ + _hd_hh_item->hh_next = NULL; \ + _hd_hh_item->hh_prev = NULL; \ +} while (0) + +#define HASH_VALUE(keyptr,keylen,hashv) \ +do { \ + HASH_FUNCTION(keyptr, keylen, hashv); \ +} while (0) + +#define HASH_FIND_BYHASHVALUE(hh,head,keyptr,keylen,hashval,out) \ +do { \ + (out) = NULL; \ + if (head) { \ + unsigned _hf_bkt; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _hf_bkt); \ + if (HASH_BLOOM_TEST((head)->hh.tbl, hashval) != 0) { \ + HASH_FIND_IN_BKT((head)->hh.tbl, hh, (head)->hh.tbl->buckets[ _hf_bkt ], keyptr, keylen, hashval, out); \ + } \ + } \ +} while (0) + +#define HASH_FIND(hh,head,keyptr,keylen,out) \ +do { \ + (out) = NULL; \ + if (head) { \ + unsigned _hf_hashv; \ + HASH_VALUE(keyptr, keylen, _hf_hashv); \ + HASH_FIND_BYHASHVALUE(hh, head, keyptr, keylen, _hf_hashv, out); \ + } \ +} while (0) + +#ifdef HASH_BLOOM +#define HASH_BLOOM_BITLEN (1UL << HASH_BLOOM) +#define HASH_BLOOM_BYTELEN (HASH_BLOOM_BITLEN/8UL) + (((HASH_BLOOM_BITLEN%8UL)!=0UL) ? 1UL : 0UL) +#define HASH_BLOOM_MAKE(tbl,oomed) \ +do { \ + (tbl)->bloom_nbits = HASH_BLOOM; \ + (tbl)->bloom_bv = (uint8_t*)uthash_malloc(HASH_BLOOM_BYTELEN); \ + if (!(tbl)->bloom_bv) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero((tbl)->bloom_bv, HASH_BLOOM_BYTELEN); \ + (tbl)->bloom_sig = HASH_BLOOM_SIGNATURE; \ + } \ +} while (0) + +#define HASH_BLOOM_FREE(tbl) \ +do { \ + uthash_free((tbl)->bloom_bv, HASH_BLOOM_BYTELEN); \ +} while (0) + +#define HASH_BLOOM_BITSET(bv,idx) (bv[(idx)/8U] |= (1U << ((idx)%8U))) +#define HASH_BLOOM_BITTEST(bv,idx) (bv[(idx)/8U] & (1U << ((idx)%8U))) + +#define HASH_BLOOM_ADD(tbl,hashv) \ + HASH_BLOOM_BITSET((tbl)->bloom_bv, ((hashv) & (uint32_t)((1UL << (tbl)->bloom_nbits) - 1U))) + +#define HASH_BLOOM_TEST(tbl,hashv) \ + HASH_BLOOM_BITTEST((tbl)->bloom_bv, ((hashv) & (uint32_t)((1UL << (tbl)->bloom_nbits) - 1U))) + +#else +#define HASH_BLOOM_MAKE(tbl,oomed) +#define HASH_BLOOM_FREE(tbl) +#define HASH_BLOOM_ADD(tbl,hashv) +#define HASH_BLOOM_TEST(tbl,hashv) (1) +#define HASH_BLOOM_BYTELEN 0U +#endif + +#define HASH_MAKE_TABLE(hh,head,oomed) \ +do { \ + (head)->hh.tbl = (UT_hash_table*)uthash_malloc(sizeof(UT_hash_table)); \ + if (!(head)->hh.tbl) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head)->hh.tbl->tail = &((head)->hh); \ + (head)->hh.tbl->num_buckets = HASH_INITIAL_NUM_BUCKETS; \ + (head)->hh.tbl->log2_num_buckets = HASH_INITIAL_NUM_BUCKETS_LOG2; \ + (head)->hh.tbl->hho = (char*)(&(head)->hh) - (char*)(head); \ + (head)->hh.tbl->buckets = (UT_hash_bucket*)uthash_malloc( \ + HASH_INITIAL_NUM_BUCKETS * sizeof(struct UT_hash_bucket)); \ + (head)->hh.tbl->signature = HASH_SIGNATURE; \ + if (!(head)->hh.tbl->buckets) { \ + HASH_RECORD_OOM(oomed); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + } else { \ + uthash_bzero((head)->hh.tbl->buckets, \ + HASH_INITIAL_NUM_BUCKETS * sizeof(struct UT_hash_bucket)); \ + HASH_BLOOM_MAKE((head)->hh.tbl, oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (oomed) { \ + uthash_free((head)->hh.tbl->buckets, \ + HASH_INITIAL_NUM_BUCKETS*sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + } \ + ) \ + } \ + } \ +} while (0) + +#define HASH_REPLACE_BYHASHVALUE_INORDER(hh,head,fieldname,keylen_in,hashval,add,replaced,cmpfcn) \ +do { \ + (replaced) = NULL; \ + HASH_FIND_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, replaced); \ + if (replaced) { \ + HASH_DELETE(hh, head, replaced); \ + } \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, &((add)->fieldname), keylen_in, hashval, add, cmpfcn); \ +} while (0) + +#define HASH_REPLACE_BYHASHVALUE(hh,head,fieldname,keylen_in,hashval,add,replaced) \ +do { \ + (replaced) = NULL; \ + HASH_FIND_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, replaced); \ + if (replaced) { \ + HASH_DELETE(hh, head, replaced); \ + } \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, add); \ +} while (0) + +#define HASH_REPLACE(hh,head,fieldname,keylen_in,add,replaced) \ +do { \ + unsigned _hr_hashv; \ + HASH_VALUE(&((add)->fieldname), keylen_in, _hr_hashv); \ + HASH_REPLACE_BYHASHVALUE(hh, head, fieldname, keylen_in, _hr_hashv, add, replaced); \ +} while (0) + +#define HASH_REPLACE_INORDER(hh,head,fieldname,keylen_in,add,replaced,cmpfcn) \ +do { \ + unsigned _hr_hashv; \ + HASH_VALUE(&((add)->fieldname), keylen_in, _hr_hashv); \ + HASH_REPLACE_BYHASHVALUE_INORDER(hh, head, fieldname, keylen_in, _hr_hashv, add, replaced, cmpfcn); \ +} while (0) + +#define HASH_APPEND_LIST(hh, head, add) \ +do { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = ELMT_FROM_HH((head)->hh.tbl, (head)->hh.tbl->tail); \ + (head)->hh.tbl->tail->next = (add); \ + (head)->hh.tbl->tail = &((add)->hh); \ +} while (0) + +#define HASH_AKBI_INNER_LOOP(hh,head,add,cmpfcn) \ +do { \ + do { \ + if (cmpfcn(DECLTYPE(head)(_hs_iter), add) > 0) { \ + break; \ + } \ + } while ((_hs_iter = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->next)); \ +} while (0) + +#ifdef NO_DECLTYPE +#undef HASH_AKBI_INNER_LOOP +#define HASH_AKBI_INNER_LOOP(hh,head,add,cmpfcn) \ +do { \ + char *_hs_saved_head = (char*)(head); \ + do { \ + DECLTYPE_ASSIGN(head, _hs_iter); \ + if (cmpfcn(head, add) > 0) { \ + DECLTYPE_ASSIGN(head, _hs_saved_head); \ + break; \ + } \ + DECLTYPE_ASSIGN(head, _hs_saved_head); \ + } while ((_hs_iter = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->next)); \ +} while (0) +#endif + +#if HASH_NONFATAL_OOM + +#define HASH_ADD_TO_TABLE(hh,head,keyptr,keylen_in,hashval,add,oomed) \ +do { \ + if (!(oomed)) { \ + unsigned _ha_bkt; \ + (head)->hh.tbl->num_items++; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _ha_bkt); \ + HASH_ADD_TO_BKT((head)->hh.tbl->buckets[_ha_bkt], hh, &(add)->hh, oomed); \ + if (oomed) { \ + HASH_ROLLBACK_BKT(hh, head, &(add)->hh); \ + HASH_DELETE_HH(hh, head, &(add)->hh); \ + (add)->hh.tbl = NULL; \ + uthash_nonfatal_oom(add); \ + } else { \ + HASH_BLOOM_ADD((head)->hh.tbl, hashval); \ + HASH_EMIT_KEY(hh, head, keyptr, keylen_in); \ + } \ + } else { \ + (add)->hh.tbl = NULL; \ + uthash_nonfatal_oom(add); \ + } \ +} while (0) + +#else + +#define HASH_ADD_TO_TABLE(hh,head,keyptr,keylen_in,hashval,add,oomed) \ +do { \ + unsigned _ha_bkt; \ + (head)->hh.tbl->num_items++; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _ha_bkt); \ + HASH_ADD_TO_BKT((head)->hh.tbl->buckets[_ha_bkt], hh, &(add)->hh, oomed); \ + HASH_BLOOM_ADD((head)->hh.tbl, hashval); \ + HASH_EMIT_KEY(hh, head, keyptr, keylen_in); \ +} while (0) + +#endif + + +#define HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh,head,keyptr,keylen_in,hashval,add,cmpfcn) \ +do { \ + IF_HASH_NONFATAL_OOM( int _ha_oomed = 0; ) \ + (add)->hh.hashv = (hashval); \ + (add)->hh.key = (char*) (keyptr); \ + (add)->hh.keylen = (unsigned) (keylen_in); \ + if (!(head)) { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = NULL; \ + HASH_MAKE_TABLE(hh, add, _ha_oomed); \ + IF_HASH_NONFATAL_OOM( if (!_ha_oomed) { ) \ + (head) = (add); \ + IF_HASH_NONFATAL_OOM( } ) \ + } else { \ + void *_hs_iter = (head); \ + (add)->hh.tbl = (head)->hh.tbl; \ + HASH_AKBI_INNER_LOOP(hh, head, add, cmpfcn); \ + if (_hs_iter) { \ + (add)->hh.next = _hs_iter; \ + if (((add)->hh.prev = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->prev)) { \ + HH_FROM_ELMT((head)->hh.tbl, (add)->hh.prev)->next = (add); \ + } else { \ + (head) = (add); \ + } \ + HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->prev = (add); \ + } else { \ + HASH_APPEND_LIST(hh, head, add); \ + } \ + } \ + HASH_ADD_TO_TABLE(hh, head, keyptr, keylen_in, hashval, add, _ha_oomed); \ + HASH_FSCK(hh, head, "HASH_ADD_KEYPTR_BYHASHVALUE_INORDER"); \ +} while (0) + +#define HASH_ADD_KEYPTR_INORDER(hh,head,keyptr,keylen_in,add,cmpfcn) \ +do { \ + unsigned _hs_hashv; \ + HASH_VALUE(keyptr, keylen_in, _hs_hashv); \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, keyptr, keylen_in, _hs_hashv, add, cmpfcn); \ +} while (0) + +#define HASH_ADD_BYHASHVALUE_INORDER(hh,head,fieldname,keylen_in,hashval,add,cmpfcn) \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, &((add)->fieldname), keylen_in, hashval, add, cmpfcn) + +#define HASH_ADD_INORDER(hh,head,fieldname,keylen_in,add,cmpfcn) \ + HASH_ADD_KEYPTR_INORDER(hh, head, &((add)->fieldname), keylen_in, add, cmpfcn) + +#define HASH_ADD_KEYPTR_BYHASHVALUE(hh,head,keyptr,keylen_in,hashval,add) \ +do { \ + IF_HASH_NONFATAL_OOM( int _ha_oomed = 0; ) \ + (add)->hh.hashv = (hashval); \ + (add)->hh.key = (const void*) (keyptr); \ + (add)->hh.keylen = (unsigned) (keylen_in); \ + if (!(head)) { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = NULL; \ + HASH_MAKE_TABLE(hh, add, _ha_oomed); \ + IF_HASH_NONFATAL_OOM( if (!_ha_oomed) { ) \ + (head) = (add); \ + IF_HASH_NONFATAL_OOM( } ) \ + } else { \ + (add)->hh.tbl = (head)->hh.tbl; \ + HASH_APPEND_LIST(hh, head, add); \ + } \ + HASH_ADD_TO_TABLE(hh, head, keyptr, keylen_in, hashval, add, _ha_oomed); \ + HASH_FSCK(hh, head, "HASH_ADD_KEYPTR_BYHASHVALUE"); \ +} while (0) + +#define HASH_ADD_KEYPTR(hh,head,keyptr,keylen_in,add) \ +do { \ + unsigned _ha_hashv; \ + HASH_VALUE(keyptr, keylen_in, _ha_hashv); \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, keyptr, keylen_in, _ha_hashv, add); \ +} while (0) + +#define HASH_ADD_BYHASHVALUE(hh,head,fieldname,keylen_in,hashval,add) \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, add) + +#define HASH_ADD(hh,head,fieldname,keylen_in,add) \ + HASH_ADD_KEYPTR(hh, head, &((add)->fieldname), keylen_in, add) + +#define HASH_TO_BKT(hashv,num_bkts,bkt) \ +do { \ + bkt = ((hashv) & ((num_bkts) - 1U)); \ +} while (0) + +/* delete "delptr" from the hash table. + * "the usual" patch-up process for the app-order doubly-linked-list. + * The use of _hd_hh_del below deserves special explanation. + * These used to be expressed using (delptr) but that led to a bug + * if someone used the same symbol for the head and deletee, like + * HASH_DELETE(hh,users,users); + * We want that to work, but by changing the head (users) below + * we were forfeiting our ability to further refer to the deletee (users) + * in the patch-up process. Solution: use scratch space to + * copy the deletee pointer, then the latter references are via that + * scratch pointer rather than through the repointed (users) symbol. + */ +#define HASH_DELETE(hh,head,delptr) \ + HASH_DELETE_HH(hh, head, &(delptr)->hh) + +#define HASH_DELETE_HH(hh,head,delptrhh) \ +do { \ + struct UT_hash_handle *_hd_hh_del = (delptrhh); \ + if ((_hd_hh_del->prev == NULL) && (_hd_hh_del->next == NULL)) { \ + HASH_BLOOM_FREE((head)->hh.tbl); \ + uthash_free((head)->hh.tbl->buckets, \ + (head)->hh.tbl->num_buckets * sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head) = NULL; \ + } else { \ + unsigned _hd_bkt; \ + if (_hd_hh_del == (head)->hh.tbl->tail) { \ + (head)->hh.tbl->tail = HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->prev); \ + } \ + if (_hd_hh_del->prev != NULL) { \ + HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->prev)->next = _hd_hh_del->next; \ + } else { \ + DECLTYPE_ASSIGN(head, _hd_hh_del->next); \ + } \ + if (_hd_hh_del->next != NULL) { \ + HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->next)->prev = _hd_hh_del->prev; \ + } \ + HASH_TO_BKT(_hd_hh_del->hashv, (head)->hh.tbl->num_buckets, _hd_bkt); \ + HASH_DEL_IN_BKT((head)->hh.tbl->buckets[_hd_bkt], _hd_hh_del); \ + (head)->hh.tbl->num_items--; \ + } \ + HASH_FSCK(hh, head, "HASH_DELETE_HH"); \ +} while (0) + +/* convenience forms of HASH_FIND/HASH_ADD/HASH_DEL */ +#define HASH_FIND_STR(head,findstr,out) \ +do { \ + unsigned _uthash_hfstr_keylen = (unsigned)uthash_strlen(findstr); \ + HASH_FIND(hh, head, findstr, _uthash_hfstr_keylen, out); \ +} while (0) +#define HASH_ADD_STR(head,strfield,add) \ +do { \ + unsigned _uthash_hastr_keylen = (unsigned)uthash_strlen((add)->strfield); \ + HASH_ADD(hh, head, strfield[0], _uthash_hastr_keylen, add); \ +} while (0) +#define HASH_REPLACE_STR(head,strfield,add,replaced) \ +do { \ + unsigned _uthash_hrstr_keylen = (unsigned)uthash_strlen((add)->strfield); \ + HASH_REPLACE(hh, head, strfield[0], _uthash_hrstr_keylen, add, replaced); \ +} while (0) +#define HASH_FIND_INT(head,findint,out) \ + HASH_FIND(hh,head,findint,sizeof(int),out) +#define HASH_ADD_INT(head,intfield,add) \ + HASH_ADD(hh,head,intfield,sizeof(int),add) +#define HASH_REPLACE_INT(head,intfield,add,replaced) \ + HASH_REPLACE(hh,head,intfield,sizeof(int),add,replaced) +#define HASH_FIND_PTR(head,findptr,out) \ + HASH_FIND(hh,head,findptr,sizeof(void *),out) +#define HASH_ADD_PTR(head,ptrfield,add) \ + HASH_ADD(hh,head,ptrfield,sizeof(void *),add) +#define HASH_REPLACE_PTR(head,ptrfield,add,replaced) \ + HASH_REPLACE(hh,head,ptrfield,sizeof(void *),add,replaced) +#define HASH_DEL(head,delptr) \ + HASH_DELETE(hh,head,delptr) + +/* HASH_FSCK checks hash integrity on every add/delete when HASH_DEBUG is defined. + * This is for uthash developer only; it compiles away if HASH_DEBUG isn't defined. + */ +#ifdef HASH_DEBUG +#include /* fprintf, stderr */ +#define HASH_OOPS(...) do { fprintf(stderr, __VA_ARGS__); exit(-1); } while (0) +#define HASH_FSCK(hh,head,where) \ +do { \ + struct UT_hash_handle *_thh; \ + if (head) { \ + unsigned _bkt_i; \ + unsigned _count = 0; \ + char *_prev; \ + for (_bkt_i = 0; _bkt_i < (head)->hh.tbl->num_buckets; ++_bkt_i) { \ + unsigned _bkt_count = 0; \ + _thh = (head)->hh.tbl->buckets[_bkt_i].hh_head; \ + _prev = NULL; \ + while (_thh) { \ + if (_prev != (char*)(_thh->hh_prev)) { \ + HASH_OOPS("%s: invalid hh_prev %p, actual %p\n", \ + (where), (void*)_thh->hh_prev, (void*)_prev); \ + } \ + _bkt_count++; \ + _prev = (char*)(_thh); \ + _thh = _thh->hh_next; \ + } \ + _count += _bkt_count; \ + if ((head)->hh.tbl->buckets[_bkt_i].count != _bkt_count) { \ + HASH_OOPS("%s: invalid bucket count %u, actual %u\n", \ + (where), (head)->hh.tbl->buckets[_bkt_i].count, _bkt_count); \ + } \ + } \ + if (_count != (head)->hh.tbl->num_items) { \ + HASH_OOPS("%s: invalid hh item count %u, actual %u\n", \ + (where), (head)->hh.tbl->num_items, _count); \ + } \ + _count = 0; \ + _prev = NULL; \ + _thh = &(head)->hh; \ + while (_thh) { \ + _count++; \ + if (_prev != (char*)_thh->prev) { \ + HASH_OOPS("%s: invalid prev %p, actual %p\n", \ + (where), (void*)_thh->prev, (void*)_prev); \ + } \ + _prev = (char*)ELMT_FROM_HH((head)->hh.tbl, _thh); \ + _thh = (_thh->next ? HH_FROM_ELMT((head)->hh.tbl, _thh->next) : NULL); \ + } \ + if (_count != (head)->hh.tbl->num_items) { \ + HASH_OOPS("%s: invalid app item count %u, actual %u\n", \ + (where), (head)->hh.tbl->num_items, _count); \ + } \ + } \ +} while (0) +#else +#define HASH_FSCK(hh,head,where) +#endif + +/* When compiled with -DHASH_EMIT_KEYS, length-prefixed keys are emitted to + * the descriptor to which this macro is defined for tuning the hash function. + * The app can #include to get the prototype for write(2). */ +#ifdef HASH_EMIT_KEYS +#define HASH_EMIT_KEY(hh,head,keyptr,fieldlen) \ +do { \ + unsigned _klen = fieldlen; \ + write(HASH_EMIT_KEYS, &_klen, sizeof(_klen)); \ + write(HASH_EMIT_KEYS, keyptr, (unsigned long)fieldlen); \ +} while (0) +#else +#define HASH_EMIT_KEY(hh,head,keyptr,fieldlen) +#endif + +/* The Bernstein hash function, used in Perl prior to v5.6. Note (x<<5+x)=x*33. */ +#define HASH_BER(key,keylen,hashv) \ +do { \ + unsigned _hb_keylen = (unsigned)keylen; \ + const unsigned char *_hb_key = (const unsigned char*)(key); \ + (hashv) = 0; \ + while (_hb_keylen-- != 0U) { \ + (hashv) = (((hashv) << 5) + (hashv)) + *_hb_key++; \ + } \ +} while (0) + + +/* SAX/FNV/OAT/JEN hash functions are macro variants of those listed at + * http://eternallyconfuzzled.com/tuts/algorithms/jsw_tut_hashing.aspx */ +#define HASH_SAX(key,keylen,hashv) \ +do { \ + unsigned _sx_i; \ + const unsigned char *_hs_key = (const unsigned char*)(key); \ + hashv = 0; \ + for (_sx_i=0; _sx_i < keylen; _sx_i++) { \ + hashv ^= (hashv << 5) + (hashv >> 2) + _hs_key[_sx_i]; \ + } \ +} while (0) +/* FNV-1a variation */ +#define HASH_FNV(key,keylen,hashv) \ +do { \ + unsigned _fn_i; \ + const unsigned char *_hf_key = (const unsigned char*)(key); \ + (hashv) = 2166136261U; \ + for (_fn_i=0; _fn_i < keylen; _fn_i++) { \ + hashv = hashv ^ _hf_key[_fn_i]; \ + hashv = hashv * 16777619U; \ + } \ +} while (0) + +#define HASH_OAT(key,keylen,hashv) \ +do { \ + unsigned _ho_i; \ + const unsigned char *_ho_key=(const unsigned char*)(key); \ + hashv = 0; \ + for(_ho_i=0; _ho_i < keylen; _ho_i++) { \ + hashv += _ho_key[_ho_i]; \ + hashv += (hashv << 10); \ + hashv ^= (hashv >> 6); \ + } \ + hashv += (hashv << 3); \ + hashv ^= (hashv >> 11); \ + hashv += (hashv << 15); \ +} while (0) + +#define HASH_JEN_MIX(a,b,c) \ +do { \ + a -= b; a -= c; a ^= ( c >> 13 ); \ + b -= c; b -= a; b ^= ( a << 8 ); \ + c -= a; c -= b; c ^= ( b >> 13 ); \ + a -= b; a -= c; a ^= ( c >> 12 ); \ + b -= c; b -= a; b ^= ( a << 16 ); \ + c -= a; c -= b; c ^= ( b >> 5 ); \ + a -= b; a -= c; a ^= ( c >> 3 ); \ + b -= c; b -= a; b ^= ( a << 10 ); \ + c -= a; c -= b; c ^= ( b >> 15 ); \ +} while (0) + +#define HASH_JEN(key,keylen,hashv) \ +do { \ + unsigned _hj_i,_hj_j,_hj_k; \ + unsigned const char *_hj_key=(unsigned const char*)(key); \ + hashv = 0xfeedbeefu; \ + _hj_i = _hj_j = 0x9e3779b9u; \ + _hj_k = (unsigned)(keylen); \ + while (_hj_k >= 12U) { \ + _hj_i += (_hj_key[0] + ( (unsigned)_hj_key[1] << 8 ) \ + + ( (unsigned)_hj_key[2] << 16 ) \ + + ( (unsigned)_hj_key[3] << 24 ) ); \ + _hj_j += (_hj_key[4] + ( (unsigned)_hj_key[5] << 8 ) \ + + ( (unsigned)_hj_key[6] << 16 ) \ + + ( (unsigned)_hj_key[7] << 24 ) ); \ + hashv += (_hj_key[8] + ( (unsigned)_hj_key[9] << 8 ) \ + + ( (unsigned)_hj_key[10] << 16 ) \ + + ( (unsigned)_hj_key[11] << 24 ) ); \ + \ + HASH_JEN_MIX(_hj_i, _hj_j, hashv); \ + \ + _hj_key += 12; \ + _hj_k -= 12U; \ + } \ + hashv += (unsigned)(keylen); \ + switch ( _hj_k ) { \ + case 11: hashv += ( (unsigned)_hj_key[10] << 24 ); /* FALLTHROUGH */ \ + case 10: hashv += ( (unsigned)_hj_key[9] << 16 ); /* FALLTHROUGH */ \ + case 9: hashv += ( (unsigned)_hj_key[8] << 8 ); /* FALLTHROUGH */ \ + case 8: _hj_j += ( (unsigned)_hj_key[7] << 24 ); /* FALLTHROUGH */ \ + case 7: _hj_j += ( (unsigned)_hj_key[6] << 16 ); /* FALLTHROUGH */ \ + case 6: _hj_j += ( (unsigned)_hj_key[5] << 8 ); /* FALLTHROUGH */ \ + case 5: _hj_j += _hj_key[4]; /* FALLTHROUGH */ \ + case 4: _hj_i += ( (unsigned)_hj_key[3] << 24 ); /* FALLTHROUGH */ \ + case 3: _hj_i += ( (unsigned)_hj_key[2] << 16 ); /* FALLTHROUGH */ \ + case 2: _hj_i += ( (unsigned)_hj_key[1] << 8 ); /* FALLTHROUGH */ \ + case 1: _hj_i += _hj_key[0]; /* FALLTHROUGH */ \ + default: ; \ + } \ + HASH_JEN_MIX(_hj_i, _hj_j, hashv); \ +} while (0) + +/* The Paul Hsieh hash function */ +#undef get16bits +#if (defined(__GNUC__) && defined(__i386__)) || defined(__WATCOMC__) \ + || defined(_MSC_VER) || defined (__BORLANDC__) || defined (__TURBOC__) +#define get16bits(d) (*((const uint16_t *) (d))) +#endif + +#if !defined (get16bits) +#define get16bits(d) ((((uint32_t)(((const uint8_t *)(d))[1])) << 8) \ + +(uint32_t)(((const uint8_t *)(d))[0]) ) +#endif +#define HASH_SFH(key,keylen,hashv) \ +do { \ + unsigned const char *_sfh_key=(unsigned const char*)(key); \ + uint32_t _sfh_tmp, _sfh_len = (uint32_t)keylen; \ + \ + unsigned _sfh_rem = _sfh_len & 3U; \ + _sfh_len >>= 2; \ + hashv = 0xcafebabeu; \ + \ + /* Main loop */ \ + for (;_sfh_len > 0U; _sfh_len--) { \ + hashv += get16bits (_sfh_key); \ + _sfh_tmp = ((uint32_t)(get16bits (_sfh_key+2)) << 11) ^ hashv; \ + hashv = (hashv << 16) ^ _sfh_tmp; \ + _sfh_key += 2U*sizeof (uint16_t); \ + hashv += hashv >> 11; \ + } \ + \ + /* Handle end cases */ \ + switch (_sfh_rem) { \ + case 3: hashv += get16bits (_sfh_key); \ + hashv ^= hashv << 16; \ + hashv ^= (uint32_t)(_sfh_key[sizeof (uint16_t)]) << 18; \ + hashv += hashv >> 11; \ + break; \ + case 2: hashv += get16bits (_sfh_key); \ + hashv ^= hashv << 11; \ + hashv += hashv >> 17; \ + break; \ + case 1: hashv += *_sfh_key; \ + hashv ^= hashv << 10; \ + hashv += hashv >> 1; \ + break; \ + default: ; \ + } \ + \ + /* Force "avalanching" of final 127 bits */ \ + hashv ^= hashv << 3; \ + hashv += hashv >> 5; \ + hashv ^= hashv << 4; \ + hashv += hashv >> 17; \ + hashv ^= hashv << 25; \ + hashv += hashv >> 6; \ +} while (0) + +/* iterate over items in a known bucket to find desired item */ +#define HASH_FIND_IN_BKT(tbl,hh,head,keyptr,keylen_in,hashval,out) \ +do { \ + if ((head).hh_head != NULL) { \ + DECLTYPE_ASSIGN(out, ELMT_FROM_HH(tbl, (head).hh_head)); \ + } else { \ + (out) = NULL; \ + } \ + while ((out) != NULL) { \ + if ((out)->hh.hashv == (hashval) && (out)->hh.keylen == (keylen_in)) { \ + if (HASH_KEYCMP((out)->hh.key, keyptr, keylen_in) == 0) { \ + break; \ + } \ + } \ + if ((out)->hh.hh_next != NULL) { \ + DECLTYPE_ASSIGN(out, ELMT_FROM_HH(tbl, (out)->hh.hh_next)); \ + } else { \ + (out) = NULL; \ + } \ + } \ +} while (0) + +/* add an item to a bucket */ +#define HASH_ADD_TO_BKT(head,hh,addhh,oomed) \ +do { \ + UT_hash_bucket *_ha_head = &(head); \ + _ha_head->count++; \ + (addhh)->hh_next = _ha_head->hh_head; \ + (addhh)->hh_prev = NULL; \ + if (_ha_head->hh_head != NULL) { \ + _ha_head->hh_head->hh_prev = (addhh); \ + } \ + _ha_head->hh_head = (addhh); \ + if ((_ha_head->count >= ((_ha_head->expand_mult + 1U) * HASH_BKT_CAPACITY_THRESH)) \ + && !(addhh)->tbl->noexpand) { \ + HASH_EXPAND_BUCKETS(addhh,(addhh)->tbl, oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (oomed) { \ + HASH_DEL_IN_BKT(head,addhh); \ + } \ + ) \ + } \ +} while (0) + +/* remove an item from a given bucket */ +#define HASH_DEL_IN_BKT(head,delhh) \ +do { \ + UT_hash_bucket *_hd_head = &(head); \ + _hd_head->count--; \ + if (_hd_head->hh_head == (delhh)) { \ + _hd_head->hh_head = (delhh)->hh_next; \ + } \ + if ((delhh)->hh_prev) { \ + (delhh)->hh_prev->hh_next = (delhh)->hh_next; \ + } \ + if ((delhh)->hh_next) { \ + (delhh)->hh_next->hh_prev = (delhh)->hh_prev; \ + } \ +} while (0) + +/* Bucket expansion has the effect of doubling the number of buckets + * and redistributing the items into the new buckets. Ideally the + * items will distribute more or less evenly into the new buckets + * (the extent to which this is true is a measure of the quality of + * the hash function as it applies to the key domain). + * + * With the items distributed into more buckets, the chain length + * (item count) in each bucket is reduced. Thus by expanding buckets + * the hash keeps a bound on the chain length. This bounded chain + * length is the essence of how a hash provides constant time lookup. + * + * The calculation of tbl->ideal_chain_maxlen below deserves some + * explanation. First, keep in mind that we're calculating the ideal + * maximum chain length based on the *new* (doubled) bucket count. + * In fractions this is just n/b (n=number of items,b=new num buckets). + * Since the ideal chain length is an integer, we want to calculate + * ceil(n/b). We don't depend on floating point arithmetic in this + * hash, so to calculate ceil(n/b) with integers we could write + * + * ceil(n/b) = (n/b) + ((n%b)?1:0) + * + * and in fact a previous version of this hash did just that. + * But now we have improved things a bit by recognizing that b is + * always a power of two. We keep its base 2 log handy (call it lb), + * so now we can write this with a bit shift and logical AND: + * + * ceil(n/b) = (n>>lb) + ( (n & (b-1)) ? 1:0) + * + */ +#define HASH_EXPAND_BUCKETS(hh,tbl,oomed) \ +do { \ + unsigned _he_bkt; \ + unsigned _he_bkt_i; \ + struct UT_hash_handle *_he_thh, *_he_hh_nxt; \ + UT_hash_bucket *_he_new_buckets, *_he_newbkt; \ + _he_new_buckets = (UT_hash_bucket*)uthash_malloc( \ + sizeof(struct UT_hash_bucket) * (tbl)->num_buckets * 2U); \ + if (!_he_new_buckets) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero(_he_new_buckets, \ + sizeof(struct UT_hash_bucket) * (tbl)->num_buckets * 2U); \ + (tbl)->ideal_chain_maxlen = \ + ((tbl)->num_items >> ((tbl)->log2_num_buckets+1U)) + \ + ((((tbl)->num_items & (((tbl)->num_buckets*2U)-1U)) != 0U) ? 1U : 0U); \ + (tbl)->nonideal_items = 0; \ + for (_he_bkt_i = 0; _he_bkt_i < (tbl)->num_buckets; _he_bkt_i++) { \ + _he_thh = (tbl)->buckets[ _he_bkt_i ].hh_head; \ + while (_he_thh != NULL) { \ + _he_hh_nxt = _he_thh->hh_next; \ + HASH_TO_BKT(_he_thh->hashv, (tbl)->num_buckets * 2U, _he_bkt); \ + _he_newbkt = &(_he_new_buckets[_he_bkt]); \ + if (++(_he_newbkt->count) > (tbl)->ideal_chain_maxlen) { \ + (tbl)->nonideal_items++; \ + if (_he_newbkt->count > _he_newbkt->expand_mult * (tbl)->ideal_chain_maxlen) { \ + _he_newbkt->expand_mult++; \ + } \ + } \ + _he_thh->hh_prev = NULL; \ + _he_thh->hh_next = _he_newbkt->hh_head; \ + if (_he_newbkt->hh_head != NULL) { \ + _he_newbkt->hh_head->hh_prev = _he_thh; \ + } \ + _he_newbkt->hh_head = _he_thh; \ + _he_thh = _he_hh_nxt; \ + } \ + } \ + uthash_free((tbl)->buckets, (tbl)->num_buckets * sizeof(struct UT_hash_bucket)); \ + (tbl)->num_buckets *= 2U; \ + (tbl)->log2_num_buckets++; \ + (tbl)->buckets = _he_new_buckets; \ + (tbl)->ineff_expands = ((tbl)->nonideal_items > ((tbl)->num_items >> 1)) ? \ + ((tbl)->ineff_expands+1U) : 0U; \ + if ((tbl)->ineff_expands > 1U) { \ + (tbl)->noexpand = 1; \ + uthash_noexpand_fyi(tbl); \ + } \ + uthash_expand_fyi(tbl); \ + } \ +} while (0) + + +/* This is an adaptation of Simon Tatham's O(n log(n)) mergesort */ +/* Note that HASH_SORT assumes the hash handle name to be hh. + * HASH_SRT was added to allow the hash handle name to be passed in. */ +#define HASH_SORT(head,cmpfcn) HASH_SRT(hh,head,cmpfcn) +#define HASH_SRT(hh,head,cmpfcn) \ +do { \ + unsigned _hs_i; \ + unsigned _hs_looping,_hs_nmerges,_hs_insize,_hs_psize,_hs_qsize; \ + struct UT_hash_handle *_hs_p, *_hs_q, *_hs_e, *_hs_list, *_hs_tail; \ + if (head != NULL) { \ + _hs_insize = 1; \ + _hs_looping = 1; \ + _hs_list = &((head)->hh); \ + while (_hs_looping != 0U) { \ + _hs_p = _hs_list; \ + _hs_list = NULL; \ + _hs_tail = NULL; \ + _hs_nmerges = 0; \ + while (_hs_p != NULL) { \ + _hs_nmerges++; \ + _hs_q = _hs_p; \ + _hs_psize = 0; \ + for (_hs_i = 0; _hs_i < _hs_insize; ++_hs_i) { \ + _hs_psize++; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + if (_hs_q == NULL) { \ + break; \ + } \ + } \ + _hs_qsize = _hs_insize; \ + while ((_hs_psize != 0U) || ((_hs_qsize != 0U) && (_hs_q != NULL))) { \ + if (_hs_psize == 0U) { \ + _hs_e = _hs_q; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + _hs_qsize--; \ + } else if ((_hs_qsize == 0U) || (_hs_q == NULL)) { \ + _hs_e = _hs_p; \ + if (_hs_p != NULL) { \ + _hs_p = ((_hs_p->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_p->next) : NULL); \ + } \ + _hs_psize--; \ + } else if ((cmpfcn( \ + DECLTYPE(head)(ELMT_FROM_HH((head)->hh.tbl, _hs_p)), \ + DECLTYPE(head)(ELMT_FROM_HH((head)->hh.tbl, _hs_q)) \ + )) <= 0) { \ + _hs_e = _hs_p; \ + if (_hs_p != NULL) { \ + _hs_p = ((_hs_p->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_p->next) : NULL); \ + } \ + _hs_psize--; \ + } else { \ + _hs_e = _hs_q; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + _hs_qsize--; \ + } \ + if ( _hs_tail != NULL ) { \ + _hs_tail->next = ((_hs_e != NULL) ? \ + ELMT_FROM_HH((head)->hh.tbl, _hs_e) : NULL); \ + } else { \ + _hs_list = _hs_e; \ + } \ + if (_hs_e != NULL) { \ + _hs_e->prev = ((_hs_tail != NULL) ? \ + ELMT_FROM_HH((head)->hh.tbl, _hs_tail) : NULL); \ + } \ + _hs_tail = _hs_e; \ + } \ + _hs_p = _hs_q; \ + } \ + if (_hs_tail != NULL) { \ + _hs_tail->next = NULL; \ + } \ + if (_hs_nmerges <= 1U) { \ + _hs_looping = 0; \ + (head)->hh.tbl->tail = _hs_tail; \ + DECLTYPE_ASSIGN(head, ELMT_FROM_HH((head)->hh.tbl, _hs_list)); \ + } \ + _hs_insize *= 2U; \ + } \ + HASH_FSCK(hh, head, "HASH_SRT"); \ + } \ +} while (0) + +/* This function selects items from one hash into another hash. + * The end result is that the selected items have dual presence + * in both hashes. There is no copy of the items made; rather + * they are added into the new hash through a secondary hash + * hash handle that must be present in the structure. */ +#define HASH_SELECT(hh_dst, dst, hh_src, src, cond) \ +do { \ + unsigned _src_bkt, _dst_bkt; \ + void *_last_elt = NULL, *_elt; \ + UT_hash_handle *_src_hh, *_dst_hh, *_last_elt_hh=NULL; \ + ptrdiff_t _dst_hho = ((char*)(&(dst)->hh_dst) - (char*)(dst)); \ + if ((src) != NULL) { \ + for (_src_bkt=0; _src_bkt < (src)->hh_src.tbl->num_buckets; _src_bkt++) { \ + for (_src_hh = (src)->hh_src.tbl->buckets[_src_bkt].hh_head; \ + _src_hh != NULL; \ + _src_hh = _src_hh->hh_next) { \ + _elt = ELMT_FROM_HH((src)->hh_src.tbl, _src_hh); \ + if (cond(_elt)) { \ + IF_HASH_NONFATAL_OOM( int _hs_oomed = 0; ) \ + _dst_hh = (UT_hash_handle*)(void*)(((char*)_elt) + _dst_hho); \ + _dst_hh->key = _src_hh->key; \ + _dst_hh->keylen = _src_hh->keylen; \ + _dst_hh->hashv = _src_hh->hashv; \ + _dst_hh->prev = _last_elt; \ + _dst_hh->next = NULL; \ + if (_last_elt_hh != NULL) { \ + _last_elt_hh->next = _elt; \ + } \ + if ((dst) == NULL) { \ + DECLTYPE_ASSIGN(dst, _elt); \ + HASH_MAKE_TABLE(hh_dst, dst, _hs_oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (_hs_oomed) { \ + uthash_nonfatal_oom(_elt); \ + (dst) = NULL; \ + continue; \ + } \ + ) \ + } else { \ + _dst_hh->tbl = (dst)->hh_dst.tbl; \ + } \ + HASH_TO_BKT(_dst_hh->hashv, _dst_hh->tbl->num_buckets, _dst_bkt); \ + HASH_ADD_TO_BKT(_dst_hh->tbl->buckets[_dst_bkt], hh_dst, _dst_hh, _hs_oomed); \ + (dst)->hh_dst.tbl->num_items++; \ + IF_HASH_NONFATAL_OOM( \ + if (_hs_oomed) { \ + HASH_ROLLBACK_BKT(hh_dst, dst, _dst_hh); \ + HASH_DELETE_HH(hh_dst, dst, _dst_hh); \ + _dst_hh->tbl = NULL; \ + uthash_nonfatal_oom(_elt); \ + continue; \ + } \ + ) \ + HASH_BLOOM_ADD(_dst_hh->tbl, _dst_hh->hashv); \ + _last_elt = _elt; \ + _last_elt_hh = _dst_hh; \ + } \ + } \ + } \ + } \ + HASH_FSCK(hh_dst, dst, "HASH_SELECT"); \ +} while (0) + +#define HASH_CLEAR(hh,head) \ +do { \ + if ((head) != NULL) { \ + HASH_BLOOM_FREE((head)->hh.tbl); \ + uthash_free((head)->hh.tbl->buckets, \ + (head)->hh.tbl->num_buckets*sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head) = NULL; \ + } \ +} while (0) + +#define HASH_OVERHEAD(hh,head) \ + (((head) != NULL) ? ( \ + (size_t)(((head)->hh.tbl->num_items * sizeof(UT_hash_handle)) + \ + ((head)->hh.tbl->num_buckets * sizeof(UT_hash_bucket)) + \ + sizeof(UT_hash_table) + \ + (HASH_BLOOM_BYTELEN))) : 0U) + +#ifdef NO_DECLTYPE +#define HASH_ITER(hh,head,el,tmp) \ +for(((el)=(head)), ((*(char**)(&(tmp)))=(char*)((head!=NULL)?(head)->hh.next:NULL)); \ + (el) != NULL; ((el)=(tmp)), ((*(char**)(&(tmp)))=(char*)((tmp!=NULL)?(tmp)->hh.next:NULL))) +#else +#define HASH_ITER(hh,head,el,tmp) \ +for(((el)=(head)), ((tmp)=DECLTYPE(el)((head!=NULL)?(head)->hh.next:NULL)); \ + (el) != NULL; ((el)=(tmp)), ((tmp)=DECLTYPE(el)((tmp!=NULL)?(tmp)->hh.next:NULL))) +#endif + +/* obtain a count of items in the hash */ +#define HASH_COUNT(head) HASH_CNT(hh,head) +#define HASH_CNT(hh,head) ((head != NULL)?((head)->hh.tbl->num_items):0U) + +typedef struct UT_hash_bucket { + struct UT_hash_handle *hh_head; + unsigned count; + + /* expand_mult is normally set to 0. In this situation, the max chain length + * threshold is enforced at its default value, HASH_BKT_CAPACITY_THRESH. (If + * the bucket's chain exceeds this length, bucket expansion is triggered). + * However, setting expand_mult to a non-zero value delays bucket expansion + * (that would be triggered by additions to this particular bucket) + * until its chain length reaches a *multiple* of HASH_BKT_CAPACITY_THRESH. + * (The multiplier is simply expand_mult+1). The whole idea of this + * multiplier is to reduce bucket expansions, since they are expensive, in + * situations where we know that a particular bucket tends to be overused. + * It is better to let its chain length grow to a longer yet-still-bounded + * value, than to do an O(n) bucket expansion too often. + */ + unsigned expand_mult; + +} UT_hash_bucket; + +/* random signature used only to find hash tables in external analysis */ +#define HASH_SIGNATURE 0xa0111fe1u +#define HASH_BLOOM_SIGNATURE 0xb12220f2u + +typedef struct UT_hash_table { + UT_hash_bucket *buckets; + unsigned num_buckets, log2_num_buckets; + unsigned num_items; + struct UT_hash_handle *tail; /* tail hh in app order, for fast append */ + ptrdiff_t hho; /* hash handle offset (byte pos of hash handle in element */ + + /* in an ideal situation (all buckets used equally), no bucket would have + * more than ceil(#items/#buckets) items. that's the ideal chain length. */ + unsigned ideal_chain_maxlen; + + /* nonideal_items is the number of items in the hash whose chain position + * exceeds the ideal chain maxlen. these items pay the penalty for an uneven + * hash distribution; reaching them in a chain traversal takes >ideal steps */ + unsigned nonideal_items; + + /* ineffective expands occur when a bucket doubling was performed, but + * afterward, more than half the items in the hash had nonideal chain + * positions. If this happens on two consecutive expansions we inhibit any + * further expansion, as it's not helping; this happens when the hash + * function isn't a good fit for the key domain. When expansion is inhibited + * the hash will still work, albeit no longer in constant time. */ + unsigned ineff_expands, noexpand; + + uint32_t signature; /* used only to find hash tables in external analysis */ +#ifdef HASH_BLOOM + uint32_t bloom_sig; /* used only to test bloom exists in external analysis */ + uint8_t *bloom_bv; + uint8_t bloom_nbits; +#endif + +} UT_hash_table; + +typedef struct UT_hash_handle { + struct UT_hash_table *tbl; + void *prev; /* prev element in app order */ + void *next; /* next element in app order */ + struct UT_hash_handle *hh_prev; /* previous hh in bucket order */ + struct UT_hash_handle *hh_next; /* next hh in bucket order */ + const void *key; /* ptr to enclosing struct's key */ + unsigned keylen; /* enclosing struct's key len */ + unsigned hashv; /* result of hash-fcn(key) */ +} UT_hash_handle; + +#endif /* UTHASH_H */ diff --git a/tools/sdk/esp32/include/coap/libcoap/include/coap3/utlist.h b/tools/sdk/esp32/include/coap/libcoap/include/coap3/utlist.h new file mode 100644 index 00000000000..1979448a7b9 --- /dev/null +++ b/tools/sdk/esp32/include/coap/libcoap/include/coap3/utlist.h @@ -0,0 +1,1073 @@ +/* +Copyright (c) 2007-2021, Troy D. Hanson http://troydhanson.github.io/uthash/ +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. + +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 UTLIST_H +#define UTLIST_H + +#define UTLIST_VERSION 2.3.0 + +#include + +/* + * This file contains macros to manipulate singly and doubly-linked lists. + * + * 1. LL_ macros: singly-linked lists. + * 2. DL_ macros: doubly-linked lists. + * 3. CDL_ macros: circular doubly-linked lists. + * + * To use singly-linked lists, your structure must have a "next" pointer. + * To use doubly-linked lists, your structure must "prev" and "next" pointers. + * Either way, the pointer to the head of the list must be initialized to NULL. + * + * ----------------.EXAMPLE ------------------------- + * struct item { + * int id; + * struct item *prev, *next; + * } + * + * struct item *list = NULL: + * + * int main() { + * struct item *item; + * ... allocate and populate item ... + * DL_APPEND(list, item); + * } + * -------------------------------------------------- + * + * For doubly-linked lists, the append and delete macros are O(1) + * For singly-linked lists, append and delete are O(n) but prepend is O(1) + * The sort macro is O(n log(n)) for all types of single/double/circular lists. + */ + +/* These macros use decltype or the earlier __typeof GNU extension. + As decltype is only available in newer compilers (VS2010 or gcc 4.3+ + when compiling c++ source) this code uses whatever method is needed + or, for VS2008 where neither is available, uses casting workarounds. */ +#if !defined(LDECLTYPE) && !defined(NO_DECLTYPE) +#if defined(_MSC_VER) /* MS compiler */ +#if _MSC_VER >= 1600 && defined(__cplusplus) /* VS2010 or newer in C++ mode */ +#define LDECLTYPE(x) decltype(x) +#else /* VS2008 or older (or VS2010 in C mode) */ +#define NO_DECLTYPE +#endif +#elif defined(__BORLANDC__) || defined(__ICCARM__) || defined(__LCC__) || defined(__WATCOMC__) +#define NO_DECLTYPE +#else /* GNU, Sun and other compilers */ +#define LDECLTYPE(x) __typeof(x) +#endif +#endif + +/* for VS2008 we use some workarounds to get around the lack of decltype, + * namely, we always reassign our tmp variable to the list head if we need + * to dereference its prev/next pointers, and save/restore the real head.*/ +#ifdef NO_DECLTYPE +#define IF_NO_DECLTYPE(x) x +#define LDECLTYPE(x) char* +#define UTLIST_SV(elt,list) _tmp = (char*)(list); {char **_alias = (char**)&(list); *_alias = (elt); } +#define UTLIST_NEXT(elt,list,next) ((char*)((list)->next)) +#define UTLIST_NEXTASGN(elt,list,to,next) { char **_alias = (char**)&((list)->next); *_alias=(char*)(to); } +/* #define UTLIST_PREV(elt,list,prev) ((char*)((list)->prev)) */ +#define UTLIST_PREVASGN(elt,list,to,prev) { char **_alias = (char**)&((list)->prev); *_alias=(char*)(to); } +#define UTLIST_RS(list) { char **_alias = (char**)&(list); *_alias=_tmp; } +#define UTLIST_CASTASGN(a,b) { char **_alias = (char**)&(a); *_alias=(char*)(b); } +#else +#define IF_NO_DECLTYPE(x) +#define UTLIST_SV(elt,list) +#define UTLIST_NEXT(elt,list,next) ((elt)->next) +#define UTLIST_NEXTASGN(elt,list,to,next) ((elt)->next)=(to) +/* #define UTLIST_PREV(elt,list,prev) ((elt)->prev) */ +#define UTLIST_PREVASGN(elt,list,to,prev) ((elt)->prev)=(to) +#define UTLIST_RS(list) +#define UTLIST_CASTASGN(a,b) (a)=(b) +#endif + +/****************************************************************************** + * The sort macro is an adaptation of Simon Tatham's O(n log(n)) mergesort * + * Unwieldy variable names used here to avoid shadowing passed-in variables. * + *****************************************************************************/ +#define LL_SORT(list, cmp) \ + LL_SORT2(list, cmp, next) + +#define LL_SORT2(list, cmp, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + IF_NO_DECLTYPE(LDECLTYPE(list) _tmp;) \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); _ls_q = UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while (_ls_psize > 0 || (_ls_qsize > 0 && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } else if (_ls_qsize == 0 || !_ls_q) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,NULL,next); UTLIST_RS(list); \ + } \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + + +#define DL_SORT(list, cmp) \ + DL_SORT2(list, cmp, prev, next) + +#define DL_SORT2(list, cmp, prev, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + IF_NO_DECLTYPE(LDECLTYPE(list) _tmp;) \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); _ls_q = UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while ((_ls_psize > 0) || ((_ls_qsize > 0) && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } else if ((_ls_qsize == 0) || (!_ls_q)) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + UTLIST_SV(_ls_e,list); UTLIST_PREVASGN(_ls_e,list,_ls_tail,prev); UTLIST_RS(list); \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + UTLIST_CASTASGN((list)->prev, _ls_tail); \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,NULL,next); UTLIST_RS(list); \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + +#define CDL_SORT(list, cmp) \ + CDL_SORT2(list, cmp, prev, next) + +#define CDL_SORT2(list, cmp, prev, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + LDECLTYPE(list) _ls_oldhead; \ + LDECLTYPE(list) _tmp; \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + UTLIST_CASTASGN(_ls_oldhead,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); \ + if (UTLIST_NEXT(_ls_q,list,next) == _ls_oldhead) { \ + _ls_q = NULL; \ + } else { \ + _ls_q = UTLIST_NEXT(_ls_q,list,next); \ + } \ + UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while (_ls_psize > 0 || (_ls_qsize > 0 && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + if (_ls_q == _ls_oldhead) { _ls_q = NULL; } \ + } else if (_ls_qsize == 0 || !_ls_q) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + if (_ls_p == _ls_oldhead) { _ls_p = NULL; } \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + if (_ls_p == _ls_oldhead) { _ls_p = NULL; } \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + if (_ls_q == _ls_oldhead) { _ls_q = NULL; } \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + UTLIST_SV(_ls_e,list); UTLIST_PREVASGN(_ls_e,list,_ls_tail,prev); UTLIST_RS(list); \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + UTLIST_CASTASGN((list)->prev,_ls_tail); \ + UTLIST_CASTASGN(_tmp,list); \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_tmp,next); UTLIST_RS(list); \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + +/****************************************************************************** + * singly linked list macros (non-circular) * + *****************************************************************************/ +#define LL_PREPEND(head,add) \ + LL_PREPEND2(head,add,next) + +#define LL_PREPEND2(head,add,next) \ +do { \ + (add)->next = (head); \ + (head) = (add); \ +} while (0) + +#define LL_CONCAT(head1,head2) \ + LL_CONCAT2(head1,head2,next) + +#define LL_CONCAT2(head1,head2,next) \ +do { \ + LDECLTYPE(head1) _tmp; \ + if (head1) { \ + _tmp = (head1); \ + while (_tmp->next) { _tmp = _tmp->next; } \ + _tmp->next=(head2); \ + } else { \ + (head1)=(head2); \ + } \ +} while (0) + +#define LL_APPEND(head,add) \ + LL_APPEND2(head,add,next) + +#define LL_APPEND2(head,add,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + (add)->next=NULL; \ + if (head) { \ + _tmp = (head); \ + while (_tmp->next) { _tmp = _tmp->next; } \ + _tmp->next=(add); \ + } else { \ + (head)=(add); \ + } \ +} while (0) + +#define LL_INSERT_INORDER(head,add,cmp) \ + LL_INSERT_INORDER2(head,add,cmp,next) + +#define LL_INSERT_INORDER2(head,add,cmp,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + LL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + LL_APPEND_ELEM2(head, _tmp, add, next); \ + } else { \ + (head) = (add); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define LL_LOWER_BOUND(head,elt,like,cmp) \ + LL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define LL_LOWER_BOUND2(head,elt,like,cmp,next) \ + do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != NULL; (elt) = (elt)->next) { \ + if (cmp((elt)->next, like) >= 0) { \ + break; \ + } \ + } \ + } \ + } while (0) + +#define LL_DELETE(head,del) \ + LL_DELETE2(head,del,next) + +#define LL_DELETE2(head,del,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if ((head) == (del)) { \ + (head)=(head)->next; \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (del))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (del)->next; \ + } \ + } \ +} while (0) + +#define LL_COUNT(head,el,counter) \ + LL_COUNT2(head,el,counter,next) \ + +#define LL_COUNT2(head,el,counter,next) \ +do { \ + (counter) = 0; \ + LL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define LL_FOREACH(head,el) \ + LL_FOREACH2(head,el,next) + +#define LL_FOREACH2(head,el,next) \ + for ((el) = (head); el; (el) = (el)->next) + +#define LL_FOREACH_SAFE(head,el,tmp) \ + LL_FOREACH_SAFE2(head,el,tmp,next) + +#define LL_FOREACH_SAFE2(head,el,tmp,next) \ + for ((el) = (head); (el) && ((tmp) = (el)->next, 1); (el) = (tmp)) + +#define LL_SEARCH_SCALAR(head,out,field,val) \ + LL_SEARCH_SCALAR2(head,out,field,val,next) + +#define LL_SEARCH_SCALAR2(head,out,field,val,next) \ +do { \ + LL_FOREACH2(head,out,next) { \ + if ((out)->field == (val)) break; \ + } \ +} while (0) + +#define LL_SEARCH(head,out,elt,cmp) \ + LL_SEARCH2(head,out,elt,cmp,next) + +#define LL_SEARCH2(head,out,elt,cmp,next) \ +do { \ + LL_FOREACH2(head,out,next) { \ + if ((cmp(out,elt))==0) break; \ + } \ +} while (0) + +#define LL_REPLACE_ELEM2(head, el, add, next) \ +do { \ + LDECLTYPE(head) _tmp; \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (el))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (add); \ + } \ + } \ +} while (0) + +#define LL_REPLACE_ELEM(head, el, add) \ + LL_REPLACE_ELEM2(head, el, add, next) + +#define LL_PREPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + LDECLTYPE(head) _tmp; \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (el))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (add); \ + } \ + } \ + } else { \ + LL_APPEND2(head, add, next); \ + } \ +} while (0) \ + +#define LL_PREPEND_ELEM(head, el, add) \ + LL_PREPEND_ELEM2(head, el, add, next) + +#define LL_APPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (el)->next = (add); \ + } else { \ + LL_PREPEND2(head, add, next); \ + } \ +} while (0) \ + +#define LL_APPEND_ELEM(head, el, add) \ + LL_APPEND_ELEM2(head, el, add, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef LL_CONCAT2 +#define LL_CONCAT2(head1,head2,next) \ +do { \ + char *_tmp; \ + if (head1) { \ + _tmp = (char*)(head1); \ + while ((head1)->next) { (head1) = (head1)->next; } \ + (head1)->next = (head2); \ + UTLIST_RS(head1); \ + } else { \ + (head1)=(head2); \ + } \ +} while (0) + +#undef LL_APPEND2 +#define LL_APPEND2(head,add,next) \ +do { \ + if (head) { \ + (add)->next = head; /* use add->next as a temp variable */ \ + while ((add)->next->next) { (add)->next = (add)->next->next; } \ + (add)->next->next=(add); \ + } else { \ + (head)=(add); \ + } \ + (add)->next=NULL; \ +} while (0) + +#undef LL_INSERT_INORDER2 +#define LL_INSERT_INORDER2(head,add,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, add)) >= 0) { \ + (add)->next = (head); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next != NULL && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->next = (head)->next; \ + (head)->next = (add); \ + UTLIST_RS(head); \ + } \ +} while (0) + +#undef LL_DELETE2 +#define LL_DELETE2(head,del,next) \ +do { \ + if ((head) == (del)) { \ + (head)=(head)->next; \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next && ((head)->next != (del))) { \ + (head) = (head)->next; \ + } \ + if ((head)->next) { \ + (head)->next = ((del)->next); \ + } \ + UTLIST_RS(head); \ + } \ +} while (0) + +#undef LL_REPLACE_ELEM2 +#define LL_REPLACE_ELEM2(head, el, add, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->next = head; \ + while ((add)->next->next && ((add)->next->next != (el))) { \ + (add)->next = (add)->next->next; \ + } \ + if ((add)->next->next) { \ + (add)->next->next = (add); \ + } \ + } \ + (add)->next = (el)->next; \ +} while (0) + +#undef LL_PREPEND_ELEM2 +#define LL_PREPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->next = (head); \ + while ((add)->next->next && ((add)->next->next != (el))) { \ + (add)->next = (add)->next->next; \ + } \ + if ((add)->next->next) { \ + (add)->next->next = (add); \ + } \ + } \ + (add)->next = (el); \ + } else { \ + LL_APPEND2(head, add, next); \ + } \ +} while (0) \ + +#endif /* NO_DECLTYPE */ + +/****************************************************************************** + * doubly linked list macros (non-circular) * + *****************************************************************************/ +#define DL_PREPEND(head,add) \ + DL_PREPEND2(head,add,prev,next) + +#define DL_PREPEND2(head,add,prev,next) \ +do { \ + (add)->next = (head); \ + if (head) { \ + (add)->prev = (head)->prev; \ + (head)->prev = (add); \ + } else { \ + (add)->prev = (add); \ + } \ + (head) = (add); \ +} while (0) + +#define DL_APPEND(head,add) \ + DL_APPEND2(head,add,prev,next) + +#define DL_APPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (head)->prev->next = (add); \ + (head)->prev = (add); \ + (add)->next = NULL; \ + } else { \ + (head)=(add); \ + (head)->prev = (head); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define DL_INSERT_INORDER(head,add,cmp) \ + DL_INSERT_INORDER2(head,add,cmp,prev,next) + +#define DL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + DL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + DL_APPEND_ELEM2(head, _tmp, add, prev, next); \ + } else { \ + (head) = (add); \ + (head)->prev = (head); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define DL_LOWER_BOUND(head,elt,like,cmp) \ + DL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define DL_LOWER_BOUND2(head,elt,like,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != NULL; (elt) = (elt)->next) { \ + if ((cmp((elt)->next, like)) >= 0) { \ + break; \ + } \ + } \ + } \ +} while (0) + +#define DL_CONCAT(head1,head2) \ + DL_CONCAT2(head1,head2,prev,next) + +#define DL_CONCAT2(head1,head2,prev,next) \ +do { \ + LDECLTYPE(head1) _tmp; \ + if (head2) { \ + if (head1) { \ + UTLIST_CASTASGN(_tmp, (head2)->prev); \ + (head2)->prev = (head1)->prev; \ + (head1)->prev->next = (head2); \ + UTLIST_CASTASGN((head1)->prev, _tmp); \ + } else { \ + (head1)=(head2); \ + } \ + } \ +} while (0) + +#define DL_DELETE(head,del) \ + DL_DELETE2(head,del,prev,next) + +#define DL_DELETE2(head,del,prev,next) \ +do { \ + assert((head) != NULL); \ + assert((del)->prev != NULL); \ + if ((del)->prev == (del)) { \ + (head)=NULL; \ + } else if ((del)==(head)) { \ + (del)->next->prev = (del)->prev; \ + (head) = (del)->next; \ + } else { \ + (del)->prev->next = (del)->next; \ + if ((del)->next) { \ + (del)->next->prev = (del)->prev; \ + } else { \ + (head)->prev = (del)->prev; \ + } \ + } \ +} while (0) + +#define DL_COUNT(head,el,counter) \ + DL_COUNT2(head,el,counter,next) \ + +#define DL_COUNT2(head,el,counter,next) \ +do { \ + (counter) = 0; \ + DL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define DL_FOREACH(head,el) \ + DL_FOREACH2(head,el,next) + +#define DL_FOREACH2(head,el,next) \ + for ((el) = (head); el; (el) = (el)->next) + +/* this version is safe for deleting the elements during iteration */ +#define DL_FOREACH_SAFE(head,el,tmp) \ + DL_FOREACH_SAFE2(head,el,tmp,next) + +#define DL_FOREACH_SAFE2(head,el,tmp,next) \ + for ((el) = (head); (el) && ((tmp) = (el)->next, 1); (el) = (tmp)) + +/* these are identical to their singly-linked list counterparts */ +#define DL_SEARCH_SCALAR LL_SEARCH_SCALAR +#define DL_SEARCH LL_SEARCH +#define DL_SEARCH_SCALAR2 LL_SEARCH_SCALAR2 +#define DL_SEARCH2 LL_SEARCH2 + +#define DL_REPLACE_ELEM2(head, el, add, prev, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + (add)->next = (el)->next; \ + if ((el)->next == NULL) { \ + (add)->prev = (add); \ + } else { \ + (add)->prev = (el)->prev; \ + (add)->next->prev = (add); \ + } \ + } else { \ + (add)->next = (el)->next; \ + (add)->prev = (el)->prev; \ + (add)->prev->next = (add); \ + if ((el)->next == NULL) { \ + (head)->prev = (add); \ + } else { \ + (add)->next->prev = (add); \ + } \ + } \ +} while (0) + +#define DL_REPLACE_ELEM(head, el, add) \ + DL_REPLACE_ELEM2(head, el, add, prev, next) + +#define DL_PREPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + (add)->prev = (el)->prev; \ + (el)->prev = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->prev->next = (add); \ + } \ + } else { \ + DL_APPEND2(head, add, prev, next); \ + } \ +} while (0) \ + +#define DL_PREPEND_ELEM(head, el, add) \ + DL_PREPEND_ELEM2(head, el, add, prev, next) + +#define DL_APPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (add)->prev = (el); \ + (el)->next = (add); \ + if ((add)->next) { \ + (add)->next->prev = (add); \ + } else { \ + (head)->prev = (add); \ + } \ + } else { \ + DL_PREPEND2(head, add, prev, next); \ + } \ +} while (0) \ + +#define DL_APPEND_ELEM(head, el, add) \ + DL_APPEND_ELEM2(head, el, add, prev, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef DL_INSERT_INORDER2 +#define DL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + if ((head) == NULL) { \ + (add)->prev = (add); \ + (add)->next = NULL; \ + (head) = (add); \ + } else if ((cmp(head, add)) >= 0) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->prev = (head); \ + (add)->next = (head)->next; \ + (head)->next = (add); \ + UTLIST_RS(head); \ + if ((add)->next) { \ + (add)->next->prev = (add); \ + } else { \ + (head)->prev = (add); \ + } \ + } \ +} while (0) +#endif /* NO_DECLTYPE */ + +/****************************************************************************** + * circular doubly linked list macros * + *****************************************************************************/ +#define CDL_APPEND(head,add) \ + CDL_APPEND2(head,add,prev,next) + +#define CDL_APPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (add)->prev->next = (add); \ + } else { \ + (add)->prev = (add); \ + (add)->next = (add); \ + (head) = (add); \ + } \ +} while (0) + +#define CDL_PREPEND(head,add) \ + CDL_PREPEND2(head,add,prev,next) + +#define CDL_PREPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (add)->prev->next = (add); \ + } else { \ + (add)->prev = (add); \ + (add)->next = (add); \ + } \ + (head) = (add); \ +} while (0) + +#define CDL_INSERT_INORDER(head,add,cmp) \ + CDL_INSERT_INORDER2(head,add,cmp,prev,next) + +#define CDL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + CDL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + CDL_APPEND_ELEM2(head, _tmp, add, prev, next); \ + } else { \ + (head) = (add); \ + (head)->next = (head); \ + (head)->prev = (head); \ + } \ +} while (0) + +#define CDL_LOWER_BOUND(head,elt,like,cmp) \ + CDL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define CDL_LOWER_BOUND2(head,elt,like,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != (head); (elt) = (elt)->next) { \ + if ((cmp((elt)->next, like)) >= 0) { \ + break; \ + } \ + } \ + } \ +} while (0) + +#define CDL_DELETE(head,del) \ + CDL_DELETE2(head,del,prev,next) + +#define CDL_DELETE2(head,del,prev,next) \ +do { \ + if (((head)==(del)) && ((head)->next == (head))) { \ + (head) = NULL; \ + } else { \ + (del)->next->prev = (del)->prev; \ + (del)->prev->next = (del)->next; \ + if ((del) == (head)) (head)=(del)->next; \ + } \ +} while (0) + +#define CDL_COUNT(head,el,counter) \ + CDL_COUNT2(head,el,counter,next) \ + +#define CDL_COUNT2(head, el, counter,next) \ +do { \ + (counter) = 0; \ + CDL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define CDL_FOREACH(head,el) \ + CDL_FOREACH2(head,el,next) + +#define CDL_FOREACH2(head,el,next) \ + for ((el)=(head);el;(el)=(((el)->next==(head)) ? NULL : (el)->next)) + +#define CDL_FOREACH_SAFE(head,el,tmp1,tmp2) \ + CDL_FOREACH_SAFE2(head,el,tmp1,tmp2,prev,next) + +#define CDL_FOREACH_SAFE2(head,el,tmp1,tmp2,prev,next) \ + for ((el) = (head), (tmp1) = (head) ? (head)->prev : NULL; \ + (el) && ((tmp2) = (el)->next, 1); \ + (el) = ((el) == (tmp1) ? NULL : (tmp2))) + +#define CDL_SEARCH_SCALAR(head,out,field,val) \ + CDL_SEARCH_SCALAR2(head,out,field,val,next) + +#define CDL_SEARCH_SCALAR2(head,out,field,val,next) \ +do { \ + CDL_FOREACH2(head,out,next) { \ + if ((out)->field == (val)) break; \ + } \ +} while (0) + +#define CDL_SEARCH(head,out,elt,cmp) \ + CDL_SEARCH2(head,out,elt,cmp,next) + +#define CDL_SEARCH2(head,out,elt,cmp,next) \ +do { \ + CDL_FOREACH2(head,out,next) { \ + if ((cmp(out,elt))==0) break; \ + } \ +} while (0) + +#define CDL_REPLACE_ELEM2(head, el, add, prev, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((el)->next == (el)) { \ + (add)->next = (add); \ + (add)->prev = (add); \ + (head) = (add); \ + } else { \ + (add)->next = (el)->next; \ + (add)->prev = (el)->prev; \ + (add)->next->prev = (add); \ + (add)->prev->next = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } \ + } \ +} while (0) + +#define CDL_REPLACE_ELEM(head, el, add) \ + CDL_REPLACE_ELEM2(head, el, add, prev, next) + +#define CDL_PREPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + (add)->prev = (el)->prev; \ + (el)->prev = (add); \ + (add)->prev->next = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } \ + } else { \ + CDL_APPEND2(head, add, prev, next); \ + } \ +} while (0) + +#define CDL_PREPEND_ELEM(head, el, add) \ + CDL_PREPEND_ELEM2(head, el, add, prev, next) + +#define CDL_APPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (add)->prev = (el); \ + (el)->next = (add); \ + (add)->next->prev = (add); \ + } else { \ + CDL_PREPEND2(head, add, prev, next); \ + } \ +} while (0) + +#define CDL_APPEND_ELEM(head, el, add) \ + CDL_APPEND_ELEM2(head, el, add, prev, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef CDL_INSERT_INORDER2 +#define CDL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + if ((head) == NULL) { \ + (add)->prev = (add); \ + (add)->next = (add); \ + (head) = (add); \ + } else if ((cmp(head, add)) >= 0) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (add)->prev->next = (add); \ + (head)->prev = (add); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((char*)(head)->next != _tmp && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->prev = (head); \ + (add)->next = (head)->next; \ + (add)->next->prev = (add); \ + (head)->next = (add); \ + UTLIST_RS(head); \ + } \ +} while (0) +#endif /* NO_DECLTYPE */ + +#endif /* UTLIST_H */ diff --git a/tools/sdk/esp32/include/coap/port/include/coap3/coap.h b/tools/sdk/esp32/include/coap/port/include/coap3/coap.h new file mode 100644 index 00000000000..c69d2734b3a --- /dev/null +++ b/tools/sdk/esp32/include/coap/port/include/coap3/coap.h @@ -0,0 +1,51 @@ +/* Modify head file implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * define operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef _COAP_H_ +#define _COAP_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +#include "coap3/libcoap.h" + +#include "coap3/coap_forward_decls.h" +#include "coap3/address.h" +#include "coap3/async.h" +#include "coap3/block.h" +#include "coap3/coap_cache.h" +#include "coap3/coap_dtls.h" +#include "coap3/coap_event.h" +#include "coap3/coap_io.h" +#include "coap3/coap_time.h" +#include "coap3/coap_debug.h" +#include "coap3/encode.h" +#include "coap3/mem.h" +#include "coap3/net.h" +#include "coap3/option.h" +#include "coap3/pdu.h" +#include "coap3/coap_prng.h" +#include "coap3/resource.h" +#include "coap3/str.h" +#include "coap3/subscribe.h" +#include "coap3/uri.h" + +#ifdef __cplusplus +} +#endif + +#endif /* _COAP_H_ */ diff --git a/tools/sdk/esp32/include/coap/port/include/coap_config.h b/tools/sdk/esp32/include/coap/port/include/coap_config.h new file mode 100644 index 00000000000..1efa37aa7f7 --- /dev/null +++ b/tools/sdk/esp32/include/coap/port/include/coap_config.h @@ -0,0 +1,42 @@ +/* + * libcoap configure implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * configure operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef _CONFIG_H_ +#define _CONFIG_H_ + +/* Always enabled in ESP-IDF */ +#ifndef WITH_POSIX +#define WITH_POSIX +#endif + +#include "coap_config_posix.h" + +#define HAVE_STDIO_H +#define HAVE_ASSERT_H + +#define PACKAGE_STRING PACKAGE_NAME PACKAGE_VERSION + +/* it's just provided by libc. i hope we don't get too many of those, as + * actually we'd need autotools again to find out what environment we're + * building in */ +#define HAVE_STRNLEN 1 + +#define HAVE_LIMITS_H + +#define COAP_RESOURCES_NOHASH + +#endif /* _CONFIG_H_ */ diff --git a/tools/sdk/esp32/include/coap/port/include/coap_config_posix.h b/tools/sdk/esp32/include/coap/port/include/coap_config_posix.h new file mode 100644 index 00000000000..b24335ad156 --- /dev/null +++ b/tools/sdk/esp32/include/coap/port/include/coap_config_posix.h @@ -0,0 +1,60 @@ +/* + * libcoap configure implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * configure operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_CONFIG_POSIX_H_ +#define COAP_CONFIG_POSIX_H_ + +#ifdef WITH_POSIX + +#include +#include + +#define HAVE_SYS_SOCKET_H +#define HAVE_MALLOC +#define HAVE_ARPA_INET_H +#define HAVE_TIME_H +#define HAVE_NETDB_H +#define HAVE_NETINET_IN_H +#define HAVE_STRUCT_CMSGHDR +#define COAP_DISABLE_TCP 0 + +#define ipi_spec_dst ipi_addr +struct in6_pktinfo { + struct in6_addr ipi6_addr; /* src/dst IPv6 address */ + unsigned int ipi6_ifindex; /* send/recv interface index */ +}; +#define IN6_IS_ADDR_V4MAPPED(a) \ + ((((__const uint32_t *) (a))[0] == 0) \ + && (((__const uint32_t *) (a))[1] == 0) \ + && (((__const uint32_t *) (a))[2] == htonl (0xffff))) + +/* As not defined, just need to define is as something innocuous */ +#define IPV6_PKTINFO IPV6_CHECKSUM + +#define PACKAGE_NAME "libcoap-posix" +#define PACKAGE_VERSION "?" + +#ifdef CONFIG_MBEDTLS_TLS_ENABLED +#define HAVE_MBEDTLS +#endif /* CONFIG_MBEDTLS_TLS_ENABLED */ +#define COAP_CONSTRAINED_STACK 1 +#define ESPIDF_VERSION + +#define gai_strerror(x) "gai_strerror() not supported" + +#endif /* WITH_POSIX */ +#endif /* COAP_CONFIG_POSIX_H_ */ diff --git a/tools/sdk/esp32/include/config/sdkconfig.h b/tools/sdk/esp32/include/config/sdkconfig.h index 7e47bb079ec..b57d1022057 100644 --- a/tools/sdk/esp32/include/config/sdkconfig.h +++ b/tools/sdk/esp32/include/config/sdkconfig.h @@ -87,7 +87,6 @@ #define CONFIG_APPTRACE_DEST_NONE 1 #define CONFIG_APPTRACE_LOCK_ENABLE 1 #define CONFIG_BT_ENABLED 1 -#define CONFIG_BT_CTRL_ESP32 1 #define CONFIG_BTDM_CTRL_MODE_BTDM 1 #define CONFIG_BTDM_CTRL_BLE_MAX_CONN 3 #define CONFIG_BTDM_CTRL_BR_EDR_MAX_ACL_CONN 2 @@ -120,24 +119,8 @@ #define CONFIG_BTDM_BLE_ADV_REPORT_FLOW_CTRL_SUPP 1 #define CONFIG_BTDM_BLE_ADV_REPORT_FLOW_CTRL_NUM 100 #define CONFIG_BTDM_BLE_ADV_REPORT_DISCARD_THRSHOLD 20 -#define CONFIG_BT_CTRL_MODE_EFF 1 -#define CONFIG_BT_CTRL_BLE_MAX_ACT 10 -#define CONFIG_BT_CTRL_BLE_MAX_ACT_EFF 10 -#define CONFIG_BT_CTRL_BLE_STATIC_ACL_TX_BUF_NB 0 -#define CONFIG_BT_CTRL_PINNED_TO_CORE 0 -#define CONFIG_BT_CTRL_HCI_TL 1 -#define CONFIG_BT_CTRL_ADV_DUP_FILT_MAX 30 -#define CONFIG_BT_CTRL_HW_CCA_EFF 0 -#define CONFIG_BT_CTRL_DFT_TX_POWER_LEVEL_EFF 0 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_FLOW_CTRL_SUPP 1 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_FLOW_CTRL_NUM 100 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_DISCARD_THRSHOLD 20 -#define CONFIG_BT_CTRL_BLE_SCAN_DUPL 1 -#define CONFIG_BT_CTRL_SCAN_DUPL_TYPE 0 -#define CONFIG_BT_CTRL_SCAN_DUPL_CACHE_SIZE 100 -#define CONFIG_BT_CTRL_SLEEP_MODE_EFF 0 -#define CONFIG_BT_CTRL_SLEEP_CLOCK_EFF 0 -#define CONFIG_BT_CTRL_HCI_TL_EFF 1 +#define CONFIG_BTDM_RESERVE_DRAM 0xdb5c +#define CONFIG_BTDM_CTRL_HLI 1 #define CONFIG_BT_BLUEDROID_ENABLED 1 #define CONFIG_BT_BTC_TASK_STACK_SIZE 8192 #define CONFIG_BT_BLUEDROID_PINNED_TO_CORE_0 1 @@ -165,8 +148,6 @@ #define CONFIG_BT_BLE_DYNAMIC_ENV_MEMORY 1 #define CONFIG_BT_SMP_ENABLE 1 #define CONFIG_BT_BLE_ESTAB_LINK_CONN_TOUT 30 -#define CONFIG_BT_RESERVE_DRAM 0xdb5c -#define CONFIG_BT_NIMBLE_USE_ESP_TIMER 1 #define CONFIG_COAP_MBEDTLS_PSK 1 #define CONFIG_COAP_LOG_DEFAULT_LEVEL 0 #define CONFIG_ADC_DISABLE_DAC 1 @@ -259,7 +240,6 @@ #define CONFIG_ESP_IPC_TASK_STACK_SIZE 1024 #define CONFIG_ESP_IPC_USES_CALLERS_PRIORITY 1 #define CONFIG_ESP_IPC_ISR_ENABLE 1 -#define CONFIG_LCD_PERIPH_CLK_SRC_PLL160M 1 #define CONFIG_LCD_PANEL_IO_FORMAT_BUF_SIZE 32 #define CONFIG_ESP_NETIF_IP_LOST_TIMER_INTERVAL 120 #define CONFIG_ESP_NETIF_TCPIP_LWIP 1 @@ -287,6 +267,7 @@ #define CONFIG_ESP_TASK_WDT_PANIC 1 #define CONFIG_ESP_TASK_WDT_TIMEOUT_S 5 #define CONFIG_ESP_TASK_WDT_CHECK_IDLE_TASK_CPU0 1 +#define CONFIG_ESP_SYSTEM_CHECK_INT_LEVEL_5 1 #define CONFIG_ESP_TIME_FUNCS_USE_RTC_TIMER 1 #define CONFIG_ESP_TIME_FUNCS_USE_ESP_TIMER 1 #define CONFIG_ESP_TIMER_TASK_STACK_SIZE 4096 @@ -393,7 +374,6 @@ #define CONFIG_LWIP_DHCPS_MAX_STATION_NUM 8 #define CONFIG_LWIP_IPV6 1 #define CONFIG_LWIP_IPV6_NUM_ADDRESSES 3 -#define CONFIG_LWIP_IPV6_RDNSS_MAX_DNS_SERVERS 0 #define CONFIG_LWIP_NETIF_LOOPBACK 1 #define CONFIG_LWIP_LOOPBACK_MAX_PBUFS 8 #define CONFIG_LWIP_MAX_ACTIVE_TCP 16 @@ -695,5 +675,5 @@ #define CONFIG_ULP_COPROC_ENABLED CONFIG_ESP32_ULP_COPROC_ENABLED #define CONFIG_ULP_COPROC_RESERVE_MEM CONFIG_ESP32_ULP_COPROC_RESERVE_MEM #define CONFIG_WARN_WRITE_STRINGS CONFIG_COMPILER_WARN_WRITE_STRINGS -#define CONFIG_ARDUINO_IDF_COMMIT "61299f879e" +#define CONFIG_ARDUINO_IDF_COMMIT "3e370c4296" #define CONFIG_ARDUINO_IDF_BRANCH "master" diff --git a/tools/sdk/esp32/include/driver/include/driver/i2s.h b/tools/sdk/esp32/include/driver/include/driver/i2s.h index 0c8a43db0d5..aa649ed479c 100644 --- a/tools/sdk/esp32/include/driver/include/driver/i2s.h +++ b/tools/sdk/esp32/include/driver/include/driver/i2s.h @@ -17,7 +17,7 @@ #include "driver/periph_ctrl.h" #include "esp_intr_alloc.h" -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_ADC #include "driver/adc.h" #endif @@ -221,7 +221,7 @@ esp_err_t i2s_set_pdm_tx_up_sample(i2s_port_t i2s_num, const i2s_pdm_tx_upsample * - ESP_OK Success * - ESP_ERR_INVALID_ARG Parameter error * - ESP_ERR_NO_MEM Out of memory - * - ESP_ERR_NOT_FOUND I2S port is not found or has been installed by others (e.g. LCD i80) + * - ESP_ERR_INVALID_STATE Current I2S port is in use */ esp_err_t i2s_driver_install(i2s_port_t i2s_num, const i2s_config_t *i2s_config, int queue_size, void *i2s_queue); @@ -355,7 +355,7 @@ esp_err_t i2s_stop(i2s_port_t i2s_num); * * @param i2s_num I2S port number * -* @return + * @return * - ESP_OK Success * - ESP_ERR_INVALID_ARG Parameter error */ @@ -430,7 +430,7 @@ esp_err_t i2s_set_clk(i2s_port_t i2s_num, uint32_t rate, uint32_t bits_cfg, i2s_ */ float i2s_get_clk(i2s_port_t i2s_num); -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_ADC /** * @brief Set built-in ADC mode for I2S DMA, this function will initialize ADC pad, * and set ADC parameters. @@ -466,7 +466,9 @@ esp_err_t i2s_adc_enable(i2s_port_t i2s_num); * - ESP_ERR_INVALID_STATE Driver state error */ esp_err_t i2s_adc_disable(i2s_port_t i2s_num); +#endif // SOC_I2S_SUPPORTS_ADC +#if SOC_I2S_SUPPORTS_DAC /** * @brief Set I2S dac mode, I2S built-in DAC is disabled by default * @@ -481,7 +483,7 @@ esp_err_t i2s_adc_disable(i2s_port_t i2s_num); * - ESP_ERR_INVALID_ARG Parameter error */ esp_err_t i2s_set_dac_mode(i2s_dac_mode_t dac_mode); -#endif //SOC_I2S_SUPPORTS_ADC_DAC +#endif //SOC_I2S_SUPPORTS_DAC #ifdef __cplusplus diff --git a/tools/sdk/esp32/include/driver/include/driver/mcpwm.h b/tools/sdk/esp32/include/driver/include/driver/mcpwm.h index 20b41ffd32a..2a4e825f77c 100644 --- a/tools/sdk/esp32/include/driver/include/driver/mcpwm.h +++ b/tools/sdk/esp32/include/driver/include/driver/mcpwm.h @@ -130,11 +130,30 @@ typedef enum { * @brief MCPWM select sync signal input */ typedef enum { - MCPWM_SELECT_SYNC0 = 4, /*!. @c data argument is pointer to memory of uint32_t datatype from where the configuration option is read. +* @li @c ETH_CMD_G_PHY_ADDR gets PHY address. @c data argument is pointer to memory of uint32_t datatype to which the PHY address is to be stored. +* @li @c ETH_CMD_G_SPEED gets current Ethernet link speed. @c data argument is pointer to memory of eth_speed_t datatype to which the speed is to be stored. +* @li @c ETH_CMD_S_PROMISCUOUS sets/resets Ethernet interface promiscuous mode. @c data argument is pointer to memory of bool datatype from which the configuration option is read. +* @li @c ETH_CMD_S_FLOW_CTRL sets/resets Ethernet interface flow control. @c data argument is pointer to memory of bool datatype from which the configuration option is read. +* @li @c ETH_CMD_G_DUPLEX_MODE gets current Ethernet link duplex mode. @c data argument is pointer to memory of eth_duplex_t datatype to which the duplex mode is to be stored. +* @li @c ETH_CMD_S_PHY_LOOPBACK sets/resets PHY to/from loopback mode. @c data argument is pointer to memory of bool datatype from which the configuration option is read. +* */ esp_err_t esp_eth_ioctl(esp_eth_handle_t hdl, esp_eth_io_cmd_t cmd, void *data); diff --git a/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_com.h b/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_com.h index 46409ed710a..7ce0538fbe8 100644 --- a/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_com.h +++ b/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_com.h @@ -89,6 +89,7 @@ typedef enum { ETH_CMD_S_PROMISCUOUS, /*!< Set promiscuous mode */ ETH_CMD_S_FLOW_CTRL, /*!< Set flow control */ ETH_CMD_G_DUPLEX_MODE, /*!< Get Duplex mode */ + ETH_CMD_S_PHY_LOOPBACK,/*!< Set PHY loopback */ } esp_eth_io_cmd_t; /** diff --git a/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_phy.h b/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_phy.h index 4b4d860bd78..f85b7d43043 100644 --- a/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_phy.h +++ b/tools/sdk/esp32c3/include/esp_eth/include/esp_eth_phy.h @@ -173,6 +173,19 @@ struct esp_eth_phy_s { */ esp_err_t (*advertise_pause_ability)(esp_eth_phy_t *phy, uint32_t ability); + /** + * @brief + * + * @param[in] phy: Ethernet PHY instance + * @param[in] enable: enables or disables PHY loopback + * + * @return + * - ESP_OK: configures PHY instance loopback function successfully + * - ESP_FAIL: PHY instance loopback configuration failed because some error occurred + * + */ + esp_err_t (*loopback)(esp_eth_phy_t *phy, bool enable); + /** * @brief Free memory of Ethernet PHY instance * diff --git a/tools/sdk/esp32c3/include/esp_hid/include/esp_hid_common.h b/tools/sdk/esp32c3/include/esp_hid/include/esp_hid_common.h index 9fd7a2c6375..d7582cbc841 100644 --- a/tools/sdk/esp32c3/include/esp_hid/include/esp_hid_common.h +++ b/tools/sdk/esp32c3/include/esp_hid/include/esp_hid_common.h @@ -126,6 +126,21 @@ typedef enum { ESP_HID_COD_MIN_MAX } esp_hid_cod_min_t; +/* HID transaction Types */ +typedef enum { + ESP_HID_TRANS_HANDSHAKE = 0, + ESP_HID_TRANS_CONTROL = 1, + ESP_HID_TRANS_GET_REPORT = 4, + ESP_HID_TRANS_SET_REPORT = 5, + ESP_HID_TRANS_GET_PROTOCOL = 6, + ESP_HID_TRANS_SET_PROTOCOL = 7, + ESP_HID_TRANS_GET_IDLE = 8, + ESP_HID_TRANS_SET_IDLE = 9, + ESP_HID_TRANS_DATA = 10, + ESP_HID_TRANS_DATAC = 11, + ESP_HID_TRANS_MAX +} esp_hid_trans_type_t; + /** * @brief HID report item structure */ diff --git a/tools/sdk/esp32c3/include/esp_hid/include/esp_hidd.h b/tools/sdk/esp32c3/include/esp_hid/include/esp_hidd.h index ef596c6b2ba..3e1bfc2c06f 100644 --- a/tools/sdk/esp32c3/include/esp_hid/include/esp_hidd.h +++ b/tools/sdk/esp32c3/include/esp_hid/include/esp_hidd.h @@ -53,11 +53,28 @@ typedef struct esp_hidd_dev_s esp_hidd_dev_t; * @brief HIDD callback parameters union */ typedef union { + /** + * @brief ESP_HIDD_START_EVENT + * @note Used only for Classic Bluetooth. + */ + struct { + esp_err_t status; /*!< HID device operation status */ + } start; /*!< HID callback param of ESP_HIDD_START_EVENT */ + + /** + * @brief ESP_HIDD_STOP_EVENT + * @note Used only for Classic Bluetooth. + */ + struct { + esp_err_t status; /*!< HID device operation status */ + } stop; /*!< HID callback param of ESP_HIDD_STOP_EVENT */ + /** * @brief ESP_HIDD_CONNECT_EVENT */ struct { esp_hidd_dev_t *dev; /*!< HID device structure */ + esp_err_t status; /*!< HID device operation status, used only for Classic Bluetooth */ } connect; /*!< HID callback param of ESP_HIDD_CONNECT_EVENT */ /** @@ -66,6 +83,7 @@ typedef union { struct { esp_hidd_dev_t *dev; /*!< HID device structure */ int reason; /*!< Indicate the reason of disconnection */ + esp_err_t status; /*!< HID device operation status, used only for Classic Bluetooth */ } disconnect; /*!< HID callback param of ESP_HIDD_DISCONNECT_EVENT */ /** @@ -90,6 +108,8 @@ typedef union { uint16_t length; /*!< data length */ uint8_t *data; /*!< The pointer to the data */ uint8_t map_index; /*!< HID config report map index */ + uint8_t trans_type; /*!< HID device feature transaction type, used only for Classic Bluetooth */ + uint8_t report_type; /*!< HID device feature report type, used only for Classic Bluetooth */ } feature; /*!< HID callback param of ESP_HIDD_FEATURE_EVENT */ /** diff --git a/tools/sdk/esp32c3/include/esp_hid/include/esp_hidh.h b/tools/sdk/esp32c3/include/esp_hid/include/esp_hidh.h index d3d10021034..d49f76e6807 100644 --- a/tools/sdk/esp32c3/include/esp_hid/include/esp_hidh.h +++ b/tools/sdk/esp32c3/include/esp_hid/include/esp_hidh.h @@ -42,6 +42,8 @@ typedef enum { ESP_HIDH_INPUT_EVENT, /*!< Received HID device INPUT report */ ESP_HIDH_FEATURE_EVENT, /*!< Received HID device FEATURE report */ ESP_HIDH_CLOSE_EVENT, /*!< HID device closed */ + ESP_HIDH_START_EVENT, /*!< HID host stack started, used only for Classic Bluetooth */ + ESP_HIDH_STOP_EVENT, /*!< HID host stack stopped, used only for Classic Bluetooth */ ESP_HIDH_MAX_EVENT, /*!< HID events end marker */ } esp_hidh_event_t; @@ -49,11 +51,28 @@ typedef enum { * @brief HIDH callback parameters union */ typedef union { + /** + * @brief ESP_HIDH_START_EVENT + * @note Used only for Classic Bluetooth. + */ + struct { + esp_err_t status; /*!< HID host operation status */ + } start; /*!< HID callback param of ESP_HIDH_START_EVENT */ + + /** + * @brief ESP_HIDH_STOP_EVENT + * @note Used only for Classic Bluetooth. + */ + struct { + esp_err_t status; /*!< HID host operation status */ + } stop; /*!< HID callback param of ESP_HIDH_STOP_EVENT */ + /** * @brief ESP_HIDH_OPEN_EVENT */ struct { esp_hidh_dev_t *dev; /*!< HID Remote bluetooth device */ + esp_err_t status; /*!< HID host operation status, used only for Classic Bluetooth */ } open; /*!< HID callback param of ESP_HIDH_OPEN_EVENT */ /** @@ -62,6 +81,7 @@ typedef union { struct { esp_hidh_dev_t *dev; /*!< HID Remote bluetooth device. */ int reason; /*!< Reason why the connection was closed. BLE Only */ + esp_err_t status; /*!< HID host operation status, used only for Classic Bluetooth */ } close; /*!< HID callback param of ESP_HIDH_CLOSE_EVENT */ /** @@ -70,6 +90,7 @@ typedef union { struct { esp_hidh_dev_t *dev; /*!< HID Remote bluetooth device */ uint8_t level; /*!< Battery Level (0-100%) */ + esp_err_t status; /*!< HID host operation status */ } battery; /*!< HID callback param of ESP_HIDH_BATTERY_EVENT */ /** @@ -80,7 +101,7 @@ typedef union { esp_hid_usage_t usage; /*!< HID report usage */ uint16_t report_id; /*!< HID report index */ uint16_t length; /*!< HID data length */ - uint8_t *data; /*!< The pointer to the HID data */ + uint8_t *data; /*!< The pointer to the HID data */ uint8_t map_index; /*!< HID report map index */ } input; /*!< HID callback param of ESP_HIDH_INPUT_EVENT */ @@ -92,8 +113,10 @@ typedef union { esp_hid_usage_t usage; /*!< HID report usage */ uint16_t report_id; /*!< HID report index */ uint16_t length; /*!< HID data length */ - uint8_t *data; /*!< The pointer to the HID data */ + uint8_t *data; /*!< The pointer to the HID data */ uint8_t map_index; /*!< HID report map index */ + esp_err_t status; /*!< HID host operation status, used only for Classic Bluetooth */ + esp_hid_trans_type_t trans_type; /*!< HID host feature transaction type, used only for Classic Bluetooth */ } feature; /*!< HID callback param of ESP_HIDH_FEATURE_EVENT */ } esp_hidh_event_data_t; @@ -101,6 +124,7 @@ typedef union { typedef struct { esp_event_handler_t callback; uint16_t event_stack_size; + void *callback_arg; } esp_hidh_config_t; /** @@ -136,6 +160,14 @@ esp_err_t esp_hidh_dev_close(esp_hidh_dev_t *dev); */ esp_err_t esp_hidh_dev_free(esp_hidh_dev_t *dev); +/** + * @brief Check if the device still exists. + * @param dev : pointer to the device + * + * @return: true if exists + */ +bool esp_hidh_dev_exists(esp_hidh_dev_t *dev); + /** * @brief Send an OUTPUT report to the device * @param dev : pointer to the device @@ -173,6 +205,79 @@ esp_err_t esp_hidh_dev_feature_set(esp_hidh_dev_t *dev, size_t map_index, size_t */ esp_err_t esp_hidh_dev_feature_get(esp_hidh_dev_t *dev, size_t map_index, size_t report_id, size_t max_len, uint8_t *data, size_t *length); +/** + * @brief Set_Report command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * @param map_index : index of the device report map + * @param report_id : id of the HID FEATURE report + * @param report_type : report type, defines in `esp_hid_common.h` + * @param data : pointer to the data to send + * @param length : length of the data to send + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_set_report(esp_hidh_dev_t *dev, size_t map_index, size_t report_id, int report_type, + uint8_t *data, size_t length); + +/** + * @brief Get_Report command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * @param map_index : index of the device report map + * @param report_id : id of the HID FEATURE report + * @param report_type : report type, defines in `esp_hid_common.h` + * @param max_len : size of the buffer that will hold the data + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_get_report(esp_hidh_dev_t *dev, size_t map_index, size_t report_id, int report_type, + size_t max_len); + +/** + * @brief Get_Idle Command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_get_idle(esp_hidh_dev_t *dev); + +/** + * @brief Set_Idle Command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * @param idle_time : idle_time + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_set_idle(esp_hidh_dev_t *dev, uint8_t idle_time); + +/** + * @brief Get_Protocol Command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_get_protocol(esp_hidh_dev_t *dev); + +/** + * @brief Set_Protocol Command. + * @note For now, this function used only for Classic Bluetooth. + * + * @param dev : pointer to the device + * @param protocol_mode : protocol_mode + * + * @return: ESP_OK on success + */ +esp_err_t esp_hidh_dev_set_protocol(esp_hidh_dev_t *dev, uint8_t protocol_mode); + /** * @brief Dump the properties of HID Device to UART * @param dev : pointer to the HID Device diff --git a/tools/sdk/esp32c3/include/esp_http_server/include/esp_http_server.h b/tools/sdk/esp32c3/include/esp_http_server/include/esp_http_server.h index d583bf1d60e..1c8b78583ff 100644 --- a/tools/sdk/esp32c3/include/esp_http_server/include/esp_http_server.h +++ b/tools/sdk/esp32c3/include/esp_http_server/include/esp_http_server.h @@ -1603,6 +1603,11 @@ typedef struct httpd_ws_frame { size_t len; /*!< Length of the WebSocket data */ } httpd_ws_frame_t; +/** + * @brief Transfer complete callback + */ +typedef void (*transfer_complete_cb)(esp_err_t err, int socket, void *arg); + /** * @brief Receive and parse a WebSocket frame * @@ -1663,6 +1668,35 @@ esp_err_t httpd_ws_send_frame_async(httpd_handle_t hd, int fd, httpd_ws_frame_t */ httpd_ws_client_info_t httpd_ws_get_fd_info(httpd_handle_t hd, int fd); +/** + * @brief Sends data to to specified websocket synchronously + * + * @param[in] handle Server instance data + * @param[in] socket Socket descriptor + * @param[in] frame Websocket frame + * @return + * - ESP_OK : On successful + * - ESP_FAIL : When socket errors occurs + * - ESP_ERR_NO_MEM : Unable to allocate memory + */ +esp_err_t httpd_ws_send_data(httpd_handle_t handle, int socket, httpd_ws_frame_t *frame); + +/** + * @brief Sends data to to specified websocket asynchronously + * + * @param[in] handle Server instance data + * @param[in] socket Socket descriptor + * @param[in] frame Websocket frame + * @param[in] callback Callback invoked after sending data + * @param[in] arg User data passed to provided callback + * @return + * - ESP_OK : On successful + * - ESP_FAIL : When socket errors occurs + * - ESP_ERR_NO_MEM : Unable to allocate memory + */ +esp_err_t httpd_ws_send_data_async(httpd_handle_t handle, int socket, httpd_ws_frame_t *frame, + transfer_complete_cb callback, void *arg); + #endif /* CONFIG_HTTPD_WS_SUPPORT */ /** End of WebSocket related stuff * @} diff --git a/tools/sdk/esp32c3/include/esp_https_server/include/esp_https_server.h b/tools/sdk/esp32c3/include/esp_https_server/include/esp_https_server.h index 52f9dc2132a..00565a963ad 100644 --- a/tools/sdk/esp32c3/include/esp_https_server/include/esp_https_server.h +++ b/tools/sdk/esp32c3/include/esp_https_server/include/esp_https_server.h @@ -63,6 +63,9 @@ struct httpd_ssl_config { /** Port used when transport mode is insecure (default 80) */ uint16_t port_insecure; + + /** Enable tls session tickets */ + bool session_tickets; }; typedef struct httpd_ssl_config httpd_ssl_config_t; @@ -109,6 +112,7 @@ typedef struct httpd_ssl_config httpd_ssl_config_t; .transport_mode = HTTPD_SSL_TRANSPORT_SECURE, \ .port_secure = 443, \ .port_insecure = 80, \ + .session_tickets = false, \ } /** diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_chip_info.h b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_chip_info.h index afaa12638a2..69d23c08d36 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_chip_info.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_chip_info.h @@ -22,7 +22,7 @@ extern "C" { typedef enum { CHIP_ESP32 = 1, //!< ESP32 CHIP_ESP32S2 = 2, //!< ESP32-S2 - CHIP_ESP32S3 = 4, //!< ESP32-S3 + CHIP_ESP32S3 = 9, //!< ESP32-S3 CHIP_ESP32C3 = 5, //!< ESP32-C3 CHIP_ESP32H2 = 6, //!< ESP32-H2 } esp_chip_model_t; diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_gpio.h b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_gpio.h new file mode 100644 index 00000000000..abab21871a4 --- /dev/null +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_gpio.h @@ -0,0 +1,46 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once +#include +#include "sdkconfig.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @file sleep_gpio.h + * + * This file contains declarations of GPIO related functions in light sleep mode. + */ + +#if SOC_GPIO_SUPPORT_SLP_SWITCH && CONFIG_GPIO_ESP32_SUPPORT_SWITCH_SLP_PULL + +/** + * @brief Save GPIO pull-up and pull-down configuration information in the wake-up state + * + * In light sleep mode, the pull-up and pull-down resistors of GPIO will cause + * leakage current when the system sleeps. In order to reduce the power + * consumption of system sleep, it needs to save the configuration information + * of all GPIO pull-up and pull-down resistors and disable the pull-up and + * pull-down resistors of GPIO before the system enters sleep. + */ +void gpio_sleep_mode_config_apply(void); + +/** + * @brief Restore GPIO pull-up and pull-down configuration information in the wake-up state + * + * In light sleep mode, after the system wakes up, it needs to restore all GPIO + * pull-up and pull-down configurations before the last sleep. + */ +void gpio_sleep_mode_config_unapply(void); + +#endif // SOC_GPIO_SUPPORT_SLP_SWITCH && CONFIG_GPIO_ESP32_SUPPORT_SWITCH_SLP_PULL + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_mac_bb.h b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_mac_bb.h new file mode 100644 index 00000000000..6b4019639d8 --- /dev/null +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_mac_bb.h @@ -0,0 +1,43 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once +#include +#include "sdkconfig.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @file sleep_mac_bb.h + * + * This file contains declarations of MAC and baseband power consumption related functions in light sleep mode. + */ + +#if CONFIG_MAC_BB_PD + +/** + * @brief A callback function completes MAC and baseband power down operation + * + * In light sleep mode, execute Wi-Fi and Bluetooth module MAC and baseband + * power down and backup register configuration information operations. + */ +void mac_bb_power_down_cb_execute(void); + +/** + * @brief A callback function completes MAC and baseband power up operation + * + * In light sleep mode, execute Wi-Fi and Bluetooth module MAC and baseband + * power up and restore register configuration information operations. + */ +void mac_bb_power_up_cb_execute(void); + +#endif // CONFIG_MAC_BB_PD + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_retention.h b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_retention.h new file mode 100644 index 00000000000..001e559c0c7 --- /dev/null +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_private/sleep_retention.h @@ -0,0 +1,55 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once +#include +#include "sdkconfig.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @file sleep_retention.h + * + * This file contains declarations of memory retention related functions in light sleeo mode. + */ + +#if SOC_PM_SUPPORT_CPU_PD + +/** + * @brief Whether to allow the cpu power domain to be powered off. + * + * In light sleep mode, only when the system can provide enough memory + * for cpu retention, the cpu power domain can be powered off. + */ +bool cpu_domain_pd_allowed(void); + +#endif + +#if SOC_PM_SUPPORT_CPU_PD || SOC_PM_SUPPORT_TAGMEM_PD + +/** + * @brief Enable memory retention of some modules. + * + * In light sleep mode, before the system goes to sleep, enable the memory + * retention of modules such as CPU and I/D-cache tag memory. + */ +void sleep_enable_memory_retention(void); + +/** + * @brief Disable memory retention of some modules. + * + * In light sleep mode, after the system exits sleep, disable the memory + * retention of moudles such as CPU and I/D-cache tag memory. + */ +void sleep_disable_memory_retention(void); + +#endif // SOC_PM_SUPPORT_CPU_PD || SOC_PM_SUPPORT_TAGMEM_PD + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_sleep.h b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_sleep.h index 9822f0ba3d0..cfdfbc04186 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/esp_sleep.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/esp_sleep.h @@ -41,7 +41,9 @@ typedef enum { ESP_PD_DOMAIN_RTC_SLOW_MEM, //!< RTC slow memory ESP_PD_DOMAIN_RTC_FAST_MEM, //!< RTC fast memory ESP_PD_DOMAIN_XTAL, //!< XTAL oscillator +#if SOC_PM_SUPPORT_CPU_PD ESP_PD_DOMAIN_CPU, //!< CPU core +#endif ESP_PD_DOMAIN_VDDSDIO, //!< VDD_SDIO ESP_PD_DOMAIN_MAX //!< Number of domains } esp_sleep_pd_domain_t; diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32/spiram.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32/spiram.h index e58712d1fa6..a6086f3d311 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32/spiram.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32/spiram.h @@ -85,6 +85,15 @@ size_t esp_spiram_get_size(void); */ void esp_spiram_writeback_cache(void); +/** + * @brief get psram CS IO + * + * This interface should be called after PSRAM is enabled, otherwise it will + * return an invalid value -1/0xff. + * + * @return psram CS IO or -1/0xff if psram not enabled + */ +uint8_t esp_spiram_get_cs_io(void); /** diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32c3/esp_hmac.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32c3/esp_hmac.h index cea11ee1ba8..26e2bc71a05 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32c3/esp_hmac.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32c3/esp_hmac.h @@ -52,6 +52,35 @@ esp_err_t esp_hmac_calculate(hmac_key_id_t key_id, size_t message_len, uint8_t *hmac); +/** + * @brief Use HMAC peripheral in Downstream mode to re-enable the JTAG, if it is not permanently disabled by HW. + * In downstream mode, HMAC calculations performed by peripheral are used internally and not provided back to user. + * + * @param key_id Determines which of the 6 key blocks in the efuses should be used for the HMAC calculation. + * The corresponding purpose field of the key block in the efuse must be set to HMAC downstream purpose. + * + * @param token Pre calculated HMAC value of the 32-byte 0x00 using SHA-256 and the known private HMAC key. The key is already + * programmed to a eFuse key block. The key block number is provided as the first parameter to this function. + * + * @return + * * ESP_OK, if the calculation was successful, + * if the calculated HMAC value matches with provided token, + * JTAG will be re-enable otherwise JTAG will remain disabled. + * Return value does not indicate the JTAG status. + * * ESP_FAIL, if the hmac calculation failed or JTAG is permanently disabled by EFUSE_HARD_DIS_JTAG eFuse parameter. + * * ESP_ERR_INVALID_ARG, invalid input arguments + */ +esp_err_t esp_hmac_jtag_enable(hmac_key_id_t key_id, const uint8_t *token); + +/** + * @brief Disable the JTAG which might be enabled using the HMAC downstream mode. This function just clears the result generated + * by calling esp_hmac_jtag_enable() API. + * + * @return + * * ESP_OK return ESP_OK after writing the HMAC_SET_INVALIDATE_JTAG_REG with value 1. + */ +esp_err_t esp_hmac_jtag_disable(void); + #ifdef __cplusplus } #endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32h2/esp_hmac.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32h2/esp_hmac.h index cea11ee1ba8..26e2bc71a05 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32h2/esp_hmac.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32h2/esp_hmac.h @@ -52,6 +52,35 @@ esp_err_t esp_hmac_calculate(hmac_key_id_t key_id, size_t message_len, uint8_t *hmac); +/** + * @brief Use HMAC peripheral in Downstream mode to re-enable the JTAG, if it is not permanently disabled by HW. + * In downstream mode, HMAC calculations performed by peripheral are used internally and not provided back to user. + * + * @param key_id Determines which of the 6 key blocks in the efuses should be used for the HMAC calculation. + * The corresponding purpose field of the key block in the efuse must be set to HMAC downstream purpose. + * + * @param token Pre calculated HMAC value of the 32-byte 0x00 using SHA-256 and the known private HMAC key. The key is already + * programmed to a eFuse key block. The key block number is provided as the first parameter to this function. + * + * @return + * * ESP_OK, if the calculation was successful, + * if the calculated HMAC value matches with provided token, + * JTAG will be re-enable otherwise JTAG will remain disabled. + * Return value does not indicate the JTAG status. + * * ESP_FAIL, if the hmac calculation failed or JTAG is permanently disabled by EFUSE_HARD_DIS_JTAG eFuse parameter. + * * ESP_ERR_INVALID_ARG, invalid input arguments + */ +esp_err_t esp_hmac_jtag_enable(hmac_key_id_t key_id, const uint8_t *token); + +/** + * @brief Disable the JTAG which might be enabled using the HMAC downstream mode. This function just clears the result generated + * by calling esp_hmac_jtag_enable() API. + * + * @return + * * ESP_OK return ESP_OK after writing the HMAC_SET_INVALIDATE_JTAG_REG with value 1. + */ +esp_err_t esp_hmac_jtag_disable(void); + #ifdef __cplusplus } #endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s2/spiram.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s2/spiram.h index 7750d45abe7..70d07e61a85 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s2/spiram.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s2/spiram.h @@ -70,6 +70,15 @@ size_t esp_spiram_get_size(void); */ void esp_spiram_writeback_cache(void); +/** + * @brief get psram CS IO + * + * This interface should be called after PSRAM is enabled, otherwise it will + * return an invalid value -1/0xff. + * + * @return psram CS IO or -1/0xff if psram not enabled + */ +uint8_t esp_spiram_get_cs_io(void); /** diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_crypto_lock.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_crypto_lock.h index d45cc2e3223..074754a86b2 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_crypto_lock.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_crypto_lock.h @@ -18,6 +18,20 @@ extern "C" { * Other unrelated components must not use it. */ +/** + * @brief Acquire lock for Digital Signature(DS) cryptography peripheral + * + * Internally also takes the HMAC lock, as the DS depends on the HMAC peripheral + */ +void esp_crypto_ds_lock_acquire(void); + +/** + * @brief Release lock for Digital Signature(DS) cryptography peripheral + * + * Internally also releases the HMAC lock, as the DS depends on the HMAC peripheral + */ +void esp_crypto_ds_lock_release(void); + /** * @brief Acquire lock for HMAC cryptography peripheral * diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_ds.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_ds.h new file mode 100644 index 00000000000..46a1d22a543 --- /dev/null +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_ds.h @@ -0,0 +1,192 @@ +/* + * SPDX-FileCopyrightText: 2020-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once +#include + +#include "esp_hmac.h" +#include "esp_err.h" +#include "soc/soc_caps.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define ESP32S3_ERR_HW_CRYPTO_DS_HMAC_FAIL ESP_ERR_HW_CRYPTO_BASE + 0x1 /*!< HMAC peripheral problem */ +#define ESP32S3_ERR_HW_CRYPTO_DS_INVALID_KEY ESP_ERR_HW_CRYPTO_BASE + 0x2 /*!< given HMAC key isn't correct, + HMAC peripheral problem */ +#define ESP32S3_ERR_HW_CRYPTO_DS_INVALID_DIGEST ESP_ERR_HW_CRYPTO_BASE + 0x4 /*!< message digest check failed, + result is invalid */ +#define ESP32S3_ERR_HW_CRYPTO_DS_INVALID_PADDING ESP_ERR_HW_CRYPTO_BASE + 0x5 /*!< padding check failed, but result + is produced anyway and can be read*/ + +#define ESP_DS_IV_LEN 16 + +/* Length of parameter 'C' stored in flash */ +#define ESP_DS_C_LEN (12672 / 8) + +typedef struct esp_ds_context esp_ds_context_t; + +typedef enum { + ESP_DS_RSA_1024 = (1024 / 32) - 1, + ESP_DS_RSA_2048 = (2048 / 32) - 1, + ESP_DS_RSA_3072 = (3072 / 32) - 1, + ESP_DS_RSA_4096 = (4096 / 32) - 1 +} esp_digital_signature_length_t; + +/** + * Encrypted private key data. Recommended to store in flash in this format. + * + * @note This struct has to match to one from the ROM code! This documentation is mostly taken from there. + */ +typedef struct esp_digital_signature_data { + /** + * RSA LENGTH register parameters + * (number of words in RSA key & operands, minus one). + * + * Max value 127 (for RSA 4096). + * + * This value must match the length field encrypted and stored in 'c', + * or invalid results will be returned. (The DS peripheral will + * always use the value in 'c', not this value, so an attacker can't + * alter the DS peripheral results this way, it will just truncate or + * extend the message and the resulting signature in software.) + * + * @note In IDF, the enum type length is the same as of type unsigned, so they can be used interchangably. + * See the ROM code for the original declaration of struct \c ets_ds_data_t. + */ + esp_digital_signature_length_t rsa_length; + + /** + * IV value used to encrypt 'c' + */ + uint8_t iv[ESP_DS_IV_LEN]; + + /** + * Encrypted Digital Signature parameters. Result of AES-CBC encryption + * of plaintext values. Includes an encrypted message digest. + */ + uint8_t c[ESP_DS_C_LEN]; +} esp_ds_data_t; + +/** Plaintext parameters used by Digital Signature. + * + * Not used for signing with DS peripheral, but can be encrypted + * in-device by calling esp_ds_encrypt_params() + * + * @note This documentation is mostly taken from the ROM code. + */ +typedef struct { + uint32_t Y[SOC_RSA_MAX_BIT_LEN / 32]; //!< RSA exponent + uint32_t M[SOC_RSA_MAX_BIT_LEN / 32]; //!< RSA modulus + uint32_t Rb[SOC_RSA_MAX_BIT_LEN / 32]; //!< RSA r inverse operand + uint32_t M_prime; //!< RSA M prime operand + esp_digital_signature_length_t length; //!< RSA length +} esp_ds_p_data_t; + +/** + * Sign the message. + * + * This function is a wrapper around \c esp_ds_finish_sign() and \c esp_ds_start_sign(), so do not use them + * in parallel. + * It blocks until the signing is finished and then returns the signature. + * + * @note This function locks the HMAC, SHA, AES and RSA components during its entire execution time. + * + * @param message the message to be signed; its length is determined by data->rsa_length + * @param data the encrypted signing key data (AES encrypted RSA key + IV) + * @param key_id the HMAC key ID determining the HMAC key of the HMAC which will be used to decrypt the + * signing key data + * @param signature the destination of the signature, should be (data->rsa_length + 1)*4 bytes long + * + * @return + * - ESP_OK if successful, the signature was written to the parameter \c signature. + * - ESP_ERR_INVALID_ARG if one of the parameters is NULL or data->rsa_length is too long or 0 + * - ESP_ERR_HW_CRYPTO_DS_HMAC_FAIL if there was an HMAC failure during retrieval of the decryption key + * - ESP_ERR_NO_MEM if there hasn't been enough memory to allocate the context object + * - ESP_ERR_HW_CRYPTO_DS_INVALID_KEY if there's a problem with passing the HMAC key to the DS component + * - ESP_ERR_HW_CRYPTO_DS_INVALID_DIGEST if the message digest didn't match; the signature is invalid. + * - ESP_ERR_HW_CRYPTO_DS_INVALID_PADDING if the message padding is incorrect, the signature can be read though + * since the message digest matches. + */ +esp_err_t esp_ds_sign(const void *message, + const esp_ds_data_t *data, + hmac_key_id_t key_id, + void *signature); + +/** + * Start the signing process. + * + * This function yields a context object which needs to be passed to \c esp_ds_finish_sign() to finish the signing + * process. + * + * @note This function locks the HMAC, SHA, AES and RSA components, so the user has to ensure to call + * \c esp_ds_finish_sign() in a timely manner. + * + * @param message the message to be signed; its length is determined by data->rsa_length + * @param data the encrypted signing key data (AES encrypted RSA key + IV) + * @param key_id the HMAC key ID determining the HMAC key of the HMAC which will be used to decrypt the + * signing key data + * @param esp_ds_ctx the context object which is needed for finishing the signing process later + * + * @return + * - ESP_OK if successful, the ds operation was started now and has to be finished with \c esp_ds_finish_sign() + * - ESP_ERR_INVALID_ARG if one of the parameters is NULL or data->rsa_length is too long or 0 + * - ESP_ERR_HW_CRYPTO_DS_HMAC_FAIL if there was an HMAC failure during retrieval of the decryption key + * - ESP_ERR_NO_MEM if there hasn't been enough memory to allocate the context object + * - ESP_ERR_HW_CRYPTO_DS_INVALID_KEY if there's a problem with passing the HMAC key to the DS component + */ +esp_err_t esp_ds_start_sign(const void *message, + const esp_ds_data_t *data, + hmac_key_id_t key_id, + esp_ds_context_t **esp_ds_ctx); + +/** + * Return true if the DS peripheral is busy, otherwise false. + * + * @note Only valid if \c esp_ds_start_sign() was called before. + */ +bool esp_ds_is_busy(void); + +/** + * Finish the signing process. + * + * @param signature the destination of the signature, should be (data->rsa_length + 1)*4 bytes long + * @param esp_ds_ctx the context object retreived by \c esp_ds_start_sign() + * + * @return + * - ESP_OK if successful, the ds operation has been finished and the result is written to signature. + * - ESP_ERR_INVALID_ARG if one of the parameters is NULL + * - ESP_ERR_HW_CRYPTO_DS_INVALID_DIGEST if the message digest didn't match; the signature is invalid. + * - ESP_ERR_HW_CRYPTO_DS_INVALID_PADDING if the message padding is incorrect, the signature can be read though + * since the message digest matches. + */ +esp_err_t esp_ds_finish_sign(void *signature, esp_ds_context_t *esp_ds_ctx); + +/** + * Encrypt the private key parameters. + * + * @param data Output buffer to store encrypted data, suitable for later use generating signatures. + * The allocated memory must be in internal memory and word aligned since it's filled by DMA. Both is asserted + * at run time. + * @param iv Pointer to 16 byte IV buffer, will be copied into 'data'. Should be randomly generated bytes each time. + * @param p_data Pointer to input plaintext key data. The expectation is this data will be deleted after this process + * is done and 'data' is stored. + * @param key Pointer to 32 bytes of key data. Type determined by key_type parameter. The expectation is the + * corresponding HMAC key will be stored to efuse and then permanently erased. + * + * @return + * - ESP_OK if successful, the ds operation has been finished and the result is written to signature. + * - ESP_ERR_INVALID_ARG if one of the parameters is NULL or p_data->rsa_length is too long + */ +esp_err_t esp_ds_encrypt_params(esp_ds_data_t *data, + const void *iv, + const esp_ds_p_data_t *p_data, + const void *key); + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_hmac.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_hmac.h index 8f8677e38c4..101dce556b6 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_hmac.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/esp_hmac.h @@ -50,6 +50,35 @@ esp_err_t esp_hmac_calculate(hmac_key_id_t key_id, size_t message_len, uint8_t *hmac); +/** + * @brief Use HMAC peripheral in Downstream mode to re-enable the JTAG, if it is not permanently disabled by HW. + * In downstream mode, HMAC calculations performed by peripheral are used internally and not provided back to user. + * + * @param key_id Determines which of the 6 key blocks in the efuses should be used for the HMAC calculation. + * The corresponding purpose field of the key block in the efuse must be set to HMAC downstream purpose. + * + * @param token Pre calculated HMAC value of the 32-byte 0x00 using SHA-256 and the known private HMAC key. The key is already + * programmed to a eFuse key block. The key block number is provided as the first parameter to this function. + * + * @return + * * ESP_OK, if the calculation was successful, + * if the calculated HMAC value matches with provided token, + * JTAG will be re-enable otherwise JTAG will remain disabled. + * Return value does not indicate the JTAG status. + * * ESP_FAIL, if the hmac calculation failed or JTAG is permanently disabled by EFUSE_HARD_DIS_JTAG eFuse parameter. + * * ESP_ERR_INVALID_ARG, invalid input arguments + */ +esp_err_t esp_hmac_jtag_enable(hmac_key_id_t key_id, const uint8_t *token); + +/** + * @brief Disable the JTAG which might be enabled using the HMAC downstream mode. This function just clears the result generated + * by calling esp_hmac_jtag_enable() API. + * + * @return + * * ESP_OK return ESP_OK after writing the HMAC_SET_INVALIDATE_JTAG_REG with value 1. + */ +esp_err_t esp_hmac_jtag_disable(void); + #ifdef __cplusplus } #endif diff --git a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/spiram.h b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/spiram.h index 7efb6169460..067c3d27bf8 100644 --- a/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/spiram.h +++ b/tools/sdk/esp32c3/include/esp_hw_support/include/soc/esp32s3/spiram.h @@ -79,6 +79,16 @@ void esp_spiram_writeback_cache(void); */ bool esp_spiram_is_initialized(void); +/** + * @brief get psram CS IO + * + * This interface should be called after PSRAM is enabled, otherwise it will + * return an invalid value -1/0xff. + * + * @return psram CS IO or -1/0xff if psram not enabled + */ +uint8_t esp_spiram_get_cs_io(void); + /** * @brief Reserve a pool of internal memory for specific DMA/internal allocations * diff --git a/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_io.h b/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_io.h index b3b4fe81f38..eebcabf42b4 100644 --- a/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_io.h +++ b/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_io.h @@ -9,6 +9,7 @@ #include "esp_err.h" #include "esp_lcd_types.h" #include "soc/soc_caps.h" +#include "hal/lcd_types.h" #ifdef __cplusplus extern "C" { @@ -130,6 +131,7 @@ esp_err_t esp_lcd_new_panel_io_i2c(esp_lcd_i2c_bus_handle_t bus, const esp_lcd_p typedef struct { int dc_gpio_num; /*!< GPIO used for D/C line */ int wr_gpio_num; /*!< GPIO used for WR line */ + lcd_clock_source_t clk_src; /*!< Clock source for the I80 LCD peripheral */ int data_gpio_nums[SOC_LCD_I80_BUS_WIDTH]; /*!< GPIOs used for data lines */ size_t bus_width; /*!< Number of data lines, 8 or 16 */ size_t max_transfer_bytes; /*!< Maximum transfer size, this determines the length of internal DMA link */ @@ -163,7 +165,7 @@ esp_err_t esp_lcd_del_i80_bus(esp_lcd_i80_bus_handle_t bus); * @brief Panel IO configuration structure, for intel 8080 interface */ typedef struct { - int cs_gpio_num; /*!< GPIO used for CS line */ + int cs_gpio_num; /*!< GPIO used for CS line, set to -1 will declaim exclusively use of I80 bus */ unsigned int pclk_hz; /*!< Frequency of pixel clock */ size_t trans_queue_depth; /*!< Transaction queue size, larger queue, higher throughput */ bool (*on_color_trans_done)(esp_lcd_panel_io_handle_t panel_io, void *user_data, void *event_data); /*!< Callback, invoked when color data was tranferred done */ diff --git a/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_rgb.h b/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_rgb.h index 64932924606..2ddd2b6b9a6 100644 --- a/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_rgb.h +++ b/tools/sdk/esp32c3/include/esp_lcd/include/esp_lcd_panel_rgb.h @@ -9,6 +9,7 @@ #include "esp_err.h" #include "esp_lcd_types.h" #include "soc/soc_caps.h" +#include "hal/lcd_types.h" #ifdef __cplusplus extern "C" { @@ -41,6 +42,7 @@ typedef struct { * @brief LCD RGB panel configuration structure */ typedef struct { + lcd_clock_source_t clk_src; /*!< Clock source for the RGB LCD peripheral */ esp_lcd_rgb_timing_t timings; /*!< RGB timing parameters */ size_t data_width; /*!< Number of data lines */ int hsync_gpio_num; /*!< GPIO used for HSYNC signal */ diff --git a/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs.h b/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs.h index 35bbbabfa7b..ad491627fe1 100644 --- a/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs.h +++ b/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs.h @@ -9,6 +9,7 @@ #include #include +#include "lfs_util.h" #ifdef __cplusplus extern "C" @@ -21,7 +22,7 @@ extern "C" // Software library version // Major (top-nibble), incremented on backwards incompatible changes // Minor (bottom-nibble), incremented on feature additions -#define LFS_VERSION 0x00020002 +#define LFS_VERSION 0x00020004 #define LFS_VERSION_MAJOR (0xffff & (LFS_VERSION >> 16)) #define LFS_VERSION_MINOR (0xffff & (LFS_VERSION >> 0)) @@ -123,20 +124,25 @@ enum lfs_type { enum lfs_open_flags { // open flags LFS_O_RDONLY = 1, // Open a file as read only +#ifndef LFS_READONLY LFS_O_WRONLY = 2, // Open a file as write only LFS_O_RDWR = 3, // Open a file as read and write LFS_O_CREAT = 0x0100, // Create a file if it does not exist LFS_O_EXCL = 0x0200, // Fail if a file already exists LFS_O_TRUNC = 0x0400, // Truncate the existing file to zero size LFS_O_APPEND = 0x0800, // Move to end of file on every write +#endif // internally used flags +#ifndef LFS_READONLY LFS_F_DIRTY = 0x010000, // File does not match storage LFS_F_WRITING = 0x020000, // File has been written since last flush +#endif LFS_F_READING = 0x040000, // File has been read since last flush - LFS_F_ERRED = 0x080000, // An error occured during write +#ifndef LFS_READONLY + LFS_F_ERRED = 0x080000, // An error occurred during write +#endif LFS_F_INLINE = 0x100000, // Currently inlined in directory entry - LFS_F_OPENED = 0x200000, // File has been opened }; // File seek flags @@ -174,6 +180,16 @@ struct lfs_config { // are propogated to the user. int (*sync)(const struct lfs_config *c); +#ifdef LFS_THREADSAFE + // Lock the underlying block device. Negative error codes + // are propogated to the user. + int (*lock)(const struct lfs_config *c); + + // Unlock the underlying block device. Negative error codes + // are propogated to the user. + int (*unlock)(const struct lfs_config *c); +#endif + // Minimum size of a block read. All read operations will be a // multiple of this value. lfs_size_t read_size; @@ -191,7 +207,7 @@ struct lfs_config { // Number of erasable blocks on the device. lfs_size_t block_count; - // Number of erase cycles before littlefs evicts metadata logs and moves + // Number of erase cycles before littlefs evicts metadata logs and moves // the metadata to another block. Suggested values are in the // range 100-1000, with large values having better performance at the cost // of less consistent wear distribution. @@ -240,6 +256,12 @@ struct lfs_config { // larger attributes size but must be <= LFS_ATTR_MAX. Defaults to // LFS_ATTR_MAX when zero. lfs_size_t attr_max; + + // Optional upper limit on total space given to metadata pairs in bytes. On + // devices with large blocks (e.g. 128kB) setting this to a low size (2-8kB) + // can help bound the metadata compaction time. Must be <= block_size. + // Defaults to block_size when zero. + lfs_size_t metadata_max; }; // File info structure @@ -399,6 +421,7 @@ typedef struct lfs { /// Filesystem functions /// +#ifndef LFS_READONLY // Format a block device with the littlefs // // Requires a littlefs object and config struct. This clobbers the littlefs @@ -407,6 +430,7 @@ typedef struct lfs { // // Returns a negative error code on failure. int lfs_format(lfs_t *lfs, const struct lfs_config *config); +#endif // Mounts a littlefs // @@ -426,12 +450,15 @@ int lfs_unmount(lfs_t *lfs); /// General operations /// +#ifndef LFS_READONLY // Removes a file or directory // // If removing a directory, the directory must be empty. // Returns a negative error code on failure. int lfs_remove(lfs_t *lfs, const char *path); +#endif +#ifndef LFS_READONLY // Rename or move a file or directory // // If the destination exists, it must match the source in type. @@ -439,6 +466,7 @@ int lfs_remove(lfs_t *lfs, const char *path); // // Returns a negative error code on failure. int lfs_rename(lfs_t *lfs, const char *oldpath, const char *newpath); +#endif // Find info about a file or directory // @@ -461,6 +489,7 @@ int lfs_stat(lfs_t *lfs, const char *path, struct lfs_info *info); lfs_ssize_t lfs_getattr(lfs_t *lfs, const char *path, uint8_t type, void *buffer, lfs_size_t size); +#ifndef LFS_READONLY // Set custom attributes // // Custom attributes are uniquely identified by an 8-bit type and limited @@ -470,13 +499,16 @@ lfs_ssize_t lfs_getattr(lfs_t *lfs, const char *path, // Returns a negative error code on failure. int lfs_setattr(lfs_t *lfs, const char *path, uint8_t type, const void *buffer, lfs_size_t size); +#endif +#ifndef LFS_READONLY // Removes a custom attribute // // If an attribute is not found, nothing happens. // // Returns a negative error code on failure. int lfs_removeattr(lfs_t *lfs, const char *path, uint8_t type); +#endif /// File operations /// @@ -525,6 +557,7 @@ int lfs_file_sync(lfs_t *lfs, lfs_file_t *file); lfs_ssize_t lfs_file_read(lfs_t *lfs, lfs_file_t *file, void *buffer, lfs_size_t size); +#ifndef LFS_READONLY // Write data to file // // Takes a buffer and size indicating the data to write. The file will not @@ -533,6 +566,7 @@ lfs_ssize_t lfs_file_read(lfs_t *lfs, lfs_file_t *file, // Returns the number of bytes written, or a negative error code on failure. lfs_ssize_t lfs_file_write(lfs_t *lfs, lfs_file_t *file, const void *buffer, lfs_size_t size); +#endif // Change the position of the file // @@ -541,10 +575,12 @@ lfs_ssize_t lfs_file_write(lfs_t *lfs, lfs_file_t *file, lfs_soff_t lfs_file_seek(lfs_t *lfs, lfs_file_t *file, lfs_soff_t off, int whence); +#ifndef LFS_READONLY // Truncates the size of the file to the specified size // // Returns a negative error code on failure. int lfs_file_truncate(lfs_t *lfs, lfs_file_t *file, lfs_off_t size); +#endif // Return the position of the file // @@ -567,10 +603,12 @@ lfs_soff_t lfs_file_size(lfs_t *lfs, lfs_file_t *file); /// Directory operations /// +#ifndef LFS_READONLY // Create a directory // // Returns a negative error code on failure. int lfs_mkdir(lfs_t *lfs, const char *path); +#endif // Open a directory // @@ -632,6 +670,7 @@ lfs_ssize_t lfs_fs_size(lfs_t *lfs); // Returns a negative error code on failure. int lfs_fs_traverse(lfs_t *lfs, int (*cb)(void*, lfs_block_t), void *data); +#ifndef LFS_READONLY #ifdef LFS_MIGRATE // Attempts to migrate a previous version of littlefs // @@ -646,6 +685,7 @@ int lfs_fs_traverse(lfs_t *lfs, int (*cb)(void*, lfs_block_t), void *data); // Returns a negative error code on failure. int lfs_migrate(lfs_t *lfs, const struct lfs_config *cfg); #endif +#endif #ifdef __cplusplus diff --git a/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs_util.h b/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs_util.h index dbb4c5ba866..fc1b0c2ae86 100644 --- a/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs_util.h +++ b/tools/sdk/esp32c3/include/esp_littlefs/src/littlefs/lfs_util.h @@ -49,6 +49,7 @@ extern "C" // code footprint // Logging functions +#ifndef LFS_TRACE #ifdef LFS_YES_TRACE #define LFS_TRACE_(fmt, ...) \ printf("%s:%d:trace: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__) @@ -56,7 +57,9 @@ extern "C" #else #define LFS_TRACE(...) #endif +#endif +#ifndef LFS_DEBUG #ifndef LFS_NO_DEBUG #define LFS_DEBUG_(fmt, ...) \ printf("%s:%d:debug: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__) @@ -64,7 +67,9 @@ extern "C" #else #define LFS_DEBUG(...) #endif +#endif +#ifndef LFS_WARN #ifndef LFS_NO_WARN #define LFS_WARN_(fmt, ...) \ printf("%s:%d:warn: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__) @@ -72,7 +77,9 @@ extern "C" #else #define LFS_WARN(...) #endif +#endif +#ifndef LFS_ERROR #ifndef LFS_NO_ERROR #define LFS_ERROR_(fmt, ...) \ printf("%s:%d:error: " fmt "%s\n", __FILE__, __LINE__, __VA_ARGS__) @@ -80,13 +87,16 @@ extern "C" #else #define LFS_ERROR(...) #endif +#endif // Runtime assertions +#ifndef LFS_ASSERT #ifndef LFS_NO_ASSERT #define LFS_ASSERT(test) assert(test) #else #define LFS_ASSERT(test) #endif +#endif // Builtin functions, these may be replaced by more efficient diff --git a/tools/sdk/esp32c3/include/esp_netif/include/esp_netif_ppp.h b/tools/sdk/esp32c3/include/esp_netif/include/esp_netif_ppp.h index 413910c4331..159388e80ea 100644 --- a/tools/sdk/esp32c3/include/esp_netif/include/esp_netif_ppp.h +++ b/tools/sdk/esp32c3/include/esp_netif/include/esp_netif_ppp.h @@ -38,6 +38,11 @@ typedef struct esp_netif_ppp_config { */ #define NETIF_PP_PHASE_OFFSET (0x100) +/** @brief event id offset for internal errors + * + */ +#define NETIF_PPP_INTERNAL_ERR_OFFSET (0x200) + /** @brief event ids for different PPP related events * */ @@ -68,6 +73,7 @@ typedef enum { NETIF_PPP_PHASE_RUNNING = NETIF_PP_PHASE_OFFSET + 10, NETIF_PPP_PHASE_TERMINATE = NETIF_PP_PHASE_OFFSET + 11, NETIF_PPP_PHASE_DISCONNECT = NETIF_PP_PHASE_OFFSET + 12, + NETIF_PPP_CONNECT_FAILED = NETIF_PPP_INTERNAL_ERR_OFFSET + 0, } esp_netif_ppp_status_event_t; /** @brief definitions of different authorisation types @@ -89,7 +95,8 @@ typedef enum { * @param[in] user User name * @param[in] passwd Password * - * @return ESP_OK on success, ESP_ERR_ESP_NETIF_INVALID_PARAMS if netif null or not PPP + * @return ESP_OK on success, + * ESP_ERR_ESP_NETIF_INVALID_PARAMS if the supplied netif is not of PPP type, or netif is null */ esp_err_t esp_netif_ppp_set_auth(esp_netif_t *netif, esp_netif_auth_type_t authtype, const char *user, const char *passwd); @@ -98,10 +105,20 @@ esp_err_t esp_netif_ppp_set_auth(esp_netif_t *netif, esp_netif_auth_type_t autht * @param[in] esp_netif Handle to esp-netif instance * @param[in] config Pointer to PPP netif configuration structure * - * @return ESP_OK on success, ESP_ERR_ESP_NETIF_INVALID_PARAMS if netif null or not PPP + * @return ESP_OK on success, + * ESP_ERR_ESP_NETIF_INVALID_PARAMS if the supplied netif is not of PPP type, or netif is null */ esp_err_t esp_netif_ppp_set_params(esp_netif_t *netif, const esp_netif_ppp_config_t *config); +/** @brief Gets parameters configured in the supplied esp-netif. + * + * @param[in] esp_netif Handle to esp-netif instance + * @param[out] config Pointer to PPP netif configuration structure + * + * @return ESP_OK on success, + * ESP_ERR_ESP_NETIF_INVALID_PARAMS if the supplied netif is not of PPP type, or netif is null + */ +esp_err_t esp_netif_ppp_get_params(esp_netif_t *netif, esp_netif_ppp_config_t *config); #ifdef __cplusplus } diff --git a/tools/sdk/esp32c3/include/esp_rom/include/esp32c3/rom/rtc.h b/tools/sdk/esp32c3/include/esp_rom/include/esp32c3/rom/rtc.h index 76ece7e8194..2a7f6cb6140 100644 --- a/tools/sdk/esp32c3/include/esp_rom/include/esp32c3/rom/rtc.h +++ b/tools/sdk/esp32c3/include/esp_rom/include/esp32c3/rom/rtc.h @@ -85,8 +85,7 @@ typedef enum { NO_MEAN = 0, POWERON_RESET = 1, /**<1, Vbat power on reset*/ RTC_SW_SYS_RESET = 3, /**<3, Software reset digital core*/ - DEEPSLEEP_RESET = 5, /**<3, Deep Sleep reset digital core*/ - SDIO_RESET = 6, /**<6, Reset by SLC module, reset digital core*/ + DEEPSLEEP_RESET = 5, /**<5, Deep Sleep reset digital core*/ TG0WDT_SYS_RESET = 7, /**<7, Timer Group0 Watch dog reset digital core*/ TG1WDT_SYS_RESET = 8, /**<8, Timer Group1 Watch dog reset digital core*/ RTCWDT_SYS_RESET = 9, /**<9, RTC Watch dog Reset digital core*/ @@ -96,8 +95,13 @@ typedef enum { RTCWDT_CPU_RESET = 13, /**<13, RTC Watch dog Reset CPU*/ RTCWDT_BROWN_OUT_RESET = 15, /**<15, Reset when the vdd voltage is not stable*/ RTCWDT_RTC_RESET = 16, /**<16, RTC Watch dog reset digital core and rtc module*/ - TG1WDT_CPU_RESET = 17, /**<11, Time Group1 reset CPU*/ - SUPER_WDT_RESET = 18, /**<11, super watchdog reset digital core and rtc module*/ + TG1WDT_CPU_RESET = 17, /**<17, Time Group1 reset CPU*/ + SUPER_WDT_RESET = 18, /**<18, super watchdog reset digital core and rtc module*/ + GLITCH_RTC_RESET = 19, /**<19, glitch reset digital core and rtc module*/ + EFUSE_RESET = 20, /**<20, efuse reset digital core*/ + USB_UART_CHIP_RESET = 21, /**<21, usb uart reset digital core */ + USB_JTAG_CHIP_RESET = 22, /**<22, usb jtag reset digital core */ + POWER_GLITCH_RESET = 23, /**<23, power glitch reset digital core and rtc module*/ } RESET_REASON; // Check if the reset reason defined in ROM is compatible with soc/reset_reasons.h @@ -112,7 +116,13 @@ _Static_assert((soc_reset_reason_t)RTC_SW_CPU_RESET == RESET_REASON_CPU0_SW, "RT _Static_assert((soc_reset_reason_t)RTCWDT_CPU_RESET == RESET_REASON_CPU0_RTC_WDT, "RTCWDT_CPU_RESET != RESET_REASON_CPU0_RTC_WDT"); _Static_assert((soc_reset_reason_t)RTCWDT_BROWN_OUT_RESET == RESET_REASON_SYS_BROWN_OUT, "RTCWDT_BROWN_OUT_RESET != RESET_REASON_SYS_BROWN_OUT"); _Static_assert((soc_reset_reason_t)RTCWDT_RTC_RESET == RESET_REASON_SYS_RTC_WDT, "RTCWDT_RTC_RESET != RESET_REASON_SYS_RTC_WDT"); +_Static_assert((soc_reset_reason_t)TG1WDT_CPU_RESET == RESET_REASON_CPU0_MWDT1, "TG1WDT_CPU_RESET != RESET_REASON_CPU0_MWDT1"); _Static_assert((soc_reset_reason_t)SUPER_WDT_RESET == RESET_REASON_SYS_SUPER_WDT, "SUPER_WDT_RESET != RESET_REASON_SYS_SUPER_WDT"); +_Static_assert((soc_reset_reason_t)GLITCH_RTC_RESET == RESET_REASON_SYS_CLK_GLITCH, "GLITCH_RTC_RESET != RESET_REASON_SYS_CLK_GLITCH"); +_Static_assert((soc_reset_reason_t)EFUSE_RESET == RESET_REASON_CORE_EFUSE_CRC, "EFUSE_RESET != RESET_REASON_CORE_EFUSE_CRC"); +_Static_assert((soc_reset_reason_t)USB_UART_CHIP_RESET == RESET_REASON_CORE_USB_UART, "USB_UART_CHIP_RESET != RESET_REASON_CORE_USB_UART"); +_Static_assert((soc_reset_reason_t)USB_JTAG_CHIP_RESET == RESET_REASON_CORE_USB_JTAG, "USB_JTAG_CHIP_RESET != RESET_REASON_CORE_USB_JTAG"); +_Static_assert((soc_reset_reason_t)POWER_GLITCH_RESET == RESET_REASON_CORE_PWR_GLITCH, "POWER_GLITCH_RESET != RESET_REASON_CORE_PWR_GLITCH"); typedef enum { NO_SLEEP = 0, diff --git a/tools/sdk/esp32c3/include/esp_rom/include/esp32h2/rom/rtc.h b/tools/sdk/esp32c3/include/esp_rom/include/esp32h2/rom/rtc.h index 76ece7e8194..ad4f45c2ca7 100644 --- a/tools/sdk/esp32c3/include/esp_rom/include/esp32h2/rom/rtc.h +++ b/tools/sdk/esp32c3/include/esp_rom/include/esp32h2/rom/rtc.h @@ -85,8 +85,7 @@ typedef enum { NO_MEAN = 0, POWERON_RESET = 1, /**<1, Vbat power on reset*/ RTC_SW_SYS_RESET = 3, /**<3, Software reset digital core*/ - DEEPSLEEP_RESET = 5, /**<3, Deep Sleep reset digital core*/ - SDIO_RESET = 6, /**<6, Reset by SLC module, reset digital core*/ + DEEPSLEEP_RESET = 5, /**<5, Deep Sleep reset digital core*/ TG0WDT_SYS_RESET = 7, /**<7, Timer Group0 Watch dog reset digital core*/ TG1WDT_SYS_RESET = 8, /**<8, Timer Group1 Watch dog reset digital core*/ RTCWDT_SYS_RESET = 9, /**<9, RTC Watch dog Reset digital core*/ @@ -96,8 +95,14 @@ typedef enum { RTCWDT_CPU_RESET = 13, /**<13, RTC Watch dog Reset CPU*/ RTCWDT_BROWN_OUT_RESET = 15, /**<15, Reset when the vdd voltage is not stable*/ RTCWDT_RTC_RESET = 16, /**<16, RTC Watch dog reset digital core and rtc module*/ - TG1WDT_CPU_RESET = 17, /**<11, Time Group1 reset CPU*/ - SUPER_WDT_RESET = 18, /**<11, super watchdog reset digital core and rtc module*/ + TG1WDT_CPU_RESET = 17, /**<17, Time Group1 reset CPU*/ + SUPER_WDT_RESET = 18, /**<18, super watchdog reset digital core and rtc module*/ + GLITCH_RTC_RESET = 19, /**<19, glitch reset digital core and rtc module*/ + EFUSE_RESET = 20, /**<20, efuse reset digital core*/ + USB_UART_CHIP_RESET = 21, /**<21, usb uart reset digital core */ + USB_JTAG_CHIP_RESET = 22, /**<22, usb jtag reset digital core */ + POWER_GLITCH_RESET = 23, /**<23, power glitch reset digital core and rtc module*/ + JTAG_RESET = 24, /**<24, jtag reset CPU*/ } RESET_REASON; // Check if the reset reason defined in ROM is compatible with soc/reset_reasons.h @@ -112,7 +117,14 @@ _Static_assert((soc_reset_reason_t)RTC_SW_CPU_RESET == RESET_REASON_CPU0_SW, "RT _Static_assert((soc_reset_reason_t)RTCWDT_CPU_RESET == RESET_REASON_CPU0_RTC_WDT, "RTCWDT_CPU_RESET != RESET_REASON_CPU0_RTC_WDT"); _Static_assert((soc_reset_reason_t)RTCWDT_BROWN_OUT_RESET == RESET_REASON_SYS_BROWN_OUT, "RTCWDT_BROWN_OUT_RESET != RESET_REASON_SYS_BROWN_OUT"); _Static_assert((soc_reset_reason_t)RTCWDT_RTC_RESET == RESET_REASON_SYS_RTC_WDT, "RTCWDT_RTC_RESET != RESET_REASON_SYS_RTC_WDT"); +_Static_assert((soc_reset_reason_t)TG1WDT_CPU_RESET == RESET_REASON_CPU0_MWDT1, "TG1WDT_CPU_RESET != RESET_REASON_CPU0_MWDT1"); _Static_assert((soc_reset_reason_t)SUPER_WDT_RESET == RESET_REASON_SYS_SUPER_WDT, "SUPER_WDT_RESET != RESET_REASON_SYS_SUPER_WDT"); +_Static_assert((soc_reset_reason_t)GLITCH_RTC_RESET == RESET_REASON_SYS_CLK_GLITCH, "GLITCH_RTC_RESET != RESET_REASON_SYS_CLK_GLITCH"); +_Static_assert((soc_reset_reason_t)EFUSE_RESET == RESET_REASON_CORE_EFUSE_CRC, "EFUSE_RESET != RESET_REASON_CORE_EFUSE_CRC"); +_Static_assert((soc_reset_reason_t)USB_UART_CHIP_RESET == RESET_REASON_CORE_USB_UART, "USB_UART_CHIP_RESET != RESET_REASON_CORE_USB_UART"); +_Static_assert((soc_reset_reason_t)USB_JTAG_CHIP_RESET == RESET_REASON_CORE_USB_JTAG, "USB_JTAG_CHIP_RESET != RESET_REASON_CORE_USB_JTAG"); +_Static_assert((soc_reset_reason_t)POWER_GLITCH_RESET == RESET_REASON_CORE_PWR_GLITCH, "POWER_GLITCH_RESET != RESET_REASON_CORE_PWR_GLITCH"); +_Static_assert((soc_reset_reason_t)JTAG_RESET == RESET_REASON_CPU_JTAG, "JTAG_RESET != RESET_REASON_CPU_JTAG"); typedef enum { NO_SLEEP = 0, diff --git a/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/cache.h b/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/cache.h index 0ec6308f7cd..27780446fe0 100644 --- a/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/cache.h +++ b/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/cache.h @@ -103,6 +103,11 @@ typedef enum { CACHE_AUTOLOAD_NEGATIVE = 1, /*!< cache autoload step is negative */ } cache_autoload_order_t; +typedef enum { + CACHE_AUTOLOAD_REGION0 = 0, /*!< cache autoload region0 */ + CACHE_AUTOLOAD_REGION1 = 1, /*!< cache autoload region1 */ +} cache_autoload_region_t; + #define CACHE_AUTOLOAD_STEP(i) ((i) - 1) typedef enum { @@ -144,14 +149,17 @@ struct dcache_tag_item { }; struct autoload_config { + uint8_t ena; /*!< autoload enable */ uint8_t order; /*!< autoload step is positive or negative */ uint8_t trigger; /*!< autoload trigger */ - uint8_t ena0; /*!< autoload region0 enable */ - uint8_t ena1; /*!< autoload region1 enable */ - uint32_t addr0; /*!< autoload region0 start address */ - uint32_t size0; /*!< autoload region0 size */ - uint32_t addr1; /*!< autoload region1 start address */ - uint32_t size1; /*!< autoload region1 size */ + uint8_t size; /*!< autoload size */ +}; + +struct autoload_region_config { + uint8_t region; /*!< autoload region*/ + uint8_t ena; /*!< autoload region enable */ + uint32_t addr; /*!< autoload region start address */ + uint32_t size; /*!< autoload region size */ }; struct tag_group_info { @@ -160,6 +168,7 @@ struct tag_group_info { uint32_t vaddr_offset; /*!< virtual address offset of the cache ways */ uint32_t tag_addr[MAX_CACHE_WAYS]; /*!< tag memory address, only [0~mode.ways-1] is valid to use */ uint32_t cache_memory_offset[MAX_CACHE_WAYS]; /*!< cache memory address, only [0~mode.ways-1] is valid to use */ + uint8_t use_legacy; /*!< 1 for using legacy tag api, 0 for using 2rd tag api */ }; struct lock_config { @@ -168,6 +177,39 @@ struct lock_config { uint16_t group; /*!< manual lock group, 0 or 1*/ }; +struct cache_internal_stub_table { + uint32_t (* icache_line_size)(void); + uint32_t (* dcache_line_size)(void); + uint32_t (* icache_addr)(uint32_t addr); + uint32_t (* dcache_addr)(uint32_t addr); + void (* invalidate_icache_items)(uint32_t addr, uint32_t items); + void (* invalidate_dcache_items)(uint32_t addr, uint32_t items); + void (* clean_items)(uint32_t addr, uint32_t items); + void (* writeback_items)(uint32_t addr, uint32_t items); + void (* lock_icache_items)(uint32_t addr, uint32_t items); + void (* lock_dcache_items)(uint32_t addr, uint32_t items); + void (* unlock_icache_items)(uint32_t addr, uint32_t items); + void (* unlock_dcache_items)(uint32_t addr, uint32_t items); + void (* occupy_items)(uint32_t addr, uint32_t items); + uint32_t (* suspend_icache_autoload)(void); + void (* resume_icache_autoload)(uint32_t autoload); + uint32_t (* suspend_dcache_autoload)(void); + void (* resume_dcache_autoload)(uint32_t autoload); + void (* freeze_icache_enable)(cache_freeze_mode_t mode); + void (* freeze_icache_disable)(void); + void (* freeze_dcache_enable)(cache_freeze_mode_t mode); + void (* freeze_dcache_disable)(void); + int (* op_addr)(uint32_t op_icache, uint32_t start_addr, uint32_t size, uint32_t cache_line_size, uint32_t max_sync_num, void(* cache_Iop)(uint32_t, uint32_t), void(* cache_Dop)(uint32_t, uint32_t)); +}; + +typedef void (* cache_op_start)(void); +typedef void (* cache_op_end)(void); + +typedef struct { + cache_op_start start; + cache_op_end end; +} cache_op_cb_t; + #define ESP_ROM_ERR_INVALID_ARG 1 #define MMU_SET_ADDR_ALIGNED_ERROR 2 #define MMU_SET_PASE_SIZE_ERROR 3 @@ -190,7 +232,7 @@ void Cache_MMU_Init(void); * @brief Set ICache mmu mapping. * Please do not call this function in your SDK application. * - * @param uint32_t ext_ram : DPORT_MMU_ACCESS_FLASH for flash, DPORT_MMU_ACCESS_SPIRAM for spiram, DPORT_MMU_INVALID for invalid. + * @param uint32_t ext_ram : MMU_ACCESS_FLASH for flash, MMU_ACCESS_SPIRAM for spiram, MMU_INVALID for invalid. * * @param uint32_t vaddr : virtual address in CPU address space. * Can be Iram0,Iram1,Irom0,Drom0 and AHB buses address. @@ -217,7 +259,7 @@ int Cache_Ibus_MMU_Set(uint32_t ext_ram, uint32_t vaddr, uint32_t paddr, uint32 * @brief Set DCache mmu mapping. * Please do not call this function in your SDK application. * - * @param uint32_t ext_ram : DPORT_MMU_ACCESS_FLASH for flash, DPORT_MMU_ACCESS_SPIRAM for spiram, DPORT_MMU_INVALID for invalid. + * @param uint32_t ext_ram : MMU_ACCESS_FLASH for flash, MMU_ACCESS_SPIRAM for spiram, MMU_INVALID for invalid. * * @param uint32_t vaddr : virtual address in CPU address space. * Can be DRam0, DRam1, DRom0, DPort and AHB buses address. @@ -272,9 +314,9 @@ uint32_t Cache_Flash_To_SPIRAM_Copy(uint32_t bus, uint32_t bus_start_addr, uint3 * @brief allocate memory to used by ICache. * Please do not call this function in your SDK application. * - * @param cache_array_t icache_low : the data array bank used by icache low part, can be CACHE_MEMORY_INVALID, CACHE_MEMORY_IBANK0, CACHE_MEMORY_IBANK1 + * @param cache_array_t icache_low : the data array bank used by icache low part. Due to timing constraint, can only be CACHE_MEMORY_INVALID, CACHE_MEMORY_IBANK0 * - * @param cache_array_t icache_high : the data array bank used by icache high part, can be CACHE_MEMORY_INVALID, CACHE_MEMORY_IBANK0, CACHE_MEMORY_IBANK1 only if icache_low and icache_high is not CACHE_MEMORY_INVALID + * @param cache_array_t icache_high : the data array bank used by icache high part. Due to timing constraint, can only be CACHE_MEMORY_INVALID, or CACHE_MEMORY_IBANK1 only if icache_low and icache_high is CACHE_MEMORY_IBANK0 * * return none */ @@ -284,9 +326,9 @@ void Cache_Occupy_ICache_MEMORY(cache_array_t icache_low, cache_array_t icache_h * @brief allocate memory to used by DCache. * Please do not call this function in your SDK application. * - * @param cache_array_t dcache_low : the data array bank used by dcache low part, can be CACHE_MEMORY_INVALID, CACHE_MEMORY_DBANK0, CACHE_MEMORY_DBANK1 + * @param cache_array_t dcache_low : the data array bank used by dcache low part. Due to timing constraint, can only be CACHE_MEMORY_INVALID, CACHE_MEMORY_DBANK1 * - * @param cache_array_t dcache1_high : the data array bank used by dcache high part, can be CACHE_MEMORY_INVALID, CACHE_MEMORY_DBANK0, CACHE_MEMORY_DBANK1 only if dcache_low0 and dcache_low1 is not CACHE_MEMORY_INVALID + * @param cache_array_t dcache1_high : the data array bank used by dcache high part. Due to timing constraint, can only be CACHE_MEMORY_INVALID, or CACHE_MEMORY_DBANK0 only if dcache_low0 and dcache_low1 is CACHE_MEMORY_DBANK1 * * return none */ @@ -310,7 +352,7 @@ void Cache_Get_Mode(struct cache_mode *mode); * * @param cache_ways_t ways : the associate ways of cache, can be CACHE_4WAYS_ASSOC and CACHE_8WAYS_ASSOC * - * @param cache_line_size_t cache_line_size : the cache line size, can be CACHE_LINE_SIZE_16B, CACHE_LINE_SIZE_32B and CACHE_LINE_SIZE_64B + * @param cache_line_size_t cache_line_size : the cache line size, can be CACHE_LINE_SIZE_16B and CACHE_LINE_SIZE_32B * * return none */ @@ -320,9 +362,9 @@ void Cache_Set_ICache_Mode(cache_size_t cache_size, cache_ways_t ways, cache_lin * @brief set DCache modes: cache size, associate ways and cache line size. * Please do not call this function in your SDK application. * - * @param cache_size_t cache_size : the cache size, can be CACHE_SIZE_8KB and CACHE_SIZE_16KB + * @param cache_size_t cache_size : the cache size, can be CACHE_SIZE_HALF and CACHE_SIZE_FULL * - * @param cache_ways_t ways : the associate ways of cache, can be CACHE_4WAYS_ASSOC and CACHE_8WAYS_ASSOC + * @param cache_ways_t ways : the associate ways of cache, can be CACHE_4WAYS_ASSOC and CACHE_8WAYS_ASSOC, only CACHE_4WAYS_ASSOC works * * @param cache_line_size_t cache_line_size : the cache line size, can be CACHE_LINE_SIZE_16B, CACHE_LINE_SIZE_32B and CACHE_LINE_SIZE_64B * @@ -351,7 +393,7 @@ uint32_t Cache_Address_Through_ICache(uint32_t addr); uint32_t Cache_Address_Through_DCache(uint32_t addr); /** - * @brief Init mmu owner register to make i/d cache use half mmu entries. + * @brief Init Cache for ROM boot, including resetting the Dcache, initializing Owner, MMU, setting DCache mode, Enabling DCache, unmasking bus. * * @param None * @@ -636,6 +678,16 @@ void Cache_End_DCache_Preload(uint32_t autoload); */ void Cache_Config_ICache_Autoload(const struct autoload_config *config); +/** + * @brief Config region autoload parameters of ICache. + * Please do not call this function in your SDK application. + * + * @param struct autoload_region_config * config : region autoload parameters. + * + * @return ESP_ROM_ERR_INVALID_ARG : invalid param, 0 : success + */ +int Cache_Config_ICache_Region_Autoload(const struct autoload_region_config *config); + /** * @brief Enable auto preload for ICache. * Please do not call this function in your SDK application. @@ -666,6 +718,16 @@ void Cache_Disable_ICache_Autoload(void); */ void Cache_Config_DCache_Autoload(const struct autoload_config *config); +/** + * @brief Config region autoload parameters of DCache. + * Please do not call this function in your SDK application. + * + * @param struct autoload_region_config * config : region autoload parameters. + * + * @return ESP_ROM_ERR_INVALID_ARG : invalid param, 0 : success + */ +int Cache_Config_DCache_Region_Autoload(const struct autoload_region_config *config); + /** * @brief Enable auto preload for DCache. * Please do not call this function in your SDK application. @@ -1008,7 +1070,24 @@ void Cache_Freeze_DCache_Disable(void); * * @return None */ -void Cache_Travel_Tag_Memory(struct cache_mode *mode, uint32_t filter_addr, void (* process)(struct tag_group_info *)); +void Cache_Travel_Tag_Memory(struct cache_mode * mode, uint32_t filter_addr, void (* process)(struct tag_group_info *)); + +/** + * @brief Travel tag memory to run a call back function, using 2nd tag registers. + * ICache and DCache are suspend when doing this. + * The callback will get the parameter tag_group_info, which will include a group of tag memory addresses and cache memory addresses. + * Please do not call this function in your SDK application. + * + * @param struct cache_mode * mode : the cache to check and the cache mode. + * + * @param uint32_t filter_addr : only the cache lines which may include the filter_address will be returned to the call back function. + * 0 for do not filter, all cache lines will be returned. + * + * @param void (* process)(struct tag_group_info *) : call back function, which may be called many times, a group(the addresses in the group are in the same position in the cache ways) a time. + * + * @return None + */ +void Cache_Travel_Tag_Memory2(struct cache_mode * mode, uint32_t filter_addr, void (* process)(struct tag_group_info *)); /** * @brief Get the virtual address from cache mode, cache tag and the virtual address offset of cache ways. @@ -1092,6 +1171,8 @@ int flash2spiram_rodata_offset(void); uint32_t flash_instr_rodata_start_page(uint32_t bus); uint32_t flash_instr_rodata_end_page(uint32_t bus); +extern struct cache_internal_stub_table* rom_cache_internal_table_ptr; +extern cache_op_cb_t rom_cache_op_cb; #ifdef __cplusplus } #endif diff --git a/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/rtc.h b/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/rtc.h index 09d2376ef38..d928c4dee44 100644 --- a/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/rtc.h +++ b/tools/sdk/esp32c3/include/esp_rom/include/esp32s3/rom/rtc.h @@ -92,6 +92,9 @@ typedef enum { SUPER_WDT_RESET = 18, /**<18, super watchdog reset digital core and rtc module*/ GLITCH_RTC_RESET = 19, /**<19, glitch reset digital core and rtc module*/ EFUSE_RESET = 20, /**<20, efuse reset digital core*/ + USB_UART_CHIP_RESET = 21, /**<21, usb uart reset digital core */ + USB_JTAG_CHIP_RESET = 22, /**<22, usb jtag reset digital core */ + POWER_GLITCH_RESET = 23, /**<23, power glitch reset digital core and rtc module*/ } RESET_REASON; // Check if the reset reason defined in ROM is compatible with soc/reset_reasons.h @@ -106,9 +109,13 @@ _Static_assert((soc_reset_reason_t)RTC_SW_CPU_RESET == RESET_REASON_CPU0_SW, "RT _Static_assert((soc_reset_reason_t)RTCWDT_CPU_RESET == RESET_REASON_CPU0_RTC_WDT, "RTCWDT_CPU_RESET != RESET_REASON_CPU0_RTC_WDT"); _Static_assert((soc_reset_reason_t)RTCWDT_BROWN_OUT_RESET == RESET_REASON_SYS_BROWN_OUT, "RTCWDT_BROWN_OUT_RESET != RESET_REASON_SYS_BROWN_OUT"); _Static_assert((soc_reset_reason_t)RTCWDT_RTC_RESET == RESET_REASON_SYS_RTC_WDT, "RTCWDT_RTC_RESET != RESET_REASON_SYS_RTC_WDT"); +_Static_assert((soc_reset_reason_t)TG1WDT_CPU_RESET == RESET_REASON_CPU0_MWDT1, "TG1WDT_CPU_RESET != RESET_REASON_CPU0_MWDT1"); _Static_assert((soc_reset_reason_t)SUPER_WDT_RESET == RESET_REASON_SYS_SUPER_WDT, "SUPER_WDT_RESET != RESET_REASON_SYS_SUPER_WDT"); _Static_assert((soc_reset_reason_t)GLITCH_RTC_RESET == RESET_REASON_SYS_CLK_GLITCH, "GLITCH_RTC_RESET != RESET_REASON_SYS_CLK_GLITCH"); _Static_assert((soc_reset_reason_t)EFUSE_RESET == RESET_REASON_CORE_EFUSE_CRC, "EFUSE_RESET != RESET_REASON_CORE_EFUSE_CRC"); +_Static_assert((soc_reset_reason_t)USB_UART_CHIP_RESET == RESET_REASON_CORE_USB_UART, "USB_UART_CHIP_RESET != RESET_REASON_CORE_USB_UART"); +_Static_assert((soc_reset_reason_t)USB_JTAG_CHIP_RESET == RESET_REASON_CORE_USB_JTAG, "USB_JTAG_CHIP_RESET != RESET_REASON_CORE_USB_JTAG"); +_Static_assert((soc_reset_reason_t)POWER_GLITCH_RESET == RESET_REASON_CORE_PWR_GLITCH, "POWER_GLITCH_RESET != RESET_REASON_CORE_PWR_GLITCH"); typedef enum { NO_SLEEP = 0, diff --git a/tools/sdk/esp32c3/include/esp_system/include/esp_xt_wdt.h b/tools/sdk/esp32c3/include/esp_system/include/esp_xt_wdt.h new file mode 100644 index 00000000000..3b39d8056dc --- /dev/null +++ b/tools/sdk/esp32c3/include/esp_system/include/esp_xt_wdt.h @@ -0,0 +1,63 @@ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once + +#include + +#include "esp_err.h" +#include "esp_intr_alloc.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief esp_xt_wdt configuration struct + * + */ +typedef struct { + uint8_t timeout; /*!< Watchdog timeout */ + bool auto_backup_clk_enable; /*!< Enable automatic switch to backup clock at timeout */ +} esp_xt_wdt_config_t; + +/* Callback function for WDT interrupt*/ +typedef void (*esp_xt_callback_t)(void *arg); + +/** + * @brief Initializes the xtal32k watchdog timer + * + * @param cfg Pointer to configuration struct + * @return esp_err_t + * - ESP_OK: XTWDT was successfully enabled + * - ESP_ERR_NO_MEM: Failed to allocate ISR + */ +esp_err_t esp_xt_wdt_init(const esp_xt_wdt_config_t *cfg); + +/** + * @brief Register a callback function that will be called when the watchdog + * times out. + * + * @note This function will be called from an interrupt context where the cache might be disabled. + * Thus the function should be placed in IRAM and must not perform any blocking operations. + * + * Only one callback function can be registered, any call to esp_xt_wdt_register_callback + * will override the previous callback function. + * + * @param func The callback function to register + * @param arg Pointer to argument that will be passed to the callback function + */ +void esp_xt_wdt_register_callback(esp_xt_callback_t func, void *arg); + +/** + * @brief Restores the xtal32k clock and re-enables the WDT + * + */ +void esp_xt_wdt_restore_clk(void); + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOSConfig.h b/tools/sdk/esp32c3/include/freertos/include/esp_additions/freertos/FreeRTOSConfig.h similarity index 98% rename from tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOSConfig.h rename to tools/sdk/esp32c3/include/freertos/include/esp_additions/freertos/FreeRTOSConfig.h index c1dcd1cd48a..a01a56e9fd4 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOSConfig.h +++ b/tools/sdk/esp32c3/include/freertos/include/esp_additions/freertos/FreeRTOSConfig.h @@ -71,8 +71,12 @@ #define FREERTOS_CONFIG_H #include "sdkconfig.h" -// The arch-specific FreeRTOSConfig.h in port//include. -#include_next "freertos/FreeRTOSConfig.h" + +/* for likely and unlikely */ +#include "esp_compiler.h" + +// The arch-specific FreeRTOSConfig_arch.h in port//include. +#include "freertos/FreeRTOSConfig_arch.h" #if !(defined(FREERTOS_CONFIG_XTENSA_H) \ || defined(FREERTOS_CONFIG_RISCV_H) \ @@ -300,4 +304,6 @@ extern void vPortCleanUpTCB ( void *pxTCB ); #define configINCLUDE_FREERTOS_TASK_C_ADDITIONS_H 1 +#define configTASK_NOTIFICATION_ARRAY_ENTRIES 1 + #endif /* FREERTOS_CONFIG_H */ diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOS.h b/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOS.h index 0b0fce99dc9..eb0ee6be357 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOS.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/FreeRTOS.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -53,11 +53,8 @@ #endif /* *INDENT-ON* */ -/* for likely and unlikely */ -#include "esp_compiler.h" - /* Application specific configuration options. */ -#include "freertos/FreeRTOSConfig.h" +#include "FreeRTOSConfig.h" /* Basic FreeRTOS definitions. */ #include "projdefs.h" @@ -129,8 +126,28 @@ #define INCLUDE_vTaskSuspend 0 #endif -#ifndef INCLUDE_vTaskDelayUntil - #define INCLUDE_vTaskDelayUntil 0 +#ifdef INCLUDE_xTaskDelayUntil + #ifdef INCLUDE_vTaskDelayUntil + /* INCLUDE_vTaskDelayUntil was replaced by INCLUDE_xTaskDelayUntil. Backward + * compatibility is maintained if only one or the other is defined, but + * there is a conflict if both are defined. */ + #error INCLUDE_vTaskDelayUntil and INCLUDE_xTaskDelayUntil are both defined. INCLUDE_vTaskDelayUntil is no longer required and should be removed + #endif +#endif + +#ifndef INCLUDE_xTaskDelayUntil + #ifdef INCLUDE_vTaskDelayUntil + /* If INCLUDE_vTaskDelayUntil is set but INCLUDE_xTaskDelayUntil is not then + * the project's FreeRTOSConfig.h probably pre-dates the introduction of + * xTaskDelayUntil and setting INCLUDE_xTaskDelayUntil to whatever + * INCLUDE_vTaskDelayUntil is set to will ensure backward compatibility. + */ + #define INCLUDE_xTaskDelayUntil INCLUDE_vTaskDelayUntil + #endif +#endif + +#ifndef INCLUDE_xTaskDelayUntil + #define INCLUDE_xTaskDelayUntil 0 #endif #ifndef INCLUDE_vTaskDelay @@ -246,11 +263,11 @@ #define configASSERT_DEFINED 1 #endif -/* configPRECONDITION should be resolve to configASSERT. +/* configPRECONDITION should be defined as configASSERT. * The CBMC proofs need a way to track assumptions and assertions. - * A configPRECONDITION statement should express an implicit invariant or assumption made. - * A configASSERT statement should express an invariant that must hold explicit before calling - * the code. */ + * A configPRECONDITION statement should express an implicit invariant or + * assumption made. A configASSERT statement should express an invariant that must + * hold explicit before calling the code. */ #ifndef configPRECONDITION #define configPRECONDITION( X ) configASSERT( X ) #define configPRECONDITION_DEFINED 0 @@ -262,6 +279,10 @@ #define portMEMORY_BARRIER() #endif +#ifndef portSOFTWARE_BARRIER + #define portSOFTWARE_BARRIER() +#endif + /* The timers module relies on xTaskGetSchedulerState(). */ #if configUSE_TIMERS == 1 @@ -467,9 +488,15 @@ #define traceCREATE_COUNTING_SEMAPHORE_FAILED() #endif +#ifndef traceQUEUE_SET_SEND + #define traceQUEUE_SET_SEND traceQUEUE_SEND +#endif + +#ifdef ESP_PLATFORM #ifndef traceQUEUE_SEMAPHORE_RECEIVE #define traceQUEUE_SEMAPHORE_RECEIVE( pxQueue ) #endif +#endif // ESP_PLATFORM #ifndef traceQUEUE_SEND #define traceQUEUE_SEND( pxQueue ) @@ -523,6 +550,7 @@ #define traceQUEUE_DELETE( pxQueue ) #endif +#ifdef ESP_PLATFORM #ifndef traceQUEUE_GIVE_FROM_ISR #define traceQUEUE_GIVE_FROM_ISR( pxQueue ) #endif @@ -530,6 +558,7 @@ #ifndef traceQUEUE_GIVE_FROM_ISR_FAILED #define traceQUEUE_GIVE_FROM_ISR_FAILED( pxQueue ) #endif +#endif // ESP_PLATFORM #ifndef traceTASK_CREATE #define traceTASK_CREATE( pxNewTCB ) @@ -656,31 +685,31 @@ #endif #ifndef traceTASK_NOTIFY_TAKE_BLOCK - #define traceTASK_NOTIFY_TAKE_BLOCK() + #define traceTASK_NOTIFY_TAKE_BLOCK( uxIndexToWait ) #endif #ifndef traceTASK_NOTIFY_TAKE - #define traceTASK_NOTIFY_TAKE() + #define traceTASK_NOTIFY_TAKE( uxIndexToWait ) #endif #ifndef traceTASK_NOTIFY_WAIT_BLOCK - #define traceTASK_NOTIFY_WAIT_BLOCK() + #define traceTASK_NOTIFY_WAIT_BLOCK( uxIndexToWait ) #endif #ifndef traceTASK_NOTIFY_WAIT - #define traceTASK_NOTIFY_WAIT() + #define traceTASK_NOTIFY_WAIT( uxIndexToWait ) #endif #ifndef traceTASK_NOTIFY - #define traceTASK_NOTIFY() + #define traceTASK_NOTIFY( uxIndexToNotify ) #endif #ifndef traceTASK_NOTIFY_FROM_ISR - #define traceTASK_NOTIFY_FROM_ISR() + #define traceTASK_NOTIFY_FROM_ISR( uxIndexToNotify ) #endif #ifndef traceTASK_NOTIFY_GIVE_FROM_ISR - #define traceTASK_NOTIFY_GIVE_FROM_ISR() + #define traceTASK_NOTIFY_GIVE_FROM_ISR( uxIndexToNotify ) #endif #ifndef traceSTREAM_BUFFER_CREATE_FAILED @@ -735,6 +764,7 @@ #define traceSTREAM_BUFFER_RECEIVE_FROM_ISR( xStreamBuffer, xReceivedLength ) #endif +#ifdef ESP_PLATFORM #ifndef traceISR_EXIT_TO_SCHEDULER #define traceISR_EXIT_TO_SCHEDULER() #endif @@ -746,6 +776,7 @@ #ifndef traceISR_ENTER #define traceISR_ENTER(_n_) #endif +#endif // ESP_PLATFORM #ifndef configGENERATE_RUN_TIME_STATS #define configGENERATE_RUN_TIME_STATS 0 @@ -869,6 +900,14 @@ #define configUSE_TASK_NOTIFICATIONS 1 #endif +#ifndef configTASK_NOTIFICATION_ARRAY_ENTRIES + #define configTASK_NOTIFICATION_ARRAY_ENTRIES 1 +#endif + +#if configTASK_NOTIFICATION_ARRAY_ENTRIES < 1 + #error configTASK_NOTIFICATION_ARRAY_ENTRIES must be at least 1 +#endif + #ifndef configUSE_POSIX_ERRNO #define configUSE_POSIX_ERRNO 0 #endif @@ -887,13 +926,20 @@ #define configSUPPORT_DYNAMIC_ALLOCATION 1 #endif +#ifndef configSTACK_ALLOCATION_FROM_SEPARATE_HEAP + /* Defaults to 0 for backward compatibility. */ + #define configSTACK_ALLOCATION_FROM_SEPARATE_HEAP 0 +#endif + #ifndef configSTACK_DEPTH_TYPE + /* Defaults to uint16_t for backward compatibility, but can be overridden * in FreeRTOSConfig.h if uint16_t is too restrictive. */ #define configSTACK_DEPTH_TYPE uint16_t #endif #ifndef configMESSAGE_BUFFER_LENGTH_TYPE + /* Defaults to size_t for backward compatibility, but can be overridden * in FreeRTOSConfig.h if lengths will always be less than the number of bytes * in a size_t. */ @@ -920,6 +966,7 @@ #endif #if ( portTICK_TYPE_IS_ATOMIC == 0 ) + /* Either variables of tick type cannot be read atomically, or * portTICK_TYPE_IS_ATOMIC was not set - map the critical sections used when * the tick count is returned to the standard critical section macros. */ @@ -967,7 +1014,7 @@ #ifndef configMIN -/* The application writer has not provided their own MAX macro, so define +/* The application writer has not provided their own MIN macro, so define * the following generic implementation. */ #define configMIN( a, b ) ( ( ( a ) < ( b ) ) ? ( a ) : ( b ) ) #endif @@ -992,6 +1039,7 @@ #define pcTimerGetTimerName pcTimerGetName #define pcQueueGetQueueName pcQueueGetName #define vTaskGetTaskInfo vTaskGetInfo + #define xTaskGetIdleRunTimeCounter ulTaskGetIdleRunTimeCounter /* Backward compatibility within the scheduler code only - these definitions * are not really required but are included for completeness. */ @@ -1005,9 +1053,11 @@ #define pxContainer pvContainer #endif /* configENABLE_BACKWARD_COMPATIBILITY */ +#ifdef ESP_PLATFORM #ifndef configESP32_PER_TASK_DATA #define configESP32_PER_TASK_DATA 1 #endif +#endif // ESP_PLATFORM #if ( configUSE_ALTERNATIVE_API != 0 ) #error The alternative API was deprecated some time ago, and was removed in FreeRTOS V9.0 0 @@ -1096,7 +1146,7 @@ * data hiding policy, so the real structures used by FreeRTOS to maintain the * state of tasks, queues, semaphores, etc. are not accessible to the application * code. However, if the application writer wants to statically allocate such - * an object then the size of the object needs to be know. Dummy structures + * an object then the size of the object needs to be known. Dummy structures * that are guaranteed to have the same size and alignment requirements of the * real objects are used for this purpose. The dummy list and list item * structures below are used for inclusion in such a dummy structure. @@ -1145,7 +1195,7 @@ typedef struct xSTATIC_LIST * strict data hiding policy. This means the Task structure used internally by * FreeRTOS is not accessible to application code. However, if the application * writer wants to statically allocate the memory required to create a task then - * the size of the task object needs to be know. The StaticTask_t structure + * the size of the task object needs to be known. The StaticTask_t structure * below is provided for this purpose. Its sizes and alignment requirements are * guaranteed to match those of the genuine structure, no matter which * architecture is being used, and no matter how the values in FreeRTOSConfig.h @@ -1191,8 +1241,8 @@ typedef struct xSTATIC_TCB struct _reent xDummy17; #endif #if ( configUSE_TASK_NOTIFICATIONS == 1 ) - uint32_t ulDummy18; - uint8_t ucDummy19; + uint32_t ulDummy18[ configTASK_NOTIFICATION_ARRAY_ENTRIES ]; + uint8_t ucDummy19[ configTASK_NOTIFICATION_ARRAY_ENTRIES ]; #endif #if ( tskSTATIC_AND_DYNAMIC_ALLOCATION_POSSIBLE != 0 ) uint8_t uxDummy20; @@ -1212,7 +1262,7 @@ typedef struct xSTATIC_TCB * strict data hiding policy. This means the Queue structure used internally by * FreeRTOS is not accessible to application code. However, if the application * writer wants to statically allocate the memory required to create a queue - * then the size of the queue object needs to be know. The StaticQueue_t + * then the size of the queue object needs to be known. The StaticQueue_t * structure below is provided for this purpose. Its sizes and alignment * requirements are guaranteed to match those of the genuine structure, no * matter which architecture is being used, and no matter how the values in @@ -1246,9 +1296,7 @@ typedef struct xSTATIC_QUEUE UBaseType_t uxDummy8; uint8_t ucDummy9; #endif - portMUX_TYPE xDummy10; - } StaticQueue_t; typedef StaticQueue_t StaticSemaphore_t; @@ -1278,9 +1326,7 @@ typedef struct xSTATIC_EVENT_GROUP #if ( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) uint8_t ucDummy4; #endif - portMUX_TYPE xDummy5; - } StaticEventGroup_t; /* @@ -1289,7 +1335,7 @@ typedef struct xSTATIC_EVENT_GROUP * strict data hiding policy. This means the software timer structure used * internally by FreeRTOS is not accessible to application code. However, if * the application writer wants to statically allocate the memory required to - * create a software timer then the size of the queue object needs to be know. + * create a software timer then the size of the queue object needs to be known. * The StaticTimer_t structure below is provided for this purpose. Its sizes * and alignment requirements are guaranteed to match those of the genuine * structure, no matter which architecture is being used, and no matter how the @@ -1317,12 +1363,12 @@ typedef struct xSTATIC_TIMER * internally by FreeRTOS is not accessible to application code. However, if * the application writer wants to statically allocate the memory required to * create a stream buffer then the size of the stream buffer object needs to be - * know. The StaticStreamBuffer_t structure below is provided for this purpose. - * Its size and alignment requirements are guaranteed to match those of the - * genuine structure, no matter which architecture is being used, and no matter - * how the values in FreeRTOSConfig.h are set. Its contents are somewhat - * obfuscated in the hope users will recognise that it would be unwise to make - * direct use of the structure members. + * known. The StaticStreamBuffer_t structure below is provided for this + * purpose. Its size and alignment requirements are guaranteed to match those + * of the genuine structure, no matter which architecture is being used, and + * no matter how the values in FreeRTOSConfig.h are set. Its contents are + * somewhat obfuscated in the hope users will recognise that it would be unwise + * to make direct use of the structure members. */ typedef struct xSTATIC_STREAM_BUFFER { @@ -1332,9 +1378,7 @@ typedef struct xSTATIC_STREAM_BUFFER #if ( configUSE_TRACE_FACILITY == 1 ) UBaseType_t uxDummy4; #endif - portMUX_TYPE xDummy5; - } StaticStreamBuffer_t; /* Message buffers are built on stream buffers. */ diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/StackMacros.h b/tools/sdk/esp32c3/include/freertos/include/freertos/StackMacros.h new file mode 100644 index 00000000000..8d09f10cd1d --- /dev/null +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/StackMacros.h @@ -0,0 +1,32 @@ +/* + * FreeRTOS Kernel V10.4.3 + * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of + * this software and associated documentation files (the "Software"), to deal in + * the Software without restriction, including without limitation the rights to + * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is furnished to do so, + * subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS + * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR + * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER + * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + * https://www.FreeRTOS.org + * https://github.com/FreeRTOS + * + */ + + +#ifndef _MSC_VER /* Visual Studio doesn't support #warning. */ + #warning The name of this file has changed to stack_macros.h. Please update your code accordingly. This source file (which has the original name) will be removed in future released. +#endif + +#include "stack_macros.h" diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/atomic.h b/tools/sdk/esp32c3/include/freertos/include/freertos/atomic.h index d392e4193c3..a47b96723cc 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/atomic.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/atomic.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/croutine.h b/tools/sdk/esp32c3/include/freertos/include/freertos/croutine.h index 9b0a47de87b..99322d219f2 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/croutine.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/croutine.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/deprecated_definitions.h b/tools/sdk/esp32c3/include/freertos/include/freertos/deprecated_definitions.h index 40c4b4ee176..d3b942666d0 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/deprecated_definitions.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/deprecated_definitions.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/event_groups.h b/tools/sdk/esp32c3/include/freertos/include/freertos/event_groups.h index 9b7d2fd9236..84505ddaaa0 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/event_groups.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/event_groups.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/list.h b/tools/sdk/esp32c3/include/freertos/include/freertos/list.h index c91ecb9b06c..f76328f8e03 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/list.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/list.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/message_buffer.h b/tools/sdk/esp32c3/include/freertos/include/freertos/message_buffer.h index a2f56fe8682..e57c589fbac 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/message_buffer.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/message_buffer.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -676,7 +676,7 @@ typedef void * MessageBufferHandle_t; /** * @cond * message_buffer.h - * @code{c}{c} + * @code{c} * BaseType_t xMessageBufferIsEmpty( MessageBufferHandle_t xMessageBuffer ) ); * @endcode * @endcond diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_prototypes.h b/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_prototypes.h new file mode 100644 index 00000000000..ceb74f3e5bc --- /dev/null +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_prototypes.h @@ -0,0 +1,257 @@ +/* + * FreeRTOS Kernel V10.4.3 + * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. + * + * Permission is hereby granted, free of charge, to any person obtaining a copy of + * this software and associated documentation files (the "Software"), to deal in + * the Software without restriction, including without limitation the rights to + * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of + * the Software, and to permit persons to whom the Software is furnished to do so, + * subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS + * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR + * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER + * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN + * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + * + * https://www.FreeRTOS.org + * https://github.com/FreeRTOS + * + */ + +/* + * When the MPU is used the standard (non MPU) API functions are mapped to + * equivalents that start "MPU_", the prototypes for which are defined in this + * header files. This will cause the application code to call the MPU_ version + * which wraps the non-MPU version with privilege promoting then demoting code, + * so the kernel code always runs will full privileges. + */ + + +#ifndef MPU_PROTOTYPES_H +#define MPU_PROTOTYPES_H + +/* MPU versions of tasks.h API functions. */ +BaseType_t MPU_xTaskCreate( TaskFunction_t pxTaskCode, + const char * const pcName, + const uint16_t usStackDepth, + void * const pvParameters, + UBaseType_t uxPriority, + TaskHandle_t * const pxCreatedTask ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xTaskCreateStatic( TaskFunction_t pxTaskCode, + const char * const pcName, + const uint32_t ulStackDepth, + void * const pvParameters, + UBaseType_t uxPriority, + StackType_t * const puxStackBuffer, + StaticTask_t * const pxTaskBuffer ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskDelete( TaskHandle_t xTaskToDelete ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskDelay( const TickType_t xTicksToDelay ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskDelayUntil( TickType_t * const pxPreviousWakeTime, + const TickType_t xTimeIncrement ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskAbortDelay( TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxTaskPriorityGet( const TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +eTaskState MPU_eTaskGetState( TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskGetInfo( TaskHandle_t xTask, + TaskStatus_t * pxTaskStatus, + BaseType_t xGetFreeStackSpace, + eTaskState eState ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskPrioritySet( TaskHandle_t xTask, + UBaseType_t uxNewPriority ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskSuspend( TaskHandle_t xTaskToSuspend ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskResume( TaskHandle_t xTaskToResume ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskStartScheduler( void ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskSuspendAll( void ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskResumeAll( void ) FREERTOS_SYSTEM_CALL; +TickType_t MPU_xTaskGetTickCount( void ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxTaskGetNumberOfTasks( void ) FREERTOS_SYSTEM_CALL; +char * MPU_pcTaskGetName( TaskHandle_t xTaskToQuery ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xTaskGetHandle( const char * pcNameToQuery ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxTaskGetStackHighWaterMark( TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +configSTACK_DEPTH_TYPE MPU_uxTaskGetStackHighWaterMark2( TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskSetApplicationTaskTag( TaskHandle_t xTask, + TaskHookFunction_t pxHookFunction ) FREERTOS_SYSTEM_CALL; +TaskHookFunction_t MPU_xTaskGetApplicationTaskTag( TaskHandle_t xTask ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskSetThreadLocalStoragePointer( TaskHandle_t xTaskToSet, + BaseType_t xIndex, + void * pvValue ) FREERTOS_SYSTEM_CALL; +void * MPU_pvTaskGetThreadLocalStoragePointer( TaskHandle_t xTaskToQuery, + BaseType_t xIndex ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskCallApplicationTaskHook( TaskHandle_t xTask, + void * pvParameter ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xTaskGetIdleTaskHandle( void ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxTaskGetSystemState( TaskStatus_t * const pxTaskStatusArray, + const UBaseType_t uxArraySize, + uint32_t * const pulTotalRunTime ) FREERTOS_SYSTEM_CALL; +uint32_t MPU_ulTaskGetIdleRunTimeCounter( void ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskList( char * pcWriteBuffer ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskGetRunTimeStats( char * pcWriteBuffer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskGenericNotify( TaskHandle_t xTaskToNotify, + UBaseType_t uxIndexToNotify, + uint32_t ulValue, + eNotifyAction eAction, + uint32_t * pulPreviousNotificationValue ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskGenericNotifyWait( UBaseType_t uxIndexToWaitOn, + uint32_t ulBitsToClearOnEntry, + uint32_t ulBitsToClearOnExit, + uint32_t * pulNotificationValue, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +uint32_t MPU_ulTaskGenericNotifyTake( UBaseType_t uxIndexToWaitOn, + BaseType_t xClearCountOnExit, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskGenericNotifyStateClear( TaskHandle_t xTask, + UBaseType_t uxIndexToClear ) FREERTOS_SYSTEM_CALL; +uint32_t MPU_ulTaskGenericNotifyValueClear( TaskHandle_t xTask, + UBaseType_t uxIndexToClear, + uint32_t ulBitsToClear ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskIncrementTick( void ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xTaskGetCurrentTaskHandle( void ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskSetTimeOutState( TimeOut_t * const pxTimeOut ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskCheckForTimeOut( TimeOut_t * const pxTimeOut, + TickType_t * const pxTicksToWait ) FREERTOS_SYSTEM_CALL; +void MPU_vTaskMissedYield( void ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskGetSchedulerState( void ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTaskCatchUpTicks( TickType_t xTicksToCatchUp ) FREERTOS_SYSTEM_CALL; + +/* MPU versions of queue.h API functions. */ +BaseType_t MPU_xQueueGenericSend( QueueHandle_t xQueue, + const void * const pvItemToQueue, + TickType_t xTicksToWait, + const BaseType_t xCopyPosition ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueReceive( QueueHandle_t xQueue, + void * const pvBuffer, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueuePeek( QueueHandle_t xQueue, + void * const pvBuffer, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueSemaphoreTake( QueueHandle_t xQueue, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxQueueMessagesWaiting( const QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxQueueSpacesAvailable( const QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +void MPU_vQueueDelete( QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueCreateMutex( const uint8_t ucQueueType ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueCreateMutexStatic( const uint8_t ucQueueType, + StaticQueue_t * pxStaticQueue ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueCreateCountingSemaphore( const UBaseType_t uxMaxCount, + const UBaseType_t uxInitialCount ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueCreateCountingSemaphoreStatic( const UBaseType_t uxMaxCount, + const UBaseType_t uxInitialCount, + StaticQueue_t * pxStaticQueue ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xQueueGetMutexHolder( QueueHandle_t xSemaphore ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueTakeMutexRecursive( QueueHandle_t xMutex, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueGiveMutexRecursive( QueueHandle_t pxMutex ) FREERTOS_SYSTEM_CALL; +void MPU_vQueueAddToRegistry( QueueHandle_t xQueue, + const char * pcName ) FREERTOS_SYSTEM_CALL; +void MPU_vQueueUnregisterQueue( QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +const char * MPU_pcQueueGetName( QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueGenericCreate( const UBaseType_t uxQueueLength, + const UBaseType_t uxItemSize, + const uint8_t ucQueueType ) FREERTOS_SYSTEM_CALL; +QueueHandle_t MPU_xQueueGenericCreateStatic( const UBaseType_t uxQueueLength, + const UBaseType_t uxItemSize, + uint8_t * pucQueueStorage, + StaticQueue_t * pxStaticQueue, + const uint8_t ucQueueType ) FREERTOS_SYSTEM_CALL; +QueueSetHandle_t MPU_xQueueCreateSet( const UBaseType_t uxEventQueueLength ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueAddToSet( QueueSetMemberHandle_t xQueueOrSemaphore, + QueueSetHandle_t xQueueSet ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueRemoveFromSet( QueueSetMemberHandle_t xQueueOrSemaphore, + QueueSetHandle_t xQueueSet ) FREERTOS_SYSTEM_CALL; +QueueSetMemberHandle_t MPU_xQueueSelectFromSet( QueueSetHandle_t xQueueSet, + const TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xQueueGenericReset( QueueHandle_t xQueue, + BaseType_t xNewQueue ) FREERTOS_SYSTEM_CALL; +void MPU_vQueueSetQueueNumber( QueueHandle_t xQueue, + UBaseType_t uxQueueNumber ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxQueueGetQueueNumber( QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; +uint8_t MPU_ucQueueGetQueueType( QueueHandle_t xQueue ) FREERTOS_SYSTEM_CALL; + +/* MPU versions of timers.h API functions. */ +TimerHandle_t MPU_xTimerCreate( const char * const pcTimerName, + const TickType_t xTimerPeriodInTicks, + const UBaseType_t uxAutoReload, + void * const pvTimerID, + TimerCallbackFunction_t pxCallbackFunction ) FREERTOS_SYSTEM_CALL; +TimerHandle_t MPU_xTimerCreateStatic( const char * const pcTimerName, + const TickType_t xTimerPeriodInTicks, + const UBaseType_t uxAutoReload, + void * const pvTimerID, + TimerCallbackFunction_t pxCallbackFunction, + StaticTimer_t * pxTimerBuffer ) FREERTOS_SYSTEM_CALL; +void * MPU_pvTimerGetTimerID( const TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +void MPU_vTimerSetTimerID( TimerHandle_t xTimer, + void * pvNewID ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTimerIsTimerActive( TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +TaskHandle_t MPU_xTimerGetTimerDaemonTaskHandle( void ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTimerPendFunctionCall( PendedFunction_t xFunctionToPend, + void * pvParameter1, + uint32_t ulParameter2, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +const char * MPU_pcTimerGetName( TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +void MPU_vTimerSetReloadMode( TimerHandle_t xTimer, + const UBaseType_t uxAutoReload ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxTimerGetReloadMode( TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +TickType_t MPU_xTimerGetPeriod( TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +TickType_t MPU_xTimerGetExpiryTime( TimerHandle_t xTimer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTimerCreateTimerTask( void ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xTimerGenericCommand( TimerHandle_t xTimer, + const BaseType_t xCommandID, + const TickType_t xOptionalValue, + BaseType_t * const pxHigherPriorityTaskWoken, + const TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; + +/* MPU versions of event_group.h API functions. */ +EventGroupHandle_t MPU_xEventGroupCreate( void ) FREERTOS_SYSTEM_CALL; +EventGroupHandle_t MPU_xEventGroupCreateStatic( StaticEventGroup_t * pxEventGroupBuffer ) FREERTOS_SYSTEM_CALL; +EventBits_t MPU_xEventGroupWaitBits( EventGroupHandle_t xEventGroup, + const EventBits_t uxBitsToWaitFor, + const BaseType_t xClearOnExit, + const BaseType_t xWaitForAllBits, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +EventBits_t MPU_xEventGroupClearBits( EventGroupHandle_t xEventGroup, + const EventBits_t uxBitsToClear ) FREERTOS_SYSTEM_CALL; +EventBits_t MPU_xEventGroupSetBits( EventGroupHandle_t xEventGroup, + const EventBits_t uxBitsToSet ) FREERTOS_SYSTEM_CALL; +EventBits_t MPU_xEventGroupSync( EventGroupHandle_t xEventGroup, + const EventBits_t uxBitsToSet, + const EventBits_t uxBitsToWaitFor, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +void MPU_vEventGroupDelete( EventGroupHandle_t xEventGroup ) FREERTOS_SYSTEM_CALL; +UBaseType_t MPU_uxEventGroupGetNumber( void * xEventGroup ) FREERTOS_SYSTEM_CALL; + +/* MPU versions of message/stream_buffer.h API functions. */ +size_t MPU_xStreamBufferSend( StreamBufferHandle_t xStreamBuffer, + const void * pvTxData, + size_t xDataLengthBytes, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +size_t MPU_xStreamBufferReceive( StreamBufferHandle_t xStreamBuffer, + void * pvRxData, + size_t xBufferLengthBytes, + TickType_t xTicksToWait ) FREERTOS_SYSTEM_CALL; +size_t MPU_xStreamBufferNextMessageLengthBytes( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +void MPU_vStreamBufferDelete( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xStreamBufferIsFull( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xStreamBufferIsEmpty( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xStreamBufferReset( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +size_t MPU_xStreamBufferSpacesAvailable( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +size_t MPU_xStreamBufferBytesAvailable( StreamBufferHandle_t xStreamBuffer ) FREERTOS_SYSTEM_CALL; +BaseType_t MPU_xStreamBufferSetTriggerLevel( StreamBufferHandle_t xStreamBuffer, + size_t xTriggerLevel ) FREERTOS_SYSTEM_CALL; +StreamBufferHandle_t MPU_xStreamBufferGenericCreate( size_t xBufferSizeBytes, + size_t xTriggerLevelBytes, + BaseType_t xIsMessageBuffer ) FREERTOS_SYSTEM_CALL; +StreamBufferHandle_t MPU_xStreamBufferGenericCreateStatic( size_t xBufferSizeBytes, + size_t xTriggerLevelBytes, + BaseType_t xIsMessageBuffer, + uint8_t * const pucStreamBufferStorageArea, + StaticStreamBuffer_t * const pxStaticStreamBuffer ) FREERTOS_SYSTEM_CALL; + + + +#endif /* MPU_PROTOTYPES_H */ diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_wrappers.h b/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_wrappers.h index b881448a5d5..c02dcd0c41e 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_wrappers.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/mpu_wrappers.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/portable.h b/tools/sdk/esp32c3/include/freertos/include/freertos/portable.h index ce832f6c265..acc337cb968 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/portable.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/portable.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -181,6 +181,13 @@ void vPortInitialiseBlocks( void ) PRIVILEGED_FUNCTION; size_t xPortGetFreeHeapSize( void ) PRIVILEGED_FUNCTION; size_t xPortGetMinimumEverFreeHeapSize( void ) PRIVILEGED_FUNCTION; +#if( configSTACK_ALLOCATION_FROM_SEPARATE_HEAP == 1 ) + void *pvPortMallocStack( size_t xSize ) PRIVILEGED_FUNCTION; + void vPortFreeStack( void *pv ) PRIVILEGED_FUNCTION; +#else + #define pvPortMallocStack pvPortMalloc + #define vPortFreeStack vPortFree +#endif #else // configUSE_FREERTOS_PROVIDED_HEAP /* @@ -210,6 +217,21 @@ BaseType_t xPortStartScheduler( void ) PRIVILEGED_FUNCTION; */ void vPortEndScheduler( void ) PRIVILEGED_FUNCTION; +/* + * The structures and methods of manipulating the MPU are contained within the + * port layer. + * + * Fills the xMPUSettings structure with the memory region information + * contained in xRegions. + */ +#if ( portUSING_MPU_WRAPPERS == 1 ) + struct xMEMORY_REGION; + void vPortStoreTaskMPUSettings( xMPU_SETTINGS * xMPUSettings, + const struct xMEMORY_REGION * const xRegions, + StackType_t * pxBottomOfStack, + uint32_t ulStackDepth ) PRIVILEGED_FUNCTION; +#endif + /* *INDENT-OFF* */ #ifdef __cplusplus } diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/projdefs.h b/tools/sdk/esp32c3/include/freertos/include/freertos/projdefs.h index 04f7b123439..ec8022ca0b0 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/projdefs.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/projdefs.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -37,13 +37,13 @@ typedef void (* TaskFunction_t)( void * ); * overridden by a macro of the same name defined in FreeRTOSConfig.h in case the * definition here is not suitable for your application. */ #ifndef pdMS_TO_TICKS - #define pdMS_TO_TICKS( xTimeInMs ) ( ( TickType_t ) ( ( ( TickType_t ) ( xTimeInMs ) * ( TickType_t ) configTICK_RATE_HZ ) / ( TickType_t ) 1000 ) ) + #define pdMS_TO_TICKS( xTimeInMs ) ( ( TickType_t ) ( ( ( TickType_t ) ( xTimeInMs ) * ( TickType_t ) configTICK_RATE_HZ ) / ( TickType_t ) 1000U ) ) #endif - +#ifdef ESP_PLATFORM #ifndef pdTICKS_TO_MS #define pdTICKS_TO_MS( xTicks ) ( ( uint32_t ) ( xTicks ) * 1000 / configTICK_RATE_HZ ) #endif - +#endif // ESP_PLATFORM #define pdFALSE ( ( BaseType_t ) 0 ) #define pdTRUE ( ( BaseType_t ) 1 ) diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/queue.h b/tools/sdk/esp32c3/include/freertos/include/freertos/queue.h index 9ff31d7eb82..81cccc05df3 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/queue.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/queue.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -80,8 +80,30 @@ typedef struct QueueDefinition * QueueSetMemberHandle_t; /** @endcond */ /** - * Creates a new queue instance. This allocates the storage required by the - * new queue and returns a handle for the queue. + * @cond + * queue. h + * @code{c} + * QueueHandle_t xQueueCreate( + * UBaseType_t uxQueueLength, + * UBaseType_t uxItemSize + * ); + * @endcode + * @endcond + * + * Creates a new queue instance, and returns a handle by which the new queue + * can be referenced. + * + * Internally, within the FreeRTOS implementation, queues use two blocks of + * memory. The first block is used to hold the queue's data structures. The + * second block is used to hold items placed into the queue. If a queue is + * created using xQueueCreate() then both blocks of memory are automatically + * dynamically allocated inside the xQueueCreate() function. (see + * https://www.FreeRTOS.org/a00111.html). If a queue is created using + * xQueueCreateStatic() then the application writer must provide the memory that + * will get used by the queue. xQueueCreateStatic() therefore allows a queue to + * be created without using any dynamic memory allocation. + * + * https://www.FreeRTOS.org/Embedded-RTOS-Queues.html * * @param uxQueueLength The maximum number of items that the queue can contain. * @@ -1167,7 +1189,7 @@ void vQueueDelete( QueueHandle_t xQueue ) PRIVILEGED_FUNCTION; * void vFunction( void *pvParameters ) * { * // Create a queue to hold one uint32_t value. It is strongly - * // recommended \*not\* to use xQueueOverwriteFromISR() on queues that can + * // recommended *not* to use xQueueOverwriteFromISR() on queues that can * // contain more than one value, and doing so will trigger an assertion * // if configASSERT() is defined. * xQueue = xQueueCreate( 1, sizeof( uint32_t ) ); @@ -1562,7 +1584,8 @@ BaseType_t xQueueGiveMutexRecursive( QueueHandle_t xMutex ) PRIVILEGED_FUNCTION; * preferably in ROM/Flash), not on the stack. */ #if ( configQUEUE_REGISTRY_SIZE > 0 ) - void vQueueAddToRegistry( QueueHandle_t xQueue, const char * pcQueueName ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + void vQueueAddToRegistry( QueueHandle_t xQueue, + const char * pcQueueName ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ #endif /** diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/semphr.h b/tools/sdk/esp32c3/include/freertos/include/freertos/semphr.h index d692375e651..7e99c0b396c 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/semphr.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/semphr.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -312,6 +312,16 @@ typedef QueueHandle_t SemaphoreHandle_t; #define xSemaphoreTake( xSemaphore, xBlockTime ) xQueueSemaphoreTake( ( xSemaphore ), ( xBlockTime ) ) /** + * @cond + * semphr. h + * @code{c} + * xSemaphoreTakeRecursive( + * SemaphoreHandle_t xMutex, + * TickType_t xBlockTime + * ); + * @endcode + * @endcond + * * Macro to recursively obtain, or 'take', a mutex type semaphore. * The mutex must have previously been created using a call to * xSemaphoreCreateRecursiveMutex(); @@ -400,22 +410,6 @@ typedef QueueHandle_t SemaphoreHandle_t; */ #define xSemaphoreTakeRecursive( xMutex, xBlockTime ) xQueueTakeMutexRecursive( ( xMutex ), ( xBlockTime ) ) -/** @cond */ -/* - * xSemaphoreAltTake() is an alternative version of xSemaphoreTake(). - * - * The source code that implements the alternative (Alt) API is much - * simpler because it executes everything from within a critical section. - * This is the approach taken by many other RTOSes, but FreeRTOS.org has the - * preferred fully featured API too. The fully featured API has more - * complex code that takes longer to execute, but makes much less use of - * critical sections. Therefore the alternative API sacrifices interrupt - * responsiveness to gain execution speed, whereas the fully featured API - * sacrifices execution speed to ensure better interrupt responsiveness. - */ -#define xSemaphoreAltTake( xSemaphore, xBlockTime ) xQueueAltGenericReceive( ( QueueHandle_t ) ( xSemaphore ), NULL, ( xBlockTime ), pdFALSE ) -/** @endcond */ - /** * Macro to release a semaphore. The semaphore must have previously been * created with a call to xSemaphoreCreateBinary(), xSemaphoreCreateMutex() or @@ -568,23 +562,6 @@ typedef QueueHandle_t SemaphoreHandle_t; */ #define xSemaphoreGiveRecursive( xMutex ) xQueueGiveMutexRecursive( ( xMutex ) ) -/** @cond */ -/* - * xSemaphoreAltGive() is an alternative version of xSemaphoreGive(). - * - * The source code that implements the alternative (Alt) API is much - * simpler because it executes everything from within a critical section. - * This is the approach taken by many other RTOSes, but FreeRTOS.org has the - * preferred fully featured API too. The fully featured API has more - * complex code that takes longer to execute, but makes much less use of - * critical sections. Therefore the alternative API sacrifices interrupt - * responsiveness to gain execution speed, whereas the fully featured API - * sacrifices execution speed to ensure better interrupt responsiveness. - */ -#define xSemaphoreAltGive( xSemaphore ) xQueueAltGenericSend( ( QueueHandle_t ) ( xSemaphore ), NULL, semGIVE_BLOCK_TIME, queueSEND_TO_BACK ) - -/** @endcond */ - /** * Macro to release a semaphore. The semaphore must have previously been * created with a call to xSemaphoreCreateBinary() or xSemaphoreCreateCounting(). @@ -950,7 +927,7 @@ typedef QueueHandle_t SemaphoreHandle_t; * returned. * * Example usage: - * @code + * @code{c} * SemaphoreHandle_t xSemaphore; * StaticSemaphore_t xMutexBuffer; * diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/stack_macros.h b/tools/sdk/esp32c3/include/freertos/include/freertos/stack_macros.h index 27a01ccf04b..249c4ef840d 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/stack_macros.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/stack_macros.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -65,8 +65,8 @@ /* Only the current stack state is to be checked. */ #define taskFIRST_CHECK_FOR_STACK_OVERFLOW() \ - { \ - /* Is the currently saved stack pointer within the stack limit? */ \ + { \ + /* Is the currently saved stack pointer within the stack limit? */ \ if( pxCurrentTCB[ xPortGetCoreID() ]->pxTopOfStack <= pxCurrentTCB[ xPortGetCoreID() ]->pxStack ) \ { \ vApplicationStackOverflowHook( ( TaskHandle_t ) pxCurrentTCB[ xPortGetCoreID() ], pxCurrentTCB[ xPortGetCoreID() ]->pcTaskName ); \ @@ -80,8 +80,8 @@ /* Only the current stack state is to be checked. */ #define taskFIRST_CHECK_FOR_STACK_OVERFLOW() \ - { \ - \ + { \ + \ /* Is the currently saved stack pointer within the stack limit? */ \ if( pxCurrentTCB[ xPortGetCoreID() ]->pxTopOfStack >= pxCurrentTCB[ xPortGetCoreID() ]->pxEndOfStack ) \ { \ @@ -92,22 +92,22 @@ #endif /* configCHECK_FOR_STACK_OVERFLOW == 1 */ /*-----------------------------------------------------------*/ -#if( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) && ( portSTACK_GROWTH < 0 ) ) +#if ( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) && ( portSTACK_GROWTH < 0 ) ) #define taskSECOND_CHECK_FOR_STACK_OVERFLOW() \ - { \ + { \ static const uint8_t ucExpectedStackBytes[] = { tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE }; \ - \ + \ \ /* Has the extremity of the task stack ever been written over? */ \ if( memcmp( ( void * ) pxCurrentTCB[ xPortGetCoreID() ]->pxStack, ( void * ) ucExpectedStackBytes, sizeof( ucExpectedStackBytes ) ) != 0 ) \ - { \ + { \ vApplicationStackOverflowHook( ( TaskHandle_t ) pxCurrentTCB[ xPortGetCoreID() ], pxCurrentTCB[ xPortGetCoreID() ]->pcTaskName ); \ - } \ + } \ } #endif /* #if( configCHECK_FOR_STACK_OVERFLOW > 1 ) */ @@ -116,7 +116,7 @@ #if ( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) && ( portSTACK_GROWTH > 0 ) ) #define taskSECOND_CHECK_FOR_STACK_OVERFLOW() \ - { \ + { \ int8_t *pcEndOfStack = ( int8_t * ) pxCurrentTCB[ xPortGetCoreID() ]->pxEndOfStack; \ static const uint8_t ucExpectedStackBytes[] = { tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, tskSTACK_FILL_BYTE, \ diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/stream_buffer.h b/tools/sdk/esp32c3/include/freertos/include/freertos/stream_buffer.h index ba8282ce73f..9e58cff120c 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/stream_buffer.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/stream_buffer.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/task.h b/tools/sdk/esp32c3/include/freertos/include/freertos/task.h index 8d525f244bf..9135b76f014 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/task.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/task.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of @@ -47,10 +47,10 @@ * MACROS AND DEFINITIONS *----------------------------------------------------------*/ -#define tskKERNEL_VERSION_NUMBER "V10.2.1" -#define tskKERNEL_VERSION_MAJOR 10 -#define tskKERNEL_VERSION_MINOR 2 -#define tskKERNEL_VERSION_BUILD 1 +#define tskKERNEL_VERSION_NUMBER "V10.4.3" +#define tskKERNEL_VERSION_MAJOR 10 +#define tskKERNEL_VERSION_MINOR 4 +#define tskKERNEL_VERSION_BUILD 3 /* MPU region parameters passed in ulParameters * of MemoryRegion_t struct. */ @@ -60,7 +60,15 @@ #define tskMPU_REGION_NORMAL_MEMORY ( 1UL << 3UL ) #define tskMPU_REGION_DEVICE_MEMORY ( 1UL << 4UL ) +/* The direct to task notification feature used to have only a single notification + * per task. Now there is an array of notifications per task that is dimensioned by + * configTASK_NOTIFICATION_ARRAY_ENTRIES. For backward compatibility, any use of the + * original direct to task notification defaults to using the first index in the + * array. */ +#define tskDEFAULT_INDEX_TO_NOTIFY ( 0 ) + #define tskNO_AFFINITY ( 0x7FFFFFFF ) + /** * task. h * @@ -143,10 +151,8 @@ typedef struct xTASK_PARAMETERS #endif } TaskParameters_t; - -/* - * Used with the uxTaskGetSystemState() function to return the state of each task in the system. - */ +/* Used with the uxTaskGetSystemState() function to return the state of each task + * in the system. */ typedef struct xTASK_STATUS { TaskHandle_t xHandle; /* The handle of the task to which the rest of the information in the structure relates. */ @@ -155,8 +161,8 @@ typedef struct xTASK_STATUS eTaskState eCurrentState; /* The state in which the task existed when the structure was populated. */ UBaseType_t uxCurrentPriority; /* The priority at which the task was running (may be inherited) when the structure was populated. */ UBaseType_t uxBasePriority; /* The priority to which the task will return if the task's current priority has been inherited to avoid unbounded priority inversion when obtaining a mutex. Only valid if configUSE_MUTEXES is defined as 1 in FreeRTOSConfig.h. */ - uint32_t ulRunTimeCounter; /* The total run time allocated to the task so far, as defined by the run time stats clock. See http://www.freertos.org/rtos-run-time-stats.html. Only valid when configGENERATE_RUN_TIME_STATS is defined as 1 in FreeRTOSConfig.h. */ - StackType_t *pxStackBase; /* Points to the lowest address of the task's stack area. */ + uint32_t ulRunTimeCounter; /* The total run time allocated to the task so far, as defined by the run time stats clock. See https://www.FreeRTOS.org/rtos-run-time-stats.html. Only valid when configGENERATE_RUN_TIME_STATS is defined as 1 in FreeRTOSConfig.h. */ + StackType_t * pxStackBase; /* Points to the lowest address of the task's stack area. */ configSTACK_DEPTH_TYPE usStackHighWaterMark; /* The minimum amount of stack space that has remained for the task since the task was created. The closer this value is to zero the closer the task has come to overflowing its stack. */ #if configTASKLIST_INCLUDE_COREID BaseType_t xCoreID; /*!< Core this task is pinned to (0, 1, or -1 for tskNO_AFFINITY). This field is present if CONFIG_FREERTOS_VTASKLIST_INCLUDE_COREID is set. */ @@ -605,7 +611,16 @@ typedef enum } #endif /* configSUPPORT_STATIC_ALLOCATION */ -/* +/** + * @cond + * task. h + * @code{c} + * BaseType_t xTaskCreateRestricted( TaskParameters_t *pxTaskDefinition, TaskHandle_t *pxCreatedTask ); + * @endcode + * @endcond + * + * Only available when configSUPPORT_DYNAMIC_ALLOCATION is set to 1. + * * xTaskCreateRestricted() should only be used in systems that include an MPU * implementation. * @@ -675,15 +690,22 @@ typedef enum */ #if ( portUSING_MPU_WRAPPERS == 1 ) BaseType_t xTaskCreateRestricted( const TaskParameters_t * const pxTaskDefinition, - TaskHandle_t * pxCreatedTask ); + TaskHandle_t * pxCreatedTask ); #endif -/* - * xTaskCreateRestrictedStatic() should only be used in systems that include an - * MPU implementation. +/** + * @cond + * task. h + * @code{c} + * BaseType_t xTaskCreateRestrictedStatic( TaskParameters_t *pxTaskDefinition, TaskHandle_t *pxCreatedTask ); + * @endcode + * @endcond * * Only available when configSUPPORT_STATIC_ALLOCATION is set to 1. * + * xTaskCreateRestrictedStatic() should only be used in systems that include an + * MPU implementation. + * * Internally, within the FreeRTOS implementation, tasks use two blocks of * memory. The first block is used to hold the task's data structures. The * second block is used by the task as its stack. If a task is created using @@ -762,7 +784,7 @@ typedef enum */ #if ( ( portUSING_MPU_WRAPPERS == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) BaseType_t xTaskCreateRestrictedStatic( const TaskParameters_t * const pxTaskDefinition, - TaskHandle_t * pxCreatedTask ); + TaskHandle_t * pxCreatedTask ) PRIVILEGED_FUNCTION; #endif /** @@ -820,8 +842,12 @@ void vTaskAllocateMPURegions( TaskHandle_t xTask, const MemoryRegion_t * const pxRegions ) PRIVILEGED_FUNCTION; /** - * Remove a task from the RTOS real time kernel's management. The task being - * deleted will be removed from all ready, blocked, suspended and event lists. + * @cond + * task. h + * @code{c} + * void vTaskDelete( TaskHandle_t xTask ); + * @endcode + * @endcond * * INCLUDE_vTaskDelete must be defined as 1 for this function to be available. * See the configuration section for more information. @@ -867,7 +893,10 @@ void vTaskDelete( TaskHandle_t xTaskToDelete ) PRIVILEGED_FUNCTION; *----------------------------------------------------------*/ /** - * Delay a task for a given number of ticks. + * task. h + * @code{c} + * void vTaskDelay( const TickType_t xTicksToDelay ); + * @endcode * * Delay a task for a given number of ticks. The actual time that the * task remains blocked depends on the tick rate. The constant @@ -885,7 +914,7 @@ void vTaskDelete( TaskHandle_t xTaskToDelete ) PRIVILEGED_FUNCTION; * of controlling the frequency of a periodic task as the path taken through the * code, as well as other task and interrupt activity, will effect the frequency * at which vTaskDelay() gets called and therefore the time at which the task - * next executes. See vTaskDelayUntil() for an alternative API function designed + * next executes. See xTaskDelayUntil() for an alternative API function designed * to facilitate fixed frequency execution. It does this by specifying an * absolute time (rather than a relative time) at which the calling task should * unblock. @@ -917,9 +946,12 @@ void vTaskDelete( TaskHandle_t xTaskToDelete ) PRIVILEGED_FUNCTION; void vTaskDelay( const TickType_t xTicksToDelay ) PRIVILEGED_FUNCTION; /** - * Delay a task until a specified time. + * task. h + * @code{c} + * BaseType_t xTaskDelayUntil( TickType_t *pxPreviousWakeTime, const TickType_t xTimeIncrement ); + * @endcode * - * INCLUDE_vTaskDelayUntil must be defined as 1 for this function to be available. + * INCLUDE_xTaskDelayUntil must be defined as 1 for this function to be available. * See the configuration section for more information. * * Delay a task until a specified time. This function can be used by periodic @@ -934,22 +966,26 @@ void vTaskDelay( const TickType_t xTicksToDelay ) PRIVILEGED_FUNCTION; * each time it executes]. * * Whereas vTaskDelay () specifies a wake time relative to the time at which the function - * is called, vTaskDelayUntil () specifies the absolute (exact) time at which it wishes to + * is called, xTaskDelayUntil () specifies the absolute (exact) time at which it wishes to * unblock. * - * The constant portTICK_PERIOD_MS can be used to calculate real time from the tick - * rate - with the resolution of one tick period. + * The macro pdMS_TO_TICKS() can be used to calculate the number of ticks from a + * time specified in milliseconds with a resolution of one tick period. * * @param pxPreviousWakeTime Pointer to a variable that holds the time at which the * task was last unblocked. The variable must be initialised with the current time * prior to its first use (see the example below). Following this the variable is - * automatically updated within vTaskDelayUntil (). + * automatically updated within xTaskDelayUntil (). * * @param xTimeIncrement The cycle time period. The task will be unblocked at - * time *pxPreviousWakeTime + xTimeIncrement. Calling vTaskDelayUntil with the + * time *pxPreviousWakeTime + xTimeIncrement. Calling xTaskDelayUntil with the * same xTimeIncrement parameter value will cause the task to execute with * a fixed interface period. * + * @return Value which can be used to check whether the task was actually delayed. + * Will be pdTRUE if the task way delayed and pdFALSE otherwise. A task will not + * be delayed if the next expected wake time is in the past. + * * Example usage: * @code{c} * // Perform an action every 10 ticks. @@ -957,15 +993,17 @@ void vTaskDelay( const TickType_t xTicksToDelay ) PRIVILEGED_FUNCTION; * { * TickType_t xLastWakeTime; * const TickType_t xFrequency = 10; + * BaseType_t xWasDelayed; * * // Initialise the xLastWakeTime variable with the current time. * xLastWakeTime = xTaskGetTickCount (); * for( ;; ) * { * // Wait for the next cycle. - * vTaskDelayUntil( &xLastWakeTime, xFrequency ); + * xWasDelayed = xTaskDelayUntil( &xLastWakeTime, xFrequency ); * - * // Perform action here. + * // Perform action here. xWasDelayed value can be used to determine + * // whether a deadline was missed if the code here took too long. * } * } * @endcode @@ -974,9 +1012,19 @@ void vTaskDelay( const TickType_t xTicksToDelay ) PRIVILEGED_FUNCTION; * @endcond * \ingroup TaskCtrl */ -void vTaskDelayUntil( TickType_t * const pxPreviousWakeTime, +BaseType_t xTaskDelayUntil( TickType_t * const pxPreviousWakeTime, const TickType_t xTimeIncrement ) PRIVILEGED_FUNCTION; +/* + * vTaskDelayUntil() is the older version of xTaskDelayUntil() and does not + * return a value. + */ +#define vTaskDelayUntil( pxPreviousWakeTime, xTimeIncrement ) \ +{ \ + ( void ) xTaskDelayUntil( pxPreviousWakeTime, xTimeIncrement ); \ +} + + /** * @cond * task. h @@ -1215,7 +1263,12 @@ void vTaskPrioritySet( TaskHandle_t xTask, UBaseType_t uxNewPriority ) PRIVILEGED_FUNCTION; /** - * Suspend a task. + * @cond + * task. h + * @code{c} + * void vTaskSuspend( TaskHandle_t xTaskToSuspend ); + * @endcode + * @endcond * * INCLUDE_vTaskSuspend must be defined as 1 for this function to be available. * See the configuration section for more information. @@ -1322,11 +1375,18 @@ void vTaskSuspend( TaskHandle_t xTaskToSuspend ) PRIVILEGED_FUNCTION; void vTaskResume( TaskHandle_t xTaskToResume ) PRIVILEGED_FUNCTION; /** - * An implementation of vTaskResume() that can be called from within an ISR. + * @cond + * task. h + * @code{c} + * void xTaskResumeFromISR( TaskHandle_t xTaskToResume ); + * @endcode + * @endcond * * INCLUDE_xTaskResumeFromISR must be defined as 1 for this function to be * available. See the configuration section for more information. * + * An implementation of vTaskResume() that can be called from within an ISR. + * * A task that has been suspended by one or more calls to vTaskSuspend () * will be made available for running again by a single call to * xTaskResumeFromISR (). @@ -1354,14 +1414,20 @@ BaseType_t xTaskResumeFromISR( TaskHandle_t xTaskToResume ) PRIVILEGED_FUNCTION; *----------------------------------------------------------*/ /** @cond */ /** - * Starts the real time kernel tick processing. + * @cond + * task. h + * @code{c} + * void vTaskStartScheduler( void ); + * @endcode + * @endcond * + * Starts the real time kernel tick processing. After calling the kernel + * has control over which tasks are executed and when. + * NOTE: In ESP-IDF the scheduler is started automatically during * application startup, vTaskStartScheduler() should not be called from * ESP-IDF applications. * - * After calling the kernel has control over which tasks are executed and when. - * * See the demo application file main.c for an example of creating * tasks and starting the kernel. * @@ -1387,7 +1453,12 @@ BaseType_t xTaskResumeFromISR( TaskHandle_t xTaskToResume ) PRIVILEGED_FUNCTION; void vTaskStartScheduler( void ) PRIVILEGED_FUNCTION; /** - * Stops the real time kernel tick. + * @cond + * task. h + * @code{c} + * void vTaskEndScheduler( void ); + * @endcode + * @endcond * * NOTE: At the time of writing only the x86 real mode port, which runs on a PC * in place of DOS, implements this function. @@ -1446,9 +1517,15 @@ void vTaskEndScheduler( void ) PRIVILEGED_FUNCTION; /** @endcond */ /** - * Suspends the scheduler without disabling interrupts. + * @cond + * task. h + * @code{c} + * void vTaskSuspendAll( void ); + * @endcode + * @endcond * - * Context switches will not occur while the scheduler is suspended. + * Suspends the scheduler without disabling interrupts. Context switches will + * not occur while the scheduler is suspended. * * After calling vTaskSuspendAll () the calling task will continue to execute * without risk of being swapped out until a call to xTaskResumeAll () has been @@ -1561,7 +1638,12 @@ BaseType_t xTaskResumeAll( void ) PRIVILEGED_FUNCTION; *----------------------------------------------------------*/ /** - * Get tick count + * @cond + * task. h + * @code{c} + * TickType_t xTaskGetTickCount( void ); + * @endcode + * @endcond * * @return The count of ticks since vTaskStartScheduler was called. * @@ -1573,7 +1655,12 @@ BaseType_t xTaskResumeAll( void ) PRIVILEGED_FUNCTION; TickType_t xTaskGetTickCount( void ) PRIVILEGED_FUNCTION; /** - * Get tick count from ISR + * @cond + * task. h + * @code{c} + * TickType_t xTaskGetTickCountFromISR( void ); + * @endcode + * @endcond * * @return The count of ticks since vTaskStartScheduler was called. * @@ -1590,7 +1677,12 @@ TickType_t xTaskGetTickCount( void ) PRIVILEGED_FUNCTION; TickType_t xTaskGetTickCountFromISR( void ) PRIVILEGED_FUNCTION; /** - * Get current number of tasks + * @cond + * task. h + * @code{c} + * uint16_t uxTaskGetNumberOfTasks( void ); + * @endcode + * @endcond * * @return The number of tasks that the real time kernel is currently managing. * This includes all ready, blocked and suspended tasks. A task that @@ -1605,7 +1697,12 @@ TickType_t xTaskGetTickCountFromISR( void ) PRIVILEGED_FUNCTION; UBaseType_t uxTaskGetNumberOfTasks( void ) PRIVILEGED_FUNCTION; /** - * Get task name + * @cond + * task. h + * @code{c} + * char *pcTaskGetName( TaskHandle_t xTaskToQuery ); + * @endcode + * @endcond * * @return The text (human readable) name of the task referenced by the handle * xTaskToQuery. A task can query its own name by either passing in its own @@ -1616,10 +1713,17 @@ UBaseType_t uxTaskGetNumberOfTasks( void ) PRIVILEGED_FUNCTION; * @endcond * \ingroup TaskUtils */ -char *pcTaskGetName( TaskHandle_t xTaskToQuery ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +char * pcTaskGetName( TaskHandle_t xTaskToQuery ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ /** - * @note This function takes a relatively long time to complete and should be + * @cond + * task. h + * @code{c} + * TaskHandle_t xTaskGetHandle( const char *pcNameToQuery ); + * @endcode + * @endcond + * + * NOTE: This function takes a relatively long time to complete and should be * used sparingly. * * @return The handle of the task that has the human readable name pcNameToQuery. @@ -1769,7 +1873,9 @@ uint8_t* pxTaskGetStackStart( TaskHandle_t xTask) PRIVILEGED_FUNCTION; * configNUM_THREAD_LOCAL_STORAGE_POINTERS - 1. * @param pvValue Pointer value to set. */ - void vTaskSetThreadLocalStoragePointer( TaskHandle_t xTaskToSet, BaseType_t xIndex, void *pvValue ) PRIVILEGED_FUNCTION; + void vTaskSetThreadLocalStoragePointer( TaskHandle_t xTaskToSet, + BaseType_t xIndex, + void * pvValue ) PRIVILEGED_FUNCTION; /** @@ -1785,7 +1891,8 @@ uint8_t* pxTaskGetStackStart( TaskHandle_t xTask) PRIVILEGED_FUNCTION; * configNUM_THREAD_LOCAL_STORAGE_POINTERS - 1. * @return Pointer value */ - void *pvTaskGetThreadLocalStoragePointer( TaskHandle_t xTaskToQuery, BaseType_t xIndex ) PRIVILEGED_FUNCTION; + void * pvTaskGetThreadLocalStoragePointer( TaskHandle_t xTaskToQuery, + BaseType_t xIndex ) PRIVILEGED_FUNCTION; #if ( configTHREAD_LOCAL_STORAGE_DELETE_CALLBACKS ) @@ -1822,6 +1929,62 @@ uint8_t* pxTaskGetStackStart( TaskHandle_t xTask) PRIVILEGED_FUNCTION; #endif +#if ( configCHECK_FOR_STACK_OVERFLOW > 0 ) + + /** + * @cond + * task.h + * @code{c} + * void vApplicationStackOverflowHook( TaskHandle_t xTask char *pcTaskName); + * @endcode + * @endcond + * The application stack overflow hook is called when a stack overflow is detected for a task. + * + * Details on stack overflow detection can be found here: https://www.FreeRTOS.org/Stacks-and-stack-overflow-checking.html + * + * @param xTask the task that just exceeded its stack boundaries. + * @param pcTaskName A character string containing the name of the offending task. + */ + void vApplicationStackOverflowHook( TaskHandle_t xTask, + char * pcTaskName ); + +#endif + +#if ( configUSE_TICK_HOOK > 0 ) + /** + * @cond + * task.h + * @code{c} + * void vApplicationTickHook( void ); + * @endcode + * @endcond + * + * This hook function is called in the system tick handler after any OS work is completed. + */ + void vApplicationTickHook( void ); /*lint !e526 Symbol not defined as it is an application callback. */ + +#endif + +#if ( configSUPPORT_STATIC_ALLOCATION == 1 ) + /** + * @cond + * task.h + * @code{c} + * void vApplicationGetIdleTaskMemory( StaticTask_t ** ppxIdleTaskTCBBuffer, StackType_t ** ppxIdleTaskStackBuffer, uint32_t *pulIdleTaskStackSize ) + * @endcode + * @endcond + * This function is used to provide a statically allocated block of memory to FreeRTOS to hold the Idle Task TCB. This function is required when + * configSUPPORT_STATIC_ALLOCATION is set. For more information see this URI: https://www.FreeRTOS.org/a00110.html#configSUPPORT_STATIC_ALLOCATION + * + * @param ppxIdleTaskTCBBuffer A handle to a statically allocated TCB buffer + * @param ppxIdleTaskStackBuffer A handle to a statically allocated Stack buffer for thie idle task + * @param pulIdleTaskStackSize A pointer to the number of elements that will fit in the allocated stack buffer + */ + void vApplicationGetIdleTaskMemory( StaticTask_t ** ppxIdleTaskTCBBuffer, + StackType_t ** ppxIdleTaskStackBuffer, + uint32_t * pulIdleTaskStackSize ); /*lint !e526 Symbol not defined as it is an application callback. */ +#endif + /** * @cond * task.h @@ -2057,7 +2220,9 @@ void vTaskGetRunTimeStats( char * pcWriteBuffer ) PRIVILEGED_FUNCTION; /*lin /** * @cond * task. h - * @code{c}uint32_t ulTaskGetIdleRunTimeCounter( void );@endcode + * @code + * uint32_t ulTaskGetIdleRunTimeCounter( void ); + * @endcode * @endcond * * configGENERATE_RUN_TIME_STATS and configUSE_STATS_FORMATTING_FUNCTIONS @@ -2089,11 +2254,25 @@ void vTaskGetRunTimeStats( char * pcWriteBuffer ) PRIVILEGED_FUNCTION; /*lin uint32_t ulTaskGetIdleRunTimeCounter( void ) PRIVILEGED_FUNCTION; /** - * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this - * function to be available. + * task. h + * @code{c} + * BaseType_t xTaskNotifyIndexed( TaskHandle_t xTaskToNotify, UBaseType_t uxIndexToNotify, uint32_t ulValue, eNotifyAction eAction ); + * BaseType_t xTaskNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction ); + * @endcode + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). + * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for these + * functions to be available. + * + * Sends a direct to task notification to a task, with an optional value and + * action. + * + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2101,28 +2280,46 @@ uint32_t ulTaskGetIdleRunTimeCounter( void ) PRIVILEGED_FUNCTION; * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * - * A notification sent to a task will remain pending until it is cleared by the - * task calling xTaskNotifyWait() or ulTaskNotifyTake(). If the task was - * already in the Blocked state to wait for a notification when the notification - * arrives then the task will automatically be removed from the Blocked state - * (unblocked) and the notification cleared. - * - * A task can use xTaskNotifyWait() to [optionally] block to wait for a - * notification to be pending, or ulTaskNotifyTake() to [optionally] block - * to wait for its notification value to have a non-zero value. The task does + * A task can use xTaskNotifyWaitIndexed() to [optionally] block to wait for a + * notification to be pending, or ulTaskNotifyTakeIndexed() to [optionally] block + * to wait for a notification value to have a non-zero value. The task does * not consume any CPU time while it is in the Blocked state. * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * A notification sent to a task will remain pending until it is cleared by the + * task calling xTaskNotifyWaitIndexed() or ulTaskNotifyTakeIndexed() (or their + * un-indexed equivalents). If the task was already in the Blocked state to + * wait for a notification when the notification arrives then the task will + * automatically be removed from the Blocked state (unblocked) and the + * notification cleared. + * + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotify() is the original API function, and remains backward + * compatible by always operating on the notification value at index 0 in the + * array. Calling xTaskNotify() is equivalent to calling xTaskNotifyIndexed() + * with the uxIndexToNotify parameter set to 0. * * @param xTaskToNotify The handle of the task being notified. The handle to a * task can be returned from the xTaskCreate() API function used to create the * task, and the handle of the currently running task can be obtained by calling * xTaskGetCurrentTaskHandle(). * + * @param uxIndexToNotify The index within the target task's array of + * notification values to which the notification is to be sent. uxIndexToNotify + * must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. xTaskNotify() does + * not have this parameter and always sends notifications to index 0. + * * @param ulValue Data that can be sent with the notification. How the data is * used depends on the value of the eAction parameter. * @@ -2130,54 +2327,100 @@ uint32_t ulTaskGetIdleRunTimeCounter( void ) PRIVILEGED_FUNCTION; * value, if at all. Valid values for eAction are as follows: * * eSetBits - - * The task's notification value is bitwise ORed with ulValue. xTaskNofify() - * always returns pdPASS in this case. + * The target notification value is bitwise ORed with ulValue. + * xTaskNotifyIndexed() always returns pdPASS in this case. * * eIncrement - - * The task's notification value is incremented. ulValue is not used and - * xTaskNotify() always returns pdPASS in this case. + * The target notification value is incremented. ulValue is not used and + * xTaskNotifyIndexed() always returns pdPASS in this case. * * eSetValueWithOverwrite - - * The task's notification value is set to the value of ulValue, even if the - * task being notified had not yet processed the previous notification (the - * task already had a notification pending). xTaskNotify() always returns - * pdPASS in this case. + * The target notification value is set to the value of ulValue, even if the + * task being notified had not yet processed the previous notification at the + * same array index (the task already had a notification pending at that index). + * xTaskNotifyIndexed() always returns pdPASS in this case. * * eSetValueWithoutOverwrite - - * If the task being notified did not already have a notification pending then - * the task's notification value is set to ulValue and xTaskNotify() will - * return pdPASS. If the task being notified already had a notification - * pending then no action is performed and pdFAIL is returned. + * If the task being notified did not already have a notification pending at the + * same array index then the target notification value is set to ulValue and + * xTaskNotifyIndexed() will return pdPASS. If the task being notified already + * had a notification pending at the same array index then no action is + * performed and pdFAIL is returned. * * eNoAction - - * The task receives a notification without its notification value being - * updated. ulValue is not used and xTaskNotify() always returns pdPASS in - * this case. + * The task receives a notification at the specified array index without the + * notification value at that index being updated. ulValue is not used and + * xTaskNotifyIndexed() always returns pdPASS in this case. * - * @param pulPreviousNotificationValue Can be used to pass out the subject - * task's notification value before any bits are modified by the notify - * function. + * pulPreviousNotificationValue - + * Can be used to pass out the subject task's notification value before any + * bits are modified by the notify function. * * @return Dependent on the value of eAction. See the description of the * eAction parameter. * + * \defgroup xTaskNotifyIndexed xTaskNotifyIndexed * \ingroup TaskNotifications */ -BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotificationValue ) PRIVILEGED_FUNCTION; -#define xTaskNotify( xTaskToNotify, ulValue, eAction ) xTaskGenericNotify( ( xTaskToNotify ), ( ulValue ), ( eAction ), NULL ) -#define xTaskNotifyAndQuery( xTaskToNotify, ulValue, eAction, pulPreviousNotifyValue ) xTaskGenericNotify( ( xTaskToNotify ), ( ulValue ), ( eAction ), ( pulPreviousNotifyValue ) ) +BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, + UBaseType_t uxIndexToNotify, + uint32_t ulValue, + eNotifyAction eAction, + uint32_t * pulPreviousNotificationValue ) PRIVILEGED_FUNCTION; +#define xTaskNotify( xTaskToNotify, ulValue, eAction ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( ulValue ), ( eAction ), NULL ) +#define xTaskNotifyIndexed( xTaskToNotify, uxIndexToNotify, ulValue, eAction ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( uxIndexToNotify ), ( ulValue ), ( eAction ), NULL ) /** - * Send task notification from an ISR. + * task. h + * @code{c} + * BaseType_t xTaskNotifyAndQueryIndexed( TaskHandle_t xTaskToNotify, UBaseType_t uxIndexToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotifyValue ); + * BaseType_t xTaskNotifyAndQuery( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotifyValue ); + * @endcode * - * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this - * function to be available. + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * + * xTaskNotifyAndQueryIndexed() performs the same operation as + * xTaskNotifyIndexed() with the addition that it also returns the subject + * task's prior notification value (the notification value at the time the + * function is called rather than when the function returns) in the additional + * pulPreviousNotifyValue parameter. + * + * xTaskNotifyAndQuery() performs the same operation as xTaskNotify() with the + * addition that it also returns the subject task's prior notification value + * (the notification value as it was at the time the function is called, rather + * than when the function returns) in the additional pulPreviousNotifyValue + * parameter. + * + * \defgroup xTaskNotifyAndQueryIndexed xTaskNotifyAndQueryIndexed + * \ingroup TaskNotifications + */ +#define xTaskNotifyAndQuery( xTaskToNotify, ulValue, eAction, pulPreviousNotifyValue ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( ulValue ), ( eAction ), ( pulPreviousNotifyValue ) ) +#define xTaskNotifyAndQueryIndexed( xTaskToNotify, uxIndexToNotify, ulValue, eAction, pulPreviousNotifyValue ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( uxIndexToNotify ), ( ulValue ), ( eAction ), ( pulPreviousNotifyValue ) ) + +/** + * task. h + * @code{c} + * BaseType_t xTaskNotifyIndexedFromISR( TaskHandle_t xTaskToNotify, UBaseType_t uxIndexToNotify, uint32_t ulValue, eNotifyAction eAction, BaseType_t *pxHigherPriorityTaskWoken ); + * BaseType_t xTaskNotifyFromISR( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction, BaseType_t *pxHigherPriorityTaskWoken ); + * @endcode * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. * - * A version of xTaskNotify() that can be used from an interrupt service routine - * (ISR). + * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for these + * functions to be available. + * + * A version of xTaskNotifyIndexed() that can be used from an interrupt service + * routine (ISR). + * + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2185,22 +2428,40 @@ BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNo * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * - * A notification sent to a task will remain pending until it is cleared by the - * task calling xTaskNotifyWait() or ulTaskNotifyTake(). If the task was - * already in the Blocked state to wait for a notification when the notification - * arrives then the task will automatically be removed from the Blocked state - * (unblocked) and the notification cleared. - * - * A task can use xTaskNotifyWait() to [optionally] block to wait for a - * notification to be pending, or ulTaskNotifyTake() to [optionally] block - * to wait for its notification value to have a non-zero value. The task does + * A task can use xTaskNotifyWaitIndexed() to [optionally] block to wait for a + * notification to be pending, or ulTaskNotifyTakeIndexed() to [optionally] block + * to wait for a notification value to have a non-zero value. The task does * not consume any CPU time while it is in the Blocked state. * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * A notification sent to a task will remain pending until it is cleared by the + * task calling xTaskNotifyWaitIndexed() or ulTaskNotifyTakeIndexed() (or their + * un-indexed equivalents). If the task was already in the Blocked state to + * wait for a notification when the notification arrives then the task will + * automatically be removed from the Blocked state (unblocked) and the + * notification cleared. + * + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotifyFromISR() is the original API function, and remains + * backward compatible by always operating on the notification value at index 0 + * within the array. Calling xTaskNotifyFromISR() is equivalent to calling + * xTaskNotifyIndexedFromISR() with the uxIndexToNotify parameter set to 0. + * + * @param uxIndexToNotify The index within the target task's array of + * notification values to which the notification is to be sent. uxIndexToNotify + * must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. xTaskNotifyFromISR() + * does not have this parameter and always sends notifications to index 0. * * @param xTaskToNotify The handle of the task being notified. The handle to a * task can be returned from the xTaskCreate() API function used to create the @@ -2214,7 +2475,7 @@ BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNo * value, if at all. Valid values for eAction are as follows: * * eSetBits - - * The task's notification value is bitwise ORed with ulValue. xTaskNofify() + * The task's notification value is bitwise ORed with ulValue. xTaskNotify() * always returns pdPASS in this case. * * eIncrement - @@ -2238,9 +2499,6 @@ BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNo * updated. ulValue is not used and xTaskNotify() always returns pdPASS in * this case. * - * @param pulPreviousNotificationValue Can be used to pass out the subject task's - * notification value before any bits are modified by the notify function. - * * @param pxHigherPriorityTaskWoken xTaskNotifyFromISR() will set * *pxHigherPriorityTaskWoken to pdTRUE if sending the notification caused the * task to which the notification was sent to leave the Blocked state, and the @@ -2253,20 +2511,70 @@ BaseType_t xTaskGenericNotify( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNo * @return Dependent on the value of eAction. See the description of the * eAction parameter. * + * \defgroup xTaskNotifyIndexedFromISR xTaskNotifyIndexedFromISR * \ingroup TaskNotifications */ -BaseType_t xTaskGenericNotifyFromISR( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotificationValue, BaseType_t *pxHigherPriorityTaskWoken ) PRIVILEGED_FUNCTION; -#define xTaskNotifyFromISR( xTaskToNotify, ulValue, eAction, pxHigherPriorityTaskWoken ) xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( ulValue ), ( eAction ), NULL, ( pxHigherPriorityTaskWoken ) ) -#define xTaskNotifyAndQueryFromISR( xTaskToNotify, ulValue, eAction, pulPreviousNotificationValue, pxHigherPriorityTaskWoken ) xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( ulValue ), ( eAction ), ( pulPreviousNotificationValue ), ( pxHigherPriorityTaskWoken ) ) +BaseType_t xTaskGenericNotifyFromISR( TaskHandle_t xTaskToNotify, + UBaseType_t uxIndexToNotify, + uint32_t ulValue, + eNotifyAction eAction, + uint32_t * pulPreviousNotificationValue, + BaseType_t * pxHigherPriorityTaskWoken ) PRIVILEGED_FUNCTION; +#define xTaskNotifyFromISR( xTaskToNotify, ulValue, eAction, pxHigherPriorityTaskWoken ) \ + xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( ulValue ), ( eAction ), NULL, ( pxHigherPriorityTaskWoken ) ) +#define xTaskNotifyIndexedFromISR( xTaskToNotify, uxIndexToNotify, ulValue, eAction, pxHigherPriorityTaskWoken ) \ + xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( uxIndexToNotify ), ( ulValue ), ( eAction ), NULL, ( pxHigherPriorityTaskWoken ) ) /** - * Wait for task notification + * task. h + * @code{c} + * BaseType_t xTaskNotifyAndQueryIndexedFromISR( TaskHandle_t xTaskToNotify, UBaseType_t uxIndexToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotificationValue, BaseType_t *pxHigherPriorityTaskWoken ); + * BaseType_t xTaskNotifyAndQueryFromISR( TaskHandle_t xTaskToNotify, uint32_t ulValue, eNotifyAction eAction, uint32_t *pulPreviousNotificationValue, BaseType_t *pxHigherPriorityTaskWoken ); + * @endcode + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * + * xTaskNotifyAndQueryIndexedFromISR() performs the same operation as + * xTaskNotifyIndexedFromISR() with the addition that it also returns the + * subject task's prior notification value (the notification value at the time + * the function is called rather than at the time the function returns) in the + * additional pulPreviousNotifyValue parameter. + * + * xTaskNotifyAndQueryFromISR() performs the same operation as + * xTaskNotifyFromISR() with the addition that it also returns the subject + * task's prior notification value (the notification value at the time the + * function is called rather than at the time the function returns) in the + * additional pulPreviousNotifyValue parameter. + * + * \defgroup xTaskNotifyAndQueryIndexedFromISR xTaskNotifyAndQueryIndexedFromISR + * \ingroup TaskNotifications + */ +#define xTaskNotifyAndQueryIndexedFromISR( xTaskToNotify, uxIndexToNotify, ulValue, eAction, pulPreviousNotificationValue, pxHigherPriorityTaskWoken ) \ + xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( uxIndexToNotify ), ( ulValue ), ( eAction ), ( pulPreviousNotificationValue ), ( pxHigherPriorityTaskWoken ) ) +#define xTaskNotifyAndQueryFromISR( xTaskToNotify, ulValue, eAction, pulPreviousNotificationValue, pxHigherPriorityTaskWoken ) \ + xTaskGenericNotifyFromISR( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( ulValue ), ( eAction ), ( pulPreviousNotificationValue ), ( pxHigherPriorityTaskWoken ) ) + +/** + * task. h + * @code{c} + * BaseType_t xTaskNotifyWaitIndexed( UBaseType_t uxIndexToWaitOn, uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClearOnExit, uint32_t *pulNotificationValue, TickType_t xTicksToWait ); + * + * BaseType_t xTaskNotifyWait( uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClearOnExit, uint32_t *pulNotificationValue, TickType_t xTicksToWait ); + * @endcode + * + * Waits for a direct to task notification to be pending at a given index within + * an array of direct to task notifications. + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. * * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this * function to be available. * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2274,22 +2582,41 @@ BaseType_t xTaskGenericNotifyFromISR( TaskHandle_t xTaskToNotify, uint32_t ulVal * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * * A notification sent to a task will remain pending until it is cleared by the - * task calling xTaskNotifyWait() or ulTaskNotifyTake(). If the task was - * already in the Blocked state to wait for a notification when the notification - * arrives then the task will automatically be removed from the Blocked state - * (unblocked) and the notification cleared. - * - * A task can use xTaskNotifyWait() to [optionally] block to wait for a - * notification to be pending, or ulTaskNotifyTake() to [optionally] block - * to wait for its notification value to have a non-zero value. The task does + * task calling xTaskNotifyWaitIndexed() or ulTaskNotifyTakeIndexed() (or their + * un-indexed equivalents). If the task was already in the Blocked state to + * wait for a notification when the notification arrives then the task will + * automatically be removed from the Blocked state (unblocked) and the + * notification cleared. + * + * A task can use xTaskNotifyWaitIndexed() to [optionally] block to wait for a + * notification to be pending, or ulTaskNotifyTakeIndexed() to [optionally] block + * to wait for a notification value to have a non-zero value. The task does * not consume any CPU time while it is in the Blocked state. * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotifyWait() is the original API function, and remains backward + * compatible by always operating on the notification value at index 0 in the + * array. Calling xTaskNotifyWait() is equivalent to calling + * xTaskNotifyWaitIndexed() with the uxIndexToWaitOn parameter set to 0. + * + * @param uxIndexToWaitOn The index within the calling task's array of + * notification values on which the calling task will wait for a notification to + * be received. uxIndexToWaitOn must be less than + * configTASK_NOTIFICATION_ARRAY_ENTRIES. xTaskNotifyWait() does + * not have this parameter and always waits for notifications on index 0. * * @param ulBitsToClearOnEntry Bits that are set in ulBitsToClearOnEntry value * will be cleared in the calling task's notification value before the task @@ -2328,18 +2655,39 @@ BaseType_t xTaskGenericNotifyFromISR( TaskHandle_t xTaskToNotify, uint32_t ulVal * already pending when xTaskNotifyWait was called) then pdPASS is * returned. Otherwise pdFAIL is returned. * + * \defgroup xTaskNotifyWaitIndexed xTaskNotifyWaitIndexed * \ingroup TaskNotifications */ -BaseType_t xTaskNotifyWait( uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClearOnExit, uint32_t *pulNotificationValue, TickType_t xTicksToWait ) PRIVILEGED_FUNCTION; +BaseType_t xTaskGenericNotifyWait( UBaseType_t uxIndexToWaitOn, + uint32_t ulBitsToClearOnEntry, + uint32_t ulBitsToClearOnExit, + uint32_t * pulNotificationValue, + TickType_t xTicksToWait ) PRIVILEGED_FUNCTION; +#define xTaskNotifyWait( ulBitsToClearOnEntry, ulBitsToClearOnExit, pulNotificationValue, xTicksToWait ) \ + xTaskGenericNotifyWait( tskDEFAULT_INDEX_TO_NOTIFY, ( ulBitsToClearOnEntry ), ( ulBitsToClearOnExit ), ( pulNotificationValue ), ( xTicksToWait ) ) +#define xTaskNotifyWaitIndexed( uxIndexToWaitOn, ulBitsToClearOnEntry, ulBitsToClearOnExit, pulNotificationValue, xTicksToWait ) \ + xTaskGenericNotifyWait( ( uxIndexToWaitOn ), ( ulBitsToClearOnEntry ), ( ulBitsToClearOnExit ), ( pulNotificationValue ), ( xTicksToWait ) ) /** - * Simplified macro for sending task notification. + * task. h + * @code{c} + * BaseType_t xTaskNotifyGiveIndexed( TaskHandle_t xTaskToNotify, UBaseType_t uxIndexToNotify ); + * BaseType_t xTaskNotifyGive( TaskHandle_t xTaskToNotify ); + * @endcode * - * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this macro - * to be available. + * Sends a direct to task notification to a particular index in the target + * task's notification array in a manner similar to giving a counting semaphore. + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for more details. * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). + * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for these + * macros to be available. + * + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2347,46 +2695,76 @@ BaseType_t xTaskNotifyWait( uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClea * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * - * xTaskNotifyGive() is a helper macro intended for use when task notifications - * are used as light weight and faster binary or counting semaphore equivalents. - * Actual FreeRTOS semaphores are given using the xSemaphoreGive() API function, - * the equivalent action that instead uses a task notification is - * xTaskNotifyGive(). + * xTaskNotifyGiveIndexed() is a helper macro intended for use when task + * notifications are used as light weight and faster binary or counting + * semaphore equivalents. Actual FreeRTOS semaphores are given using the + * xSemaphoreGive() API function, the equivalent action that instead uses a task + * notification is xTaskNotifyGiveIndexed(). * * When task notifications are being used as a binary or counting semaphore * equivalent then the task being notified should wait for the notification - * using the ulTaskNotificationTake() API function rather than the - * xTaskNotifyWait() API function. - * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for more details. + * using the ulTaskNotificationTakeIndexed() API function rather than the + * xTaskNotifyWaitIndexed() API function. + * + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotifyGive() is the original API function, and remains backward + * compatible by always operating on the notification value at index 0 in the + * array. Calling xTaskNotifyGive() is equivalent to calling + * xTaskNotifyGiveIndexed() with the uxIndexToNotify parameter set to 0. * * @param xTaskToNotify The handle of the task being notified. The handle to a * task can be returned from the xTaskCreate() API function used to create the * task, and the handle of the currently running task can be obtained by calling * xTaskGetCurrentTaskHandle(). * + * @param uxIndexToNotify The index within the target task's array of + * notification values to which the notification is to be sent. uxIndexToNotify + * must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. xTaskNotifyGive() + * does not have this parameter and always sends notifications to index 0. + * * @return xTaskNotifyGive() is a macro that calls xTaskNotify() with the * eAction parameter set to eIncrement - so pdPASS is always returned. * + * \defgroup xTaskNotifyGiveIndexed xTaskNotifyGiveIndexed * \ingroup TaskNotifications */ -#define xTaskNotifyGive( xTaskToNotify ) xTaskGenericNotify( ( xTaskToNotify ), ( 0 ), eIncrement, NULL ) +#define xTaskNotifyGive( xTaskToNotify ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( 0 ), eIncrement, NULL ) +#define xTaskNotifyGiveIndexed( xTaskToNotify, uxIndexToNotify ) \ + xTaskGenericNotify( ( xTaskToNotify ), ( uxIndexToNotify ), ( 0 ), eIncrement, NULL ) /** - * Simplified macro for sending task notification from ISR. + * task. h + * @code{c} + * void vTaskNotifyGiveIndexedFromISR( TaskHandle_t xTaskHandle, UBaseType_t uxIndexToNotify, BaseType_t *pxHigherPriorityTaskWoken ); + * void vTaskNotifyGiveFromISR( TaskHandle_t xTaskHandle, BaseType_t *pxHigherPriorityTaskWoken ); + * @endcode + * + * A version of xTaskNotifyGiveIndexed() that can be called from an interrupt + * service routine (ISR). + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for more details. * * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this macro * to be available. * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). - * - * A version of xTaskNotifyGive() that can be called from an interrupt service - * routine (ISR). + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2394,28 +2772,46 @@ BaseType_t xTaskNotifyWait( uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClea * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * - * vTaskNotifyGiveFromISR() is intended for use when task notifications are - * used as light weight and faster binary or counting semaphore equivalents. + * vTaskNotifyGiveIndexedFromISR() is intended for use when task notifications + * are used as light weight and faster binary or counting semaphore equivalents. * Actual FreeRTOS semaphores are given from an ISR using the * xSemaphoreGiveFromISR() API function, the equivalent action that instead uses - * a task notification is vTaskNotifyGiveFromISR(). + * a task notification is vTaskNotifyGiveIndexedFromISR(). * * When task notifications are being used as a binary or counting semaphore * equivalent then the task being notified should wait for the notification - * using the ulTaskNotificationTake() API function rather than the - * xTaskNotifyWait() API function. - * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for more details. + * using the ulTaskNotificationTakeIndexed() API function rather than the + * xTaskNotifyWaitIndexed() API function. + * + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotifyFromISR() is the original API function, and remains + * backward compatible by always operating on the notification value at index 0 + * within the array. Calling xTaskNotifyGiveFromISR() is equivalent to calling + * xTaskNotifyGiveIndexedFromISR() with the uxIndexToNotify parameter set to 0. * * @param xTaskToNotify The handle of the task being notified. The handle to a * task can be returned from the xTaskCreate() API function used to create the * task, and the handle of the currently running task can be obtained by calling * xTaskGetCurrentTaskHandle(). * + * @param uxIndexToNotify The index within the target task's array of + * notification values to which the notification is to be sent. uxIndexToNotify + * must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. + * xTaskNotifyGiveFromISR() does not have this parameter and always sends + * notifications to index 0. + * * @param pxHigherPriorityTaskWoken vTaskNotifyGiveFromISR() will set * *pxHigherPriorityTaskWoken to pdTRUE if sending the notification caused the * task to which the notification was sent to leave the Blocked state, and the @@ -2425,18 +2821,38 @@ BaseType_t xTaskNotifyWait( uint32_t ulBitsToClearOnEntry, uint32_t ulBitsToClea * requested from an ISR is dependent on the port - see the documentation page * for the port in use. * + * \defgroup vTaskNotifyGiveIndexedFromISR vTaskNotifyGiveIndexedFromISR * \ingroup TaskNotifications */ -void vTaskNotifyGiveFromISR( TaskHandle_t xTaskToNotify, BaseType_t *pxHigherPriorityTaskWoken ) PRIVILEGED_FUNCTION; +void vTaskGenericNotifyGiveFromISR( TaskHandle_t xTaskToNotify, + UBaseType_t uxIndexToNotify, + BaseType_t * pxHigherPriorityTaskWoken ) PRIVILEGED_FUNCTION; +#define vTaskNotifyGiveFromISR( xTaskToNotify, pxHigherPriorityTaskWoken ) \ + vTaskGenericNotifyGiveFromISR( ( xTaskToNotify ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( pxHigherPriorityTaskWoken ) ); +#define vTaskNotifyGiveIndexedFromISR( xTaskToNotify, uxIndexToNotify, pxHigherPriorityTaskWoken ) \ + vTaskGenericNotifyGiveFromISR( ( xTaskToNotify ), ( uxIndexToNotify ), ( pxHigherPriorityTaskWoken ) ); /** - * Simplified macro for receiving task notification. + * task. h + * @code{c} + * uint32_t ulTaskNotifyTakeIndexed( UBaseType_t uxIndexToWaitOn, BaseType_t xClearCountOnExit, TickType_t xTicksToWait ); + * + * uint32_t ulTaskNotifyTake( BaseType_t xClearCountOnExit, TickType_t xTicksToWait ); + * @endcode + * + * Waits for a direct to task notification on a particular index in the calling + * task's notification array in a manner similar to taking a counting semaphore. + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. * * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for this * function to be available. * - * When configUSE_TASK_NOTIFICATIONS is set to one each task has its own private - * "notification value", which is a 32-bit unsigned integer (uint32_t). + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. * * Events can be sent to a task using an intermediary object. Examples of such * objects are queues, semaphores, mutexes and event groups. Task notifications @@ -2444,35 +2860,54 @@ void vTaskNotifyGiveFromISR( TaskHandle_t xTaskToNotify, BaseType_t *pxHigherPri * an intermediary object. * * A notification sent to a task can optionally perform an action, such as - * update, overwrite or increment the task's notification value. In that way - * task notifications can be used to send data to a task, or be used as light - * weight and fast binary or counting semaphores. + * update, overwrite or increment one of the task's notification values. In + * that way task notifications can be used to send data to a task, or be used as + * light weight and fast binary or counting semaphores. * - * ulTaskNotifyTake() is intended for use when a task notification is used as a - * faster and lighter weight binary or counting semaphore alternative. Actual - * FreeRTOS semaphores are taken using the xSemaphoreTake() API function, the - * equivalent action that instead uses a task notification is - * ulTaskNotifyTake(). + * ulTaskNotifyTakeIndexed() is intended for use when a task notification is + * used as a faster and lighter weight binary or counting semaphore alternative. + * Actual FreeRTOS semaphores are taken using the xSemaphoreTake() API function, + * the equivalent action that instead uses a task notification is + * ulTaskNotifyTakeIndexed(). * * When a task is using its notification value as a binary or counting semaphore - * other tasks should send notifications to it using the xTaskNotifyGive() - * macro, or xTaskNotify() function with the eAction parameter set to + * other tasks should send notifications to it using the xTaskNotifyGiveIndexed() + * macro, or xTaskNotifyIndex() function with the eAction parameter set to * eIncrement. * - * ulTaskNotifyTake() can either clear the task's notification value to - * zero on exit, in which case the notification value acts like a binary - * semaphore, or decrement the task's notification value on exit, in which case - * the notification value acts like a counting semaphore. + * ulTaskNotifyTakeIndexed() can either clear the task's notification value at + * the array index specified by the uxIndexToWaitOn parameter to zero on exit, + * in which case the notification value acts like a binary semaphore, or + * decrement the notification value on exit, in which case the notification + * value acts like a counting semaphore. * - * A task can use ulTaskNotifyTake() to [optionally] block to wait for a + * A task can use ulTaskNotifyTakeIndexed() to [optionally] block to wait for * the task's notification value to be non-zero. The task does not consume any * CPU time while it is in the Blocked state. * - * Where as xTaskNotifyWait() will return when a notification is pending, - * ulTaskNotifyTake() will return when the task's notification value is + * Where as xTaskNotifyWaitIndexed() will return when a notification is pending, + * ulTaskNotifyTakeIndexed() will return when the task's notification value is * not zero. * - * See http://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * **NOTE** Each notification within the array operates independently - a task + * can only block on one notification within the array at a time and will not be + * unblocked by a notification sent to any other array index. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. ulTaskNotifyTake() is the original API function, and remains backward + * compatible by always operating on the notification value at index 0 in the + * array. Calling ulTaskNotifyTake() is equivalent to calling + * ulTaskNotifyTakeIndexed() with the uxIndexToWaitOn parameter set to 0. + * + * @param uxIndexToWaitOn The index within the calling task's array of + * notification values on which the calling task will wait for a notification to + * be non-zero. uxIndexToWaitOn must be less than + * configTASK_NOTIFICATION_ARRAY_ENTRIES. xTaskNotifyTake() does + * not have this parameter and always waits for notifications on index 0. * * @param xClearCountOnExit if xClearCountOnExit is pdFALSE then the task's * notification value is decremented when the function exits. In this way the @@ -2492,23 +2927,289 @@ void vTaskNotifyGiveFromISR( TaskHandle_t xTaskToNotify, BaseType_t *pxHigherPri * @return The task's notification count before it is either cleared to zero or * decremented (see the xClearCountOnExit parameter). * + * \defgroup ulTaskNotifyTakeIndexed ulTaskNotifyTakeIndexed * \ingroup TaskNotifications */ -uint32_t ulTaskNotifyTake( BaseType_t xClearCountOnExit, TickType_t xTicksToWait ) PRIVILEGED_FUNCTION; +uint32_t ulTaskGenericNotifyTake( UBaseType_t uxIndexToWaitOn, + BaseType_t xClearCountOnExit, + TickType_t xTicksToWait ) PRIVILEGED_FUNCTION; +#define ulTaskNotifyTake( xClearCountOnExit, xTicksToWait ) \ + ulTaskGenericNotifyTake( ( tskDEFAULT_INDEX_TO_NOTIFY ), ( xClearCountOnExit ), ( xTicksToWait ) ) +#define ulTaskNotifyTakeIndexed( uxIndexToWaitOn, xClearCountOnExit, xTicksToWait ) \ + ulTaskGenericNotifyTake( ( uxIndexToWaitOn ), ( xClearCountOnExit ), ( xTicksToWait ) ) /** + * task. h + * @code{c} + * BaseType_t xTaskNotifyStateClearIndexed( TaskHandle_t xTask, UBaseType_t uxIndexToCLear ); * - * If the notification state of the task referenced by the handle xTask is - * eNotified, then set the task's notification state to eNotWaitingNotification. - * The task's notification value is not altered. Set xTask to NULL to clear the - * notification state of the calling task. + * BaseType_t xTaskNotifyStateClear( TaskHandle_t xTask ); + * @endcode + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * + * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for these + * functions to be available. + * + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. + * + * If a notification is sent to an index within the array of notifications then + * the notification at that index is said to be 'pending' until it is read or + * explicitly cleared by the receiving task. xTaskNotifyStateClearIndexed() + * is the function that clears a pending notification without reading the + * notification value. The notification value at the same array index is not + * altered. Set xTask to NULL to clear the notification state of the calling + * task. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. xTaskNotifyStateClear() is the original API function, and remains + * backward compatible by always operating on the notification value at index 0 + * within the array. Calling xTaskNotifyStateClear() is equivalent to calling + * xTaskNotifyStateClearIndexed() with the uxIndexToNotify parameter set to 0. + * + * @param xTask The handle of the RTOS task that will have a notification state + * cleared. Set xTask to NULL to clear a notification state in the calling + * task. To obtain a task's handle create the task using xTaskCreate() and + * make use of the pxCreatedTask parameter, or create the task using + * xTaskCreateStatic() and store the returned value, or use the task's name in + * a call to xTaskGetHandle(). + * + * @param uxIndexToClear The index within the target task's array of + * notification values to act upon. For example, setting uxIndexToClear to 1 + * will clear the state of the notification at index 1 within the array. + * uxIndexToClear must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. + * ulTaskNotifyStateClear() does not have this parameter and always acts on the + * notification at index 0. * * @return pdTRUE if the task's notification state was set to * eNotWaitingNotification, otherwise pdFALSE. * + * \defgroup xTaskNotifyStateClearIndexed xTaskNotifyStateClearIndexed * \ingroup TaskNotifications */ -BaseType_t xTaskNotifyStateClear( TaskHandle_t xTask ); +BaseType_t xTaskGenericNotifyStateClear( TaskHandle_t xTask, + UBaseType_t uxIndexToClear ) PRIVILEGED_FUNCTION; +#define xTaskNotifyStateClear( xTask ) \ + xTaskGenericNotifyStateClear( ( xTask ), ( tskDEFAULT_INDEX_TO_NOTIFY ) ) +#define xTaskNotifyStateClearIndexed( xTask, uxIndexToClear ) \ + xTaskGenericNotifyStateClear( ( xTask ), ( uxIndexToClear ) ) + +/** + * task. h + * @code{c} + * uint32_t ulTaskNotifyValueClearIndexed( TaskHandle_t xTask, UBaseType_t uxIndexToClear, uint32_t ulBitsToClear ); + * + * uint32_t ulTaskNotifyValueClear( TaskHandle_t xTask, uint32_t ulBitsToClear ); + * @endcode + * + * See https://www.FreeRTOS.org/RTOS-task-notifications.html for details. + * + * configUSE_TASK_NOTIFICATIONS must be undefined or defined as 1 for these + * functions to be available. + * + * Each task has a private array of "notification values" (or 'notifications'), + * each of which is a 32-bit unsigned integer (uint32_t). The constant + * configTASK_NOTIFICATION_ARRAY_ENTRIES sets the number of indexes in the + * array, and (for backward compatibility) defaults to 1 if left undefined. + * Prior to FreeRTOS V10.4.0 there was only one notification value per task. + * + * ulTaskNotifyValueClearIndexed() clears the bits specified by the + * ulBitsToClear bit mask in the notification value at array index uxIndexToClear + * of the task referenced by xTask. + * + * Backward compatibility information: + * Prior to FreeRTOS V10.4.0 each task had a single "notification value", and + * all task notification API functions operated on that value. Replacing the + * single notification value with an array of notification values necessitated a + * new set of API functions that could address specific notifications within the + * array. ulTaskNotifyValueClear() is the original API function, and remains + * backward compatible by always operating on the notification value at index 0 + * within the array. Calling ulTaskNotifyValueClear() is equivalent to calling + * ulTaskNotifyValueClearIndexed() with the uxIndexToClear parameter set to 0. + * + * @param xTask The handle of the RTOS task that will have bits in one of its + * notification values cleared. Set xTask to NULL to clear bits in a + * notification value of the calling task. To obtain a task's handle create the + * task using xTaskCreate() and make use of the pxCreatedTask parameter, or + * create the task using xTaskCreateStatic() and store the returned value, or + * use the task's name in a call to xTaskGetHandle(). + * + * @param uxIndexToClear The index within the target task's array of + * notification values in which to clear the bits. uxIndexToClear + * must be less than configTASK_NOTIFICATION_ARRAY_ENTRIES. + * ulTaskNotifyValueClear() does not have this parameter and always clears bits + * in the notification value at index 0. + * + * @param ulBitsToClear Bit mask of the bits to clear in the notification value of + * xTask. Set a bit to 1 to clear the corresponding bits in the task's notification + * value. Set ulBitsToClear to 0xffffffff (UINT_MAX on 32-bit architectures) to clear + * the notification value to 0. Set ulBitsToClear to 0 to query the task's + * notification value without clearing any bits. + * + * + * @return The value of the target task's notification value before the bits + * specified by ulBitsToClear were cleared. + * \defgroup ulTaskNotifyValueClear ulTaskNotifyValueClear + * \ingroup TaskNotifications + */ +uint32_t ulTaskGenericNotifyValueClear( TaskHandle_t xTask, + UBaseType_t uxIndexToClear, + uint32_t ulBitsToClear ) PRIVILEGED_FUNCTION; +#define ulTaskNotifyValueClear( xTask, ulBitsToClear ) \ + ulTaskGenericNotifyValueClear( ( xTask ), ( tskDEFAULT_INDEX_TO_NOTIFY ), ( ulBitsToClear ) ) +#define ulTaskNotifyValueClearIndexed( xTask, uxIndexToClear, ulBitsToClear ) \ + ulTaskGenericNotifyValueClear( ( xTask ), ( uxIndexToClear ), ( ulBitsToClear ) ) + +/** + * @cond + * task.h + * @code{c} + * void vTaskSetTimeOutState( TimeOut_t * const pxTimeOut ); + * @endcode + * @endcond + * + * Capture the current time for future use with xTaskCheckForTimeOut(). + * + * @param pxTimeOut Pointer to a timeout object into which the current time + * is to be captured. The captured time includes the tick count and the number + * of times the tick count has overflowed since the system first booted. + * \defgroup vTaskSetTimeOutState vTaskSetTimeOutState + * @cond + * \ingroup TaskCtrl + * @endcond + */ +void vTaskSetTimeOutState( TimeOut_t * const pxTimeOut ) PRIVILEGED_FUNCTION; + +/** + * @cond + * task.h + * @code + * BaseType_t xTaskCheckForTimeOut( TimeOut_t * const pxTimeOut, TickType_t * const pxTicksToWait ); + * @endcode + * @endcond + * + * Determines if pxTicksToWait ticks has passed since a time was captured + * using a call to vTaskSetTimeOutState(). The captured time includes the tick + * count and the number of times the tick count has overflowed. + * + * @param pxTimeOut The time status as captured previously using + * vTaskSetTimeOutState. If the timeout has not yet occurred, it is updated + * to reflect the current time status. + * @param pxTicksToWait The number of ticks to check for timeout i.e. if + * pxTicksToWait ticks have passed since pxTimeOut was last updated (either by + * vTaskSetTimeOutState() or xTaskCheckForTimeOut()), the timeout has occurred. + * If the timeout has not occurred, pxTicksToWait is updated to reflect the + * number of remaining ticks. + * + * @return If timeout has occurred, pdTRUE is returned. Otherwise pdFALSE is + * returned and pxTicksToWait is updated to reflect the number of remaining + * ticks. + * + * @see https://www.FreeRTOS.org/xTaskCheckForTimeOut.html + * + * Example Usage: + * @code + * // Driver library function used to receive uxWantedBytes from an Rx buffer + * // that is filled by a UART interrupt. If there are not enough bytes in the + * // Rx buffer then the task enters the Blocked state until it is notified that + * // more data has been placed into the buffer. If there is still not enough + * // data then the task re-enters the Blocked state, and xTaskCheckForTimeOut() + * // is used to re-calculate the Block time to ensure the total amount of time + * // spent in the Blocked state does not exceed MAX_TIME_TO_WAIT. This + * // continues until either the buffer contains at least uxWantedBytes bytes, + * // or the total amount of time spent in the Blocked state reaches + * // MAX_TIME_TO_WAIT – at which point the task reads however many bytes are + * // available up to a maximum of uxWantedBytes. + * + * size_t xUART_Receive( uint8_t *pucBuffer, size_t uxWantedBytes ) + * { + * size_t uxReceived = 0; + * TickType_t xTicksToWait = MAX_TIME_TO_WAIT; + * TimeOut_t xTimeOut; + * + * // Initialize xTimeOut. This records the time at which this function + * // was entered. + * vTaskSetTimeOutState( &xTimeOut ); + * + * // Loop until the buffer contains the wanted number of bytes, or a + * // timeout occurs. + * while( UART_bytes_in_rx_buffer( pxUARTInstance ) < uxWantedBytes ) + * { + * // The buffer didn't contain enough data so this task is going to + * // enter the Blocked state. Adjusting xTicksToWait to account for + * // any time that has been spent in the Blocked state within this + * // function so far to ensure the total amount of time spent in the + * // Blocked state does not exceed MAX_TIME_TO_WAIT. + * if( xTaskCheckForTimeOut( &xTimeOut, &xTicksToWait ) != pdFALSE ) + * { + * //Timed out before the wanted number of bytes were available, + * // exit the loop. + * break; + * } + * + * // Wait for a maximum of xTicksToWait ticks to be notified that the + * // receive interrupt has placed more data into the buffer. + * ulTaskNotifyTake( pdTRUE, xTicksToWait ); + * } + * + * // Attempt to read uxWantedBytes from the receive buffer into pucBuffer. + * // The actual number of bytes read (which might be less than + * // uxWantedBytes) is returned. + * uxReceived = UART_read_from_receive_buffer( pxUARTInstance, + * pucBuffer, + * uxWantedBytes ); + * + * return uxReceived; + * } + * @endcode + * @cond + * \defgroup xTaskCheckForTimeOut xTaskCheckForTimeOut + * @endcond + * \ingroup TaskCtrl + */ +BaseType_t xTaskCheckForTimeOut( TimeOut_t * const pxTimeOut, + TickType_t * const pxTicksToWait ) PRIVILEGED_FUNCTION; + +/** + * @cond + * task.h + * @code{c} + * BaseType_t xTaskCatchUpTicks( TickType_t xTicksToCatchUp ); + * @endcode + * @endcond + * + * This function corrects the tick count value after the application code has held + * interrupts disabled for an extended period resulting in tick interrupts having + * been missed. + * + * This function is similar to vTaskStepTick(), however, unlike + * vTaskStepTick(), xTaskCatchUpTicks() may move the tick count forward past a + * time at which a task should be removed from the blocked state. That means + * tasks may have to be removed from the blocked state as the tick count is + * moved. + * + * @param xTicksToCatchUp The number of tick interrupts that have been missed due to + * interrupts being disabled. Its value is not computed automatically, so must be + * computed by the application writer. + * + * @return pdTRUE if moving the tick count forward resulted in a task leaving the + * blocked state and a context switch being performed. Otherwise pdFALSE. + * + * \defgroup xTaskCatchUpTicks xTaskCatchUpTicks + * @cond + * \ingroup TaskCtrl + * @endcond + */ +BaseType_t xTaskCatchUpTicks( TickType_t xTicksToCatchUp ) PRIVILEGED_FUNCTION; + /*----------------------------------------------------------- * SCHEDULER INTERNALS AVAILABLE FOR PORTING PURPOSES @@ -2535,7 +3236,6 @@ TaskHandle_t xTaskGetCurrentTaskHandleForCPU( BaseType_t cpuid ); */ TaskHandle_t xTaskGetIdleTaskHandleForCPU( UBaseType_t cpuid ); - /* * Get the current core affinity of a task */ @@ -2575,7 +3275,7 @@ BaseType_t xTaskIncrementTick( void ) PRIVILEGED_FUNCTION; * xItemValue value, and inserts the list item at the end of the list. * * The 'ordered' version uses the existing event list item value (which is the - * owning tasks priority) to insert the list item into the event list is task + * owning task's priority) to insert the list item into the event list in task * priority order. * * @param pxEventList The list containing tasks that are blocked waiting @@ -2585,7 +3285,7 @@ BaseType_t xTaskIncrementTick( void ) PRIVILEGED_FUNCTION; * event list is not ordered by task priority. * * @param xTicksToWait The maximum amount of time that the task should wait - * for the event to occur. This is specified in kernel ticks,the constant + * for the event to occur. This is specified in kernel ticks, the constant * portTICK_PERIOD_MS can be used to convert kernel ticks into a real time * period. */ @@ -2646,7 +3346,7 @@ BaseType_t xTaskRemoveFromUnorderedEventList( ListItem_t * pxEventListItem, * Sets the pointer to the current TCB to the TCB of the highest priority task * that is ready to run. */ -void vTaskSwitchContext( void ) PRIVILEGED_FUNCTION; +portDONT_DISCARD void vTaskSwitchContext( void ) PRIVILEGED_FUNCTION; /* * THESE FUNCTIONS MUST NOT BE USED FROM APPLICATION CODE. THEY ARE USED BY @@ -2659,17 +3359,6 @@ TickType_t uxTaskResetEventItemValue( void ) PRIVILEGED_FUNCTION; */ TaskHandle_t xTaskGetCurrentTaskHandle( void ) PRIVILEGED_FUNCTION; -/* - * Capture the current time status for future reference. - */ -void vTaskSetTimeOutState( TimeOut_t * const pxTimeOut ) PRIVILEGED_FUNCTION; - -/* - * Compare the time status now with that previously captured to see if the - * timeout has expired. - */ -BaseType_t xTaskCheckForTimeOut( TimeOut_t * const pxTimeOut, TickType_t * const pxTicksToWait ) PRIVILEGED_FUNCTION; - /* * Shortcut used by the queue implementation to prevent unnecessary call to * taskYIELD(); @@ -2732,19 +3421,6 @@ void vTaskSetTaskNumber( TaskHandle_t xTask, */ void vTaskStepTick( const TickType_t xTicksToJump ) PRIVILEGED_FUNCTION; -/* Correct the tick count value after the application code has held -interrupts disabled for an extended period. xTicksToCatchUp is the number -of tick interrupts that have been missed due to interrupts being disabled. -Its value is not computed automatically, so must be computed by the -application writer. - -This function is similar to vTaskStepTick(), however, unlike -vTaskStepTick(), xTaskCatchUpTicks() may move the tick count forward past a -time at which a task should be removed from the blocked state. That means -tasks may have to be removed from the blocked state as the tick count is -moved. */ -BaseType_t xTaskCatchUpTicks( TickType_t xTicksToCatchUp ) PRIVILEGED_FUNCTION; - /* * Only available when configUSE_TICKLESS_IDLE is set to 1. * Provided for use within portSUPPRESS_TICKS_AND_SLEEP() to allow the port diff --git a/tools/sdk/esp32c3/include/freertos/include/freertos/timers.h b/tools/sdk/esp32c3/include/freertos/include/freertos/timers.h index 21cd63f80c7..a8bc4f38c78 100644 --- a/tools/sdk/esp32c3/include/freertos/include/freertos/timers.h +++ b/tools/sdk/esp32c3/include/freertos/include/freertos/timers.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2020 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/FreeRTOSConfig.h b/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/FreeRTOSConfig_arch.h similarity index 100% rename from tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/FreeRTOSConfig.h rename to tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/FreeRTOSConfig_arch.h diff --git a/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/portmacro.h b/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/portmacro.h index 9ead3fea267..cb58b422658 100644 --- a/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/portmacro.h +++ b/tools/sdk/esp32c3/include/freertos/port/riscv/include/freertos/portmacro.h @@ -1,5 +1,5 @@ /* - * FreeRTOS Kernel V10.2.1 + * FreeRTOS Kernel V10.4.3 * Copyright (C) 2019 Amazon.com, Inc. or its affiliates. All Rights Reserved. * * Permission is hereby granted, free of charge, to any person obtaining a copy of diff --git a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/cpu_ll.h b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/cpu_ll.h index 5c9e56dfc92..fe0f11d4346 100644 --- a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/cpu_ll.h +++ b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/cpu_ll.h @@ -28,6 +28,11 @@ #define CSR_PCMR_MACHINE 0x7e1 #define CSR_PCCR_MACHINE 0x7e2 +/*fast gpio*/ +#define CSR_GPIO_OEN_USER 0x803 +#define CSR_GPIO_IN_USER 0x804 +#define CSR_GPIO_OUT_USER 0x805 + #ifdef __cplusplus extern "C" { #endif @@ -137,7 +142,7 @@ static inline void cpu_ll_clear_watchpoint(int id) FORCE_INLINE_ATTR bool cpu_ll_is_debugger_attached(void) { - return REG_GET_BIT(ASSIST_DEBUG_C0RE_0_DEBUG_MODE_REG, ASSIST_DEBUG_CORE_0_DEBUG_MODULE_ACTIVE); + return REG_GET_BIT(ASSIST_DEBUG_CORE_0_DEBUG_MODE_REG, ASSIST_DEBUG_CORE_0_DEBUG_MODULE_ACTIVE); } static inline void cpu_ll_break(void) @@ -163,6 +168,34 @@ static inline void cpu_ll_waiti(void) asm volatile ("wfi\n"); } +static inline void cpu_ll_enable_dedic_gpio_output(uint32_t mask) +{ + RV_WRITE_CSR(CSR_GPIO_OEN_USER, mask); +} + +static inline void cpu_ll_write_dedic_gpio_all(uint32_t value) +{ + RV_WRITE_CSR(CSR_GPIO_OUT_USER, value); +} + +static inline uint32_t cpu_ll_read_dedic_gpio_in(void) +{ + uint32_t value = RV_READ_CSR(CSR_GPIO_IN_USER); + return value; +} + +static inline uint32_t cpu_ll_read_dedic_gpio_out(void) +{ + uint32_t value = RV_READ_CSR(CSR_GPIO_OUT_USER); + return value; +} + +static inline void cpu_ll_write_dedic_gpio_mask(uint32_t mask, uint32_t value) +{ + RV_SET_CSR(CSR_GPIO_OUT_USER, mask & value); + RV_CLEAR_CSR(CSR_GPIO_OUT_USER, mask & ~(value)); +} + #ifdef __cplusplus } #endif diff --git a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/i2s_ll.h b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/i2s_ll.h index 30fbfb7e517..670db91616b 100644 --- a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/i2s_ll.h +++ b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/i2s_ll.h @@ -44,7 +44,7 @@ typedef struct { uint16_t mclk_div; // I2S module clock devider, Fmclk = Fsclk /(mclk_div+b/a) uint16_t a; uint16_t b; // The decimal part of module clock devider, the decimal is: b/a -} i2s_ll_clk_cal_t; +} i2s_ll_mclk_div_t; /** * @brief I2S module general init, enable I2S clock. @@ -56,6 +56,16 @@ static inline void i2s_ll_enable_clock(i2s_dev_t *hw) hw->tx_clkm_conf.clk_en = 1; } +/** + * @brief I2S module disable I2S clock. + * + * @param hw Peripheral I2S hardware instance address. + */ +static inline void i2s_ll_disable_clock(i2s_dev_t *hw) +{ + hw->tx_clkm_conf.clk_en = 0; +} + /** * @brief Enable I2S tx module clock * @@ -201,7 +211,7 @@ static inline void i2s_ll_tx_set_bck_div_num(i2s_dev_t *hw, uint32_t val) * @param hw Peripheral I2S hardware instance address. * @param set Pointer to I2S clock devider configuration paramater */ -static inline void i2s_ll_tx_set_clk(i2s_dev_t *hw, i2s_ll_clk_cal_t *set) +static inline void i2s_ll_tx_set_clk(i2s_dev_t *hw, i2s_ll_mclk_div_t *set) { if (set->a == 0 || set->b == 0) { hw->tx_clkm_div_conf.tx_clkm_div_x = 0; @@ -240,7 +250,7 @@ static inline void i2s_ll_rx_set_bck_div_num(i2s_dev_t *hw, uint32_t val) * @param hw Peripheral I2S hardware instance address. * @param set Pointer to I2S clock devider configuration paramater */ -static inline void i2s_ll_rx_set_clk(i2s_dev_t *hw, i2s_ll_clk_cal_t *set) +static inline void i2s_ll_rx_set_clk(i2s_dev_t *hw, i2s_ll_mclk_div_t *set) { if (set->a == 0 || set->b == 0) { hw->rx_clkm_div_conf.rx_clkm_div_x = 0; @@ -781,13 +791,41 @@ static inline void i2s_ll_set_single_data(i2s_dev_t *hw, uint32_t data) hw->conf_single_data = data; } +/** + * @brief Enable TX mono mode + * @note MONO in hardware means only one channel got data, but another doesn't + * MONO in software means two channel share same data + * This function aims to use MONO in software meaning + * so 'tx_mono' and 'tx_chan_equal' should be enabled at the same time + * + * @param hw Peripheral I2S hardware instance address. + * @param mono_ena Set true to enable mono mde. + */ +static inline void i2s_ll_tx_enable_mono_mode(i2s_dev_t *hw, bool mono_ena) +{ + hw->tx_conf.tx_mono = mono_ena; + hw->tx_conf.tx_chan_equal = mono_ena; +} + +/** + * @brief Enable RX mono mode + * + * @param hw Peripheral I2S hardware instance address. + * @param mono_ena Set true to enable mono mde. + */ +static inline void i2s_ll_rx_enable_mono_mode(i2s_dev_t *hw, bool mono_ena) +{ + hw->rx_conf.rx_mono = mono_ena; + hw->rx_conf.rx_mono_fst_vld = mono_ena; +} + /** * @brief Enable loopback mode * * @param hw Peripheral I2S hardware instance address. - * @param ena Set true to enable loopback mode. + * @param ena Set true to share BCK and WS signal for tx module and rx module. */ -static inline void i2s_ll_enable_loop_back(i2s_dev_t *hw, bool ena) +static inline void i2s_ll_share_bck_ws(i2s_dev_t *hw, bool ena) { hw->tx_conf.sig_loopback = ena; } diff --git a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/rtc_cntl_ll.h b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/rtc_cntl_ll.h index 72385568a47..9f298bbf09b 100644 --- a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/rtc_cntl_ll.h +++ b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/rtc_cntl_ll.h @@ -17,7 +17,7 @@ #include "soc/soc.h" #include "soc/rtc.h" #include "soc/rtc_cntl_reg.h" -#include "soc/apb_ctrl_reg.h" +#include "soc/syscon_reg.h" #ifdef __cplusplus extern "C" { @@ -47,12 +47,18 @@ static inline void rtc_cntl_ll_gpio_clear_wakeup_pins(void) REG_SET_BIT(RTC_CNTL_GPIO_WAKEUP_REG, RTC_CNTL_GPIO_WAKEUP_STATUS_CLR); } -static inline void rtc_cntl_ll_enable_cpu_retention(uint32_t addr) +static inline void rtc_cntl_ll_set_cpu_retention_link_addr(uint32_t addr) +{ + REG_SET_FIELD(SYSCON_RETENTION_CTRL_REG, SYSCON_RETENTION_LINK_ADDR, (uint32_t)addr); +} + +static inline void rtc_cntl_ll_enable_cpu_retention_clock(void) { - /* write memory address to register */ - REG_SET_FIELD(APB_CTRL_RETENTION_CTRL_REG, APB_CTRL_RETENTION_LINK_ADDR, (uint32_t)addr); - /* Enable clock */ REG_SET_BIT(RTC_CNTL_CLK_CONF_REG, RTC_CNTL_DIG_CLK8M_EN); +} + +static inline void rtc_cntl_ll_enable_cpu_retention(void) +{ /* Enable retention when cpu sleep enable */ REG_SET_BIT(RTC_CNTL_RETENTION_CTRL_REG, RTC_CNTL_RETENTION_EN); } diff --git a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/uhci_ll.h b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/uhci_ll.h index 235d28ab3a3..a766797ea0f 100644 --- a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/uhci_ll.h +++ b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/uhci_ll.h @@ -18,9 +18,13 @@ #pragma once #include -#include "uhci_types.h" +#include "hal/uhci_types.h" #include "soc/uhci_struct.h" +#ifdef __cplusplus +extern "C" { +#endif + #define UHCI_LL_GET_HW(num) (((num) == 0) ? (&UHCI0) : (NULL)) typedef enum { @@ -128,3 +132,7 @@ static inline void uhci_ll_set_eof_mode(uhci_dev_t *hw, uint32_t eof_mode) hw->conf0.len_eof_en = 1; } } + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/xt_wdt_ll.h b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/xt_wdt_ll.h new file mode 100644 index 00000000000..65b36253e58 --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/esp32c3/include/hal/xt_wdt_ll.h @@ -0,0 +1,101 @@ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +// The LL layer for xtal32k WDT register operations. +// Note that most of the register operations in this layer are non-atomic operations. + +#pragma once + +#include +#include "soc/rtc_cntl_periph.h" + +#ifdef __cplusplus +extern "C" { +#endif + +#define XT_WDT_LL_XTAL32_DEAD_INTR_MASK RTC_CNTL_XTAL32K_DEAD_INT_ST_M + +/** + * @brief Enable the XT_WDT + * + * @param hw Start address of the peripheral registers. + */ +inline void xt_wdt_ll_enable(rtc_cntl_dev_t *hw, bool enable) +{ + hw->ext_xtl_conf.xtal32k_wdt_en = enable; +} + +/** + * @brief Check if the XT_WDT is enabled + * + * @param hw Start address of the peripheral registers. + * @return True if XT WDT is enabled + */ +inline bool xt_wdt_ll_check_if_enabled(rtc_cntl_dev_t *hw) +{ + return (hw->ext_xtl_conf.xtal32k_wdt_en) ? true : false; +} + +/** + * @brief Set the watchdog timeout value + * + * @param hw Start address of the peripheral registers. + * @param timeout timeout value in RTC_CLK cycles + */ +inline void xt_wdt_ll_set_timeout(rtc_cntl_dev_t *hw, uint8_t timeout) +{ + hw->xtal32k_conf.xtal32k_wdt_timeout = timeout; +} + + +/** + * @brief Reset the XT_WDT + * + * @param hw Start address of the peripheral registers. + */ +inline void xt_wdt_ll_reset(rtc_cntl_dev_t *hw) +{ + hw->ext_xtl_conf.xtal32k_wdt_reset = 1; + hw->ext_xtl_conf.xtal32k_wdt_reset = 0; +} + + +/** + * @brief Set the backup clock value + * + * @param hw Start address of the peripheral registers. + * @param backup_clk_val Backup clock value, see TRM for definition + */ +inline void xt_wdt_ll_set_backup_clk_factor(rtc_cntl_dev_t *hw, uint32_t backup_clk_val) +{ + hw->xtal32k_clk_factor = backup_clk_val; +} + +/** + * @brief Enable the auto-backup clock feature + * + * @param hw Start address of the peripheral registers. + * @param enable True - enable, False - disable + */ +inline void xt_wdt_ll_auto_backup_enable(rtc_cntl_dev_t *hw, bool enable) +{ + hw->ext_xtl_conf.xtal32k_auto_backup = enable; +} + +/** + * @brief Enable the timeout interrupt + * + * @param hw Start address of the peripheral registers. + * @param enable True - enable, False - disable + */ +inline void xt_wdt_ll_intr_enable(rtc_cntl_dev_t *hw, bool enable) +{ + hw->int_ena.rtc_xtal32k_dead = enable; +} + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/include/hal/adc_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/adc_hal.h index 5effc61b4b4..807d620c639 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/adc_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/adc_hal.h @@ -276,7 +276,7 @@ esp_err_t adc_hal_convert(adc_ll_num_t adc_n, int channel, int *out_raw); /*--------------------------------------------------------------- ADC calibration setting ---------------------------------------------------------------*/ -#if SOC_ADC_HW_CALIBRATION_V1 +#if SOC_ADC_CALIBRATION_V1_SUPPORTED // ESP32-S2, C3 and H2 support HW offset calibration. /** @@ -312,7 +312,7 @@ void adc_hal_set_calibration_param(adc_ll_num_t adc_n, uint32_t param); */ uint32_t adc_hal_self_calibration(adc_ll_num_t adc_n, adc_channel_t channel, adc_atten_t atten, bool internal_gnd); -#endif //SOC_ADC_HW_CALIBRATION_V1 +#endif //SOC_ADC_CALIBRATION_V1_SUPPORTED #if CONFIG_IDF_TARGET_ESP32C3 || CONFIG_IDF_TARGET_ESP32H2 /*--------------------------------------------------------------- diff --git a/tools/sdk/esp32c3/include/hal/include/hal/ds_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/ds_hal.h index 253fab9f962..40d5c358936 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/ds_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/ds_hal.h @@ -21,7 +21,7 @@ #pragma once #if CONFIG_IDF_TARGET_ESP32 - #error "ESP32 doesn't have a DS peripheral" +#error "ESP32 doesn't have a DS peripheral" #endif #include diff --git a/tools/sdk/esp32c3/include/hal/include/hal/i2s_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/i2s_hal.h index d0446f7a476..a08813db808 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/i2s_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/i2s_hal.h @@ -33,16 +33,16 @@ extern "C" { #endif /** - * @brief I2S channel bits configurations - * + * @brief I2S clock configuration */ -typedef union { - struct { - uint32_t sample_bits : 16; /*!< I2S sample bits in one channel */ - uint32_t chan_bits : 16; /*!< I2S total bits in one channel. Should not be smaller than 'sample_bits', default '0' means equal to 'sample_bits' */ - }; - uint32_t val; /*!< I2S cannel bits configiration value */ -} i2s_hal_bits_cfg_t; +typedef struct { + uint32_t sclk; /*!< I2S module clock */ + uint32_t mclk; /*!< I2S master clock */ + uint32_t bclk; /*!< I2S bit clock */ + uint16_t mclk_div; /*!< I2S master clock division */ + uint16_t bclk_div; /*!< I2S bit clock division*/ +} i2s_hal_clock_cfg_t; + /** * @brief I2S HAL configurations @@ -50,17 +50,19 @@ typedef union { typedef struct { i2s_mode_t mode; /*!< I2S work mode, using ored mask of `i2s_mode_t`*/ uint32_t sample_rate; /*!< I2S sample rate*/ - i2s_channel_t ch; /*!< I2S channels*/ i2s_comm_format_t comm_fmt; /*!< I2S communication format */ i2s_channel_fmt_t chan_fmt; /*!< I2S channel format, there are total 16 channels in TDM mode.*/ - i2s_hal_bits_cfg_t bits_cfg; /*!< Channel bits configuration*/ -#if SOC_I2S_SUPPORTS_TDM + uint32_t sample_bits; /*!< I2S sample bits in one channel */ + uint32_t chan_bits; /*!< I2S total bits in one channel. Should not be smaller than 'sample_bits', default '0' means equal to 'sample_bits' */ + uint32_t active_chan; /*!< I2S active channel number */ uint32_t total_chan; /*!< Total number of I2S channels */ + +#if SOC_I2S_SUPPORTS_TDM uint32_t chan_mask; /*!< Active channel bit mask, set value in `i2s_channel_t` to enable specific channel, the bit map of active channel can not exceed (0x1<dev); + +/** + * @brief Disable I2S module clock + * + * @param hal Context of the HAL layer + */ +#define i2s_hal_disable_module_clock(hal) i2s_ll_disable_clock((hal)->dev); + /** * @brief Reset I2S TX channel * @@ -101,7 +117,8 @@ typedef struct { #define i2s_hal_reset_rx_fifo(hal) i2s_ll_rx_reset_fifo((hal)->dev) /** - * @brief Init the I2S hal. This function should be called first before other hal layer function is called + * @brief Get I2S hardware instance and enable I2S module clock + * @note This function should be called first before other hal layer function is called * * @param hal Context of the HAL layer * @param i2s_num The uart port number, the max port number is (I2S_NUM_MAX -1) @@ -133,7 +150,7 @@ void i2s_hal_tx_set_channel_style(i2s_hal_context_t *hal, const i2s_hal_config_t void i2s_hal_rx_set_channel_style(i2s_hal_context_t *hal, const i2s_hal_config_t *hal_cfg); /** - * @brief Config I2S param + * @brief Initialize I2S hardware * * @param hal Context of the HAL layer * @param hal_cfg I2S hal configuration structer, refer to `i2s_hal_config_t` @@ -212,46 +229,56 @@ void i2s_hal_enable_slave_fd_mode(i2s_hal_context_t *hal); * @brief Configure I2S TX module clock devider * * @param hal Context of the HAL layer - * @param sclk I2S source clock freq - * @param fbck I2S bck freq - * @param factor bck factor, factor=sclk/fbck + * @param clk_cfg I2S clock configuration */ -void i2s_hal_tx_clock_config(i2s_hal_context_t *hal, uint32_t sclk, uint32_t fbck, int factor); +void i2s_hal_tx_clock_config(i2s_hal_context_t *hal, i2s_hal_clock_cfg_t *clk_cfg); /** * @brief Configure I2S RX module clock devider * * @param hal Context of the HAL layer - * @param sclk I2S source clock freq - * @param fbck I2S bck freq - * @param factor bck factor, factor=sclk/fbck + * @param clk_cfg I2S clock configuration */ -void i2s_hal_rx_clock_config(i2s_hal_context_t *hal, uint32_t sclk, uint32_t fbck, int factor); +void i2s_hal_rx_clock_config(i2s_hal_context_t *hal, i2s_hal_clock_cfg_t *clk_cfg); -#if SOC_I2S_SUPPORTS_PCM /** - * @brief Configure I2S TX PCM encoder or decoder. + * @brief Set I2S tx clock source * * @param hal Context of the HAL layer - * @param cfg PCM configure paramater, refer to `i2s_pcm_compress_t` + * @param clk_src i2s tx clock source (see 'i2s_clock_src_t') */ -#define i2s_hal_tx_pcm_cfg(hal, cfg) i2s_ll_tx_set_pcm_type((hal)->dev, cfg) +#define i2s_hal_tx_set_clock_source(hal, clk_src) i2s_ll_tx_clk_set_src((hal)->dev, clk_src) /** - * @brief Configure I2S RX PCM encoder or decoder. + * @brief Set I2S rx clock source * * @param hal Context of the HAL layer - * @param cfg PCM configure paramater, refer to `i2s_pcm_compress_t` + * @param clk_src i2s rx clock source (see 'i2s_clock_src_t') */ -#define i2s_hal_rx_pcm_cfg(hal, cfg) i2s_ll_rx_set_pcm_type((hal)->dev, cfg) -#endif +#define i2s_hal_rx_set_clock_source(hal, clk_src) i2s_ll_rx_clk_set_src((hal)->dev, clk_src) + +/** + * @brief Enable I2S tx slave mode + * + * @param hal Context of the HAL layer + * @param enable set 'true' to enable tx slave mode + */ +#define i2s_hal_tx_enable_slave_mode(hal, enable) i2s_ll_tx_set_slave_mod((hal)->dev, enable) + +/** + * @brief Enable I2S rx slave mode + * + * @param hal Context of the HAL layer + * @param enable set 'true' to enable rx slave mode + */ +#define i2s_hal_rx_enable_slave_mode(hal, enable) i2s_ll_rx_set_slave_mod((hal)->dev, enable) /** * @brief Enable loopback mode * * @param hal Context of the HAL layer */ -#define i2s_hal_enable_sig_loopback(hal) i2s_ll_enable_loop_back((hal)->dev, true) +#define i2s_hal_enable_sig_loopback(hal) i2s_ll_share_bck_ws((hal)->dev, true) /** * @brief Set I2S configuration for common TX mode @@ -271,6 +298,24 @@ void i2s_hal_tx_set_common_mode(i2s_hal_context_t *hal, const i2s_hal_config_t * */ void i2s_hal_rx_set_common_mode(i2s_hal_context_t *hal, const i2s_hal_config_t *hal_cfg); +#if SOC_I2S_SUPPORTS_PCM +/** + * @brief Configure I2S TX PCM encoder or decoder. + * + * @param hal Context of the HAL layer + * @param cfg PCM configure paramater, refer to `i2s_pcm_compress_t` + */ +#define i2s_hal_tx_pcm_cfg(hal, cfg) i2s_ll_tx_set_pcm_type((hal)->dev, cfg) + +/** + * @brief Configure I2S RX PCM encoder or decoder. + * + * @param hal Context of the HAL layer + * @param cfg PCM configure paramater, refer to `i2s_pcm_compress_t` + */ +#define i2s_hal_rx_pcm_cfg(hal, cfg) i2s_ll_rx_set_pcm_type((hal)->dev, cfg) +#endif + #if SOC_I2S_SUPPORTS_PDM_TX /** * @brief Configure I2S TX PDM sample rate @@ -470,7 +515,7 @@ void i2s_hal_rx_set_pdm_mode_default(i2s_hal_context_t *hal); #define i2s_hal_get_in_eof_des_addr(hal, addr) i2s_ll_rx_get_eof_des_addr((hal)->dev, addr) #endif -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_ADC /** * @brief Enable Builtin DAC * @@ -486,18 +531,20 @@ void i2s_hal_rx_set_pdm_mode_default(i2s_hal_context_t *hal); #define i2s_hal_enable_builtin_adc(hal) i2s_ll_enable_builtin_adc((hal)->dev, true); /** - * @brief Disable Builtin DAC + * @brief Disable Builtin ADC * * @param hal Context of the HAL layer */ -#define i2s_hal_disable_builtin_dac(hal) i2s_ll_enable_builtin_dac((hal)->dev, false); +#define i2s_hal_disable_builtin_adc(hal) i2s_ll_enable_builtin_adc((hal)->dev, false); +#endif +#if SOC_I2S_SUPPORTS_DAC /** - * @brief Disable Builtin ADC + * @brief Disable Builtin DAC * * @param hal Context of the HAL layer */ -#define i2s_hal_disable_builtin_adc(hal) i2s_ll_enable_builtin_adc((hal)->dev, false); +#define i2s_hal_disable_builtin_dac(hal) i2s_ll_enable_builtin_dac((hal)->dev, false); #endif #ifdef __cplusplus diff --git a/tools/sdk/esp32c3/include/hal/include/hal/i2s_types.h b/tools/sdk/esp32c3/include/hal/include/hal/i2s_types.h index 630aedb1496..48d745eb2fa 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/i2s_types.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/i2s_types.h @@ -107,8 +107,8 @@ typedef enum { I2S_CHANNEL_FMT_RIGHT_LEFT, /*!< Separated left and right channel */ I2S_CHANNEL_FMT_ALL_RIGHT, /*!< Load right channel data in both two channels */ I2S_CHANNEL_FMT_ALL_LEFT, /*!< Load left channel data in both two channels */ - I2S_CHANNEL_FMT_ONLY_RIGHT, /*!< Only load data in right channel */ - I2S_CHANNEL_FMT_ONLY_LEFT, /*!< Only load data in left channel */ + I2S_CHANNEL_FMT_ONLY_RIGHT, /*!< Only load data in right channel (mono mode) */ + I2S_CHANNEL_FMT_ONLY_LEFT, /*!< Only load data in left channel (mono mode) */ #if SOC_I2S_SUPPORTS_TDM // Multiple channels are available with TDM feature I2S_CHANNEL_FMT_MULTIPLE, /*!< More than two channels are used */ @@ -123,11 +123,13 @@ typedef enum { I2S_MODE_SLAVE = (0x1 << 1), /*!< Slave mode*/ I2S_MODE_TX = (0x1 << 2), /*!< TX mode*/ I2S_MODE_RX = (0x1 << 3), /*!< RX mode*/ -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_DAC //built-in DAC functions are only supported on I2S0 for ESP32 chip. I2S_MODE_DAC_BUILT_IN = (0x1 << 4), /*!< Output I2S data to built-in DAC, no matter the data format is 16bit or 32 bit, the DAC module will only take the 8bits from MSB*/ +#endif // SOC_I2S_SUPPORTS_DAC +#if SOC_I2S_SUPPORTS_ADC I2S_MODE_ADC_BUILT_IN = (0x1 << 5), /*!< Input I2S data from built-in ADC, each data can be 12-bit width at most*/ -#endif +#endif // SOC_I2S_SUPPORTS_ADC // PDM functions are only supported on I2S0 (all chips). I2S_MODE_PDM = (0x1 << 6), /*!< I2S PDM mode*/ } i2s_mode_t; @@ -152,7 +154,7 @@ typedef enum { I2S_MCLK_MULTIPLE_384 = 384, /*!< mclk = sample_rate * 384 */ } i2s_mclk_multiple_t; -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_DAC /** * @brief I2S DAC mode for i2s_set_dac_mode. * @@ -165,7 +167,7 @@ typedef enum { I2S_DAC_CHANNEL_BOTH_EN = 0x3, /*!< Enable both of the I2S built-in DAC channels.*/ I2S_DAC_CHANNEL_MAX = 0x4, /*!< I2S built-in DAC mode max index*/ } i2s_dac_mode_t; -#endif //SOC_I2S_SUPPORTS_ADC_DAC +#endif //SOC_I2S_SUPPORTS_DAC #if SOC_I2S_SUPPORTS_PCM /** diff --git a/tools/sdk/esp32c3/include/hal/include/hal/lcd_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/lcd_hal.h index a6bcba166c6..76e28dda0e4 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/lcd_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/lcd_hal.h @@ -24,10 +24,10 @@ extern "C" { #endif -#include "soc/lcd_cam_struct.h" +typedef struct lcd_cam_dev_t *lcd_soc_handle_t; typedef struct { - lcd_cam_dev_t *dev; + lcd_soc_handle_t dev; } lcd_hal_context_t; void lcd_hal_init(lcd_hal_context_t *hal, int id); diff --git a/tools/sdk/esp32c3/include/hal/include/hal/lcd_types.h b/tools/sdk/esp32c3/include/hal/include/hal/lcd_types.h new file mode 100644 index 00000000000..69dab14801d --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/include/hal/lcd_types.h @@ -0,0 +1,42 @@ +// Copyright 2021 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +#pragma once + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief LCD clock source + * @note User should select the clock source based on the real requirement: + * ╔═════════════════════╦══════════════════════════╦════════════════════════════╗ + * ║ LCD clock source ║ Features ║ Power Management ║ + * ╠═════════════════════╬══════════════════════════╬════════════════════════════╣ + * ║ LCD_CLK_SRC_PLL160M ║ High resolution, fixed ║ ESP_PM_APB_FREQ_MAX lock ║ + * ╠═════════════════════╬══════════════════════════╬════════════════════════════╣ + * ║ LCD_CLK_SRC_APLL ║ Configurable resolution ║ ESP_PM_NO_LIGHT_SLEEP lock ║ + * ╠═════════════════════╬══════════════════════════╬════════════════════════════╣ + * ║ LCD_CLK_SRC_XTAL ║ Medium resolution, fixed ║ No PM lock ║ + * ╚═════════════════════╩══════════════════════════╩════════════════════════════╝ + */ +typedef enum { + LCD_CLK_SRC_PLL160M, /*!< Select PLL160M as the source clock */ + LCD_CLK_SRC_APLL, /*!< Select APLL as the source clock */ + LCD_CLK_SRC_XTAL, /*!< Select XTAL as the source clock */ +} lcd_clock_source_t; + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/include/hal/rtc_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/rtc_hal.h index 8d74f4c4cd8..90f965ed58c 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/rtc_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/rtc_hal.h @@ -14,12 +14,36 @@ #pragma once +#include "soc/soc_caps.h" #include "hal/gpio_types.h" #include "hal/rtc_cntl_ll.h" #if !CONFIG_IDF_TARGET_ESP32C3 && !CONFIG_IDF_TARGET_ESP32H2 #include "hal/rtc_io_ll.h" #endif +typedef struct rtc_cntl_sleep_retent { +#if SOC_PM_SUPPORT_CPU_PD + void *cpu_pd_mem; /* Internal ram address for cpu retention */ +#endif // SOC_PM_SUPPORT_CPU_PD +#if SOC_PM_SUPPORT_TAGMEM_PD + struct { + void *link_addr; /* Internal ram address for tagmem retention */ + struct { + uint32_t start_point: 8, /* the row of start for i-cache tag memory */ + vld_size: 8, /* valid size of i-cache tag memory, unit: 4 i-cache tagmem blocks */ + size: 8, /* i-cache tag memory size, unit: 4 i-cache tagmem blocks */ + enable: 1; /* enable or disable i-cache tagmem retention */ + } icache; + struct { + uint32_t start_point: 9, /* the row of start for d-cache tag memory */ + vld_size: 9, /* valid size of d-cache tag memory, unit: 4 d-cache tagmem blocks */ + size: 9, /* d-cache tag memory size, unit: 4 d-cache tagmem blocks */ + enable: 1; /* enable or disable d-cache tagmem retention */ + } dcache; + } tagmem; +#endif // SOC_PM_SUPPORT_TAGMEM_PD +} rtc_cntl_sleep_retent_t; + #define RTC_HAL_DMA_LINK_NODE_SIZE (16) #if SOC_PM_SUPPORT_EXT_WAKEUP @@ -46,9 +70,21 @@ void * rtc_cntl_hal_dma_link_init(void *elem, void *buff, int size, void *next); +#if SOC_PM_SUPPORT_CPU_PD + void rtc_cntl_hal_enable_cpu_retention(void *addr); -#define rtc_cntl_hal_disable_cpu_retention() rtc_cntl_ll_disable_cpu_retention() +void rtc_cntl_hal_disable_cpu_retention(void *addr); + +#endif + +#if SOC_PM_SUPPORT_TAGMEM_PD + +void rtc_cntl_hal_enable_tagmem_retention(void *addr); + +void rtc_cntl_hal_disable_tagmem_retention(void *addr); + +#endif /* * Enable wakeup from ULP coprocessor. diff --git a/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_hal.h index dbbb5ff53b5..ae37016fa2d 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_hal.h @@ -51,20 +51,41 @@ typedef struct { uint32_t flags; ///< Flags for configurations with one set of driver code. (e.g. QPI mode, auto-suspend mode, 64-bit address mode, etc.) #define SPI_FLASH_HOST_CONTEXT_FLAG_AUTO_SUSPEND BIT(0) ///< When the auto-suspend is setup in configuration. #define SPI_FLASH_HOST_CONTEXT_FLAG_AUTO_RESUME BIT(1) ///< Setup auto-resume feature. +#define SPI_FLASH_HOST_CONTEXT_FLAG_OCTAL_MODE BIT(2) ///< Flash works under octal spi mode. spi_flash_sus_cmd_conf sus_cfg; ///< To store suspend command/mask information. + uint32_t slicer_flags; /// Slicer flags for configuring how to slice data correctly while reading or writing. +#define SPI_FLASH_HOST_CONTEXT_SLICER_FLAG_DTR BIT(0) ///< Slice data according to DTR mode, the address and length must be even (A0=0). } spi_flash_hal_context_t; -_Static_assert(sizeof(spi_flash_hal_context_t) == 36, "size of spi_flash_hal_context_t incorrect. Please check data compatibility with the ROM"); +_Static_assert(sizeof(spi_flash_hal_context_t) == 40, "size of spi_flash_hal_context_t incorrect. Please check data compatibility with the ROM"); + +/// This struct provide MSPI Flash necessary timing related config, should be consistent with that in union in `spi_flash_hal_config_t`. +typedef struct { + uint32_t extra_dummy; + uint32_t cs_hold; + uint8_t cs_setup; + spi_flash_ll_clock_reg_t clock_config; +} spi_flash_hal_timing_config_t; /// Configuration structure for the SPI driver. typedef struct { - spi_host_device_t host_id; ///< SPI peripheral ID. - int cs_num; ///< Which cs pin is used, 0-(SOC_SPI_PERIPH_CS_NUM-1). + union { + struct { + uint32_t extra_dummy; ///< extra dummy for timing compensation. + uint32_t cs_hold; ///< CS hold time config used by the host + uint8_t cs_setup; ///< (cycles-1) of prepare phase by spi clock + spi_flash_ll_clock_reg_t clock_config; ///< (optional) Clock configuration for Octal flash. + }; + spi_flash_hal_timing_config_t timing_reg; ///< Reconfigure timing tuning regs. + }; bool iomux; ///< Whether the IOMUX is used, used for timing compensation. int input_delay_ns; ///< Input delay on the MISO pin after the launch clock, used for timing compensation. esp_flash_speed_t speed;///< SPI flash clock speed to work at. - uint32_t cs_hold; ///< CS hold time config used by the host - uint8_t cs_setup; ///< (cycles-1) of prepare phase by spi clock + spi_host_device_t host_id; ///< SPI peripheral ID. + int cs_num; ///< Which cs pin is used, 0-(SOC_SPI_PERIPH_CS_NUM-1). bool auto_sus_en; ///< Auto suspend feature enable bit 1: enable, 0: disable. + bool octal_mode_en; ///< Octal spi flash mode enable bit 1: enable, 0: disable. + bool using_timing_tuning; ///< System exist SPI0/1 timing tuning, using value from system directely if set to 1. + esp_flash_io_mode_t default_io_mode; ///< Default flash io mode. } spi_flash_hal_config_t; /** diff --git a/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_types.h b/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_types.h index 0cc605595f2..c9d5035e60e 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_types.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/spi_flash_types.h @@ -37,6 +37,7 @@ typedef struct { #define SPI_FLASH_TRANS_FLAG_BYTE_SWAP BIT(2) ///< Used for DTR mode, to swap the bytes of a pair of rising/falling edge uint16_t command; ///< Command to send uint8_t dummy_bitlen; ///< Basic dummy bits to use + uint32_t io_mode; ///< Flash working mode when `SPI_FLASH_IGNORE_BASEIO` is specified. } spi_flash_trans_t; /** @@ -54,6 +55,7 @@ typedef enum { ESP_FLASH_26MHZ, ///< The flash runs under 26MHz ESP_FLASH_40MHZ, ///< The flash runs under 40MHz ESP_FLASH_80MHZ, ///< The flash runs under 80MHz + ESP_FLASH_120MHZ, ///< The flash runs under 120MHz, 120MHZ can only be used by main flash after timing tuning in system. Do not use this directely in any API. ESP_FLASH_SPEED_MAX, ///< The maximum frequency supported by the host is ``ESP_FLASH_SPEED_MAX-1``. } esp_flash_speed_t; @@ -71,7 +73,9 @@ typedef enum { SPI_FLASH_DIO, ///< Both address & data transferred using dual I/O SPI_FLASH_QOUT, ///< Data read using quad I/O SPI_FLASH_QIO, ///< Both address & data transferred using quad I/O - +#define SPI_FLASH_OPI_FLAG 16 ///< A flag for flash work in opi mode, the io mode below are opi, above are SPI/QSPI mode. DO NOT use this value in any API. + SPI_FLASH_OPI_STR = SPI_FLASH_OPI_FLAG,///< Only support on OPI flash, flash read and write under STR mode + SPI_FLASH_OPI_DTR,///< Only support on OPI flash, flash read and write under DTR mode SPI_FLASH_READ_MODE_MAX, ///< The fastest io mode supported by the host is ``ESP_FLASH_READ_MODE_MAX-1``. } esp_flash_io_mode_t; diff --git a/tools/sdk/esp32c3/include/hal/include/hal/timer_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/timer_hal.h index f8c91739d91..cb3d5e0671d 100644 --- a/tools/sdk/esp32c3/include/hal/include/hal/timer_hal.h +++ b/tools/sdk/esp32c3/include/hal/include/hal/timer_hal.h @@ -59,6 +59,15 @@ void timer_hal_init(timer_hal_context_t *hal, timer_group_t group_num, timer_idx */ void timer_hal_get_status_reg_mask_bit(timer_hal_context_t *hal, uint32_t *status_reg, uint32_t *mask_bit); +/** + * @brief Reset timer peripheral + * + * @param hal Context of the HAL layer + * + * @return None + */ +void timer_hal_reset_periph(timer_hal_context_t *hal); + /** * @brief Set timer clock prescale value * diff --git a/tools/sdk/esp32c3/include/hal/include/hal/uhci_types.h b/tools/sdk/esp32c3/include/hal/include/hal/uhci_types.h new file mode 100644 index 00000000000..7122e2a41a9 --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/include/hal/uhci_types.h @@ -0,0 +1,54 @@ +// Copyright 2015-2019 Espressif Systems (Shanghai) PTE LTD +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at + +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + + + +// Though the UHCI driver hasn't been published, some types are defined here +// for users to develop over the HAL. See example: controller_hci_uart_esp32c3 + +#pragma once + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @brief UHCI escape sequence + */ +typedef struct { + uint8_t seper_chr; /*!< escape sequence character */ + uint8_t sub_chr1; /*!< escape sequence sub-character 1 */ + uint8_t sub_chr2; /*!< escape sequence sub-character 2 */ + bool sub_chr_en; /*!< enable use of sub-chaacter of escape sequence */ +} uhci_seper_chr_t; + +/** + * @brief UHCI software flow control + */ +typedef struct { + uint8_t xon_chr; /*!< character for XON */ + uint8_t xon_sub1; /*!< sub-character 1 for XON */ + uint8_t xon_sub2; /*!< sub-character 2 for XON */ + uint8_t xoff_chr; /*!< character 2 for XOFF */ + uint8_t xoff_sub1; /*!< sub-character 1 for XOFF */ + uint8_t xoff_sub2; /*!< sub-character 2 for XOFF */ + uint8_t flow_en; /*!< enable use of software flow control */ +} uhci_swflow_ctrl_sub_chr_t; + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_hal.h new file mode 100644 index 00000000000..fe77eb87446 --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_hal.h @@ -0,0 +1,81 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once + +#include "usb_types_private.h" +#include "usb_phy_types.h" +#include "soc/soc_caps.h" +#include "soc/usb_wrap_struct.h" +#if SOC_USB_SERIAL_JTAG_SUPPORTED +#include "soc/usb_serial_jtag_struct.h" +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * Context that should be maintained by both the driver and the HAL + */ +typedef struct { + usb_wrap_dev_t *wrap_dev; /**< Pointer to base address of USB Wrapper registers */ +#if SOC_USB_SERIAL_JTAG_SUPPORTED + usb_serial_jtag_dev_t *jtag_dev; /**< Pointer to base address of USB Serial JTAG registers */ +#endif +} usb_phy_hal_context_t; + +/** + * @brief Init the USB PHY hal. This function should be called first before other hal layer function is called + * + * @param hal Context of the HAL layer + */ +void usb_phy_hal_init(usb_phy_hal_context_t *hal); + +/** + * @brief Configure internal/external PHY for USB_OTG + * + * @param hal Context of the HAL layer + * @param phy_target USB PHY target + */ +void usb_phy_hal_otg_conf(usb_phy_hal_context_t *hal, usb_phy_target_t phy_target); + +#if SOC_USB_SERIAL_JTAG_SUPPORTED +/** + * @brief Configure internal/external PHY for USB_Serial_JTAG + * + * @param hal Context of the HAL layer + * @param phy_target USB PHY target + */ +void usb_phy_hal_jtag_conf(usb_phy_hal_context_t *hal, usb_phy_target_t phy_target); +#endif + +/** + * @brief Configure pullup/pulldown loads for the D+/D- as a host + * + * @param hal Context of the HAL layer + */ +void usb_phy_hal_int_load_conf_host(usb_phy_hal_context_t *hal); + +/** + * @brief Configure pullup/pulldown loads for the D+/D- as a device + * + * @param hal Context of the HAL layer + * @param speed USB speed + */ +void usb_phy_hal_int_load_conf_dev(usb_phy_hal_context_t *hal, usb_priv_speed_t speed); + +/** + * @brief Enable/Disable test mode for internal PHY to mimick host-device disconnection + * + * @param hal Context of the HAL layer + * @param disconn Whether to disconnect + */ +void usb_phy_hal_int_mimick_disconn(usb_phy_hal_context_t *hal, bool disconn); + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_types.h b/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_types.h new file mode 100644 index 00000000000..1f5ac431efa --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/include/hal/usb_phy_types.h @@ -0,0 +1,63 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +/* +Note: This header file contains USB2.0 related types and macros that can be used by code specific to the DWC_OTG +controller (i.e., the HW specific layers of the USB host stack). Thus, this header is only meant to be used below (and +including) the HAL layer. For types and macros that are HW implementation agnostic (i.e., HCD layer and above), add them +to the "usb/usb_types_ch9.h" header instead. +*/ + +#pragma once + +#ifdef __cplusplus +extern "C" +{ +#endif + +/** + * @brief USB PHY target + */ +typedef enum { + USB_PHY_TARGET_INT, /**< USB target is internal PHY */ + USB_PHY_TARGET_EXT, /**< USB target is external PHY */ + USB_PHY_TARGET_MAX, +} usb_phy_target_t; + +/** + * @brief USB PHY source + */ +typedef enum { + USB_PHY_CTRL_OTG, /**< PHY controller is USB OTG */ +#if SOC_USB_SERIAL_JTAG_SUPPORTED + USB_PHY_CTRL_SERIAL_JTAG, /**< PHY controller is USB Serial JTAG */ +#endif + USB_PHY_CTRL_MAX, +} usb_phy_controller_t; + +/** + * @brief USB OTG mode + */ +typedef enum { + USB_PHY_MODE_DEFAULT, /**< USB OTG default mode */ + USB_OTG_MODE_HOST, /**< USB OTG host mode */ + USB_OTG_MODE_DEVICE, /**< USB OTG device mode */ + USB_OTG_MODE_MAX, +} usb_otg_mode_t; + +/** + * @brief USB speed + */ +typedef enum { + USB_PHY_SPEED_UNDEFINED, + USB_PHY_SPEED_LOW, /**< USB Low Speed (1.5 Mbit/s) */ + USB_PHY_SPEED_FULL, /**< USB Full Speed (12 Mbit/s) */ + USB_PHY_SPEED_MAX, +} usb_phy_speed_t; + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/include/hal/xt_wdt_hal.h b/tools/sdk/esp32c3/include/hal/include/hal/xt_wdt_hal.h new file mode 100644 index 00000000000..bd08f2a989f --- /dev/null +++ b/tools/sdk/esp32c3/include/hal/include/hal/xt_wdt_hal.h @@ -0,0 +1,61 @@ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once + +#include +#include + +#include "hal/xt_wdt_ll.h" + +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + rtc_cntl_dev_t *dev; /* Pointer to the RTC register struct */ +} xt_wdt_hal_context_t; /* HAL context struct */ + +typedef struct { + uint32_t timeout; /* Watchdog timer timeout in RTC_CLK cycles*/ +} xt_wdt_hal_config_t; /* HAL config parameter struct */ + +/* ---------------------------- Init and Config ----------------------------- */ + +/** + * @brief Initialize the WDTs associated HAL context + * + * Prepares the register for enabling the WDT and sets the timeout value + * + * @param hal Pointer to the HAL layer context + * @param config Pointer to config struct + */ +void xt_wdt_hal_init(xt_wdt_hal_context_t *hal, const xt_wdt_hal_config_t *config); + + +/** + * @brief Enable or disable the WDT + * + * @param hal Pointer to the HAL layer context + * @param enable true for enable WDT, false for disable + */ +void xt_wdt_hal_enable(xt_wdt_hal_context_t *hal, bool enable); + +/** + * @brief Enable the automatic RTC backup clock with the given frequency + * + * Calculates and sets the necessary hardware parameters to meet the desired + * backup clock frequency + * + * @param hal Pointer to the HAL layer context + * @param rtc_clk_frequency_khz desired frequency for the backup clock + * @return uint32_t the calculated clock factor value + */ +uint32_t xt_wdt_hal_enable_backup_clk(xt_wdt_hal_context_t *hal, uint32_t rtc_clk_frequency_khz); + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/hal/platform_port/include/hal/misc.h b/tools/sdk/esp32c3/include/hal/platform_port/include/hal/misc.h index 3b2f172ab99..4afb49653ff 100644 --- a/tools/sdk/esp32c3/include/hal/platform_port/include/hal/misc.h +++ b/tools/sdk/esp32c3/include/hal/platform_port/include/hal/misc.h @@ -19,20 +19,41 @@ /** @cond */ //Doxy command to hide preprocessor definitions from docs */ -// In case the compiler optimise a 32bit instruction (e.g. s32i) into 8/16bit instruction with size optimization enabled -// which is not allowed on s2 and later chips (s2, s3, c3, h2) -// use these wrappers for manually read-modify-write with l32i and s32i - -// modify register as uint32_t -#define HAL_FORCE_MODIFY_U32_REG_FIELD(base_reg, field, val) \ +/** + * @brief Macro to force a 32-bit read, modify, then write on a peripheral register + * + * Due to a GCC bug, the compiler may still try to optimize read/writes to peripheral register fields by using 8/16 bit + * access, even if they are marked volatile (i.e., -fstrict-volatile-bitfields has no effect). + * + * For ESP chips, the peripheral bus only allows 32-bit read/writes. The following macro works around the compiler issue + * by forcing a 32-bit read/modify/write. + * + * @note This macro should only be called on register fields of xxx_struct.h type headers, as it depends on the presence + * of a 'val' field of the register union. + * @note Current implementation reads into a uint32_t instead of copy base_reg direclty to temp_reg. The reason being + * that C++ does not create a copy constructor for volatile structs. + */ +#define HAL_FORCE_MODIFY_U32_REG_FIELD(base_reg, reg_field, field_val) \ { \ - typeof(base_reg) temp_reg = (base_reg); \ - temp_reg.field = (val); \ - (base_reg) = temp_reg; \ + uint32_t temp_val = base_reg.val; \ + typeof(base_reg) temp_reg; \ + temp_reg.val = temp_val; \ + temp_reg.reg_field = (field_val); \ + (base_reg).val = temp_reg.val; \ } -// read register as uint32_t -#define HAL_FORCE_READ_U32_REG_FIELD(base_reg, field) \ -( ((typeof(base_reg))((base_reg).val)).field ) +/** + * @brief Macro to force a 32-bit read on a peripheral register + * + * @note This macro should only be called on register fields of xxx_struct.h type headers. See description above for + * more details. + * @note Current implementation reads into a uint32_t. See description above for more details. + */ +#define HAL_FORCE_READ_U32_REG_FIELD(base_reg, reg_field) ({ \ + uint32_t temp_val = base_reg.val; \ + typeof(base_reg) temp_reg; \ + temp_reg.val = temp_val; \ + temp_reg.reg_field; \ +}) /** @endcond */ diff --git a/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154.h b/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154.h index a8d4678e924..e31a5ca37e5 100644 --- a/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154.h +++ b/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154.h @@ -192,6 +192,24 @@ void esp_ieee802154_get_extended_address(uint8_t *ext_addr); */ void esp_ieee802154_set_extended_address(const uint8_t *ext_addr); +/** + * @brief Get the device coordinator. + * + * @return + * - True The coordinator is enabled. + * - False The coordinator is disabled. + * + */ +bool esp_ieee802154_get_coordinator(void); + +/** + * @brief Set the device coordinator role. + * + * @param[in] enable The coordinator role to be set. + * + */ +void esp_ieee802154_set_coordinator(bool enable); + /** * @brief Get the auto frame pending mode. * diff --git a/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154_types.h b/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154_types.h index 14075631710..823e3cdcf3f 100644 --- a/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154_types.h +++ b/tools/sdk/esp32c3/include/ieee802154/include/esp_ieee802154_types.h @@ -62,6 +62,7 @@ typedef enum { ESP_IEEE802154_AUTO_PENDING_DISABLE, /*!< Frame pending bit always set to 1 in the ack to Data Request */ ESP_IEEE802154_AUTO_PENDING_ENABLE, /*!< Frame pending bit set to 1 if src address matches, in the ack to Data Request */ ESP_IEEE802154_AUTO_PENDING_ENHANCED, /*!< Frame pending bit set to 1 if src address matches, in all ack frames */ + ESP_IEEE802154_AUTO_PENDING_ZIGBEE, /*!< Frame pending bit set to 0 only if src address is short address and matches in table, in the ack to Data Request */ } esp_ieee802154_pending_mode_t; /** diff --git a/tools/sdk/esp32c3/include/log/include/esp_log.h b/tools/sdk/esp32c3/include/log/include/esp_log.h index 45fff0c8e47..0e3148f62dc 100644 --- a/tools/sdk/esp32c3/include/log/include/esp_log.h +++ b/tools/sdk/esp32c3/include/log/include/esp_log.h @@ -88,6 +88,9 @@ esp_log_level_t esp_log_level_get(const char* tag); * output to some other destination, such as file or network. Returns the original * log handler, which may be necessary to return output to the previous destination. * + * @note Please note that function callback here must be re-entrant as it can be + * invoked in parallel from multiple thread context. + * * @param func new Function used for output. Must have same signature as vprintf. * * @return func old Function used for output. diff --git a/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver.h b/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver.h index 39a58bbfa94..262ebf43d85 100644 --- a/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver.h +++ b/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver.h @@ -17,6 +17,10 @@ #include "sdkconfig.h" #include "lwip/ip_addr.h" +#ifdef __cplusplus +extern "C" { +#endif + typedef struct dhcps_state{ s16_t state; } dhcps_state; @@ -91,4 +95,8 @@ void dhcps_dns_setserver(const ip_addr_t *dnsserver); ip4_addr_t dhcps_dns_getserver(void); void dhcps_set_new_lease_cb(dhcps_cb_t cb); +#ifdef __cplusplus +} #endif + +#endif /* __DHCPS_H__ */ diff --git a/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver_options.h b/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver_options.h index 38d46f6bff2..31a67992831 100644 --- a/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver_options.h +++ b/tools/sdk/esp32c3/include/lwip/include/apps/dhcpserver/dhcpserver_options.h @@ -13,6 +13,9 @@ // limitations under the License. #pragma once +#ifdef __cplusplus +extern "C" { +#endif /** DHCP Options This macros are not part of the public dhcpserver.h interface. @@ -132,3 +135,7 @@ typedef enum DOMAIN_SEARCH = 119, CLASSLESS_ROUTE = 121, } dhcp_msg_option; + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/lwip/port/esp32/include/lwipopts.h b/tools/sdk/esp32c3/include/lwip/port/esp32/include/lwipopts.h index b6e526491f4..4bc2ad13960 100644 --- a/tools/sdk/esp32c3/include/lwip/port/esp32/include/lwipopts.h +++ b/tools/sdk/esp32c3/include/lwip/port/esp32/include/lwipopts.h @@ -978,6 +978,8 @@ #define LWIP_ND6_RDNSS_MAX_DNS_SERVERS CONFIG_LWIP_IPV6_RDNSS_MAX_DNS_SERVERS +#define LWIP_IPV6_DHCP6 CONFIG_LWIP_IPV6_DHCP6 + /* Enable all Espressif-only options */ #define ESP_LWIP 1 diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/assist_debug_reg.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/assist_debug_reg.h index a0c1e9c9d8c..2b13d1f5f41 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/assist_debug_reg.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/assist_debug_reg.h @@ -652,7 +652,7 @@ extern "C" { #define ASSIST_DEBUG_LOG_MEM_FULL_FLAG_V 0x1 #define ASSIST_DEBUG_LOG_MEM_FULL_FLAG_S 0 -#define ASSIST_DEBUG_C0RE_0_LASTPC_BEFORE_EXCEPTION_REG (DR_REG_ASSIST_DEBUG_BASE + 0x094) +#define ASSIST_DEBUG_CORE_0_LASTPC_BEFORE_EXCEPTION_REG (DR_REG_ASSIST_DEBUG_BASE + 0x094) /* ASSIST_DEBUG_CORE_0_LASTPC_BEFORE_EXC : RO ;bitpos:[31:0] ;default: 32'b0 ; */ /*description: */ #define ASSIST_DEBUG_CORE_0_LASTPC_BEFORE_EXC 0xFFFFFFFF @@ -660,7 +660,7 @@ extern "C" { #define ASSIST_DEBUG_CORE_0_LASTPC_BEFORE_EXC_V 0xFFFFFFFF #define ASSIST_DEBUG_CORE_0_LASTPC_BEFORE_EXC_S 0 -#define ASSIST_DEBUG_C0RE_0_DEBUG_MODE_REG (DR_REG_ASSIST_DEBUG_BASE + 0x098) +#define ASSIST_DEBUG_CORE_0_DEBUG_MODE_REG (DR_REG_ASSIST_DEBUG_BASE + 0x098) /* ASSIST_DEBUG_CORE_0_DEBUG_MODULE_ACTIVE : RO ;bitpos:[1] ;default: 1'b0 ; */ /*description: */ #define ASSIST_DEBUG_CORE_0_DEBUG_MODULE_ACTIVE (BIT(1)) diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_reg.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_reg.h index ddaff7285c6..aca7304f530 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_reg.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_reg.h @@ -141,12 +141,12 @@ extern "C" { #define EFUSE_DIS_ICACHE_M (BIT(8)) #define EFUSE_DIS_ICACHE_V 0x1 #define EFUSE_DIS_ICACHE_S 8 -/* EFUSE_DIS_RTC_RAM_BOOT : R/W ;bitpos:[7] ;default: 1'b0 ; */ -/*description: Set this bit to disable boot from RTC RAM.*/ -#define EFUSE_DIS_RTC_RAM_BOOT (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_M (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_V 0x1 -#define EFUSE_DIS_RTC_RAM_BOOT_S 7 +/* EFUSE_RPT4_RESERVED5 : R/W ;bitpos:[7] ;default: 1'b0 ; */ +/*description: Reserved.*/ +#define EFUSE_RPT4_RESERVED5 (BIT(7)) +#define EFUSE_RPT4_RESERVED5_M (BIT(7)) +#define EFUSE_RPT4_RESERVED5_V 0x1 +#define EFUSE_RPT4_RESERVED5_S 7 /* EFUSE_RD_DIS : R/W ;bitpos:[6:0] ;default: 7'h0 ; */ /*description: Set this bit to disable reading from BlOCK4-10.*/ #define EFUSE_RD_DIS 0x0000007F @@ -516,12 +516,12 @@ extern "C" { #define EFUSE_DIS_ICACHE_M (BIT(8)) #define EFUSE_DIS_ICACHE_V 0x1 #define EFUSE_DIS_ICACHE_S 8 -/* EFUSE_DIS_RTC_RAM_BOOT : RO ;bitpos:[7] ;default: 1'b0 ; */ -/*description: The value of DIS_RTC_RAM_BOOT.*/ -#define EFUSE_DIS_RTC_RAM_BOOT (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_M (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_V 0x1 -#define EFUSE_DIS_RTC_RAM_BOOT_S 7 +/* EFUSE_RPT4_RESERVED5 : RO ;bitpos:[7] ;default: 1'b0 ; */ +/*description: Reserved.*/ +#define EFUSE_RPT4_RESERVED5 (BIT(7)) +#define EFUSE_RPT4_RESERVED5_M (BIT(7)) +#define EFUSE_RPT4_RESERVED5_V 0x1 +#define EFUSE_RPT4_RESERVED5_S 7 /* EFUSE_RD_DIS : RO ;bitpos:[6:0] ;default: 7'h0 ; */ /*description: The value of RD_DIS.*/ #define EFUSE_RD_DIS 0x0000007F @@ -1486,12 +1486,12 @@ extern "C" { #define EFUSE_DIS_ICACHE_ERR_M (BIT(8)) #define EFUSE_DIS_ICACHE_ERR_V 0x1 #define EFUSE_DIS_ICACHE_ERR_S 8 -/* EFUSE_DIS_RTC_RAM_BOOT_ERR : RO ;bitpos:[7] ;default: 1'b0 ; */ -/*description: If DIS_RTC_RAM_BOOT is 1 then it indicates a programming error.*/ -#define EFUSE_DIS_RTC_RAM_BOOT_ERR (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_ERR_M (BIT(7)) -#define EFUSE_DIS_RTC_RAM_BOOT_ERR_V 0x1 -#define EFUSE_DIS_RTC_RAM_BOOT_ERR_S 7 +/* EFUSE_RPT4_RESERVED5_ERR : RO ;bitpos:[7] ;default: 1'b0 ; */ +/*description: Reserved..*/ +#define EFUSE_RPT4_RESERVED5_ERR (BIT(7)) +#define EFUSE_RPT4_RESERVED5_ERR_M (BIT(7)) +#define EFUSE_RPT4_RESERVED5_ERR_V 0x1 +#define EFUSE_RPT4_RESERVED5_ERR_S 7 /* EFUSE_RD_DIS_ERR : RO ;bitpos:[6:0] ;default: 7'h0 ; */ /*description: If any bit in RD_DIS is 1 then it indicates a programming error.*/ #define EFUSE_RD_DIS_ERR 0x0000007F @@ -1691,7 +1691,7 @@ extern "C" { #define EFUSE_DIS_DOWNLOAD_MODE_ERR_V 0x1 #define EFUSE_DIS_DOWNLOAD_MODE_ERR_S 0 -#define EFUSE_RD_REPEAT_ERR4_REG (DR_REG_EFUSE_BASE + 0x190) +#define EFUSE_RD_REPEAT_ERR4_REG (DR_REG_EFUSE_BASE + 0x18C) /* EFUSE_RPT4_RESERVED4_ERR : RO ;bitpos:[23:0] ;default: 24'h0 ; */ /*description: Reserved.*/ #define EFUSE_RPT4_RESERVED4_ERR 0x00FFFFFF diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_struct.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_struct.h index eed9c2544f0..24915ba8104 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_struct.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/efuse_struct.h @@ -22,7 +22,7 @@ typedef volatile struct efuse_dev_s { union { struct { uint32_t rd_dis: 7; /*Set this bit to disable reading from BlOCK4-10.*/ - uint32_t dis_rtc_ram_boot: 1; /*Set this bit to disable boot from RTC RAM.*/ + uint32_t rpt4_reserved5: 1; /*Reserved*/ uint32_t dis_icache: 1; /*Set this bit to disable Icache.*/ uint32_t dis_usb_jtag: 1; /*Set this bit to disable function of usb switch to jtag in module of usb device.*/ uint32_t dis_download_icache: 1; /*Set this bit to disable Icache in download mode (boot_mode[3:0] is 0 1 2 3 6 7).*/ @@ -106,7 +106,7 @@ typedef volatile struct efuse_dev_s { union { struct { uint32_t rd_dis: 7; /*The value of RD_DIS.*/ - uint32_t dis_rtc_ram_boot: 1; /*The value of DIS_RTC_RAM_BOOT.*/ + uint32_t rpt4_reserved5: 1; /*Reserved*/ uint32_t dis_icache: 1; /*The value of DIS_ICACHE.*/ uint32_t dis_usb_jtag: 1; /*The value of DIS_USB_JTAG.*/ uint32_t dis_download_icache: 1; /*The value of DIS_DOWNLOAD_ICACHE.*/ @@ -274,7 +274,7 @@ typedef volatile struct efuse_dev_s { union { struct { uint32_t rd_dis_err: 7; /*If any bit in RD_DIS is 1 then it indicates a programming error.*/ - uint32_t dis_rtc_ram_boot_err: 1; /*If DIS_RTC_RAM_BOOT is 1 then it indicates a programming error.*/ + uint32_t rpt4_reserved5_err: 1; /*Reserved.*/ uint32_t dis_icache_err: 1; /*If DIS_ICACHE is 1 then it indicates a programming error.*/ uint32_t dis_usb_jtag_err: 1; /*If DIS_USB_JTAG is 1 then it indicates a programming error.*/ uint32_t dis_download_icache: 1; /*If DIS_DOWNLOAD_ICACHE is 1 then it indicates a programming error.*/ @@ -342,7 +342,6 @@ typedef volatile struct efuse_dev_s { }; uint32_t val; } rd_repeat_err3; - uint32_t reserved_18c; union { struct { uint32_t rpt4_reserved4_err:24; /*Reserved.*/ @@ -350,6 +349,7 @@ typedef volatile struct efuse_dev_s { }; uint32_t val; } rd_repeat_err4; + uint32_t reserved_190; uint32_t reserved_194; uint32_t reserved_198; uint32_t reserved_19c; diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/gpio_sig_map.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/gpio_sig_map.h index 45be68b3e5c..61aa95a3c45 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/gpio_sig_map.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/gpio_sig_map.h @@ -53,26 +53,26 @@ #define GPIO_WLAN_PRIO_IDX 18 #define GPIO_BT_ACTIVE_IDX 19 #define GPIO_WLAN_ACTIVE_IDX 19 -#define BB_DIAG0_IDX 20 -#define BB_DIAG1_IDX 21 -#define BB_DIAG2_IDX 22 -#define BB_DIAG3_IDX 23 -#define BB_DIAG4_IDX 24 -#define BB_DIAG5_IDX 25 -#define BB_DIAG6_IDX 26 -#define BB_DIAG7_IDX 27 -#define BB_DIAG8_IDX 28 -#define BB_DIAG9_IDX 29 -#define BB_DIAG10_IDX 30 -#define BB_DIAG11_IDX 31 -#define BB_DIAG12_IDX 32 -#define BB_DIAG13_IDX 33 -#define BB_DIAG14_IDX 34 -#define BB_DIAG15_IDX 35 -#define BB_DIAG16_IDX 36 -#define BB_DIAG17_IDX 37 -#define BB_DIAG18_IDX 38 -#define BB_DIAG19_IDX 39 +#define CPU_GPIO_IN0_IDX 28 +#define CPU_GPIO_OUT0_IDX 28 +#define CPU_GPIO_IN1_IDX 29 +#define CPU_GPIO_OUT1_IDX 29 +#define CPU_GPIO_IN2_IDX 30 +#define CPU_GPIO_OUT2_IDX 30 +#define CPU_GPIO_IN3_IDX 31 +#define CPU_GPIO_OUT3_IDX 31 +#define CPU_GPIO_IN4_IDX 32 +#define CPU_GPIO_OUT4_IDX 32 +#define CPU_GPIO_IN5_IDX 33 +#define CPU_GPIO_OUT5_IDX 33 +#define CPU_GPIO_IN6_IDX 34 +#define CPU_GPIO_OUT6_IDX 34 +#define CPU_GPIO_IN7_IDX 35 +#define CPU_GPIO_OUT7_IDX 35 +#define USB_JTAG_TCK_OUT_IDX 36 +#define USB_JTAG_TMS_OUT_IDX 37 +#define USB_JTAG_TDI_OUT_IDX 38 +#define USB_JTAG_TDO_OUT_IDX 39 #define USB_EXTPHY_VP_IDX 40 #define USB_EXTPHY_OEN_IDX 40 #define USB_EXTPHY_VM_IDX 41 @@ -179,6 +179,7 @@ #define CLK_OUT_OUT2_IDX 124 #define CLK_OUT_OUT3_IDX 125 #define SPICS1_OUT_IDX 126 +#define USB_JTAG_TRST_OUT_IDX 127 #define SIG_GPIO_OUT_IDX 128 #define GPIO_MAP_DATE_IDX 0x2006130 #endif /* _SOC_GPIO_SIG_MAP_H_ */ diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/hwcrypto_reg.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/hwcrypto_reg.h index 68446273887..474b07faa3b 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/hwcrypto_reg.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/hwcrypto_reg.h @@ -133,6 +133,7 @@ #define HMAC_SET_MESSAGE_END_REG ((DR_REG_HMAC_BASE) + 0x58) #define HMAC_SET_RESULT_FINISH_REG ((DR_REG_HMAC_BASE) + 0x5c) #define HMAC_SET_INVALIDATE_JTAG_REG ((DR_REG_HMAC_BASE) + 0x60) +#define HMAC_INVALIDATE_JTAG BIT(0) #define HMAC_SET_INVALIDATE_DS_REG ((DR_REG_HMAC_BASE) + 0x64) #define HMAC_QUERY_ERROR_REG ((DR_REG_HMAC_BASE) + 0x68) #define HMAC_QUERY_BUSY_REG ((DR_REG_HMAC_BASE) + 0x6c) diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/reset_reasons.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/reset_reasons.h index 0bb99f5851b..c624619bb38 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/reset_reasons.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/reset_reasons.h @@ -52,6 +52,8 @@ typedef enum { RESET_REASON_SYS_SUPER_WDT = 0x12, // Super watch dog resets the digital core and rtc module RESET_REASON_SYS_CLK_GLITCH = 0x13, // Glitch on clock resets the digital core and rtc module RESET_REASON_CORE_EFUSE_CRC = 0x14, // eFuse CRC error resets the digital core + RESET_REASON_CORE_USB_UART = 0x15, // USB UART resets the digital core + RESET_REASON_CORE_USB_JTAG = 0x16, // USB JTAG resets the digital core RESET_REASON_CORE_PWR_GLITCH = 0x17, // Glitch on power resets the digital core } soc_reset_reason_t; diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/rtc.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/rtc.h index 3fda6cb8a77..40e6ec81d14 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/rtc.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/rtc.h @@ -206,7 +206,8 @@ typedef enum { typedef enum { RTC_CAL_RTC_MUX = 0, //!< Currently selected RTC SLOW_CLK RTC_CAL_8MD256 = 1, //!< Internal 8 MHz RC oscillator, divided by 256 - RTC_CAL_32K_XTAL = 2 //!< External 32 kHz XTAL + RTC_CAL_32K_XTAL = 2, //!< External 32 kHz XTAL + RTC_CAL_INTERNAL_OSC = 3 //!< Internal 150 kHz oscillator } rtc_cal_sel_t; /** diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/soc_caps.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/soc_caps.h index b30d095498e..0406c5665af 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/soc_caps.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/soc_caps.h @@ -6,6 +6,7 @@ #pragma once #define SOC_CPU_CORES_NUM 1 +#define SOC_DEDICATED_GPIO_SUPPORTED 1 #define SOC_GDMA_SUPPORTED 1 #define SOC_TWAI_SUPPORTED 1 #define SOC_BT_SUPPORTED 1 @@ -14,7 +15,9 @@ #define SOC_ASYNC_MEMCPY_SUPPORTED 1 #define SOC_USB_SERIAL_JTAG_SUPPORTED 1 #define SOC_TEMP_SENSOR_SUPPORTED 1 -#define SOC_FLASH_ENCRYPTION_XTS_AES 1 +#define SOC_FLASH_ENCRYPTION_XTS_AES 1 +#define SOC_XT_WDT_SUPPORTED 1 + /*-------------------------- COMMON CAPS ---------------------------------------*/ #define SOC_SUPPORTS_SECURE_DL_MODE 1 @@ -32,19 +35,30 @@ #define SOC_AES_SUPPORT_AES_256 (1) /*-------------------------- ADC CAPS -------------------------------*/ +/*!< SAR ADC Module*/ +#define SOC_ADC_ARBITER_SUPPORTED 1 +#define SOC_ADC_FILTER_SUPPORTED 1 +#define SOC_ADC_MONITOR_SUPPORTED 1 #define SOC_ADC_PERIPH_NUM (2) -#define SOC_ADC_PATT_LEN_MAX (16) #define SOC_ADC_CHANNEL_NUM(PERIPH_NUM) ((PERIPH_NUM==0)? 5 : 1) #define SOC_ADC_MAX_CHANNEL_NUM (5) -#define SOC_ADC_MAX_BITWIDTH (12) + +/*!< Digital */ +#define SOC_ADC_DIGI_CONTROLLER_NUM (1) +#define SOC_ADC_PATT_LEN_MAX (8) /*!< One pattern table, each contains 8 items. Each item takes 1 byte */ +#define SOC_ADC_DIGI_MAX_BITWIDTH (12) #define SOC_ADC_DIGI_FILTER_NUM (2) #define SOC_ADC_DIGI_MONITOR_NUM (2) -#define SOC_ADC_HW_CALIBRATION_V1 (1) /*!< support HW offset calibration */ -#define SOC_ADC_SUPPORT_DMA_MODE(PERIPH_NUM) 1 -//F_sample = F_digi_con / 2 / interval. F_digi_con = 5M for now. 30 <= interva <= 4095 +/*!< F_sample = F_digi_con / 2 / interval. F_digi_con = 5M for now. 30 <= interva <= 4095 */ #define SOC_ADC_SAMPLE_FREQ_THRES_HIGH 83333 #define SOC_ADC_SAMPLE_FREQ_THRES_LOW 611 -#define SOC_ADC_ARBITER_SUPPORTED 1 + +/*!< RTC */ +#define SOC_ADC_MAX_BITWIDTH (12) + +/*!< Calibration */ +#define SOC_ADC_CALIBRATION_V1_SUPPORTED (1) /*!< support HW offset calibration version 1*/ + /*-------------------------- APB BACKUP DMA CAPS -------------------------------*/ #define SOC_APB_BACKUP_DMA (1) @@ -95,6 +109,11 @@ // Support to configure sleep status #define SOC_GPIO_SUPPORT_SLP_SWITCH (1) +/*-------------------------- Dedicated GPIO CAPS -----------------------------*/ +#define SOC_DEDIC_GPIO_OUT_CHANNELS_NUM (8) /*!< 8 outward channels on each CPU core */ +#define SOC_DEDIC_GPIO_IN_CHANNELS_NUM (8) /*!< 8 inward channels on each CPU core */ +#define SOC_DEDIC_PERIPH_AUTO_ENABLE (1) /*!< The dedicated GPIO peripheral is enabled automatically */ + /*-------------------------- I2C CAPS ----------------------------------------*/ // ESP32-C3 have 2 I2C. #define SOC_I2C_NUM (1) diff --git a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/syscon_struct.h b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/syscon_struct.h index 4be6b7f791a..b8afdf6ec8b 100644 --- a/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/syscon_struct.h +++ b/tools/sdk/esp32c3/include/soc/esp32c3/include/soc/syscon_struct.h @@ -20,23 +20,23 @@ extern "C" { typedef volatile struct syscon_dev_s { union { struct { - uint32_t apb_ctrl_pre_div_cnt: 10; - uint32_t apb_ctrl_clk_320m_en: 1; - uint32_t clk_en: 1; - uint32_t apb_ctrl_rst_tick_cnt: 1; - uint32_t reserved13: 19; + uint32_t pre_div_cnt: 10; + uint32_t clk_320m_en: 1; + uint32_t clk_en: 1; + uint32_t rst_tick_cnt: 1; + uint32_t reserved13: 19; }; uint32_t val; - } apb_ctrl_sysclk_conf; + } sysclk_conf; union { struct { - uint32_t apb_ctrl_xtal_tick_num: 8; - uint32_t apb_ctrl_ck8m_tick_num: 8; - uint32_t apb_ctrl_tick_enable: 1; - uint32_t reserved17: 15; + uint32_t xtal_tick_num: 8; + uint32_t ck8m_tick_num: 8; + uint32_t tick_enable: 1; + uint32_t reserved17: 15; }; uint32_t val; - } apb_ctrl_tick_conf; + } tick_conf; union { struct { uint32_t clk20_oen: 1; @@ -53,7 +53,7 @@ typedef volatile struct syscon_dev_s { uint32_t reserved11: 21; }; uint32_t val; - } apb_ctrl_clk_out_en; + } clk_out_en; uint32_t wifi_bb_cfg; /**/ uint32_t wifi_bb_cfg_2; /**/ uint32_t wifi_clk_en; /**/ @@ -161,7 +161,7 @@ typedef volatile struct syscon_dev_s { uint32_t reserved1: 31; }; uint32_t val; - } apb_ctrl_sdio_ctrl; + } sdio_ctrl; union { struct { uint32_t redcy_sig0: 31; @@ -472,7 +472,7 @@ typedef volatile struct syscon_dev_s { uint32_t reserved_3f0; uint32_t reserved_3f4; uint32_t reserved_3f8; - uint32_t apb_ctrl_date; /*Version control*/ + uint32_t date; /*Version control*/ } syscon_dev_t; extern syscon_dev_t SYSCON; #ifdef __cplusplus diff --git a/tools/sdk/esp32c3/include/soc/include/soc/adc_periph.h b/tools/sdk/esp32c3/include/soc/include/soc/adc_periph.h index 796ea18e906..437d8ad6e6a 100644 --- a/tools/sdk/esp32c3/include/soc/include/soc/adc_periph.h +++ b/tools/sdk/esp32c3/include/soc/include/soc/adc_periph.h @@ -18,7 +18,7 @@ #include "soc/soc_caps.h" #include "soc/syscon_struct.h" -#if SOC_ADC_SUPPORT_RTC_CTRL +#if SOC_ADC_RTC_CTRL_SUPPORTED #include "soc/sens_reg.h" #include "soc/sens_struct.h" #endif diff --git a/tools/sdk/esp32c3/include/soc/include/soc/i2s_periph.h b/tools/sdk/esp32c3/include/soc/include/soc/i2s_periph.h index 59e31674d56..167c84700fd 100644 --- a/tools/sdk/esp32c3/include/soc/include/soc/i2s_periph.h +++ b/tools/sdk/esp32c3/include/soc/include/soc/i2s_periph.h @@ -28,12 +28,20 @@ extern "C" { */ typedef struct { const uint8_t mck_out_sig; - const uint8_t tx_bck_sig; - const uint8_t rx_bck_sig; - const uint8_t tx_ws_sig; - const uint8_t rx_ws_sig; + + const uint8_t m_tx_bck_sig; + const uint8_t m_rx_bck_sig; + const uint8_t m_tx_ws_sig; + const uint8_t m_rx_ws_sig; + + const uint8_t s_tx_bck_sig; + const uint8_t s_rx_bck_sig; + const uint8_t s_tx_ws_sig; + const uint8_t s_rx_ws_sig; + const uint8_t data_out_sig; const uint8_t data_in_sig; + const uint8_t irq; const periph_module_t module; } i2s_signal_conn_t; diff --git a/tools/sdk/esp32c3/include/soc/include/soc/rtc_io_periph.h b/tools/sdk/esp32c3/include/soc/include/soc/rtc_io_periph.h index e9309771c63..618b64cd8f7 100644 --- a/tools/sdk/esp32c3/include/soc/include/soc/rtc_io_periph.h +++ b/tools/sdk/esp32c3/include/soc/include/soc/rtc_io_periph.h @@ -27,7 +27,7 @@ #include "soc/rtc_cntl_reg.h" #include "soc/rtc_cntl_struct.h" -#if SOC_ADC_SUPPORT_RTC_CTRL +#if SOC_ADC_RTC_CTRL_SUPPORTED #include "soc/sens_struct.h" #endif diff --git a/tools/sdk/esp32c3/include/soc/include/soc/usb_phy_periph.h b/tools/sdk/esp32c3/include/soc/include/soc/usb_phy_periph.h new file mode 100644 index 00000000000..802d1720cec --- /dev/null +++ b/tools/sdk/esp32c3/include/soc/include/soc/usb_phy_periph.h @@ -0,0 +1,35 @@ +/* + * SPDX-FileCopyrightText: 2015-2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + +#pragma once +#include +#include "soc/soc_caps.h" +#include "soc/periph_defs.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* + Stores a bunch of USB-peripheral data. +*/ +typedef struct { + const uint8_t extphy_vp_in; + const uint8_t extphy_vm_in; + const uint8_t extphy_rcv_in; + const uint8_t extphy_oen_out; + const uint8_t extphy_vpo_out; + const uint8_t extphy_vmo_out; + const uint8_t extphy_suspend_in; + const uint8_t extphy_speed_in; + const periph_module_t module; +} usb_phy_signal_conn_t; + +extern const usb_phy_signal_conn_t usb_phy_periph_signal; + +#ifdef __cplusplus +} +#endif diff --git a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash/spi_flash_defs.h b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash/spi_flash_defs.h index cf26fda1486..1ff0bfdea5c 100644 --- a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash/spi_flash_defs.h +++ b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash/spi_flash_defs.h @@ -68,3 +68,7 @@ #define SPI_FLASH_FASTRD_DUMMY_BITLEN 8 #define SPI_FLASH_SLOWRD_ADDR_BITLEN 24 #define SPI_FLASH_SLOWRD_DUMMY_BITLEN 0 +#define SPI_FLASH_OPISTR_ADDR_BITLEN 32 +#define SPI_FLASH_OPISTR_DUMMY_BITLEN 20 +#define SPI_FLASH_OPIDTR_ADDR_BITLEN 32 +#define SPI_FLASH_OPIDTR_DUMMY_BITLEN 40 diff --git a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_driver.h b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_driver.h index 9a143d84d2e..d2ef25bf6de 100644 --- a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_driver.h +++ b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_driver.h @@ -206,6 +206,11 @@ struct spi_flash_chip_t { * Get the capabilities of the flash chip. See SPI_FLASH_CHIP_CAP_* macros as reference. */ spi_flash_caps_t (*get_chip_caps)(esp_flash_t *chip); + + /** + * Configure the host registers to use the specified read mode set in the ``chip->read_mode``. + */ + esp_err_t (*config_host_io_mode)(esp_flash_t *chip, uint32_t flags); }; /* Pointer to an array of pointers to all known drivers for flash chips. This array is used diff --git a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_generic.h b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_generic.h index 9e99f73e44b..019a6966a40 100644 --- a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_generic.h +++ b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_generic.h @@ -370,14 +370,15 @@ esp_err_t spi_flash_common_set_io_mode(esp_flash_t *chip, esp_flash_wrsr_func_t * transactions. Also prepare the command to be sent in read functions. * * @param chip Pointer to SPI flash chip to use. If NULL, esp_flash_default_chip is substituted. - * @param addr_32bit Whether 32 bit commands will be used (Currently only W25Q256 and GD25Q256 are supported) + * @param flags Special rules to configure io mode, (i.e. Whether 32 bit commands will be used (Currently only W25Q256 and GD25Q256 are supported)) * * @return * - ESP_OK if success * - ESP_ERR_FLASH_NOT_INITIALISED if chip not initialized properly * - or other error passed from the ``configure_host_mode`` function of host driver */ -esp_err_t spi_flash_chip_generic_config_host_io_mode(esp_flash_t *chip, bool addr_32bit); +esp_err_t spi_flash_chip_generic_config_host_io_mode(esp_flash_t *chip, uint32_t flags); +#define SPI_FLASH_CONFIG_IO_MODE_32B_ADDR BIT(0) /** * @brief Handle explicit yield requests @@ -396,5 +397,15 @@ esp_err_t spi_flash_chip_generic_yield(esp_flash_t* chip, uint32_t wip); */ esp_err_t spi_flash_chip_generic_suspend_cmd_conf(esp_flash_t *chip); +/** + * + * @brief Read the chip unique ID unsupported function. + * + * @param chip Pointer to SPI flash chip to use. + * @param flash_unique_id Pointer to store output unique id (Although this function is an unsupported function, but the parameter should be kept for the consistence of the function pointer). + * @return Always ESP_ERR_NOT_SUPPORTED. + */ +esp_err_t spi_flash_chip_generic_read_unique_id_none(esp_flash_t *chip, uint64_t* flash_unique_id); + /// Default timeout configuration used by most chips -const flash_chip_op_timeout_t spi_flash_chip_generic_timeout; +extern const flash_chip_op_timeout_t spi_flash_chip_generic_timeout; diff --git a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_mxic.h b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_mxic.h index f998c1564e5..201ad496e2a 100644 --- a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_mxic.h +++ b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_chip_mxic.h @@ -25,3 +25,10 @@ * is not found. */ extern const spi_flash_chip_t esp_flash_chip_mxic; + +/** + * MXIC OPI flash chip_drv, uses all the above functions for its operations. In + * default autodetection, this is used as a catchall if a more specific chip_drv + * is not found. + */ +extern const spi_flash_chip_t esp_flash_chip_mxic_opi; diff --git a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_private.h b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_private.h index 1a8ad6f231c..9d822fb9475 100644 --- a/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_private.h +++ b/tools/sdk/esp32c3/include/spi_flash/include/spi_flash_private.h @@ -26,23 +26,13 @@ #elif CONFIG_IDF_TARGET_ESP32S3 #include "esp32s3/rom/spi_flash.h" #endif +#include "esp_flash.h" +#include "hal/spi_flash_hal.h" #ifdef __cplusplus extern "C" { #endif -/** - * This struct provide MSPI Flash necessary timing related config - */ -typedef struct { - uint8_t flash_clk_div; /*!< clock divider of Flash module. */ - uint8_t flash_extra_dummy; /*!< timing required extra dummy length for Flash */ - bool flash_setup_en; /*!< SPI0/1 Flash setup enable or not */ - uint8_t flash_setup_time; /*!< SPI0/1 Flash setup time. This value should be set to register directly */ - bool flash_hold_en; /*!< SPI0/1 Flash hold enable or not */ - uint8_t flash_hold_time; /*!< SPI0/1 Flash hold time. This value should be set to register directly */ -} spi_timing_flash_config_t; - /** * @brief Register ROM functions and init flash device registers to make use of octal flash */ @@ -82,10 +72,21 @@ void esp_mspi_pin_init(void); void spi_flash_set_rom_required_regs(void); /** - * @brief Get MSPI Flash necessary timing related config - * @param config see `spi_timing_flash_config_t` + * @brief Initialize main flash + * @param chip Pointer to main SPI flash(SPI1 CS0) chip to use.. + */ +esp_err_t esp_flash_init_main(esp_flash_t *chip); + +/** + * @brief Should be only used by SPI1 Flash driver to know the necessary timing registers + * @param out_timing_config Pointer to timing_tuning parameters. + */ +void spi_timing_get_flash_timing_param(spi_flash_hal_timing_config_t *out_timing_config); + +/** + * @brief Judge if the flash in tuned */ -void spi_timing_get_flash_regs(spi_timing_flash_config_t *config); +bool spi_timine_config_flash_is_tuned(void); #ifdef __cplusplus } diff --git a/tools/sdk/esp32c3/ld/libbtdm_app.a b/tools/sdk/esp32c3/ld/libbtdm_app.a index 35adc032d7f..6c0defb2e79 100644 Binary files a/tools/sdk/esp32c3/ld/libbtdm_app.a and b/tools/sdk/esp32c3/ld/libbtdm_app.a differ diff --git a/tools/sdk/esp32c3/ld/memory.ld b/tools/sdk/esp32c3/ld/memory.ld index 3267ab1f551..250e0796cbc 100644 --- a/tools/sdk/esp32c3/ld/memory.ld +++ b/tools/sdk/esp32c3/ld/memory.ld @@ -1,3 +1,8 @@ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ /** * ESP32-C3 Linker Script Memory Layout * This file describes the memory layout (memory blocks) by virtual memory addresses. @@ -11,6 +16,17 @@ */ /* List of deprecated options */ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ +/* CPU instruction prefetch padding size for flash mmap scenario */ +_esp_flash_mmap_prefetch_pad_size = 16; +/* CPU instruction prefetch padding size for memory protection scenario */ +_esp_memprot_prefetch_pad_size = 16; +/* Memory alignment size for PMS */ +_esp_memprot_align_size = 512; MEMORY { /** diff --git a/tools/sdk/esp32c3/ld/sections.ld b/tools/sdk/esp32c3/ld/sections.ld index bd3cbd95a22..2338ee8b467 100644 --- a/tools/sdk/esp32c3/ld/sections.ld +++ b/tools/sdk/esp32c3/ld/sections.ld @@ -2,6 +2,12 @@ /* Espressif IoT Development Framework Linker Script */ /* Generated from: /home/runner/work/esp32-arduino-lib-builder/esp32-arduino-lib-builder/esp-idf/components/esp_system/ld/esp32c3/sections.ld.in */ +/* + * SPDX-FileCopyrightText: 2021 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Apache-2.0 + */ + /* Default entry point */ ENTRY(call_start_cpu0); @@ -305,8 +311,8 @@ SECTIONS _bss_start = ABSOLUTE(.); *(.bss .bss.*) - *(.ext_ram.bss .ext_ram.bss.*) *(.dynbss .dynsbss .gnu.linkonce.b .gnu.linkonce.b.* .gnu.linkonce.sb .gnu.linkonce.sb.* .gnu.linkonce.sb2 .gnu.linkonce.sb2.* .sbss .sbss.* .sbss2 .sbss2.* .scommon .share.mem) + *(.ext_ram.bss .ext_ram.bss.*) *(COMMON) _bt_bss_start = ABSOLUTE(.); *libbt.a:(.bss .bss.* COMMON) @@ -371,7 +377,7 @@ SECTIONS * safe access to up to 16 bytes after the last real instruction, add * dummy bytes to ensure this */ - . += 16; + . += _esp_flash_mmap_prefetch_pad_size; _text_end = ABSOLUTE(.); _instruction_reserved_end = ABSOLUTE(.); @@ -515,9 +521,9 @@ SECTIONS /* Marks the end of IRAM code segment */ .iram0.text_end (NOLOAD) : { - /* C3 memprot requires 16B padding for possible CPU prefetch and 512B alignment for PMS split lines */ - . += 16; - . = ALIGN (0x200); + /* ESP32-C3 memprot requires 16B padding for possible CPU prefetch and 512B alignment for PMS split lines */ + . += _esp_memprot_prefetch_pad_size; + . = ALIGN(_esp_memprot_align_size); /* iram_end_test section exists for use by memprot unit tests only */ *(.iram_end_test) _iram_text_end = ABSOLUTE(.); diff --git a/tools/sdk/esp32c3/lib/libapp_trace.a b/tools/sdk/esp32c3/lib/libapp_trace.a index 9144eabf73b..f41ecffbefc 100644 Binary files a/tools/sdk/esp32c3/lib/libapp_trace.a and b/tools/sdk/esp32c3/lib/libapp_trace.a differ diff --git a/tools/sdk/esp32c3/lib/libapp_update.a b/tools/sdk/esp32c3/lib/libapp_update.a index 8248ea09f97..a76a5a0d19e 100644 Binary files a/tools/sdk/esp32c3/lib/libapp_update.a and b/tools/sdk/esp32c3/lib/libapp_update.a differ diff --git a/tools/sdk/esp32c3/lib/libasio.a b/tools/sdk/esp32c3/lib/libasio.a index acb17945979..e501be2ec82 100644 Binary files a/tools/sdk/esp32c3/lib/libasio.a and b/tools/sdk/esp32c3/lib/libasio.a differ diff --git a/tools/sdk/esp32c3/lib/libbootloader_support.a b/tools/sdk/esp32c3/lib/libbootloader_support.a index 82311904844..8dee3407a13 100644 Binary files a/tools/sdk/esp32c3/lib/libbootloader_support.a and b/tools/sdk/esp32c3/lib/libbootloader_support.a differ diff --git a/tools/sdk/esp32c3/lib/libbt.a b/tools/sdk/esp32c3/lib/libbt.a index 75bc3b96588..97808822530 100644 Binary files a/tools/sdk/esp32c3/lib/libbt.a and b/tools/sdk/esp32c3/lib/libbt.a differ diff --git a/tools/sdk/esp32c3/lib/libcoap.a b/tools/sdk/esp32c3/lib/libcoap.a index a7fbdadf34a..407310ba1cb 100644 Binary files a/tools/sdk/esp32c3/lib/libcoap.a and b/tools/sdk/esp32c3/lib/libcoap.a differ diff --git a/tools/sdk/esp32c3/lib/libconsole.a b/tools/sdk/esp32c3/lib/libconsole.a index 9285a1dd177..91bd32add2d 100644 Binary files a/tools/sdk/esp32c3/lib/libconsole.a and b/tools/sdk/esp32c3/lib/libconsole.a differ diff --git a/tools/sdk/esp32c3/lib/libcxx.a b/tools/sdk/esp32c3/lib/libcxx.a index 71a017a4c07..9617dd86b74 100644 Binary files a/tools/sdk/esp32c3/lib/libcxx.a and b/tools/sdk/esp32c3/lib/libcxx.a differ diff --git a/tools/sdk/esp32c3/lib/libdriver.a b/tools/sdk/esp32c3/lib/libdriver.a index 3ad836e793f..71809d7ec58 100644 Binary files a/tools/sdk/esp32c3/lib/libdriver.a and b/tools/sdk/esp32c3/lib/libdriver.a differ diff --git a/tools/sdk/esp32c3/lib/libefuse.a b/tools/sdk/esp32c3/lib/libefuse.a index 6311688ed6b..f4bb53d7dae 100644 Binary files a/tools/sdk/esp32c3/lib/libefuse.a and b/tools/sdk/esp32c3/lib/libefuse.a differ diff --git a/tools/sdk/esp32c3/lib/libesp-tls.a b/tools/sdk/esp32c3/lib/libesp-tls.a index 9e684a457dd..4e304a6646f 100644 Binary files a/tools/sdk/esp32c3/lib/libesp-tls.a and b/tools/sdk/esp32c3/lib/libesp-tls.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_adc_cal.a b/tools/sdk/esp32c3/lib/libesp_adc_cal.a index 8da278a789e..757dbdaf9da 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_adc_cal.a and b/tools/sdk/esp32c3/lib/libesp_adc_cal.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_common.a b/tools/sdk/esp32c3/lib/libesp_common.a index 541695d5461..577a8884b7f 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_common.a and b/tools/sdk/esp32c3/lib/libesp_common.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_eth.a b/tools/sdk/esp32c3/lib/libesp_eth.a index 73097c63d6b..457368b2747 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_eth.a and b/tools/sdk/esp32c3/lib/libesp_eth.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_event.a b/tools/sdk/esp32c3/lib/libesp_event.a index b8d86de6e89..eb12ef2bb70 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_event.a and b/tools/sdk/esp32c3/lib/libesp_event.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_gdbstub.a b/tools/sdk/esp32c3/lib/libesp_gdbstub.a index b3bb92dbb8e..e7c39833d73 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_gdbstub.a and b/tools/sdk/esp32c3/lib/libesp_gdbstub.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_hid.a b/tools/sdk/esp32c3/lib/libesp_hid.a index faf958a742f..f976d5ab228 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_hid.a and b/tools/sdk/esp32c3/lib/libesp_hid.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_http_client.a b/tools/sdk/esp32c3/lib/libesp_http_client.a index f7c403487f0..f82ad10086d 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_http_client.a and b/tools/sdk/esp32c3/lib/libesp_http_client.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_http_server.a b/tools/sdk/esp32c3/lib/libesp_http_server.a index ad74c5b16b7..78a0206aab2 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_http_server.a and b/tools/sdk/esp32c3/lib/libesp_http_server.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_https_ota.a b/tools/sdk/esp32c3/lib/libesp_https_ota.a index 02a5571f815..e1702191f75 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_https_ota.a and b/tools/sdk/esp32c3/lib/libesp_https_ota.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_https_server.a b/tools/sdk/esp32c3/lib/libesp_https_server.a index 1e791414abb..41c852b2f76 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_https_server.a and b/tools/sdk/esp32c3/lib/libesp_https_server.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_hw_support.a b/tools/sdk/esp32c3/lib/libesp_hw_support.a index c3c03eff307..441d8231622 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_hw_support.a and b/tools/sdk/esp32c3/lib/libesp_hw_support.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_lcd.a b/tools/sdk/esp32c3/lib/libesp_lcd.a index e1d0bd3052a..d5f9a5d15a7 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_lcd.a and b/tools/sdk/esp32c3/lib/libesp_lcd.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_littlefs.a b/tools/sdk/esp32c3/lib/libesp_littlefs.a index 1d3bac05161..10ece18e6f5 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_littlefs.a and b/tools/sdk/esp32c3/lib/libesp_littlefs.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_local_ctrl.a b/tools/sdk/esp32c3/lib/libesp_local_ctrl.a index 27167e63690..79208e5d357 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_local_ctrl.a and b/tools/sdk/esp32c3/lib/libesp_local_ctrl.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_netif.a b/tools/sdk/esp32c3/lib/libesp_netif.a index 6599b28ba4c..3deef9ca7dc 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_netif.a and b/tools/sdk/esp32c3/lib/libesp_netif.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_phy.a b/tools/sdk/esp32c3/lib/libesp_phy.a index d30c9b6f16b..b2b9885f59f 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_phy.a and b/tools/sdk/esp32c3/lib/libesp_phy.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_pm.a b/tools/sdk/esp32c3/lib/libesp_pm.a index ae5314eb25b..f32146b8ca0 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_pm.a and b/tools/sdk/esp32c3/lib/libesp_pm.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_ringbuf.a b/tools/sdk/esp32c3/lib/libesp_ringbuf.a index 4455c0ebd9a..d08c234dc5b 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_ringbuf.a and b/tools/sdk/esp32c3/lib/libesp_ringbuf.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_serial_slave_link.a b/tools/sdk/esp32c3/lib/libesp_serial_slave_link.a index 33b53cb8356..3a5cbd2b6ad 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_serial_slave_link.a and b/tools/sdk/esp32c3/lib/libesp_serial_slave_link.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_system.a b/tools/sdk/esp32c3/lib/libesp_system.a index cba9a1c3868..f8421329011 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_system.a and b/tools/sdk/esp32c3/lib/libesp_system.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_timer.a b/tools/sdk/esp32c3/lib/libesp_timer.a index c484b8b23e0..d74a2ac003b 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_timer.a and b/tools/sdk/esp32c3/lib/libesp_timer.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_websocket_client.a b/tools/sdk/esp32c3/lib/libesp_websocket_client.a index a68a058e0d8..d02f65a06fa 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_websocket_client.a and b/tools/sdk/esp32c3/lib/libesp_websocket_client.a differ diff --git a/tools/sdk/esp32c3/lib/libesp_wifi.a b/tools/sdk/esp32c3/lib/libesp_wifi.a index 377f8ce14a9..3a89f878c94 100644 Binary files a/tools/sdk/esp32c3/lib/libesp_wifi.a and b/tools/sdk/esp32c3/lib/libesp_wifi.a differ diff --git a/tools/sdk/esp32c3/lib/libespcoredump.a b/tools/sdk/esp32c3/lib/libespcoredump.a index 5d953c1c258..4af35b8b809 100644 Binary files a/tools/sdk/esp32c3/lib/libespcoredump.a and b/tools/sdk/esp32c3/lib/libespcoredump.a differ diff --git a/tools/sdk/esp32c3/lib/libfatfs.a b/tools/sdk/esp32c3/lib/libfatfs.a index bd49d0a91a5..86f197e368c 100644 Binary files a/tools/sdk/esp32c3/lib/libfatfs.a and b/tools/sdk/esp32c3/lib/libfatfs.a differ diff --git a/tools/sdk/esp32c3/lib/libfreemodbus.a b/tools/sdk/esp32c3/lib/libfreemodbus.a index 536c8b04177..b46ecaac145 100644 Binary files a/tools/sdk/esp32c3/lib/libfreemodbus.a and b/tools/sdk/esp32c3/lib/libfreemodbus.a differ diff --git a/tools/sdk/esp32c3/lib/libfreertos.a b/tools/sdk/esp32c3/lib/libfreertos.a index c2d3e021758..ac3c0fd50d1 100644 Binary files a/tools/sdk/esp32c3/lib/libfreertos.a and b/tools/sdk/esp32c3/lib/libfreertos.a differ diff --git a/tools/sdk/esp32c3/lib/libhal.a b/tools/sdk/esp32c3/lib/libhal.a index f62f1ef10c3..12ad247f09c 100644 Binary files a/tools/sdk/esp32c3/lib/libhal.a and b/tools/sdk/esp32c3/lib/libhal.a differ diff --git a/tools/sdk/esp32c3/lib/libheap.a b/tools/sdk/esp32c3/lib/libheap.a index 6e16a4b4a4e..240bbab74e0 100644 Binary files a/tools/sdk/esp32c3/lib/libheap.a and b/tools/sdk/esp32c3/lib/libheap.a differ diff --git a/tools/sdk/esp32c3/lib/liblog.a b/tools/sdk/esp32c3/lib/liblog.a index b7dfcf458d2..4be299b20b5 100644 Binary files a/tools/sdk/esp32c3/lib/liblog.a and b/tools/sdk/esp32c3/lib/liblog.a differ diff --git a/tools/sdk/esp32c3/lib/liblwip.a b/tools/sdk/esp32c3/lib/liblwip.a index d011a95f195..668266754ba 100644 Binary files a/tools/sdk/esp32c3/lib/liblwip.a and b/tools/sdk/esp32c3/lib/liblwip.a differ diff --git a/tools/sdk/esp32c3/lib/libmbedcrypto.a b/tools/sdk/esp32c3/lib/libmbedcrypto.a index 96027a5bcdd..b1cb253b4d7 100644 Binary files a/tools/sdk/esp32c3/lib/libmbedcrypto.a and b/tools/sdk/esp32c3/lib/libmbedcrypto.a differ diff --git a/tools/sdk/esp32c3/lib/libmbedtls.a b/tools/sdk/esp32c3/lib/libmbedtls.a index f386b4acb69..3abdde11dd3 100644 Binary files a/tools/sdk/esp32c3/lib/libmbedtls.a and b/tools/sdk/esp32c3/lib/libmbedtls.a differ diff --git a/tools/sdk/esp32c3/lib/libmdns.a b/tools/sdk/esp32c3/lib/libmdns.a index f44a018b8c5..b3df4d78b13 100644 Binary files a/tools/sdk/esp32c3/lib/libmdns.a and b/tools/sdk/esp32c3/lib/libmdns.a differ diff --git a/tools/sdk/esp32c3/lib/libmqtt.a b/tools/sdk/esp32c3/lib/libmqtt.a index e37684518c5..7b2acfde2a4 100644 Binary files a/tools/sdk/esp32c3/lib/libmqtt.a and b/tools/sdk/esp32c3/lib/libmqtt.a differ diff --git a/tools/sdk/esp32c3/lib/libnewlib.a b/tools/sdk/esp32c3/lib/libnewlib.a index 3c9701f5c33..e0ebeacbfd1 100644 Binary files a/tools/sdk/esp32c3/lib/libnewlib.a and b/tools/sdk/esp32c3/lib/libnewlib.a differ diff --git a/tools/sdk/esp32c3/lib/libnvs_flash.a b/tools/sdk/esp32c3/lib/libnvs_flash.a index 4ca33b223a6..72bb887799b 100644 Binary files a/tools/sdk/esp32c3/lib/libnvs_flash.a and b/tools/sdk/esp32c3/lib/libnvs_flash.a differ diff --git a/tools/sdk/esp32c3/lib/libopenssl.a b/tools/sdk/esp32c3/lib/libopenssl.a index b4571402b7e..4019e41f7a4 100644 Binary files a/tools/sdk/esp32c3/lib/libopenssl.a and b/tools/sdk/esp32c3/lib/libopenssl.a differ diff --git a/tools/sdk/esp32c3/lib/libprotocomm.a b/tools/sdk/esp32c3/lib/libprotocomm.a index 6525c0f5d14..b604bd05cd1 100644 Binary files a/tools/sdk/esp32c3/lib/libprotocomm.a and b/tools/sdk/esp32c3/lib/libprotocomm.a differ diff --git a/tools/sdk/esp32c3/lib/libpthread.a b/tools/sdk/esp32c3/lib/libpthread.a index a926b06ffb3..b16b6ff4e64 100644 Binary files a/tools/sdk/esp32c3/lib/libpthread.a and b/tools/sdk/esp32c3/lib/libpthread.a differ diff --git a/tools/sdk/esp32c3/lib/libsdmmc.a b/tools/sdk/esp32c3/lib/libsdmmc.a index e375b4a7118..04cbb827fc5 100644 Binary files a/tools/sdk/esp32c3/lib/libsdmmc.a and b/tools/sdk/esp32c3/lib/libsdmmc.a differ diff --git a/tools/sdk/esp32c3/lib/libsoc.a b/tools/sdk/esp32c3/lib/libsoc.a index c38615ee5b9..77e18e1335a 100644 Binary files a/tools/sdk/esp32c3/lib/libsoc.a and b/tools/sdk/esp32c3/lib/libsoc.a differ diff --git a/tools/sdk/esp32c3/lib/libspi_flash.a b/tools/sdk/esp32c3/lib/libspi_flash.a index 86901b0f97f..ac3b0ee32af 100644 Binary files a/tools/sdk/esp32c3/lib/libspi_flash.a and b/tools/sdk/esp32c3/lib/libspi_flash.a differ diff --git a/tools/sdk/esp32c3/lib/libspiffs.a b/tools/sdk/esp32c3/lib/libspiffs.a index efd95033b3c..120571b2b86 100644 Binary files a/tools/sdk/esp32c3/lib/libspiffs.a and b/tools/sdk/esp32c3/lib/libspiffs.a differ diff --git a/tools/sdk/esp32c3/lib/libtcp_transport.a b/tools/sdk/esp32c3/lib/libtcp_transport.a index 0a8077799df..42d386c8e1a 100644 Binary files a/tools/sdk/esp32c3/lib/libtcp_transport.a and b/tools/sdk/esp32c3/lib/libtcp_transport.a differ diff --git a/tools/sdk/esp32c3/lib/libtcpip_adapter.a b/tools/sdk/esp32c3/lib/libtcpip_adapter.a index 4d738ae96e1..316d8562b49 100644 Binary files a/tools/sdk/esp32c3/lib/libtcpip_adapter.a and b/tools/sdk/esp32c3/lib/libtcpip_adapter.a differ diff --git a/tools/sdk/esp32c3/lib/libunity.a b/tools/sdk/esp32c3/lib/libunity.a index 9d9d59c9e10..d35d93ca03f 100644 Binary files a/tools/sdk/esp32c3/lib/libunity.a and b/tools/sdk/esp32c3/lib/libunity.a differ diff --git a/tools/sdk/esp32c3/lib/libvfs.a b/tools/sdk/esp32c3/lib/libvfs.a index 5c1d33958b1..4b644d301c0 100644 Binary files a/tools/sdk/esp32c3/lib/libvfs.a and b/tools/sdk/esp32c3/lib/libvfs.a differ diff --git a/tools/sdk/esp32c3/lib/libwear_levelling.a b/tools/sdk/esp32c3/lib/libwear_levelling.a index ad320d39a55..8e320e50db7 100644 Binary files a/tools/sdk/esp32c3/lib/libwear_levelling.a and b/tools/sdk/esp32c3/lib/libwear_levelling.a differ diff --git a/tools/sdk/esp32c3/lib/libwifi_provisioning.a b/tools/sdk/esp32c3/lib/libwifi_provisioning.a index 3ac89515c37..08e7562e415 100644 Binary files a/tools/sdk/esp32c3/lib/libwifi_provisioning.a and b/tools/sdk/esp32c3/lib/libwifi_provisioning.a differ diff --git a/tools/sdk/esp32c3/lib/libwpa_supplicant.a b/tools/sdk/esp32c3/lib/libwpa_supplicant.a index 962bfd4ef79..60617dc9981 100644 Binary files a/tools/sdk/esp32c3/lib/libwpa_supplicant.a and b/tools/sdk/esp32c3/lib/libwpa_supplicant.a differ diff --git a/tools/sdk/esp32c3/sdkconfig b/tools/sdk/esp32c3/sdkconfig index a2439f97019..85edbebed07 100644 --- a/tools/sdk/esp32c3/sdkconfig +++ b/tools/sdk/esp32c3/sdkconfig @@ -234,19 +234,10 @@ CONFIG_APPTRACE_LOCK_ENABLE=y # Bluetooth # CONFIG_BT_ENABLED=y -CONFIG_BT_CTRL_ESP32C3=y CONFIG_BT_SOC_SUPPORT_5_0=y -CONFIG_BTDM_CTRL_BR_EDR_SCO_DATA_PATH_EFF=0 -CONFIG_BTDM_CTRL_PCM_ROLE_EFF=0 -CONFIG_BTDM_CTRL_PCM_POLAR_EFF=0 -CONFIG_BTDM_CTRL_BLE_MAX_CONN_EFF=0 -CONFIG_BTDM_CTRL_BR_EDR_MAX_ACL_CONN_EFF=0 -CONFIG_BTDM_CTRL_BR_EDR_MAX_SYNC_CONN_EFF=0 -CONFIG_BTDM_CTRL_PINNED_TO_CORE=0 -CONFIG_BTDM_BLE_SLEEP_CLOCK_ACCURACY_INDEX_EFF=1 # -# Bluetooth controller(ESP32C3 Bluetooth Low Energy) +# Bluetooth controller # CONFIG_BT_CTRL_MODE_EFF=1 CONFIG_BT_CTRL_BLE_MAX_ACT=10 @@ -310,12 +301,7 @@ CONFIG_BT_CTRL_SLEEP_MODE_EFF=0 CONFIG_BT_CTRL_SLEEP_CLOCK_EFF=0 CONFIG_BT_CTRL_HCI_TL_EFF=1 # CONFIG_BT_CTRL_AGC_RECORRECT_EN is not set -# end of Bluetooth controller(ESP32C3 Bluetooth Low Energy) - -# -# MODEM SLEEP Options -# -# end of MODEM SLEEP Options +# end of Bluetooth controller CONFIG_BT_BLUEDROID_ENABLED=y # CONFIG_BT_NIMBLE_ENABLED is not set @@ -526,11 +512,7 @@ CONFIG_BT_BLE_ESTAB_LINK_CONN_TOUT=30 CONFIG_BT_BLE_RPA_SUPPORTED=y CONFIG_BT_BLE_50_FEATURES_SUPPORTED=y CONFIG_BT_BLE_42_FEATURES_SUPPORTED=y -CONFIG_BT_RESERVE_DRAM=0xdb5c # end of Bluedroid Options - -CONFIG_BT_NIMBLE_ENABLE_CONN_REATTEMPT=y -CONFIG_BT_NIMBLE_USE_ESP_TIMER=y # end of Bluetooth # CONFIG_BLE_MESH is not set @@ -597,6 +579,8 @@ CONFIG_EFUSE_MAX_BLK_LEN=256 CONFIG_ESP_TLS_USING_MBEDTLS=y CONFIG_ESP_TLS_USE_DS_PERIPHERAL=y CONFIG_ESP_TLS_SERVER=y +# CONFIG_ESP_TLS_CLIENT_SESSION_TICKETS is not set +# CONFIG_ESP_TLS_SERVER_SESSION_TICKETS is not set # CONFIG_ESP_TLS_PSK_VERIFICATION is not set # CONFIG_ESP_TLS_INSECURE is not set # end of ESP-TLS @@ -720,6 +704,7 @@ CONFIG_ESP32C3_UNIVERSAL_MAC_ADDRESSES=4 # Sleep Config # CONFIG_ESP_SLEEP_POWER_DOWN_FLASH=y +# CONFIG_ESP_SLEEP_FLASH_LEAKAGE_WORKAROUND is not set # end of Sleep Config # end of Hardware Settings @@ -736,8 +721,6 @@ CONFIG_ESP_IPC_TASK_STACK_SIZE=1024 # # LCD Peripheral Configuration # -CONFIG_LCD_PERIPH_CLK_SRC_PLL160M=y -# CONFIG_LCD_PERIPH_CLK_SRC_XTAL is not set CONFIG_LCD_PANEL_IO_FORMAT_BUF_SIZE=32 # end of LCD Peripheral Configuration # end of LCD and Touch Panel @@ -783,8 +766,11 @@ CONFIG_ESP_SYSTEM_ALLOW_RTC_FAST_MEM_AS_HEAP=y # # Memory protection # +CONFIG_ESP_SYSTEM_MEMPROT_DEPCHECK=y CONFIG_ESP_SYSTEM_MEMPROT_FEATURE=y CONFIG_ESP_SYSTEM_MEMPROT_FEATURE_LOCK=y +CONFIG_ESP_SYSTEM_MEMPROT_CPU_PREFETCH_PAD_SIZE=16 +CONFIG_ESP_SYSTEM_MEMPROT_MEM_ALIGN_SIZE=512 # end of Memory protection CONFIG_ESP_SYSTEM_EVENT_QUEUE_SIZE=32 @@ -808,6 +794,7 @@ CONFIG_ESP_TASK_WDT=y CONFIG_ESP_TASK_WDT_TIMEOUT_S=5 CONFIG_ESP_TASK_WDT_CHECK_IDLE_TASK_CPU0=y # CONFIG_ESP_PANIC_HANDLER_IRAM is not set +CONFIG_ESP_SYSTEM_CHECK_INT_LEVEL_4=y # end of ESP System Settings # @@ -1071,7 +1058,6 @@ CONFIG_LWIP_IPV6=y # CONFIG_LWIP_IPV6_AUTOCONFIG is not set CONFIG_LWIP_IPV6_NUM_ADDRESSES=3 # CONFIG_LWIP_IPV6_FORWARD is not set -CONFIG_LWIP_IPV6_RDNSS_MAX_DNS_SERVERS=0 # CONFIG_LWIP_NETIF_STATUS_CALLBACK is not set CONFIG_LWIP_NETIF_LOOPBACK=y CONFIG_LWIP_LOOPBACK_MAX_PBUFS=8 @@ -1568,10 +1554,6 @@ CONFIG_STACK_CHECK_NONE=y # CONFIG_ESP32_APPTRACE_DEST_TRAX is not set CONFIG_ESP32_APPTRACE_DEST_NONE=y CONFIG_ESP32_APPTRACE_LOCK_ENABLE=y -CONFIG_BTDM_CONTROLLER_BLE_MAX_CONN_EFF=0 -CONFIG_BTDM_CONTROLLER_BR_EDR_MAX_ACL_CONN_EFF=0 -CONFIG_BTDM_CONTROLLER_BR_EDR_MAX_SYNC_CONN_EFF=0 -CONFIG_BTDM_CONTROLLER_PINNED_TO_CORE=0 CONFIG_BLUEDROID_ENABLED=y # CONFIG_NIMBLE_ENABLED is not set CONFIG_BTC_TASK_STACK_SIZE=3072 diff --git a/tools/sdk/esp32s2/bin/bootloader_dio_40m.bin b/tools/sdk/esp32s2/bin/bootloader_dio_40m.bin index f101ba18095..38bb414d787 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_dio_40m.bin and b/tools/sdk/esp32s2/bin/bootloader_dio_40m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_dio_80m.bin b/tools/sdk/esp32s2/bin/bootloader_dio_80m.bin index 80846dd13f6..d454c318da5 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_dio_80m.bin and b/tools/sdk/esp32s2/bin/bootloader_dio_80m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_dout_40m.bin b/tools/sdk/esp32s2/bin/bootloader_dout_40m.bin index 8975692c273..425e8a4adec 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_dout_40m.bin and b/tools/sdk/esp32s2/bin/bootloader_dout_40m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_dout_80m.bin b/tools/sdk/esp32s2/bin/bootloader_dout_80m.bin index aa58cbf621e..bd6f458ee2d 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_dout_80m.bin and b/tools/sdk/esp32s2/bin/bootloader_dout_80m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_qio_40m.bin b/tools/sdk/esp32s2/bin/bootloader_qio_40m.bin index b44032d9c9c..f2ca21c91f3 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_qio_40m.bin and b/tools/sdk/esp32s2/bin/bootloader_qio_40m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_qio_80m.bin b/tools/sdk/esp32s2/bin/bootloader_qio_80m.bin index 6aec289c3aa..94e44340c3e 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_qio_80m.bin and b/tools/sdk/esp32s2/bin/bootloader_qio_80m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_qout_40m.bin b/tools/sdk/esp32s2/bin/bootloader_qout_40m.bin index 3f44aabfbad..838fec2d4a2 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_qout_40m.bin and b/tools/sdk/esp32s2/bin/bootloader_qout_40m.bin differ diff --git a/tools/sdk/esp32s2/bin/bootloader_qout_80m.bin b/tools/sdk/esp32s2/bin/bootloader_qout_80m.bin index e426f9e01e3..e678a4d3e9c 100644 Binary files a/tools/sdk/esp32s2/bin/bootloader_qout_80m.bin and b/tools/sdk/esp32s2/bin/bootloader_qout_80m.bin differ diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_common.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_common.h index 687f980bef2..1899b35cc3d 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_common.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_common.h @@ -372,7 +372,7 @@ typedef struct static inline const char* tu_lookup_find(tu_lookup_table_t const* p_table, uint32_t key) { - static char not_found[10]; + static char not_found[11]; for(uint16_t i=0; icount; i++) { @@ -380,7 +380,7 @@ static inline const char* tu_lookup_find(tu_lookup_table_t const* p_table, uint3 } // not found return the key value in hex - sprintf(not_found, "0x%08lX", key); + sprintf(not_found, "0x%08lX", (unsigned long) key); return not_found; } diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_compiler.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_compiler.h index d3adbbc2d9b..3e85939b068 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_compiler.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_compiler.h @@ -32,6 +32,7 @@ #ifndef _TUSB_COMPILER_H_ #define _TUSB_COMPILER_H_ +#define TU_TOKEN(x) x #define TU_STRING(x) #x ///< stringify without expand #define TU_XSTRING(x) TU_STRING(x) ///< expand then stringify @@ -41,6 +42,8 @@ #define TU_XSTRCAT(a, b) TU_STRCAT(a, b) ///< expand then concat #define TU_XSTRCAT3(a, b, c) TU_STRCAT3(a, b, c) ///< expand then concat 3 tokens +#define TU_INCLUDE_PATH(_dir,_file) TU_XSTRING( TU_TOKEN(_dir)TU_TOKEN(_file) ) + #if defined __COUNTER__ && __COUNTER__ != __COUNTER__ #define _TU_COUNTER_ __COUNTER__ #else diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_types.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_types.h index d23c6b2dd20..f26983a7483 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_types.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/common/tusb_types.h @@ -372,7 +372,7 @@ typedef struct TU_ATTR_PACKED uint8_t bNumInterfaces ; ///< Number of interfaces supported by this speed configuration uint8_t bConfigurationValue ; ///< Value to use to select configuration - uint8_t IConfiguration ; ///< Index of string descriptor + uint8_t iConfiguration ; ///< Index of string descriptor uint8_t bmAttributes ; ///< Same as Configuration descriptor uint8_t bMaxPower ; ///< Same as Configuration descriptor } tusb_desc_other_speed_t; @@ -387,11 +387,14 @@ typedef struct TU_ATTR_PACKED uint8_t bDeviceClass ; ///< Class Code uint8_t bDeviceSubClass ; ///< SubClass Code uint8_t bDeviceProtocol ; ///< Protocol Code + uint8_t bMaxPacketSize0 ; ///< Maximum packet size for other speed uint8_t bNumConfigurations ; ///< Number of Other-speed Configurations uint8_t bReserved ; ///< Reserved for future use, must be zero } tusb_desc_device_qualifier_t; +TU_VERIFY_STATIC( sizeof(tusb_desc_device_qualifier_t) == 10, "size is not correct"); + /// USB Interface Association Descriptor (IAD ECN) typedef struct TU_ATTR_PACKED { diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/device/usbd.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/device/usbd.h index 9becf2d0d15..638d9309470 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/device/usbd.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/device/usbd.h @@ -113,9 +113,16 @@ uint16_t const* tud_descriptor_string_cb(uint8_t index, uint16_t langid); TU_ATTR_WEAK uint8_t const * tud_descriptor_bos_cb(void); // Invoked when received GET DEVICE QUALIFIER DESCRIPTOR request -// Application return pointer to descriptor, whose contents must exist long enough for transfer to complete +// Application return pointer to descriptor, whose contents must exist long enough for transfer to complete. +// device_qualifier descriptor describes information about a high-speed capable device that would +// change if the device were operating at the other speed. If not highspeed capable stall this request. TU_ATTR_WEAK uint8_t const* tud_descriptor_device_qualifier_cb(void); +// Invoked when received GET OTHER SEED CONFIGURATION DESCRIPTOR request +// Application return pointer to descriptor, whose contents must exist long enough for transfer to complete +// Configuration descriptor in the other speed e.g if high speed then this is for full speed and vice versa +TU_ATTR_WEAK uint8_t const* tud_descriptor_other_speed_configuration_cb(uint8_t index); + // Invoked when device is mounted (configured) TU_ATTR_WEAK void tud_mount_cb(void); diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/osal/osal_freertos.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/osal/osal_freertos.h index 66070c273a7..4573e01f5ef 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/osal/osal_freertos.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/osal/osal_freertos.h @@ -28,10 +28,10 @@ #define _TUSB_OSAL_FREERTOS_H_ // FreeRTOS Headers -#include "FreeRTOS.h" -#include "semphr.h" -#include "queue.h" -#include "task.h" +#include TU_INCLUDE_PATH(CFG_TUSB_OS_INC_PATH,FreeRTOS.h) +#include TU_INCLUDE_PATH(CFG_TUSB_OS_INC_PATH,semphr.h) +#include TU_INCLUDE_PATH(CFG_TUSB_OS_INC_PATH,queue.h) +#include TU_INCLUDE_PATH(CFG_TUSB_OS_INC_PATH,task.h) #ifdef __cplusplus extern "C" { diff --git a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/tusb_option.h b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/tusb_option.h index a00f3489f05..ad2a26a6654 100644 --- a/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/tusb_option.h +++ b/tools/sdk/esp32s2/include/arduino_tinyusb/tinyusb/src/tusb_option.h @@ -203,14 +203,20 @@ #define CFG_TUSB_MEM_SECTION #endif +// alignment requirement of buffer used for endpoint transferring #ifndef CFG_TUSB_MEM_ALIGN #define CFG_TUSB_MEM_ALIGN TU_ATTR_ALIGNED(4) #endif +// OS selection #ifndef CFG_TUSB_OS #define CFG_TUSB_OS OPT_OS_NONE #endif +#ifndef CFG_TUSB_OS_INC_PATH + #define CFG_TUSB_OS_INC_PATH +#endif + //-------------------------------------------------------------------- // DEVICE OPTIONS //-------------------------------------------------------------------- diff --git a/tools/sdk/esp32s2/include/bootloader_support/include/bootloader_common.h b/tools/sdk/esp32s2/include/bootloader_support/include/bootloader_common.h index 2ff0e595a27..2f4e9062200 100644 --- a/tools/sdk/esp32s2/include/bootloader_support/include/bootloader_common.h +++ b/tools/sdk/esp32s2/include/bootloader_support/include/bootloader_common.h @@ -119,6 +119,15 @@ bool bootloader_common_label_search(const char *list, char *label); */ void bootloader_configure_spi_pins(int drv); +/** + * @brief Get flash CS IO + * + * Can be determined by eFuse values, or the default value + * + * @return Flash CS IO + */ +uint8_t bootloader_flash_get_cs_io(void); + /** * @brief Calculates a sha-256 for a given partition or returns a appended digest. * diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/address.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/address.h new file mode 100644 index 00000000000..8b8d9a24fae --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/address.h @@ -0,0 +1,213 @@ +/* + * address.h -- representation of network addresses + * + * Copyright (C) 2010-2011,2015-2016 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file address.h + * @brief Representation of network addresses + */ + +#ifndef COAP_ADDRESS_H_ +#define COAP_ADDRESS_H_ + +#include +#include +#include +#include +#include "libcoap.h" + +#if defined(WITH_LWIP) + +#include + +typedef struct coap_address_t { + uint16_t port; + ip_addr_t addr; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +COAP_STATIC_INLINE uint16_t +coap_address_get_port(const coap_address_t *addr) { + return ntohs(addr->port); +} + +/** + * Sets the port field of @p addr to @p port (in host byte order). + */ +COAP_STATIC_INLINE void +coap_address_set_port(coap_address_t *addr, uint16_t port) { + addr->port = htons(port); +} + +#define _coap_address_equals_impl(A, B) \ + ((A)->port == (B)->port \ + && (!!ip_addr_cmp(&(A)->addr,&(B)->addr))) + +#define _coap_address_isany_impl(A) ip_addr_isany(&(A)->addr) + +#define _coap_is_mcast_impl(Address) ip_addr_ismulticast(&(Address)->addr) + +#elif defined(WITH_CONTIKI) + +#include "uip.h" + +typedef struct coap_address_t { + uip_ipaddr_t addr; + uint16_t port; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +COAP_STATIC_INLINE uint16_t +coap_address_get_port(const coap_address_t *addr) { + return uip_ntohs(addr->port); +} + +/** + * Sets the port field of @p addr to @p port (in host byte order). + */ +COAP_STATIC_INLINE void +coap_address_set_port(coap_address_t *addr, uint16_t port) { + addr->port = uip_htons(port); +} + +#define _coap_address_equals_impl(A,B) \ + ((A)->port == (B)->port \ + && uip_ipaddr_cmp(&((A)->addr),&((B)->addr))) + +/** @todo implementation of _coap_address_isany_impl() for Contiki */ +#define _coap_address_isany_impl(A) 0 + +#define _coap_is_mcast_impl(Address) uip_is_addr_mcast(&((Address)->addr)) + +#else /* WITH_LWIP || WITH_CONTIKI */ + + /** multi-purpose address abstraction */ +typedef struct coap_address_t { + socklen_t size; /**< size of addr */ + union { + struct sockaddr sa; + struct sockaddr_in sin; + struct sockaddr_in6 sin6; + } addr; +} coap_address_t; + +/** + * Returns the port from @p addr in host byte order. + */ +uint16_t coap_address_get_port(const coap_address_t *addr); + +/** + * Set the port field of @p addr to @p port (in host byte order). + */ +void coap_address_set_port(coap_address_t *addr, uint16_t port); + +/** + * Compares given address objects @p a and @p b. This function returns @c 1 if + * addresses are equal, @c 0 otherwise. The parameters @p a and @p b must not be + * @c NULL; + */ +int coap_address_equals(const coap_address_t *a, const coap_address_t *b); + +COAP_STATIC_INLINE int +_coap_address_isany_impl(const coap_address_t *a) { + /* need to compare only relevant parts of sockaddr_in6 */ + switch (a->addr.sa.sa_family) { + case AF_INET: + return a->addr.sin.sin_addr.s_addr == INADDR_ANY; + case AF_INET6: + return memcmp(&in6addr_any, + &a->addr.sin6.sin6_addr, + sizeof(in6addr_any)) == 0; + default: + ; + } + + return 0; +} +#endif /* WITH_LWIP || WITH_CONTIKI */ + +/** + * Resets the given coap_address_t object @p addr to its default values. In + * particular, the member size must be initialized to the available size for + * storing addresses. + * + * @param addr The coap_address_t object to initialize. + */ +void coap_address_init(coap_address_t *addr); + +/* Convenience function to copy IPv6 addresses without garbage. */ + +COAP_STATIC_INLINE void +coap_address_copy( coap_address_t *dst, const coap_address_t *src ) { +#if defined(WITH_LWIP) || defined(WITH_CONTIKI) + memcpy( dst, src, sizeof( coap_address_t ) ); +#else + memset( dst, 0, sizeof( coap_address_t ) ); + dst->size = src->size; + if ( src->addr.sa.sa_family == AF_INET6 ) { + dst->addr.sin6.sin6_family = src->addr.sin6.sin6_family; + dst->addr.sin6.sin6_addr = src->addr.sin6.sin6_addr; + dst->addr.sin6.sin6_port = src->addr.sin6.sin6_port; + dst->addr.sin6.sin6_scope_id = src->addr.sin6.sin6_scope_id; + } else if ( src->addr.sa.sa_family == AF_INET ) { + dst->addr.sin = src->addr.sin; + } else { + memcpy( &dst->addr, &src->addr, src->size ); + } +#endif +} + +#if defined(WITH_LWIP) || defined(WITH_CONTIKI) +/** + * Compares given address objects @p a and @p b. This function returns @c 1 if + * addresses are equal, @c 0 otherwise. The parameters @p a and @p b must not be + * @c NULL; + */ +COAP_STATIC_INLINE int +coap_address_equals(const coap_address_t *a, const coap_address_t *b) { + assert(a); assert(b); + return _coap_address_equals_impl(a, b); +} +#endif + +/** + * Checks if given address object @p a denotes the wildcard address. This + * function returns @c 1 if this is the case, @c 0 otherwise. The parameters @p + * a must not be @c NULL; + */ +COAP_STATIC_INLINE int +coap_address_isany(const coap_address_t *a) { + assert(a); + return _coap_address_isany_impl(a); +} + +#if !defined(WITH_LWIP) && !defined(WITH_CONTIKI) + +/** + * Checks if given address @p a denotes a multicast address. This function + * returns @c 1 if @p a is multicast, @c 0 otherwise. + */ +int coap_is_mcast(const coap_address_t *a); +#else /* !WITH_LWIP && !WITH_CONTIKI */ +/** + * Checks if given address @p a denotes a multicast address. This function + * returns @c 1 if @p a is multicast, @c 0 otherwise. + */ +COAP_STATIC_INLINE int +coap_is_mcast(const coap_address_t *a) { + return a && _coap_is_mcast_impl(a); +} +#endif /* !WITH_LWIP && !WITH_CONTIKI */ + +#endif /* COAP_ADDRESS_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/async.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/async.h new file mode 100644 index 00000000000..a61e0c09828 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/async.h @@ -0,0 +1,116 @@ +/* + * async.h -- state management for asynchronous messages + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file async.h + * @brief State management for asynchronous messages + */ + +#ifndef COAP_ASYNC_H_ +#define COAP_ASYNC_H_ + +#include "net.h" + +/** + * @defgroup coap_async Asynchronous Messaging + * @{ + * API functions for Async "separate" messages. + * A coap_context_t object holds a list of coap_async_t objects that can + * be used to generate a separate response in the case a result of a request + * cannot be delivered immediately. + */ + +/** + * Returns @c 1 if libcoap was built with separate messages enabled, + * @c 0 otherwise. + */ +int coap_async_is_supported(void); + +/** + * Allocates a new coap_async_t object and fills its fields according to + * the given @p request. This function returns a pointer to the registered + * coap_async_t object or @c NULL on error. Note that this function will + * return @c NULL in case that an object with the same identifier is already + * registered. + * + * When the delay expires, a copy of the @p request will get sent to the + * appropriate request handler. + * + * @param session The session that is used for asynchronous transmissions. + * @param request The request that is handled asynchronously. + * @param delay The amount of time to delay before sending response, 0 means + * wait forever. + * + * @return A pointer to the registered coap_async_t object or @c + * NULL in case of an error. + */ +coap_async_t * +coap_register_async(coap_session_t *session, + const coap_pdu_t *request, + coap_tick_t delay); + +/** + * Update the delay timeout, so changing when the registered @p async triggers. + * + * When the new delay expires, a copy of the original request will get sent to + * the appropriate request handler. + * + * @param async The object to update. + * @param delay The amount of time to delay before sending response, 0 means + * wait forever. + */ +void +coap_async_set_delay(coap_async_t *async, coap_tick_t delay); + +/** + * Releases the memory that was allocated by coap_register_async() for the + * object @p async. + * + * @param session The session to use. + * @param async The object to delete. + */ +void +coap_free_async(coap_session_t *session, coap_async_t *async); + +/** + * Retrieves the object identified by @p token from the list of asynchronous + * transactions that are registered with @p context. This function returns a + * pointer to that object or @c NULL if not found. + * + * @param session The session that is used for asynchronous transmissions. + * @param token The PDU's token of the object to retrieve. + * + * @return A pointer to the object identified by @p token or @c NULL if + * not found. + */ +coap_async_t *coap_find_async(coap_session_t *session, coap_bin_const_t token); + +/** + * Set the application data pointer held in @p async. This overwrites any + * existing data pointer. + * + * @param async The async state object. + * @param app_data The pointer to the data. + */ +void coap_async_set_app_data(coap_async_t *async, void *app_data); + +/** + * Gets the application data pointer held in @p async. + * + * @param async The async state object. + * + * @return The applicaton data pointer. + */ +void *coap_async_get_app_data(const coap_async_t *async); + +/** @} */ + +#endif /* COAP_ASYNC_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/block.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/block.h new file mode 100644 index 00000000000..a2aac00fdc6 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/block.h @@ -0,0 +1,348 @@ +/* + * block.h -- block transfer + * + * Copyright (C) 2010-2012,2014-2015 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_BLOCK_H_ +#define COAP_BLOCK_H_ + +#include "encode.h" +#include "option.h" +#include "pdu.h" + +/** + * @defgroup block Block Transfer + * API functions for handling PDUs using CoAP BLOCK options + * @{ + */ + +#ifndef COAP_MAX_BLOCK_SZX +/** + * The largest value for the SZX component in a Block option. + */ +#define COAP_MAX_BLOCK_SZX 6 +#endif /* COAP_MAX_BLOCK_SZX */ + +/** + * Structure of Block options. + */ +typedef struct { + unsigned int num; /**< block number */ + unsigned int m:1; /**< 1 if more blocks follow, 0 otherwise */ + unsigned int szx:3; /**< block size */ +} coap_block_t; + +#define COAP_BLOCK_USE_LIBCOAP 0x01 /* Use libcoap to do block requests */ +#define COAP_BLOCK_SINGLE_BODY 0x02 /* Deliver the data as a single body */ + +/** + * Returns the value of the least significant byte of a Block option @p opt. + * For zero-length options (i.e. num == m == szx == 0), COAP_OPT_BLOCK_LAST + * returns @c NULL. + */ +#define COAP_OPT_BLOCK_LAST(opt) \ + (coap_opt_length(opt) ? (coap_opt_value(opt) + (coap_opt_length(opt)-1)) : 0) + +/** Returns the value of the More-bit of a Block option @p opt. */ +#define COAP_OPT_BLOCK_MORE(opt) \ + (coap_opt_length(opt) ? (*COAP_OPT_BLOCK_LAST(opt) & 0x08) : 0) + +/** Returns the value of the SZX-field of a Block option @p opt. */ +#define COAP_OPT_BLOCK_SZX(opt) \ + (coap_opt_length(opt) ? (*COAP_OPT_BLOCK_LAST(opt) & 0x07) : 0) + +/** + * Returns the value of field @c num in the given block option @p block_opt. + */ +unsigned int coap_opt_block_num(const coap_opt_t *block_opt); + +/** + * Checks if more than @p num blocks are required to deliver @p data_len + * bytes of data for a block size of 1 << (@p szx + 4). + */ +COAP_STATIC_INLINE int +coap_more_blocks(size_t data_len, unsigned int num, uint16_t szx) { + return ((num+1) << (szx + 4)) < data_len; +} + +#if 0 +/** Sets the More-bit in @p block_opt */ +COAP_STATIC_INLINE void +coap_opt_block_set_m(coap_opt_t *block_opt, int m) { + if (m) + *(coap_opt_value(block_opt) + (coap_opt_length(block_opt) - 1)) |= 0x08; + else + *(coap_opt_value(block_opt) + (coap_opt_length(block_opt) - 1)) &= ~0x08; +} +#endif + +/** + * Initializes @p block from @p pdu. @p number must be either COAP_OPTION_BLOCK1 + * or COAP_OPTION_BLOCK2. When option @p number was found in @p pdu, @p block is + * initialized with values from this option and the function returns the value + * @c 1. Otherwise, @c 0 is returned. + * + * @param pdu The pdu to search for option @p number. + * @param number The option number to search for (must be COAP_OPTION_BLOCK1 or + * COAP_OPTION_BLOCK2). + * @param block The block structure to initilize. + * + * @return @c 1 on success, @c 0 otherwise. + */ +int coap_get_block(const coap_pdu_t *pdu, coap_option_num_t number, + coap_block_t *block); + +/** + * Writes a block option of type @p number to message @p pdu. If the requested + * block size is too large to fit in @p pdu, it is reduced accordingly. An + * exception is made for the final block when less space is required. The actual + * length of the resource is specified in @p data_length. + * + * This function may change *block to reflect the values written to @p pdu. As + * the function takes into consideration the remaining space @p pdu, no more + * options should be added after coap_write_block_opt() has returned. + * + * @param block The block structure to use. On return, this object is + * updated according to the values that have been written to + * @p pdu. + * @param number COAP_OPTION_BLOCK1 or COAP_OPTION_BLOCK2. + * @param pdu The message where the block option should be written. + * @param data_length The length of the actual data that will be added the @p + * pdu by calling coap_add_block(). + * + * @return @c 1 on success, or a negative value on error. + */ +int coap_write_block_opt(coap_block_t *block, + coap_option_num_t number, + coap_pdu_t *pdu, + size_t data_length); + +/** + * Adds the @p block_num block of size 1 << (@p block_szx + 4) from source @p + * data to @p pdu. + * + * @param pdu The message to add the block. + * @param len The length of @p data. + * @param data The source data to fill the block with. + * @param block_num The actual block number. + * @param block_szx Encoded size of block @p block_number. + * + * @return @c 1 on success, @c 0 otherwise. + */ +int coap_add_block(coap_pdu_t *pdu, + size_t len, + const uint8_t *data, + unsigned int block_num, + unsigned char block_szx); + +/** + * Re-assemble payloads into a body + * + * @param body_data The pointer to the data for the body holding the + * representation so far or NULL if the first time. + * @param length The length of @p data. + * @param data The payload data to update the body with. + * @param offset The offset of the @p data into the body. + * @param total The estimated total size of the body. + * + * @return The current representation of the body or @c NULL if error. + * If NULL, @p body_data will have been de-allocated. + */ +coap_binary_t * +coap_block_build_body(coap_binary_t *body_data, size_t length, + const uint8_t *data, size_t offset, size_t total); + +/** + * Adds the appropriate part of @p data to the @p response pdu. If blocks are + * required, then the appropriate block will be added to the PDU and sent. + * Adds a ETAG option that is the hash of the entire data if the data is to be + * split into blocks + * Used by a request handler. + * + * Note: The application will get called for every packet of a large body to + * process. Consider using coap_add_data_response_large() instead. + * + * @param request The requesting pdu. + * @param response The response pdu. + * @param media_type The format of the data. + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage. + * @param length The total length of the data. + * @param data The entire data block to transmit. + * + */ +void +coap_add_data_blocked_response(const coap_pdu_t *request, + coap_pdu_t *response, + uint16_t media_type, + int maxage, + size_t length, + const uint8_t* data); + +/** + * Callback handler for de-allocating the data based on @p app_ptr provided to + * coap_add_data_large_*() functions following transmission of the supplied + * data. + * + * @param session The session that this data is associated with + * @param app_ptr The application provided pointer provided to the + * coap_add_data_large_* functions. + */ +typedef void (*coap_release_large_data_t)(coap_session_t *session, + void *app_ptr); + +/** + * Associates given data with the @p pdu that is passed as second parameter. + * + * If all the data can be transmitted in a single PDU, this is functionally + * the same as coap_add_data() except @p release_func (if not NULL) will get + * invoked after data transmission. + * + * Used for a client request. + * + * If the data spans multiple PDUs, then the data will get transmitted using + * BLOCK1 option with the addition of the SIZE1 option. + * The underlying library will handle the transmission of the individual blocks. + * Once the body of data has been transmitted (or a failure occurred), then + * @p release_func (if not NULL) will get called so the application can + * de-allocate the @p data based on @p app_data. It is the responsibility of + * the application not to change the contents of @p data until the data + * transfer has completed. + * + * There is no need for the application to include the BLOCK1 option in the + * @p pdu. + * + * coap_add_data_large_request() (or the alternative coap_add_data_large_*() + * functions) must be called only once per PDU and must be the last PDU update + * before the PDU is transmitted. The (potentially) initial data will get + * transmitted when coap_send() is invoked. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set by coap_context_set_block_mode() + * for libcoap to work correctly when using this function. + * + * @param session The session to associate the data with. + * @param pdu The PDU to associate the data with. + * @param length The length of data to transmit. + * @param data The data to transmit. + * @param release_func The function to call to de-allocate @p data or @c NULL + * if the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if addition is successful, else @c 0. + */ +int coap_add_data_large_request(coap_session_t *session, + coap_pdu_t *pdu, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * Associates given data with the @p response pdu that is passed as fourth + * parameter. + * + * If all the data can be transmitted in a single PDU, this is functionally + * the same as coap_add_data() except @p release_func (if not NULL) will get + * invoked after data transmission. The MEDIA_TYPE, MAXAGE and ETAG options may + * be added in as appropriate. + * + * Used by a server request handler to create the response. + * + * If the data spans multiple PDUs, then the data will get transmitted using + * BLOCK2 (response) option with the addition of the SIZE2 and ETAG + * options. The underlying library will handle the transmission of the + * individual blocks. Once the body of data has been transmitted (or a + * failure occurred), then @p release_func (if not NULL) will get called so the + * application can de-allocate the @p data based on @p app_data. It is the + * responsibility of the application not to change the contents of @p data + * until the data transfer has completed. + * + * There is no need for the application to include the BLOCK2 option in the + * @p pdu. + * + * coap_add_data_large_response() (or the alternative coap_add_data_large*() + * functions) must be called only once per PDU and must be the last PDU update + * before returning from the request handler function. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set by coap_context_set_block_mode() + * for libcoap to work correctly when using this function. + * + * @param resource The resource the data is associated with. + * @param session The coap session. + * @param request The requesting pdu. + * @param response The response pdu. + * @param query The query taken from the (original) requesting pdu. + * @param media_type The format of the data. + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage. + * @param etag ETag to use if not 0. + * @param length The total length of the data. + * @param data The entire data block to transmit. + * @param release_func The function to call to de-allocate @p data or NULL if + * the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if addition is successful, else @c 0. + */ +int +coap_add_data_large_response(coap_resource_t *resource, + coap_session_t *session, + const coap_pdu_t *request, + coap_pdu_t *response, + const coap_string_t *query, + uint16_t media_type, + int maxage, + uint64_t etag, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * Set the context level CoAP block handling bits for handling RFC7959. + * These bits flow down to a session when a session is created and if the peer + * does not support something, an appropriate bit may get disabled in the + * session block_mode. + * The session block_mode then flows down into coap_crcv_t or coap_srcv_t where + * again an appropriate bit may get disabled. + * + * Note: This function must be called before the session is set up. + * + * Note: COAP_BLOCK_USE_LIBCOAP must be set if libcoap is to do all the + * block tracking and requesting, otherwise the application will have to do + * all of this work (the default if coap_context_set_block_mode() is not + * called). + * + * @param context The coap_context_t object. + * @param block_mode Zero or more COAP_BLOCK_ or'd options + */ +void coap_context_set_block_mode(coap_context_t *context, + uint8_t block_mode); + +/** + * Cancel an observe that is being tracked by the client large receive logic. + * (coap_context_set_block_mode() has to be called) + * This will trigger the sending of an observe cancel pdu to the server. + * + * @param session The session that is being used for the observe. + * @param token The original token used to initiate the observation. + * @param message_type The COAP_MESSAGE_ type (NON or CON) to send the observe + * cancel pdu as. + * + * @return @c 1 if observe cancel transmission initiation is successful, + * else @c 0. + */ +int coap_cancel_observe(coap_session_t *session, coap_binary_t *token, + coap_pdu_type_t message_type); + +/**@}*/ + +#endif /* COAP_BLOCK_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_asn1_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_asn1_internal.h new file mode 100644 index 00000000000..5bb4e2a8dbe --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_asn1_internal.h @@ -0,0 +1,89 @@ +/* + * coap_asn1_internal.h -- ASN.1 functions for libcoap + * + * Copyright (C) 2020 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_asn1_internal.h + * @brief COAP ASN.1 internal information + */ + +#ifndef COAP_ASN1_INTERNAL_H_ +#define COAP_ASN1_INTERNAL_H_ + + +/** + * @defgroup asn1 ASN.1 Support (Internal) + * CoAP ASN.1 Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +typedef enum { + COAP_ASN1_NONE = 0, + COAP_ASN1_INTEGER = 2, + COAP_ASN1_BITSTRING = 3, + COAP_ASN1_OCTETSTRING = 4, + COAP_ASN1_IDENTIFIER = 6, +} coap_asn1_tag_t; + +/** + * Callback to validate the asn1 tag and data. + * + * Internal function. + * + * @param data The start of the tag and data + * @param size The size of the tag and data + * + * @return @c 1 if pass, else @c 0 if fail + */ +typedef int (*asn1_validate)(const uint8_t *data, size_t size); + +/** + * Get the asn1 length from the current @p ptr. + * + * Internal function. + * + * @param ptr The current asn.1 object length pointer + * + * @return The length of the asn.1 object. @p ptr is updated to be after the length. + */ +size_t asn1_len(const uint8_t **ptr); + +/** + * Get the asn1 tag from the current @p ptr. + * + * Internal function. + * + * @param ptr The current asn.1 object tag pointer + * @param constructed 1 if current tag is constructed + * @param class The current class of the tag + * + * @return The tag value.@p ptr is updated to be after the tag. + */ +coap_asn1_tag_t asn1_tag_c(const uint8_t **ptr, int *constructed, int *class); + +/** + * Get the asn1 tag and data from the current @p ptr. + * + * Internal function. + * + * @param ltag The tag to look for + * @param ptr The current asn.1 object pointer + * @param tlen The remaining size oof the asn.1 data + * @param validate Call validate to verify tag data or @c NULL + * + * @return The asn.1 tag and data or @c NULL if not found + */ +coap_binary_t *get_asn1_tag(coap_asn1_tag_t ltag, const uint8_t *ptr, + size_t tlen, asn1_validate validate); + +/** @} */ + +#endif /* COAP_ASN1_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_async_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_async_internal.h new file mode 100644 index 00000000000..a23b1c8e697 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_async_internal.h @@ -0,0 +1,67 @@ +/* + * coap_async_internal.h -- state management for asynchronous messages + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_async_internal.h + * @brief CoAP async internal information + */ + +#ifndef COAP_ASYNC_INTERNAL_H_ +#define COAP_ASYNC_INTERNAL_H_ + +#include "coap3/net.h" + +#ifndef WITHOUT_ASYNC + +/** + * @defgroup coap_async_internal Asynchronous Messaging (Internal) + * @{ + * CoAP Async Structures, Enums and Functions that are not exposed to + * applications. + * A coap_context_t object holds a list of coap_async_t objects that can be + * used to generate a separate response in the case a result of a request cannot + * be delivered immediately. + */ +struct coap_async_t { + struct coap_async_t *next; /**< internally used for linking */ + coap_tick_t delay; /**< When to delay to before triggering the response + 0 indicates never trigger */ + coap_session_t *session; /**< transaction session */ + coap_pdu_t *pdu; /**< copy of request pdu */ + void* appdata; /** User definable data pointer */ +}; + +/** + * Checks if there are any pending Async requests - if so, send them off. + * Otherewise return the time remaining for the next Async to be triggered + * or 0 if nothing to do. + * + * @param context The current context. + * @param now The current time in ticks. + * + * @return The tick time before the next Async needs to go, else 0 if + * nothing to do. + */ +coap_tick_t coap_check_async(coap_context_t *context, coap_tick_t now); + +/** + * Removes and frees off all of the async entries for the given context. + * + * @param context The context to remove all async entries from. + */ +void +coap_delete_all_async(coap_context_t *context); + +/** @} */ + +#endif /* WITHOUT_ASYNC */ + +#endif /* COAP_ASYNC_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_block_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_block_internal.h new file mode 100644 index 00000000000..9abe81557fa --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_block_internal.h @@ -0,0 +1,239 @@ +/* + * coap_block_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * Copyright (C) 2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_block_internal.h + * @brief COAP block internal information + */ + +#ifndef COAP_BLOCK_INTERNAL_H_ +#define COAP_BLOCK_INTERNAL_H_ + +#include "coap_pdu_internal.h" +#include "resource.h" + +/** + * @defgroup block_internal Block (Internal) + * Structures, Enums and Functions that are not exposed to applications + * @{ + */ + +typedef enum { + COAP_RECURSE_OK, + COAP_RECURSE_NO +} coap_recurse_t; + +struct coap_lg_range { + uint32_t begin; + uint32_t end; +}; + +#define COAP_RBLOCK_CNT 4 +/** + * Structure to keep track of received blocks + */ +typedef struct coap_rblock_t { + uint32_t used; + uint32_t retry; + struct coap_lg_range range[COAP_RBLOCK_CNT]; + coap_tick_t last_seen; +} coap_rblock_t; + +/** + * Structure to keep track of block1 specific information + * (Requests) + */ +typedef struct coap_l_block1_t { + coap_binary_t *app_token; /**< original PDU token */ + uint8_t token[8]; /**< last used token */ + size_t token_length; /**< length of token */ + uint32_t count; /**< the number of packets sent for payload */ +} coap_l_block1_t; + +/** + * Structure to keep track of block2 specific information + * (Responses) + */ +typedef struct coap_l_block2_t { + coap_resource_t *resource; /**< associated resource */ + coap_string_t *query; /**< Associated query for the resource */ + uint64_t etag; /**< ETag value */ + coap_time_t maxage_expire; /**< When this entry expires */ +} coap_l_block2_t; + +/** + * Structure to hold large body (many blocks) transmission information + */ +struct coap_lg_xmit_t { + struct coap_lg_xmit_t *next; + uint8_t blk_size; /**< large block transmission size */ + uint16_t option; /**< large block transmisson CoAP option */ + int last_block; /**< last acknowledged block number */ + const uint8_t *data; /**< large data ptr */ + size_t length; /**< large data length */ + size_t offset; /**< large data next offset to transmit */ + union { + coap_l_block1_t b1; + coap_l_block2_t b2; + } b; + coap_pdu_t pdu; /**< skeletal PDU */ + coap_tick_t last_payload; /**< Last time MAX_PAYLOAD was sent or 0 */ + coap_tick_t last_used; /**< Last time all data sent or 0 */ + coap_release_large_data_t release_func; /**< large data de-alloc function */ + void *app_ptr; /**< applicaton provided ptr for de-alloc function */ +}; + +/** + * Structure to hold large body (many blocks) client receive information + */ +struct coap_lg_crcv_t { + struct coap_lg_crcv_t *next; + uint8_t observe[3]; /**< Observe data (if set) (only 24 bits) */ + uint8_t observe_length;/**< Length of observe data */ + uint8_t observe_set; /**< Set if this is an observe receive PDU */ + uint8_t etag_set; /**< Set if ETag is in receive PDU */ + uint8_t etag_length; /**< ETag length */ + uint8_t etag[8]; /**< ETag for block checking */ + uint16_t content_format; /**< Content format for the set of blocks */ + uint8_t last_type; /**< Last request type (CON/NON) */ + uint8_t initial; /**< If set, has not been used yet */ + uint8_t szx; /**< size of individual blocks */ + size_t total_len; /**< Length as indicated by SIZE2 option */ + coap_binary_t *body_data; /**< Used for re-assembling entire body */ + coap_binary_t *app_token; /**< app requesting PDU token */ + uint8_t base_token[8]; /**< established base PDU token */ + size_t base_token_length; /**< length of token */ + uint8_t token[8]; /**< last used token */ + size_t token_length; /**< length of token */ + coap_pdu_t pdu; /**< skeletal PDU */ + coap_rblock_t rec_blocks; /** < list of received blocks */ + coap_tick_t last_used; /**< Last time all data sent or 0 */ + uint16_t block_option; /**< Block option in use */ +}; + +/** + * Structure to hold large body (many blocks) server receive information + */ +struct coap_lg_srcv_t { + struct coap_lg_srcv_t *next; + uint8_t observe[3]; /**< Observe data (if set) (only 24 bits) */ + uint8_t observe_length;/**< Length of observe data */ + uint8_t observe_set; /**< Set if this is an observe receive PDU */ + uint8_t rtag_set; /**< Set if RTag is in receive PDU */ + uint8_t rtag_length; /**< RTag length */ + uint8_t rtag[8]; /**< RTag for block checking */ + uint16_t content_format; /**< Content format for the set of blocks */ + uint8_t last_type; /**< Last request type (CON/NON) */ + uint8_t szx; /**< size of individual blocks */ + size_t total_len; /**< Length as indicated by SIZE1 option */ + coap_binary_t *body_data; /**< Used for re-assembling entire body */ + size_t amount_so_far; /**< Amount of data seen so far */ + coap_resource_t *resource; /**< associated resource */ + coap_str_const_t *uri_path; /** set to uri_path if unknown resource */ + coap_rblock_t rec_blocks; /** < list of received blocks */ + uint8_t last_token[8]; /**< last used token */ + size_t last_token_length; /**< length of token */ + coap_mid_t last_mid; /**< Last received mid for this set of packets */ + coap_tick_t last_used; /**< Last time data sent or 0 */ + uint16_t block_option; /**< Block option in use */ +}; + +coap_lg_crcv_t * coap_block_new_lg_crcv(coap_session_t *session, + coap_pdu_t *pdu); + +void coap_block_delete_lg_crcv(coap_session_t *session, + coap_lg_crcv_t *lg_crcv); + +coap_tick_t coap_block_check_lg_crcv_timeouts(coap_session_t *session, + coap_tick_t now); + +void coap_block_delete_lg_srcv(coap_session_t *session, + coap_lg_srcv_t *lg_srcv); + +coap_tick_t coap_block_check_lg_srcv_timeouts(coap_session_t *session, + coap_tick_t now); + +int coap_handle_request_send_block(coap_session_t *session, + coap_pdu_t *pdu, + coap_pdu_t *response, + coap_resource_t *resource, + coap_string_t *query); + +int coap_handle_request_put_block(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *pdu, + coap_pdu_t *response, + coap_resource_t *resource, + coap_string_t *uri_path, + coap_opt_t *observe, + coap_string_t *query, + coap_method_handler_t h, + int *added_block); + +int coap_handle_response_send_block(coap_session_t *session, coap_pdu_t *rcvd); + +int coap_handle_response_get_block(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *sent, + coap_pdu_t *rcvd, + coap_recurse_t recursive); + +void coap_block_delete_lg_xmit(coap_session_t *session, + coap_lg_xmit_t *lg_xmit); + +/** + * The function that does all the work for the coap_add_data_large*() + * functions. + * + * @param session The session to associate the data with. + * @param pdu The PDU to associate the data with. + * @param resource The resource to associate the data with (BLOCK2). + * @param query The query to associate the data with (BLOCK2). + * @param maxage The maxmimum life of the data. If @c -1, then there + * is no maxage (BLOCK2). + * @param etag ETag to use if not 0 (BLOCK2). + * @param length The length of data to transmit. + * @param data The data to transmit. + * @param release_func The function to call to de-allocate @p data or NULL if + * the function is not required. + * @param app_ptr A Pointer that the application can provide for when + * release_func() is called. + * + * @return @c 1 if transmission initiation is successful, else @c 0. + */ +int coap_add_data_large_internal(coap_session_t *session, + coap_pdu_t *pdu, + coap_resource_t *resource, + const coap_string_t *query, + int maxage, + uint64_t etag, + size_t length, + const uint8_t *data, + coap_release_large_data_t release_func, + void *app_ptr); + +/** + * The function checks that the code in a newly formed lg_xmit created by + * coap_add_data_large_response() is updated. + * + * @param session The session + * @param response The response PDU to to check + * @param resource The requested resource + * @param query The requested query + */ +void coap_check_code_lg_xmit(coap_session_t *session, coap_pdu_t *response, + coap_resource_t *resource, coap_string_t *query); + +/** @} */ + +#endif /* COAP_BLOCK_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache.h new file mode 100644 index 00000000000..a8d2fd7a84e --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache.h @@ -0,0 +1,232 @@ +/* coap_cache.h -- Caching of CoAP requests +* +* Copyright (C) 2020 Olaf Bergmann +* + * SPDX-License-Identifier: BSD-2-Clause + * +* This file is part of the CoAP library libcoap. Please see +* README for terms of use. +*/ + +/** + * @file coap_cache.h + * @brief Provides a simple cache request storage for CoAP requests + */ + +#ifndef COAP_CACHE_H_ +#define COAP_CACHE_H_ + +#include "coap_forward_decls.h" + +/** + * @defgroup cache Cache Support + * API functions for CoAP Caching + * @{ + */ + +/** + * Callback to free off the app data when the cache-entry is + * being deleted / freed off. + * + * @param data The app data to be freed off. + */ +typedef void (*coap_cache_app_data_free_callback_t)(void *data); + +typedef enum coap_cache_session_based_t { + COAP_CACHE_NOT_SESSION_BASED, + COAP_CACHE_IS_SESSION_BASED +} coap_cache_session_based_t; + +typedef enum coap_cache_record_pdu_t { + COAP_CACHE_NOT_RECORD_PDU, + COAP_CACHE_RECORD_PDU +} coap_cache_record_pdu_t; + +/** + * Calculates a cache-key for the given CoAP PDU. See + * https://tools.ietf.org/html/rfc7252#section-5.6 + * for an explanation of CoAP cache keys. + * + * Specific CoAP options can be removed from the cache-key. Examples of + * this are the BLOCK1 and BLOCK2 options - which make no real sense including + * them in a client or server environment, but should be included in a proxy + * caching environment where things are cached on a per block basis. + * This is done globally by calling the coap_cache_ignore_options() + * function. + * + * NOTE: The returned cache-key needs to be freed off by the caller by + * calling coap_cache_delete_key(). + * + * @param session The session to add into cache-key if @p session_based + * is set. + * @param pdu The CoAP PDU for which a cache-key is to be + * calculated. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key, else COAP_CACHE_NOT_SESSION_BASED. + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_key_t *coap_cache_derive_key(const coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based); + +/** + * Calculates a cache-key for the given CoAP PDU. See + * https://tools.ietf.org/html/rfc7252#section-5.6 + * for an explanation of CoAP cache keys. + * + * Specific CoAP options can be removed from the cache-key. Examples of + * this are the BLOCK1 and BLOCK2 options - which make no real sense including + * them in a client or server environment, but should be included in a proxy + * caching environment where things are cached on a per block basis. + * This is done individually by specifying @p cache_ignore_count and + * @p cache_ignore_options . + * + * NOTE: The returned cache-key needs to be freed off by the caller by + * calling coap_cache_delete_key(). + * + * @param session The session to add into cache-key if @p session_based + * is set. + * @param pdu The CoAP PDU for which a cache-key is to be + * calculated. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key, else COAP_CACHE_NOT_SESSION_BASED. + * @param ignore_options The array of options to ignore. + * @param ignore_count The number of options to ignore. + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_key_t *coap_cache_derive_key_w_ignore(const coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based, + const uint16_t *ignore_options, + size_t ignore_count); + +/** + * Delete the cache-key. + * + * @param cache_key The cache-key to delete. + */ +void coap_delete_cache_key(coap_cache_key_t *cache_key); + +/** + * Define the CoAP options that are not to be included when calculating + * the cache-key. Options that are defined as Non-Cache and the Observe + * option are always ignored. + * + * @param context The context to save the ignored options information in. + * @param options The array of options to ignore. + * @param count The number of options to ignore. Use 0 to reset the + * options matching. + * + * @return @return @c 1 if successful, else @c 0. + */ +int coap_cache_ignore_options(coap_context_t *context, + const uint16_t *options, size_t count); + +/** + * Create a new cache-entry hash keyed by cache-key derived from the PDU. + * + * If @p session_based is set, then this cache-entry will get deleted when + * the session is freed off. + * If @p record_pdu is set, then the copied PDU will get freed off when + * this cache-entry is deleted. + * + * The cache-entry is maintained on a context hash list. + * + * @param session The session to use to derive the context from. + * @param pdu The pdu to use to generate the cache-key. + * @param record_pdu COAP_CACHE_RECORD_PDU if to take a copy of the PDU for + * later use, else COAP_CACHE_NOT_RECORD_PDU. + * @param session_based COAP_CACHE_IS_SESSION_BASED if to associate this + * cache-entry with the the session (which is embedded + * in the cache-entry), else COAP_CACHE_NOT_SESSION_BASED. + * @param idle_time Idle time in seconds before cache-entry is expired. + * If set to 0, it does not expire (but will get + * deleted if the session is deleted and it is session_based). + * + * @return The returned cache-key or @c NULL if failure. + */ +coap_cache_entry_t *coap_new_cache_entry(coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_record_pdu_t record_pdu, + coap_cache_session_based_t session_based, + unsigned int idle_time); + +/** + * Remove a cache-entry from the hash list and free off all the appropriate + * contents apart from app_data. + * + * @param context The context to use. + * @param cache_entry The cache-entry to remove. + */ +void coap_delete_cache_entry(coap_context_t *context, + coap_cache_entry_t *cache_entry); + +/** + * Searches for a cache-entry identified by @p cache_key. This + * function returns the corresponding cache-entry or @c NULL + * if not found. + * + * @param context The context to use. + * @param cache_key The cache-key to get the hashed coap-entry. + * + * @return The cache-entry for @p cache_key or @c NULL if not found. + */ +coap_cache_entry_t *coap_cache_get_by_key(coap_context_t *context, + const coap_cache_key_t *cache_key); + +/** + * Searches for a cache-entry corresponding to @p pdu. This + * function returns the corresponding cache-entry or @c NULL if not + * found. + * + * @param session The session to use. + * @param pdu The CoAP request to search for. + * @param session_based COAP_CACHE_IS_SESSION_BASED if session based + * cache-key to be used, else COAP_CACHE_NOT_SESSION_BASED. + * + * @return The cache-entry for @p request or @c NULL if not found. + */ +coap_cache_entry_t *coap_cache_get_by_pdu(coap_session_t *session, + const coap_pdu_t *pdu, + coap_cache_session_based_t session_based); + +/** + * Returns the PDU information stored in the @p coap_cache entry. + * + * @param cache_entry The CoAP cache entry. + * + * @return The PDU information stored in the cache_entry or NULL + * if the PDU was not initially copied. + */ +const coap_pdu_t *coap_cache_get_pdu(const coap_cache_entry_t *cache_entry); + +/** + * Stores @p data with the given cache entry. This function + * overwrites any value that has previously been stored with @p + * cache_entry. + * + * @param cache_entry The CoAP cache entry. + * @param data The data pointer to store with wih the cache entry. Note that + * this data must be valid during the lifetime of @p cache_entry. + * @param callback The callback to call to free off this data when the + * cache-entry is deleted, or @c NULL if not required. + */ +void coap_cache_set_app_data(coap_cache_entry_t *cache_entry, void *data, + coap_cache_app_data_free_callback_t callback); + +/** + * Returns any application-specific data that has been stored with @p + * cache_entry using the function coap_cache_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param cache_entry The CoAP cache entry. + * + * @return The data pointer previously stored or @c NULL if no data stored. + */ +void *coap_cache_get_app_data(const coap_cache_entry_t *cache_entry); + +/** @} */ + +#endif /* COAP_CACHE_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache_internal.h new file mode 100644 index 00000000000..29c0756875c --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_cache_internal.h @@ -0,0 +1,111 @@ +/* + * coap_cache_internal.h -- Cache functions for libcoap + * + * Copyright (C) 2019--2020 Olaf Bergmann and others + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_cache_internal.h + * @brief COAP cache internal information + */ + +#ifndef COAP_CACHE_INTERNAL_H_ +#define COAP_CACHE_INTERNAL_H_ + +#include "coap_io.h" + +/** + * @defgroup cache_internal Cache Support (Internal) + * CoAP Cache Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/* Holds a digest in binary typically sha256 except for notls */ +typedef struct coap_digest_t { + uint8_t key[32]; +} coap_digest_t; + +struct coap_cache_key_t { + uint8_t key[32]; +}; + +struct coap_cache_entry_t { + UT_hash_handle hh; + coap_cache_key_t *cache_key; + coap_session_t *session; + coap_pdu_t *pdu; + void* app_data; + coap_tick_t expire_ticks; + unsigned int idle_timeout; + coap_cache_app_data_free_callback_t callback; +}; + +/** + * Expire coap_cache_entry_t entries + * + * Internal function. + * + * @param context The context holding the coap-entries to exire + */ +void coap_expire_cache_entries(coap_context_t *context); + +typedef void coap_digest_ctx_t; + +/** + * Initialize a coap_digest + * + * Internal function. + * + * @return The digest context or @c NULL if failure. + */ +coap_digest_ctx_t *coap_digest_setup(void); + +/** + * Free off coap_digest_ctx_t. Always done by + * coap_digest_final() + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + */ +void coap_digest_free(coap_digest_ctx_t *digest_ctx); + +/** + * Update the coap_digest information with the next chunk of data + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + * @param data Pointer to data. + * @param data_len Number of bytes. + * + * @return @c 1 success, @c 0 failure. + */ +int coap_digest_update(coap_digest_ctx_t *digest_ctx, + const uint8_t *data, + size_t data_len + ); + +/** + * Finalize the coap_digest information into the provided + * @p digest_buffer. + * + * Internal function. + * + * @param digest_ctx The coap_digest context. + * @param digest_buffer Pointer to digest buffer to update + * + * @return @c 1 success, @c 0 failure. + */ +int coap_digest_final(coap_digest_ctx_t *digest_ctx, + coap_digest_t *digest_buffer); + +/** @} */ + +#endif /* COAP_CACHE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_debug.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_debug.h new file mode 100644 index 00000000000..f8f70f64495 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_debug.h @@ -0,0 +1,247 @@ +/* + * coap_debug.h -- debug utilities + * + * Copyright (C) 2010-2011,2014 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DEBUG_H_ +#define COAP_DEBUG_H_ + +/** + * @defgroup logging Logging Support + * API functions for logging support + * @{ + */ + +#ifndef COAP_DEBUG_FD +/** + * Used for output for @c LOG_DEBUG to @c LOG_ERR. + */ +#define COAP_DEBUG_FD stdout +#endif + +#ifndef COAP_ERR_FD +/** + * Used for output for @c LOG_CRIT to @c LOG_EMERG. + */ +#define COAP_ERR_FD stderr +#endif + +#ifdef HAVE_SYSLOG_H +#include +/** + * Logging type. One of LOG_* from @b syslog. + */ +typedef short coap_log_t; +/* + LOG_DEBUG+2 gives ciphers in GnuTLS + Use COAP_LOG_CIPHERS to output Cipher Info in OpenSSL etc. + */ +#define COAP_LOG_CIPHERS (LOG_DEBUG+2) +#else /* !HAVE_SYSLOG_H */ +/** Pre-defined log levels akin to what is used in \b syslog + with LOG_CIPHERS added. */ + +#if !defined(RIOT_VERSION) +typedef enum { + LOG_EMERG=0, /**< Emergency */ + LOG_ALERT, /**< Alert */ + LOG_CRIT, /**< Critical */ + LOG_ERR, /**< Error */ + LOG_WARNING, /**< Warning */ + LOG_NOTICE, /**< Notice */ + LOG_INFO, /**< Information */ + LOG_DEBUG, /**< Debug */ + COAP_LOG_CIPHERS=LOG_DEBUG+2 /**< CipherInfo */ +} coap_log_t; +#else /* RIOT_VERSION */ +/* RIOT defines a subset of the syslog levels in log.h with different + * numeric values. The remaining levels are defined here. Note that + * output granularity differs from what would be expected when + * adhering to the syslog levels. + */ +#include +typedef short coap_log_t; +#define LOG_EMERG (0) +#define LOG_ALERT (1) +#define LOG_CRIT (2) +#define LOG_ERR (3) +/* LOG_WARNING (4) */ +#define LOG_NOTICE (5) +/* LOG_INFO (6) */ +/* LOG_DEBUG (7) */ +#define COAP_LOG_CIPHERS (9) +#endif /* RIOT_VERSION */ + +#endif /* !HAVE_SYSLOG_H */ + +/** + * Get the current logging level. + * + * @return One of the LOG_* values. + */ +coap_log_t coap_get_log_level(void); + +/** + * Sets the log level to the specified value. + * + * @param level One of the LOG_* values. + */ +void coap_set_log_level(coap_log_t level); + +/** + * Logging callback handler definition. + * + * @param level One of the LOG_* values. + * @param message Zero-terminated string message to log. + */ +typedef void (*coap_log_handler_t) (coap_log_t level, const char *message); + +/** + * Add a custom log callback handler. + * + * @param handler The logging handler to use or @p NULL to use default handler. + */ +void coap_set_log_handler(coap_log_handler_t handler); + +/** + * Get the library package name. + * + * @return Zero-terminated string with the name of this library. + */ +const char *coap_package_name(void); + +/** + * Get the library package version. + * + * @return Zero-terminated string with the library version. + */ +const char *coap_package_version(void); + +/** + * Writes the given text to @c COAP_ERR_FD (for @p level <= @c LOG_CRIT) or @c + * COAP_DEBUG_FD (for @p level >= @c LOG_ERR). The text is output only when + * @p level is below or equal to the log level that set by coap_set_log_level(). + * + * Internal function. + * + * @param level One of the LOG_* values. + & @param format The format string to use. + */ +#if (defined(__GNUC__)) +void coap_log_impl(coap_log_t level, + const char *format, ...) __attribute__ ((format(printf, 2, 3))); +#else +void coap_log_impl(coap_log_t level, const char *format, ...); +#endif + +#ifndef coap_log +/** + * Logging function. + * Writes the given text to @c COAP_ERR_FD (for @p level <= @c LOG_CRIT) or @c + * COAP_DEBUG_FD (for @p level >= @c LOG_ERR). The text is output only when + * @p level is below or equal to the log level that set by coap_set_log_level(). + * + * @param level One of the LOG_* values. + */ +#define coap_log(level, ...) do { \ + if ((int)((level))<=(int)coap_get_log_level()) \ + coap_log_impl((level), __VA_ARGS__); \ +} while(0) +#endif + +#include "pdu.h" + +/** + * Defines the output mode for the coap_show_pdu() function. + * + * @param use_fprintf @p 1 if the output is to use fprintf() (the default) + * @p 0 if the output is to use coap_log(). + */ +void coap_set_show_pdu_output(int use_fprintf); + +/** + * Display the contents of the specified @p pdu. + * Note: The output method of coap_show_pdu() is dependent on the setting of + * coap_set_show_pdu_output(). + * + * @param level The required minimum logging level. + * @param pdu The PDU to decode. + */ +void coap_show_pdu(coap_log_t level, const coap_pdu_t *pdu); + +/** + * Display the current (D)TLS library linked with and built for version. + * + * @param level The required minimum logging level. + */ +void coap_show_tls_version(coap_log_t level); + +/** + * Build a string containing the current (D)TLS library linked with and + * built for version. + * + * @param buffer The buffer to put the string into. + * @param bufsize The size of the buffer to put the string into. + * + * @return A pointer to the provided buffer. + */ +char *coap_string_tls_version(char *buffer, size_t bufsize); + +/** + * Build a string containing the current (D)TLS library support + * + * @param buffer The buffer to put the string into. + * @param bufsize The size of the buffer to put the string into. + * + * @return A pointer to the provided buffer. + */ +char *coap_string_tls_support(char *buffer, size_t bufsize); + +/** + * Print the address into the defined buffer. + * + * Internal Function. + * + * @param address The address to print. + * @param buffer The buffer to print into. + * @param size The size of the buffer to print into. + * + * @return The amount written into the buffer. + */ +size_t coap_print_addr(const coap_address_t *address, + unsigned char *buffer, size_t size); + +/** @} */ + +/** + * Set the packet loss level for testing. This can be in one of two forms. + * + * Percentage : 0% to 100%. Use the specified probability. + * 0% is send all packets, 100% is drop all packets. + * + * List: A comma separated list of numbers or number ranges that are the + * packets to drop. + * + * @param loss_level The defined loss level (percentage or list). + * + * @return @c 1 If loss level set, @c 0 if there is an error. + */ +int coap_debug_set_packet_loss(const char *loss_level); + +/** + * Check to see whether a packet should be sent or not. + * + * Internal function + * + * @return @c 1 if packet is to be sent, @c 0 if packet is to be dropped. + */ +int coap_debug_send_packet(void); + + +#endif /* COAP_DEBUG_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls.h new file mode 100644 index 00000000000..cbd369dfce6 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls.h @@ -0,0 +1,479 @@ +/* + * coap_dtls.h -- (Datagram) Transport Layer Support for libcoap + * + * Copyright (C) 2016 Olaf Bergmann + * Copyright (C) 2017 Jean-Claude Michelou + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DTLS_H_ +#define COAP_DTLS_H_ + +#include "coap_time.h" +#include "str.h" + +/** + * @defgroup dtls DTLS Support + * API functions for interfacing with DTLS libraries. + * @{ + */ + +typedef struct coap_dtls_pki_t coap_dtls_pki_t; + +#ifndef COAP_DTLS_HINT_LENGTH +#define COAP_DTLS_HINT_LENGTH 128 +#endif + +typedef enum coap_dtls_role_t { + COAP_DTLS_ROLE_CLIENT, /**< Internal function invoked for client */ + COAP_DTLS_ROLE_SERVER /**< Internal function invoked for server */ +} coap_dtls_role_t; + +#define COAP_DTLS_RPK_CERT_CN "RPK" + +/** + * Check whether DTLS is available. + * + * @return @c 1 if support for DTLS is enabled, or @c 0 otherwise. + */ +int coap_dtls_is_supported(void); + +/** + * Check whether TLS is available. + * + * @return @c 1 if support for TLS is enabled, or @c 0 otherwise. + */ +int coap_tls_is_supported(void); + +typedef enum coap_tls_library_t { + COAP_TLS_LIBRARY_NOTLS = 0, /**< No DTLS library */ + COAP_TLS_LIBRARY_TINYDTLS, /**< Using TinyDTLS library */ + COAP_TLS_LIBRARY_OPENSSL, /**< Using OpenSSL library */ + COAP_TLS_LIBRARY_GNUTLS, /**< Using GnuTLS library */ + COAP_TLS_LIBRARY_MBEDTLS, /**< Using Mbed TLS library */ +} coap_tls_library_t; + +/** + * The structure used for returning the underlying (D)TLS library + * information. + */ +typedef struct coap_tls_version_t { + uint64_t version; /**< (D)TLS runtime Library Version */ + coap_tls_library_t type; /**< Library type. One of COAP_TLS_LIBRARY_* */ + uint64_t built_version; /**< (D)TLS Built against Library Version */ +} coap_tls_version_t; + +/** + * Determine the type and version of the underlying (D)TLS library. + * + * @return The version and type of library libcoap was compiled against. + */ +coap_tls_version_t *coap_get_tls_library_version(void); + +/** + * Additional Security setup handler that can be set up by + * coap_context_set_pki(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to do some additional checks/changes/updates. + * + * @param tls_session The security session definition - e.g. SSL * for OpenSSL. + * NULL if server callback. + * This will be dependent on the underlying TLS library - + * see coap_get_tls_library_version() + * @param setup_data A structure containing setup data originally passed into + * coap_context_set_pki() or coap_new_client_session_pki(). + * + * @return @c 1 if successful, else @c 0. + */ +typedef int (*coap_dtls_security_setup_t)(void* tls_session, + coap_dtls_pki_t *setup_data); + +/** + * CN Validation callback that can be set up by coap_context_set_pki(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the CN is allowed. + * CN is the SubjectAltName in the cert, if not present, then the leftmost + * Common Name (CN) component of the subject name. + * NOTE: If using RPK, then the Public Key does not contain a CN, but the + * content of COAP_DTLS_RPK_CERT_CN is presented for the @p cn parameter. + * + * @param cn The determined CN from the certificate + * @param asn1_public_cert The ASN.1 DER encoded X.509 certificate + * @param asn1_length The ASN.1 length + * @param coap_session The CoAP session associated with the certificate update + * @param depth Depth in cert chain. If 0, then client cert, else a CA + * @param validated TLS layer can find no issues if 1 + * @param arg The same as was passed into coap_context_set_pki() + * in setup_data->cn_call_back_arg + * + * @return @c 1 if accepted, else @c 0 if to be rejected. + */ +typedef int (*coap_dtls_cn_callback_t)(const char *cn, + const uint8_t *asn1_public_cert, + size_t asn1_length, + coap_session_t *coap_session, + unsigned int depth, + int validated, + void *arg); + +/** + * The enum used for determining the provided PKI ASN.1 (DER) Private Key + * formats. + */ +typedef enum coap_asn1_privatekey_type_t { + COAP_ASN1_PKEY_NONE, /**< NONE */ + COAP_ASN1_PKEY_RSA, /**< RSA type */ + COAP_ASN1_PKEY_RSA2, /**< RSA2 type */ + COAP_ASN1_PKEY_DSA, /**< DSA type */ + COAP_ASN1_PKEY_DSA1, /**< DSA1 type */ + COAP_ASN1_PKEY_DSA2, /**< DSA2 type */ + COAP_ASN1_PKEY_DSA3, /**< DSA3 type */ + COAP_ASN1_PKEY_DSA4, /**< DSA4 type */ + COAP_ASN1_PKEY_DH, /**< DH type */ + COAP_ASN1_PKEY_DHX, /**< DHX type */ + COAP_ASN1_PKEY_EC, /**< EC type */ + COAP_ASN1_PKEY_HMAC, /**< HMAC type */ + COAP_ASN1_PKEY_CMAC, /**< CMAC type */ + COAP_ASN1_PKEY_TLS1_PRF, /**< TLS1_PRF type */ + COAP_ASN1_PKEY_HKDF /**< HKDF type */ +} coap_asn1_privatekey_type_t; + +/** + * The enum used for determining the PKI key formats. + */ +typedef enum coap_pki_key_t { + COAP_PKI_KEY_PEM = 0, /**< The PKI key type is PEM file */ + COAP_PKI_KEY_ASN1, /**< The PKI key type is ASN.1 (DER) buffer */ + COAP_PKI_KEY_PEM_BUF, /**< The PKI key type is PEM buffer */ + COAP_PKI_KEY_PKCS11, /**< The PKI key type is PKCS11 (DER) */ +} coap_pki_key_t; + +/** + * The structure that holds the PKI PEM definitions. + */ +typedef struct coap_pki_key_pem_t { + const char *ca_file; /**< File location of Common CA in PEM format */ + const char *public_cert; /**< File location of Public Cert */ + const char *private_key; /**< File location of Private Key in PEM format */ +} coap_pki_key_pem_t; + +/** + * The structure that holds the PKI PEM buffer definitions. + * The certificates and private key data must be in PEM format. + * + * Note: The Certs and Key should be NULL terminated strings for + * performance reasons (to save a potential buffer copy) and the length include + * this NULL terminator. It is not a requirement to have the NULL terminator + * though and the length must then reflect the actual data size. + */ +typedef struct coap_pki_key_pem_buf_t { + const uint8_t *ca_cert; /**< PEM buffer Common CA Cert */ + const uint8_t *public_cert; /**< PEM buffer Public Cert, or Public Key if RPK */ + const uint8_t *private_key; /**< PEM buffer Private Key + If RPK and 'EC PRIVATE KEY' this can be used + for both the public_cert and private_key */ + size_t ca_cert_len; /**< PEM buffer CA Cert length */ + size_t public_cert_len; /**< PEM buffer Public Cert length */ + size_t private_key_len; /**< PEM buffer Private Key length */ +} coap_pki_key_pem_buf_t; + +/** + * The structure that holds the PKI ASN.1 (DER) definitions. + */ +typedef struct coap_pki_key_asn1_t { + const uint8_t *ca_cert; /**< ASN1 (DER) Common CA Cert */ + const uint8_t *public_cert; /**< ASN1 (DER) Public Cert, or Public Key if RPK */ + const uint8_t *private_key; /**< ASN1 (DER) Private Key */ + size_t ca_cert_len; /**< ASN1 CA Cert length */ + size_t public_cert_len; /**< ASN1 Public Cert length */ + size_t private_key_len; /**< ASN1 Private Key length */ + coap_asn1_privatekey_type_t private_key_type; /**< Private Key Type */ +} coap_pki_key_asn1_t; + +/** + * The structure that holds the PKI PKCS11 definitions. + */ +typedef struct coap_pki_key_pkcs11_t { + const char *ca; /**< pkcs11: URI for Common CA Certificate */ + const char *public_cert; /**< pkcs11: URI for Public Cert */ + const char *private_key; /**< pkcs11: URI for Private Key */ + const char *user_pin; /**< User pin to access PKCS11. If NULL, then + pin-value= parameter must be set in + pkcs11: URI as a query. */ +} coap_pki_key_pkcs11_t; + +/** + * The structure that holds the PKI key information. + */ +typedef struct coap_dtls_key_t { + coap_pki_key_t key_type; /**< key format type */ + union { + coap_pki_key_pem_t pem; /**< for PEM file keys */ + coap_pki_key_pem_buf_t pem_buf; /**< for PEM memory keys */ + coap_pki_key_asn1_t asn1; /**< for ASN.1 (DER) memory keys */ + coap_pki_key_pkcs11_t pkcs11; /**< for PKCS11 keys */ + } key; +} coap_dtls_key_t; + +/** + * Server Name Indication (SNI) Validation callback that can be set up by + * coap_context_set_pki(). + * Invoked if the SNI is not previously seen and prior to sending a certificate + * set back to the client so that the appropriate certificate set can be used + * based on the requesting SNI. + * + * @param sni The requested SNI + * @param arg The same as was passed into coap_context_set_pki() + * in setup_data->sni_call_back_arg + * + * @return New set of certificates to use, or @c NULL if SNI is to be rejected. + */ +typedef coap_dtls_key_t *(*coap_dtls_pki_sni_callback_t)(const char *sni, + void* arg); + + +#define COAP_DTLS_PKI_SETUP_VERSION 1 /**< Latest PKI setup version */ + +/** + * The structure used for defining the PKI setup data to be used. + */ +struct coap_dtls_pki_t { + uint8_t version; /** Set to COAP_DTLS_PKI_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t verify_peer_cert; /**< 1 if peer cert is to be verified */ + uint8_t check_common_ca; /**< 1 if peer cert is to be signed by + * the same CA as the local cert */ + uint8_t allow_self_signed; /**< 1 if self-signed certs are allowed. + * Ignored if check_common_ca set */ + uint8_t allow_expired_certs; /**< 1 if expired certs are allowed */ + uint8_t cert_chain_validation; /**< 1 if to check cert_chain_verify_depth */ + uint8_t cert_chain_verify_depth; /**< recommended depth is 3 */ + uint8_t check_cert_revocation; /**< 1 if revocation checks wanted */ + uint8_t allow_no_crl; /**< 1 ignore if CRL not there */ + uint8_t allow_expired_crl; /**< 1 if expired crl is allowed */ + uint8_t allow_bad_md_hash; /**< 1 if unsupported MD hashes are allowed */ + uint8_t allow_short_rsa_length; /**< 1 if small RSA keysizes are allowed */ + uint8_t is_rpk_not_cert; /**< 1 is RPK instead of Public Certificate. + * If set, PKI key format type cannot be + * COAP_PKI_KEY_PEM */ + uint8_t reserved[3]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 3 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_PKI_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** CN check callback function. + * If not NULL, is called when the TLS connection has passed the configured + * TLS options above for the application to verify if the CN is valid. + */ + coap_dtls_cn_callback_t validate_cn_call_back; + void *cn_call_back_arg; /**< Passed in to the CN callback function */ + + /** SNI check callback function. + * If not @p NULL, called if the SNI is not previously seen and prior to + * sending a certificate set back to the client so that the appropriate + * certificate set can be used based on the requesting SNI. + */ + coap_dtls_pki_sni_callback_t validate_sni_call_back; + void *sni_call_back_arg; /**< Passed in to the sni callback function */ + + /** Additional Security callback handler that is invoked when libcoap has + * done the standard, defined validation checks at the TLS level, + * If not @p NULL, called from within the TLS Client Hello connection + * setup. + */ + coap_dtls_security_setup_t additional_tls_setup_call_back; + + char* client_sni; /**< If not NULL, SNI to use in client TLS setup. + Owned by the client app and must remain valid + during the call to coap_new_client_session_pki() */ + + coap_dtls_key_t pki_key; /**< PKI key definition */ +}; + +/** + * The structure that holds the Client PSK information. + */ +typedef struct coap_dtls_cpsk_info_t { + coap_bin_const_t identity; + coap_bin_const_t key; +} coap_dtls_cpsk_info_t; + +/** + * Identity Hint Validation callback that can be set up by + * coap_new_client_session_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the Identity Hint is allowed, + * and thus needs to use the appropriate PSK information for the Identity + * Hint for the (D)TLS session. + * Note: Identity Hint is not supported in (D)TLS1.3. + * + * @param hint The server provided Identity Hint + * @param coap_session The CoAP session associated with the Identity Hint + * @param arg The same as was passed into coap_new_client_session_psk2() + * in setup_data->ih_call_back_arg + * + * @return New coap_dtls_cpsk_info_t object or @c NULL on error. + */ +typedef const coap_dtls_cpsk_info_t *(*coap_dtls_ih_callback_t)( + coap_str_const_t *hint, + coap_session_t *coap_session, + void *arg); + +#define COAP_DTLS_CPSK_SETUP_VERSION 1 /**< Latest CPSK setup version */ + +/** + * The structure used for defining the Client PSK setup data to be used. + */ +typedef struct coap_dtls_cpsk_t { + uint8_t version; /** Set to COAP_DTLS_CPSK_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t reserved[7]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 7 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_CPSK_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** Identity Hint check callback function. + * If not NULL, is called when the Identity Hint (TLS1.2 or earlier) is + * provided by the server. + * The appropriate Identity and Pre-shared Key to use can then be returned. + */ + coap_dtls_ih_callback_t validate_ih_call_back; + void *ih_call_back_arg; /**< Passed in to the Identity Hint callback + function */ + + char* client_sni; /**< If not NULL, SNI to use in client TLS setup. + Owned by the client app and must remain valid + during the call to coap_new_client_session_psk2() + Note: Not supported by TinyDTLS. */ + + coap_dtls_cpsk_info_t psk_info; /**< Client PSK definition */ +} coap_dtls_cpsk_t; + +/** + * The structure that holds the Server Pre-Shared Key and Identity + * Hint information. + */ +typedef struct coap_dtls_spsk_info_t { + coap_bin_const_t hint; + coap_bin_const_t key; +} coap_dtls_spsk_info_t; + + +/** + * Identity Validation callback that can be set up by + * coap_context_set_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level, + * but the application needs to check that the Identity is allowed, + * and needs to use the appropriate Pre-Shared Key for the (D)TLS session. + * + * @param identity The client provided Identity + * @param coap_session The CoAP session associated with the Identity Hint + * @param arg The value as passed into coap_context_set_psk2() + * in setup_data->id_call_back_arg + * + * @return New coap_bin_const_t object containing the Pre-Shared Key or + @c NULL on error. + * Note: This information will be duplicated into an internal + * structure. + */ +typedef const coap_bin_const_t *(*coap_dtls_id_callback_t)( + coap_bin_const_t *identity, + coap_session_t *coap_session, + void *arg); +/** + * PSK SNI callback that can be set up by coap_context_set_psk2(). + * Invoked when libcoap has done the validation checks at the TLS level + * and the application needs to:- + * a) check that the SNI is allowed + * b) provide the appropriate PSK information for the (D)TLS session. + * + * @param sni The client provided SNI + * @param coap_session The CoAP session associated with the SNI + * @param arg The same as was passed into coap_context_set_psk2() + * in setup_data->sni_call_back_arg + * + * @return New coap_dtls_spsk_info_t object or @c NULL on error. + */ +typedef const coap_dtls_spsk_info_t *(*coap_dtls_psk_sni_callback_t)( + const char *sni, + coap_session_t *coap_session, + void *arg); + +#define COAP_DTLS_SPSK_SETUP_VERSION 1 /**< Latest SPSK setup version */ + +/** + * The structure used for defining the Server PSK setup data to be used. + */ +typedef struct coap_dtls_spsk_t { + uint8_t version; /** Set to COAP_DTLS_SPSK_SETUP_VERSION + to support this version of the struct */ + + /* Options to enable different TLS functionality in libcoap */ + uint8_t reserved[7]; /**< Reserved - must be set to 0 for + future compatibility */ + /* Size of 7 chosen to align to next + * parameter, so if newly defined option + * it can use one of the reserverd slot so + * no need to change + * COAP_DTLS_SPSK_SETUP_VERSION and just + * decrement the reserved[] count. + */ + + /** Identity check callback function. + * If not @p NULL, is called when the Identity is provided by the client. + * The appropriate Pre-Shared Key to use can then be returned. + */ + coap_dtls_id_callback_t validate_id_call_back; + void *id_call_back_arg; /**< Passed in to the Identity callback function */ + + /** SNI check callback function. + * If not @p NULL, called if the SNI is not previously seen and prior to + * sending PSK information back to the client so that the appropriate + * PSK information can be used based on the requesting SNI. + */ + coap_dtls_psk_sni_callback_t validate_sni_call_back; + void *sni_call_back_arg; /**< Passed in to the SNI callback function */ + + coap_dtls_spsk_info_t psk_info; /**< Server PSK definition */ +} coap_dtls_spsk_t; + + +/** @} */ + +/** + * @ingroup logging + * Sets the (D)TLS logging level to the specified @p level. + * Note: coap_log_level() will influence output if at a specified level. + * + * @param level The logging level to use - LOG_* + */ +void coap_dtls_set_log_level(int level); + +/** + * @ingroup logging + * Get the current (D)TLS logging. + * + * @return The current log level (one of LOG_*). + */ +int coap_dtls_get_log_level(void); + + +#endif /* COAP_DTLS_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls_internal.h new file mode 100644 index 00000000000..8ea09a4eb3e --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_dtls_internal.h @@ -0,0 +1,345 @@ +/* + * coap_dtls_internal.h -- (Datagram) Transport Layer Support for libcoap + * + * Copyright (C) 2016 Olaf Bergmann + * Copyright (C) 2017 Jean-Claude Michelou + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_DTLS_INTERNAL_H_ +#define COAP_DTLS_INTERNAL_H_ + +/** + * @defgroup dtls_internal DTLS Support (Internal) + * CoAP DTLS Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/* https://tools.ietf.org/html/rfc6347#section-4.2.4.1 */ +#ifndef COAP_DTLS_RETRANSMIT_MS +#define COAP_DTLS_RETRANSMIT_MS 1000 +#endif +#ifndef COAP_DTLS_RETRANSMIT_TOTAL_MS +#define COAP_DTLS_RETRANSMIT_TOTAL_MS 60000 +#endif + +#define COAP_DTLS_RETRANSMIT_COAP_TICKS (COAP_DTLS_RETRANSMIT_MS * COAP_TICKS_PER_SECOND / 1000) + +/** + * Creates a new DTLS context for the given @p coap_context. This function + * returns a pointer to a new DTLS context object or @c NULL on error. + * + * @param coap_context The CoAP context where the DTLS object shall be used. + * + * @return A DTLS context object or @c NULL on error. + */ +void * +coap_dtls_new_context(coap_context_t *coap_context); + +/** + * Set the DTLS context's default server PSK information. + * This does the PSK specifics following coap_dtls_new_context(). + * + * @param coap_context The CoAP context. + * @param setup_data A structure containing setup data originally passed into + * coap_context_set_psk2(). + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_spsk(coap_context_t *coap_context, + coap_dtls_spsk_t *setup_data); + +/** + * Set the DTLS context's default client PSK information. + * This does the PSK specifics following coap_dtls_new_context(). + * + * @param coap_context The CoAP context. + * @param setup_data A structure containing setup data originally passed into + * coap_new_client_session_psk2(). + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_cpsk(coap_context_t *coap_context, + coap_dtls_cpsk_t *setup_data); + +/** + * Set the DTLS context's default server PKI information. + * This does the PKI specifics following coap_dtls_new_context(). + * If @p COAP_DTLS_ROLE_SERVER, then the information will get put into the + * TLS library's context (from which sessions are derived). + * If @p COAP_DTLS_ROLE_CLIENT, then the information will get put into the + * TLS library's session. + * + * @param coap_context The CoAP context. + * @param setup_data Setup information defining how PKI is to be setup. + * Required parameter. If @p NULL, PKI will not be + * set up. + * @param role One of @p COAP_DTLS_ROLE_CLIENT or @p COAP_DTLS_ROLE_SERVER + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_pki(coap_context_t *coap_context, + const coap_dtls_pki_t *setup_data, + const coap_dtls_role_t role); + +/** + * Set the dtls context's default Root CA information for a client or server. + * + * @param coap_context The current coap_context_t object. + * @param ca_file If not @p NULL, is the full path name of a PEM encoded + * file containing all the Root CAs to be used. + * @param ca_dir If not @p NULL, points to a directory containing PEM + * encoded files containing all the Root CAs to be used. + * + * @return @c 1 if successful, else @c 0. + */ + +int +coap_dtls_context_set_pki_root_cas(coap_context_t *coap_context, + const char *ca_file, + const char *ca_dir); + +/** + * Check whether one of the coap_dtls_context_set_{psk|pki}() functions have + * been called. + * + * @param coap_context The current coap_context_t object. + * + * @return @c 1 if coap_dtls_context_set_{psk|pki}() called, else @c 0. + */ + +int coap_dtls_context_check_keys_enabled(coap_context_t *coap_context); + +/** + * Releases the storage allocated for @p dtls_context. + * + * @param dtls_context The DTLS context as returned by coap_dtls_new_context(). + */ +void coap_dtls_free_context(void *dtls_context); + +/** + * Create a new client-side session. This should send a HELLO to the server. + * + * @param coap_session The CoAP session. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. +*/ +void *coap_dtls_new_client_session(coap_session_t *coap_session); + +/** + * Create a new DTLS server-side session. + * Called after coap_dtls_hello() has returned @c 1, signalling that a validated + * HELLO was received from a client. + * This should send a HELLO to the server. + * + * @param coap_session The CoAP session. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the DTLS session. + */ +void *coap_dtls_new_server_session(coap_session_t *coap_session); + +/** + * Terminates the DTLS session (may send an ALERT if necessary) then frees the + * underlying TLS library object containing security parameters for the session. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_free_session(coap_session_t *coap_session); + +/** + * Notify of a change in the CoAP session's MTU, for example after + * a PMTU update. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_session_update_mtu(coap_session_t *coap_session); + +/** + * Send data to a DTLS peer. + * + * @param coap_session The CoAP session. + * @param data pointer to data. + * @param data_len Number of bytes to send. + * + * @return @c 0 if this would be blocking, @c -1 if there is an error or the + * number of cleartext bytes sent. + */ +int coap_dtls_send(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Check if timeout is handled per CoAP session or per CoAP context. + * + * @return @c 1 of timeout and retransmit is per context, @c 0 if it is + * per session. + */ +int coap_dtls_is_context_timeout(void); + +/** + * Do all pending retransmits and get next timeout + * + * @param dtls_context The DTLS context. + * + * @return @c 0 if no event is pending or date of the next retransmit. + */ +coap_tick_t coap_dtls_get_context_timeout(void *dtls_context); + +/** + * Get next timeout for this session. + * + * @param coap_session The CoAP session. + * @param now The current time in ticks. + * + * @return @c 0 If no event is pending or ticks time of the next retransmit. + */ +coap_tick_t coap_dtls_get_timeout(coap_session_t *coap_session, + coap_tick_t now); + +/** + * Handle a DTLS timeout expiration. + * + * @param coap_session The CoAP session. + */ +void coap_dtls_handle_timeout(coap_session_t *coap_session); + +/** + * Handling incoming data from a DTLS peer. + * + * @param coap_session The CoAP session. + * @param data Encrypted datagram. + * @param data_len Encrypted datagram size. + * + * @return Result of coap_handle_dgram on the decrypted CoAP PDU + * or @c -1 for error. + */ +int coap_dtls_receive(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Handling client HELLO messages from a new candiate peer. + * Note that session->tls is empty. + * + * @param coap_session The CoAP session. + * @param data Encrypted datagram. + * @param data_len Encrypted datagram size. + * + * @return @c 0 if a cookie verification message has been sent, @c 1 if the + * HELLO contains a valid cookie and a server session should be created, + * @c -1 if the message is invalid. + */ +int coap_dtls_hello(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len); + +/** + * Get DTLS overhead over cleartext PDUs. + * + * @param coap_session The CoAP session. + * + * @return Maximum number of bytes added by DTLS layer. + */ +unsigned int coap_dtls_get_overhead(coap_session_t *coap_session); + +/** + * Create a new TLS client-side session. + * + * @param coap_session The CoAP session. + * @param connected Updated with whether the connection is connected yet or not. + * @c 0 is not connected, @c 1 is connected. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. +*/ +void *coap_tls_new_client_session(coap_session_t *coap_session, int *connected); + +/** + * Create a TLS new server-side session. + * + * @param coap_session The CoAP session. + * @param connected Updated with whether the connection is connected yet or not. + * @c 0 is not connected, @c 1 is connected. + * + * @return Opaque handle to underlying TLS library object containing security + * parameters for the session. + */ +void *coap_tls_new_server_session(coap_session_t *coap_session, int *connected); + +/** + * Terminates the TLS session (may send an ALERT if necessary) then frees the + * underlying TLS library object containing security parameters for the session. + * + * @param coap_session The CoAP session. + */ +void coap_tls_free_session( coap_session_t *coap_session ); + +/** + * Send data to a TLS peer, with implicit flush. + * + * @param coap_session The CoAP session. + * @param data Pointer to data. + * @param data_len Number of bytes to send. + * + * @return @c 0 if this should be retried, @c -1 if there is an error + * or the number of cleartext bytes sent. + */ +ssize_t coap_tls_write(coap_session_t *coap_session, + const uint8_t *data, + size_t data_len + ); + +/** + * Read some data from a TLS peer. + * + * @param coap_session The CoAP session. + * @param data Pointer to data. + * @param data_len Maximum number of bytes to read. + * + * @return @c 0 if this should be retried, @c -1 if there is an error + * or the number of cleartext bytes read. + */ +ssize_t coap_tls_read(coap_session_t *coap_session, + uint8_t *data, + size_t data_len + ); + +/** + * Initialize the underlying (D)TLS Library layer. + * + */ +void coap_dtls_startup(void); + +/** + * Close down the underlying (D)TLS Library layer. + * + */ +void coap_dtls_shutdown(void); + +/** + * Get the actual (D)TLS object for the session. + * + * @param session The session. + * @param tls_lib Updated with the library type. + * + * @return The TLS information. + */ +void *coap_dtls_get_tls(const coap_session_t *session, + coap_tls_library_t *tls_lib); + +/** @} */ + +#endif /* COAP_DTLS_INTERNAL_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_event.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_event.h new file mode 100644 index 00000000000..89b2a63967c --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_event.h @@ -0,0 +1,104 @@ +/* + * coap_event.h -- libcoap Event API + * + * Copyright (C) 2016 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_EVENT_H_ +#define COAP_EVENT_H_ + +#include "libcoap.h" + +/** + * @defgroup events Event API + * API functions for event delivery from lower-layer library functions. + * @{ + */ + +/** + * Scalar type to represent different events, e.g. DTLS events or + * retransmission timeouts. + */ + typedef unsigned int coap_event_t; + +/** + * (D)TLS events for COAP_PROTO_DTLS and COAP_PROTO_TLS + */ +#define COAP_EVENT_DTLS_CLOSED 0x0000 +#define COAP_EVENT_DTLS_CONNECTED 0x01DE +#define COAP_EVENT_DTLS_RENEGOTIATE 0x01DF +#define COAP_EVENT_DTLS_ERROR 0x0200 + +/** + * TCP events for COAP_PROTO_TCP and COAP_PROTO_TLS + */ +#define COAP_EVENT_TCP_CONNECTED 0x1001 +#define COAP_EVENT_TCP_CLOSED 0x1002 +#define COAP_EVENT_TCP_FAILED 0x1003 + +/** + * CSM exchange events for reliable protocols only + */ +#define COAP_EVENT_SESSION_CONNECTED 0x2001 +#define COAP_EVENT_SESSION_CLOSED 0x2002 +#define COAP_EVENT_SESSION_FAILED 0x2003 + +/** + * BLOCK2 receive errors + */ +#define COAP_EVENT_PARTIAL_BLOCK 0x3001 + +/** + * Type for event handler functions that can be registered with a CoAP + * context using the unction coap_set_event_handler(). When called by + * the library, the first argument will be the current coap_session_t object + * which is associated with the original CoAP context. The second parameter + * is the event type. + */ +typedef int (*coap_event_handler_t)(coap_session_t *session, + const coap_event_t event); + +/** + * Registers the function @p hnd as callback for events from the given + * CoAP context @p context. Any event handler that has previously been + * registered with @p context will be overwritten by this operation. + * + * @param context The CoAP context to register the event handler with. + * @param hnd The event handler to be registered. @c NULL if to be + * de-registered. + */ +void coap_register_event_handler(coap_context_t *context, + coap_event_handler_t hnd); + +/** @} */ + +/** + * Registers the function @p hnd as callback for events from the given + * CoAP context @p context. Any event handler that has previously been + * registered with @p context will be overwritten by this operation. + * + * @deprecated Use coap_register_event_handler() instead. + * + * @param context The CoAP context to register the event handler with. + * @param hnd The event handler to be registered. + */ +COAP_DEPRECATED +void coap_set_event_handler(coap_context_t *context, + coap_event_handler_t hnd); + +/** + * Clears the event handler registered with @p context. + * + * @deprecated Use coap_register_event_handler() instead with NULL for hnd. + * + * @param context The CoAP context whose event handler is to be removed. + */ +COAP_DEPRECATED +void coap_clear_event_handler(coap_context_t *context); + +#endif /* COAP_EVENT_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_forward_decls.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_forward_decls.h new file mode 100644 index 00000000000..3bedbf7899a --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_forward_decls.h @@ -0,0 +1,107 @@ +/* + * coap_forward_decls.h -- Forward declarations of structures that are + * opaque to application programming that use libcoap. + * + * Copyright (C) 2019-2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_forward_decls.h + * @brief COAP forward definitions + */ + +#ifndef COAP_FORWARD_DECLS_H_ +#define COAP_FORWARD_DECLS_H_ + +/* + * Define the forward declations for the structures (even non-opaque) + * so that applications (using coap.h) as well as libcoap builds + * can reference them (and makes .h file dependencies a lot simpler). + */ +struct coap_address_t; +struct coap_bin_const_t; +struct coap_dtls_pki_t; +struct coap_str_const_t; +struct coap_string_t; + +/* + * typedef all the opaque structures that are defined in coap_*_internal.h + */ + +/* ************* coap_async_internal.h ***************** */ + +/** + * Async Entry information. + */ +typedef struct coap_async_t coap_async_t; + +/* ************* coap_block_internal.h ***************** */ + +/* + * Block handling information. + */ +typedef struct coap_lg_xmit_t coap_lg_xmit_t; +typedef struct coap_lg_crcv_t coap_lg_crcv_t; +typedef struct coap_lg_srcv_t coap_lg_srcv_t; + +/* ************* coap_cache_internal.h ***************** */ + +/* + * Cache Entry information. + */ +typedef struct coap_cache_entry_t coap_cache_entry_t; +typedef struct coap_cache_key_t coap_cache_key_t; + +/* ************* coap_io_internal.h ***************** */ + +/** + * coap_socket_t and coap_packet_t information. + */ +typedef struct coap_packet_t coap_packet_t; +typedef struct coap_socket_t coap_socket_t; + +/* ************* coap_net_internal.h ***************** */ + +/* + * Net information. + */ +typedef struct coap_context_t coap_context_t; +typedef struct coap_queue_t coap_queue_t; + +/* ************* coap_pdu_internal.h ***************** */ + +/** + * PDU information. + */ +typedef struct coap_pdu_t coap_pdu_t; + +/* ************* coap_resource_internal.h ***************** */ + +/* + * Resource information. + */ +typedef struct coap_attr_t coap_attr_t; +typedef struct coap_resource_t coap_resource_t; + +/* ************* coap_session_internal.h ***************** */ + +/* + * Session information. + */ +typedef struct coap_addr_hash_t coap_addr_hash_t; +typedef struct coap_endpoint_t coap_endpoint_t; +typedef struct coap_session_t coap_session_t; + +/* ************* coap_subscribe_internal.h ***************** */ + +/* + * Observe subscriber information. + */ +typedef struct coap_subscription_t coap_subscription_t; + +#endif /* COAP_FORWARD_DECLS_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_hashkey.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_hashkey.h new file mode 100644 index 00000000000..11a797bde7a --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_hashkey.h @@ -0,0 +1,61 @@ +/* + * coap_hashkey.h -- definition of hash key type and helper functions + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_hashkey.h + * @brief definition of hash key type and helper functions + */ + +#ifndef COAP_HASHKEY_H_ +#define COAP_HASHKEY_H_ + +#include "libcoap.h" +#include "uthash.h" +#include "str.h" + +typedef unsigned char coap_key_t[4]; + +#ifndef coap_hash +/** + * Calculates a fast hash over the given string @p s of length @p len and stores + * the result into @p h. Depending on the exact implementation, this function + * cannot be used as one-way function to check message integrity or simlar. + * + * @param s The string used for hash calculation. + * @param len The length of @p s. + * @param h The result buffer to store the calculated hash key. + */ +void coap_hash_impl(const unsigned char *s, size_t len, coap_key_t h); + +#define coap_hash(String,Length,Result) \ + coap_hash_impl((String),(Length),(Result)) + +/* This is used to control the pre-set hash-keys for resources. */ +#define COAP_DEFAULT_HASH +#else +#undef COAP_DEFAULT_HASH +#endif /* coap_hash */ + +/** + * Calls coap_hash() with given @c coap_string_t object as parameter. + * + * @param Str Must contain a pointer to a coap string object. + * @param H A coap_key_t object to store the result. + * + * @hideinitializer + */ +#define coap_str_hash(Str,H) { \ + assert(Str); \ + memset((H), 0, sizeof(coap_key_t)); \ + coap_hash((Str)->s, (Str)->length, (H)); \ + } + +#endif /* COAP_HASHKEY_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_internal.h new file mode 100644 index 00000000000..5eee5c12867 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_internal.h @@ -0,0 +1,65 @@ +/* + * coap_internal.h -- Structures, Enums & Functions that are not exposed to + * application programming + * + * Copyright (C) 2019-2021 Jon Shallow + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/* + * All libcoap library files should include this file which then pulls in all + * of the other appropriate header files. + * + * Note: This file should never be included in application code (with the + * possible exception of internal test suites). + */ + +/** + * @file coap_internal.h + * @brief Pulls together all the internal only header files + */ + +#ifndef COAP_INTERNAL_H_ +#define COAP_INTERNAL_H_ + +#include "coap_config.h" + +/* + * Correctly set up assert() based on NDEBUG for libcoap + */ +#if defined(HAVE_ASSERT_H) && !defined(assert) +# include +#endif + +#include "coap3/coap.h" + +/* + * Include all the header files that are for internal use only. + */ + +/* Not defined in coap.h - internal usage .h files */ +#include "utlist.h" +#include "uthash.h" +#include "coap_hashkey.h" +#include "coap_mutex.h" + +/* Specifically defined internal .h files */ +#include "coap_asn1_internal.h" +#include "coap_async_internal.h" +#include "coap_block_internal.h" +#include "coap_cache_internal.h" +#include "coap_dtls_internal.h" +#include "coap_io_internal.h" +#include "coap_net_internal.h" +#include "coap_pdu_internal.h" +#include "coap_session_internal.h" +#include "coap_resource_internal.h" +#include "coap_session_internal.h" +#include "coap_subscribe_internal.h" +#include "coap_tcp_internal.h" + +#endif /* COAP_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io.h new file mode 100644 index 00000000000..b27921f8be1 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io.h @@ -0,0 +1,72 @@ +/* + * coap_io.h -- Default network I/O functions for libcoap + * + * Copyright (C) 2012-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_IO_H_ +#define COAP_IO_H_ + +#include + +#include "address.h" + +#ifdef RIOT_VERSION +#include "net/gnrc.h" +#endif /* RIOT_VERSION */ + +#ifndef COAP_RXBUFFER_SIZE +#define COAP_RXBUFFER_SIZE 1472 +#endif /* COAP_RXBUFFER_SIZE */ + +/* + * It may may make sense to define this larger on busy systems + * (lots of sessions, large number of which are active), by using + * -DCOAP_MAX_EPOLL_EVENTS=nn at compile time. + */ +#ifndef COAP_MAX_EPOLL_EVENTS +#define COAP_MAX_EPOLL_EVENTS 10 +#endif /* COAP_MAX_EPOLL_EVENTS */ + +#ifdef _WIN32 +typedef SOCKET coap_fd_t; +#define coap_closesocket closesocket +#define COAP_SOCKET_ERROR SOCKET_ERROR +#define COAP_INVALID_SOCKET INVALID_SOCKET +#else +typedef int coap_fd_t; +#define coap_closesocket close +#define COAP_SOCKET_ERROR (-1) +#define COAP_INVALID_SOCKET (-1) +#endif + +typedef uint16_t coap_socket_flags_t; + +typedef struct coap_addr_tuple_t { + coap_address_t remote; /**< remote address and port */ + coap_address_t local; /**< local address and port */ +} coap_addr_tuple_t; + +const char *coap_socket_strerror( void ); + +/** + * Check whether TCP is available. + * + * @return @c 1 if support for TCP is enabled, or @c 0 otherwise. + */ +int coap_tcp_is_supported(void); + +typedef enum { + COAP_NACK_TOO_MANY_RETRIES, + COAP_NACK_NOT_DELIVERABLE, + COAP_NACK_RST, + COAP_NACK_TLS_FAILED, + COAP_NACK_ICMP_ISSUE +} coap_nack_reason_t; + +#endif /* COAP_IO_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io_internal.h new file mode 100644 index 00000000000..241ef7f9955 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_io_internal.h @@ -0,0 +1,168 @@ +/* + * coap_io.h -- Default network I/O functions for libcoap + * + * Copyright (C) 2012-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_IO_INTERNAL_H_ +#define COAP_IO_INTERNAL_H_ + +#include + +#include "address.h" + +#ifdef RIOT_VERSION +#include "net/gnrc.h" +#endif /* RIOT_VERSION */ + +struct coap_socket_t { +#if defined(WITH_LWIP) + struct udp_pcb *pcb; +#elif defined(WITH_CONTIKI) + void *conn; +#else + coap_fd_t fd; +#endif /* WITH_LWIP */ +#if defined(RIOT_VERSION) + gnrc_pktsnip_t *pkt; /* pointer to received packet for processing */ +#endif /* RIOT_VERSION */ + coap_socket_flags_t flags; + coap_session_t *session; /* Used by the epoll logic for an active session. */ + coap_endpoint_t *endpoint; /* Used by the epoll logic for a listening + endpoint. */ +}; + +/** + * coap_socket_flags_t values + */ +#define COAP_SOCKET_EMPTY 0x0000 /**< the socket is not used */ +#define COAP_SOCKET_NOT_EMPTY 0x0001 /**< the socket is not empty */ +#define COAP_SOCKET_BOUND 0x0002 /**< the socket is bound */ +#define COAP_SOCKET_CONNECTED 0x0004 /**< the socket is connected */ +#define COAP_SOCKET_WANT_READ 0x0010 /**< non blocking socket is waiting for reading */ +#define COAP_SOCKET_WANT_WRITE 0x0020 /**< non blocking socket is waiting for writing */ +#define COAP_SOCKET_WANT_ACCEPT 0x0040 /**< non blocking server socket is waiting for accept */ +#define COAP_SOCKET_WANT_CONNECT 0x0080 /**< non blocking client socket is waiting for connect */ +#define COAP_SOCKET_CAN_READ 0x0100 /**< non blocking socket can now read without blocking */ +#define COAP_SOCKET_CAN_WRITE 0x0200 /**< non blocking socket can now write without blocking */ +#define COAP_SOCKET_CAN_ACCEPT 0x0400 /**< non blocking server socket can now accept without blocking */ +#define COAP_SOCKET_CAN_CONNECT 0x0800 /**< non blocking client socket can now connect without blocking */ +#define COAP_SOCKET_MULTICAST 0x1000 /**< socket is used for multicast communication */ + +coap_endpoint_t *coap_malloc_endpoint( void ); +void coap_mfree_endpoint( coap_endpoint_t *ep ); + +const char *coap_socket_format_errno(int error); + +int +coap_socket_connect_udp(coap_socket_t *sock, + const coap_address_t *local_if, + const coap_address_t *server, + int default_port, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +int +coap_socket_bind_udp(coap_socket_t *sock, + const coap_address_t *listen_addr, + coap_address_t *bound_addr ); + +void coap_socket_close(coap_socket_t *sock); + +ssize_t +coap_socket_send( coap_socket_t *sock, coap_session_t *session, + const uint8_t *data, size_t data_len ); + +ssize_t +coap_socket_write(coap_socket_t *sock, const uint8_t *data, size_t data_len); + +ssize_t +coap_socket_read(coap_socket_t *sock, uint8_t *data, size_t data_len); + +void +coap_epoll_ctl_mod(coap_socket_t *sock, uint32_t events, const char *func); + +#ifdef WITH_LWIP +ssize_t +coap_socket_send_pdu( coap_socket_t *sock, coap_session_t *session, + coap_pdu_t *pdu ); +#endif + +/** + * Function interface for data transmission. This function returns the number of + * bytes that have been transmitted, or a value less than zero on error. + * + * @param sock Socket to send data with + * @param session Addressing information for unconnected sockets, or NULL + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_network_send( coap_socket_t *sock, const coap_session_t *session, const uint8_t *data, size_t datalen ); + +/** + * Function interface for reading data. This function returns the number of + * bytes that have been read, or a value less than zero on error. In case of an + * error, @p *packet is set to NULL. + * + * @param sock Socket to read data from + * @param packet Received packet metadata and payload. src and dst should be preset. + * + * @return The number of bytes received on success, or a value less than + * zero on error. + */ +ssize_t coap_network_read( coap_socket_t *sock, coap_packet_t *packet ); + +#ifndef coap_mcast_interface +# define coap_mcast_interface(Local) 0 +#endif + +/** + * Given a packet, set msg and msg_len to an address and length of the packet's + * data in memory. + * */ +void coap_packet_get_memmapped(coap_packet_t *packet, + unsigned char **address, + size_t *length); + +#ifdef WITH_LWIP +/** + * Get the pbuf of a packet. The caller takes over responsibility for freeing + * the pbuf. + */ +struct pbuf *coap_packet_extract_pbuf(coap_packet_t *packet); +#endif + +#if defined(WITH_LWIP) +/* + * This is only included in coap_io.h instead of .c in order to be available for + * sizeof in lwippools.h. + * Simple carry-over of the incoming pbuf that is later turned into a node. + * + * Source address data is currently side-banded via ip_current_dest_addr & co + * as the packets have limited lifetime anyway. + */ +struct coap_packet_t { + struct pbuf *pbuf; + const coap_endpoint_t *local_interface; + coap_addr_tuple_t addr_info; /**< local and remote addresses */ + int ifindex; /**< the interface index */ +// uint16_t srcport; +}; +#else +struct coap_packet_t { + coap_addr_tuple_t addr_info; /**< local and remote addresses */ + int ifindex; /**< the interface index */ + size_t length; /**< length of payload */ + unsigned char payload[COAP_RXBUFFER_SIZE]; /**< payload */ +}; +#endif + +#endif /* COAP_IO_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_mutex.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_mutex.h new file mode 100644 index 00000000000..44084fecb1c --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_mutex.h @@ -0,0 +1,59 @@ +/* + * coap_mutex.h -- mutex utilities + * + * Copyright (C) 2019 Jon Shallow + * 2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_mutex.h + * @brief COAP mutex mechanism wrapper + */ + +#ifndef COAP_MUTEX_H_ +#define COAP_MUTEX_H_ + +/* + * Mutexes are currently only used if there is a constrained stack, + * and large static variables (instead of the large variable being on + * the stack) need to be protected. + */ +#if COAP_CONSTRAINED_STACK + +#if defined(HAVE_PTHREAD_H) && defined(HAVE_PTHREAD_MUTEX_LOCK) +#include + +typedef pthread_mutex_t coap_mutex_t; +#define COAP_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER +#define coap_mutex_lock(a) pthread_mutex_lock(a) +#define coap_mutex_trylock(a) pthread_mutex_trylock(a) +#define coap_mutex_unlock(a) pthread_mutex_unlock(a) + +#elif defined(RIOT_VERSION) +/* use RIOT's mutex API */ +#include + +typedef mutex_t coap_mutex_t; +#define COAP_MUTEX_INITIALIZER MUTEX_INIT +#define coap_mutex_lock(a) mutex_lock(a) +#define coap_mutex_trylock(a) mutex_trylock(a) +#define coap_mutex_unlock(a) mutex_unlock(a) + +#else +/* define stub mutex functions */ +typedef int coap_mutex_t; +#define COAP_MUTEX_INITIALIZER 0 +#define coap_mutex_lock(a) *(a) = 1 +#define coap_mutex_trylock(a) *(a) = 1 +#define coap_mutex_unlock(a) *(a) = 0 + +#endif /* !RIOT_VERSION && !HAVE_PTHREAD_H && !HAVE_PTHREAD_MUTEX_LOCK */ + +#endif /* COAP_CONSTRAINED_STACK */ + +#endif /* COAP_MUTEX_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_net_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_net_internal.h new file mode 100644 index 00000000000..bf243f3d022 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_net_internal.h @@ -0,0 +1,366 @@ +/* + * coap_context_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_net_internal.h + * @brief COAP net internal information + */ + +#ifndef COAP_NET_INTERNAL_H_ +#define COAP_NET_INTERNAL_H_ + +/** + * @defgroup context_internal Context Handling (Internal) + * CoAP Context Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/** + * Queue entry + */ +struct coap_queue_t { + struct coap_queue_t *next; + coap_tick_t t; /**< when to send PDU for the next time */ + unsigned char retransmit_cnt; /**< retransmission counter, will be removed + * when zero */ + unsigned int timeout; /**< the randomized timeout value */ + coap_session_t *session; /**< the CoAP session */ + coap_mid_t id; /**< CoAP message id */ + coap_pdu_t *pdu; /**< the CoAP PDU to send */ +}; + +/** + * The CoAP stack's global state is stored in a coap_context_t object. + */ +struct coap_context_t { + coap_opt_filter_t known_options; + coap_resource_t *resources; /**< hash table or list of known + resources */ + coap_resource_t *unknown_resource; /**< can be used for handling + unknown resources */ + coap_resource_t *proxy_uri_resource; /**< can be used for handling + proxy URI resources */ + coap_resource_release_userdata_handler_t release_userdata; + /**< function to release user_data + when resource is deleted */ + +#ifndef WITHOUT_ASYNC + /** + * list of asynchronous message ids */ + coap_async_t *async_state; +#endif /* WITHOUT_ASYNC */ + + /** + * The time stamp in the first element of the sendqeue is relative + * to sendqueue_basetime. */ + coap_tick_t sendqueue_basetime; + coap_queue_t *sendqueue; + coap_endpoint_t *endpoint; /**< the endpoints used for listening */ + coap_session_t *sessions; /**< client sessions */ + +#ifdef WITH_CONTIKI + struct uip_udp_conn *conn; /**< uIP connection object */ + struct etimer retransmit_timer; /**< fires when the next packet must be + sent */ + struct etimer notify_timer; /**< used to check resources periodically */ +#endif /* WITH_CONTIKI */ + +#ifdef WITH_LWIP + uint8_t timer_configured; /**< Set to 1 when a retransmission is + * scheduled using lwIP timers for this + * context, otherwise 0. */ +#endif /* WITH_LWIP */ + + coap_response_handler_t response_handler; + coap_nack_handler_t nack_handler; + coap_ping_handler_t ping_handler; + coap_pong_handler_t pong_handler; + + /** + * Callback function that is used to signal events to the + * application. This field is set by coap_set_event_handler(). + */ + coap_event_handler_t handle_event; + + ssize_t (*network_send)(coap_socket_t *sock, const coap_session_t *session, + const uint8_t *data, size_t datalen); + + ssize_t (*network_read)(coap_socket_t *sock, coap_packet_t *packet); + + size_t(*get_client_psk)(const coap_session_t *session, const uint8_t *hint, + size_t hint_len, uint8_t *identity, + size_t *identity_len, size_t max_identity_len, + uint8_t *psk, size_t max_psk_len); + size_t(*get_server_psk)(const coap_session_t *session, + const uint8_t *identity, size_t identity_len, + uint8_t *psk, size_t max_psk_len); + size_t(*get_server_hint)(const coap_session_t *session, uint8_t *hint, + size_t max_hint_len); + + void *dtls_context; + + coap_dtls_spsk_t spsk_setup_data; /**< Contains the initial PSK server setup + data */ + + unsigned int session_timeout; /**< Number of seconds of inactivity after + which an unused session will be closed. + 0 means use default. */ + unsigned int max_idle_sessions; /**< Maximum number of simultaneous unused + sessions per endpoint. 0 means no + maximum. */ + unsigned int max_handshake_sessions; /**< Maximum number of simultaneous + negotating sessions per endpoint. 0 + means use default. */ + unsigned int ping_timeout; /**< Minimum inactivity time before + sending a ping message. 0 means + disabled. */ + unsigned int csm_timeout; /**< Timeout for waiting for a CSM from + the remote side. 0 means disabled. */ + uint8_t observe_pending; /**< Observe response pending */ + uint8_t block_mode; /**< Zero or more COAP_BLOCK_ or'd options */ + uint64_t etag; /**< Next ETag to use */ + + coap_cache_entry_t *cache; /**< CoAP cache-entry cache */ + uint16_t *cache_ignore_options; /**< CoAP options to ignore when creating a + cache-key */ + size_t cache_ignore_count; /**< The number of CoAP options to ignore + when creating a cache-key */ + void *app; /**< application-specific data */ +#ifdef COAP_EPOLL_SUPPORT + int epfd; /**< External FD for epoll */ + int eptimerfd; /**< Internal FD for timeout */ + coap_tick_t next_timeout; /**< When the next timeout is to occur */ +#endif /* COAP_EPOLL_SUPPORT */ +}; + +/** + * Adds @p node to given @p queue, ordered by variable t in @p node. + * + * @param queue Queue to add to. + * @param node Node entry to add to Queue. + * + * @return @c 1 added to queue, @c 0 failure. + */ +int coap_insert_node(coap_queue_t **queue, coap_queue_t *node); + +/** + * Destroys specified @p node. + * + * @param node Node entry to remove. + * + * @return @c 1 node deleted from queue, @c 0 failure. + */ +int coap_delete_node(coap_queue_t *node); + +/** + * Removes all items from given @p queue and frees the allocated storage. + * + * Internal function. + * + * @param queue The queue to delete. + */ +void coap_delete_all(coap_queue_t *queue); + +/** + * Creates a new node suitable for adding to the CoAP sendqueue. + * + * @return New node entry, or @c NULL if failure. + */ +coap_queue_t *coap_new_node(void); + +/** + * Set sendqueue_basetime in the given context object @p ctx to @p now. This + * function returns the number of elements in the queue head that have timed + * out. + */ +unsigned int coap_adjust_basetime(coap_context_t *ctx, coap_tick_t now); + +/** + * Returns the next pdu to send without removing from sendqeue. + */ +coap_queue_t *coap_peek_next( coap_context_t *context ); + +/** + * Returns the next pdu to send and removes it from the sendqeue. + */ +coap_queue_t *coap_pop_next( coap_context_t *context ); + +/** + * Handles retransmissions of confirmable messages + * + * @param context The CoAP context. + * @param node The node to retransmit. + * + * @return The message id of the sent message or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_retransmit(coap_context_t *context, coap_queue_t *node); + +/** + * Parses and interprets a CoAP datagram with context @p ctx. This function + * returns @c 0 if the datagram was handled, or a value less than zero on + * error. + * + * @param ctx The current CoAP context. + * @param session The current CoAP session. + * @param data The received packet'd data. + * @param data_len The received packet'd data length. + * + * @return @c 0 if message was handled successfully, or less than zero on + * error. + */ +int coap_handle_dgram(coap_context_t *ctx, coap_session_t *session, uint8_t *data, size_t data_len); + +/** + * This function removes the element with given @p id from the list given list. + * If @p id was found, @p node is updated to point to the removed element. Note + * that the storage allocated by @p node is @b not released. The caller must do + * this manually using coap_delete_node(). This function returns @c 1 if the + * element with id @p id was found, @c 0 otherwise. For a return value of @c 0, + * the contents of @p node is undefined. + * + * @param queue The queue to search for @p id. + * @param session The session to look for. + * @param id The message id to look for. + * @param node If found, @p node is updated to point to the removed node. You + * must release the storage pointed to by @p node manually. + * + * @return @c 1 if @p id was found, @c 0 otherwise. + */ +int coap_remove_from_queue(coap_queue_t **queue, + coap_session_t *session, + coap_mid_t id, + coap_queue_t **node); + +coap_mid_t +coap_wait_ack( coap_context_t *context, coap_session_t *session, + coap_queue_t *node); + +/** + * Cancels all outstanding messages for session @p session that have the specified + * token. + * + * @param context The context in use. + * @param session Session of the messages to remove. + * @param token Message token. + * @param token_length Actual length of @p token. + */ +void coap_cancel_all_messages(coap_context_t *context, + coap_session_t *session, + const uint8_t *token, + size_t token_length); + +/** +* Cancels all outstanding messages for session @p session. +* +* @param context The context in use. +* @param session Session of the messages to remove. +* @param reason The reasion for the session cancellation +*/ +void +coap_cancel_session_messages(coap_context_t *context, + coap_session_t *session, + coap_nack_reason_t reason); + +/** + * Dispatches the PDUs from the receive queue in given context. + */ +void coap_dispatch(coap_context_t *context, coap_session_t *session, + coap_pdu_t *pdu); + +/** + * Verifies that @p pdu contains no unknown critical options. Options must be + * registered at @p ctx, using the function coap_register_option(). A basic set + * of options is registered automatically by coap_new_context(). This function + * returns @c 1 if @p pdu is ok, @c 0 otherwise. The given filter object @p + * unknown will be updated with the unknown options. As only @c COAP_MAX_OPT + * options can be signalled this way, remaining options must be examined + * manually. + * + * @code + coap_opt_filter_t f = COAP_OPT_NONE; + coap_opt_iterator_t opt_iter; + + if (coap_option_check_critical(ctx, pdu, f) == 0) { + coap_option_iterator_init(pdu, &opt_iter, f); + + while (coap_option_next(&opt_iter)) { + if (opt_iter.type & 0x01) { + ... handle unknown critical option in opt_iter ... + } + } + } + @endcode + * + * @param ctx The context where all known options are registered. + * @param pdu The PDU to check. + * @param unknown The output filter that will be updated to indicate the + * unknown critical options found in @p pdu. + * + * @return @c 1 if everything was ok, @c 0 otherwise. + */ +int coap_option_check_critical(coap_context_t *ctx, + coap_pdu_t *pdu, + coap_opt_filter_t *unknown); + +/** + * Creates a new response for given @p request with the contents of @c + * .well-known/core. The result is NULL on error or a newly allocated PDU that + * must be either sent with coap_sent() or released by coap_delete_pdu(). + * + * @param context The current coap context to use. + * @param session The CoAP session. + * @param request The request for @c .well-known/core . + * + * @return A new 2.05 response for @c .well-known/core or NULL on error. + */ +coap_pdu_t *coap_wellknown_response(coap_context_t *context, + coap_session_t *session, + coap_pdu_t *request); + +/** + * Calculates the initial timeout based on the session CoAP transmission + * parameters 'ack_timeout', 'ack_random_factor', and COAP_TICKS_PER_SECOND. + * The calculation requires 'ack_timeout' and 'ack_random_factor' to be in + * Qx.FRAC_BITS fixed point notation, whereas the passed parameter @p r + * is interpreted as the fractional part of a Q0.MAX_BITS random value. + * + * @param session session timeout is associated with + * @param r random value as fractional part of a Q0.MAX_BITS fixed point + * value + * @return COAP_TICKS_PER_SECOND * 'ack_timeout' * + * (1 + ('ack_random_factor' - 1) * r) + */ +unsigned int coap_calc_timeout(coap_session_t *session, unsigned char r); + +/** + * Sends a CoAP message to given peer. The memory that is + * allocated for the pdu will be released by coap_send_internal(). + * The caller must not use the pdu after calling coap_send_internal(). + * + * If the response body is split into multiple payloads using blocks, libcoap + * will handle asking for the subsequent blocks and any necessary recovery + * needed. + * + * @param session The CoAP session. + * @param pdu The CoAP PDU to send. + * + * @return The message id of the sent message or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_send_internal(coap_session_t *session, coap_pdu_t *pdu); + +/** @} */ + +#endif /* COAP_NET_INTERNAL_H_ */ + diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_pdu_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_pdu_internal.h new file mode 100644 index 00000000000..0d8446c0d4c --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_pdu_internal.h @@ -0,0 +1,300 @@ +/* + * coap_pdu_internal.h -- CoAP PDU structure + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_pdu_internal.h + * @brief CoAP PDU internal information + */ + +#ifndef COAP_COAP_PDU_INTERNAL_H_ +#define COAP_COAP_PDU_INTERNAL_H_ + +#ifdef WITH_LWIP +#include +#endif + +#include + +/** + * @defgroup pdu_internal PDU (Internal) + * CoAP PDU Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +#define COAP_DEFAULT_VERSION 1 /* version of CoAP supported */ + +/* TCP Message format constants, do not modify */ +#define COAP_MESSAGE_SIZE_OFFSET_TCP8 13 +#define COAP_MESSAGE_SIZE_OFFSET_TCP16 269 /* 13 + 256 */ +#define COAP_MESSAGE_SIZE_OFFSET_TCP32 65805 /* 269 + 65536 */ + +/* Derived message size limits */ +#define COAP_MAX_MESSAGE_SIZE_TCP0 (COAP_MESSAGE_SIZE_OFFSET_TCP8-1) /* 12 */ +#define COAP_MAX_MESSAGE_SIZE_TCP8 (COAP_MESSAGE_SIZE_OFFSET_TCP16-1) /* 268 */ +#define COAP_MAX_MESSAGE_SIZE_TCP16 (COAP_MESSAGE_SIZE_OFFSET_TCP32-1) /* 65804 */ +#define COAP_MAX_MESSAGE_SIZE_TCP32 (COAP_MESSAGE_SIZE_OFFSET_TCP32+0xFFFFFFFF) + +#ifndef COAP_DEBUG_BUF_SIZE +#if defined(WITH_CONTIKI) || defined(WITH_LWIP) +#define COAP_DEBUG_BUF_SIZE 128 +#else /* defined(WITH_CONTIKI) || defined(WITH_LWIP) */ +/* 1024 derived from RFC7252 4.6. Message Size max payload */ +#define COAP_DEBUG_BUF_SIZE (8 + 1024 * 2) +#endif /* defined(WITH_CONTIKI) || defined(WITH_LWIP) */ +#endif /* COAP_DEBUG_BUF_SIZE */ + +#ifndef COAP_DEFAULT_MAX_PDU_RX_SIZE +#if defined(WITH_CONTIKI) || defined(WITH_LWIP) +#define COAP_DEFAULT_MAX_PDU_RX_SIZE (COAP_MAX_MESSAGE_SIZE_TCP16+4UL) +#else +/* 8 MiB max-message-size plus some space for options */ +#define COAP_DEFAULT_MAX_PDU_RX_SIZE (8UL*1024*1024+256) +#endif +#endif /* COAP_DEFAULT_MAX_PDU_RX_SIZE */ + +/** + * Indicates that a response is suppressed. This will occur for error + * responses if the request was received via IP multicast. + */ +#define COAP_DROPPED_RESPONSE -2 + +#define COAP_PDU_DELAYED -3 + +#define COAP_PAYLOAD_START 0xFF /* payload marker */ + +#define COAP_PDU_IS_EMPTY(pdu) ((pdu)->code == 0) +#define COAP_PDU_IS_REQUEST(pdu) (!COAP_PDU_IS_EMPTY(pdu) && (pdu)->code < 32) +#define COAP_PDU_IS_RESPONSE(pdu) ((pdu)->code >= 64 && (pdu)->code < 224) +#define COAP_PDU_IS_SIGNALING(pdu) ((pdu)->code >= 224) + +#define COAP_PDU_MAX_UDP_HEADER_SIZE 4 +#define COAP_PDU_MAX_TCP_HEADER_SIZE 6 + +/** + * structure for CoAP PDUs + * token, if any, follows the fixed size header, then options until + * payload marker (0xff), then the payload if stored inline. + * Memory layout is: + * <---header--->|<---token---><---options--->0xff<---payload---> + * header is addressed with a negative offset to token, its maximum size is + * max_hdr_size. + * options starts at token + token_length + * payload starts at data, its length is used_size - (data - token) + */ + +struct coap_pdu_t { + coap_pdu_type_t type; /**< message type */ + coap_pdu_code_t code; /**< request method (value 1--31) or response code + (value 64-255) */ + coap_mid_t mid; /**< message id, if any, in regular host byte + order */ + uint8_t max_hdr_size; /**< space reserved for protocol-specific header */ + uint8_t hdr_size; /**< actual size used for protocol-specific + header */ + uint8_t token_length; /**< length of Token */ + uint16_t max_opt; /**< highest option number in PDU */ + size_t alloc_size; /**< allocated storage for token, options and + payload */ + size_t used_size; /**< used bytes of storage for token, options and + payload */ + size_t max_size; /**< maximum size for token, options and payload, + or zero for variable size pdu */ + uint8_t *token; /**< first byte of token, if any, or options */ + uint8_t *data; /**< first byte of payload, if any */ +#ifdef WITH_LWIP + struct pbuf *pbuf; /**< lwIP PBUF. The package data will always reside + * inside the pbuf's payload, but this pointer + * has to be kept because no exact offset can be + * given. This field must not be accessed from + * outside, because the pbuf's reference count + * is checked to be 1 when the pbuf is assigned + * to the pdu, and the pbuf stays exclusive to + * this pdu. */ +#endif + const uint8_t *body_data; /**< Holds ptr to re-assembled data or NULL */ + size_t body_length; /**< Holds body data length */ + size_t body_offset; /**< Holds body data offset */ + size_t body_total; /**< Holds body data total size */ + coap_lg_xmit_t *lg_xmit; /**< Holds ptr to lg_xmit if sending a set of + blocks */ +}; + +/** + * Dynamically grows the size of @p pdu to @p new_size. The new size + * must not exceed the PDU's configure maximum size. On success, this + * function returns 1, otherwise 0. + * + * @param pdu The PDU to resize. + * @param new_size The new size in bytes. + * @return 1 if the operation succeeded, 0 otherwise. + */ +int coap_pdu_resize(coap_pdu_t *pdu, size_t new_size); + +/** + * Dynamically grows the size of @p pdu to @p new_size if needed. The new size + * must not exceed the PDU's configured maximum size. On success, this + * function returns 1, otherwise 0. + * + * @param pdu The PDU to resize. + * @param new_size The new size in bytes. + * @return 1 if the operation succeeded, 0 otherwise. + */ +int coap_pdu_check_resize(coap_pdu_t *pdu, size_t new_size); + +/** +* Interprets @p data to determine the number of bytes in the header. +* This function returns @c 0 on error or a number greater than zero on success. +* +* @param proto Session's protocol +* @param data The first byte of raw data to parse as CoAP PDU. +* +* @return A value greater than zero on success or @c 0 on error. +*/ +size_t coap_pdu_parse_header_size(coap_proto_t proto, + const uint8_t *data); + +/** + * Parses @p data to extract the message size. + * @p length must be at least coap_pdu_parse_header_size(proto, data). + * This function returns @c 0 on error or a number greater than zero on success. + * + * @param proto Session's protocol + * @param data The raw data to parse as CoAP PDU. + * @param length The actual size of @p data. + * + * @return A value greater than zero on success or @c 0 on error. + */ +size_t coap_pdu_parse_size(coap_proto_t proto, + const uint8_t *data, + size_t length); + +/** + * Decode the protocol specific header for the specified PDU. + * @param pdu A newly received PDU. + * @param proto The target wire protocol. + * @return 1 for success or 0 on error. + */ + +int coap_pdu_parse_header(coap_pdu_t *pdu, coap_proto_t proto); + +/** + * Verify consistency in the given CoAP PDU structure and locate the data. + * This function returns @c 0 on error or a number greater than zero on + * success. + * This function only parses the token and options, up to the payload start + * marker. + * + * @param pdu The PDU structure to check. + * + * @return 1 on success or @c 0 on error. + */ +int coap_pdu_parse_opt(coap_pdu_t *pdu); + +/** +* Parses @p data into the CoAP PDU structure given in @p result. +* The target pdu must be large enough to +* This function returns @c 0 on error or a number greater than zero on success. +* +* @param proto Session's protocol +* @param data The raw data to parse as CoAP PDU. +* @param length The actual size of @p data. +* @param pdu The PDU structure to fill. Note that the structure must +* provide space to hold at least the token and options +* part of the message. +* +* @return 1 on success or @c 0 on error. +*/ +int coap_pdu_parse(coap_proto_t proto, + const uint8_t *data, + size_t length, + coap_pdu_t *pdu); + +/** + * Clears any contents from @p pdu and resets @c used_size, + * and @c data pointers. @c max_size is set to @p size, any + * other field is set to @c 0. Note that @p pdu must be a valid + * pointer to a coap_pdu_t object created e.g. by coap_pdu_init(). + * + * @param pdu The PDU to clear. + * @param size The maximum size of the PDU. + */ +void coap_pdu_clear(coap_pdu_t *pdu, size_t size); + +/** + * Removes (first) option of given number from the @p pdu. + * + * @param pdu The PDU to remove the option from. + * @param number The number of the CoAP option to remove (first only removed). + * + * @return @c 1 if success else @c 0 if error. + */ +int coap_remove_option(coap_pdu_t *pdu, coap_option_num_t number); + +/** + * Inserts option of given number in the @p pdu with the appropriate data. + * The option will be inserted in the appropriate place in the options in + * the pdu. + * + * @param pdu The PDU where the option is to be inserted. + * @param number The number of the new option. + * @param len The length of the new option. + * @param data The data of the new option. + * + * @return The overall length of the option or @c 0 on failure. + */ +size_t coap_insert_option(coap_pdu_t *pdu, coap_option_num_t number, + size_t len, const uint8_t *data); + +/** + * Updates existing first option of given number in the @p pdu with the new + * data. + * + * @param pdu The PDU where the option is to be updated. + * @param number The number of the option to update (first only updated). + * @param len The length of the updated option. + * @param data The data of the updated option. + * + * @return The overall length of the updated option or @c 0 on failure. + */ +size_t coap_update_option(coap_pdu_t *pdu, + coap_option_num_t number, + size_t len, + const uint8_t *data); + +/** + * Compose the protocol specific header for the specified PDU. + * + * @param pdu A newly composed PDU. + * @param proto The target wire protocol. + * + * @return Number of header bytes prepended before pdu->token or 0 on error. + */ + +size_t coap_pdu_encode_header(coap_pdu_t *pdu, coap_proto_t proto); + + /** + * Updates token in @p pdu with length @p len and @p data. + * This function returns @c 0 on error or a value greater than zero on success. + * + * @param pdu The PDU where the token is to be updated. + * @param len The length of the new token. + * @param data The token to add. + * + * @return A value greater than zero on success, or @c 0 on error. + */ +int coap_update_token(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** @} */ + +#endif /* COAP_COAP_PDU_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_prng.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_prng.h new file mode 100644 index 00000000000..6d297afaec3 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_prng.h @@ -0,0 +1,113 @@ +/* + * coap_prng.h -- Pseudo Random Numbers + * + * Copyright (C) 2010-2020 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_prng.h + * @brief Pseudo Random Numbers + */ + +#ifndef COAP_PRNG_H_ +#define COAP_PRNG_H_ + +/** + * @defgroup coap_prng Pseudo Random Numbers + * API functions for gerating pseudo random numbers + * @{ + */ + +#if defined(WITH_CONTIKI) +#include + +/** + * Fills \p buf with \p len random bytes. This is the default implementation for + * coap_prng(). You might want to change contiki_prng_impl() to use a better + * PRNG on your specific platform. + */ +COAP_STATIC_INLINE int +contiki_prng_impl(unsigned char *buf, size_t len) { + uint16_t v = random_rand(); + while (len > sizeof(v)) { + memcpy(buf, &v, sizeof(v)); + len -= sizeof(v); + buf += sizeof(v); + v = random_rand(); + } + + memcpy(buf, &v, len); + return 1; +} + +#define coap_prng(Buf,Length) contiki_prng_impl((Buf), (Length)) +#define coap_prng_init(Value) random_init((uint16_t)(Value)) + +#elif defined(WITH_LWIP) && defined(LWIP_RAND) + +COAP_STATIC_INLINE int +lwip_prng_impl(unsigned char *buf, size_t len) { + u32_t v = LWIP_RAND(); + while (len > sizeof(v)) { + memcpy(buf, &v, sizeof(v)); + len -= sizeof(v); + buf += sizeof(v); + v = LWIP_RAND(); + } + + memcpy(buf, &v, len); + return 1; +} + +#define coap_prng(Buf,Length) lwip_prng_impl((Buf), (Length)) +#define coap_prng_init(Value) (void)Value + +#else + +/** + * Data type for random number generator function. The function must + * fill @p len bytes of random data into the buffer starting at @p + * out. On success, the function should return 1, zero otherwise. + */ +typedef int (*coap_rand_func_t)(void *out, size_t len); + +/** + * Replaces the current random number generation function with the + * default function @p rng. + * + * @param rng The random number generation function to use. + */ +void coap_set_prng(coap_rand_func_t rng); + +/** + * Seeds the default random number generation function with the given + * @p seed. The default random number generation function will use + * getrandom() if available, ignoring the seed. + * + * @param seed The seed for the pseudo random number generator. + */ +void coap_prng_init(unsigned int seed); + +/** + * Fills @p buf with @p len random bytes using the default pseudo + * random number generator. The default PRNG can be changed with + * coap_set_prng(). This function returns 1 when @p len random bytes + * have been written to @p buf, zero otherwise. + * + * @param buf The buffer to fill with random bytes. + * @param len The number of random bytes to write into @p buf. + * + * @return 1 on success, 0 otherwise. + */ +int coap_prng(void *buf, size_t len); + +#endif /* POSIX */ + +/** @} */ + +#endif /* COAP_PRNG_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_resource_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_resource_internal.h new file mode 100644 index 00000000000..cbcc36a664c --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_resource_internal.h @@ -0,0 +1,141 @@ +/* + * coap_resource_internal.h -- generic resource handling + * + * Copyright (C) 2010,2011,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_resource_internal.h + * @brief Generic resource internal handling + */ + +#ifndef COAP_RESOURCE_INTERNAL_H_ +#define COAP_RESOURCE_INTERNAL_H_ + +#include "uthash.h" + +/** + * @defgroup coap_resource_internal Resources (Internal) + * Structures, Enums and Functions that are not exposed to applications + * @{ + */ + +/** +* Abstraction of attribute associated with a resource. +*/ +struct coap_attr_t { + struct coap_attr_t *next; /**< Pointer to next in chain or NULL */ + coap_str_const_t *name; /**< Name of the attribute */ + coap_str_const_t *value; /**< Value of the attribute (can be NULL) */ + int flags; +}; + +/** +* Abstraction of resource that can be attached to coap_context_t. +* The key is uri_path. +*/ +struct coap_resource_t { + unsigned int dirty:1; /**< set to 1 if resource has changed */ + unsigned int partiallydirty:1; /**< set to 1 if some subscribers have not yet + * been notified of the last change */ + unsigned int observable:1; /**< can be observed */ + unsigned int cacheable:1; /**< can be cached */ + unsigned int is_unknown:1; /**< resource created for unknown handler */ + unsigned int is_proxy_uri:1; /**< resource created for proxy URI handler */ + + /** + * Used to store handlers for the seven coap methods @c GET, @c POST, @c PUT, + * @c DELETE, @c FETCH, @c PATCH and @c IPATCH. + * coap_dispatch() will pass incoming requests to handle_request() and then + * to the handler that corresponds to its request method or generate a 4.05 + * response if no handler is available. + */ + coap_method_handler_t handler[7]; + + UT_hash_handle hh; + + coap_attr_t *link_attr; /**< attributes to be included with the link format */ + coap_subscription_t *subscribers; /**< list of observers for this resource */ + + /** + * Request URI Path for this resource. This field will point into static + * or allocated memory which must remain there for the duration of the + * resource. + */ + coap_str_const_t *uri_path; /**< the key used for hash lookup for this + resource */ + int flags; /**< zero or more COAP_RESOURCE_FLAGS_* or'd together */ + + /** + * The next value for the Observe option. This field must be increased each + * time the resource changes. Only the lower 24 bits are sent. + */ + unsigned int observe; + + /** + * Pointer back to the context that 'owns' this resource. + */ + coap_context_t *context; + + /** + * Count of valid names this host is known by (proxy support) + */ + size_t proxy_name_count; + + /** + * Array valid names this host is known by (proxy support) + */ + coap_str_const_t ** proxy_name_list; + + /** + * This pointer is under user control. It can be used to store context for + * the coap handler. + */ + void *user_data; + +}; + +/** + * Deletes all resources from given @p context and frees their storage. + * + * @param context The CoAP context with the resources to be deleted. + */ +void coap_delete_all_resources(coap_context_t *context); + +#define RESOURCES_ADD(r, obj) \ + HASH_ADD(hh, (r), uri_path->s[0], (obj)->uri_path->length, (obj)) + +#define RESOURCES_DELETE(r, obj) \ + HASH_DELETE(hh, (r), (obj)) + +#define RESOURCES_ITER(r,tmp) \ + coap_resource_t *tmp, *rtmp; \ + HASH_ITER(hh, (r), tmp, rtmp) + +#define RESOURCES_FIND(r, k, res) { \ + HASH_FIND(hh, (r), (k)->s, (k)->length, (res)); \ + } + +/** + * Deletes an attribute. + * Note: This is for internal use only, as it is not deleted from its chain. + * + * @param attr Pointer to a previously created attribute. + * + */ +void coap_delete_attr(coap_attr_t *attr); + +coap_print_status_t coap_print_wellknown(coap_context_t *, + unsigned char *, + size_t *, size_t, + coap_opt_t *); + + +/** @} */ + +#endif /* COAP_RESOURCE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_riot.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_riot.h new file mode 100644 index 00000000000..fc4bfa2e655 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_riot.h @@ -0,0 +1,34 @@ +/* coap_riot.h -- RIOT-specific definitions for libcoap + * + * Copyright (C) 2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see + * README for terms of use. + */ + +#ifndef COAP_RIOT_H_ +#define COAP_RIOT_H_ + +#ifndef LIBCOAP_MSG_QUEUE_SIZE +/** + * Size of the queue for passing messages between the network + * interface and the coap stack. */ +#define LIBCOAP_MSG_QUEUE_SIZE (32U) +#endif /* LIBCOAP_MSG_QUEUE_SIZE */ + +#ifndef LIBCOAP_MAX_SOCKETS +/** + * Maximum number of sockets that are simultaneously considered for + * reading or writing. */ +#define LIBCOAP_MAX_SOCKETS (16U) +#endif /* LIBCOAP_MAX_SOCKETS */ + +/** + * This function must be called in the RIOT CoAP thread for + * RIOT-specific initialization. + */ +void coap_riot_startup(void); + +#endif /* COAP_RIOT_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session.h new file mode 100644 index 00000000000..6c49b78e97d --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session.h @@ -0,0 +1,591 @@ +/* coap_session.h -- Session management for libcoap +* +* Copyright (C) 2017 Jean-Claue Michelou +* + * SPDX-License-Identifier: BSD-2-Clause + * +* This file is part of the CoAP library libcoap. Please see +* README for terms of use. +*/ + +/** + * @file coap_session.h + * @brief Defines the application visible session information + */ + +#ifndef COAP_SESSION_H_ +#define COAP_SESSION_H_ + +/** + * @defgroup session Sessions + * API functions for CoAP Sessions + * @{ + */ + +/** +* Abstraction of a fixed point number that can be used where necessary instead +* of a float. 1,000 fractional bits equals one integer +*/ +typedef struct coap_fixed_point_t { + uint16_t integer_part; /**< Integer part of fixed point variable */ + uint16_t fractional_part; /**< Fractional part of fixed point variable + 1/1000 (3 points) precision */ +} coap_fixed_point_t; + +#define COAP_PROTO_NOT_RELIABLE(p) ((p)==COAP_PROTO_UDP || (p)==COAP_PROTO_DTLS) +#define COAP_PROTO_RELIABLE(p) ((p)==COAP_PROTO_TCP || (p)==COAP_PROTO_TLS) + +/** + * coap_session_type_t values + */ +typedef enum coap_session_type_t { + COAP_SESSION_TYPE_NONE = 0, /**< Not defined */ + COAP_SESSION_TYPE_CLIENT, /**< client-side */ + COAP_SESSION_TYPE_SERVER, /**< server-side */ + COAP_SESSION_TYPE_HELLO, /**< server-side ephemeral session for + responding to a client hello */ +} coap_session_type_t; + +/** + * coap_session_state_t values + */ +typedef enum coap_session_state_t { + COAP_SESSION_STATE_NONE = 0, + COAP_SESSION_STATE_CONNECTING, + COAP_SESSION_STATE_HANDSHAKE, + COAP_SESSION_STATE_CSM, + COAP_SESSION_STATE_ESTABLISHED, +} coap_session_state_t; + +/** + * Increment reference counter on a session. + * + * @param session The CoAP session. + * @return same as session + */ +coap_session_t *coap_session_reference(coap_session_t *session); + +/** + * Decrement reference counter on a session. + * Note that the session may be deleted as a result and should not be used + * after this call. + * + * @param session The CoAP session. + */ +void coap_session_release(coap_session_t *session); + +/** + * Notify session that it has failed. This cleans up any outstanding / queued + * transmissions, observations etc.. + * + * @param session The CoAP session. + * @param reason The reason why the session was disconnected. + */ +void coap_session_disconnected(coap_session_t *session, + coap_nack_reason_t reason); + +/** + * Stores @p data with the given session. This function overwrites any value + * that has previously been stored with @p session. + * + * @param session The CoAP session. + * @param data The pointer to the data to store. + */ +void coap_session_set_app_data(coap_session_t *session, void *data); + +/** + * Returns any application-specific data that has been stored with @p + * session using the function coap_session_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param session The CoAP session. + * + * @return Pointer to the stored data or @c NULL. + */ +void *coap_session_get_app_data(const coap_session_t *session); + +/** + * Get the remote IP address from the session. + * + * @param session The CoAP session. + * + * @return The session's remote address or @c NULL on failure. + */ +const coap_address_t *coap_session_get_addr_remote( + const coap_session_t *session); + +/** + * Get the local IP address from the session. + * + * @param session The CoAP session. + * + * @return The session's local address or @c NULL on failure. + */ +const coap_address_t *coap_session_get_addr_local( + const coap_session_t *session); + +/** + * Get the session protocol type + * + * @param session The CoAP session. + * + * @return The session's protocol type + */ +coap_proto_t coap_session_get_proto(const coap_session_t *session); + +/** + * Get the session type + * + * @param session The CoAP session. + * + * @return The session's type + */ +coap_session_type_t coap_session_get_type(const coap_session_t *session); + +/** + * Get the session state + * + * @param session The CoAP session. + * + * @return The session's state + */ +coap_session_state_t coap_session_get_state(const coap_session_t *session); + +/** + * Get the session if index + * + * @param session The CoAP session. + * + * @return The session's if index, or @c -1 on error. + */ +int coap_session_get_ifindex(const coap_session_t *session); + +/** + * Get the session TLS security ptr (TLS type dependent) + * + * OpenSSL: SSL* + * GnuTLS: gnutls_session_t (implicit *) + * Mbed TLS: mbedtls_ssl_context* + * TinyDTLS: struct dtls_context* + * + * @param session The CoAP session. + * @param tls_lib Updated with the library type. + * + * @return The session TLS ptr or @c NULL if not set up + */ +void *coap_session_get_tls(const coap_session_t *session, + coap_tls_library_t *tls_lib); + +/** + * Get the session context + * + * @param session The CoAP session. + * + * @return The session's context + */ +coap_context_t *coap_session_get_context(const coap_session_t *session); + +/** + * Set the session type to client. Typically used in a call-home server. + * The session needs to be of type COAP_SESSION_TYPE_SERVER. + * Note: If this function is successful, the session reference count is + * incremented and a subsequent coap_session_release() taking the + * reference count to 0 will cause the session to be freed off. + * + * @param session The CoAP session. + * + * @return @c 1 if updated, @c 0 on failure. + */ +int coap_session_set_type_client(coap_session_t *session); + +/** + * Set the session MTU. This is the maximum message size that can be sent, + * excluding IP and UDP overhead. + * + * @param session The CoAP session. + * @param mtu maximum message size + */ +void coap_session_set_mtu(coap_session_t *session, unsigned mtu); + +/** + * Get maximum acceptable PDU size + * + * @param session The CoAP session. + * @return maximum PDU size, not including header (but including token). + */ +size_t coap_session_max_pdu_size(const coap_session_t *session); + +/** +* Creates a new client session to the designated server. +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to let the operating system choose a suitable local interface. If an address is specified, the port number should be zero, which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default port for the protocol will be used. +* @param proto Protocol. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release to free. +*/ +coap_session_t *coap_new_client_session( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto +); + +/** +* Creates a new client session to the designated server with PSK credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to let the operating system choose a suitable local interface. If an address is specified, the port number should be zero, which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default port for the protocol will be used. +* @param proto Protocol. +* @param identity PSK client identity +* @param key PSK shared key +* @param key_len PSK shared key length +* +* @return A new CoAP session or NULL if failed. Call coap_session_release to free. +*/ +coap_session_t *coap_new_client_session_psk( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + const char *identity, + const uint8_t *key, + unsigned key_len +); + +/** +* Creates a new client session to the designated server with PSK credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to +* let the operating system choose a suitable local interface. +* If an address is specified, the port number should be zero, +* which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default +* port for the protocol will be used. +* @param proto CoAP Protocol. +* @param setup_data PSK parameters. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release() +* to free. +*/ +coap_session_t *coap_new_client_session_psk2( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_cpsk_t *setup_data +); + +/** + * Get the server session's current Identity Hint (PSK). + * + * @param session The current coap_session_t object. + * + * @return @c hint if successful, else @c NULL. + */ +const coap_bin_const_t * coap_session_get_psk_hint( + const coap_session_t *session); + +/** + * Get the session's current pre-shared key (PSK). + * + * @param session The current coap_session_t object. + * + * @return @c psk_key if successful, else @c NULL. + */ +const coap_bin_const_t * coap_session_get_psk_key( + const coap_session_t *session); + +/** +* Creates a new client session to the designated server with PKI credentials +* @param ctx The CoAP context. +* @param local_if Address of local interface. It is recommended to use NULL to +* let the operating system choose a suitable local interface. +* If an address is specified, the port number should be zero, +* which means that a free port is automatically selected. +* @param server The server's address. If the port number is zero, the default +* port for the protocol will be used. +* @param proto CoAP Protocol. +* @param setup_data PKI parameters. +* +* @return A new CoAP session or NULL if failed. Call coap_session_release() +* to free. +*/ +coap_session_t *coap_new_client_session_pki( + coap_context_t *ctx, + const coap_address_t *local_if, + const coap_address_t *server, + coap_proto_t proto, + coap_dtls_pki_t *setup_data +); + +/** + * Initializes the token value to use as a starting point. + * + * @param session The current coap_session_t object. + * @param length The length of the token (0 - 8 bytes). + * @param token The token data. + * + */ +void coap_session_init_token(coap_session_t *session, size_t length, + const uint8_t *token); + +/** + * Creates a new token for use. + * + * @param session The current coap_session_t object. + * @param length Updated with the length of the new token. + * @param token Updated with the new token data (must be 8 bytes long). + * + */ +void coap_session_new_token(coap_session_t *session, size_t *length, + uint8_t *token); + +/** + * @ingroup logging + * Get session description. + * + * @param session The CoAP session. + * @return description string. + */ +const char *coap_session_str(const coap_session_t *session); + +/** +* Create a new endpoint for communicating with peers. +* +* @param context The coap context that will own the new endpoint +* @param listen_addr Address the endpoint will listen for incoming requests on or originate outgoing requests from. Use NULL to specify that no incoming request will be accepted and use a random endpoint. +* @param proto Protocol used on this endpoint +*/ + +coap_endpoint_t *coap_new_endpoint(coap_context_t *context, const coap_address_t *listen_addr, coap_proto_t proto); + +/** +* Set the endpoint's default MTU. This is the maximum message size that can be +* sent, excluding IP and UDP overhead. +* +* @param endpoint The CoAP endpoint. +* @param mtu maximum message size +*/ +void coap_endpoint_set_default_mtu(coap_endpoint_t *endpoint, unsigned mtu); + +void coap_free_endpoint(coap_endpoint_t *ep); + +/** @} */ + +/** + * @ingroup logging +* Get endpoint description. +* +* @param endpoint The CoAP endpoint. +* @return description string. +*/ +const char *coap_endpoint_str(const coap_endpoint_t *endpoint); + +coap_session_t *coap_session_get_by_peer(const coap_context_t *ctx, + const coap_address_t *remote_addr, int ifindex); + + /** + * @defgroup cc Rate Control + * The transmission parameters for CoAP rate control ("Congestion + * Control" in stream-oriented protocols) are defined in + * https://tools.ietf.org/html/rfc7252#section-4.8 + * @{ + */ + + /** + * Number of seconds when to expect an ACK or a response to an + * outstanding CON message. + * RFC 7252, Section 4.8 Default value of ACK_TIMEOUT is 2 + * + * Configurable using coap_session_set_ack_timeout() + */ +#define COAP_DEFAULT_ACK_TIMEOUT ((coap_fixed_point_t){2,0}) + + /** + * A factor that is used to randomize the wait time before a message + * is retransmitted to prevent synchronization effects. + * RFC 7252, Section 4.8 Default value of ACK_RANDOM_FACTOR is 1.5 + * + * Configurable using coap_session_set_ack_random_factor() + */ +#define COAP_DEFAULT_ACK_RANDOM_FACTOR ((coap_fixed_point_t){1,500}) + + /** + * Number of message retransmissions before message sending is stopped + * RFC 7252, Section 4.8 Default value of MAX_RETRANSMIT is 4 + * + * Configurable using coap_session_set_max_retransmit() + */ +#define COAP_DEFAULT_MAX_RETRANSMIT 4 + + /** + * The number of simultaneous outstanding interactions that a client + * maintains to a given server. + * RFC 7252, Section 4.8 Default value of NSTART is 1 + */ +#define COAP_DEFAULT_NSTART 1 + + /** + * The maximum number of seconds before sending back a response to a + * multicast request. + * RFC 7252, Section 4.8 DEFAULT_LEISURE is 5. + */ +#ifndef COAP_DEFAULT_LEISURE +#define COAP_DEFAULT_LEISURE (5U) +#endif /* COAP_DEFAULT_LEISURE */ + + /** + * The MAX_TRANSMIT_SPAN definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_TRAMSMIT_SPAN + * ACK_TIMEOUT * ((2 ** (MAX_RETRANSMIT)) - 1) * ACK_RANDOM_FACTOR + */ +#define COAP_MAX_TRANSMIT_SPAN(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part) * \ + ((1 << (s->max_retransmit)) -1) * \ + (s->ack_random_factor.integer_part * 1000 + \ + s->ack_random_factor.fractional_part) \ + / 1000000) + + /** + * The MAX_TRANSMIT_WAIT definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_TRAMSMIT_WAIT + * ACK_TIMEOUT * ((2 ** (MAX_RETRANSMIT + 1)) - 1) * ACK_RANDOM_FACTOR + */ +#define COAP_MAX_TRANSMIT_WAIT(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part) * \ + ((1 << (s->max_retransmit + 1)) -1) * \ + (s->ack_random_factor.integer_part * 1000 + \ + s->ack_random_factor.fractional_part) \ + / 1000000) + + /** + * The MAX_LATENCY definition. + * RFC 7252, Section 4.8.2 MAX_LATENCY is 100. + */ +#define COAP_MAX_LATENCY 100 + + /** + * The PROCESSING_DELAY definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of PROCESSING_DELAY + * PROCESSING_DELAY set to ACK_TIMEOUT + */ +#define COAP_PROCESSING_DELAY(s) \ + ((s->ack_timeout.integer_part * 1000 + s->ack_timeout.fractional_part + 500) \ + / 1000) + + /** + * The MAX_RTT definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of MAX_RTT + * (2 * MAX_LATENCY) + PROCESSING_DELAY + */ +#define COAP_MAX_RTT(s) \ + ((2 * COAP_MAX_LATENCY) + COAP_PROCESSING_DELAY(s)) + + /** + * The EXCHANGE_LIFETIME definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of EXCHANGE_LIFETIME + * MAX_TRANSMIT_SPAN + (2 * MAX_LATENCY) + PROCESSING_DELAY + */ +#define COAP_EXCHANGE_LIFETIME(s) \ + (COAP_MAX_TRANSMIT_SPAN(s) + (2 * COAP_MAX_LATENCY) + COAP_PROCESSING_DELAY(s)) + + /** + * The NON_LIFETIME definition for the session (s). + * + * RFC 7252, Section 4.8.2 Calculation of NON_LIFETIME + * MAX_TRANSMIT_SPAN + MAX_LATENCY + */ +#define COAP_NON_LIFETIME(s) \ + (COAP_MAX_TRANSMIT_SPAN(s) + COAP_MAX_LATENCY) + + /** @} */ + +/** +* Set the CoAP maximum retransmit count before failure +* +* Number of message retransmissions before message sending is stopped +* +* @param session The CoAP session. +* @param value The value to set to. The default is 4 and should not normally +* get changed. +*/ +void coap_session_set_max_retransmit(coap_session_t *session, + unsigned int value); + +/** +* Set the CoAP initial ack response timeout before the next re-transmit +* +* Number of seconds when to expect an ACK or a response to an +* outstanding CON message. +* +* @param session The CoAP session. +* @param value The value to set to. The default is 2 and should not normally +* get changed. +*/ +void coap_session_set_ack_timeout(coap_session_t *session, + coap_fixed_point_t value); + +/** +* Set the CoAP ack randomize factor +* +* A factor that is used to randomize the wait time before a message +* is retransmitted to prevent synchronization effects. +* +* @param session The CoAP session. +* @param value The value to set to. The default is 1.5 and should not normally +* get changed. +*/ +void coap_session_set_ack_random_factor(coap_session_t *session, + coap_fixed_point_t value); + +/** +* Get the CoAP maximum retransmit before failure +* +* Number of message retransmissions before message sending is stopped +* +* @param session The CoAP session. +* +* @return Current maximum retransmit value +*/ +unsigned int coap_session_get_max_retransmit(const coap_session_t *session); + +/** +* Get the CoAP initial ack response timeout before the next re-transmit +* +* Number of seconds when to expect an ACK or a response to an +* outstanding CON message. +* +* @param session The CoAP session. +* +* @return Current ack response timeout value +*/ +coap_fixed_point_t coap_session_get_ack_timeout(const coap_session_t *session); + +/** +* Get the CoAP ack randomize factor +* +* A factor that is used to randomize the wait time before a message +* is retransmitted to prevent synchronization effects. +* +* @param session The CoAP session. +* +* @return Current ack randomize value +*/ +coap_fixed_point_t coap_session_get_ack_random_factor( + const coap_session_t *session); + +/** + * Send a ping message for the session. + * @param session The CoAP session. + * + * @return COAP_INVALID_MID if there is an error + */ +coap_mid_t coap_session_send_ping(coap_session_t *session); + +#endif /* COAP_SESSION_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session_internal.h new file mode 100644 index 00000000000..1fd2de9ecf1 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_session_internal.h @@ -0,0 +1,295 @@ +/* + * coap_session_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_session_internal.h + * @brief COAP session internal information + */ + +#ifndef COAP_SESSION_INTERNAL_H_ +#define COAP_SESSION_INTERNAL_H_ + +#include "coap_io_internal.h" + +#define COAP_DEFAULT_SESSION_TIMEOUT 300 +#define COAP_PARTIAL_SESSION_TIMEOUT_TICKS (30 * COAP_TICKS_PER_SECOND) +#define COAP_DEFAULT_MAX_HANDSHAKE_SESSIONS 100 + +/** + * @defgroup session_internal Sessions (Internal) + * CoAP Session Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +/** + * Only used for servers for hashing incoming packets. Cannot have local IP + * address as this may be an initial multicast and subsequent unicast address + */ +struct coap_addr_hash_t { + coap_address_t remote; /**< remote address and port */ + uint16_t lport; /**< local port */ + coap_proto_t proto; /**< CoAP protocol */ +}; + +/** + * Abstraction of virtual session that can be attached to coap_context_t + * (client) or coap_endpoint_t (server). + */ +struct coap_session_t { + coap_proto_t proto; /**< protocol used */ + coap_session_type_t type; /**< client or server side socket */ + coap_session_state_t state; /**< current state of relationaship with + peer */ + unsigned ref; /**< reference count from queues */ + size_t tls_overhead; /**< overhead of TLS layer */ + size_t mtu; /**< path or CSM mtu */ + coap_addr_hash_t addr_hash; /**< Address hash for server incoming packets */ + UT_hash_handle hh; + coap_addr_tuple_t addr_info; /**< key: remote/local address info */ + int ifindex; /**< interface index */ + coap_socket_t sock; /**< socket object for the session, if + any */ + coap_endpoint_t *endpoint; /**< session's endpoint */ + coap_context_t *context; /**< session's context */ + void *tls; /**< security parameters */ + uint16_t tx_mid; /**< the last message id that was used in + this session */ + uint8_t con_active; /**< Active CON request sent */ + uint8_t csm_block_supported; /**< CSM TCP blocks supported */ + coap_mid_t last_ping_mid; /**< the last keepalive message id that was + used in this session */ + coap_queue_t *delayqueue; /**< list of delayed messages waiting to + be sent */ + coap_lg_xmit_t *lg_xmit; /**< list of large transmissions */ + coap_lg_crcv_t *lg_crcv; /**< Client list of expected large receives */ + coap_lg_srcv_t *lg_srcv; /**< Server list of expected large receives */ + size_t partial_write; /**< if > 0 indicates number of bytes + already written from the pdu at the + head of sendqueue */ + uint8_t read_header[8]; /**< storage space for header of incoming + message header */ + size_t partial_read; /**< if > 0 indicates number of bytes + already read for an incoming message */ + coap_pdu_t *partial_pdu; /**< incomplete incoming pdu */ + coap_tick_t last_rx_tx; + coap_tick_t last_tx_rst; + coap_tick_t last_ping; + coap_tick_t last_pong; + coap_tick_t csm_tx; + coap_dtls_cpsk_t cpsk_setup_data; /**< client provided PSK initial setup + data */ + coap_bin_const_t *psk_identity; /**< If client, this field contains the + current identity for server; When this + field is NULL, the current identity is + contained in cpsk_setup_data + + If server, this field contains the client + provided identity. + + Value maintained internally */ + coap_bin_const_t *psk_key; /**< If client, this field contains the + current pre-shared key for server; + When this field is NULL, the current + key is contained in cpsk_setup_data + + If server, this field contains the + client's current key. + + Value maintained internally */ + coap_bin_const_t *psk_hint; /**< If client, this field contains the + server provided identity hint. + + If server, this field contains the + current hint for the client; When this + field is NULL, the current hint is + contained in context->spsk_setup_data + + Value maintained internally */ + void *app; /**< application-specific data */ + unsigned int max_retransmit; /**< maximum re-transmit count (default + 4) */ + coap_fixed_point_t ack_timeout; /**< timeout waiting for ack (default 2 + secs) */ + coap_fixed_point_t ack_random_factor; /**< ack random factor backoff (default + 1.5) */ + unsigned int dtls_timeout_count; /**< dtls setup retry counter */ + int dtls_event; /**< Tracking any (D)TLS events on this + sesison */ + uint8_t block_mode; /**< Zero or more COAP_BLOCK_ or'd options */ + uint64_t tx_token; /**< Next token number to use */ +}; + +/** + * Abstraction of virtual endpoint that can be attached to coap_context_t. The + * keys (port, bind_addr) must uniquely identify this endpoint. + */ +struct coap_endpoint_t { + struct coap_endpoint_t *next; + coap_context_t *context; /**< endpoint's context */ + coap_proto_t proto; /**< protocol used on this interface */ + uint16_t default_mtu; /**< default mtu for this interface */ + coap_socket_t sock; /**< socket object for the interface, if + any */ + coap_address_t bind_addr; /**< local interface address */ + coap_session_t *sessions; /**< hash table or list of active sessions */ +}; + +/** + * Notify session transport has just connected and CSM exchange can now start. + * + * @param session The CoAP session. + */ +void coap_session_send_csm(coap_session_t *session); + +/** + * Notify session that it has just connected or reconnected. + * + * @param session The CoAP session. + */ +void coap_session_connected(coap_session_t *session); + +/** + * Refresh the session's current Identity Hint (PSK). + * Note: A copy of @p psk_hint is maintained in the session by libcoap. + * + * @param session The current coap_session_t object. + * @param psk_hint If NULL, the Identity Hint will revert to the + * initial Identity Hint used at session setup. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_session_refresh_psk_hint(coap_session_t *session, + const coap_bin_const_t *psk_hint); + +/** + * Refresh the session's current pre-shared key (PSK). + * Note: A copy of @p psk_key is maintained in the session by libcoap. + * + * @param session The current coap_session_t object. + * @param psk_key If NULL, the pre-shared key will revert to the + * initial pre-shared key used as session setup. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_session_refresh_psk_key(coap_session_t *session, + const coap_bin_const_t *psk_key); + +/** + * Creates a new server session for the specified endpoint. + * @param ctx The CoAP context. + * @param ep An endpoint where an incoming connection request is pending. + * + * @return A new CoAP session or NULL if failed. Call coap_session_release to + * add to unused queue. + */ +coap_session_t *coap_new_server_session( + coap_context_t *ctx, + coap_endpoint_t *ep +); + +/** + * Function interface for datagram data transmission. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. + * + * @param session Session to send data on. + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_send(coap_session_t *session, + const uint8_t *data, size_t datalen); + +/** + * Function interface for stream data transmission. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. The number of bytes written may be less than datalen because of + * congestion control. + * + * @param session Session to send data on. + * @param data The data to send. + * @param datalen The actual length of @p data. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_write(coap_session_t *session, + const uint8_t *data, size_t datalen); + +/** + * Send a pdu according to the session's protocol. This function returns + * the number of bytes that have been transmitted, or a value less than zero + * on error. + * + * @param session Session to send pdu on. + * @param pdu The pdu to send. + * + * @return The number of bytes written on success, or a value + * less than zero on error. + */ +ssize_t coap_session_send_pdu(coap_session_t *session, coap_pdu_t *pdu); + +ssize_t +coap_session_delay_pdu(coap_session_t *session, coap_pdu_t *pdu, + coap_queue_t *node); + +/** + * Lookup the server session for the packet received on an endpoint, or create + * a new one. + * + * @param endpoint Active endpoint the packet was received on. + * @param packet Received packet. + * @param now The current time in ticks. + * @return The CoAP session or @c NULL if error. + */ +coap_session_t *coap_endpoint_get_session(coap_endpoint_t *endpoint, + const coap_packet_t *packet, coap_tick_t now); + +/** + * Create a new DTLS session for the @p session. + * Note: the @p session is released if no DTLS server session can be created. + * + * @ingroup dtls_internal + * + * @param session Session to add DTLS session to + * @param now The current time in ticks. + * + * @return CoAP session or @c NULL if error. + */ +coap_session_t *coap_session_new_dtls_session(coap_session_t *session, + coap_tick_t now); + +void coap_session_free(coap_session_t *session); +void coap_session_mfree(coap_session_t *session); + +/** @} */ + +#define SESSIONS_ADD(e, obj) \ + HASH_ADD(hh, (e), addr_hash, sizeof((obj)->addr_hash), (obj)) + +#define SESSIONS_DELETE(e, obj) \ + HASH_DELETE(hh, (e), (obj)) + +#define SESSIONS_ITER(e, el, rtmp) \ + HASH_ITER(hh, (e), el, rtmp) + +#define SESSIONS_ITER_SAFE(e, el, rtmp) \ +for ((el) = (e); (el) && ((rtmp) = (el)->hh.next, 1); (el) = (rtmp)) + +#define SESSIONS_FIND(e, k, res) { \ + HASH_FIND(hh, (e), &(k), sizeof(k), (res)); \ + } + +#endif /* COAP_SESSION_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_subscribe_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_subscribe_internal.h new file mode 100644 index 00000000000..b7702362bee --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_subscribe_internal.h @@ -0,0 +1,151 @@ +/* + * coap_subscribe_internal.h -- Structures, Enums & Functions that are not + * exposed to application programming + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_subscribe_internal.h + * @brief COAP subscribe internal information + */ + +#ifndef COAP_SUBSCRIBE_INTERNAL_H_ +#define COAP_SUBSCRIBE_INTERNAL_H_ + +/** + * @defgroup subscribe_internal Observe Subscription (Internal) + * CoAP Observe Subscription Structures, Enums and Functions that are not + * exposed to applications + * @{ + */ + +#ifndef COAP_OBS_MAX_NON +/** + * Number of notifications that may be sent non-confirmable before a confirmable + * message is sent to detect if observers are alive. The maximum allowed value + * here is @c 15. + */ +#define COAP_OBS_MAX_NON 5 +#endif /* COAP_OBS_MAX_NON */ + +#ifndef COAP_OBS_MAX_FAIL +/** + * Number of confirmable notifications that may fail (i.e. time out without + * being ACKed) before an observer is removed. The maximum value for + * COAP_OBS_MAX_FAIL is @c 3. + */ +#define COAP_OBS_MAX_FAIL 3 +#endif /* COAP_OBS_MAX_FAIL */ + +/** Subscriber information */ +struct coap_subscription_t { + struct coap_subscription_t *next; /**< next element in linked list */ + struct coap_session_t *session; /**< subscriber session */ + + unsigned int non_cnt:4; /**< up to 15 non-confirmable notifies allowed */ + unsigned int fail_cnt:2; /**< up to 3 confirmable notifies can fail */ + unsigned int dirty:1; /**< set if the notification temporarily could not be + * sent (in that case, the resource's partially + * dirty flag is set too) */ + coap_cache_key_t *cache_key; /** cache_key to identify requester */ + coap_pdu_t *pdu; /**< PDU to use for additional requests */ +}; + +void coap_subscription_init(coap_subscription_t *); + +/** + * Handles a failed observe notify. + * + * @param context The context holding the resource. + * @param session The session that the observe notify failed on. + * @param token The token used when the observe notify failed. + */ +void +coap_handle_failed_notify(coap_context_t *context, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Checks all known resources to see if they are dirty and then notifies + * subscribed observers. + * + * @param context The context to check for dirty resources. + */ +void coap_check_notify(coap_context_t *context); + +/** + * Adds the specified peer as observer for @p resource. The subscription is + * identified by the given @p token. This function returns the registered + * subscription information if the @p observer has been added, or @c NULL on + * error. + * + * @param resource The observed resource. + * @param session The observer's session + * @param token The token that identifies this subscription. + * @param pdu The requesting pdu. + * + * @return A pointer to the added/updated subscription + * information or @c NULL on error. + */ +coap_subscription_t *coap_add_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token, + const coap_pdu_t *pdu); + +/** + * Returns a subscription object for given @p peer. + * + * @param resource The observed resource. + * @param session The observer's session + * @param token The token that identifies this subscription or @c NULL for + * any token. + * @return A valid subscription if exists or @c NULL otherwise. + */ +coap_subscription_t *coap_find_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Flags that data is ready to be sent to observers. + * + * @param context The CoAP context to use. + * @param session The observer's session + * @param token The corresponding token that has been used for the + * subscription. + */ +void coap_touch_observer(coap_context_t *context, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Removes any subscription for @p observer from @p resource and releases the + * allocated storage. The result is @c 1 if an observation relationship with @p + * observer and @p token existed, @c 0 otherwise. + * + * @param resource The observed resource. + * @param session The observer's session. + * @param token The token that identifies this subscription or @c NULL for + * any token. + * @return @c 1 if the observer has been deleted, @c 0 otherwise. + */ +int coap_delete_observer(coap_resource_t *resource, + coap_session_t *session, + const coap_binary_t *token); + +/** + * Removes any subscription for @p session and releases the allocated storage. + * + * @param context The CoAP context to use. + * @param session The observer's session. + */ +void coap_delete_observers(coap_context_t *context, coap_session_t *session); + +/** @} */ + +#endif /* COAP_SUBSCRIBE_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_tcp_internal.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_tcp_internal.h new file mode 100644 index 00000000000..4fd31b38d01 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_tcp_internal.h @@ -0,0 +1,111 @@ +/* + * coap_tcp_internal.h -- TCP functions for libcoap + * + * Copyright (C) 2019--2020 Olaf Bergmann and others + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_tcp_internal.h + * @brief COAP tcp internal information + */ + +#ifndef COAP_TCP_INTERNAL_H_ +#define COAP_TCP_INTERNAL_H_ + +#include "coap_io.h" + +/** + * @defgroup tcp TCP Support (Internal) + * CoAP TCP Structures, Enums and Functions that are not exposed to + * applications + * @{ + */ + +#if !COAP_DISABLE_TCP + +/** + * Create a new TCP socket and initiate the connection + * + * Internal function. + * + * @param sock Where socket information is to be filled in + * @param local_if The local address to use or NULL + * @param server The address to connect to + * @param default_port The port to use if not set in @p server + * @param local_addr Filled in after connection initiation with + * the local address + * @param remote_addr Filled in after connection initiation with + * the remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_connect_tcp1(coap_socket_t *sock, + const coap_address_t *local_if, + const coap_address_t *server, + int default_port, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +/** + * Complete the TCP Connection + * + * Internal function. + * + * @param sock The socket information to use + * @param local_addr Filled in with the final local address + * @param remote_addr Filled in with the final remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_connect_tcp2(coap_socket_t *sock, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +/** + * Create a new TCP socket and then listen for new incoming TCP sessions + * + * Internal function. + * + * @param sock Where socket information is to be filled in + * @param listen_addr The address to be listening for new incoming sessions + * @param bound_addr Filled in with the address that the TCP layer + * is listening on for new incoming TCP sessions + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_bind_tcp(coap_socket_t *sock, + const coap_address_t *listen_addr, + coap_address_t *bound_addr); + +/** + * Accept a new incoming TCP session + * + * Internal function. + * + * @param server The socket information to use to accept the TCP connection + * @param new_client Filled in socket information with the new incoming + * session information + * @param local_addr Filled in with the local address + * @param remote_addr Filled in with the remote address + * + * @return @c 1 if succesful, @c 0 if failure of some sort +*/ +int +coap_socket_accept_tcp(coap_socket_t *server, + coap_socket_t *new_client, + coap_address_t *local_addr, + coap_address_t *remote_addr); + +#endif /* !COAP_DISABLE_TCP */ + +/** @} */ + +#endif /* COAP_TCP_INTERNAL_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_time.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_time.h new file mode 100644 index 00000000000..baa8650eaff --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/coap_time.h @@ -0,0 +1,199 @@ +/* + * coap_time.h -- Clock Handling + * + * Copyright (C) 2010-2019 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file coap_time.h + * @brief Clock Handling + */ + +#ifndef COAP_TIME_H_ +#define COAP_TIME_H_ + +/** + * @defgroup clock Clock Handling + * Default implementation of internal clock. + * @{ + */ + +#if defined(WITH_LWIP) + +#include +#include + +/* lwIP provides ms in sys_now */ +#define COAP_TICKS_PER_SECOND 1000 + +typedef uint32_t coap_tick_t; +typedef uint32_t coap_time_t; +typedef int32_t coap_tick_diff_t; + +COAP_STATIC_INLINE void coap_ticks_impl(coap_tick_t *t) { + *t = sys_now(); +} + +COAP_STATIC_INLINE void coap_clock_init_impl(void) { +} + +#define coap_clock_init coap_clock_init_impl +#define coap_ticks coap_ticks_impl + +COAP_STATIC_INLINE coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / COAP_TICKS_PER_SECOND; +} + +COAP_STATIC_INLINE uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND; +} + +#elif defined(WITH_CONTIKI) + +#include "clock.h" + +typedef clock_time_t coap_tick_t; +typedef clock_time_t coap_time_t; + +/** + * This data type is used to represent the difference between two clock_tick_t + * values. This data type must have the same size in memory as coap_tick_t to + * allow wrapping. + */ +typedef int coap_tick_diff_t; + +#define COAP_TICKS_PER_SECOND CLOCK_SECOND + +COAP_STATIC_INLINE void coap_clock_init(void) { + clock_init(); +} + +COAP_STATIC_INLINE void coap_ticks(coap_tick_t *t) { + *t = clock_time(); +} + +COAP_STATIC_INLINE coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / COAP_TICKS_PER_SECOND; +} + +COAP_STATIC_INLINE uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND; +} + +#elif defined(RIOT_VERSION) +#include + +#define COAP_TICKS_PER_SECOND (XTIMER_HZ) + +typedef uint64_t coap_tick_t; +typedef int64_t coap_tick_diff_t; +typedef uint32_t coap_time_t; + +static inline void coap_clock_init(void) {} + +static inline void coap_ticks(coap_tick_t *t) { + *t = xtimer_now_usec64(); +} + +static inline coap_time_t coap_ticks_to_rt(coap_tick_t t) { + return t / 1000000UL; +} + +static inline uint64_t coap_ticks_to_rt_us(coap_tick_t t) { + return t; +} + +static inline coap_tick_t coap_ticks_from_rt_us(uint64_t t) { + return t / 1000000UL; +} +#else /* !WITH_LWIP && !WITH_CONTIKI && !RIOT_VERSION */ + +#include + +/** + * This data type represents internal timer ticks with COAP_TICKS_PER_SECOND + * resolution. + */ +typedef uint64_t coap_tick_t; + +/** + * CoAP time in seconds since epoch. + */ +typedef time_t coap_time_t; + +/** + * This data type is used to represent the difference between two clock_tick_t + * values. This data type must have the same size in memory as coap_tick_t to + * allow wrapping. + */ +typedef int64_t coap_tick_diff_t; + +/** Use ms resolution on POSIX systems */ +#define COAP_TICKS_PER_SECOND ((coap_tick_t)(1000U)) + +/** + * Initializes the internal clock. + */ +void coap_clock_init(void); + +/** + * Sets @p t to the internal time with COAP_TICKS_PER_SECOND resolution. + */ +void coap_ticks(coap_tick_t *t); + +/** + * Helper function that converts coap ticks to wallclock time. On POSIX, this + * function returns the number of seconds since the epoch. On other systems, it + * may be the calculated number of seconds since last reboot or so. + * + * @param t Internal system ticks. + * + * @return The number of seconds that has passed since a specific reference + * point (seconds since epoch on POSIX). + */ +coap_time_t coap_ticks_to_rt(coap_tick_t t); + +/** +* Helper function that converts coap ticks to POSIX wallclock time in us. +* +* @param t Internal system ticks. +* +* @return The number of seconds that has passed since a specific reference +* point (seconds since epoch on POSIX). +*/ +uint64_t coap_ticks_to_rt_us(coap_tick_t t); + +/** +* Helper function that converts POSIX wallclock time in us to coap ticks. +* +* @param t POSIX time is us +* +* @return coap ticks +*/ +coap_tick_t coap_ticks_from_rt_us(uint64_t t); +#endif + +/** + * Returns @c 1 if and only if @p a is less than @p b where less is defined on a + * signed data type. + */ +COAP_STATIC_INLINE int coap_time_lt(coap_tick_t a, coap_tick_t b) { + return ((coap_tick_diff_t)(a - b)) < 0; +} + +/** + * Returns @c 1 if and only if @p a is less than or equal @p b where less is + * defined on a signed data type. + */ +COAP_STATIC_INLINE int coap_time_le(coap_tick_t a, coap_tick_t b) { + return a == b || coap_time_lt(a,b); +} + +/** @} */ + +#endif /* COAP_TIME_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/encode.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/encode.h new file mode 100644 index 00000000000..a79146fc862 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/encode.h @@ -0,0 +1,120 @@ +/* + * encode.h -- encoding and decoding of CoAP data types + * + * Copyright (C) 2010-2012 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_ENCODE_H_ +#define COAP_ENCODE_H_ + +#if (BSD >= 199103) || defined(WITH_CONTIKI) || defined(_WIN32) +# include +#else +# include +#endif + +#include + +#ifndef HAVE_FLS +/* include this only if fls() is not available */ +extern int coap_fls(unsigned int i); +#else +#define coap_fls(i) fls(i) +#endif + +#ifndef HAVE_FLSLL + /* include this only if flsll() is not available */ +extern int coap_flsll(long long i); +#else +#define coap_flsll(i) flsll(i) +#endif + +/** + * @defgroup encode Encode / Decode API + * API functions for endoding/decoding CoAP options. + * @{ + */ + +/** + * Decodes multiple-length byte sequences. @p buf points to an input byte + * sequence of length @p length. Returns the up to 4 byte decoded value. + * + * @param buf The input byte sequence to decode from + * @param length The length of the input byte sequence + * + * @return The decoded value + */ +unsigned int coap_decode_var_bytes(const uint8_t *buf, size_t length); + +/** + * Decodes multiple-length byte sequences. @p buf points to an input byte + * sequence of length @p length. Returns the up to 8 byte decoded value. + * + * @param buf The input byte sequence to decode from + * @param length The length of the input byte sequence + * + * @return The decoded value + */ +uint64_t coap_decode_var_bytes8(const uint8_t *buf, size_t length); + +/** + * Encodes multiple-length byte sequences. @p buf points to an output buffer of + * sufficient length to store the encoded bytes. @p value is the 4 byte value + * to encode. + * Returns the number of bytes used to encode @p value or 0 on error. + * + * @param buf The output buffer to encode into + * @param length The output buffer size to encode into (must be sufficient) + * @param value The value to encode into the buffer + * + * @return The number of bytes used to encode @p value or @c 0 on error. + */ +unsigned int coap_encode_var_safe(uint8_t *buf, + size_t length, + unsigned int value); + +/** + * Encodes multiple-length byte sequences. @p buf points to an output buffer of + * sufficient length to store the encoded bytes. @p value is the 8 byte value + * to encode. + * Returns the number of bytes used to encode @p value or 0 on error. + * + * @param buf The output buffer to encode into + * @param length The output buffer size to encode into (must be sufficient) + * @param value The value to encode into the buffer + * + * @return The number of bytes used to encode @p value or @c 0 on error. + */ +unsigned int coap_encode_var_safe8(uint8_t *buf, + size_t length, + uint64_t value); + +/** @} */ + +/** + * @deprecated Use coap_encode_var_safe() instead. + * Provided for backward compatibility. As @p value has a + * maximum value of 0xffffffff, and buf is usually defined as an array, it + * is unsafe to continue to use this variant if buf[] is less than buf[4]. + * + * For example + * char buf[1],oops; + * .. + * coap_encode_var_bytes(buf, 0xfff); + * would cause oops to get overwritten. This error can only be found by code + * inspection. + * coap_encode_var_safe(buf, sizeof(buf), 0xfff); + * would catch this error at run-time and should be used instead. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_encode_var_bytes(uint8_t *buf, unsigned int value +) { + return (int)coap_encode_var_safe(buf, sizeof(value), value); +} + +#endif /* COAP_ENCODE_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/libcoap.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/libcoap.h new file mode 100644 index 00000000000..60ca3b64b90 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/libcoap.h @@ -0,0 +1,63 @@ +/* + * libcoap.h -- platform specific header file for CoAP stack + * + * Copyright (C) 2015 Carsten Schoenert + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_LIBCOAP_H_ +#define COAP_LIBCOAP_H_ + +/* The non posix embedded platforms like Contiki, TinyOS, RIOT, ... doesn't have + * a POSIX compatible header structure so we have to slightly do some platform + * related things. Currently there is only Contiki available so we check for a + * CONTIKI environment and do *not* include the POSIX related network stuff. If + * there are other platforms in future there need to be analogous environments. + * + * The CONTIKI variable is within the Contiki build environment! */ + +#if defined(_WIN32) +#pragma comment(lib,"Ws2_32.lib") +#include +typedef SSIZE_T ssize_t; +typedef USHORT in_port_t; +#elif !defined (CONTIKI) +#include +#include +#endif /* CONTIKI */ + +#ifndef COAP_STATIC_INLINE +# if defined(__cplusplus) +# define COAP_STATIC_INLINE inline +# else +# if defined(_MSC_VER) +# define COAP_STATIC_INLINE static __inline +# else +# define COAP_STATIC_INLINE static inline +# endif +# endif +#endif +#ifndef COAP_DEPRECATED +# if defined(_MSC_VER) +# define COAP_DEPRECATED __declspec(deprecated) +# else +# define COAP_DEPRECATED __attribute__ ((deprecated)) +# endif +#endif +#ifndef COAP_UNUSED +# ifdef __GNUC__ +# define COAP_UNUSED __attribute__((unused)) +# else /* __GNUC__ */ +# define COAP_UNUSED +# endif /* __GNUC__ */ +#endif /* COAP_UNUSED */ + +void coap_startup(void); + +void coap_cleanup(void); + +#endif /* COAP_LIBCOAP_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/lwippools.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/lwippools.h new file mode 100644 index 00000000000..445bce4a94a --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/lwippools.h @@ -0,0 +1,117 @@ +/* + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/* Memory pool definitions for the libcoap when used with lwIP (which has its + * own mechanism for quickly allocating chunks of data with known sizes). Has + * to be findable by lwIP (ie. an #include must either directly + * include this or include something more generic which includes this), and + * MEMP_USE_CUSTOM_POOLS has to be set in lwipopts.h. */ + +#include "coap_internal.h" +#include "net.h" +#include "resource.h" +#include "subscribe.h" + +#ifndef MEMP_NUM_COAPCONTEXT +#define MEMP_NUM_COAPCONTEXT 1 +#endif + +#ifndef MEMP_NUM_COAPENDPOINT +#define MEMP_NUM_COAPENDPOINT 1 +#endif + +/* 1 is sufficient as this is very short-lived */ +#ifndef MEMP_NUM_COAPPACKET +#define MEMP_NUM_COAPPACKET 1 +#endif + +#ifndef MEMP_NUM_COAPNODE +#define MEMP_NUM_COAPNODE 4 +#endif + +#ifndef MEMP_NUM_COAPPDU +#define MEMP_NUM_COAPPDU MEMP_NUM_COAPNODE +#endif + +#ifndef MEMP_NUM_COAPSESSION +#define MEMP_NUM_COAPSESSION 2 +#endif + +#ifndef MEMP_NUM_COAP_SUBSCRIPTION +#define MEMP_NUM_COAP_SUBSCRIPTION 4 +#endif + +#ifndef MEMP_NUM_COAPRESOURCE +#define MEMP_NUM_COAPRESOURCE 10 +#endif + +#ifndef MEMP_NUM_COAPRESOURCEATTR +#define MEMP_NUM_COAPRESOURCEATTR 20 +#endif + +#ifndef MEMP_NUM_COAPOPTLIST +#define MEMP_NUM_COAPOPTLIST 1 +#endif + +#ifndef MEMP_LEN_COAPOPTLIST +#define MEMP_LEN_COAPOPTLIST 12 +#endif + +#ifndef MEMP_NUM_COAPSTRING +#define MEMP_NUM_COAPSTRING 10 +#endif + +#ifndef MEMP_LEN_COAPSTRING +#define MEMP_LEN_COAPSTRING 32 +#endif + +#ifndef MEMP_NUM_COAPCACHE_KEYS +#define MEMP_NUM_COAPCACHE_KEYS (2U) +#endif /* MEMP_NUM_COAPCACHE_KEYS */ + +#ifndef MEMP_NUM_COAPCACHE_ENTRIES +#define MEMP_NUM_COAPCACHE_ENTRIES (2U) +#endif /* MEMP_NUM_COAPCACHE_ENTRIES */ + +#ifndef MEMP_NUM_COAPPDUBUF +#define MEMP_NUM_COAPPDUBUF 2 +#endif + +#ifndef MEMP_LEN_COAPPDUBUF +#define MEMP_LEN_COAPPDUBUF 32 +#endif + +#ifndef MEMP_NUM_COAPLGXMIT +#define MEMP_NUM_COAPLGXMIT 2 +#endif + +#ifndef MEMP_NUM_COAPLGCRCV +#define MEMP_NUM_COAPLGCRCV 2 +#endif + +#ifndef MEMP_NUM_COAPLGSRCV +#define MEMP_NUM_COAPLGSRCV 2 +#endif + +LWIP_MEMPOOL(COAP_CONTEXT, MEMP_NUM_COAPCONTEXT, sizeof(coap_context_t), "COAP_CONTEXT") +LWIP_MEMPOOL(COAP_ENDPOINT, MEMP_NUM_COAPENDPOINT, sizeof(coap_endpoint_t), "COAP_ENDPOINT") +LWIP_MEMPOOL(COAP_PACKET, MEMP_NUM_COAPPACKET, sizeof(coap_packet_t), "COAP_PACKET") +LWIP_MEMPOOL(COAP_NODE, MEMP_NUM_COAPNODE, sizeof(coap_queue_t), "COAP_NODE") +LWIP_MEMPOOL(COAP_PDU, MEMP_NUM_COAPPDU, sizeof(coap_pdu_t), "COAP_PDU") +LWIP_MEMPOOL(COAP_SESSION, MEMP_NUM_COAPSESSION, sizeof(coap_session_t), "COAP_SESSION") +LWIP_MEMPOOL(COAP_subscription, MEMP_NUM_COAP_SUBSCRIPTION, sizeof(coap_subscription_t), "COAP_subscription") +LWIP_MEMPOOL(COAP_RESOURCE, MEMP_NUM_COAPRESOURCE, sizeof(coap_resource_t), "COAP_RESOURCE") +LWIP_MEMPOOL(COAP_RESOURCEATTR, MEMP_NUM_COAPRESOURCEATTR, sizeof(coap_attr_t), "COAP_RESOURCEATTR") +LWIP_MEMPOOL(COAP_OPTLIST, MEMP_NUM_COAPOPTLIST, sizeof(coap_optlist_t)+MEMP_LEN_COAPOPTLIST, "COAP_OPTLIST") +LWIP_MEMPOOL(COAP_STRING, MEMP_NUM_COAPSTRING, sizeof(coap_string_t)+MEMP_LEN_COAPSTRING, "COAP_STRING") +LWIP_MEMPOOL(COAP_CACHE_KEY, MEMP_NUM_COAPCACHE_KEYS, sizeof(coap_cache_key_t), "COAP_CACHE_KEY") +LWIP_MEMPOOL(COAP_CACHE_ENTRY, MEMP_NUM_COAPCACHE_ENTRIES, sizeof(coap_cache_entry_t), "COAP_CACHE_ENTRY") +LWIP_MEMPOOL(COAP_PDU_BUF, MEMP_NUM_COAPPDUBUF, MEMP_LEN_COAPPDUBUF, "COAP_PDU_BUF") +LWIP_MEMPOOL(COAP_LG_XMIT, MEMP_NUM_COAPLGXMIT, sizeof(coap_lg_xmit_t), "COAP_LG_XMIT") +LWIP_MEMPOOL(COAP_LG_CRCV, MEMP_NUM_COAPLGCRCV, sizeof(coap_lg_crcv_t), "COAP_LG_CRCV") +LWIP_MEMPOOL(COAP_LG_SRCV, MEMP_NUM_COAPLGSRCV, sizeof(coap_lg_srcv_t), "COAP_LG_SRCV") + diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/mem.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/mem.h new file mode 100644 index 00000000000..c42008963da --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/mem.h @@ -0,0 +1,139 @@ +/* + * mem.h -- CoAP memory handling + * + * Copyright (C) 2010-2011,2014-2015 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_MEM_H_ +#define COAP_MEM_H_ + +#include + +#ifndef WITH_LWIP +/** + * Initializes libcoap's memory management. + * This function must be called once before coap_malloc() can be used on + * constrained devices. + */ +void coap_memory_init(void); +#endif /* WITH_LWIP */ + +/** + * Type specifiers for coap_malloc_type(). Memory objects can be typed to + * facilitate arrays of type objects to be used instead of dynamic memory + * management on constrained devices. + */ +typedef enum { + COAP_STRING, + COAP_ATTRIBUTE_NAME, + COAP_ATTRIBUTE_VALUE, + COAP_PACKET, + COAP_NODE, + COAP_CONTEXT, + COAP_ENDPOINT, + COAP_PDU, + COAP_PDU_BUF, + COAP_RESOURCE, + COAP_RESOURCEATTR, +#ifdef HAVE_LIBTINYDTLS + COAP_DTLS_SESSION, +#endif + COAP_SESSION, + COAP_OPTLIST, + COAP_CACHE_KEY, + COAP_CACHE_ENTRY, + COAP_LG_XMIT, + COAP_LG_CRCV, + COAP_LG_SRCV, +} coap_memory_tag_t; + +#ifndef WITH_LWIP + +/** + * Allocates a chunk of @p size bytes and returns a pointer to the newly + * allocated memory. The @p type is used to select the appropriate storage + * container on constrained devices. The storage allocated by coap_malloc_type() + * must be released with coap_free_type(). + * + * @param type The type of object to be stored. + * @param size The number of bytes requested. + * @return A pointer to the allocated storage or @c NULL on error. + */ +void *coap_malloc_type(coap_memory_tag_t type, size_t size); + +/** + * Reallocates a chunk @p p of bytes created by coap_malloc_type() or + * coap_realloc_type() and returns a pointer to the newly allocated memory of + * @p size. + * Only COAP_STRING type is supported. + * + * Note: If there is an error, @p p will separately need to be released by + * coap_free_type(). + * + * @param type The type of object to be stored. + * @param p A pointer to memory that was allocated by coap_malloc_type(). + * @param size The number of bytes requested. + * @return A pointer to the allocated storage or @c NULL on error. + */ +void *coap_realloc_type(coap_memory_tag_t type, void *p, size_t size); + +/** + * Releases the memory that was allocated by coap_malloc_type(). The type tag @p + * type must be the same that was used for allocating the object pointed to by + * @p . + * + * @param type The type of the object to release. + * @param p A pointer to memory that was allocated by coap_malloc_type(). + */ +void coap_free_type(coap_memory_tag_t type, void *p); + +/** + * Wrapper function to coap_malloc_type() for backwards compatibility. + */ +COAP_STATIC_INLINE void *coap_malloc(size_t size) { + return coap_malloc_type(COAP_STRING, size); +} + +/** + * Wrapper function to coap_free_type() for backwards compatibility. + */ +COAP_STATIC_INLINE void coap_free(void *object) { + coap_free_type(COAP_STRING, object); +} + +#endif /* not WITH_LWIP */ + +#ifdef WITH_LWIP + +#include + +/* no initialization needed with lwip (or, more precisely: lwip must be + * completely initialized anyway by the time coap gets active) */ +COAP_STATIC_INLINE void coap_memory_init(void) {} + +/* It would be nice to check that size equals the size given at the memp + * declaration, but i currently don't see a standard way to check that without + * sourcing the custom memp pools and becoming dependent of its syntax + */ +#define coap_malloc_type(type, size) memp_malloc(MEMP_ ## type) +#define coap_free_type(type, p) memp_free(MEMP_ ## type, p) + +/* Those are just here to make uri.c happy where string allocation has not been + * made conditional. + */ +COAP_STATIC_INLINE void *coap_malloc(size_t size) { + LWIP_ASSERT("coap_malloc must not be used in lwIP", 0); +} + +COAP_STATIC_INLINE void coap_free(void *pointer) { + LWIP_ASSERT("coap_free must not be used in lwIP", 0); +} + +#endif /* WITH_LWIP */ + +#endif /* COAP_MEM_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/net.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/net.h new file mode 100644 index 00000000000..577a0b5d5a5 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/net.h @@ -0,0 +1,779 @@ +/* + * net.h -- CoAP network interface + * + * Copyright (C) 2010-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_NET_H_ +#define COAP_NET_H_ + +#include +#include +#ifndef _WIN32 +#include +#endif +#include + +#ifdef WITH_LWIP +#include +#endif + +#include "coap_io.h" +#include "coap_dtls.h" +#include "coap_event.h" +#include "pdu.h" +#include "coap_session.h" + +/** + * @defgroup context Context Handling + * API functions for handling PDUs using CoAP Contexts + * @{ + */ + +typedef enum coap_response_t { + COAP_RESPONSE_FAIL, /**< Response not liked - send CoAP RST packet */ + COAP_RESPONSE_OK /**< Response is fine */ +} coap_response_t; + +/** + * Response handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param sent The PDU that was transmitted. + * @param received The PDU that was received. + * @param mid CoAP transaction ID. + + * @return @c COAP_RESPONSE_OK if successful, else @c COAP_RESPONSE_FAIL which + * triggers sending a RST packet. + */ +typedef coap_response_t (*coap_response_handler_t)(coap_session_t *session, + const coap_pdu_t *sent, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Negative Acknowedge handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param sent The PDU that was transmitted. + * @param reason The reason for the NACK. + * @param mid CoAP message ID. + */ +typedef void (*coap_nack_handler_t)(coap_session_t *session, + const coap_pdu_t *sent, + const coap_nack_reason_t reason, + const coap_mid_t mid); + +/** + * Received Ping handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param received The PDU that was received. + * @param mid CoAP message ID. + */ +typedef void (*coap_ping_handler_t)(coap_session_t *session, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Received Pong handler that is used as callback in coap_context_t. + * + * @param session CoAP session. + * @param received The PDU that was received. + * @param mid CoAP message ID. + */ +typedef void (*coap_pong_handler_t)(coap_session_t *session, + const coap_pdu_t *received, + const coap_mid_t mid); + +/** + * Registers a new message handler that is called whenever a response is + * received. + * + * @param context The context to register the handler for. + * @param handler The response handler to register. + */ +void +coap_register_response_handler(coap_context_t *context, + coap_response_handler_t handler); + +/** + * Registers a new message handler that is called whenever a confirmable + * message (request or response) is dropped after all retries have been + * exhausted, or a rst message was received, or a network or TLS level + * event was received that indicates delivering the message is not possible. + * + * @param context The context to register the handler for. + * @param handler The nack handler to register. + */ +void +coap_register_nack_handler(coap_context_t *context, + coap_nack_handler_t handler); + +/** + * Registers a new message handler that is called whenever a CoAP Ping + * message is received. + * + * @param context The context to register the handler for. + * @param handler The ping handler to register. + */ +void +coap_register_ping_handler(coap_context_t *context, + coap_ping_handler_t handler); + +/** + * Registers a new message handler that is called whenever a CoAP Pong + * message is received. + * + * @param context The context to register the handler for. + * @param handler The pong handler to register. + */ +void +coap_register_pong_handler(coap_context_t *context, + coap_pong_handler_t handler); + +/** + * Registers the option type @p type with the given context object @p ctx. + * + * @param ctx The context to use. + * @param type The option type to register. + */ +void +coap_register_option(coap_context_t *ctx, uint16_t type); + +/** + * Creates a new coap_context_t object that will hold the CoAP stack status. + */ +coap_context_t *coap_new_context(const coap_address_t *listen_addr); + +/** + * Set the context's default PSK hint and/or key for a server. + * + * @param context The current coap_context_t object. + * @param hint The default PSK server hint sent to a client. If NULL, PSK + * authentication is disabled. Empty string is a valid hint. + * @param key The default PSK key. If NULL, PSK authentication will fail. + * @param key_len The default PSK key's length. If @p 0, PSK authentication will + * fail. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_context_set_psk( coap_context_t *context, const char *hint, + const uint8_t *key, size_t key_len ); + +/** + * Set the context's default PSK hint and/or key for a server. + * + * @param context The current coap_context_t object. + * @param setup_data If NULL, PSK authentication will fail. PSK + * information required. + * + * @return @c 1 if successful, else @c 0. + */ +int coap_context_set_psk2(coap_context_t *context, + coap_dtls_spsk_t *setup_data); + +/** + * Set the context's default PKI information for a server. + * + * @param context The current coap_context_t object. + * @param setup_data If NULL, PKI authentication will fail. Certificate + * information required. + * + * @return @c 1 if successful, else @c 0. + */ +int +coap_context_set_pki(coap_context_t *context, + const coap_dtls_pki_t *setup_data); + +/** + * Set the context's default Root CA information for a client or server. + * + * @param context The current coap_context_t object. + * @param ca_file If not NULL, is the full path name of a PEM encoded + * file containing all the Root CAs to be used. + * @param ca_dir If not NULL, points to a directory containing PEM + * encoded files containing all the Root CAs to be used. + * + * @return @c 1 if successful, else @c 0. + */ +int +coap_context_set_pki_root_cas(coap_context_t *context, + const char *ca_file, + const char *ca_dir); + +/** + * Set the context keepalive timer for sessions. + * A keepalive message will be sent after if a session has been inactive, + * i.e. no packet sent or received, for the given number of seconds. + * For unreliable protocols, a CoAP Empty message will be sent. If a + * CoAP RST is not received, the CoAP Empty messages will get resent based + * on the Confirmable retry parameters until there is a failure timeout, + * at which point the session will be considered as disconnected. + * For reliable protocols, a CoAP PING message will be sent. If a CoAP PONG + * has not been received before the next PING is due to be sent, the session + * will be considered as disconnected. + * + * @param context The coap_context_t object. + * @param seconds Number of seconds for the inactivity timer, or zero + * to disable CoAP-level keepalive messages. + */ +void coap_context_set_keepalive(coap_context_t *context, unsigned int seconds); + +/** + * Get the libcoap internal file descriptor for using in an application's + * select() or returned as an event in an application's epoll_wait() call. + * + * @param context The coap_context_t object. + * + * @return The libcoap file descriptor or @c -1 if epoll is not available. + */ +int coap_context_get_coap_fd(const coap_context_t *context); + +/** + * Set the maximum idle sessions count. The number of server sessions that + * are currently not in use. If this number is exceeded, the least recently + * used server session is completely removed. + * 0 (the default) means that the number is not monitored. + * + * @param context The coap_context_t object. + * @param max_idle_sessions The maximum idle session count. + */ +void +coap_context_set_max_idle_sessions(coap_context_t *context, + unsigned int max_idle_sessions); + +/** + * Get the maximum idle sessions count. + * + * @param context The coap_context_t object. + * + * @return The count of max idle sessions. + */ +unsigned int +coap_context_get_max_idle_sessions(const coap_context_t *context); + +/** + * Set the session timeout value. The number of seconds of inactivity after + * which an unused server session will be closed. + * 0 means use default (300 secs). + * + * @param context The coap_context_t object. + * @param session_timeout The session timeout value. + */ +void +coap_context_set_session_timeout(coap_context_t *context, + unsigned int session_timeout); + +/** + * Get the session timeout value + * + * @param context The coap_context_t object. + * + * @return The session timeout value. + */ +unsigned int +coap_context_get_session_timeout(const coap_context_t *context); + +/** + * Set the CSM timeout value. The number of seconds to wait for a (TCP) CSM + * negotiation response from the peer. + * 0 (the default) means use wait forever. + * + * @param context The coap_context_t object. + * @param csm_tmeout The CSM timeout value. + */ +void +coap_context_set_csm_timeout(coap_context_t *context, + unsigned int csm_tmeout); + +/** + * Get the CSM timeout value + * + * @param context The coap_context_t object. + * + * @return The CSM timeout value. + */ +unsigned int +coap_context_get_csm_timeout(const coap_context_t *context); + +/** + * Set the maximum number of sessions in (D)TLS handshake value. If this number + * is exceeded, the least recently used server session in handshake is + * completely removed. + * 0 (the default) means that the number is not monitored. + * + * @param context The coap_context_t object. + * @param max_handshake_sessions The maximum number of sessions in handshake. + */ +void +coap_context_set_max_handshake_sessions(coap_context_t *context, + unsigned int max_handshake_sessions); + +/** + * Get the session timeout value + * + * @param context The coap_context_t object. + * + * @return The maximim number of sessions in (D)TLS handshake value. + */ +unsigned int +coap_context_get_max_handshake_sessions(const coap_context_t *context); + +/** + * Returns a new message id and updates @p session->tx_mid accordingly. The + * message id is returned in network byte order to make it easier to read in + * tracing tools. + * + * @param session The current coap_session_t object. + * + * @return Incremented message id in network byte order. + */ +uint16_t coap_new_message_id(coap_session_t *session); + +/** + * CoAP stack context must be released with coap_free_context(). This function + * clears all entries from the receive queue and send queue and deletes the + * resources that have been registered with @p context, and frees the attached + * endpoints. + * + * @param context The current coap_context_t object to free off. + */ +void coap_free_context(coap_context_t *context); + +/** + * Stores @p data with the given CoAP context. This function + * overwrites any value that has previously been stored with @p + * context. + * + * @param context The CoAP context. + * @param data The data to store with wih the context. Note that this data + * must be valid during the lifetime of @p context. + */ +void coap_set_app_data(coap_context_t *context, void *data); + +/** + * Returns any application-specific data that has been stored with @p + * context using the function coap_set_app_data(). This function will + * return @c NULL if no data has been stored. + * + * @param context The CoAP context. + * + * @return The data previously stored or @c NULL if not data stored. + */ +void *coap_get_app_data(const coap_context_t *context); + +/** + * Creates a new ACK PDU with specified error @p code. The options specified by + * the filter expression @p opts will be copied from the original request + * contained in @p request. Unless @c SHORT_ERROR_RESPONSE was defined at build + * time, the textual reason phrase for @p code will be added as payload, with + * Content-Type @c 0. + * This function returns a pointer to the new response message, or @c NULL on + * error. The storage allocated for the new message must be released with + * coap_free(). + * + * @param request Specification of the received (confirmable) request. + * @param code The error code to set. + * @param opts An option filter that specifies which options to copy from + * the original request in @p node. + * + * @return A pointer to the new message or @c NULL on error. + */ +coap_pdu_t *coap_new_error_response(const coap_pdu_t *request, + coap_pdu_code_t code, + coap_opt_filter_t *opts); + +/** + * Sends an error response with code @p code for request @p request to @p dst. + * @p opts will be passed to coap_new_error_response() to copy marked options + * from the request. This function returns the message id if the message was + * sent, or @c COAP_INVALID_MID otherwise. + * + * @param session The CoAP session. + * @param request The original request to respond to. + * @param code The response code. + * @param opts A filter that specifies the options to copy from the + * @p request. + * + * @return The message id if the message was sent, or @c + * COAP_INVALID_MID otherwise. + */ +coap_mid_t coap_send_error(coap_session_t *session, + const coap_pdu_t *request, + coap_pdu_code_t code, + coap_opt_filter_t *opts); + +/** + * Helper function to create and send a message with @p type (usually ACK or + * RST). This function returns @c COAP_INVALID_MID when the message was not + * sent, a valid transaction id otherwise. + * + * @param session The CoAP session. + * @param request The request that should be responded to. + * @param type Which type to set. + * @return message id on success or @c COAP_INVALID_MID + * otherwise. + */ +coap_mid_t +coap_send_message_type(coap_session_t *session, const coap_pdu_t *request, + coap_pdu_type_t type); + +/** + * Sends an ACK message with code @c 0 for the specified @p request to @p dst. + * This function returns the corresponding message id if the message was + * sent or @c COAP_INVALID_MID on error. + * + * @param session The CoAP session. + * @param request The request to be acknowledged. + * + * @return The message id if ACK was sent or @c + * COAP_INVALID_MID on error. + */ +coap_mid_t coap_send_ack(coap_session_t *session, const coap_pdu_t *request); + +/** + * Sends an RST message with code @c 0 for the specified @p request to @p dst. + * This function returns the corresponding message id if the message was + * sent or @c COAP_INVALID_MID on error. + * + * @param session The CoAP session. + * @param request The request to be reset. + * + * @return The message id if RST was sent or @c + * COAP_INVALID_MID on error. + */ +COAP_STATIC_INLINE coap_mid_t +coap_send_rst(coap_session_t *session, const coap_pdu_t *request) { + return coap_send_message_type(session, request, COAP_MESSAGE_RST); +} + +/** +* Sends a CoAP message to given peer. The memory that is +* allocated for the pdu will be released by coap_send(). +* The caller must not use the pdu after calling coap_send(). +* +* @param session The CoAP session. +* @param pdu The CoAP PDU to send. +* +* @return The message id of the sent message or @c +* COAP_INVALID_MID on error. +*/ +coap_mid_t coap_send( coap_session_t *session, coap_pdu_t *pdu ); + +#define coap_send_large(session, pdu) coap_send(session, pdu) + +/** + * Invokes the event handler of @p context for the given @p event and + * @p data. + * + * @param context The CoAP context whose event handler is to be called. + * @param event The event to deliver. + * @param session The session related to @p event. + * @return The result from the associated event handler or 0 if none was + * registered. + */ +int coap_handle_event(coap_context_t *context, + coap_event_t event, + coap_session_t *session); +/** + * Returns 1 if there are no messages to send or to dispatch in the context's + * queues. */ +int coap_can_exit(coap_context_t *context); + +/** + * Returns the current value of an internal tick counter. The counter counts \c + * COAP_TICKS_PER_SECOND ticks every second. + */ +void coap_ticks(coap_tick_t *); + +/** + * Function interface for joining a multicast group for listening for the + * currently defined endpoints that are UDP. + * + * @param ctx The current context. + * @param groupname The name of the group that is to be joined for listening. + * @param ifname Network interface to join the group on, or NULL if first + * appropriate interface is to be chosen by the O/S. + * + * @return 0 on success, -1 on error + */ +int +coap_join_mcast_group_intf(coap_context_t *ctx, const char *groupname, + const char *ifname); + +#define coap_join_mcast_group(ctx, groupname) \ + (coap_join_mcast_group_intf(ctx, groupname, NULL)) + +/** + * Function interface for defining the hop count (ttl) for sending + * multicast traffic + * + * @param session The current contexsion. + * @param hops The number of hops (ttl) to use before the multicast + * packet expires. + * + * @return 1 on success, 0 on error + */ +int +coap_mcast_set_hops(coap_session_t *session, size_t hops); + +/**@}*/ + +/** + * @defgroup app_io Application I/O Handling + * API functions for Application Input / Output + * @{ + */ + +#define COAP_IO_WAIT 0 +#define COAP_IO_NO_WAIT ((uint32_t)-1) + +/** + * The main I/O processing function. All pending network I/O is completed, + * and then optionally waits for the next input packet. + * + * This internally calls coap_io_prepare_io(), then select() for the appropriate + * sockets, updates COAP_SOCKET_CAN_xxx where appropriate and then calls + * coap_io_do_io() before returning with the time spent in the function. + * + * Alternatively, if libcoap is compiled with epoll support, this internally + * calls coap_io_prepare_epoll(), then epoll_wait() for waiting for any file + * descriptors that have (internally) been set up with epoll_ctl() and + * finally coap_io_do_epoll() before returning with the time spent in the + * function. + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * + * @return Number of milliseconds spent in function or @c -1 if there was + * an error + */ +int coap_io_process(coap_context_t *ctx, uint32_t timeout_ms); + +#ifndef RIOT_VERSION +/** + * The main message processing loop with additional fds for internal select. + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * @param nfds The maximum FD set in readfds, writefds or exceptfds + * plus one, + * @param readfds Read FDs to additionally check for in internal select() + * or NULL if not required. + * @param writefds Write FDs to additionally check for in internal select() + * or NULL if not required. + * @param exceptfds Except FDs to additionally check for in internal select() + * or NULL if not required. + * + * + * @return Number of milliseconds spent in coap_io_process_with_fds, or @c -1 + * if there was an error. If defined, readfds, writefds, exceptfds + * are updated as returned by the internal select() call. + */ +int coap_io_process_with_fds(coap_context_t *ctx, uint32_t timeout_ms, + int nfds, fd_set *readfds, fd_set *writefds, + fd_set *exceptfds); +#endif /* !RIOT_VERSION */ + +/**@}*/ + +/** + * @defgroup app_io_internal Application I/O Handling (Internal) + * Internal API functions for Application Input / Output + * @{ + */ + +/** +* Iterates through all the coap_socket_t structures embedded in endpoints or +* sessions associated with the @p ctx to determine which are wanting any +* read, write, accept or connect I/O (COAP_SOCKET_WANT_xxx is set). If set, +* the coap_socket_t is added to the @p sockets. +* +* Any now timed out delayed packet is transmitted, along with any packets +* associated with requested observable response. +* +* In addition, it returns when the next expected I/O is expected to take place +* (e.g. a packet retransmit). +* +* Prior to calling coap_io_do_io(), the @p sockets must be tested to see +* if any of the COAP_SOCKET_WANT_xxx have the appropriate information and if +* so, COAP_SOCKET_CAN_xxx is set. This typically will be done after using a +* select() call. +* +* Note: If epoll support is compiled into libcoap, coap_io_prepare_epoll() must +* be used instead of coap_io_prepare_io(). +* +* Internal function. +* +* @param ctx The CoAP context +* @param sockets Array of socket descriptors, filled on output +* @param max_sockets Size of socket array. +* @param num_sockets Pointer to the number of valid entries in the socket +* arrays on output. +* @param now Current time. +* +* @return timeout Maxmimum number of milliseconds that can be used by a +* select() to wait for network events or 0 if wait should be +* forever. +*/ +unsigned int +coap_io_prepare_io(coap_context_t *ctx, + coap_socket_t *sockets[], + unsigned int max_sockets, + unsigned int *num_sockets, + coap_tick_t now +); + +/** + * Processes any outstanding read, write, accept or connect I/O as indicated + * in the coap_socket_t structures (COAP_SOCKET_CAN_xxx set) embedded in + * endpoints or sessions associated with @p ctx. + * + * Note: If epoll support is compiled into libcoap, coap_io_do_epoll() must + * be used instead of coap_io_do_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time + */ +void coap_io_do_io(coap_context_t *ctx, coap_tick_t now); + +/** + * Any now timed out delayed packet is transmitted, along with any packets + * associated with requested observable response. + * + * In addition, it returns when the next expected I/O is expected to take place + * (e.g. a packet retransmit). + * + * Note: If epoll support is compiled into libcoap, coap_io_prepare_epoll() must + * be used instead of coap_io_prepare_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time. + * + * @return timeout Maxmimum number of milliseconds that can be used by a + * epoll_wait() to wait for network events or 0 if wait should be + * forever. + */ +unsigned int +coap_io_prepare_epoll(coap_context_t *ctx, coap_tick_t now); + +struct epoll_event; + +/** + * Process all the epoll events + * + * Note: If epoll support is compiled into libcoap, coap_io_do_epoll() must + * be used instead of coap_io_do_io(). + * + * Internal function + * + * @param ctx The current CoAP context. + * @param events The list of events returned from an epoll_wait() call. + * @param nevents The number of events. + * + */ +void coap_io_do_epoll(coap_context_t *ctx, struct epoll_event* events, + size_t nevents); + +/**@}*/ + +/** + * @deprecated Use coap_io_process() instead. + * + * This function just calls coap_io_process(). + * + * @param ctx The CoAP context + * @param timeout_ms Minimum number of milliseconds to wait for new packets + * before returning after doing any processing. + * If COAP_IO_WAIT, the call will block until the next + * internal action (e.g. packet retransmit) if any, or block + * until the next packet is received whichever is the sooner + * and do the necessary processing. + * If COAP_IO_NO_WAIT, the function will return immediately + * after processing without waiting for any new input + * packets to arrive. + * + * @return Number of milliseconds spent in function or @c -1 if there was + * an error + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_run_once(coap_context_t *ctx, uint32_t timeout_ms) +{ + return coap_io_process(ctx, timeout_ms); +} + +/** +* @deprecated Use coap_io_prepare_io() instead. +* +* This function just calls coap_io_prepare_io(). +* +* Internal function. +* +* @param ctx The CoAP context +* @param sockets Array of socket descriptors, filled on output +* @param max_sockets Size of socket array. +* @param num_sockets Pointer to the number of valid entries in the socket +* arrays on output. +* @param now Current time. +* +* @return timeout Maxmimum number of milliseconds that can be used by a +* select() to wait for network events or 0 if wait should be +* forever. +*/ +COAP_STATIC_INLINE COAP_DEPRECATED unsigned int +coap_write(coap_context_t *ctx, + coap_socket_t *sockets[], + unsigned int max_sockets, + unsigned int *num_sockets, + coap_tick_t now +) { + return coap_io_prepare_io(ctx, sockets, max_sockets, num_sockets, now); +} + +/** + * @deprecated Use coap_io_do_io() instead. + * + * This function just calls coap_io_do_io(). + * + * Internal function. + * + * @param ctx The CoAP context + * @param now Current time + */ +COAP_STATIC_INLINE COAP_DEPRECATED void +coap_read(coap_context_t *ctx, coap_tick_t now +) { + coap_io_do_io(ctx, now); +} + +/* Old definitions which may be hanging around in old code - be helpful! */ +#define COAP_RUN_NONBLOCK COAP_RUN_NONBLOCK_deprecated_use_COAP_IO_NO_WAIT +#define COAP_RUN_BLOCK COAP_RUN_BLOCK_deprecated_use_COAP_IO_WAIT + +#endif /* COAP_NET_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/option.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/option.h new file mode 100644 index 00000000000..c01e8f6688b --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/option.h @@ -0,0 +1,439 @@ +/* + * option.h -- helpers for handling options in CoAP PDUs + * + * Copyright (C) 2010-2013 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file option.h + * @brief Helpers for handling options in CoAP PDUs + */ + +#ifndef COAP_OPTION_H_ +#define COAP_OPTION_H_ + +typedef uint16_t coap_option_num_t; + +/** + * Use byte-oriented access methods here because sliding a complex struct + * coap_opt_t over the data buffer may cause bus error on certain platforms. + */ +typedef uint8_t coap_opt_t; +#define PCHAR(p) ((coap_opt_t *)(p)) + +/** + * Representation of CoAP options. + */ +typedef struct { + uint16_t delta; + size_t length; + const uint8_t *value; +} coap_option_t; + +/** + * Parses the option pointed to by @p opt into @p result. This function returns + * the number of bytes that have been parsed, or @c 0 on error. An error is + * signaled when illegal delta or length values are encountered or when option + * parsing would result in reading past the option (i.e. beyond opt + length). + * + * @param opt The beginning of the option to parse. + * @param length The maximum length of @p opt. + * @param result A pointer to the coap_option_t structure that is filled with + * actual values iff coap_opt_parse() > 0. + * @return The number of bytes parsed or @c 0 on error. + */ +size_t coap_opt_parse(const coap_opt_t *opt, + size_t length, + coap_option_t *result); + +/** + * Returns the size of the given option, taking into account a possible option + * jump. + * + * @param opt An option jump or the beginning of the option. + * @return The number of bytes between @p opt and the end of the option + * starting at @p opt. In case of an error, this function returns + * @c 0 as options need at least one byte storage space. + */ +size_t coap_opt_size(const coap_opt_t *opt); + +/** + * @defgroup opt_filter Option Filters + * API functions for access option filters + * @{ + */ + +/** + * The number of option types below 256 that can be stored in an + * option filter. COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be + * at most 16. Each coap_option_filter_t object reserves + * ((COAP_OPT_FILTER_SHORT + 1) / 2) * 2 bytes for short options. + */ +#define COAP_OPT_FILTER_SHORT 6 + +/** + * The number of option types above 255 that can be stored in an + * option filter. COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be + * at most 16. Each coap_option_filter_t object reserves + * COAP_OPT_FILTER_LONG * 2 bytes for short options. + */ +#define COAP_OPT_FILTER_LONG 2 + +/* Ensure that COAP_OPT_FILTER_SHORT and COAP_OPT_FILTER_LONG are set + * correctly. */ +#if (COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG > 16) +#error COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG must be less or equal 16 +#endif /* (COAP_OPT_FILTER_SHORT + COAP_OPT_FILTER_LONG > 16) */ + +/* + * mask contains a bit vector that indicates which fields in the long_opts[] + * and subsequent short_opts[] are used. The first COAP_OPT_FILTER_LONG bits + * correspond to the long option types that are stored in long_opts[] + * elements. The next COAP_OPT_FILTER_SHORT bits correspond to the short + * option types that are stored in short_opts[]. + */ +typedef struct coap_opt_filter_t { + uint16_t mask; + uint16_t long_opts[COAP_OPT_FILTER_LONG]; + uint8_t short_opts[COAP_OPT_FILTER_SHORT]; +} coap_opt_filter_t; + +/** Pre-defined filter that includes all options. */ +#define COAP_OPT_ALL NULL + +/** + * Clears filter @p filter. + * + * @param filter The filter to clear. + */ +void +coap_option_filter_clear(coap_opt_filter_t *filter); + +/** + * Sets the corresponding entry for @p number in @p filter. This + * function returns @c 1 if bit was set or @c 0 on error (i.e. when + * the given number does not fit in the filter). + * + * @param filter The filter object to change. + * @param number The option number for which the bit should be set. + * + * @return @c 1 if bit was set, @c 0 otherwise. + */ +int coap_option_filter_set(coap_opt_filter_t *filter, coap_option_num_t number); + +/** + * Clears the corresponding entry for @p number in @p filter. This + * function returns @c 1 if bit was set or @c 0 on error (i.e. when + * the given number does not fit in the filter). + * + * @param filter The filter object to change. + * @param number The option number that should be cleared from the filter. + * + * @return @c 1 if bit was set, @c 0 otherwise. + */ +int coap_option_filter_unset(coap_opt_filter_t *filter, + coap_option_num_t number); + +/** + * Checks if @p number is contained in @p filter. This function returns + * @c 1 if found, @c 0 if not, or @c -1 on error (i.e. when the given + * number does not fit in the filter). + * + * @param filter The filter object to search. + * @param number The option number to search for. + * + * @return @c 1 if @p number was found, @c 0 otherwise, or @c -1 on error. + */ +int coap_option_filter_get(coap_opt_filter_t *filter, coap_option_num_t number); + +/** + * Iterator to run through PDU options. This object must be + * initialized with coap_option_iterator_init(). Call + * coap_option_next() to walk through the list of options until + * coap_option_next() returns @c NULL. + * + * @code + * coap_opt_t *option; + * coap_opt_iterator_t opt_iter; + * coap_option_iterator_init(pdu, &opt_iter, COAP_OPT_ALL); + * + * while ((option = coap_option_next(&opt_iter))) { + * ... do something with option ... + * } + * @endcode + */ +typedef struct { + size_t length; /**< remaining length of PDU */ + coap_option_num_t number; /**< decoded option number */ + unsigned int bad:1; /**< iterator object is ok if not set */ + unsigned int filtered:1; /**< denotes whether or not filter is used */ + coap_opt_t *next_option; /**< pointer to the unparsed next option */ + coap_opt_filter_t filter; /**< option filter */ +} coap_opt_iterator_t; + +/** + * Initializes the given option iterator @p oi to point to the beginning of the + * @p pdu's option list. This function returns @p oi on success, @c NULL + * otherwise (i.e. when no options exist). Note that a length check on the + * option list must be performed before coap_option_iterator_init() is called. + * + * @param pdu The PDU the options of which should be walked through. + * @param oi An iterator object that will be initilized. + * @param filter An optional option number filter. + * With @p number != @c COAP_OPT_ALL, coap_option_next() + * will return only options matching this bitmask. + * Fence-post options @c 14, @c 28, @c 42, ... are always + * skipped. + * + * @return The iterator object @p oi on success, @c NULL otherwise. + */ +coap_opt_iterator_t *coap_option_iterator_init(const coap_pdu_t *pdu, + coap_opt_iterator_t *oi, + const coap_opt_filter_t *filter); + +/** + * Updates the iterator @p oi to point to the next option. This function returns + * a pointer to that option or @c NULL if no more options exist. The contents of + * @p oi will be updated. In particular, @c oi->n specifies the current option's + * ordinal number (counted from @c 1), @c oi->number is the option's number + * value, and @c oi->option points to the beginning of the current option + * itself. When * advanced past the last option, @c oi->option will be @c NULL. + * + * Note that options are skipped whose corresponding bits in the filter + * specified with coap_option_iterator_init() are @c 0. Options with numbers + * that do not fit in this filter hence will always be returned. + * + * @param oi The option iterator to update. + * + * @return The next option or @c NULL if no more options exist. + */ +coap_opt_t *coap_option_next(coap_opt_iterator_t *oi); + +/** + * Retrieves the first option of number @p number from @p pdu. @p oi must + * point to a coap_opt_iterator_t object that will be initialized by this + * function to filter only options with number @p number. This function returns + * the first option with this number, or @c NULL if not found. + * + * @param pdu The PDU to parse for options. + * @param number The option number to search for. + * @param oi An iterator object to use. + * + * @return A pointer to the first option of number @p number, or @c NULL if + * not found. + */ +coap_opt_t *coap_check_option(const coap_pdu_t *pdu, + coap_option_num_t number, + coap_opt_iterator_t *oi); + +/** + * Encodes the given delta and length values into @p opt. This function returns + * the number of bytes that were required to encode @p delta and @p length or @c + * 0 on error. Note that the result indicates by how many bytes @p opt must be + * advanced to encode the option value. + * + * @param opt The option buffer space where @p delta and @p length are + * written. + * @param maxlen The maximum length of @p opt. + * @param delta The actual delta value to encode. + * @param length The actual length value to encode. + * + * @return The number of bytes used or @c 0 on error. + */ +size_t coap_opt_setheader(coap_opt_t *opt, + size_t maxlen, + uint16_t delta, + size_t length); + +/** + * Compute storage bytes needed for an option with given @p delta and + * @p length + * + * @param delta The option delta. + * @param length The option length. + * + * @return The number of bytes required to encode this option. + */ +size_t coap_opt_encode_size(uint16_t delta, size_t length); + +/** + * Encodes option with given @p delta into @p opt. This function returns the + * number of bytes written to @p opt or @c 0 on error. This happens especially + * when @p opt does not provide sufficient space to store the option value, + * delta, and option jumps when required. + * + * @param opt The option buffer space where @p val is written. + * @param n Maximum length of @p opt. + * @param delta The option delta. + * @param val The option value to copy into @p opt. + * @param length The actual length of @p val. + * + * @return The number of bytes that have been written to @p opt or @c 0 on + * error. The return value will always be less than @p n. + */ +size_t coap_opt_encode(coap_opt_t *opt, + size_t n, + uint16_t delta, + const uint8_t *val, + size_t length); + +/** + * Returns the length of the given option. @p opt must point to an option jump + * or the beginning of the option. This function returns @c 0 when @p opt is not + * an option or the actual length of @p opt (which can be @c 0 as well). + * + * @note {The rationale for using @c 0 in case of an error is that in most + * contexts, the result of this function is used to skip the next + * coap_opt_length() bytes.} + * + * @param opt The option whose length should be returned. + * + * @return The option's length or @c 0 when undefined. + */ +uint32_t coap_opt_length(const coap_opt_t *opt); + +/** + * Returns a pointer to the value of the given option. @p opt must point to an + * option jump or the beginning of the option. This function returns @c NULL if + * @p opt is not a valid option. + * + * @param opt The option whose value should be returned. + * + * @return A pointer to the option value or @c NULL on error. + */ +const uint8_t *coap_opt_value(const coap_opt_t *opt); + +/** + * Representation of chained list of CoAP options to install. + * + * @code + * coap_optlist_t *optlist_chain = NULL; + * coap_pdu_t *pdu = coap_new_pdu(session); + * + * ... other set up code ... + * coap_insert_optlist(&optlist_chain, coap_new_optlist(COAP_OPTION_OBSERVE, + * COAP_OBSERVE_ESTABLISH, NULL)); + * + * coap_add_optlist_pdu(pdu, &optlist_chain); + * ... other code ... + * coap_delete_optlist(optlist_chain); + * @endcode + */ +typedef struct coap_optlist_t { + struct coap_optlist_t *next; /**< next entry in the optlist chain */ + uint16_t number; /**< the option number (no delta coding) */ + size_t length; /**< the option value length */ + uint8_t *data; /**< the option data */ +} coap_optlist_t; + +/** + * Create a new optlist entry. + * + * Note: Where possible, the option data needs to be stripped of leading zeros + * (big endian) to reduce the amount of data needed in the PDU, as well as in + * some cases the maximum data size of an opton can be exceeded if not stripped + * and hence be illegal. This is done by using coap_encode_var_safe() or + * coap_encode_var_safe8(). + * + * @param number The option number (COAP_OPTION_*) + * @param length The option length + * @param data The option value data + * + * @return A pointer to the new optlist entry, or @c NULL if error + */ +coap_optlist_t *coap_new_optlist(uint16_t number, + size_t length, + const uint8_t *data); + +/** + * The current optlist of @p optlist_chain is first sorted (as per RFC7272 + * ordering requirements) and then added to the @p pdu. + * + * @param pdu The pdu to add the options to from the chain list + * @param optlist_chain The chained list of optlist to add to the pdu + * + * @return @c 1 if succesful or @c 0 if failure; + */ +int coap_add_optlist_pdu(coap_pdu_t *pdu, coap_optlist_t** optlist_chain); + +/** + * Adds @p optlist to the given @p optlist_chain. The optlist_chain variable + * be set to NULL before the initial call to coap_insert_optlist(). + * The optlist_chain will need to be deleted using coap_delete_optlist() + * when no longer required. + * + * @param optlist_chain The chain to add optlist to + * @param optlist The optlist to add to the queue + * + * @return @c 1 if successful, @c 0 otherwise. + */ +int coap_insert_optlist(coap_optlist_t **optlist_chain, + coap_optlist_t *optlist); + +/** + * Removes all entries from the @p optlist_chain, freeing off their + * memory usage. + * + * @param optlist_chain The optlist chain to remove all the entries from + */ +void coap_delete_optlist(coap_optlist_t *optlist_chain); + +/** @} */ + +/** + * Sets the corresponding bit for @p type in @p filter. This function returns @c + * 1 if bit was set or @c -1 on error (i.e. when the given type does not fit in + * the filter). + * + * @deprecated Use coap_option_filter_set() instead. + * + * @param filter The filter object to change. + * @param type The type for which the bit should be set. + * + * @return @c 1 if bit was set, @c -1 otherwise. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_setb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_set(filter, type) ? 1 : -1; +} + +/** + * Clears the corresponding bit for @p type in @p filter. This function returns + * @c 1 if bit was cleared or @c -1 on error (i.e. when the given type does not + * fit in the filter). + * + * @deprecated Use coap_option_filter_unset() instead. + * + * @param filter The filter object to change. + * @param type The type for which the bit should be cleared. + * + * @return @c 1 if bit was set, @c -1 otherwise. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_clrb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_unset(filter, type) ? 1 : -1; +} + +/** + * Gets the corresponding bit for @p type in @p filter. This function returns @c + * 1 if the bit is set @c 0 if not, or @c -1 on error (i.e. when the given type + * does not fit in the filter). + * + * @deprecated Use coap_option_filter_get() instead. + * + * @param filter The filter object to read bit from. + * @param type The type for which the bit should be read. + * + * @return @c 1 if bit was set, @c 0 if not, @c -1 on error. + */ +COAP_STATIC_INLINE COAP_DEPRECATED int +coap_option_getb(coap_opt_filter_t *filter, uint16_t type) { + return coap_option_filter_get(filter, type); +} + +#endif /* COAP_OPTION_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/pdu.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/pdu.h new file mode 100644 index 00000000000..a22869b69ed --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/pdu.h @@ -0,0 +1,572 @@ +/* + * pdu.h -- CoAP message structure + * + * Copyright (C) 2010-2014 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file pdu.h + * @brief Pre-defined constants that reflect defaults for CoAP + */ + +#ifndef COAP_PDU_H_ +#define COAP_PDU_H_ + +#include "uri.h" +#include "option.h" + +#ifdef WITH_LWIP +#include +#endif + +#include + +/** + * @defgroup pdu PDU + * API functions for PDUs + * @{ + */ + +#define COAP_DEFAULT_PORT 5683 /* CoAP default UDP/TCP port */ +#define COAPS_DEFAULT_PORT 5684 /* CoAP default UDP/TCP port for secure transmission */ +#define COAP_DEFAULT_MAX_AGE 60 /* default maximum object lifetime in seconds */ +#ifndef COAP_DEFAULT_MTU +#define COAP_DEFAULT_MTU 1152 +#endif /* COAP_DEFAULT_MTU */ + +#ifndef COAP_DEFAULT_HOP_LIMIT +#define COAP_DEFAULT_HOP_LIMIT 16 +#endif /* COAP_DEFAULT_HOP_LIMIT */ + +#define COAP_DEFAULT_SCHEME "coap" /* the default scheme for CoAP URIs */ + +/** well-known resources URI */ +#define COAP_DEFAULT_URI_WELLKNOWN ".well-known/core" + +/* CoAP message types */ + +/** + * CoAP PDU message type definitions + */ +typedef enum coap_pdu_type_t { + COAP_MESSAGE_CON, /* 0 confirmable message (requires ACK/RST) */ + COAP_MESSAGE_NON, /* 1 non-confirmable message (one-shot message) */ + COAP_MESSAGE_ACK, /* 2 used to acknowledge confirmable messages */ + COAP_MESSAGE_RST /* 3 indicates error in received messages */ +} coap_pdu_type_t; + +/** + * CoAP PDU Request methods + */ +typedef enum coap_request_t { + COAP_REQUEST_GET = 1, + COAP_REQUEST_POST, /* 2 */ + COAP_REQUEST_PUT, /* 3 */ + COAP_REQUEST_DELETE, /* 4 */ + COAP_REQUEST_FETCH, /* 5 RFC 8132 */ + COAP_REQUEST_PATCH, /* 6 RFC 8132 */ + COAP_REQUEST_IPATCH, /* 7 RFC 8132 */ +} coap_request_t; + +/* + * CoAP option numbers (be sure to update coap_option_check_critical() and + * coap_add_option() when adding options + */ + +/* + * The C, U, and N flags indicate the properties + * Critical, Unsafe, and NoCacheKey, respectively. + * If U is set, then N has no meaning as per + * https://tools.ietf.org/html/rfc7252#section-5.10 + * and is set to a -. + * + * Separately, R is for the options that can be repeated + * + * The least significant byte of the option is set as followed + * as per https://tools.ietf.org/html/rfc7252#section-5.4.6 + * + * 0 1 2 3 4 5 6 7 + * --+---+---+---+---+---+---+---+ + * | NoCacheKey| U | C | + * --+---+---+---+---+---+---+---+ + * + * https://tools.ietf.org/html/rfc8613#section-4 goes on to define E, I and U + * properties Encrypted and Integrity Protected, Integrity Protected Only, and + * Unprotected respectively. Integrity Protected Only is not currently used. + * + * An Option is tagged with CUNREIU with any of the letters replaced with _ if + * not set, or - for N if U is set (see above) for aiding understanding of the + * Option. + */ + +#define COAP_OPTION_IF_MATCH 1 /* C__RE__, opaque, 0-8 B, RFC7252 */ +#define COAP_OPTION_URI_HOST 3 /* CU-___U, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_ETAG 4 /* ___RE__, opaque, 1-8 B, RFC7252 */ +#define COAP_OPTION_IF_NONE_MATCH 5 /* C___E__, empty, 0 B, RFC7252 */ +#define COAP_OPTION_OBSERVE 6 /* _U-_E_U, empty/uint,0/0-3 B, RFC7641 */ +#define COAP_OPTION_URI_PORT 7 /* CU-___U, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_LOCATION_PATH 8 /* ___RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_OSCORE 9 /* C_____U, *, 0-255 B, RFC8613 */ +#define COAP_OPTION_URI_PATH 11 /* CU-RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_CONTENT_FORMAT 12 /* ____E__, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_CONTENT_TYPE COAP_OPTION_CONTENT_FORMAT +/* COAP_OPTION_MAXAGE default 60 seconds if not set */ +#define COAP_OPTION_MAXAGE 14 /* _U-_E_U, uint, 0-4 B, RFC7252 */ +#define COAP_OPTION_URI_QUERY 15 /* CU-RE__, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_HOP_LIMIT 16 /* ______U, uint, 1 B, RFC8768 */ +#define COAP_OPTION_ACCEPT 17 /* C___E__, uint, 0-2 B, RFC7252 */ +#define COAP_OPTION_LOCATION_QUERY 20 /* ___RE__, String, 0-255 B, RFC7252 */ +#define COAP_OPTION_BLOCK2 23 /* CU-_E_U, uint, 0-3 B, RFC7959 */ +#define COAP_OPTION_BLOCK1 27 /* CU-_E_U, uint, 0-3 B, RFC7959 */ +#define COAP_OPTION_SIZE2 28 /* __N_E_U, uint, 0-4 B, RFC7959 */ +#define COAP_OPTION_PROXY_URI 35 /* CU-___U, String, 1-1034 B, RFC7252 */ +#define COAP_OPTION_PROXY_SCHEME 39 /* CU-___U, String, 1-255 B, RFC7252 */ +#define COAP_OPTION_SIZE1 60 /* __N_E_U, uint, 0-4 B, RFC7252 */ +#define COAP_OPTION_NORESPONSE 258 /* _U-_E_U, uint, 0-1 B, RFC7967 */ + +#define COAP_MAX_OPT 65535 /**< the highest option number we know */ + +/* CoAP result codes (HTTP-Code / 100 * 40 + HTTP-Code % 100) */ + +/* As of draft-ietf-core-coap-04, response codes are encoded to base + * 32, i.e. the three upper bits determine the response class while + * the remaining five fine-grained information specific to that class. + */ +#define COAP_RESPONSE_CODE(N) (((N)/100 << 5) | (N)%100) + +/* Determines the class of response code C */ +#define COAP_RESPONSE_CLASS(C) (((C) >> 5) & 0xFF) + +#ifndef SHORT_ERROR_RESPONSE +/** + * Returns a human-readable response phrase for the specified CoAP response @p + * code. This function returns @c NULL if not found. + * + * @param code The response code for which the literal phrase should be + * retrieved. + * + * @return A zero-terminated string describing the error, or @c NULL if not + * found. + */ +const char *coap_response_phrase(unsigned char code); + +#define COAP_ERROR_PHRASE_LENGTH 32 /**< maximum length of error phrase */ + +#else +#define coap_response_phrase(x) ((char *)NULL) + +#define COAP_ERROR_PHRASE_LENGTH 0 /**< maximum length of error phrase */ +#endif /* SHORT_ERROR_RESPONSE */ + +#define COAP_SIGNALING_CODE(N) (((N)/100 << 5) | (N)%100) + +typedef enum coap_pdu_signaling_proto_t { + COAP_SIGNALING_CSM = COAP_SIGNALING_CODE(701), + COAP_SIGNALING_PING = COAP_SIGNALING_CODE(702), + COAP_SIGNALING_PONG = COAP_SIGNALING_CODE(703), + COAP_SIGNALING_RELEASE = COAP_SIGNALING_CODE(704), + COAP_SIGNALING_ABORT = COAP_SIGNALING_CODE(705), +} coap_pdu_signaling_proto_t; + +/* Applies to COAP_SIGNALING_CSM */ +#define COAP_SIGNALING_OPTION_MAX_MESSAGE_SIZE 2 +#define COAP_SIGNALING_OPTION_BLOCK_WISE_TRANSFER 4 +/* Applies to COAP_SIGNALING_PING / COAP_SIGNALING_PONG */ +#define COAP_SIGNALING_OPTION_CUSTODY 2 +/* Applies to COAP_SIGNALING_RELEASE */ +#define COAP_SIGNALING_OPTION_ALTERNATIVE_ADDRESS 2 +#define COAP_SIGNALING_OPTION_HOLD_OFF 4 +/* Applies to COAP_SIGNALING_ABORT */ +#define COAP_SIGNALING_OPTION_BAD_CSM_OPTION 2 + +/* CoAP media type encoding */ + +#define COAP_MEDIATYPE_TEXT_PLAIN 0 /* text/plain (UTF-8) */ +#define COAP_MEDIATYPE_APPLICATION_LINK_FORMAT 40 /* application/link-format */ +#define COAP_MEDIATYPE_APPLICATION_XML 41 /* application/xml */ +#define COAP_MEDIATYPE_APPLICATION_OCTET_STREAM 42 /* application/octet-stream */ +#define COAP_MEDIATYPE_APPLICATION_RDF_XML 43 /* application/rdf+xml */ +#define COAP_MEDIATYPE_APPLICATION_EXI 47 /* application/exi */ +#define COAP_MEDIATYPE_APPLICATION_JSON 50 /* application/json */ +#define COAP_MEDIATYPE_APPLICATION_CBOR 60 /* application/cbor */ +#define COAP_MEDIATYPE_APPLICATION_CWT 61 /* application/cwt, RFC 8392 */ + +/* Content formats from RFC 8152 */ +#define COAP_MEDIATYPE_APPLICATION_COSE_SIGN 98 /* application/cose; cose-type="cose-sign" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_SIGN1 18 /* application/cose; cose-type="cose-sign1" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_ENCRYPT 96 /* application/cose; cose-type="cose-encrypt" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_ENCRYPT0 16 /* application/cose; cose-type="cose-encrypt0" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_MAC 97 /* application/cose; cose-type="cose-mac" */ +#define COAP_MEDIATYPE_APPLICATION_COSE_MAC0 17 /* application/cose; cose-type="cose-mac0" */ + +#define COAP_MEDIATYPE_APPLICATION_COSE_KEY 101 /* application/cose-key */ +#define COAP_MEDIATYPE_APPLICATION_COSE_KEY_SET 102 /* application/cose-key-set */ + +/* Content formats from RFC 8428 */ +#define COAP_MEDIATYPE_APPLICATION_SENML_JSON 110 /* application/senml+json */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_JSON 111 /* application/sensml+json */ +#define COAP_MEDIATYPE_APPLICATION_SENML_CBOR 112 /* application/senml+cbor */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_CBOR 113 /* application/sensml+cbor */ +#define COAP_MEDIATYPE_APPLICATION_SENML_EXI 114 /* application/senml-exi */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_EXI 115 /* application/sensml-exi */ +#define COAP_MEDIATYPE_APPLICATION_SENML_XML 310 /* application/senml+xml */ +#define COAP_MEDIATYPE_APPLICATION_SENSML_XML 311 /* application/sensml+xml */ + +/* Content formats from RFC 8782 */ +#define COAP_MEDIATYPE_APPLICATION_DOTS_CBOR 271 /* application/dots+cbor */ + +/* Note that identifiers for registered media types are in the range 0-65535. We + * use an unallocated type here and hope for the best. */ +#define COAP_MEDIATYPE_ANY 0xff /* any media type */ + +/** + * coap_mid_t is used to store the CoAP Message ID of a CoAP PDU. + * Valid message ids are 0 to 2^16. Negative values are error codes. + */ +typedef int coap_mid_t; + +/** Indicates an invalid message id. */ +#define COAP_INVALID_MID -1 + +/** + * Indicates an invalid message id. + * @deprecated Use COAP_INVALID_MID instead. + */ +#define COAP_INVALID_TID COAP_INVALID_MID + +/** + * @deprecated Use coap_optlist_t instead. + * + * Structures for more convenient handling of options. (To be used with ordered + * coap_list_t.) The option's data will be added to the end of the coap_option + * structure (see macro COAP_OPTION_DATA). + */ +COAP_DEPRECATED typedef struct { + uint16_t key; /* the option key (no delta coding) */ + unsigned int length; +} coap_option; + +#define COAP_OPTION_KEY(option) (option).key +#define COAP_OPTION_LENGTH(option) (option).length +#define COAP_OPTION_DATA(option) ((unsigned char *)&(option) + sizeof(coap_option)) + +#ifdef WITH_LWIP +/** + * Creates a CoAP PDU from an lwIP @p pbuf, whose reference is passed on to this + * function. + * + * The pbuf is checked for being contiguous, and for having only one reference. + * The reference is stored in the PDU and will be freed when the PDU is freed. + * + * (For now, these are fatal errors; in future, a new pbuf might be allocated, + * the data copied and the passed pbuf freed). + * + * This behaves like coap_pdu_init(0, 0, 0, pbuf->tot_len), and afterwards + * copying the contents of the pbuf to the pdu. + * + * @return A pointer to the new PDU object or @c NULL on error. + */ +coap_pdu_t * coap_pdu_from_pbuf(struct pbuf *pbuf); +#endif + +/** +* CoAP protocol types +*/ +typedef enum coap_proto_t { + COAP_PROTO_NONE = 0, + COAP_PROTO_UDP, + COAP_PROTO_DTLS, + COAP_PROTO_TCP, + COAP_PROTO_TLS, +} coap_proto_t; + +/** + * Set of codes available for a PDU. + */ +typedef enum coap_pdu_code_t { + COAP_EMPTY_CODE = 0, + + COAP_REQUEST_CODE_GET = COAP_REQUEST_GET, + COAP_REQUEST_CODE_POST = COAP_REQUEST_POST, + COAP_REQUEST_CODE_PUT = COAP_REQUEST_PUT, + COAP_REQUEST_CODE_DELETE = COAP_REQUEST_DELETE, + COAP_REQUEST_CODE_FETCH = COAP_REQUEST_FETCH, + COAP_REQUEST_CODE_PATCH = COAP_REQUEST_PATCH, + COAP_REQUEST_CODE_IPATCH = COAP_REQUEST_IPATCH, + + COAP_RESPONSE_CODE_OK = COAP_RESPONSE_CODE(200), + COAP_RESPONSE_CODE_CREATED = COAP_RESPONSE_CODE(201), + COAP_RESPONSE_CODE_DELETED = COAP_RESPONSE_CODE(202), + COAP_RESPONSE_CODE_VALID = COAP_RESPONSE_CODE(203), + COAP_RESPONSE_CODE_CHANGED = COAP_RESPONSE_CODE(204), + COAP_RESPONSE_CODE_CONTENT = COAP_RESPONSE_CODE(205), + COAP_RESPONSE_CODE_CONTINUE = COAP_RESPONSE_CODE(231), + COAP_RESPONSE_CODE_BAD_REQUEST = COAP_RESPONSE_CODE(400), + COAP_RESPONSE_CODE_UNAUTHORIZED = COAP_RESPONSE_CODE(401), + COAP_RESPONSE_CODE_BAD_OPTION = COAP_RESPONSE_CODE(402), + COAP_RESPONSE_CODE_FORBIDDEN = COAP_RESPONSE_CODE(403), + COAP_RESPONSE_CODE_NOT_FOUND = COAP_RESPONSE_CODE(404), + COAP_RESPONSE_CODE_NOT_ALLOWED = COAP_RESPONSE_CODE(405), + COAP_RESPONSE_CODE_NOT_ACCEPTABLE = COAP_RESPONSE_CODE(406), + COAP_RESPONSE_CODE_INCOMPLETE = COAP_RESPONSE_CODE(408), + COAP_RESPONSE_CODE_CONFLICT = COAP_RESPONSE_CODE(409), + COAP_RESPONSE_CODE_PRECONDITION_FAILED = COAP_RESPONSE_CODE(412), + COAP_RESPONSE_CODE_REQUEST_TOO_LARGE = COAP_RESPONSE_CODE(413), + COAP_RESPONSE_CODE_UNSUPPORTED_CONTENT_FORMAT = COAP_RESPONSE_CODE(415), + COAP_RESPONSE_CODE_UNPROCESSABLE = COAP_RESPONSE_CODE(422), + COAP_RESPONSE_CODE_TOO_MANY_REQUESTS = COAP_RESPONSE_CODE(429), + COAP_RESPONSE_CODE_INTERNAL_ERROR = COAP_RESPONSE_CODE(500), + COAP_RESPONSE_CODE_NOT_IMPLEMENTED = COAP_RESPONSE_CODE(501), + COAP_RESPONSE_CODE_BAD_GATEWAY = COAP_RESPONSE_CODE(502), + COAP_RESPONSE_CODE_SERVICE_UNAVAILABLE = COAP_RESPONSE_CODE(503), + COAP_RESPONSE_CODE_GATEWAY_TIMEOUT = COAP_RESPONSE_CODE(504), + COAP_RESPONSE_CODE_PROXYING_NOT_SUPPORTED = COAP_RESPONSE_CODE(505), + COAP_RESPONSE_CODE_HOP_LIMIT_REACHED = COAP_RESPONSE_CODE(508), + + COAP_SIGNALING_CODE_CSM = COAP_SIGNALING_CSM, + COAP_SIGNALING_CODE_PING = COAP_SIGNALING_PING, + COAP_SIGNALING_CODE_PONG = COAP_SIGNALING_PONG, + COAP_SIGNALING_CODE_RELEASE = COAP_SIGNALING_RELEASE, + COAP_SIGNALING_CODE_ABORT = COAP_SIGNALING_ABORT +} coap_pdu_code_t; + +/** + * Creates a new CoAP PDU with at least enough storage space for the given + * @p size maximum message size. The function returns a pointer to the + * node coap_pdu_t object on success, or @c NULL on error. The storage allocated + * for the result must be released with coap_delete_pdu() if coap_send() + * is not called. + * + * @param type The type of the PDU (one of COAP_MESSAGE_CON, COAP_MESSAGE_NON, + * COAP_MESSAGE_ACK, COAP_MESSAGE_RST). + * @param code The message code of the PDU. + * @param mid The message id to set or 0 if unknown / not applicable. + * @param size The maximum allowed number of byte for the message. + * @return A pointer to the new PDU object or @c NULL on error. + */ +coap_pdu_t *coap_pdu_init(coap_pdu_type_t type, coap_pdu_code_t code, + coap_mid_t mid, size_t size); + +/** + * Creates a new CoAP PDU. + * + * @param type The type of the PDU (one of COAP_MESSAGE_CON, COAP_MESSAGE_NON, + * COAP_MESSAGE_ACK, COAP_MESSAGE_RST). + * @param code The message code of the PDU. + * @param session The session that will be using this PDU + * + * @return The skeletal PDU or @c NULL if failure. + */ +coap_pdu_t *coap_new_pdu(coap_pdu_type_t type, coap_pdu_code_t code, + coap_session_t *session); + +/** + * Dispose of an CoAP PDU and frees associated storage. + * Not that in general you should not call this function directly. + * When a PDU is sent with coap_send(), coap_delete_pdu() will be called + * automatically for you. + * + * @param pdu The PDU for free off. + */ +void coap_delete_pdu(coap_pdu_t *pdu); + +/** + * Duplicate an existing PDU. Specific options can be ignored and not copied + * across. The PDU data payload is not copied across. + * + * @param old_pdu The PDU to duplicate + * @param session The session that will be using this PDU. + * @param token_length The length of the token to use in this duplicated PDU. + * @param token The token to use in this duplicated PDU. + * @param drop_options A list of options not to copy into the duplicated PDU. + * If @c NULL, then all options are copied across. + * + * @return The duplicated PDU or @c NULL if failure. + */ +coap_pdu_t * +coap_pdu_duplicate(const coap_pdu_t *old_pdu, + coap_session_t *session, + size_t token_length, + const uint8_t *token, + coap_opt_filter_t *drop_options); + +/** + * Adds token of length @p len to @p pdu. + * Adding the token destroys any following contents of the pdu. Hence options + * and data must be added after coap_add_token() has been called. In @p pdu, + * length is set to @p len + @c 4, and max_delta is set to @c 0. This function + * returns @c 0 on error or a value greater than zero on success. + * + * @param pdu The PDU where the token is to be added. + * @param len The length of the new token. + * @param data The token to add. + * + * @return A value greater than zero on success, or @c 0 on error. + */ +int coap_add_token(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** + * Adds option of given number to pdu that is passed as first + * parameter. + * coap_add_option() destroys the PDU's data, so coap_add_data() must be called + * after all options have been added. As coap_add_token() destroys the options + * following the token, the token must be added before coap_add_option() is + * called. This function returns the number of bytes written or @c 0 on error. + * + * Note: Where possible, the option data needs to be stripped of leading zeros + * (big endian) to reduce the amount of data needed in the PDU, as well as in + * some cases the maximum data size of an opton can be exceeded if not stripped + * and hence be illegal. This is done by using coap_encode_var_safe() or + * coap_encode_var_safe8(). + * + * @param pdu The PDU where the option is to be added. + * @param number The number of the new option. + * @param len The length of the new option. + * @param data The data of the new option. + * + * @return The overall length of the option or @c 0 on failure. + */ +size_t coap_add_option(coap_pdu_t *pdu, + coap_option_num_t number, + size_t len, + const uint8_t *data); + +/** + * Adds given data to the pdu that is passed as first parameter. Note that the + * PDU's data is destroyed by coap_add_option(). coap_add_data() must be called + * only once per PDU, otherwise the result is undefined. + * + * @param pdu The PDU where the data is to be added. + * @param len The length of the data. + * @param data The data to add. + * + * @return @c 1 if success, else @c 0 if failure. + */ +int coap_add_data(coap_pdu_t *pdu, + size_t len, + const uint8_t *data); + +/** + * Adds given data to the pdu that is passed as first parameter but does not + * copy it. Note that the PDU's data is destroyed by coap_add_option(). + * coap_add_data() must be have been called once for this PDU, otherwise the + * result is undefined. + * The actual data must be copied at the returned location. + * + * @param pdu The PDU where the data is to be added. + * @param len The length of the data. + * + * @return Where to copy the data of len to, or @c NULL is error. + */ +uint8_t *coap_add_data_after(coap_pdu_t *pdu, size_t len); + +/** + * Retrieves the length and data pointer of specified PDU. Returns 0 on error or + * 1 if *len and *data have correct values. Note that these values are destroyed + * with the pdu. + * + * @param pdu The specified PDU. + * @param len Returns the length of the current data + * @param data Returns the ptr to the current data + * + * @return @c 1 if len and data are correctly filled in, else + * @c 0 if there is no data. + */ +int coap_get_data(const coap_pdu_t *pdu, + size_t *len, + const uint8_t **data); + +/** + * Retrieves the data from a PDU, with support for large bodies of data that + * spans multiple PDUs. + * + * Note: The data pointed to on return is destroyed when the PDU is destroyed. + * + * @param pdu The specified PDU. + * @param len Returns the length of the current data + * @param data Returns the ptr to the current data + * @param offset Returns the offset of the current data from the start of the + * body comprising of many blocks (RFC7959) + * @param total Returns the total size of the body. + * If offset + length < total, then there is more data to follow. + * + * @return @c 1 if len, data, offset and total are correctly filled in, else + * @c 0 if there is no data. + */ +int coap_get_data_large(const coap_pdu_t *pdu, + size_t *len, + const uint8_t **data, + size_t *offset, + size_t *total); + +/** + * Gets the PDU code associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The PDU code. + */ +coap_pdu_code_t coap_pdu_get_code(const coap_pdu_t *pdu); + +/** + * Sets the PDU code in the @p pdu. + * + * @param pdu The PDU object. + * @param code The code to set in the PDU. + */ +void coap_pdu_set_code(coap_pdu_t *pdu, coap_pdu_code_t code); + +/** + * Gets the PDU type associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The PDU type. + */ +coap_pdu_type_t coap_pdu_get_type(const coap_pdu_t *pdu); + +/** + * Sets the PDU type in the @p pdu. + * + * @param pdu The PDU object. + * @param type The type to set for the PDU. + */ +void coap_pdu_set_type(coap_pdu_t *pdu, coap_pdu_type_t type); + +/** + * Gets the token associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The token information. + */ +coap_bin_const_t coap_pdu_get_token(const coap_pdu_t *pdu); + +/** + * Gets the message id associated with @p pdu. + * + * @param pdu The PDU object. + * + * @return The message id. + */ +coap_mid_t coap_pdu_get_mid(const coap_pdu_t *pdu); + +/** + * Sets the message id in the @p pdu. + * + * @param pdu The PDU object. + * @param mid The message id value to set in the PDU. + * + */ +void coap_pdu_set_mid(coap_pdu_t *pdu, coap_mid_t mid); + +/** @} */ + +#endif /* COAP_PDU_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/resource.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/resource.h new file mode 100644 index 00000000000..2cd9aea48fa --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/resource.h @@ -0,0 +1,378 @@ +/* + * resource.h -- generic resource handling + * + * Copyright (C) 2010,2011,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file resource.h + * @brief Generic resource handling + */ + +#ifndef COAP_RESOURCE_H_ +#define COAP_RESOURCE_H_ + +#ifndef COAP_RESOURCE_CHECK_TIME +/** The interval in seconds to check if resources have changed. */ +#define COAP_RESOURCE_CHECK_TIME 2 +#endif /* COAP_RESOURCE_CHECK_TIME */ + +#include "async.h" +#include "block.h" +#include "str.h" +#include "pdu.h" +#include "net.h" +#include "subscribe.h" + +/** + * @defgroup coap_resource Resource Configuraton + * API functions for setting up resources + * @{ + */ + +/** + * Definition of message handler function + */ +typedef void (*coap_method_handler_t) + (coap_resource_t *, + coap_session_t *, + const coap_pdu_t * /* request */, + const coap_string_t * /* query string */, + coap_pdu_t * /* response */); + +#define COAP_ATTR_FLAGS_RELEASE_NAME 0x1 +#define COAP_ATTR_FLAGS_RELEASE_VALUE 0x2 + +/** The URI passed to coap_resource_init() is free'd by coap_delete_resource(). */ +#define COAP_RESOURCE_FLAGS_RELEASE_URI 0x1 + +/** + * Notifications will be sent non-confirmable by default. RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + * Libcoap will always send every fifth packet as confirmable. + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_NON 0x0 + +/** + * Notifications will be sent confirmable. RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_CON 0x2 + +/** + * Notifications will always be sent non-confirmable. This is in + * violation of RFC 7641 Section 4.5 + * https://tools.ietf.org/html/rfc7641#section-4.5 + * but required by the DOTS signal channel protocol which needs to operate in + * lossy DDoS attack environments. + * https://tools.ietf.org/html/rfc8782#section-4.4.2.1 + */ +#define COAP_RESOURCE_FLAGS_NOTIFY_NON_ALWAYS 0x4 + +/** + * Creates a new resource object and initializes the link field to the string + * @p uri_path. This function returns the new coap_resource_t object. + * + * If the string is going to be freed off by coap_delete_resource() when + * COAP_RESOURCE_FLAGS_RELEASE_URI is set in @p flags, then either the 's' + * variable of coap_str_const_t has to point to constant text, or point to data + * within the allocated coap_str_const_t parameter. + * + * @param uri_path The string URI path of the new resource. + * @param flags Flags for memory management (in particular release of + * memory). Possible values:@n + * + * COAP_RESOURCE_FLAGS_RELEASE_URI + * If this flag is set, the URI passed to + * coap_resource_init() is free'd by + * coap_delete_resource()@n + * + * COAP_RESOURCE_FLAGS_NOTIFY_CON + * If this flag is set, coap-observe notifications + * will be sent confirmable by default.@n + * + * COAP_RESOURCE_FLAGS_NOTIFY_NON (default) + * If this flag is set, coap-observe notifications + * will be sent non-confirmable by default.@n + * + * If flags is set to 0 then the + * COAP_RESOURCE_FLAGS_NOTIFY_NON is considered. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_init(coap_str_const_t *uri_path, + int flags); + + +/** + * Creates a new resource object for the unknown resource handler with support + * for PUT. + * + * In the same way that additional handlers can be added to the resource + * created by coap_resource_init() by using coap_register_handler(), POST, + * GET, DELETE etc. handlers can be added to this resource. It is the + * responsibility of the application to manage the unknown resources by either + * creating new resources with coap_resource_init() (which should have a + * DELETE handler specified for the resource removal) or by maintaining an + * active resource list. + * + * Note: There can only be one unknown resource handler per context - attaching + * a new one overrides the previous definition. + * + * Note: It is not possible to observe the unknown resource with a GET request + * - a separate resource needs to be reated by the PUT (or POST) handler, + * and make that resource observable. + * + * This function returns the new coap_resource_t object. + * + * @param put_handler The PUT handler to register with @p resource for + * unknown Uri-Path. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_unknown_init(coap_method_handler_t put_handler); + +/** + * Creates a new resource object for handling proxy URIs. + * This function returns the new coap_resource_t object. + * + * Note: There can only be one proxy resource handler per context - attaching + * a new one overrides the previous definition. + * + * @param handler The PUT/POST/GET etc. handler that handles all request types. + * @param host_name_count The number of provided host_name_list entries. A + * minimum of 1 must be provided. + * @param host_name_list Array of depth host_name_count names that this proxy + * is known by. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_resource_t *coap_resource_proxy_uri_init(coap_method_handler_t handler, + size_t host_name_count, const char *host_name_list[]); + +/** + * Returns the resource identified by the unique string @p uri_path. If no + * resource was found, this function returns @c NULL. + * + * @param context The context to look for this resource. + * @param uri_path The unique string uri of the resource. + * + * @return A pointer to the resource or @c NULL if not found. + */ +coap_resource_t *coap_get_resource_from_uri_path(coap_context_t *context, + coap_str_const_t *uri_path); + +/** + * Get the uri_path from a @p resource. + * + * @param resource The CoAP resource to check. + * + * @return The uri_path if it exists or @c NULL otherwise. + */ +coap_str_const_t* coap_resource_get_uri_path(coap_resource_t *resource); + +/** + * Sets the notification message type of resource @p resource to given + * @p mode + + * @param resource The resource to update. + * @param mode Must be one of @c COAP_RESOURCE_FLAGS_NOTIFY_NON + * or @c COAP_RESOURCE_FLAGS_NOTIFY_CON. + */ +void coap_resource_set_mode(coap_resource_t *resource, int mode); + +/** + * Sets the user_data. The user_data is exclusively used by the library-user + * and can be used as user defined context in the handler functions. + * + * @param resource Resource to attach the data to + * @param data Data to attach to the user_data field. This pointer is + * only used for storage, the data remains under user control + */ +void coap_resource_set_userdata(coap_resource_t *resource, void *data); + +/** + * Gets the user_data. The user_data is exclusively used by the library-user + * and can be used as context in the handler functions. + * + * @param resource Resource to retrieve the user_data from + * + * @return The user_data pointer + */ +void *coap_resource_get_userdata(coap_resource_t *resource); + +/** + * Definition of release resource user_data callback function + */ +typedef void (*coap_resource_release_userdata_handler_t)(void *user_data); + +/** + * Defines the context wide callback to use to when the resource is deleted + * to release the data held in the resource's user_data. + * + * @param context The context to associate the release callback with + * @param callback The callback to invoke when the resource is deleted or NULL + * + */ +void coap_resource_release_userdata_handler(coap_context_t *context, + coap_resource_release_userdata_handler_t callback); + +/** + * Registers the given @p resource for @p context. The resource must have been + * created by coap_resource_init() or coap_resource_unknown_init(), the + * storage allocated for the resource will be released by coap_delete_resource(). + * + * @param context The context to use. + * @param resource The resource to store. + */ +void coap_add_resource(coap_context_t *context, coap_resource_t *resource); + +/** + * Deletes a resource identified by @p resource. The storage allocated for that + * resource is freed, and removed from the context. + * + * @param context The context where the resources are stored. + * @param resource The resource to delete. + * + * @return @c 1 if the resource was found (and destroyed), + * @c 0 otherwise. + */ +int coap_delete_resource(coap_context_t *context, coap_resource_t *resource); + +/** + * Registers the specified @p handler as message handler for the request type @p + * method + * + * @param resource The resource for which the handler shall be registered. + * @param method The CoAP request method to handle. + * @param handler The handler to register with @p resource. + */ +void coap_register_handler(coap_resource_t *resource, + coap_request_t method, + coap_method_handler_t handler); + +/** + * Registers a new attribute with the given @p resource. As the + * attribute's coap_str_const_ fields will point to @p name and @p value the + * caller must ensure that these pointers are valid during the + * attribute's lifetime. + + * If the @p name and/or @p value string is going to be freed off at attribute + * removal time by the setting of COAP_ATTR_FLAGS_RELEASE_NAME or + * COAP_ATTR_FLAGS_RELEASE_VALUE in @p flags, then either the 's' + * variable of coap_str_const_t has to point to constant text, or point to data + * within the allocated coap_str_const_t parameter. + * + * @param resource The resource to register the attribute with. + * @param name The attribute's name as a string. + * @param value The attribute's value as a string or @c NULL if none. + * @param flags Flags for memory management (in particular release of + * memory). Possible values:@n + * + * COAP_ATTR_FLAGS_RELEASE_NAME + * If this flag is set, the name passed to + * coap_add_attr_release() is free'd + * when the attribute is deleted@n + * + * COAP_ATTR_FLAGS_RELEASE_VALUE + * If this flag is set, the value passed to + * coap_add_attr_release() is free'd + * when the attribute is deleted@n + * + * @return A pointer to the new attribute or @c NULL on error. + */ +coap_attr_t *coap_add_attr(coap_resource_t *resource, + coap_str_const_t *name, + coap_str_const_t *value, + int flags); + +/** + * Returns @p resource's coap_attr_t object with given @p name if found, @c NULL + * otherwise. + * + * @param resource The resource to search for attribute @p name. + * @param name Name of the requested attribute as a string. + * @return The first attribute with specified @p name or @c NULL if none + * was found. + */ +coap_attr_t *coap_find_attr(coap_resource_t *resource, + coap_str_const_t *name); + +/** + * Returns @p attribute's value. + * + * @param attribute Pointer to attribute. + * + * @return Attribute's value or @c NULL. + */ +coap_str_const_t *coap_attr_get_value(coap_attr_t *attribute); + +/** + * Status word to encode the result of conditional print or copy operations such + * as coap_print_link(). The lower 28 bits of coap_print_status_t are used to + * encode the number of characters that has actually been printed, bits 28 to 31 + * encode the status. When COAP_PRINT_STATUS_ERROR is set, an error occurred + * during output. In this case, the other bits are undefined. + * COAP_PRINT_STATUS_TRUNC indicates that the output is truncated, i.e. the + * printing would have exceeded the current buffer. + */ +typedef unsigned int coap_print_status_t; + +#define COAP_PRINT_STATUS_MASK 0xF0000000u +#define COAP_PRINT_OUTPUT_LENGTH(v) ((v) & ~COAP_PRINT_STATUS_MASK) +#define COAP_PRINT_STATUS_ERROR 0x80000000u +#define COAP_PRINT_STATUS_TRUNC 0x40000000u + +/** + * Writes a description of this resource in link-format to given text buffer. @p + * len must be initialized to the maximum length of @p buf and will be set to + * the number of characters actually written if successful. This function + * returns @c 1 on success or @c 0 on error. + * + * @param resource The resource to describe. + * @param buf The output buffer to write the description to. + * @param len Must be initialized to the length of @p buf and + * will be set to the length of the printed link description. + * @param offset The offset within the resource description where to + * start writing into @p buf. This is useful for dealing + * with the Block2 option. @p offset is updated during + * output as it is consumed. + * + * @return If COAP_PRINT_STATUS_ERROR is set, an error occured. Otherwise, + * the lower 28 bits will indicate the number of characters that + * have actually been output into @p buffer. The flag + * COAP_PRINT_STATUS_TRUNC indicates that the output has been + * truncated. + */ +coap_print_status_t coap_print_link(const coap_resource_t *resource, + unsigned char *buf, + size_t *len, + size_t *offset); + +/** @} */ + +/** + * Returns the resource identified by the unique string @p uri_path. If no + * resource was found, this function returns @c NULL. + * + * @param context The context to look for this resource. + * @param uri_path The unique string uri of the resource. + * + * @return A pointer to the resource or @c NULL if not found. + */ +coap_resource_t *coap_get_resource_from_uri_path(coap_context_t *context, + coap_str_const_t *uri_path); + +/** + * @deprecated use coap_resource_notify_observers() instead. + */ +COAP_DEPRECATED int +coap_resource_set_dirty(coap_resource_t *r, + const coap_string_t *query); + +#endif /* COAP_RESOURCE_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/str.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/str.h new file mode 100644 index 00000000000..dbf53d0c475 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/str.h @@ -0,0 +1,204 @@ +/* + * str.h -- strings to be used in the CoAP library + * + * Copyright (C) 2010-2011 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_STR_H_ +#define COAP_STR_H_ + +#include + + +/** + * @defgroup string String handling support + * API functions for handling strings and binary data + * @{ + */ + +/* + * Note: string and binary use equivalent objects. + * string is likely to contain readable textual information, binary will not. + */ + +/** + * CoAP string data definition + */ +typedef struct coap_string_t { + size_t length; /**< length of string */ + uint8_t *s; /**< string data */ +} coap_string_t; + +/** + * CoAP string data definition with const data + */ +typedef struct coap_str_const_t { + size_t length; /**< length of string */ + const uint8_t *s; /**< read-only string data */ +} coap_str_const_t; + +#define COAP_SET_STR(st,l,v) { (st)->length = (l), (st)->s = (v); } + +/** + * CoAP binary data definition + */ +typedef struct coap_binary_t { + size_t length; /**< length of binary data */ + uint8_t *s; /**< binary data */ +} coap_binary_t; + +/** + * CoAP binary data definition with const data + */ +typedef struct coap_bin_const_t { + size_t length; /**< length of binary data */ + const uint8_t *s; /**< read-only binary data */ +} coap_bin_const_t; + +/** + * Returns a new string object with at least size+1 bytes storage allocated. + * It is the responsibility of the caller to fill in all the appropriate + * information. + * The string must be released using coap_delete_string(). + * + * @param size The size to allocate for the string data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_string_t *coap_new_string(size_t size); + +/** + * Deletes the given string and releases any memory allocated. + * + * @param string The string to free off. + */ +void coap_delete_string(coap_string_t *string); + +/** + * Returns a new const string object with at least size+1 bytes storage + * allocated, and the provided data copied into the string object. + * The string must be released using coap_delete_str_const(). + * + * @param data The data to put in the new string object. + * @param size The size to allocate for the binary string data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_str_const_t *coap_new_str_const(const uint8_t *data, size_t size); + +/** + * Deletes the given const string and releases any memory allocated. + * + * @param string The string to free off. + */ +void coap_delete_str_const(coap_str_const_t *string); + +/** + * Returns a new binary object with at least size bytes storage allocated. + * It is the responsibility of the caller to fill in all the appropriate + * information. + * The coap_binary_t object must be released using coap_delete_binary(). + * + * @param size The size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_binary_t *coap_new_binary(size_t size); + +/** + * Deletes the given coap_binary_t object and releases any memory allocated. + * + * @param binary The coap_binary_t object to free off. + */ +void coap_delete_binary(coap_binary_t *binary); + +/** + * Resizes the given coap_binary_t object. + * It is the responsibility of the caller to fill in all the appropriate + * additional information. + * + * Note: If there is an error, @p binary will separately need to be released by + * coap_delete_binary(). + * + * @param binary The coap_binary_t object to resize. + * @param new_size The new size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_binary_t *coap_resize_binary(coap_binary_t *binary, size_t new_size); + +/** + * Take the specified byte array (text) and create a coap_bin_const_t * + * Returns a new const binary object with at least size bytes storage + * allocated, and the provided data copied into the binary object. + * The binary data must be released using coap_delete_bin_const(). + * + * @param data The data to put in the new string object. + * @param size The size to allocate for the binary data. + * + * @return A pointer to the new object or @c NULL on error. + */ +coap_bin_const_t *coap_new_bin_const(const uint8_t *data, size_t size); + +/** + * Deletes the given const binary data and releases any memory allocated. + * + * @param binary The binary data to free off. + */ +void coap_delete_bin_const(coap_bin_const_t *binary); + +#ifndef COAP_MAX_STR_CONST_FUNC +#define COAP_MAX_STR_CONST_FUNC 2 +#endif /* COAP_MAX_STR_CONST_FUNC */ + +/** + * Take the specified byte array (text) and create a coap_str_const_t * + * + * Note: the array is 2 deep as there are up to two callings of + * coap_make_str_const in a function call. e.g. coap_add_attr(). + * Caution: If there are local variable assignments, these will cycle around + * the var[COAP_MAX_STR_CONST_FUNC] set. No current examples do this. + * + * @param string The const string to convert to a coap_str_const_t * + * + * @return A pointer to one of two static variables containing the + * coap_str_const_t * result + */ +coap_str_const_t *coap_make_str_const(const char *string); + +/** + * Compares the two strings for equality + * + * @param string1 The first string. + * @param string2 The second string. + * + * @return @c 1 if the strings are equal + * @c 0 otherwise. + */ +#define coap_string_equal(string1,string2) \ + ((string1)->length == (string2)->length && ((string1)->length == 0 || \ + ((string1)->s && (string2)->s && \ + memcmp((string1)->s, (string2)->s, (string1)->length) == 0))) + +/** + * Compares the two binary data for equality + * + * @param binary1 The first binary data. + * @param binary2 The second binary data. + * + * @return @c 1 if the binary data is equal + * @c 0 otherwise. + */ +#define coap_binary_equal(binary1,binary2) \ + ((binary1)->length == (binary2)->length && ((binary1)->length == 0 || \ + ((binary1)->s && (binary2)->s && \ + memcmp((binary1)->s, (binary2)->s, (binary1)->length) == 0))) + +/** @} */ + +#endif /* COAP_STR_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/subscribe.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/subscribe.h new file mode 100644 index 00000000000..c3aabc2db04 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/subscribe.h @@ -0,0 +1,68 @@ +/* + * subscribe.h -- subscription handling for CoAP + * see RFC7641 + * + * Copyright (C) 2010-2012,2014-2021 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +/** + * @file subscribe.h + * @brief Defines the application visible subscribe information + */ + +#ifndef COAP_SUBSCRIBE_H_ +#define COAP_SUBSCRIBE_H_ + +/** + * @defgroup observe Resource Observation + * API functions for interfacing with the observe handling (RFC7641) + * @{ + */ + +/** + * The value COAP_OBSERVE_ESTABLISH in a GET/FETCH request option + * COAP_OPTION_OBSERVE indicates a new observe relationship for (sender + * address, token) is requested. + */ +#define COAP_OBSERVE_ESTABLISH 0 + +/** + * The value COAP_OBSERVE_CANCEL in a GET/FETCH request option + * COAP_OPTION_OBSERVE indicates that the observe relationship for (sender + * address, token) must be cancelled. + */ +#define COAP_OBSERVE_CANCEL 1 + +/** + * Set whether a @p resource is observable. If the resource is observable + * and the client has set the COAP_OPTION_OBSERVE in a request packet, then + * whenever the state of the resource changes (a call to + * coap_resource_trigger_observe()), an Observer response will get sent. + * + * @param resource The CoAP resource to use. + * @param mode @c 1 if Observable is to be set, @c 0 otherwise. + * + */ +void coap_resource_set_get_observable(coap_resource_t *resource, int mode); + +/** + * Initiate the sending of an Observe packet for all observers of @p resource, + * optionally matching @p query if not NULL + * + * @param resource The CoAP resource to use. + * @param query The Query to match against or NULL + * + * @return @c 1 if the Observe has been triggered, @c 0 otherwise. + */ +int +coap_resource_notify_observers(coap_resource_t *resource, + const coap_string_t *query); + +/** @} */ + +#endif /* COAP_SUBSCRIBE_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uri.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uri.h new file mode 100644 index 00000000000..8084483b500 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uri.h @@ -0,0 +1,176 @@ +/* + * uri.h -- helper functions for URI treatment + * + * Copyright (C) 2010-2020 Olaf Bergmann + * + * SPDX-License-Identifier: BSD-2-Clause + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_URI_H_ +#define COAP_URI_H_ + +#include + +#include "str.h" + +/** + * The scheme specifiers. Secure schemes have an odd numeric value, + * others are even. + */ +typedef enum coap_uri_scheme_t { + COAP_URI_SCHEME_COAP = 0, + COAP_URI_SCHEME_COAPS, /* 1 */ + COAP_URI_SCHEME_COAP_TCP, /* 2 */ + COAP_URI_SCHEME_COAPS_TCP, /* 3 */ + COAP_URI_SCHEME_HTTP, /* 4 Proxy-Uri only */ + COAP_URI_SCHEME_HTTPS /* 5 Proxy-Uri only */ +} coap_uri_scheme_t; + +/** This mask can be used to check if a parsed URI scheme is secure. */ +#define COAP_URI_SCHEME_SECURE_MASK 0x01 + +/** + * Representation of parsed URI. Components may be filled from a string with + * coap_split_uri() or coap_split_proxy_uri() and can be used as input for + * option-creation functions. + */ +typedef struct { + coap_str_const_t host; /**< host part of the URI */ + uint16_t port; /**< The port in host byte order */ + coap_str_const_t path; /**< Beginning of the first path segment. + Use coap_split_path() to create Uri-Path options */ + coap_str_const_t query; /**< The query part if present */ + + /** The parsed scheme specifier. */ + enum coap_uri_scheme_t scheme; +} coap_uri_t; + +static inline int +coap_uri_scheme_is_secure(const coap_uri_t *uri) { + return uri && ((uri->scheme & COAP_URI_SCHEME_SECURE_MASK) != 0); +} + +/** + * Creates a new coap_uri_t object from the specified URI. Returns the new + * object or NULL on error. The memory allocated by the new coap_uri_t + * must be released using coap_free(). + * + * @param uri The URI path to copy. + * @param length The length of uri. + * + * @return New URI object or NULL on error. + */ +coap_uri_t *coap_new_uri(const uint8_t *uri, unsigned int length); + +/** + * Clones the specified coap_uri_t object. Thie function allocates sufficient + * memory to hold the coap_uri_t structure and its contents. The object must + * be released with coap_free(). */ +coap_uri_t *coap_clone_uri(const coap_uri_t *uri); + +/** + * @defgroup uri_parse URI Parsing Functions + * + * CoAP PDUs contain normalized URIs with their path and query split into + * multiple segments. The functions in this module help splitting strings. + * @{ + */ + +/** + * Parses a given string into URI components. The identified syntactic + * components are stored in the result parameter @p uri. Optional URI + * components that are not specified will be set to { 0, 0 }, except for the + * port which is set to the default port for the protocol. This function + * returns @p 0 if parsing succeeded, a value less than zero otherwise. + * + * @param str_var The string to split up. + * @param len The actual length of @p str_var + * @param uri The coap_uri_t object to store the result. + * + * @return @c 0 on success, or < 0 on error. + * + */ +int coap_split_uri(const uint8_t *str_var, size_t len, coap_uri_t *uri); + +/** + * Parses a given string into URI components. The identified syntactic + * components are stored in the result parameter @p uri. Optional URI + * components that are not specified will be set to { 0, 0 }, except for the + * port which is set to default port for the protocol. This function returns + * @p 0 if parsing succeeded, a value less than zero otherwise. + * Note: This function enforces that the given string is in Proxy-Uri format + * as well as supports different schema such as http. + * + * @param str_var The string to split up. + * @param len The actual length of @p str_var + * @param uri The coap_uri_t object to store the result. + * + * @return @c 0 on success, or < 0 on error. + * + */ +int coap_split_proxy_uri(const uint8_t *str_var, size_t len, coap_uri_t *uri); + +/** + * Splits the given URI path into segments. Each segment is preceded + * by an option pseudo-header with delta-value 0 and the actual length + * of the respective segment after percent-decoding. + * + * @param s The path string to split. + * @param length The actual length of @p s. + * @param buf Result buffer for parsed segments. + * @param buflen Maximum length of @p buf. Will be set to the actual number + * of bytes written into buf on success. + * + * @return The number of segments created or @c -1 on error. + */ +int coap_split_path(const uint8_t *s, + size_t length, + unsigned char *buf, + size_t *buflen); + +/** + * Splits the given URI query into segments. Each segment is preceded + * by an option pseudo-header with delta-value 0 and the actual length + * of the respective query term. + * + * @param s The query string to split. + * @param length The actual length of @p s. + * @param buf Result buffer for parsed segments. + * @param buflen Maximum length of @p buf. Will be set to the actual number + * of bytes written into buf on success. + * + * @return The number of segments created or @c -1 on error. + * + * @bug This function does not reserve additional space for delta > 12. + */ +int coap_split_query(const uint8_t *s, + size_t length, + unsigned char *buf, + size_t *buflen); + +/** + * Extract query string from request PDU according to escape rules in 6.5.8. + * @param request Request PDU. + * @return Reconstructed and escaped query string part or @c NULL if + * no query was contained in @p request. The coap_string_t + * object returned by this function must be released with + * coap_delete_string. + */ +coap_string_t *coap_get_query(const coap_pdu_t *request); + +/** + * Extract uri_path string from request PDU + * @param request Request PDU. + * @return Reconstructed and escaped uri path string part or @c NULL + * if no URI-Path was contained in @p request. The + * coap_string_t object returned by this function must be + * released with coap_delete_string. + */ +coap_string_t *coap_get_uri_path(const coap_pdu_t *request); + +/** @} */ + +#endif /* COAP_URI_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uthash.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uthash.h new file mode 100644 index 00000000000..9a396b6179f --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/uthash.h @@ -0,0 +1,1136 @@ +/* +Copyright (c) 2003-2021, Troy D. Hanson http://troydhanson.github.io/uthash/ +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. + +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 UTHASH_H +#define UTHASH_H + +#define UTHASH_VERSION 2.3.0 + +#include /* memcmp, memset, strlen */ +#include /* ptrdiff_t */ +#include /* exit */ + +#if defined(HASH_DEFINE_OWN_STDINT) && HASH_DEFINE_OWN_STDINT +/* This codepath is provided for backward compatibility, but I plan to remove it. */ +#warning "HASH_DEFINE_OWN_STDINT is deprecated; please use HASH_NO_STDINT instead" +typedef unsigned int uint32_t; +typedef unsigned char uint8_t; +#elif defined(HASH_NO_STDINT) && HASH_NO_STDINT +#else +#include /* uint8_t, uint32_t */ +#endif + +/* These macros use decltype or the earlier __typeof GNU extension. + As decltype is only available in newer compilers (VS2010 or gcc 4.3+ + when compiling c++ source) this code uses whatever method is needed + or, for VS2008 where neither is available, uses casting workarounds. */ +#if !defined(DECLTYPE) && !defined(NO_DECLTYPE) +#if defined(_MSC_VER) /* MS compiler */ +#if _MSC_VER >= 1600 && defined(__cplusplus) /* VS2010 or newer in C++ mode */ +#define DECLTYPE(x) (decltype(x)) +#else /* VS2008 or older (or VS2010 in C mode) */ +#define NO_DECLTYPE +#endif +#elif defined(__BORLANDC__) || defined(__ICCARM__) || defined(__LCC__) || defined(__WATCOMC__) +#define NO_DECLTYPE +#else /* GNU, Sun and other compilers */ +#define DECLTYPE(x) (__typeof(x)) +#endif +#endif + +#ifdef NO_DECLTYPE +#define DECLTYPE(x) +#define DECLTYPE_ASSIGN(dst,src) \ +do { \ + char **_da_dst = (char**)(&(dst)); \ + *_da_dst = (char*)(src); \ +} while (0) +#else +#define DECLTYPE_ASSIGN(dst,src) \ +do { \ + (dst) = DECLTYPE(dst)(src); \ +} while (0) +#endif + +#ifndef uthash_malloc +#define uthash_malloc(sz) malloc(sz) /* malloc fcn */ +#endif +#ifndef uthash_free +#define uthash_free(ptr,sz) free(ptr) /* free fcn */ +#endif +#ifndef uthash_bzero +#define uthash_bzero(a,n) memset(a,'\0',n) +#endif +#ifndef uthash_strlen +#define uthash_strlen(s) strlen(s) +#endif + +#ifndef HASH_FUNCTION +#define HASH_FUNCTION(keyptr,keylen,hashv) HASH_JEN(keyptr, keylen, hashv) +#endif + +#ifndef HASH_KEYCMP +#define HASH_KEYCMP(a,b,n) memcmp(a,b,n) +#endif + +#ifndef uthash_noexpand_fyi +#define uthash_noexpand_fyi(tbl) /* can be defined to log noexpand */ +#endif +#ifndef uthash_expand_fyi +#define uthash_expand_fyi(tbl) /* can be defined to log expands */ +#endif + +#ifndef HASH_NONFATAL_OOM +#define HASH_NONFATAL_OOM 0 +#endif + +#if HASH_NONFATAL_OOM +/* malloc failures can be recovered from */ + +#ifndef uthash_nonfatal_oom +#define uthash_nonfatal_oom(obj) do {} while (0) /* non-fatal OOM error */ +#endif + +#define HASH_RECORD_OOM(oomed) do { (oomed) = 1; } while (0) +#define IF_HASH_NONFATAL_OOM(x) x + +#else +/* malloc failures result in lost memory, hash tables are unusable */ + +#ifndef uthash_fatal +#define uthash_fatal(msg) exit(-1) /* fatal OOM error */ +#endif + +#define HASH_RECORD_OOM(oomed) uthash_fatal("out of memory") +#define IF_HASH_NONFATAL_OOM(x) + +#endif + +/* initial number of buckets */ +#define HASH_INITIAL_NUM_BUCKETS 32U /* initial number of buckets */ +#define HASH_INITIAL_NUM_BUCKETS_LOG2 5U /* lg2 of initial number of buckets */ +#define HASH_BKT_CAPACITY_THRESH 10U /* expand when bucket count reaches */ + +/* calculate the element whose hash handle address is hhp */ +#define ELMT_FROM_HH(tbl,hhp) ((void*)(((char*)(hhp)) - ((tbl)->hho))) +/* calculate the hash handle from element address elp */ +#define HH_FROM_ELMT(tbl,elp) ((UT_hash_handle*)(void*)(((char*)(elp)) + ((tbl)->hho))) + +#define HASH_ROLLBACK_BKT(hh, head, itemptrhh) \ +do { \ + struct UT_hash_handle *_hd_hh_item = (itemptrhh); \ + unsigned _hd_bkt; \ + HASH_TO_BKT(_hd_hh_item->hashv, (head)->hh.tbl->num_buckets, _hd_bkt); \ + (head)->hh.tbl->buckets[_hd_bkt].count++; \ + _hd_hh_item->hh_next = NULL; \ + _hd_hh_item->hh_prev = NULL; \ +} while (0) + +#define HASH_VALUE(keyptr,keylen,hashv) \ +do { \ + HASH_FUNCTION(keyptr, keylen, hashv); \ +} while (0) + +#define HASH_FIND_BYHASHVALUE(hh,head,keyptr,keylen,hashval,out) \ +do { \ + (out) = NULL; \ + if (head) { \ + unsigned _hf_bkt; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _hf_bkt); \ + if (HASH_BLOOM_TEST((head)->hh.tbl, hashval) != 0) { \ + HASH_FIND_IN_BKT((head)->hh.tbl, hh, (head)->hh.tbl->buckets[ _hf_bkt ], keyptr, keylen, hashval, out); \ + } \ + } \ +} while (0) + +#define HASH_FIND(hh,head,keyptr,keylen,out) \ +do { \ + (out) = NULL; \ + if (head) { \ + unsigned _hf_hashv; \ + HASH_VALUE(keyptr, keylen, _hf_hashv); \ + HASH_FIND_BYHASHVALUE(hh, head, keyptr, keylen, _hf_hashv, out); \ + } \ +} while (0) + +#ifdef HASH_BLOOM +#define HASH_BLOOM_BITLEN (1UL << HASH_BLOOM) +#define HASH_BLOOM_BYTELEN (HASH_BLOOM_BITLEN/8UL) + (((HASH_BLOOM_BITLEN%8UL)!=0UL) ? 1UL : 0UL) +#define HASH_BLOOM_MAKE(tbl,oomed) \ +do { \ + (tbl)->bloom_nbits = HASH_BLOOM; \ + (tbl)->bloom_bv = (uint8_t*)uthash_malloc(HASH_BLOOM_BYTELEN); \ + if (!(tbl)->bloom_bv) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero((tbl)->bloom_bv, HASH_BLOOM_BYTELEN); \ + (tbl)->bloom_sig = HASH_BLOOM_SIGNATURE; \ + } \ +} while (0) + +#define HASH_BLOOM_FREE(tbl) \ +do { \ + uthash_free((tbl)->bloom_bv, HASH_BLOOM_BYTELEN); \ +} while (0) + +#define HASH_BLOOM_BITSET(bv,idx) (bv[(idx)/8U] |= (1U << ((idx)%8U))) +#define HASH_BLOOM_BITTEST(bv,idx) (bv[(idx)/8U] & (1U << ((idx)%8U))) + +#define HASH_BLOOM_ADD(tbl,hashv) \ + HASH_BLOOM_BITSET((tbl)->bloom_bv, ((hashv) & (uint32_t)((1UL << (tbl)->bloom_nbits) - 1U))) + +#define HASH_BLOOM_TEST(tbl,hashv) \ + HASH_BLOOM_BITTEST((tbl)->bloom_bv, ((hashv) & (uint32_t)((1UL << (tbl)->bloom_nbits) - 1U))) + +#else +#define HASH_BLOOM_MAKE(tbl,oomed) +#define HASH_BLOOM_FREE(tbl) +#define HASH_BLOOM_ADD(tbl,hashv) +#define HASH_BLOOM_TEST(tbl,hashv) (1) +#define HASH_BLOOM_BYTELEN 0U +#endif + +#define HASH_MAKE_TABLE(hh,head,oomed) \ +do { \ + (head)->hh.tbl = (UT_hash_table*)uthash_malloc(sizeof(UT_hash_table)); \ + if (!(head)->hh.tbl) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head)->hh.tbl->tail = &((head)->hh); \ + (head)->hh.tbl->num_buckets = HASH_INITIAL_NUM_BUCKETS; \ + (head)->hh.tbl->log2_num_buckets = HASH_INITIAL_NUM_BUCKETS_LOG2; \ + (head)->hh.tbl->hho = (char*)(&(head)->hh) - (char*)(head); \ + (head)->hh.tbl->buckets = (UT_hash_bucket*)uthash_malloc( \ + HASH_INITIAL_NUM_BUCKETS * sizeof(struct UT_hash_bucket)); \ + (head)->hh.tbl->signature = HASH_SIGNATURE; \ + if (!(head)->hh.tbl->buckets) { \ + HASH_RECORD_OOM(oomed); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + } else { \ + uthash_bzero((head)->hh.tbl->buckets, \ + HASH_INITIAL_NUM_BUCKETS * sizeof(struct UT_hash_bucket)); \ + HASH_BLOOM_MAKE((head)->hh.tbl, oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (oomed) { \ + uthash_free((head)->hh.tbl->buckets, \ + HASH_INITIAL_NUM_BUCKETS*sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + } \ + ) \ + } \ + } \ +} while (0) + +#define HASH_REPLACE_BYHASHVALUE_INORDER(hh,head,fieldname,keylen_in,hashval,add,replaced,cmpfcn) \ +do { \ + (replaced) = NULL; \ + HASH_FIND_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, replaced); \ + if (replaced) { \ + HASH_DELETE(hh, head, replaced); \ + } \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, &((add)->fieldname), keylen_in, hashval, add, cmpfcn); \ +} while (0) + +#define HASH_REPLACE_BYHASHVALUE(hh,head,fieldname,keylen_in,hashval,add,replaced) \ +do { \ + (replaced) = NULL; \ + HASH_FIND_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, replaced); \ + if (replaced) { \ + HASH_DELETE(hh, head, replaced); \ + } \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, add); \ +} while (0) + +#define HASH_REPLACE(hh,head,fieldname,keylen_in,add,replaced) \ +do { \ + unsigned _hr_hashv; \ + HASH_VALUE(&((add)->fieldname), keylen_in, _hr_hashv); \ + HASH_REPLACE_BYHASHVALUE(hh, head, fieldname, keylen_in, _hr_hashv, add, replaced); \ +} while (0) + +#define HASH_REPLACE_INORDER(hh,head,fieldname,keylen_in,add,replaced,cmpfcn) \ +do { \ + unsigned _hr_hashv; \ + HASH_VALUE(&((add)->fieldname), keylen_in, _hr_hashv); \ + HASH_REPLACE_BYHASHVALUE_INORDER(hh, head, fieldname, keylen_in, _hr_hashv, add, replaced, cmpfcn); \ +} while (0) + +#define HASH_APPEND_LIST(hh, head, add) \ +do { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = ELMT_FROM_HH((head)->hh.tbl, (head)->hh.tbl->tail); \ + (head)->hh.tbl->tail->next = (add); \ + (head)->hh.tbl->tail = &((add)->hh); \ +} while (0) + +#define HASH_AKBI_INNER_LOOP(hh,head,add,cmpfcn) \ +do { \ + do { \ + if (cmpfcn(DECLTYPE(head)(_hs_iter), add) > 0) { \ + break; \ + } \ + } while ((_hs_iter = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->next)); \ +} while (0) + +#ifdef NO_DECLTYPE +#undef HASH_AKBI_INNER_LOOP +#define HASH_AKBI_INNER_LOOP(hh,head,add,cmpfcn) \ +do { \ + char *_hs_saved_head = (char*)(head); \ + do { \ + DECLTYPE_ASSIGN(head, _hs_iter); \ + if (cmpfcn(head, add) > 0) { \ + DECLTYPE_ASSIGN(head, _hs_saved_head); \ + break; \ + } \ + DECLTYPE_ASSIGN(head, _hs_saved_head); \ + } while ((_hs_iter = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->next)); \ +} while (0) +#endif + +#if HASH_NONFATAL_OOM + +#define HASH_ADD_TO_TABLE(hh,head,keyptr,keylen_in,hashval,add,oomed) \ +do { \ + if (!(oomed)) { \ + unsigned _ha_bkt; \ + (head)->hh.tbl->num_items++; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _ha_bkt); \ + HASH_ADD_TO_BKT((head)->hh.tbl->buckets[_ha_bkt], hh, &(add)->hh, oomed); \ + if (oomed) { \ + HASH_ROLLBACK_BKT(hh, head, &(add)->hh); \ + HASH_DELETE_HH(hh, head, &(add)->hh); \ + (add)->hh.tbl = NULL; \ + uthash_nonfatal_oom(add); \ + } else { \ + HASH_BLOOM_ADD((head)->hh.tbl, hashval); \ + HASH_EMIT_KEY(hh, head, keyptr, keylen_in); \ + } \ + } else { \ + (add)->hh.tbl = NULL; \ + uthash_nonfatal_oom(add); \ + } \ +} while (0) + +#else + +#define HASH_ADD_TO_TABLE(hh,head,keyptr,keylen_in,hashval,add,oomed) \ +do { \ + unsigned _ha_bkt; \ + (head)->hh.tbl->num_items++; \ + HASH_TO_BKT(hashval, (head)->hh.tbl->num_buckets, _ha_bkt); \ + HASH_ADD_TO_BKT((head)->hh.tbl->buckets[_ha_bkt], hh, &(add)->hh, oomed); \ + HASH_BLOOM_ADD((head)->hh.tbl, hashval); \ + HASH_EMIT_KEY(hh, head, keyptr, keylen_in); \ +} while (0) + +#endif + + +#define HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh,head,keyptr,keylen_in,hashval,add,cmpfcn) \ +do { \ + IF_HASH_NONFATAL_OOM( int _ha_oomed = 0; ) \ + (add)->hh.hashv = (hashval); \ + (add)->hh.key = (char*) (keyptr); \ + (add)->hh.keylen = (unsigned) (keylen_in); \ + if (!(head)) { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = NULL; \ + HASH_MAKE_TABLE(hh, add, _ha_oomed); \ + IF_HASH_NONFATAL_OOM( if (!_ha_oomed) { ) \ + (head) = (add); \ + IF_HASH_NONFATAL_OOM( } ) \ + } else { \ + void *_hs_iter = (head); \ + (add)->hh.tbl = (head)->hh.tbl; \ + HASH_AKBI_INNER_LOOP(hh, head, add, cmpfcn); \ + if (_hs_iter) { \ + (add)->hh.next = _hs_iter; \ + if (((add)->hh.prev = HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->prev)) { \ + HH_FROM_ELMT((head)->hh.tbl, (add)->hh.prev)->next = (add); \ + } else { \ + (head) = (add); \ + } \ + HH_FROM_ELMT((head)->hh.tbl, _hs_iter)->prev = (add); \ + } else { \ + HASH_APPEND_LIST(hh, head, add); \ + } \ + } \ + HASH_ADD_TO_TABLE(hh, head, keyptr, keylen_in, hashval, add, _ha_oomed); \ + HASH_FSCK(hh, head, "HASH_ADD_KEYPTR_BYHASHVALUE_INORDER"); \ +} while (0) + +#define HASH_ADD_KEYPTR_INORDER(hh,head,keyptr,keylen_in,add,cmpfcn) \ +do { \ + unsigned _hs_hashv; \ + HASH_VALUE(keyptr, keylen_in, _hs_hashv); \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, keyptr, keylen_in, _hs_hashv, add, cmpfcn); \ +} while (0) + +#define HASH_ADD_BYHASHVALUE_INORDER(hh,head,fieldname,keylen_in,hashval,add,cmpfcn) \ + HASH_ADD_KEYPTR_BYHASHVALUE_INORDER(hh, head, &((add)->fieldname), keylen_in, hashval, add, cmpfcn) + +#define HASH_ADD_INORDER(hh,head,fieldname,keylen_in,add,cmpfcn) \ + HASH_ADD_KEYPTR_INORDER(hh, head, &((add)->fieldname), keylen_in, add, cmpfcn) + +#define HASH_ADD_KEYPTR_BYHASHVALUE(hh,head,keyptr,keylen_in,hashval,add) \ +do { \ + IF_HASH_NONFATAL_OOM( int _ha_oomed = 0; ) \ + (add)->hh.hashv = (hashval); \ + (add)->hh.key = (const void*) (keyptr); \ + (add)->hh.keylen = (unsigned) (keylen_in); \ + if (!(head)) { \ + (add)->hh.next = NULL; \ + (add)->hh.prev = NULL; \ + HASH_MAKE_TABLE(hh, add, _ha_oomed); \ + IF_HASH_NONFATAL_OOM( if (!_ha_oomed) { ) \ + (head) = (add); \ + IF_HASH_NONFATAL_OOM( } ) \ + } else { \ + (add)->hh.tbl = (head)->hh.tbl; \ + HASH_APPEND_LIST(hh, head, add); \ + } \ + HASH_ADD_TO_TABLE(hh, head, keyptr, keylen_in, hashval, add, _ha_oomed); \ + HASH_FSCK(hh, head, "HASH_ADD_KEYPTR_BYHASHVALUE"); \ +} while (0) + +#define HASH_ADD_KEYPTR(hh,head,keyptr,keylen_in,add) \ +do { \ + unsigned _ha_hashv; \ + HASH_VALUE(keyptr, keylen_in, _ha_hashv); \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, keyptr, keylen_in, _ha_hashv, add); \ +} while (0) + +#define HASH_ADD_BYHASHVALUE(hh,head,fieldname,keylen_in,hashval,add) \ + HASH_ADD_KEYPTR_BYHASHVALUE(hh, head, &((add)->fieldname), keylen_in, hashval, add) + +#define HASH_ADD(hh,head,fieldname,keylen_in,add) \ + HASH_ADD_KEYPTR(hh, head, &((add)->fieldname), keylen_in, add) + +#define HASH_TO_BKT(hashv,num_bkts,bkt) \ +do { \ + bkt = ((hashv) & ((num_bkts) - 1U)); \ +} while (0) + +/* delete "delptr" from the hash table. + * "the usual" patch-up process for the app-order doubly-linked-list. + * The use of _hd_hh_del below deserves special explanation. + * These used to be expressed using (delptr) but that led to a bug + * if someone used the same symbol for the head and deletee, like + * HASH_DELETE(hh,users,users); + * We want that to work, but by changing the head (users) below + * we were forfeiting our ability to further refer to the deletee (users) + * in the patch-up process. Solution: use scratch space to + * copy the deletee pointer, then the latter references are via that + * scratch pointer rather than through the repointed (users) symbol. + */ +#define HASH_DELETE(hh,head,delptr) \ + HASH_DELETE_HH(hh, head, &(delptr)->hh) + +#define HASH_DELETE_HH(hh,head,delptrhh) \ +do { \ + struct UT_hash_handle *_hd_hh_del = (delptrhh); \ + if ((_hd_hh_del->prev == NULL) && (_hd_hh_del->next == NULL)) { \ + HASH_BLOOM_FREE((head)->hh.tbl); \ + uthash_free((head)->hh.tbl->buckets, \ + (head)->hh.tbl->num_buckets * sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head) = NULL; \ + } else { \ + unsigned _hd_bkt; \ + if (_hd_hh_del == (head)->hh.tbl->tail) { \ + (head)->hh.tbl->tail = HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->prev); \ + } \ + if (_hd_hh_del->prev != NULL) { \ + HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->prev)->next = _hd_hh_del->next; \ + } else { \ + DECLTYPE_ASSIGN(head, _hd_hh_del->next); \ + } \ + if (_hd_hh_del->next != NULL) { \ + HH_FROM_ELMT((head)->hh.tbl, _hd_hh_del->next)->prev = _hd_hh_del->prev; \ + } \ + HASH_TO_BKT(_hd_hh_del->hashv, (head)->hh.tbl->num_buckets, _hd_bkt); \ + HASH_DEL_IN_BKT((head)->hh.tbl->buckets[_hd_bkt], _hd_hh_del); \ + (head)->hh.tbl->num_items--; \ + } \ + HASH_FSCK(hh, head, "HASH_DELETE_HH"); \ +} while (0) + +/* convenience forms of HASH_FIND/HASH_ADD/HASH_DEL */ +#define HASH_FIND_STR(head,findstr,out) \ +do { \ + unsigned _uthash_hfstr_keylen = (unsigned)uthash_strlen(findstr); \ + HASH_FIND(hh, head, findstr, _uthash_hfstr_keylen, out); \ +} while (0) +#define HASH_ADD_STR(head,strfield,add) \ +do { \ + unsigned _uthash_hastr_keylen = (unsigned)uthash_strlen((add)->strfield); \ + HASH_ADD(hh, head, strfield[0], _uthash_hastr_keylen, add); \ +} while (0) +#define HASH_REPLACE_STR(head,strfield,add,replaced) \ +do { \ + unsigned _uthash_hrstr_keylen = (unsigned)uthash_strlen((add)->strfield); \ + HASH_REPLACE(hh, head, strfield[0], _uthash_hrstr_keylen, add, replaced); \ +} while (0) +#define HASH_FIND_INT(head,findint,out) \ + HASH_FIND(hh,head,findint,sizeof(int),out) +#define HASH_ADD_INT(head,intfield,add) \ + HASH_ADD(hh,head,intfield,sizeof(int),add) +#define HASH_REPLACE_INT(head,intfield,add,replaced) \ + HASH_REPLACE(hh,head,intfield,sizeof(int),add,replaced) +#define HASH_FIND_PTR(head,findptr,out) \ + HASH_FIND(hh,head,findptr,sizeof(void *),out) +#define HASH_ADD_PTR(head,ptrfield,add) \ + HASH_ADD(hh,head,ptrfield,sizeof(void *),add) +#define HASH_REPLACE_PTR(head,ptrfield,add,replaced) \ + HASH_REPLACE(hh,head,ptrfield,sizeof(void *),add,replaced) +#define HASH_DEL(head,delptr) \ + HASH_DELETE(hh,head,delptr) + +/* HASH_FSCK checks hash integrity on every add/delete when HASH_DEBUG is defined. + * This is for uthash developer only; it compiles away if HASH_DEBUG isn't defined. + */ +#ifdef HASH_DEBUG +#include /* fprintf, stderr */ +#define HASH_OOPS(...) do { fprintf(stderr, __VA_ARGS__); exit(-1); } while (0) +#define HASH_FSCK(hh,head,where) \ +do { \ + struct UT_hash_handle *_thh; \ + if (head) { \ + unsigned _bkt_i; \ + unsigned _count = 0; \ + char *_prev; \ + for (_bkt_i = 0; _bkt_i < (head)->hh.tbl->num_buckets; ++_bkt_i) { \ + unsigned _bkt_count = 0; \ + _thh = (head)->hh.tbl->buckets[_bkt_i].hh_head; \ + _prev = NULL; \ + while (_thh) { \ + if (_prev != (char*)(_thh->hh_prev)) { \ + HASH_OOPS("%s: invalid hh_prev %p, actual %p\n", \ + (where), (void*)_thh->hh_prev, (void*)_prev); \ + } \ + _bkt_count++; \ + _prev = (char*)(_thh); \ + _thh = _thh->hh_next; \ + } \ + _count += _bkt_count; \ + if ((head)->hh.tbl->buckets[_bkt_i].count != _bkt_count) { \ + HASH_OOPS("%s: invalid bucket count %u, actual %u\n", \ + (where), (head)->hh.tbl->buckets[_bkt_i].count, _bkt_count); \ + } \ + } \ + if (_count != (head)->hh.tbl->num_items) { \ + HASH_OOPS("%s: invalid hh item count %u, actual %u\n", \ + (where), (head)->hh.tbl->num_items, _count); \ + } \ + _count = 0; \ + _prev = NULL; \ + _thh = &(head)->hh; \ + while (_thh) { \ + _count++; \ + if (_prev != (char*)_thh->prev) { \ + HASH_OOPS("%s: invalid prev %p, actual %p\n", \ + (where), (void*)_thh->prev, (void*)_prev); \ + } \ + _prev = (char*)ELMT_FROM_HH((head)->hh.tbl, _thh); \ + _thh = (_thh->next ? HH_FROM_ELMT((head)->hh.tbl, _thh->next) : NULL); \ + } \ + if (_count != (head)->hh.tbl->num_items) { \ + HASH_OOPS("%s: invalid app item count %u, actual %u\n", \ + (where), (head)->hh.tbl->num_items, _count); \ + } \ + } \ +} while (0) +#else +#define HASH_FSCK(hh,head,where) +#endif + +/* When compiled with -DHASH_EMIT_KEYS, length-prefixed keys are emitted to + * the descriptor to which this macro is defined for tuning the hash function. + * The app can #include to get the prototype for write(2). */ +#ifdef HASH_EMIT_KEYS +#define HASH_EMIT_KEY(hh,head,keyptr,fieldlen) \ +do { \ + unsigned _klen = fieldlen; \ + write(HASH_EMIT_KEYS, &_klen, sizeof(_klen)); \ + write(HASH_EMIT_KEYS, keyptr, (unsigned long)fieldlen); \ +} while (0) +#else +#define HASH_EMIT_KEY(hh,head,keyptr,fieldlen) +#endif + +/* The Bernstein hash function, used in Perl prior to v5.6. Note (x<<5+x)=x*33. */ +#define HASH_BER(key,keylen,hashv) \ +do { \ + unsigned _hb_keylen = (unsigned)keylen; \ + const unsigned char *_hb_key = (const unsigned char*)(key); \ + (hashv) = 0; \ + while (_hb_keylen-- != 0U) { \ + (hashv) = (((hashv) << 5) + (hashv)) + *_hb_key++; \ + } \ +} while (0) + + +/* SAX/FNV/OAT/JEN hash functions are macro variants of those listed at + * http://eternallyconfuzzled.com/tuts/algorithms/jsw_tut_hashing.aspx */ +#define HASH_SAX(key,keylen,hashv) \ +do { \ + unsigned _sx_i; \ + const unsigned char *_hs_key = (const unsigned char*)(key); \ + hashv = 0; \ + for (_sx_i=0; _sx_i < keylen; _sx_i++) { \ + hashv ^= (hashv << 5) + (hashv >> 2) + _hs_key[_sx_i]; \ + } \ +} while (0) +/* FNV-1a variation */ +#define HASH_FNV(key,keylen,hashv) \ +do { \ + unsigned _fn_i; \ + const unsigned char *_hf_key = (const unsigned char*)(key); \ + (hashv) = 2166136261U; \ + for (_fn_i=0; _fn_i < keylen; _fn_i++) { \ + hashv = hashv ^ _hf_key[_fn_i]; \ + hashv = hashv * 16777619U; \ + } \ +} while (0) + +#define HASH_OAT(key,keylen,hashv) \ +do { \ + unsigned _ho_i; \ + const unsigned char *_ho_key=(const unsigned char*)(key); \ + hashv = 0; \ + for(_ho_i=0; _ho_i < keylen; _ho_i++) { \ + hashv += _ho_key[_ho_i]; \ + hashv += (hashv << 10); \ + hashv ^= (hashv >> 6); \ + } \ + hashv += (hashv << 3); \ + hashv ^= (hashv >> 11); \ + hashv += (hashv << 15); \ +} while (0) + +#define HASH_JEN_MIX(a,b,c) \ +do { \ + a -= b; a -= c; a ^= ( c >> 13 ); \ + b -= c; b -= a; b ^= ( a << 8 ); \ + c -= a; c -= b; c ^= ( b >> 13 ); \ + a -= b; a -= c; a ^= ( c >> 12 ); \ + b -= c; b -= a; b ^= ( a << 16 ); \ + c -= a; c -= b; c ^= ( b >> 5 ); \ + a -= b; a -= c; a ^= ( c >> 3 ); \ + b -= c; b -= a; b ^= ( a << 10 ); \ + c -= a; c -= b; c ^= ( b >> 15 ); \ +} while (0) + +#define HASH_JEN(key,keylen,hashv) \ +do { \ + unsigned _hj_i,_hj_j,_hj_k; \ + unsigned const char *_hj_key=(unsigned const char*)(key); \ + hashv = 0xfeedbeefu; \ + _hj_i = _hj_j = 0x9e3779b9u; \ + _hj_k = (unsigned)(keylen); \ + while (_hj_k >= 12U) { \ + _hj_i += (_hj_key[0] + ( (unsigned)_hj_key[1] << 8 ) \ + + ( (unsigned)_hj_key[2] << 16 ) \ + + ( (unsigned)_hj_key[3] << 24 ) ); \ + _hj_j += (_hj_key[4] + ( (unsigned)_hj_key[5] << 8 ) \ + + ( (unsigned)_hj_key[6] << 16 ) \ + + ( (unsigned)_hj_key[7] << 24 ) ); \ + hashv += (_hj_key[8] + ( (unsigned)_hj_key[9] << 8 ) \ + + ( (unsigned)_hj_key[10] << 16 ) \ + + ( (unsigned)_hj_key[11] << 24 ) ); \ + \ + HASH_JEN_MIX(_hj_i, _hj_j, hashv); \ + \ + _hj_key += 12; \ + _hj_k -= 12U; \ + } \ + hashv += (unsigned)(keylen); \ + switch ( _hj_k ) { \ + case 11: hashv += ( (unsigned)_hj_key[10] << 24 ); /* FALLTHROUGH */ \ + case 10: hashv += ( (unsigned)_hj_key[9] << 16 ); /* FALLTHROUGH */ \ + case 9: hashv += ( (unsigned)_hj_key[8] << 8 ); /* FALLTHROUGH */ \ + case 8: _hj_j += ( (unsigned)_hj_key[7] << 24 ); /* FALLTHROUGH */ \ + case 7: _hj_j += ( (unsigned)_hj_key[6] << 16 ); /* FALLTHROUGH */ \ + case 6: _hj_j += ( (unsigned)_hj_key[5] << 8 ); /* FALLTHROUGH */ \ + case 5: _hj_j += _hj_key[4]; /* FALLTHROUGH */ \ + case 4: _hj_i += ( (unsigned)_hj_key[3] << 24 ); /* FALLTHROUGH */ \ + case 3: _hj_i += ( (unsigned)_hj_key[2] << 16 ); /* FALLTHROUGH */ \ + case 2: _hj_i += ( (unsigned)_hj_key[1] << 8 ); /* FALLTHROUGH */ \ + case 1: _hj_i += _hj_key[0]; /* FALLTHROUGH */ \ + default: ; \ + } \ + HASH_JEN_MIX(_hj_i, _hj_j, hashv); \ +} while (0) + +/* The Paul Hsieh hash function */ +#undef get16bits +#if (defined(__GNUC__) && defined(__i386__)) || defined(__WATCOMC__) \ + || defined(_MSC_VER) || defined (__BORLANDC__) || defined (__TURBOC__) +#define get16bits(d) (*((const uint16_t *) (d))) +#endif + +#if !defined (get16bits) +#define get16bits(d) ((((uint32_t)(((const uint8_t *)(d))[1])) << 8) \ + +(uint32_t)(((const uint8_t *)(d))[0]) ) +#endif +#define HASH_SFH(key,keylen,hashv) \ +do { \ + unsigned const char *_sfh_key=(unsigned const char*)(key); \ + uint32_t _sfh_tmp, _sfh_len = (uint32_t)keylen; \ + \ + unsigned _sfh_rem = _sfh_len & 3U; \ + _sfh_len >>= 2; \ + hashv = 0xcafebabeu; \ + \ + /* Main loop */ \ + for (;_sfh_len > 0U; _sfh_len--) { \ + hashv += get16bits (_sfh_key); \ + _sfh_tmp = ((uint32_t)(get16bits (_sfh_key+2)) << 11) ^ hashv; \ + hashv = (hashv << 16) ^ _sfh_tmp; \ + _sfh_key += 2U*sizeof (uint16_t); \ + hashv += hashv >> 11; \ + } \ + \ + /* Handle end cases */ \ + switch (_sfh_rem) { \ + case 3: hashv += get16bits (_sfh_key); \ + hashv ^= hashv << 16; \ + hashv ^= (uint32_t)(_sfh_key[sizeof (uint16_t)]) << 18; \ + hashv += hashv >> 11; \ + break; \ + case 2: hashv += get16bits (_sfh_key); \ + hashv ^= hashv << 11; \ + hashv += hashv >> 17; \ + break; \ + case 1: hashv += *_sfh_key; \ + hashv ^= hashv << 10; \ + hashv += hashv >> 1; \ + break; \ + default: ; \ + } \ + \ + /* Force "avalanching" of final 127 bits */ \ + hashv ^= hashv << 3; \ + hashv += hashv >> 5; \ + hashv ^= hashv << 4; \ + hashv += hashv >> 17; \ + hashv ^= hashv << 25; \ + hashv += hashv >> 6; \ +} while (0) + +/* iterate over items in a known bucket to find desired item */ +#define HASH_FIND_IN_BKT(tbl,hh,head,keyptr,keylen_in,hashval,out) \ +do { \ + if ((head).hh_head != NULL) { \ + DECLTYPE_ASSIGN(out, ELMT_FROM_HH(tbl, (head).hh_head)); \ + } else { \ + (out) = NULL; \ + } \ + while ((out) != NULL) { \ + if ((out)->hh.hashv == (hashval) && (out)->hh.keylen == (keylen_in)) { \ + if (HASH_KEYCMP((out)->hh.key, keyptr, keylen_in) == 0) { \ + break; \ + } \ + } \ + if ((out)->hh.hh_next != NULL) { \ + DECLTYPE_ASSIGN(out, ELMT_FROM_HH(tbl, (out)->hh.hh_next)); \ + } else { \ + (out) = NULL; \ + } \ + } \ +} while (0) + +/* add an item to a bucket */ +#define HASH_ADD_TO_BKT(head,hh,addhh,oomed) \ +do { \ + UT_hash_bucket *_ha_head = &(head); \ + _ha_head->count++; \ + (addhh)->hh_next = _ha_head->hh_head; \ + (addhh)->hh_prev = NULL; \ + if (_ha_head->hh_head != NULL) { \ + _ha_head->hh_head->hh_prev = (addhh); \ + } \ + _ha_head->hh_head = (addhh); \ + if ((_ha_head->count >= ((_ha_head->expand_mult + 1U) * HASH_BKT_CAPACITY_THRESH)) \ + && !(addhh)->tbl->noexpand) { \ + HASH_EXPAND_BUCKETS(addhh,(addhh)->tbl, oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (oomed) { \ + HASH_DEL_IN_BKT(head,addhh); \ + } \ + ) \ + } \ +} while (0) + +/* remove an item from a given bucket */ +#define HASH_DEL_IN_BKT(head,delhh) \ +do { \ + UT_hash_bucket *_hd_head = &(head); \ + _hd_head->count--; \ + if (_hd_head->hh_head == (delhh)) { \ + _hd_head->hh_head = (delhh)->hh_next; \ + } \ + if ((delhh)->hh_prev) { \ + (delhh)->hh_prev->hh_next = (delhh)->hh_next; \ + } \ + if ((delhh)->hh_next) { \ + (delhh)->hh_next->hh_prev = (delhh)->hh_prev; \ + } \ +} while (0) + +/* Bucket expansion has the effect of doubling the number of buckets + * and redistributing the items into the new buckets. Ideally the + * items will distribute more or less evenly into the new buckets + * (the extent to which this is true is a measure of the quality of + * the hash function as it applies to the key domain). + * + * With the items distributed into more buckets, the chain length + * (item count) in each bucket is reduced. Thus by expanding buckets + * the hash keeps a bound on the chain length. This bounded chain + * length is the essence of how a hash provides constant time lookup. + * + * The calculation of tbl->ideal_chain_maxlen below deserves some + * explanation. First, keep in mind that we're calculating the ideal + * maximum chain length based on the *new* (doubled) bucket count. + * In fractions this is just n/b (n=number of items,b=new num buckets). + * Since the ideal chain length is an integer, we want to calculate + * ceil(n/b). We don't depend on floating point arithmetic in this + * hash, so to calculate ceil(n/b) with integers we could write + * + * ceil(n/b) = (n/b) + ((n%b)?1:0) + * + * and in fact a previous version of this hash did just that. + * But now we have improved things a bit by recognizing that b is + * always a power of two. We keep its base 2 log handy (call it lb), + * so now we can write this with a bit shift and logical AND: + * + * ceil(n/b) = (n>>lb) + ( (n & (b-1)) ? 1:0) + * + */ +#define HASH_EXPAND_BUCKETS(hh,tbl,oomed) \ +do { \ + unsigned _he_bkt; \ + unsigned _he_bkt_i; \ + struct UT_hash_handle *_he_thh, *_he_hh_nxt; \ + UT_hash_bucket *_he_new_buckets, *_he_newbkt; \ + _he_new_buckets = (UT_hash_bucket*)uthash_malloc( \ + sizeof(struct UT_hash_bucket) * (tbl)->num_buckets * 2U); \ + if (!_he_new_buckets) { \ + HASH_RECORD_OOM(oomed); \ + } else { \ + uthash_bzero(_he_new_buckets, \ + sizeof(struct UT_hash_bucket) * (tbl)->num_buckets * 2U); \ + (tbl)->ideal_chain_maxlen = \ + ((tbl)->num_items >> ((tbl)->log2_num_buckets+1U)) + \ + ((((tbl)->num_items & (((tbl)->num_buckets*2U)-1U)) != 0U) ? 1U : 0U); \ + (tbl)->nonideal_items = 0; \ + for (_he_bkt_i = 0; _he_bkt_i < (tbl)->num_buckets; _he_bkt_i++) { \ + _he_thh = (tbl)->buckets[ _he_bkt_i ].hh_head; \ + while (_he_thh != NULL) { \ + _he_hh_nxt = _he_thh->hh_next; \ + HASH_TO_BKT(_he_thh->hashv, (tbl)->num_buckets * 2U, _he_bkt); \ + _he_newbkt = &(_he_new_buckets[_he_bkt]); \ + if (++(_he_newbkt->count) > (tbl)->ideal_chain_maxlen) { \ + (tbl)->nonideal_items++; \ + if (_he_newbkt->count > _he_newbkt->expand_mult * (tbl)->ideal_chain_maxlen) { \ + _he_newbkt->expand_mult++; \ + } \ + } \ + _he_thh->hh_prev = NULL; \ + _he_thh->hh_next = _he_newbkt->hh_head; \ + if (_he_newbkt->hh_head != NULL) { \ + _he_newbkt->hh_head->hh_prev = _he_thh; \ + } \ + _he_newbkt->hh_head = _he_thh; \ + _he_thh = _he_hh_nxt; \ + } \ + } \ + uthash_free((tbl)->buckets, (tbl)->num_buckets * sizeof(struct UT_hash_bucket)); \ + (tbl)->num_buckets *= 2U; \ + (tbl)->log2_num_buckets++; \ + (tbl)->buckets = _he_new_buckets; \ + (tbl)->ineff_expands = ((tbl)->nonideal_items > ((tbl)->num_items >> 1)) ? \ + ((tbl)->ineff_expands+1U) : 0U; \ + if ((tbl)->ineff_expands > 1U) { \ + (tbl)->noexpand = 1; \ + uthash_noexpand_fyi(tbl); \ + } \ + uthash_expand_fyi(tbl); \ + } \ +} while (0) + + +/* This is an adaptation of Simon Tatham's O(n log(n)) mergesort */ +/* Note that HASH_SORT assumes the hash handle name to be hh. + * HASH_SRT was added to allow the hash handle name to be passed in. */ +#define HASH_SORT(head,cmpfcn) HASH_SRT(hh,head,cmpfcn) +#define HASH_SRT(hh,head,cmpfcn) \ +do { \ + unsigned _hs_i; \ + unsigned _hs_looping,_hs_nmerges,_hs_insize,_hs_psize,_hs_qsize; \ + struct UT_hash_handle *_hs_p, *_hs_q, *_hs_e, *_hs_list, *_hs_tail; \ + if (head != NULL) { \ + _hs_insize = 1; \ + _hs_looping = 1; \ + _hs_list = &((head)->hh); \ + while (_hs_looping != 0U) { \ + _hs_p = _hs_list; \ + _hs_list = NULL; \ + _hs_tail = NULL; \ + _hs_nmerges = 0; \ + while (_hs_p != NULL) { \ + _hs_nmerges++; \ + _hs_q = _hs_p; \ + _hs_psize = 0; \ + for (_hs_i = 0; _hs_i < _hs_insize; ++_hs_i) { \ + _hs_psize++; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + if (_hs_q == NULL) { \ + break; \ + } \ + } \ + _hs_qsize = _hs_insize; \ + while ((_hs_psize != 0U) || ((_hs_qsize != 0U) && (_hs_q != NULL))) { \ + if (_hs_psize == 0U) { \ + _hs_e = _hs_q; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + _hs_qsize--; \ + } else if ((_hs_qsize == 0U) || (_hs_q == NULL)) { \ + _hs_e = _hs_p; \ + if (_hs_p != NULL) { \ + _hs_p = ((_hs_p->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_p->next) : NULL); \ + } \ + _hs_psize--; \ + } else if ((cmpfcn( \ + DECLTYPE(head)(ELMT_FROM_HH((head)->hh.tbl, _hs_p)), \ + DECLTYPE(head)(ELMT_FROM_HH((head)->hh.tbl, _hs_q)) \ + )) <= 0) { \ + _hs_e = _hs_p; \ + if (_hs_p != NULL) { \ + _hs_p = ((_hs_p->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_p->next) : NULL); \ + } \ + _hs_psize--; \ + } else { \ + _hs_e = _hs_q; \ + _hs_q = ((_hs_q->next != NULL) ? \ + HH_FROM_ELMT((head)->hh.tbl, _hs_q->next) : NULL); \ + _hs_qsize--; \ + } \ + if ( _hs_tail != NULL ) { \ + _hs_tail->next = ((_hs_e != NULL) ? \ + ELMT_FROM_HH((head)->hh.tbl, _hs_e) : NULL); \ + } else { \ + _hs_list = _hs_e; \ + } \ + if (_hs_e != NULL) { \ + _hs_e->prev = ((_hs_tail != NULL) ? \ + ELMT_FROM_HH((head)->hh.tbl, _hs_tail) : NULL); \ + } \ + _hs_tail = _hs_e; \ + } \ + _hs_p = _hs_q; \ + } \ + if (_hs_tail != NULL) { \ + _hs_tail->next = NULL; \ + } \ + if (_hs_nmerges <= 1U) { \ + _hs_looping = 0; \ + (head)->hh.tbl->tail = _hs_tail; \ + DECLTYPE_ASSIGN(head, ELMT_FROM_HH((head)->hh.tbl, _hs_list)); \ + } \ + _hs_insize *= 2U; \ + } \ + HASH_FSCK(hh, head, "HASH_SRT"); \ + } \ +} while (0) + +/* This function selects items from one hash into another hash. + * The end result is that the selected items have dual presence + * in both hashes. There is no copy of the items made; rather + * they are added into the new hash through a secondary hash + * hash handle that must be present in the structure. */ +#define HASH_SELECT(hh_dst, dst, hh_src, src, cond) \ +do { \ + unsigned _src_bkt, _dst_bkt; \ + void *_last_elt = NULL, *_elt; \ + UT_hash_handle *_src_hh, *_dst_hh, *_last_elt_hh=NULL; \ + ptrdiff_t _dst_hho = ((char*)(&(dst)->hh_dst) - (char*)(dst)); \ + if ((src) != NULL) { \ + for (_src_bkt=0; _src_bkt < (src)->hh_src.tbl->num_buckets; _src_bkt++) { \ + for (_src_hh = (src)->hh_src.tbl->buckets[_src_bkt].hh_head; \ + _src_hh != NULL; \ + _src_hh = _src_hh->hh_next) { \ + _elt = ELMT_FROM_HH((src)->hh_src.tbl, _src_hh); \ + if (cond(_elt)) { \ + IF_HASH_NONFATAL_OOM( int _hs_oomed = 0; ) \ + _dst_hh = (UT_hash_handle*)(void*)(((char*)_elt) + _dst_hho); \ + _dst_hh->key = _src_hh->key; \ + _dst_hh->keylen = _src_hh->keylen; \ + _dst_hh->hashv = _src_hh->hashv; \ + _dst_hh->prev = _last_elt; \ + _dst_hh->next = NULL; \ + if (_last_elt_hh != NULL) { \ + _last_elt_hh->next = _elt; \ + } \ + if ((dst) == NULL) { \ + DECLTYPE_ASSIGN(dst, _elt); \ + HASH_MAKE_TABLE(hh_dst, dst, _hs_oomed); \ + IF_HASH_NONFATAL_OOM( \ + if (_hs_oomed) { \ + uthash_nonfatal_oom(_elt); \ + (dst) = NULL; \ + continue; \ + } \ + ) \ + } else { \ + _dst_hh->tbl = (dst)->hh_dst.tbl; \ + } \ + HASH_TO_BKT(_dst_hh->hashv, _dst_hh->tbl->num_buckets, _dst_bkt); \ + HASH_ADD_TO_BKT(_dst_hh->tbl->buckets[_dst_bkt], hh_dst, _dst_hh, _hs_oomed); \ + (dst)->hh_dst.tbl->num_items++; \ + IF_HASH_NONFATAL_OOM( \ + if (_hs_oomed) { \ + HASH_ROLLBACK_BKT(hh_dst, dst, _dst_hh); \ + HASH_DELETE_HH(hh_dst, dst, _dst_hh); \ + _dst_hh->tbl = NULL; \ + uthash_nonfatal_oom(_elt); \ + continue; \ + } \ + ) \ + HASH_BLOOM_ADD(_dst_hh->tbl, _dst_hh->hashv); \ + _last_elt = _elt; \ + _last_elt_hh = _dst_hh; \ + } \ + } \ + } \ + } \ + HASH_FSCK(hh_dst, dst, "HASH_SELECT"); \ +} while (0) + +#define HASH_CLEAR(hh,head) \ +do { \ + if ((head) != NULL) { \ + HASH_BLOOM_FREE((head)->hh.tbl); \ + uthash_free((head)->hh.tbl->buckets, \ + (head)->hh.tbl->num_buckets*sizeof(struct UT_hash_bucket)); \ + uthash_free((head)->hh.tbl, sizeof(UT_hash_table)); \ + (head) = NULL; \ + } \ +} while (0) + +#define HASH_OVERHEAD(hh,head) \ + (((head) != NULL) ? ( \ + (size_t)(((head)->hh.tbl->num_items * sizeof(UT_hash_handle)) + \ + ((head)->hh.tbl->num_buckets * sizeof(UT_hash_bucket)) + \ + sizeof(UT_hash_table) + \ + (HASH_BLOOM_BYTELEN))) : 0U) + +#ifdef NO_DECLTYPE +#define HASH_ITER(hh,head,el,tmp) \ +for(((el)=(head)), ((*(char**)(&(tmp)))=(char*)((head!=NULL)?(head)->hh.next:NULL)); \ + (el) != NULL; ((el)=(tmp)), ((*(char**)(&(tmp)))=(char*)((tmp!=NULL)?(tmp)->hh.next:NULL))) +#else +#define HASH_ITER(hh,head,el,tmp) \ +for(((el)=(head)), ((tmp)=DECLTYPE(el)((head!=NULL)?(head)->hh.next:NULL)); \ + (el) != NULL; ((el)=(tmp)), ((tmp)=DECLTYPE(el)((tmp!=NULL)?(tmp)->hh.next:NULL))) +#endif + +/* obtain a count of items in the hash */ +#define HASH_COUNT(head) HASH_CNT(hh,head) +#define HASH_CNT(hh,head) ((head != NULL)?((head)->hh.tbl->num_items):0U) + +typedef struct UT_hash_bucket { + struct UT_hash_handle *hh_head; + unsigned count; + + /* expand_mult is normally set to 0. In this situation, the max chain length + * threshold is enforced at its default value, HASH_BKT_CAPACITY_THRESH. (If + * the bucket's chain exceeds this length, bucket expansion is triggered). + * However, setting expand_mult to a non-zero value delays bucket expansion + * (that would be triggered by additions to this particular bucket) + * until its chain length reaches a *multiple* of HASH_BKT_CAPACITY_THRESH. + * (The multiplier is simply expand_mult+1). The whole idea of this + * multiplier is to reduce bucket expansions, since they are expensive, in + * situations where we know that a particular bucket tends to be overused. + * It is better to let its chain length grow to a longer yet-still-bounded + * value, than to do an O(n) bucket expansion too often. + */ + unsigned expand_mult; + +} UT_hash_bucket; + +/* random signature used only to find hash tables in external analysis */ +#define HASH_SIGNATURE 0xa0111fe1u +#define HASH_BLOOM_SIGNATURE 0xb12220f2u + +typedef struct UT_hash_table { + UT_hash_bucket *buckets; + unsigned num_buckets, log2_num_buckets; + unsigned num_items; + struct UT_hash_handle *tail; /* tail hh in app order, for fast append */ + ptrdiff_t hho; /* hash handle offset (byte pos of hash handle in element */ + + /* in an ideal situation (all buckets used equally), no bucket would have + * more than ceil(#items/#buckets) items. that's the ideal chain length. */ + unsigned ideal_chain_maxlen; + + /* nonideal_items is the number of items in the hash whose chain position + * exceeds the ideal chain maxlen. these items pay the penalty for an uneven + * hash distribution; reaching them in a chain traversal takes >ideal steps */ + unsigned nonideal_items; + + /* ineffective expands occur when a bucket doubling was performed, but + * afterward, more than half the items in the hash had nonideal chain + * positions. If this happens on two consecutive expansions we inhibit any + * further expansion, as it's not helping; this happens when the hash + * function isn't a good fit for the key domain. When expansion is inhibited + * the hash will still work, albeit no longer in constant time. */ + unsigned ineff_expands, noexpand; + + uint32_t signature; /* used only to find hash tables in external analysis */ +#ifdef HASH_BLOOM + uint32_t bloom_sig; /* used only to test bloom exists in external analysis */ + uint8_t *bloom_bv; + uint8_t bloom_nbits; +#endif + +} UT_hash_table; + +typedef struct UT_hash_handle { + struct UT_hash_table *tbl; + void *prev; /* prev element in app order */ + void *next; /* next element in app order */ + struct UT_hash_handle *hh_prev; /* previous hh in bucket order */ + struct UT_hash_handle *hh_next; /* next hh in bucket order */ + const void *key; /* ptr to enclosing struct's key */ + unsigned keylen; /* enclosing struct's key len */ + unsigned hashv; /* result of hash-fcn(key) */ +} UT_hash_handle; + +#endif /* UTHASH_H */ diff --git a/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/utlist.h b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/utlist.h new file mode 100644 index 00000000000..1979448a7b9 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/libcoap/include/coap3/utlist.h @@ -0,0 +1,1073 @@ +/* +Copyright (c) 2007-2021, Troy D. Hanson http://troydhanson.github.io/uthash/ +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. + +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 UTLIST_H +#define UTLIST_H + +#define UTLIST_VERSION 2.3.0 + +#include + +/* + * This file contains macros to manipulate singly and doubly-linked lists. + * + * 1. LL_ macros: singly-linked lists. + * 2. DL_ macros: doubly-linked lists. + * 3. CDL_ macros: circular doubly-linked lists. + * + * To use singly-linked lists, your structure must have a "next" pointer. + * To use doubly-linked lists, your structure must "prev" and "next" pointers. + * Either way, the pointer to the head of the list must be initialized to NULL. + * + * ----------------.EXAMPLE ------------------------- + * struct item { + * int id; + * struct item *prev, *next; + * } + * + * struct item *list = NULL: + * + * int main() { + * struct item *item; + * ... allocate and populate item ... + * DL_APPEND(list, item); + * } + * -------------------------------------------------- + * + * For doubly-linked lists, the append and delete macros are O(1) + * For singly-linked lists, append and delete are O(n) but prepend is O(1) + * The sort macro is O(n log(n)) for all types of single/double/circular lists. + */ + +/* These macros use decltype or the earlier __typeof GNU extension. + As decltype is only available in newer compilers (VS2010 or gcc 4.3+ + when compiling c++ source) this code uses whatever method is needed + or, for VS2008 where neither is available, uses casting workarounds. */ +#if !defined(LDECLTYPE) && !defined(NO_DECLTYPE) +#if defined(_MSC_VER) /* MS compiler */ +#if _MSC_VER >= 1600 && defined(__cplusplus) /* VS2010 or newer in C++ mode */ +#define LDECLTYPE(x) decltype(x) +#else /* VS2008 or older (or VS2010 in C mode) */ +#define NO_DECLTYPE +#endif +#elif defined(__BORLANDC__) || defined(__ICCARM__) || defined(__LCC__) || defined(__WATCOMC__) +#define NO_DECLTYPE +#else /* GNU, Sun and other compilers */ +#define LDECLTYPE(x) __typeof(x) +#endif +#endif + +/* for VS2008 we use some workarounds to get around the lack of decltype, + * namely, we always reassign our tmp variable to the list head if we need + * to dereference its prev/next pointers, and save/restore the real head.*/ +#ifdef NO_DECLTYPE +#define IF_NO_DECLTYPE(x) x +#define LDECLTYPE(x) char* +#define UTLIST_SV(elt,list) _tmp = (char*)(list); {char **_alias = (char**)&(list); *_alias = (elt); } +#define UTLIST_NEXT(elt,list,next) ((char*)((list)->next)) +#define UTLIST_NEXTASGN(elt,list,to,next) { char **_alias = (char**)&((list)->next); *_alias=(char*)(to); } +/* #define UTLIST_PREV(elt,list,prev) ((char*)((list)->prev)) */ +#define UTLIST_PREVASGN(elt,list,to,prev) { char **_alias = (char**)&((list)->prev); *_alias=(char*)(to); } +#define UTLIST_RS(list) { char **_alias = (char**)&(list); *_alias=_tmp; } +#define UTLIST_CASTASGN(a,b) { char **_alias = (char**)&(a); *_alias=(char*)(b); } +#else +#define IF_NO_DECLTYPE(x) +#define UTLIST_SV(elt,list) +#define UTLIST_NEXT(elt,list,next) ((elt)->next) +#define UTLIST_NEXTASGN(elt,list,to,next) ((elt)->next)=(to) +/* #define UTLIST_PREV(elt,list,prev) ((elt)->prev) */ +#define UTLIST_PREVASGN(elt,list,to,prev) ((elt)->prev)=(to) +#define UTLIST_RS(list) +#define UTLIST_CASTASGN(a,b) (a)=(b) +#endif + +/****************************************************************************** + * The sort macro is an adaptation of Simon Tatham's O(n log(n)) mergesort * + * Unwieldy variable names used here to avoid shadowing passed-in variables. * + *****************************************************************************/ +#define LL_SORT(list, cmp) \ + LL_SORT2(list, cmp, next) + +#define LL_SORT2(list, cmp, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + IF_NO_DECLTYPE(LDECLTYPE(list) _tmp;) \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); _ls_q = UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while (_ls_psize > 0 || (_ls_qsize > 0 && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } else if (_ls_qsize == 0 || !_ls_q) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,NULL,next); UTLIST_RS(list); \ + } \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + + +#define DL_SORT(list, cmp) \ + DL_SORT2(list, cmp, prev, next) + +#define DL_SORT2(list, cmp, prev, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + IF_NO_DECLTYPE(LDECLTYPE(list) _tmp;) \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); _ls_q = UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while ((_ls_psize > 0) || ((_ls_qsize > 0) && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } else if ((_ls_qsize == 0) || (!_ls_q)) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + UTLIST_SV(_ls_e,list); UTLIST_PREVASGN(_ls_e,list,_ls_tail,prev); UTLIST_RS(list); \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + UTLIST_CASTASGN((list)->prev, _ls_tail); \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,NULL,next); UTLIST_RS(list); \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + +#define CDL_SORT(list, cmp) \ + CDL_SORT2(list, cmp, prev, next) + +#define CDL_SORT2(list, cmp, prev, next) \ +do { \ + LDECLTYPE(list) _ls_p; \ + LDECLTYPE(list) _ls_q; \ + LDECLTYPE(list) _ls_e; \ + LDECLTYPE(list) _ls_tail; \ + LDECLTYPE(list) _ls_oldhead; \ + LDECLTYPE(list) _tmp; \ + int _ls_insize, _ls_nmerges, _ls_psize, _ls_qsize, _ls_i, _ls_looping; \ + if (list) { \ + _ls_insize = 1; \ + _ls_looping = 1; \ + while (_ls_looping) { \ + UTLIST_CASTASGN(_ls_p,list); \ + UTLIST_CASTASGN(_ls_oldhead,list); \ + (list) = NULL; \ + _ls_tail = NULL; \ + _ls_nmerges = 0; \ + while (_ls_p) { \ + _ls_nmerges++; \ + _ls_q = _ls_p; \ + _ls_psize = 0; \ + for (_ls_i = 0; _ls_i < _ls_insize; _ls_i++) { \ + _ls_psize++; \ + UTLIST_SV(_ls_q,list); \ + if (UTLIST_NEXT(_ls_q,list,next) == _ls_oldhead) { \ + _ls_q = NULL; \ + } else { \ + _ls_q = UTLIST_NEXT(_ls_q,list,next); \ + } \ + UTLIST_RS(list); \ + if (!_ls_q) break; \ + } \ + _ls_qsize = _ls_insize; \ + while (_ls_psize > 0 || (_ls_qsize > 0 && _ls_q)) { \ + if (_ls_psize == 0) { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + if (_ls_q == _ls_oldhead) { _ls_q = NULL; } \ + } else if (_ls_qsize == 0 || !_ls_q) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + if (_ls_p == _ls_oldhead) { _ls_p = NULL; } \ + } else if (cmp(_ls_p,_ls_q) <= 0) { \ + _ls_e = _ls_p; UTLIST_SV(_ls_p,list); _ls_p = \ + UTLIST_NEXT(_ls_p,list,next); UTLIST_RS(list); _ls_psize--; \ + if (_ls_p == _ls_oldhead) { _ls_p = NULL; } \ + } else { \ + _ls_e = _ls_q; UTLIST_SV(_ls_q,list); _ls_q = \ + UTLIST_NEXT(_ls_q,list,next); UTLIST_RS(list); _ls_qsize--; \ + if (_ls_q == _ls_oldhead) { _ls_q = NULL; } \ + } \ + if (_ls_tail) { \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_ls_e,next); UTLIST_RS(list); \ + } else { \ + UTLIST_CASTASGN(list,_ls_e); \ + } \ + UTLIST_SV(_ls_e,list); UTLIST_PREVASGN(_ls_e,list,_ls_tail,prev); UTLIST_RS(list); \ + _ls_tail = _ls_e; \ + } \ + _ls_p = _ls_q; \ + } \ + UTLIST_CASTASGN((list)->prev,_ls_tail); \ + UTLIST_CASTASGN(_tmp,list); \ + UTLIST_SV(_ls_tail,list); UTLIST_NEXTASGN(_ls_tail,list,_tmp,next); UTLIST_RS(list); \ + if (_ls_nmerges <= 1) { \ + _ls_looping=0; \ + } \ + _ls_insize *= 2; \ + } \ + } \ +} while (0) + +/****************************************************************************** + * singly linked list macros (non-circular) * + *****************************************************************************/ +#define LL_PREPEND(head,add) \ + LL_PREPEND2(head,add,next) + +#define LL_PREPEND2(head,add,next) \ +do { \ + (add)->next = (head); \ + (head) = (add); \ +} while (0) + +#define LL_CONCAT(head1,head2) \ + LL_CONCAT2(head1,head2,next) + +#define LL_CONCAT2(head1,head2,next) \ +do { \ + LDECLTYPE(head1) _tmp; \ + if (head1) { \ + _tmp = (head1); \ + while (_tmp->next) { _tmp = _tmp->next; } \ + _tmp->next=(head2); \ + } else { \ + (head1)=(head2); \ + } \ +} while (0) + +#define LL_APPEND(head,add) \ + LL_APPEND2(head,add,next) + +#define LL_APPEND2(head,add,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + (add)->next=NULL; \ + if (head) { \ + _tmp = (head); \ + while (_tmp->next) { _tmp = _tmp->next; } \ + _tmp->next=(add); \ + } else { \ + (head)=(add); \ + } \ +} while (0) + +#define LL_INSERT_INORDER(head,add,cmp) \ + LL_INSERT_INORDER2(head,add,cmp,next) + +#define LL_INSERT_INORDER2(head,add,cmp,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + LL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + LL_APPEND_ELEM2(head, _tmp, add, next); \ + } else { \ + (head) = (add); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define LL_LOWER_BOUND(head,elt,like,cmp) \ + LL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define LL_LOWER_BOUND2(head,elt,like,cmp,next) \ + do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != NULL; (elt) = (elt)->next) { \ + if (cmp((elt)->next, like) >= 0) { \ + break; \ + } \ + } \ + } \ + } while (0) + +#define LL_DELETE(head,del) \ + LL_DELETE2(head,del,next) + +#define LL_DELETE2(head,del,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if ((head) == (del)) { \ + (head)=(head)->next; \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (del))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (del)->next; \ + } \ + } \ +} while (0) + +#define LL_COUNT(head,el,counter) \ + LL_COUNT2(head,el,counter,next) \ + +#define LL_COUNT2(head,el,counter,next) \ +do { \ + (counter) = 0; \ + LL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define LL_FOREACH(head,el) \ + LL_FOREACH2(head,el,next) + +#define LL_FOREACH2(head,el,next) \ + for ((el) = (head); el; (el) = (el)->next) + +#define LL_FOREACH_SAFE(head,el,tmp) \ + LL_FOREACH_SAFE2(head,el,tmp,next) + +#define LL_FOREACH_SAFE2(head,el,tmp,next) \ + for ((el) = (head); (el) && ((tmp) = (el)->next, 1); (el) = (tmp)) + +#define LL_SEARCH_SCALAR(head,out,field,val) \ + LL_SEARCH_SCALAR2(head,out,field,val,next) + +#define LL_SEARCH_SCALAR2(head,out,field,val,next) \ +do { \ + LL_FOREACH2(head,out,next) { \ + if ((out)->field == (val)) break; \ + } \ +} while (0) + +#define LL_SEARCH(head,out,elt,cmp) \ + LL_SEARCH2(head,out,elt,cmp,next) + +#define LL_SEARCH2(head,out,elt,cmp,next) \ +do { \ + LL_FOREACH2(head,out,next) { \ + if ((cmp(out,elt))==0) break; \ + } \ +} while (0) + +#define LL_REPLACE_ELEM2(head, el, add, next) \ +do { \ + LDECLTYPE(head) _tmp; \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (el))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (add); \ + } \ + } \ +} while (0) + +#define LL_REPLACE_ELEM(head, el, add) \ + LL_REPLACE_ELEM2(head, el, add, next) + +#define LL_PREPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + LDECLTYPE(head) _tmp; \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + _tmp = (head); \ + while (_tmp->next && (_tmp->next != (el))) { \ + _tmp = _tmp->next; \ + } \ + if (_tmp->next) { \ + _tmp->next = (add); \ + } \ + } \ + } else { \ + LL_APPEND2(head, add, next); \ + } \ +} while (0) \ + +#define LL_PREPEND_ELEM(head, el, add) \ + LL_PREPEND_ELEM2(head, el, add, next) + +#define LL_APPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (el)->next = (add); \ + } else { \ + LL_PREPEND2(head, add, next); \ + } \ +} while (0) \ + +#define LL_APPEND_ELEM(head, el, add) \ + LL_APPEND_ELEM2(head, el, add, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef LL_CONCAT2 +#define LL_CONCAT2(head1,head2,next) \ +do { \ + char *_tmp; \ + if (head1) { \ + _tmp = (char*)(head1); \ + while ((head1)->next) { (head1) = (head1)->next; } \ + (head1)->next = (head2); \ + UTLIST_RS(head1); \ + } else { \ + (head1)=(head2); \ + } \ +} while (0) + +#undef LL_APPEND2 +#define LL_APPEND2(head,add,next) \ +do { \ + if (head) { \ + (add)->next = head; /* use add->next as a temp variable */ \ + while ((add)->next->next) { (add)->next = (add)->next->next; } \ + (add)->next->next=(add); \ + } else { \ + (head)=(add); \ + } \ + (add)->next=NULL; \ +} while (0) + +#undef LL_INSERT_INORDER2 +#define LL_INSERT_INORDER2(head,add,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, add)) >= 0) { \ + (add)->next = (head); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next != NULL && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->next = (head)->next; \ + (head)->next = (add); \ + UTLIST_RS(head); \ + } \ +} while (0) + +#undef LL_DELETE2 +#define LL_DELETE2(head,del,next) \ +do { \ + if ((head) == (del)) { \ + (head)=(head)->next; \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next && ((head)->next != (del))) { \ + (head) = (head)->next; \ + } \ + if ((head)->next) { \ + (head)->next = ((del)->next); \ + } \ + UTLIST_RS(head); \ + } \ +} while (0) + +#undef LL_REPLACE_ELEM2 +#define LL_REPLACE_ELEM2(head, el, add, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->next = head; \ + while ((add)->next->next && ((add)->next->next != (el))) { \ + (add)->next = (add)->next->next; \ + } \ + if ((add)->next->next) { \ + (add)->next->next = (add); \ + } \ + } \ + (add)->next = (el)->next; \ +} while (0) + +#undef LL_PREPEND_ELEM2 +#define LL_PREPEND_ELEM2(head, el, add, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->next = (head); \ + while ((add)->next->next && ((add)->next->next != (el))) { \ + (add)->next = (add)->next->next; \ + } \ + if ((add)->next->next) { \ + (add)->next->next = (add); \ + } \ + } \ + (add)->next = (el); \ + } else { \ + LL_APPEND2(head, add, next); \ + } \ +} while (0) \ + +#endif /* NO_DECLTYPE */ + +/****************************************************************************** + * doubly linked list macros (non-circular) * + *****************************************************************************/ +#define DL_PREPEND(head,add) \ + DL_PREPEND2(head,add,prev,next) + +#define DL_PREPEND2(head,add,prev,next) \ +do { \ + (add)->next = (head); \ + if (head) { \ + (add)->prev = (head)->prev; \ + (head)->prev = (add); \ + } else { \ + (add)->prev = (add); \ + } \ + (head) = (add); \ +} while (0) + +#define DL_APPEND(head,add) \ + DL_APPEND2(head,add,prev,next) + +#define DL_APPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (head)->prev->next = (add); \ + (head)->prev = (add); \ + (add)->next = NULL; \ + } else { \ + (head)=(add); \ + (head)->prev = (head); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define DL_INSERT_INORDER(head,add,cmp) \ + DL_INSERT_INORDER2(head,add,cmp,prev,next) + +#define DL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + DL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + DL_APPEND_ELEM2(head, _tmp, add, prev, next); \ + } else { \ + (head) = (add); \ + (head)->prev = (head); \ + (head)->next = NULL; \ + } \ +} while (0) + +#define DL_LOWER_BOUND(head,elt,like,cmp) \ + DL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define DL_LOWER_BOUND2(head,elt,like,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != NULL; (elt) = (elt)->next) { \ + if ((cmp((elt)->next, like)) >= 0) { \ + break; \ + } \ + } \ + } \ +} while (0) + +#define DL_CONCAT(head1,head2) \ + DL_CONCAT2(head1,head2,prev,next) + +#define DL_CONCAT2(head1,head2,prev,next) \ +do { \ + LDECLTYPE(head1) _tmp; \ + if (head2) { \ + if (head1) { \ + UTLIST_CASTASGN(_tmp, (head2)->prev); \ + (head2)->prev = (head1)->prev; \ + (head1)->prev->next = (head2); \ + UTLIST_CASTASGN((head1)->prev, _tmp); \ + } else { \ + (head1)=(head2); \ + } \ + } \ +} while (0) + +#define DL_DELETE(head,del) \ + DL_DELETE2(head,del,prev,next) + +#define DL_DELETE2(head,del,prev,next) \ +do { \ + assert((head) != NULL); \ + assert((del)->prev != NULL); \ + if ((del)->prev == (del)) { \ + (head)=NULL; \ + } else if ((del)==(head)) { \ + (del)->next->prev = (del)->prev; \ + (head) = (del)->next; \ + } else { \ + (del)->prev->next = (del)->next; \ + if ((del)->next) { \ + (del)->next->prev = (del)->prev; \ + } else { \ + (head)->prev = (del)->prev; \ + } \ + } \ +} while (0) + +#define DL_COUNT(head,el,counter) \ + DL_COUNT2(head,el,counter,next) \ + +#define DL_COUNT2(head,el,counter,next) \ +do { \ + (counter) = 0; \ + DL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define DL_FOREACH(head,el) \ + DL_FOREACH2(head,el,next) + +#define DL_FOREACH2(head,el,next) \ + for ((el) = (head); el; (el) = (el)->next) + +/* this version is safe for deleting the elements during iteration */ +#define DL_FOREACH_SAFE(head,el,tmp) \ + DL_FOREACH_SAFE2(head,el,tmp,next) + +#define DL_FOREACH_SAFE2(head,el,tmp,next) \ + for ((el) = (head); (el) && ((tmp) = (el)->next, 1); (el) = (tmp)) + +/* these are identical to their singly-linked list counterparts */ +#define DL_SEARCH_SCALAR LL_SEARCH_SCALAR +#define DL_SEARCH LL_SEARCH +#define DL_SEARCH_SCALAR2 LL_SEARCH_SCALAR2 +#define DL_SEARCH2 LL_SEARCH2 + +#define DL_REPLACE_ELEM2(head, el, add, prev, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((head) == (el)) { \ + (head) = (add); \ + (add)->next = (el)->next; \ + if ((el)->next == NULL) { \ + (add)->prev = (add); \ + } else { \ + (add)->prev = (el)->prev; \ + (add)->next->prev = (add); \ + } \ + } else { \ + (add)->next = (el)->next; \ + (add)->prev = (el)->prev; \ + (add)->prev->next = (add); \ + if ((el)->next == NULL) { \ + (head)->prev = (add); \ + } else { \ + (add)->next->prev = (add); \ + } \ + } \ +} while (0) + +#define DL_REPLACE_ELEM(head, el, add) \ + DL_REPLACE_ELEM2(head, el, add, prev, next) + +#define DL_PREPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + (add)->prev = (el)->prev; \ + (el)->prev = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } else { \ + (add)->prev->next = (add); \ + } \ + } else { \ + DL_APPEND2(head, add, prev, next); \ + } \ +} while (0) \ + +#define DL_PREPEND_ELEM(head, el, add) \ + DL_PREPEND_ELEM2(head, el, add, prev, next) + +#define DL_APPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (add)->prev = (el); \ + (el)->next = (add); \ + if ((add)->next) { \ + (add)->next->prev = (add); \ + } else { \ + (head)->prev = (add); \ + } \ + } else { \ + DL_PREPEND2(head, add, prev, next); \ + } \ +} while (0) \ + +#define DL_APPEND_ELEM(head, el, add) \ + DL_APPEND_ELEM2(head, el, add, prev, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef DL_INSERT_INORDER2 +#define DL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + if ((head) == NULL) { \ + (add)->prev = (add); \ + (add)->next = NULL; \ + (head) = (add); \ + } else if ((cmp(head, add)) >= 0) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((head)->next && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->prev = (head); \ + (add)->next = (head)->next; \ + (head)->next = (add); \ + UTLIST_RS(head); \ + if ((add)->next) { \ + (add)->next->prev = (add); \ + } else { \ + (head)->prev = (add); \ + } \ + } \ +} while (0) +#endif /* NO_DECLTYPE */ + +/****************************************************************************** + * circular doubly linked list macros * + *****************************************************************************/ +#define CDL_APPEND(head,add) \ + CDL_APPEND2(head,add,prev,next) + +#define CDL_APPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (add)->prev->next = (add); \ + } else { \ + (add)->prev = (add); \ + (add)->next = (add); \ + (head) = (add); \ + } \ +} while (0) + +#define CDL_PREPEND(head,add) \ + CDL_PREPEND2(head,add,prev,next) + +#define CDL_PREPEND2(head,add,prev,next) \ +do { \ + if (head) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (head)->prev = (add); \ + (add)->prev->next = (add); \ + } else { \ + (add)->prev = (add); \ + (add)->next = (add); \ + } \ + (head) = (add); \ +} while (0) + +#define CDL_INSERT_INORDER(head,add,cmp) \ + CDL_INSERT_INORDER2(head,add,cmp,prev,next) + +#define CDL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + LDECLTYPE(head) _tmp; \ + if (head) { \ + CDL_LOWER_BOUND2(head, _tmp, add, cmp, next); \ + CDL_APPEND_ELEM2(head, _tmp, add, prev, next); \ + } else { \ + (head) = (add); \ + (head)->next = (head); \ + (head)->prev = (head); \ + } \ +} while (0) + +#define CDL_LOWER_BOUND(head,elt,like,cmp) \ + CDL_LOWER_BOUND2(head,elt,like,cmp,next) + +#define CDL_LOWER_BOUND2(head,elt,like,cmp,next) \ +do { \ + if ((head) == NULL || (cmp(head, like)) >= 0) { \ + (elt) = NULL; \ + } else { \ + for ((elt) = (head); (elt)->next != (head); (elt) = (elt)->next) { \ + if ((cmp((elt)->next, like)) >= 0) { \ + break; \ + } \ + } \ + } \ +} while (0) + +#define CDL_DELETE(head,del) \ + CDL_DELETE2(head,del,prev,next) + +#define CDL_DELETE2(head,del,prev,next) \ +do { \ + if (((head)==(del)) && ((head)->next == (head))) { \ + (head) = NULL; \ + } else { \ + (del)->next->prev = (del)->prev; \ + (del)->prev->next = (del)->next; \ + if ((del) == (head)) (head)=(del)->next; \ + } \ +} while (0) + +#define CDL_COUNT(head,el,counter) \ + CDL_COUNT2(head,el,counter,next) \ + +#define CDL_COUNT2(head, el, counter,next) \ +do { \ + (counter) = 0; \ + CDL_FOREACH2(head,el,next) { ++(counter); } \ +} while (0) + +#define CDL_FOREACH(head,el) \ + CDL_FOREACH2(head,el,next) + +#define CDL_FOREACH2(head,el,next) \ + for ((el)=(head);el;(el)=(((el)->next==(head)) ? NULL : (el)->next)) + +#define CDL_FOREACH_SAFE(head,el,tmp1,tmp2) \ + CDL_FOREACH_SAFE2(head,el,tmp1,tmp2,prev,next) + +#define CDL_FOREACH_SAFE2(head,el,tmp1,tmp2,prev,next) \ + for ((el) = (head), (tmp1) = (head) ? (head)->prev : NULL; \ + (el) && ((tmp2) = (el)->next, 1); \ + (el) = ((el) == (tmp1) ? NULL : (tmp2))) + +#define CDL_SEARCH_SCALAR(head,out,field,val) \ + CDL_SEARCH_SCALAR2(head,out,field,val,next) + +#define CDL_SEARCH_SCALAR2(head,out,field,val,next) \ +do { \ + CDL_FOREACH2(head,out,next) { \ + if ((out)->field == (val)) break; \ + } \ +} while (0) + +#define CDL_SEARCH(head,out,elt,cmp) \ + CDL_SEARCH2(head,out,elt,cmp,next) + +#define CDL_SEARCH2(head,out,elt,cmp,next) \ +do { \ + CDL_FOREACH2(head,out,next) { \ + if ((cmp(out,elt))==0) break; \ + } \ +} while (0) + +#define CDL_REPLACE_ELEM2(head, el, add, prev, next) \ +do { \ + assert((head) != NULL); \ + assert((el) != NULL); \ + assert((add) != NULL); \ + if ((el)->next == (el)) { \ + (add)->next = (add); \ + (add)->prev = (add); \ + (head) = (add); \ + } else { \ + (add)->next = (el)->next; \ + (add)->prev = (el)->prev; \ + (add)->next->prev = (add); \ + (add)->prev->next = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } \ + } \ +} while (0) + +#define CDL_REPLACE_ELEM(head, el, add) \ + CDL_REPLACE_ELEM2(head, el, add, prev, next) + +#define CDL_PREPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el); \ + (add)->prev = (el)->prev; \ + (el)->prev = (add); \ + (add)->prev->next = (add); \ + if ((head) == (el)) { \ + (head) = (add); \ + } \ + } else { \ + CDL_APPEND2(head, add, prev, next); \ + } \ +} while (0) + +#define CDL_PREPEND_ELEM(head, el, add) \ + CDL_PREPEND_ELEM2(head, el, add, prev, next) + +#define CDL_APPEND_ELEM2(head, el, add, prev, next) \ +do { \ + if (el) { \ + assert((head) != NULL); \ + assert((add) != NULL); \ + (add)->next = (el)->next; \ + (add)->prev = (el); \ + (el)->next = (add); \ + (add)->next->prev = (add); \ + } else { \ + CDL_PREPEND2(head, add, prev, next); \ + } \ +} while (0) + +#define CDL_APPEND_ELEM(head, el, add) \ + CDL_APPEND_ELEM2(head, el, add, prev, next) + +#ifdef NO_DECLTYPE +/* Here are VS2008 / NO_DECLTYPE replacements for a few functions */ + +#undef CDL_INSERT_INORDER2 +#define CDL_INSERT_INORDER2(head,add,cmp,prev,next) \ +do { \ + if ((head) == NULL) { \ + (add)->prev = (add); \ + (add)->next = (add); \ + (head) = (add); \ + } else if ((cmp(head, add)) >= 0) { \ + (add)->prev = (head)->prev; \ + (add)->next = (head); \ + (add)->prev->next = (add); \ + (head)->prev = (add); \ + (head) = (add); \ + } else { \ + char *_tmp = (char*)(head); \ + while ((char*)(head)->next != _tmp && (cmp((head)->next, add)) < 0) { \ + (head) = (head)->next; \ + } \ + (add)->prev = (head); \ + (add)->next = (head)->next; \ + (add)->next->prev = (add); \ + (head)->next = (add); \ + UTLIST_RS(head); \ + } \ +} while (0) +#endif /* NO_DECLTYPE */ + +#endif /* UTLIST_H */ diff --git a/tools/sdk/esp32s2/include/coap/port/include/coap3/coap.h b/tools/sdk/esp32s2/include/coap/port/include/coap3/coap.h new file mode 100644 index 00000000000..c69d2734b3a --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/port/include/coap3/coap.h @@ -0,0 +1,51 @@ +/* Modify head file implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * define operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef _COAP_H_ +#define _COAP_H_ + +#ifdef __cplusplus +extern "C" { +#endif + +#include "coap3/libcoap.h" + +#include "coap3/coap_forward_decls.h" +#include "coap3/address.h" +#include "coap3/async.h" +#include "coap3/block.h" +#include "coap3/coap_cache.h" +#include "coap3/coap_dtls.h" +#include "coap3/coap_event.h" +#include "coap3/coap_io.h" +#include "coap3/coap_time.h" +#include "coap3/coap_debug.h" +#include "coap3/encode.h" +#include "coap3/mem.h" +#include "coap3/net.h" +#include "coap3/option.h" +#include "coap3/pdu.h" +#include "coap3/coap_prng.h" +#include "coap3/resource.h" +#include "coap3/str.h" +#include "coap3/subscribe.h" +#include "coap3/uri.h" + +#ifdef __cplusplus +} +#endif + +#endif /* _COAP_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/port/include/coap_config.h b/tools/sdk/esp32s2/include/coap/port/include/coap_config.h new file mode 100644 index 00000000000..1efa37aa7f7 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/port/include/coap_config.h @@ -0,0 +1,42 @@ +/* + * libcoap configure implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * configure operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef _CONFIG_H_ +#define _CONFIG_H_ + +/* Always enabled in ESP-IDF */ +#ifndef WITH_POSIX +#define WITH_POSIX +#endif + +#include "coap_config_posix.h" + +#define HAVE_STDIO_H +#define HAVE_ASSERT_H + +#define PACKAGE_STRING PACKAGE_NAME PACKAGE_VERSION + +/* it's just provided by libc. i hope we don't get too many of those, as + * actually we'd need autotools again to find out what environment we're + * building in */ +#define HAVE_STRNLEN 1 + +#define HAVE_LIMITS_H + +#define COAP_RESOURCES_NOHASH + +#endif /* _CONFIG_H_ */ diff --git a/tools/sdk/esp32s2/include/coap/port/include/coap_config_posix.h b/tools/sdk/esp32s2/include/coap/port/include/coap_config_posix.h new file mode 100644 index 00000000000..b24335ad156 --- /dev/null +++ b/tools/sdk/esp32s2/include/coap/port/include/coap_config_posix.h @@ -0,0 +1,60 @@ +/* + * libcoap configure implementation for ESP32 platform. + * + * Uses libcoap software implementation for failover when concurrent + * configure operations are in use. + * + * coap.h -- main header file for CoAP stack of libcoap + * + * Copyright (C) 2010-2012,2015-2016 Olaf Bergmann + * 2015 Carsten Schoenert + * + * Copyright 2015-2016 Espressif Systems (Shanghai) PTE LTD + * + * This file is part of the CoAP library libcoap. Please see README for terms + * of use. + */ + +#ifndef COAP_CONFIG_POSIX_H_ +#define COAP_CONFIG_POSIX_H_ + +#ifdef WITH_POSIX + +#include +#include + +#define HAVE_SYS_SOCKET_H +#define HAVE_MALLOC +#define HAVE_ARPA_INET_H +#define HAVE_TIME_H +#define HAVE_NETDB_H +#define HAVE_NETINET_IN_H +#define HAVE_STRUCT_CMSGHDR +#define COAP_DISABLE_TCP 0 + +#define ipi_spec_dst ipi_addr +struct in6_pktinfo { + struct in6_addr ipi6_addr; /* src/dst IPv6 address */ + unsigned int ipi6_ifindex; /* send/recv interface index */ +}; +#define IN6_IS_ADDR_V4MAPPED(a) \ + ((((__const uint32_t *) (a))[0] == 0) \ + && (((__const uint32_t *) (a))[1] == 0) \ + && (((__const uint32_t *) (a))[2] == htonl (0xffff))) + +/* As not defined, just need to define is as something innocuous */ +#define IPV6_PKTINFO IPV6_CHECKSUM + +#define PACKAGE_NAME "libcoap-posix" +#define PACKAGE_VERSION "?" + +#ifdef CONFIG_MBEDTLS_TLS_ENABLED +#define HAVE_MBEDTLS +#endif /* CONFIG_MBEDTLS_TLS_ENABLED */ +#define COAP_CONSTRAINED_STACK 1 +#define ESPIDF_VERSION + +#define gai_strerror(x) "gai_strerror() not supported" + +#endif /* WITH_POSIX */ +#endif /* COAP_CONFIG_POSIX_H_ */ diff --git a/tools/sdk/esp32s2/include/config/sdkconfig.h b/tools/sdk/esp32s2/include/config/sdkconfig.h index d4a83be06f9..48660a5006f 100644 --- a/tools/sdk/esp32s2/include/config/sdkconfig.h +++ b/tools/sdk/esp32s2/include/config/sdkconfig.h @@ -96,35 +96,6 @@ #define CONFIG_COMPILER_WARN_WRITE_STRINGS 1 #define CONFIG_APPTRACE_DEST_NONE 1 #define CONFIG_APPTRACE_LOCK_ENABLE 1 -#define CONFIG_BTDM_CTRL_BR_EDR_SCO_DATA_PATH_EFF 0 -#define CONFIG_BTDM_CTRL_PCM_ROLE_EFF 0 -#define CONFIG_BTDM_CTRL_PCM_POLAR_EFF 0 -#define CONFIG_BTDM_CTRL_BLE_MAX_CONN_EFF 0 -#define CONFIG_BTDM_CTRL_BR_EDR_MAX_ACL_CONN_EFF 0 -#define CONFIG_BTDM_CTRL_BR_EDR_MAX_SYNC_CONN_EFF 0 -#define CONFIG_BTDM_CTRL_PINNED_TO_CORE 0 -#define CONFIG_BTDM_BLE_SLEEP_CLOCK_ACCURACY_INDEX_EFF 1 -#define CONFIG_BT_CTRL_MODE_EFF 1 -#define CONFIG_BT_CTRL_BLE_MAX_ACT 10 -#define CONFIG_BT_CTRL_BLE_MAX_ACT_EFF 10 -#define CONFIG_BT_CTRL_BLE_STATIC_ACL_TX_BUF_NB 0 -#define CONFIG_BT_CTRL_PINNED_TO_CORE 0 -#define CONFIG_BT_CTRL_HCI_TL 1 -#define CONFIG_BT_CTRL_ADV_DUP_FILT_MAX 30 -#define CONFIG_BT_CTRL_HW_CCA_EFF 0 -#define CONFIG_BT_CTRL_DFT_TX_POWER_LEVEL_EFF 0 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_FLOW_CTRL_SUPP 1 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_FLOW_CTRL_NUM 100 -#define CONFIG_BT_CTRL_BLE_ADV_REPORT_DISCARD_THRSHOLD 20 -#define CONFIG_BT_CTRL_BLE_SCAN_DUPL 1 -#define CONFIG_BT_CTRL_SCAN_DUPL_TYPE 0 -#define CONFIG_BT_CTRL_SCAN_DUPL_CACHE_SIZE 100 -#define CONFIG_BT_CTRL_COEX_PHY_CODED_TX_RX_TLIM_EFF 0 -#define CONFIG_BT_CTRL_SLEEP_MODE_EFF 0 -#define CONFIG_BT_CTRL_SLEEP_CLOCK_EFF 0 -#define CONFIG_BT_CTRL_HCI_TL_EFF 1 -#define CONFIG_BT_RESERVE_DRAM 0x0 -#define CONFIG_BT_NIMBLE_USE_ESP_TIMER 1 #define CONFIG_COAP_MBEDTLS_PSK 1 #define CONFIG_COAP_LOG_DEFAULT_LEVEL 0 #define CONFIG_ADC_DISABLE_DAC 1 @@ -181,7 +152,6 @@ #define CONFIG_ESP32S2_UNIVERSAL_MAC_ADDRESSES 2 #define CONFIG_ESP_SLEEP_RTC_BUS_ISO_WORKAROUND 1 #define CONFIG_ESP_IPC_TASK_STACK_SIZE 1024 -#define CONFIG_LCD_PERIPH_CLK_SRC_PLL160M 1 #define CONFIG_LCD_PANEL_IO_FORMAT_BUF_SIZE 32 #define CONFIG_ESP_NETIF_IP_LOST_TIMER_INTERVAL 120 #define CONFIG_ESP_NETIF_TCPIP_LWIP 1 @@ -193,8 +163,11 @@ #define CONFIG_ESP_SYSTEM_SINGLE_CORE_MODE 1 #define CONFIG_ESP_SYSTEM_RTC_FAST_MEM_AS_HEAP_DEPCHECK 1 #define CONFIG_ESP_SYSTEM_ALLOW_RTC_FAST_MEM_AS_HEAP 1 +#define CONFIG_ESP_SYSTEM_MEMPROT_DEPCHECK 1 #define CONFIG_ESP_SYSTEM_MEMPROT_FEATURE 1 #define CONFIG_ESP_SYSTEM_MEMPROT_FEATURE_LOCK 1 +#define CONFIG_ESP_SYSTEM_MEMPROT_CPU_PREFETCH_PAD_SIZE 16 +#define CONFIG_ESP_SYSTEM_MEMPROT_MEM_ALIGN_SIZE 4 #define CONFIG_ESP_SYSTEM_EVENT_QUEUE_SIZE 32 #define CONFIG_ESP_SYSTEM_EVENT_TASK_STACK_SIZE 2048 #define CONFIG_ESP_MAIN_TASK_STACK_SIZE 4096 @@ -211,6 +184,7 @@ #define CONFIG_ESP_TASK_WDT 1 #define CONFIG_ESP_TASK_WDT_PANIC 1 #define CONFIG_ESP_TASK_WDT_TIMEOUT_S 5 +#define CONFIG_ESP_SYSTEM_CHECK_INT_LEVEL_4 1 #define CONFIG_ESP_TIME_FUNCS_USE_RTC_TIMER 1 #define CONFIG_ESP_TIME_FUNCS_USE_ESP_TIMER 1 #define CONFIG_ESP_TIMER_TASK_STACK_SIZE 4096 @@ -320,7 +294,6 @@ #define CONFIG_LWIP_DHCPS_MAX_STATION_NUM 8 #define CONFIG_LWIP_IPV6 1 #define CONFIG_LWIP_IPV6_NUM_ADDRESSES 3 -#define CONFIG_LWIP_IPV6_RDNSS_MAX_DNS_SERVERS 0 #define CONFIG_LWIP_NETIF_LOOPBACK 1 #define CONFIG_LWIP_LOOPBACK_MAX_PBUFS 8 #define CONFIG_LWIP_MAX_ACTIVE_TCP 16 @@ -602,5 +575,5 @@ #define CONFIG_USB_MSC_BUFSIZE CONFIG_TINYUSB_MSC_BUFSIZE #define CONFIG_USB_MSC_ENABLED CONFIG_TINYUSB_MSC_ENABLED #define CONFIG_WARN_WRITE_STRINGS CONFIG_COMPILER_WARN_WRITE_STRINGS -#define CONFIG_ARDUINO_IDF_COMMIT "61299f879e" +#define CONFIG_ARDUINO_IDF_COMMIT "3e370c4296" #define CONFIG_ARDUINO_IDF_BRANCH "master" diff --git a/tools/sdk/esp32s2/include/driver/include/driver/i2s.h b/tools/sdk/esp32s2/include/driver/include/driver/i2s.h index 0c8a43db0d5..aa649ed479c 100644 --- a/tools/sdk/esp32s2/include/driver/include/driver/i2s.h +++ b/tools/sdk/esp32s2/include/driver/include/driver/i2s.h @@ -17,7 +17,7 @@ #include "driver/periph_ctrl.h" #include "esp_intr_alloc.h" -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_ADC #include "driver/adc.h" #endif @@ -221,7 +221,7 @@ esp_err_t i2s_set_pdm_tx_up_sample(i2s_port_t i2s_num, const i2s_pdm_tx_upsample * - ESP_OK Success * - ESP_ERR_INVALID_ARG Parameter error * - ESP_ERR_NO_MEM Out of memory - * - ESP_ERR_NOT_FOUND I2S port is not found or has been installed by others (e.g. LCD i80) + * - ESP_ERR_INVALID_STATE Current I2S port is in use */ esp_err_t i2s_driver_install(i2s_port_t i2s_num, const i2s_config_t *i2s_config, int queue_size, void *i2s_queue); @@ -355,7 +355,7 @@ esp_err_t i2s_stop(i2s_port_t i2s_num); * * @param i2s_num I2S port number * -* @return + * @return * - ESP_OK Success * - ESP_ERR_INVALID_ARG Parameter error */ @@ -430,7 +430,7 @@ esp_err_t i2s_set_clk(i2s_port_t i2s_num, uint32_t rate, uint32_t bits_cfg, i2s_ */ float i2s_get_clk(i2s_port_t i2s_num); -#if SOC_I2S_SUPPORTS_ADC_DAC +#if SOC_I2S_SUPPORTS_ADC /** * @brief Set built-in ADC mode for I2S DMA, this function will initialize ADC pad, * and set ADC parameters. @@ -466,7 +466,9 @@ esp_err_t i2s_adc_enable(i2s_port_t i2s_num); * - ESP_ERR_INVALID_STATE Driver state error */ esp_err_t i2s_adc_disable(i2s_port_t i2s_num); +#endif // SOC_I2S_SUPPORTS_ADC +#if SOC_I2S_SUPPORTS_DAC /** * @brief Set I2S dac mode, I2S built-in DAC is disabled by default * @@ -481,7 +483,7 @@ esp_err_t i2s_adc_disable(i2s_port_t i2s_num); * - ESP_ERR_INVALID_ARG Parameter error */ esp_err_t i2s_set_dac_mode(i2s_dac_mode_t dac_mode); -#endif //SOC_I2S_SUPPORTS_ADC_DAC +#endif //SOC_I2S_SUPPORTS_DAC #ifdef __cplusplus diff --git a/tools/sdk/esp32s2/include/driver/include/driver/mcpwm.h b/tools/sdk/esp32s2/include/driver/include/driver/mcpwm.h index 20b41ffd32a..2a4e825f77c 100644 --- a/tools/sdk/esp32s2/include/driver/include/driver/mcpwm.h +++ b/tools/sdk/esp32s2/include/driver/include/driver/mcpwm.h @@ -130,11 +130,30 @@ typedef enum { * @brief MCPWM select sync signal input */ typedef enum { - MCPWM_SELECT_SYNC0 = 4, /*!