diff --git a/components/bt/CMakeLists.txt b/components/bt/CMakeLists.txt index 0ee0335b20..52def1a1db 100644 --- a/components/bt/CMakeLists.txt +++ b/components/bt/CMakeLists.txt @@ -910,17 +910,21 @@ if(CONFIG_BT_ENABLED) endif() if(CONFIG_IDF_TARGET_ESP32C6) add_prebuilt_library(libble_app - "${CMAKE_CURRENT_LIST_DIR}/controller/lib_esp32c6/esp32c6-bt-lib/esp32c6/libble_app.a") + "${CMAKE_CURRENT_LIST_DIR}/controller/lib_esp32c6/esp32c6-bt-lib/esp32c6/libble_app.a" + REQUIRES esp_phy) elseif(CONFIG_IDF_TARGET_ESP32C61) add_prebuilt_library(libble_app - "${CMAKE_CURRENT_LIST_DIR}/controller/lib_esp32c6/esp32c6-bt-lib/esp32c61/libble_app.a") + "${CMAKE_CURRENT_LIST_DIR}/controller/lib_esp32c6/esp32c6-bt-lib/esp32c61/libble_app.a" + REQUIRES esp_phy) else() if(CONFIG_BT_CTRL_RUN_IN_FLASH_ONLY AND CONFIG_IDF_TARGET_ESP32C2) add_prebuilt_library(libble_app - "controller/lib_${target_name}/${target_name}-bt-lib/libble_app_flash.a") + "controller/lib_${target_name}/${target_name}-bt-lib/libble_app_flash.a" + REQUIRES esp_phy) else() add_prebuilt_library(libble_app - "controller/lib_${target_name}/${target_name}-bt-lib/libble_app.a") + "controller/lib_${target_name}/${target_name}-bt-lib/libble_app.a" + REQUIRES esp_phy) endif() endif() target_link_libraries(${COMPONENT_LIB} PRIVATE libble_app) diff --git a/components/bt/common/Kconfig.in b/components/bt/common/Kconfig.in index 74b201b12a..fb17bbb9ff 100644 --- a/components/bt/common/Kconfig.in +++ b/components/bt/common/Kconfig.in @@ -9,54 +9,88 @@ config BT_ALARM_MAX_NUM config BT_BLE_LOG_SPI_OUT_ENABLED bool "Output ble logs to SPI bus (Experimental)" default n + select SPI_MASTER_IN_IRAM help Output ble logs to SPI bus -config BT_BLE_LOG_SPI_OUT_QUEUE_SIZE - int "Number of ble log async SPI output queues" +config BT_BLE_LOG_SPI_OUT_UL_TASK_BUF_SIZE + int "SPI transaction buffer size for upper layer task logs" depends on BT_BLE_LOG_SPI_OUT_ENABLED - default 4 + default 512 help - The number of ble log async SPI output queues + SPI transaction buffer size for upper layer task logs. + There will be 2 SPI DMA buffers with the same size. -config BT_BLE_LOG_SPI_OUT_TRANS_BUF_SIZE - int "Size of ble log async SPI output transaction buffer size" +config BT_BLE_LOG_SPI_OUT_HCI_ENABLED + bool "Enable HCI log output to SPI" depends on BT_BLE_LOG_SPI_OUT_ENABLED - default 2048 + default n help - The size of ble log async SPI output transaction buffer size + Enable logging of HCI packets to the SPI bus when BLE SPI log output is enabled. + +config BT_BLE_LOG_SPI_OUT_HOST_ENABLED + bool "Enable Host log output to SPI" + depends on BT_BLE_LOG_SPI_OUT_ENABLED + default n + help + This configuration applies to the logs of both Bluedroid Host and NimBLE Host. + When BLE SPI log output is enabled, this option allows host logs to be transmitted via SPI. + +config BT_BLE_LOG_SPI_OUT_LL_ENABLED + bool "Enable Controller log output to SPI" + depends on BT_BLE_LOG_SPI_OUT_ENABLED + depends on BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + default n + help + Enable controller log output to SPI bus. + +config BT_BLE_LOG_SPI_OUT_LL_TASK_BUF_SIZE + int "SPI transaction buffer size for lower layer task logs" + depends on BT_BLE_LOG_SPI_OUT_LL_ENABLED + default 1024 + help + SPI transaction buffer size for upper layer task logs. + There will be 2 SPI DMA buffers with the same size. + +config BT_BLE_LOG_SPI_OUT_LL_ISR_BUF_SIZE + int "SPI transaction buffer size for lower layer ISR logs" + depends on BT_BLE_LOG_SPI_OUT_LL_ENABLED + default 512 + help + SPI transaction buffer size for upper layer ISR logs. + There will be 2 SPI DMA buffers with the same size. config BT_BLE_LOG_SPI_OUT_MOSI_IO_NUM int "GPIO number of SPI MOSI" depends on BT_BLE_LOG_SPI_OUT_ENABLED default 0 help - GPIO number of SPI MOSI + GPIO number of SPI MOSI config BT_BLE_LOG_SPI_OUT_SCLK_IO_NUM int "GPIO number of SPI SCLK" depends on BT_BLE_LOG_SPI_OUT_ENABLED default 1 help - GPIO number of SPI SCLK + GPIO number of SPI SCLK config BT_BLE_LOG_SPI_OUT_CS_IO_NUM int "GPIO number of SPI CS" depends on BT_BLE_LOG_SPI_OUT_ENABLED default 2 help - GPIO number of SPI CS + GPIO number of SPI CS config BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED bool "Enable ble log & logic analyzer log time sync" depends on BT_BLE_LOG_SPI_OUT_ENABLED default y help - Enable ble log & logic analyzer log time sync + Enable ble log & logic analyzer log time sync config BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM int "GPIO number of SYNC IO" depends on BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED default 3 help - GPIO number of SYNC IO + GPIO number of SYNC IO diff --git a/components/bt/common/ble_log/ble_log_spi_out.c b/components/bt/common/ble_log/ble_log_spi_out.c index b9e4bf02f8..992df1cb7c 100644 --- a/components/bt/common/ble_log/ble_log_spi_out.c +++ b/components/bt/common/ble_log/ble_log_spi_out.c @@ -8,185 +8,575 @@ #if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED // Private defines +#define BLE_LOG_TAG "BLE_LOG" #define SPI_OUT_BUS SPI2_HOST -#define SPI_OUT_TAIL 0xAA +#define SPI_OUT_MAX_TRANSFER_SIZE 10240 +#define SPI_OUT_FRAME_HEAD_LEN 4 +#define SPI_OUT_FRAME_TAIL 0xAA +#define SPI_OUT_FRAME_TAIL_LEN 1 +#define SPI_OUT_FRAME_OVERHEAD (SPI_OUT_FRAME_HEAD_LEN + SPI_OUT_FRAME_TAIL_LEN) +#define SPI_OUT_RECYCLE_TIMEOUT 1000 +#define SPI_OUT_TRANS_CB_FLAG_AVAILABLE 0 +#define SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE 1 +#define SPI_OUT_TRANS_CB_FLAG_IN_QUEUE 2 #define SPI_OUT_FLUSHOUT_TIMEOUT (1000 * 1000) -#define SPI_OUT_TS_SYNC_TIMEOUT (1000 * 1000) - -// Private typedefs -typedef struct spi_out_trans { - spi_transaction_t trans; - struct spi_out_trans *next; -} spi_out_trans_t; - -// Private variables -static spi_device_handle_t spi_handle = NULL; -static spi_out_trans_t *trans_head = NULL; -static SemaphoreHandle_t mutex_handle = NULL; -static bool spi_out_inited = false; -static esp_timer_handle_t flushout_timer_handle = NULL; -static uint32_t loss_frame_cnt = 0; +#define SPI_OUT_PACKET_LOSS_UL 0 +#define SPI_OUT_PACKET_LOSS_LL_TASK 1 +#define SPI_OUT_PACKET_LOSS_LL_ISR 2 +#define SPI_OUT_PACKET_LOSS_FRAME_SIZE 6 +#define BLE_LOG_INTERFACE_FLAG_IN_ISR (1 << 3) #if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED -static bool sync_io_level = false; -static esp_timer_handle_t ts_sync_timer_handle = NULL; +#define SPI_OUT_TS_SYNC_TIMEOUT (1000 * 1000) #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED -// Private function declarations -static void spi_out_init_trans(void); -static void spi_out_deinit_trans(void); -static void spi_out_recycle_trans(uint32_t ms_to_wait); -static void spi_out_append_trans(void); -static int spi_out_write(const uint8_t *addr, uint16_t len); -static void esp_timer_cb_flushout(void); -static void esp_timer_cb_ts_sync(void); +// Private typedefs +typedef struct { + // CRITICAL: 0 for available, 1 for need queue (ISR), 2 for in queue + // This flag is for multithreading, must be a word, do not modify + volatile uint32_t flag; + uint16_t buf_size; + uint16_t length; + spi_transaction_t trans; +} spi_out_trans_cb_t; + +typedef struct { + spi_out_trans_cb_t *trans_cb[2]; + uint8_t trans_cb_idx; + uint8_t frame_cnt; + uint32_t bytes_loss_cnt; + uint8_t trans_loss_cnt; +} spi_out_log_cb_t; + +// Private variables +static bool spi_out_inited = false; +static spi_device_handle_t spi_handle = NULL; +static bool timer_enabled = true; + +static bool ul_log_inited = false; +static SemaphoreHandle_t ul_log_mutex = NULL; +static spi_out_log_cb_t *ul_log_cb = NULL; +static esp_timer_handle_t ul_log_flushout_timer = NULL; + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED +static bool ll_log_inited = false; +static bool ll_log_need_flushout = false; +static spi_out_log_cb_t *ll_task_log_cb = NULL; +static spi_out_log_cb_t *ll_isr_log_cb = NULL; +static esp_timer_handle_t ll_log_flushout_timer = NULL; +#endif // BT_BLE_LOG_SPI_OUT_LL_ENABLED #if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED -#if defined(CONFIG_IDF_TARGET_ESP32H2) || defined(CONFIG_IDF_TARGET_ESP32C6) +static bool ts_sync_inited = false; +static bool sync_io_level = false; +static esp_timer_handle_t ts_sync_timer = NULL; +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED + +// Extern function declarations +extern void esp_panic_handler_feed_wdts(void); + +// Private function declarations +static int spi_out_init_trans(spi_out_trans_cb_t **trans_cb, uint16_t buf_size); +static void spi_out_deinit_trans(spi_out_trans_cb_t **trans_cb); +static void spi_out_tx_done_cb(spi_transaction_t *ret_trans); +static inline int spi_out_append_trans(spi_out_trans_cb_t *trans_cb); + +static int spi_out_log_cb_init(spi_out_log_cb_t **log_cb, uint16_t buf_size); +static void spi_out_log_cb_deinit(spi_out_log_cb_t **log_cb); +static inline int spi_out_log_cb_check_trans(spi_out_log_cb_t *log_cb, uint16_t len); +static inline void spi_out_log_cb_append_trans(spi_out_log_cb_t *log_cb, bool in_isr); +static inline void spi_out_log_cb_flush_trans(spi_out_log_cb_t *log_cb); +static void spi_out_log_cb_write(spi_out_log_cb_t *log_cb, const uint8_t *addr, uint16_t len, \ + const uint8_t *addr_append, uint16_t len_append, uint8_t source); +static inline void spi_out_log_cb_write_packet_loss(spi_out_log_cb_t *log_cb, uint8_t flag); +static void spi_out_log_cb_dump(spi_out_log_cb_t *log_cb); + +static int spi_out_ul_log_init(void); +static void spi_out_ul_log_deinit(void); +static void esp_timer_cb_ul_log_flushout(void); + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED +static int spi_out_ll_log_init(void); +static void spi_out_ll_log_deinit(void); +static void spi_out_ll_log_ev_proc(void); +static void esp_timer_cb_ll_log_flushout(void); + +#if defined(CONFIG_IDF_TARGET_ESP32H2) || defined(CONFIG_IDF_TARGET_ESP32C6) || defined(CONFIG_IDF_TARGET_ESP32C5) ||\ + defined(CONFIG_IDF_TARGET_ESP32C61) || defined(CONFIG_IDF_TARGET_ESP32H21) +extern void r_ble_log_simple_put_ev(void); +#define BLE_LOG_LL_PUT_EV r_ble_log_simple_put_ev() +#elif defined(CONFIG_IDF_TARGET_ESP32C2) +extern void ble_log_simple_put_ev(void); +#define BLE_LOG_LL_PUT_EV ble_log_simple_put_ev() +#else +#define BLE_LOG_LL_PUT_EV +#endif + +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + +#if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED +static int spi_out_ts_sync_init(void); +static void spi_out_ts_sync_deinit(void); +static void esp_timer_cb_ts_sync(void); + +#if defined(CONFIG_IDF_TARGET_ESP32H2) || defined(CONFIG_IDF_TARGET_ESP32C6) || defined(CONFIG_IDF_TARGET_ESP32C5) ||\ + defined(CONFIG_IDF_TARGET_ESP32C61) || defined(CONFIG_IDF_TARGET_ESP32H21) extern uint32_t r_ble_lll_timer_current_tick_get(void); -#endif // CONFIG_IDF_TARGET_ESP32H2 || CONFIG_IDF_TARGET_ESP32C6 -#if defined(CONFIG_IDF_TARGET_ESP32C2) +#define SPI_OUT_GET_LC_TIME r_ble_lll_timer_current_tick_get() +#elif defined(CONFIG_IDF_TARGET_ESP32C2) extern uint32_t r_os_cputime_get32(void); -#endif // CONFIG_IDF_TARGET_ESP32C2 +#define SPI_OUT_GET_LC_TIME r_os_cputime_get32() +#else +#define SPI_OUT_GET_LC_TIME 0 +#endif + #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED // Private functions -static void spi_out_init_trans(void) +static int spi_out_init_trans(spi_out_trans_cb_t **trans_cb, uint16_t buf_size) { - for (int i = 0; i < CONFIG_BT_BLE_LOG_SPI_OUT_QUEUE_SIZE; i++) { - // Allocate memory for SPI transaction - uint8_t *buf = (uint8_t *)spi_bus_dma_memory_alloc(SPI_OUT_BUS, CONFIG_BT_BLE_LOG_SPI_OUT_TRANS_BUF_SIZE, 0); - assert(buf); - - // Initialize new trans - spi_out_trans_t *new_trans = (spi_out_trans_t *)malloc(sizeof(spi_out_trans_t)); - assert(new_trans); - memset(new_trans, 0, sizeof(spi_out_trans_t)); - new_trans->trans.tx_buffer = buf; - new_trans->trans.length = 0; - - // Append new trans to free trans list - new_trans->next = trans_head; - trans_head = new_trans; + // Memory allocations + *trans_cb = (spi_out_trans_cb_t *)malloc(sizeof(spi_out_trans_cb_t)); + if (!(*trans_cb)) { + return -1; } + uint8_t *buf = (uint8_t *)spi_bus_dma_memory_alloc(SPI_OUT_BUS, (size_t)buf_size, 0); + if (!buf) { + free(*trans_cb); + return -1; + } + + // Initialization + memset(*trans_cb, 0, sizeof(spi_out_trans_cb_t)); + (*trans_cb)->buf_size = buf_size; + (*trans_cb)->trans.tx_buffer = buf; + return 0; +} + +static void spi_out_deinit_trans(spi_out_trans_cb_t **trans_cb) +{ + if (!(*trans_cb)) { + return; + } + + free((uint8_t *)(*trans_cb)->trans.tx_buffer); + free(*trans_cb); + *trans_cb = NULL; return; } -static void spi_out_deinit_trans(void) +IRAM_ATTR static void spi_out_tx_done_cb(spi_transaction_t *ret_trans) { - // Wait up to QUEUE_SIZE * 100 ms for all transactions to complete and be recycled - spi_out_recycle_trans(100); - - // Release memory - spi_out_trans_t *next; - while (trans_head != NULL) { - next = trans_head->next; - free((uint8_t *)trans_head->trans.tx_buffer); - free(trans_head); - trans_head = next; - } - trans_head = NULL; - return; + spi_out_trans_cb_t *trans_cb = __containerof(ret_trans, spi_out_trans_cb_t, trans); + trans_cb->length = 0; + trans_cb->flag = SPI_OUT_TRANS_CB_FLAG_AVAILABLE; } -// CRITICAL: Do not recycle trans when trans_head is not empty! -IRAM_ATTR static void spi_out_recycle_trans(uint32_t ms_to_wait) +IRAM_ATTR static inline int spi_out_append_trans(spi_out_trans_cb_t *trans_cb) { - // Try to recycle transaction - spi_transaction_t *ret_trans; - spi_out_trans_t *recycled_trans; - while (ESP_OK == spi_device_get_trans_result(spi_handle, &ret_trans, pdMS_TO_TICKS(ms_to_wait))) { - recycled_trans = __containerof(ret_trans, spi_out_trans_t, trans); - recycled_trans->next = trans_head; - trans_head = recycled_trans; - trans_head->trans.length = 0; - trans_head->trans.rxlength = 0; + if (trans_cb->flag != SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE) { + return -1; + } + + // CRITICAL: Length unit conversion from bytes to bits + trans_cb->trans.length = trans_cb->length * 8; + trans_cb->trans.rxlength = 0; + if (spi_device_queue_trans(spi_handle, &(trans_cb->trans), 0) == ESP_OK) { + trans_cb->flag = SPI_OUT_TRANS_CB_FLAG_IN_QUEUE; + return 0; + } else { + return -1; } } -IRAM_ATTR static void spi_out_append_trans(void) +static int spi_out_log_cb_init(spi_out_log_cb_t **log_cb, uint16_t buf_size) { - // Stop flushout timer - esp_timer_stop(flushout_timer_handle); - - // Transaction head shall not be NULL for appending - if (trans_head) { - // Detach transaction head - spi_out_trans_t *trans_to_append = trans_head; - trans_head = trans_head->next; - trans_to_append->next = NULL; - - // CRITICAL: Length unit conversion from bytes to bits - trans_to_append->trans.length *= 8; - ESP_ERROR_CHECK(spi_device_queue_trans(spi_handle, &trans_to_append->trans, 0)); + // Initialize log control block + *log_cb = (spi_out_log_cb_t *)malloc(sizeof(spi_out_log_cb_t)); + if (!(*log_cb)) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize log control block!"); + return -1; } + memset(*log_cb, 0, sizeof(spi_out_log_cb_t)); - // Try to recycle trans - spi_out_recycle_trans(0); - - // Restart flushout timer - esp_timer_start_once(flushout_timer_handle, SPI_OUT_FLUSHOUT_TIMEOUT); -} - -IRAM_ATTR static int spi_out_write(const uint8_t *addr, uint16_t len) -{ - // Recycle trans if free buffer list is empty - if (!trans_head) { - spi_out_recycle_trans(0); + // Initialize transactions + int ret = 0; + for (uint8_t i = 0; i < 2; i++) { + ret |= spi_out_init_trans(&((*log_cb)->trans_cb[i]), buf_size); } - - // Copy user data to buffer - uint16_t copy_buf_len; - uint16_t data_left_len = len; - uint16_t empty_buf_len = CONFIG_BT_BLE_LOG_SPI_OUT_TRANS_BUF_SIZE - trans_head->trans.length; - while (data_left_len) { - // There shall always be available buffer in free buffer list during write operation - if (!trans_head) { - return -1; - } - - // Copy data to buffer and update length - copy_buf_len = (data_left_len > empty_buf_len) ? empty_buf_len : data_left_len; - memcpy((uint8_t *)trans_head->trans.tx_buffer + trans_head->trans.length, addr + (len - data_left_len), copy_buf_len); - trans_head->trans.length += copy_buf_len; - data_left_len -= copy_buf_len; - - // If buffer is full, append transaction and reset buffer length - if (trans_head->trans.length == CONFIG_BT_BLE_LOG_SPI_OUT_TRANS_BUF_SIZE) { - spi_out_append_trans(); - empty_buf_len = CONFIG_BT_BLE_LOG_SPI_OUT_TRANS_BUF_SIZE; - } + if (ret != 0) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize SPI transactions!"); + spi_out_log_cb_deinit(log_cb); + return -1; } return 0; } -// CRITICAL: This function is called in ESP Timer task -IRAM_ATTR static void esp_timer_cb_flushout(void) +static void spi_out_log_cb_deinit(spi_out_log_cb_t **log_cb) { - // Take semaphore - assert(xSemaphoreTakeRecursive(mutex_handle, portMAX_DELAY) == pdTRUE); - - // Flushout - if (trans_head) { - // Make sure there's enough space for loss frame counter - if (trans_head->next && loss_frame_cnt) { - ble_log_spi_out_write(BLE_LOG_SPI_OUT_SOURCE_LOSS, (uint8_t *)&loss_frame_cnt, sizeof(loss_frame_cnt)); - loss_frame_cnt = 0; - } - if (trans_head->trans.length) { - spi_out_append_trans(); - } - } - else { - // Restart flushout timer - esp_timer_start_once(flushout_timer_handle, SPI_OUT_FLUSHOUT_TIMEOUT); + if (!(*log_cb)) { + return; } - // Release semaphore - xSemaphoreGiveRecursive(mutex_handle); + for (uint8_t i = 0; i < 2; i++) { + if ((*log_cb)->trans_cb[i]) { + spi_out_deinit_trans(&((*log_cb)->trans_cb[i])); + } + } + free(*log_cb); + return; } +IRAM_ATTR static inline int spi_out_log_cb_check_trans(spi_out_log_cb_t *log_cb, uint16_t len) +{ + spi_out_trans_cb_t *trans_cb; + uint16_t frame_len = len + SPI_OUT_FRAME_OVERHEAD; + for (uint8_t i = 0; i < 2; i++) { + trans_cb = log_cb->trans_cb[log_cb->trans_cb_idx]; + if (frame_len > trans_cb->buf_size) { + goto failed; + } + if (trans_cb->flag == SPI_OUT_TRANS_CB_FLAG_AVAILABLE) { + if ((trans_cb->buf_size - trans_cb->length) >= (len + SPI_OUT_FRAME_OVERHEAD)) { + return 0; + } else { + trans_cb->flag = SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE; + } + } + log_cb->trans_cb_idx = !(log_cb->trans_cb_idx); + } +failed: + log_cb->bytes_loss_cnt += len + SPI_OUT_FRAME_OVERHEAD; + log_cb->frame_cnt++; + return -1; +} + +IRAM_ATTR static inline void spi_out_log_cb_append_trans(spi_out_log_cb_t *log_cb, bool in_isr) +{ + spi_out_trans_cb_t *trans_cb; + uint8_t idx = !log_cb->trans_cb_idx; + for (uint8_t i = 0; i < 2; i++) { + trans_cb = log_cb->trans_cb[idx]; + if (trans_cb->flag == SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE) { + if (!in_isr) { + if (spi_out_append_trans(trans_cb) != 0) { + log_cb->trans_loss_cnt++; + } + } +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + else { + BLE_LOG_LL_PUT_EV; + return; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + } + idx = !idx; + } +} + +IRAM_ATTR static inline void spi_out_log_cb_flush_trans(spi_out_log_cb_t *log_cb) +{ + spi_out_trans_cb_t *trans_cb = log_cb->trans_cb[log_cb->trans_cb_idx]; + if (trans_cb->length && (trans_cb->flag == SPI_OUT_TRANS_CB_FLAG_AVAILABLE)) { + trans_cb->flag = SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE; + } +} + +IRAM_ATTR static void spi_out_log_cb_write(spi_out_log_cb_t *log_cb, const uint8_t *addr, uint16_t len, \ + const uint8_t *addr_append, uint16_t len_append, uint8_t source) +{ + spi_out_trans_cb_t *trans_cb = log_cb->trans_cb[log_cb->trans_cb_idx]; + + uint8_t *buf = (uint8_t *)trans_cb->trans.tx_buffer + trans_cb->length; + uint16_t total_length = len + len_append; + const uint8_t head[4] = {total_length & 0xFF, (total_length >> 8) & 0xFF, source, log_cb->frame_cnt}; + + memcpy(buf, head, SPI_OUT_FRAME_HEAD_LEN); + memcpy(buf + SPI_OUT_FRAME_HEAD_LEN, addr, len); + if (len_append) { + memcpy(buf + SPI_OUT_FRAME_HEAD_LEN + len, addr_append, len_append); + } + buf[SPI_OUT_FRAME_HEAD_LEN + total_length] = SPI_OUT_FRAME_TAIL; + + trans_cb->length += total_length + SPI_OUT_FRAME_OVERHEAD; + log_cb->frame_cnt++; + if ((trans_cb->buf_size - trans_cb->length) <= SPI_OUT_FRAME_OVERHEAD) { + trans_cb->flag = SPI_OUT_TRANS_CB_FLAG_NEED_QUEUE; + } + return; +} + +IRAM_ATTR static inline void spi_out_log_cb_write_packet_loss(spi_out_log_cb_t *log_cb, uint8_t flag) +{ + if (log_cb->bytes_loss_cnt || log_cb->trans_loss_cnt) { + uint8_t packet_loss_frame[SPI_OUT_PACKET_LOSS_FRAME_SIZE]; + packet_loss_frame[0] = flag; + memcpy(packet_loss_frame + 1, (uint8_t *)&log_cb->bytes_loss_cnt, 4); + packet_loss_frame[5] = log_cb->trans_loss_cnt; + spi_out_log_cb_write(log_cb, packet_loss_frame, SPI_OUT_PACKET_LOSS_FRAME_SIZE, NULL, 0, BLE_LOG_SPI_OUT_SOURCE_LOSS); + log_cb->bytes_loss_cnt = 0; + log_cb->trans_loss_cnt = 0; + } +} + +static void spi_out_log_cb_dump(spi_out_log_cb_t *log_cb) +{ + spi_out_trans_cb_t *trans_cb; + uint8_t *buf; + for (uint8_t i = 0; i < 2; i++) { + // Dump the last transaction before dumping the current transaction + log_cb->trans_cb_idx = !(log_cb->trans_cb_idx); + trans_cb = log_cb->trans_cb[log_cb->trans_cb_idx]; + buf = (uint8_t *)trans_cb->trans.tx_buffer; + for (uint16_t j = 0; j < trans_cb->buf_size; j++) { + esp_rom_printf("%02x ", buf[j]); + + // Feed watchdogs periodically to avoid wdts timeout + if ((j % 100) == 0) { + esp_panic_handler_feed_wdts(); + } + } + } +} + +static int spi_out_ul_log_init(void) +{ + if (ul_log_inited) { + return 0; + } + + // Initialize mutex + ul_log_mutex = xSemaphoreCreateMutex(); + if (!ul_log_mutex) { + ESP_LOGE(BLE_LOG_TAG, "Failed to create mutex for upper layer task log!"); + goto mutex_init_failed; + } + + // Initialize flushout timer + esp_timer_create_args_t timer_args = { + .callback = (esp_timer_cb_t)esp_timer_cb_ul_log_flushout, + .dispatch_method = ESP_TIMER_TASK + }; + if (esp_timer_create(&timer_args, &ul_log_flushout_timer) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize flushout timer upper layer task log!"); + goto timer_init_failed; + } + + // Initialize log control block + if (spi_out_log_cb_init(&ul_log_cb, CONFIG_BT_BLE_LOG_SPI_OUT_UL_TASK_BUF_SIZE) != 0) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize log control blocks for upper layer task log!"); + goto log_cb_init_failed; + } + + // Initialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to initialize upper layer task log!"); + ul_log_inited = true; + return 0; + +log_cb_init_failed: + esp_timer_delete(ul_log_flushout_timer); +timer_init_failed: + vSemaphoreDelete(ul_log_mutex); +mutex_init_failed: + return -1; +} + +static void spi_out_ul_log_deinit(void) +{ + if (!ul_log_inited) { + return; + } + + esp_timer_stop(ul_log_flushout_timer); + esp_timer_delete(ul_log_flushout_timer); + + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + spi_out_log_cb_deinit(&ul_log_cb); + xSemaphoreGive(ul_log_mutex); + + vSemaphoreDelete(ul_log_mutex); + ul_log_mutex = NULL; + + ESP_LOGI(BLE_LOG_TAG, "Succeeded to deinitialize upper layer log!"); + ul_log_inited = false; + return; +} + +IRAM_ATTR static void esp_timer_cb_ul_log_flushout(void) +{ + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + if (spi_out_log_cb_check_trans(ul_log_cb, SPI_OUT_PACKET_LOSS_FRAME_SIZE) == 0) { + spi_out_log_cb_write_packet_loss(ul_log_cb, SPI_OUT_PACKET_LOSS_UL); + } + spi_out_log_cb_flush_trans(ul_log_cb); + spi_out_log_cb_append_trans(ul_log_cb, false); + xSemaphoreGive(ul_log_mutex); + + if (timer_enabled) { + esp_timer_start_once(ul_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + } +} + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED +static int spi_out_ll_log_init(void) +{ + if (ll_log_inited) { + return 0; + } + + // Initialize flushout timer + esp_timer_create_args_t timer_args = { + .callback = (esp_timer_cb_t)esp_timer_cb_ll_log_flushout, + .dispatch_method = ESP_TIMER_TASK + }; + if (esp_timer_create(&timer_args, &ll_log_flushout_timer) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize flushout timer for controller log!"); + goto timer_init_failed; + } + + // Initialize log control blocks for controller task & ISR logs + if (spi_out_log_cb_init(&ll_task_log_cb, CONFIG_BT_BLE_LOG_SPI_OUT_LL_TASK_BUF_SIZE) != 0) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize log control blocks for controller task!"); + goto task_log_cb_init_failed; + } + if (spi_out_log_cb_init(&ll_isr_log_cb, CONFIG_BT_BLE_LOG_SPI_OUT_LL_ISR_BUF_SIZE) != 0) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize log control blocks for controller ISR!"); + goto isr_log_cb_init_failed; + } + + // Initialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to initialize log control blocks for controller task & ISR!"); + ll_log_inited = true; + return 0; + +isr_log_cb_init_failed: + spi_out_log_cb_deinit(&ll_task_log_cb); +task_log_cb_init_failed: + esp_timer_delete(ll_log_flushout_timer); +timer_init_failed: + return -1; +} + +static void spi_out_ll_log_deinit(void) +{ + if (!ll_log_inited) { + return; + } + + esp_timer_stop(ll_log_flushout_timer); + esp_timer_delete(ll_log_flushout_timer); + + spi_out_log_cb_deinit(&ll_isr_log_cb); + spi_out_log_cb_deinit(&ll_task_log_cb); + + // Deinitialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to deinitialize controller log!"); + ll_log_inited = false; + return; +} + +IRAM_ATTR static void spi_out_ll_log_ev_proc(void) +{ + // Request from LL ISR + if (!ll_log_need_flushout) { + esp_timer_stop(ll_log_flushout_timer); + spi_out_log_cb_append_trans(ll_isr_log_cb, false); + if (timer_enabled) { + esp_timer_start_once(ll_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + } + return; + } + + // Request from flushout timer + ll_log_need_flushout = false; + if (spi_out_log_cb_check_trans(ll_isr_log_cb, SPI_OUT_PACKET_LOSS_FRAME_SIZE) == 0) { + spi_out_log_cb_write_packet_loss(ll_isr_log_cb, SPI_OUT_PACKET_LOSS_LL_ISR); + } + spi_out_log_cb_flush_trans(ll_isr_log_cb); + spi_out_log_cb_append_trans(ll_isr_log_cb, false); + + if (spi_out_log_cb_check_trans(ll_task_log_cb, SPI_OUT_PACKET_LOSS_FRAME_SIZE) == 0) { + spi_out_log_cb_write_packet_loss(ll_task_log_cb, SPI_OUT_PACKET_LOSS_LL_TASK); + } + spi_out_log_cb_flush_trans(ll_task_log_cb); + spi_out_log_cb_append_trans(ll_task_log_cb, false); + if (timer_enabled) { + esp_timer_start_once(ll_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + } + return; +} + +IRAM_ATTR static void esp_timer_cb_ll_log_flushout(void) +{ + ll_log_need_flushout = true; + BLE_LOG_LL_PUT_EV; +} +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + #if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED +static int spi_out_ts_sync_init(void) +{ + if (ts_sync_inited) { + return 0; + } + + // Initialize sync timer + esp_timer_create_args_t timer_args = { + .callback = (esp_timer_cb_t)esp_timer_cb_ts_sync, + .dispatch_method = ESP_TIMER_TASK + }; + if (esp_timer_create(&timer_args, &ts_sync_timer) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize timestamp synchronizer timer!"); + goto timer_init_failed; + } + + // Initialize sync IO + gpio_config_t io_conf = { + .intr_type = GPIO_INTR_DISABLE, + .mode = GPIO_MODE_OUTPUT, + .pin_bit_mask = (1UL << CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM), + .pull_down_en = 0, + .pull_up_en = 0 + }; + if (gpio_config(&io_conf) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize timestamp synchronizer IO!"); + goto gpio_init_failed; + } + + // Initialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to initialize timestamp synchronizer!"); + sync_io_level = false; + gpio_set_level(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM, sync_io_level); + ts_sync_inited = true; + return 0; + +gpio_init_failed: + esp_timer_delete(ts_sync_timer); +timer_init_failed: + return -1; +} + +static void spi_out_ts_sync_deinit(void) +{ + if (!ts_sync_inited) { + return; + } + + // Deinitialize timestamp synchronizer + esp_timer_stop(ts_sync_timer); + esp_timer_delete(ts_sync_timer); + + // Deinitialize sync IO + sync_io_level = false; + gpio_set_level(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM, sync_io_level); + gpio_reset_pin(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM); + + // Deinitialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to deinitialize timestamp synchronizer!"); + ts_sync_inited = false; + return; +} + // CRITICAL: This function is called in ESP Timer task IRAM_ATTR static void esp_timer_cb_ts_sync(void) { @@ -194,24 +584,22 @@ IRAM_ATTR static void esp_timer_cb_ts_sync(void) uint32_t lc_ts = 0; uint32_t esp_ts = 0; + // Toggle sync IO + sync_io_level = !sync_io_level; + // Enter critical portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); + portENTER_CRITICAL(&spinlock); // Get LC timestamp -#if defined(CONFIG_IDF_TARGET_ESP32H2) || defined(CONFIG_IDF_TARGET_ESP32C6) - lc_ts = r_ble_lll_timer_current_tick_get(); -#endif // CONFIG_IDF_TARGET_ESP32H2 || CONFIG_IDF_TARGET_ESP32C6 -#if defined(CONFIG_IDF_TARGET_ESP32C2) - lc_ts = r_os_cputime_get32(); -#endif // CONFIG_IDF_TARGET_ESP32C2 + lc_ts = SPI_OUT_GET_LC_TIME; - // Toggle Sync IO + // Set sync IO level gpio_set_level(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM, (uint32_t)sync_io_level); // Get ESP timestamp esp_ts = esp_timer_get_time(); - portEXIT_CRITICAL_SAFE(&spinlock); + portEXIT_CRITICAL(&spinlock); // Exit critical // Write timestamp sync log @@ -220,23 +608,17 @@ IRAM_ATTR static void esp_timer_cb_ts_sync(void) memcpy(sync_frame + 1, &lc_ts, sizeof(lc_ts)); memcpy(sync_frame + 5, &esp_ts, sizeof(esp_ts)); ble_log_spi_out_write(BLE_LOG_SPI_OUT_SOURCE_SYNC, sync_frame, 9); - - // Update IO level - sync_io_level = !sync_io_level; } #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED // Public functions -void ble_log_spi_out_init(void) +int ble_log_spi_out_init(void) { // Avoid double init if (spi_out_inited) { - return; + return 0; } - // Initialize mutex - mutex_handle = xSemaphoreCreateRecursiveMutex(); - // Initialize SPI spi_bus_config_t bus_config = { .miso_io_num = -1, @@ -244,50 +626,69 @@ void ble_log_spi_out_init(void) .sclk_io_num = CONFIG_BT_BLE_LOG_SPI_OUT_SCLK_IO_NUM, .quadwp_io_num = -1, .quadhd_io_num = -1, - .max_transfer_sz = 10240 + .max_transfer_sz = SPI_OUT_MAX_TRANSFER_SIZE, + .intr_flags = ESP_INTR_FLAG_IRAM }; spi_device_interface_config_t dev_config = { .clock_speed_hz = SPI_MASTER_FREQ_20M, .mode = 0, .spics_io_num = CONFIG_BT_BLE_LOG_SPI_OUT_CS_IO_NUM, - .queue_size = CONFIG_BT_BLE_LOG_SPI_OUT_QUEUE_SIZE + .queue_size = 4 + 2, + .post_cb = (transaction_cb_t)spi_out_tx_done_cb, + .flags = SPI_DEVICE_NO_RETURN_RESULT }; - ESP_ERROR_CHECK(spi_bus_initialize(SPI_OUT_BUS, &bus_config, SPI_DMA_CH_AUTO)); - ESP_ERROR_CHECK(spi_bus_add_device(SPI_OUT_BUS, &dev_config, &spi_handle)); + if (spi_bus_initialize(SPI_OUT_BUS, &bus_config, SPI_DMA_CH_AUTO) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to initialize SPI bus!"); + goto spi_bus_init_failed; + } + if (spi_bus_add_device(SPI_OUT_BUS, &dev_config, &spi_handle) != ESP_OK) { + ESP_LOGE(BLE_LOG_TAG, "Failed to add device to SPI bus!"); + goto spi_device_add_failed; + } - // Initialize transaction link nodes - spi_out_init_trans(); + if (spi_out_ul_log_init() != 0) { + goto ul_log_init_failed; + } - // Initialize flushout timer - esp_timer_create_args_t timer_args = { - .callback = (esp_timer_cb_t)esp_timer_cb_flushout, - .dispatch_method = ESP_TIMER_TASK - }; - ESP_ERROR_CHECK(esp_timer_create(&timer_args, &flushout_timer_handle)); - esp_timer_start_once(flushout_timer_handle, SPI_OUT_FLUSHOUT_TIMEOUT); - loss_frame_cnt = 0; +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + if (spi_out_ll_log_init() != 0) { + goto ll_log_init_failed; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED #if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED - // Initialize timestamp synchronizer - gpio_config_t io_conf = { - .intr_type = GPIO_INTR_DISABLE, - .mode = GPIO_MODE_OUTPUT, - .pin_bit_mask = (1UL << CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM), - .pull_down_en = 0, - .pull_up_en = 0 - }; - ESP_ERROR_CHECK(gpio_config(&io_conf)); - sync_io_level = false; - gpio_set_level(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM, sync_io_level); - esp_timer_create_args_t ts_sync_timer_args = { - .callback = (esp_timer_cb_t)esp_timer_cb_ts_sync, - .dispatch_method = ESP_TIMER_TASK - }; - ESP_ERROR_CHECK(esp_timer_create(&ts_sync_timer_args, &ts_sync_timer_handle)); + if (spi_out_ts_sync_init() != 0) { + goto ts_sync_init_failed; + } #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED - // Set init flag + // Initialization done + ESP_LOGI(BLE_LOG_TAG, "Succeeded to initialize BLE log SPI output interface!"); spi_out_inited = true; + + // Start flushout timer + esp_timer_start_once(ul_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + esp_timer_start_once(ll_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + return 0; + +#if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED +ts_sync_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + spi_out_ll_log_deinit(); +ll_log_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + spi_out_ul_log_deinit(); +ul_log_init_failed: + spi_bus_remove_device(spi_handle); + spi_handle = NULL; +spi_device_add_failed: + spi_bus_free(SPI_OUT_BUS); +spi_bus_init_failed: + return -1; } void ble_log_spi_out_deinit(void) @@ -298,27 +699,19 @@ void ble_log_spi_out_deinit(void) } #if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED - // Deinitialize timestamp synchronizer - esp_timer_stop(ts_sync_timer_handle); - esp_timer_delete(ts_sync_timer_handle); - gpio_reset_pin(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM); + spi_out_ts_sync_deinit(); #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED - // Deinitialize flushout timer - esp_timer_stop(flushout_timer_handle); - esp_timer_delete(flushout_timer_handle); +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + spi_out_ll_log_deinit(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED - // Deinitialize transaction link nodes - spi_out_deinit_trans(); + spi_out_ul_log_deinit(); // Deinitialize SPI - ESP_ERROR_CHECK(spi_bus_remove_device(spi_handle)); - ESP_ERROR_CHECK(spi_bus_free(SPI_OUT_BUS)); + spi_bus_remove_device(spi_handle); spi_handle = NULL; - - // Deinitialize mutex - vSemaphoreDelete(mutex_handle); - mutex_handle = NULL; + spi_bus_free(SPI_OUT_BUS); // Reset init flag spi_out_inited = false; @@ -333,9 +726,9 @@ void ble_log_spi_out_ts_sync_start(void) } // Start timestamp sync timer - if (ts_sync_timer_handle) { - if (!esp_timer_is_active(ts_sync_timer_handle)) { - esp_timer_start_periodic(ts_sync_timer_handle, SPI_OUT_TS_SYNC_TIMEOUT); + if (ts_sync_timer) { + if (!esp_timer_is_active(ts_sync_timer)) { + esp_timer_start_periodic(ts_sync_timer, SPI_OUT_TS_SYNC_TIMEOUT); } } } @@ -348,54 +741,234 @@ void ble_log_spi_out_ts_sync_stop(void) } // Stop timestamp sync timer - if (ts_sync_timer_handle) { - if (esp_timer_is_active(ts_sync_timer_handle)) { - esp_timer_stop(ts_sync_timer_handle); + if (ts_sync_timer) { + if (esp_timer_is_active(ts_sync_timer)) { + esp_timer_stop(ts_sync_timer); } + + // Set sync IO to low level + sync_io_level = 0; + gpio_set_level(CONFIG_BT_BLE_LOG_SPI_OUT_SYNC_IO_NUM, (uint32_t)sync_io_level); } } #endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED -IRAM_ATTR void ble_log_spi_out_write_esp(uint32_t len, const uint8_t *addr, bool end) +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED +// Only LL task has access to this API +IRAM_ATTR void ble_log_spi_out_ll_write(uint32_t len, const uint8_t *addr, uint32_t len_append,\ + const uint8_t *addr_append, uint32_t flag) { - return ble_log_spi_out_write(BLE_LOG_SPI_OUT_SOURCE_ESP, addr, len); -} + if (!ll_log_inited) { + return; + } -IRAM_ATTR void ble_log_spi_out_write(uint8_t source, const uint8_t *addr, uint16_t len) -{ - // Initialize frame sequence number - static uint8_t frame_sn = 0; - - // Take semaphore - assert(xSemaphoreTakeRecursive(mutex_handle, portMAX_DELAY) == pdTRUE); - - // Prepare frame head and frame tail - const uint8_t head[4] = {len & 0xFF, (len >> 8) & 0xFF, (uint8_t)source, frame_sn}; - const uint8_t tail = SPI_OUT_TAIL; - - // Write frame head first, then payload, finally frame tail - do - { - if (spi_out_write(head, 4) != 0) { - loss_frame_cnt++; - break; - } - if (spi_out_write(addr, len) != 0) { - loss_frame_cnt++; - break; - } - if (spi_out_write(&tail, 1) != 0) { - loss_frame_cnt++; - break; - } - } while (0); - - // Update frame sequence number - frame_sn++; - - // Release semaphore - xSemaphoreGiveRecursive(mutex_handle); + bool in_isr = (bool)(flag & BLE_LOG_INTERFACE_FLAG_IN_ISR); + uint8_t source = in_isr ? BLE_LOG_SPI_OUT_SOURCE_ESP_ISR : BLE_LOG_SPI_OUT_SOURCE_ESP; + spi_out_log_cb_t *log_cb = in_isr ? ll_isr_log_cb : ll_task_log_cb; + uint16_t total_length = (uint16_t)(len + len_append); + if (spi_out_log_cb_check_trans(log_cb, total_length) == 0) { + spi_out_log_cb_write(log_cb, addr, (uint16_t)len, addr_append, (uint16_t)len_append, source); + } + spi_out_log_cb_append_trans(log_cb, in_isr); return; } +IRAM_ATTR void ble_log_spi_out_ll_log_ev_proc(void) +{ + if (!ll_log_inited) { + return; + } + return spi_out_ll_log_ev_proc(); +} +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + +IRAM_ATTR int ble_log_spi_out_write(uint8_t source, const uint8_t *addr, uint16_t len) +{ + if (!ul_log_inited) { + return -1; + } + + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + int ret = spi_out_log_cb_check_trans(ul_log_cb, len); + if (ret == 0) { + spi_out_log_cb_write(ul_log_cb, addr, len, NULL, 0, source); + } + spi_out_log_cb_append_trans(ul_log_cb, false); + xSemaphoreGive(ul_log_mutex); + return ret; +} + +IRAM_ATTR int ble_log_spi_out_printf(uint8_t source, const char *format, ...) +{ + if (!ul_log_inited) { + return -1; + } + + // Get arguments + va_list args; + va_start(args, format); + + // Get len as ref to allocate heap memory + va_list args_copy; + va_copy(args_copy, args); + int len = vsnprintf(NULL, 0, format, args_copy); + va_end(args_copy); + + // Length validation + if ((len < 0) || (len > 0xFFFF)) { + va_end(args); + return -1; + } + + // Allocate memory + uint8_t *buffer = malloc(len + 1); + if (!buffer) { + va_end(args); + return -1; + } + + // Generate string + vsnprintf((char *)buffer, len + 1, format, args); + va_end(args); + + uint32_t esp_ts = esp_timer_get_time(); + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + int ret = spi_out_log_cb_check_trans(ul_log_cb, 4 + len); + if (ret == 0) { + spi_out_log_cb_write(ul_log_cb, (const uint8_t *)&esp_ts, 4, (const uint8_t *)buffer, len, source); + } + spi_out_log_cb_append_trans(ul_log_cb, false); + xSemaphoreGive(ul_log_mutex); + + // Release + free(buffer); + return ret; +} + +IRAM_ATTR int ble_log_spi_out_printf_enh(uint8_t source, uint8_t level, const char *tag, const char *format, ...) +{ + if (!ul_log_inited) { + return -1; + } + + // Create log prefix in the format: "[level][tag] " + char prefix[32]; + int prefix_len = snprintf(prefix, sizeof(prefix), "[%d][%s] ", level, tag ? tag : "NULL"); + + // Compute the length of the formatted log message + va_list args; + va_start(args, format); + va_list args_copy; + va_copy(args_copy, args); + int log_len = vsnprintf(NULL, 0, format, args_copy); + va_end(args_copy); + + // Validate length + if (log_len < 0 || log_len > 0xFFFF) { + va_end(args); + return -1; + } + + // Compute total log length (prefix + formatted message) + int total_len = prefix_len + log_len; + + // Allocate memory for the complete log message + uint8_t *buffer = malloc(total_len + 1); + if (!buffer) { + va_end(args); + return -1; + } + + // Construct the final log message + memcpy(buffer, prefix, prefix_len); // Copy the prefix + vsnprintf((char *)(buffer + prefix_len), log_len + 1, format, args); + va_end(args); + + uint32_t esp_ts = esp_timer_get_time(); + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + int ret = spi_out_log_cb_check_trans(ul_log_cb, 4 + total_len); + if (ret == 0) { + spi_out_log_cb_write(ul_log_cb, (const uint8_t *)&esp_ts, 4, (const uint8_t *)buffer, total_len, source); + } + spi_out_log_cb_append_trans(ul_log_cb, false); + xSemaphoreGive(ul_log_mutex); + + free(buffer); + return ret; +} + +IRAM_ATTR int ble_log_spi_out_write_with_ts(uint8_t source, const uint8_t *addr, uint16_t len) +{ + if (!ul_log_inited) { + return -1; + } + + uint32_t esp_ts = esp_timer_get_time(); + xSemaphoreTake(ul_log_mutex, portMAX_DELAY); + int ret = spi_out_log_cb_check_trans(ul_log_cb, 4 + len); + if (ret == 0) { + spi_out_log_cb_write(ul_log_cb, (const uint8_t *)&esp_ts, 4, addr, len, source); + } + spi_out_log_cb_append_trans(ul_log_cb, false); + xSemaphoreGive(ul_log_mutex); + return ret; +} + +void ble_log_spi_out_dump_all(void) +{ + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + if (ll_log_inited) { + // Dump lower layer log buffer + esp_rom_printf("[LL_ISR_LOG_DUMP_START:\n"); + spi_out_log_cb_dump(ll_isr_log_cb); + esp_rom_printf("\n:LL_ISR_LOG_DUMP_END]\n\n"); + + esp_rom_printf("[LL_TASK_LOG_DUMP_START:\n"); + spi_out_log_cb_dump(ll_task_log_cb); + esp_rom_printf("\n:LL_TASK_LOG_DUMP_END]\n\n"); + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + + if (ul_log_inited) { + // Dump upper layer log buffer + esp_rom_printf("[UL_LOG_DUMP_START:\n"); + spi_out_log_cb_dump(ul_log_cb); + esp_rom_printf("\n:UL_LOG_DUMP_END]\n\n"); + } + portEXIT_CRITICAL_SAFE(&spinlock); +} + +void ble_log_spi_out_timer_control(bool enable) +{ + timer_enabled = enable; + if (enable) { + if (!esp_timer_is_active(ul_log_flushout_timer)) { + esp_timer_start_once(ul_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + } + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + if (!esp_timer_is_active(ll_log_flushout_timer)) { + esp_timer_start_once(ll_log_flushout_timer, SPI_OUT_FLUSHOUT_TIMEOUT); + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + +#if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED + ble_log_spi_out_ts_sync_start(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED + } else { + esp_timer_stop(ul_log_flushout_timer); + +#if CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + esp_timer_stop(ll_log_flushout_timer); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_LL_ENABLED + +#if CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED + ble_log_spi_out_ts_sync_stop(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_TS_SYNC_ENABLED + } +} + #endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED diff --git a/components/bt/common/ble_log/include/ble_log/ble_log_spi_out.h b/components/bt/common/ble_log/include/ble_log/ble_log_spi_out.h index c2b5f8d8f3..1b22ad5f42 100644 --- a/components/bt/common/ble_log/include/ble_log/ble_log_spi_out.h +++ b/components/bt/common/ble_log/include/ble_log/ble_log_spi_out.h @@ -6,10 +6,12 @@ #ifndef __BT_SPI_OUT_H__ #define __BT_SPI_OUT_H__ +#include #include #include "driver/spi_master.h" #include "driver/gpio.h" #include "esp_timer.h" +#include "esp_log.h" #include "freertos/semphr.h" // Public typedefs @@ -19,15 +21,34 @@ #define BLE_LOG_SPI_OUT_SOURCE_NIMBLE 3 #define BLE_LOG_SPI_OUT_SOURCE_HCI_UPSTREAM 4 #define BLE_LOG_SPI_OUT_SOURCE_HCI_DOWNSTREAM 5 +#define BLE_LOG_SPI_OUT_SOURCE_ESP_ISR 6 +#define BLE_LOG_SPI_OUT_SOURCE_ESP_LEGACY_ISR 7 +#define BLE_LOG_SPI_OUT_SOURCE_USER 0x10 #define BLE_LOG_SPI_OUT_SOURCE_SYNC 0xFE #define BLE_LOG_SPI_OUT_SOURCE_LOSS 0xFF +// SPI Log Level Definitions +#define BLE_LOG_SPI_OUT_LEVEL_NONE 0 /*!< No log output */ +#define BLE_LOG_SPI_OUT_LEVEL_ERROR 1 /*!< Critical errors that SPI driver cannot recover from */ +#define BLE_LOG_SPI_OUT_LEVEL_WARN 2 /*!< Recoverable error conditions in SPI communication */ +#define BLE_LOG_SPI_OUT_LEVEL_INFO 3 /*!< Informational messages about SPI transactions */ +#define BLE_LOG_SPI_OUT_LEVEL_DEBUG 4 /*!< Detailed debug information, such as SPI register values */ +#define BLE_LOG_SPI_OUT_LEVEL_VERBOSE 5 /*!< Very detailed debugging logs, potentially flooding output */ +#define BLE_LOG_SPI_OUT_LEVEL_MAX 6 /*!< Number of SPI log levels supported */ + // Public functions -void ble_log_spi_out_init(void); +int ble_log_spi_out_init(void); void ble_log_spi_out_deinit(void); -void ble_log_spi_out_write(uint8_t source, const uint8_t *addr, uint16_t len); -void ble_log_spi_out_write_esp(uint32_t len, const uint8_t *addr, bool end); +void ble_log_spi_out_timer_control(bool enable); +int ble_log_spi_out_write(uint8_t source, const uint8_t *addr, uint16_t len); +void ble_log_spi_out_ll_write(uint32_t len, const uint8_t *addr, uint32_t len_append,\ + const uint8_t *addr_append, uint32_t flag); +void ble_log_spi_out_ll_log_ev_proc(void); void ble_log_spi_out_ts_sync_start(void); void ble_log_spi_out_ts_sync_stop(void); +int ble_log_spi_out_printf(uint8_t source, const char *format, ...); +int ble_log_spi_out_printf_enh(uint8_t source, uint8_t level, const char *tag, const char *format, ...); +int ble_log_spi_out_write_with_ts(uint8_t source, const uint8_t *addr, uint16_t len); +void ble_log_spi_out_dump_all(void); #endif // __BT_SPI_OUT_H__ diff --git a/components/bt/common/include/bt_common.h b/components/bt/common/include/bt_common.h index 09e7fa50d0..300bbc6d85 100644 --- a/components/bt/common/include/bt_common.h +++ b/components/bt/common/include/bt_common.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2015-2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -84,6 +84,20 @@ #define BT_HCI_LOG_INCLUDED FALSE #endif +// HCI LOG TO SPI +#if UC_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#define BT_BLE_LOG_SPI_OUT_HCI_ENABLED UC_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#else +#define BT_BLE_LOG_SPI_OUT_HCI_ENABLED FALSE +#endif + +// BLURDROID LOG TO SPI +#if UC_BT_BLE_LOG_SPI_OUT_HOST_ENABLED +#define BT_BLE_LOG_SPI_OUT_HOST_ENABLED UC_BT_BLE_LOG_SPI_OUT_HOST_ENABLED +#else +#define BT_BLE_LOG_SPI_OUT_HOST_ENABLED FALSE +#endif + #if UC_BT_HCI_LOG_DATA_BUFFER_SIZE #define HCI_LOG_DATA_BUFFER_SIZE UC_BT_HCI_LOG_DATA_BUFFER_SIZE #else diff --git a/components/bt/common/include/bt_user_config.h b/components/bt/common/include/bt_user_config.h index da153405ed..5632b5fe22 100644 --- a/components/bt/common/include/bt_user_config.h +++ b/components/bt/common/include/bt_user_config.h @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2015-2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -126,6 +126,20 @@ #define UC_BT_HCI_LOG_DEBUG_EN FALSE #endif +//HCI LOG TO SPI +#ifdef CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#define UC_BT_BLE_LOG_SPI_OUT_HCI_ENABLED TRUE +#else +#define UC_BT_BLE_LOG_SPI_OUT_HCI_ENABLED FALSE +#endif + +//BLUEDROID LOG TO SPI +#ifdef CONFIG_BT_BLE_LOG_SPI_OUT_HOST_ENABLED +#define UC_BT_BLE_LOG_SPI_OUT_HOST_ENABLED TRUE +#else +#define UC_BT_BLE_LOG_SPI_OUT_HOST_ENABLED FALSE +#endif + #ifdef CONFIG_BT_HCI_LOG_DATA_BUFFER_SIZE #define UC_BT_HCI_LOG_DATA_BUFFER_SIZE CONFIG_BT_HCI_LOG_DATA_BUFFER_SIZE #else diff --git a/components/bt/controller/esp32/bt.c b/components/bt/controller/esp32/bt.c index 4daf277053..abf5c3d4d3 100644 --- a/components/bt/controller/esp32/bt.c +++ b/components/bt/controller/esp32/bt.c @@ -1699,7 +1699,10 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) #endif #if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED - ble_log_spi_out_init(); + if (ble_log_spi_out_init() != 0) { + ESP_LOGE(BTDM_LOG_TAG, "BLE Log SPI output init failed"); + goto error; + } #endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED btdm_cfg_mask = btdm_config_mask_load(); @@ -1728,6 +1731,10 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) error: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + bt_controller_deinit_internal(); return err; diff --git a/components/bt/controller/esp32c2/Kconfig.in b/components/bt/controller/esp32c2/Kconfig.in index 7c17fe7562..00ea9b04bb 100644 --- a/components/bt/controller/esp32c2/Kconfig.in +++ b/components/bt/controller/esp32c2/Kconfig.in @@ -689,3 +689,33 @@ config BT_LE_CTRL_CHECK_CONNECT_IND_ACCESS_ADDRESS Enabling this option will add stricter verification of the Access Address in the CONNECT_IND PDU. This improves security by ensuring that only connection requests with valid Access Addresses are accepted. If disabled, only basic checks are applied, improving compatibility. + +menu "BLE disconnects when Instant Passed (0x28) occurs" + config BT_LE_CTRL_LLCP_CONN_UPDATE + bool "BLE ACL connection update procedure" + default n + help + If this option is enabled, Controller will terminate the connection + when Instant Passed (0x28) error occurs during connection update procedure. + + config BT_LE_CTRL_LLCP_CHAN_MAP_UPDATE + bool "BLE ACL channel map update procedure" + default n + help + If this option is enabled, Controller will terminate the connection + when Instant Passed (0x28) error occurs in channel map update procedure. + + config BT_LE_CTRL_LLCP_PHY_UPDATE + bool "BLE ACL PHY update procedure" + default n + help + If this option is enabled, Controller will terminate the connection + when Instant Passed (0x28) error occurs in PHY update procedure. +endmenu + +config BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX + int "The value of upperlimitmax during scan backoff procedure" + range 1 256 + default 32 + help + The value of upperlimitmax needs to be a power of 2. diff --git a/components/bt/controller/esp32c2/ble.c b/components/bt/controller/esp32c2/ble.c index 9ea49196e5..dd6db35eed 100644 --- a/components/bt/controller/esp32c2/ble.c +++ b/components/bt/controller/esp32c2/ble.c @@ -12,9 +12,14 @@ ************************************************************************ */ #if (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) -void adv_stack_enableClearLegacyAdvVsCmd(bool en); void scan_stack_enableAdvFlowCtrlVsCmd(bool en); +void adv_stack_enableClearLegacyAdvVsCmd(bool en); void chanSel_stack_enableSetCsaVsCmd(bool en); +void hci_stack_enableSetVsEvtMaskVsCmd(bool en); + +void adv_stack_enableScanReqRxdVsEvent(bool en); +void conn_stack_enableChanMapUpdCompVsEvent(bool en); +void sleep_stack_enableWakeupVsEvent(bool en); #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) /* Local functions definition @@ -32,10 +37,18 @@ void ble_stack_enableVsCmds(bool en) #endif // DEFAULT_BT_LE_ROLE_OBSERVER chanSel_stack_enableSetCsaVsCmd(en); + hci_stack_enableSetVsEvtMaskVsCmd(en); } void ble_stack_enableVsEvents(bool en) { +#if DEFAULT_BT_LE_ROLE_BROADCASTER + adv_stack_enableScanReqRxdVsEvent(en); +#endif // DEFAULT_BT_LE_ROLE_BROADCASTER + conn_stack_enableChanMapUpdCompVsEvent(en); +#if CONFIG_BT_LE_SLEEP_ENABLE + sleep_stack_enableWakeupVsEvent(en); +#endif // CONFIG_BT_LE_SLEEP_ENABLE } #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) diff --git a/components/bt/controller/esp32c2/bt.c b/components/bt/controller/esp32c2/bt.c index 7d3c1b349d..2364eeb3a0 100644 --- a/components/bt/controller/esp32c2/bt.c +++ b/components/bt/controller/esp32c2/bt.c @@ -65,11 +65,9 @@ #include "hal/efuse_ll.h" #include "soc/rtc.h" -#if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED #include "ble_log/ble_log_spi_out.h" -#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -#endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED /* Macro definition ************************************************************************ @@ -119,7 +117,7 @@ struct ext_funcs_t { }; #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -typedef void (*interface_func_t) (uint32_t len, const uint8_t*addr, bool end); +typedef void (*interface_func_t) (uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* External functions or variables @@ -128,8 +126,10 @@ typedef void (*interface_func_t) (uint32_t len, const uint8_t*addr, bool end); extern int ble_osi_coex_funcs_register(struct osi_coex_funcs_t *coex_funcs); extern int ble_controller_init(esp_bt_controller_config_t *cfg); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -extern int ble_log_init_async(interface_func_t bt_controller_log_interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); +extern int ble_log_init_async(interface_func_t interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); extern int ble_log_deinit_async(void); +extern int ble_log_init_simple(interface_func_t interface, void *handler); +extern void ble_log_deinit_simple(void); extern void ble_log_async_output_dump_all(bool output); extern void esp_panic_handler_feed_wdts(void); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED @@ -198,10 +198,12 @@ static int esp_ecc_gen_key_pair(uint8_t *pub, uint8_t *priv); static int esp_ecc_gen_dh_key(const uint8_t *peer_pub_key_x, const uint8_t *peer_pub_key_y, const uint8_t *our_priv_key, uint8_t *out_dhkey); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end); +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE static void esp_bt_ctrl_log_partition_get_and_erase_first_block(void); -#endif // #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* Local variable definition *************************************************************************** @@ -211,50 +213,29 @@ void *g_ble_lll_rfmgmt_env_p; #endif /* Static variable declare */ static DRAM_ATTR esp_bt_controller_status_t ble_controller_status = ESP_BT_CONTROLLER_STATUS_IDLE; + #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED const static uint32_t log_bufs_size[] = {CONFIG_BT_LE_LOG_CTRL_BUF1_SIZE, CONFIG_BT_LE_LOG_HCI_BUF_SIZE, CONFIG_BT_LE_LOG_CTRL_BUF2_SIZE}; -enum log_out_mode { - LOG_DUMP_MEMORY, - LOG_ASYNC_OUT, - LOG_STORAGE_TO_FLASH, - LOG_SPI_OUT, -}; +static bool log_is_inited = false; -bool log_is_inited = false; -#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY -uint8_t log_output_mode = LOG_DUMP_MEMORY; -#else -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -uint8_t log_output_mode = LOG_STORAGE_TO_FLASH; -#elif CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -uint8_t log_output_mode = LOG_SPI_OUT; -#else -uint8_t log_output_mode = LOG_ASYNC_OUT; -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -#endif // CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY - -void esp_bt_log_output_mode_set(uint8_t output_mode) +esp_err_t esp_bt_controller_log_init(void) { - log_output_mode = output_mode; -} - -uint8_t esp_bt_log_output_mode_get(void) -{ - return log_output_mode; -} - -esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) -{ - esp_err_t ret = ESP_OK; - interface_func_t bt_controller_log_interface; - bt_controller_log_interface = esp_bt_controller_log_interface; - bool task_create; - uint8_t buffers = 0; - if (log_is_inited) { - return ret; + return ESP_OK; } +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + if (ble_log_spi_out_init() != 0) { + goto spi_out_init_failed; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + if (ble_log_init_simple(ble_log_spi_out_ll_write, ble_log_spi_out_ll_log_ev_proc) != 0) { + goto log_init_failed; + } +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + uint8_t buffers = 0; #if CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED buffers |= ESP_BLE_LOG_BUF_CONTROLLER; #endif // CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED @@ -262,44 +243,41 @@ esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) buffers |= ESP_BLE_LOG_BUF_HCI; #endif // CONFIG_BT_LE_CONTROLLER_LOG_HCI_ENABLED - switch (log_output_mode) { - case LOG_DUMP_MEMORY: - task_create = false; - break; - case LOG_ASYNC_OUT: - case LOG_STORAGE_TO_FLASH: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - if (log_output_mode == LOG_STORAGE_TO_FLASH) { - esp_bt_ctrl_log_partition_get_and_erase_first_block(); - } -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - break; - case LOG_SPI_OUT: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ble_log_spi_out_init(); - bt_controller_log_interface = ble_log_spi_out_write_esp; + bool task_create = true; +#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY + task_create = false; +#elif CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + esp_bt_ctrl_log_partition_get_and_erase_first_block(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - break; - default: - assert(0); - } - ret = ble_log_init_async(bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size); - if (ret == ESP_OK) { - log_is_inited = true; + if (ble_log_init_async(esp_bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size) != 0) { + goto log_init_failed; } +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - return ret; + log_is_inited = true; + return ESP_OK; + +log_init_failed: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +spi_out_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + return ESP_FAIL; } -void esp_bt_ontroller_log_deinit(void) +void esp_bt_controller_log_deinit(void) { - ble_log_deinit_async(); -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED ble_log_spi_out_deinit(); -#endif +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + log_is_inited = false; } @@ -394,11 +372,11 @@ void esp_bt_read_ctrl_log_from_flash(bool output) portENTER_CRITICAL_SAFE(&spinlock); esp_panic_handler_feed_wdts(); ble_log_async_output_dump_all(true); + esp_bt_controller_log_deinit(); stop_write = true; - esp_bt_ontroller_log_deinit(); - portEXIT_CRITICAL_SAFE(&spinlock); buffer = (const uint8_t *)mapped_ptr; + esp_panic_handler_feed_wdts(); if (is_filled) { read_index = next_erase_index; } else { @@ -410,7 +388,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) while (read_index != write_index) { esp_rom_printf("%02x ", buffer[read_index]); if (print_len > max_print_len) { - vTaskDelay(2); + esp_panic_handler_feed_wdts(); print_len = 0; } @@ -418,45 +396,55 @@ void esp_bt_read_ctrl_log_from_flash(bool output) read_index = (read_index + 1) % MAX_STORAGE_SIZE; } esp_rom_printf(":DUMP_END]\r\n"); + portEXIT_CRITICAL_SAFE(&spinlock); esp_partition_munmap(mmap_handle); - err = esp_bt_controller_log_init(log_output_mode); + err = esp_bt_controller_log_init(); assert(err == ESP_OK); } #endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end) -{ - if (log_output_mode == LOG_STORAGE_TO_FLASH) { -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_controller_log_storage(len, addr, end); -#endif //CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - for (int i = 0; i < len; i++) { - esp_rom_printf("%02x ", addr[i]); - } - if (end) { - esp_rom_printf("\n"); - } +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag) +{ + bool end = flag ? true : false; +#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + esp_bt_controller_log_storage(len, addr, end); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + for (int i = 0; i < len; i++) { + esp_rom_printf("%02x ", addr[i]); } + + if (end) { + esp_rom_printf("\n"); + } + portEXIT_CRITICAL_SAFE(&spinlock); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE } +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED void esp_ble_controller_log_dump_all(bool output) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_dump_all(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_read_ctrl_log_from_flash(output); -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - BT_ASSERT_PRINT("\r\n[DUMP_START:"); - ble_log_async_output_dump_all(output); - BT_ASSERT_PRINT(":DUMP_END]\r\n"); - portEXIT_CRITICAL_SAFE(&spinlock); - } + esp_bt_read_ctrl_log_from_flash(output); +#elif !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + BT_ASSERT_PRINT("\r\n[DUMP_START:"); + ble_log_async_output_dump_all(output); + BT_ASSERT_PRINT(":DUMP_END]\r\n"); + portEXIT_CRITICAL_SAFE(&spinlock); +#endif } + #if CONFIG_BT_LE_CONTROLLER_LOG_TASK_WDT_USER_HANDLER_ENABLE void esp_task_wdt_isr_user_handler(void) { @@ -876,7 +864,7 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) ESP_LOGI(NIMBLE_PORT_LOG_TAG, "ble rom commit:[%s]", r_ble_controller_get_rom_compile_version()); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - ret = esp_bt_controller_log_init(log_output_mode); + ret = esp_bt_controller_log_init(); if (ret != ESP_OK) { ESP_LOGW(NIMBLE_PORT_LOG_TAG, "ble_controller_log_init failed %d", ret); goto controller_init_err; @@ -917,7 +905,7 @@ free_controller: controller_sleep_deinit(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED controller_init_err: - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED ble_controller_deinit(); modem_deint: @@ -946,7 +934,7 @@ esp_err_t esp_bt_controller_deinit(void) controller_sleep_deinit(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED ble_controller_deinit(); diff --git a/components/bt/controller/esp32c2/esp_bt_cfg.h b/components/bt/controller/esp32c2/esp_bt_cfg.h index 74d226a609..95a3c6b2f6 100644 --- a/components/bt/controller/esp32c2/esp_bt_cfg.h +++ b/components/bt/controller/esp32c2/esp_bt_cfg.h @@ -226,6 +226,32 @@ extern "C" { #define DEFAULT_BT_LE_CTRL_CHECK_CONNECT_IND_ACCESS_ADDRESS (0) #endif +#ifdef CONFIG_BT_LE_CTRL_LLCP_CONN_UPDATE +#define BT_CTRL_BLE_LLCP_CONN_UPDATE (1<<0) +#else +#define BT_CTRL_BLE_LLCP_CONN_UPDATE (0<<0) +#endif + +#ifdef CONFIG_BT_LE_CTRL_LLCP_CHAN_MAP_UPDATE +#define BT_CTRL_BLE_LLCP_CHAN_MAP_UPDATE (1<<1) +#else +#define BT_CTRL_BLE_LLCP_CHAN_MAP_UPDATE (0<<1) +#endif + +#ifdef CONFIG_BT_LE_CTRL_LLCP_PHY_UPDATE +#define BT_CTRL_BLE_LLCP_PHY_UPDATE (1<<2) +#else +#define BT_CTRL_BLE_LLCP_PHY_UPDATE (0<<2) +#endif + +#define BT_LE_CTRL_LLCP_DISC_FLAG (BT_CTRL_BLE_LLCP_CONN_UPDATE | BT_CTRL_BLE_LLCP_CHAN_MAP_UPDATE | BT_CTRL_BLE_LLCP_PHY_UPDATE) + +#ifdef CONFIG_BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX +#define BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX (CONFIG_BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX) +#else +#define BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX (256) +#endif + #ifdef CONFIG_BT_LE_HCI_INTERFACE_USE_UART #define HCI_UART_EN CONFIG_BT_LE_HCI_INTERFACE_USE_UART #else diff --git a/components/bt/controller/esp32c3/bt.c b/components/bt/controller/esp32c3/bt.c index 87ac7a1714..7ac3c09bf1 100644 --- a/components/bt/controller/esp32c3/bt.c +++ b/components/bt/controller/esp32c3/bt.c @@ -541,7 +541,7 @@ static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, b #if CONFIG_BT_CTRL_LE_LOG_SPI_OUT_EN static IRAM_ATTR void esp_bt_controller_spi_log_interface(uint32_t len, const uint8_t *addr, bool end) { - return ble_log_spi_out_write(BLE_LOG_SPI_OUT_SOURCE_ESP_LEGACY, addr, len); + ble_log_spi_out_write(BLE_LOG_SPI_OUT_SOURCE_ESP_LEGACY, addr, len); } #endif // CONFIG_BT_CTRL_LE_LOG_SPI_OUT_EN @@ -1757,7 +1757,10 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) #endif #if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED - ble_log_spi_out_init(); + if (ble_log_spi_out_init() != 0) { + ESP_LOGE(BT_LOG_TAG, "BLE Log SPI output init failed"); + goto error; + } #endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED periph_module_enable(PERIPH_BT_MODULE); @@ -1792,6 +1795,10 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) error: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + bt_controller_deinit_internal(); return err; diff --git a/components/bt/controller/esp32c5/Kconfig.in b/components/bt/controller/esp32c5/Kconfig.in index 5058bf0fb3..fbd1269355 100644 --- a/components/bt/controller/esp32c5/Kconfig.in +++ b/components/bt/controller/esp32c5/Kconfig.in @@ -402,6 +402,10 @@ menu "Controller debug features" default n help Retain scene with GDB to capture info, requires disabling WDT (CONFIG_ESP_INT_WDT, CONFIG_ESP_TASK_WDT_EN). + + config BT_LE_PTR_CHECK_ENABLED + bool "Enable boundary check for internal memory" + default n endmenu config BT_LE_LL_RESOLV_LIST_SIZE diff --git a/components/bt/controller/esp32c5/ble.c b/components/bt/controller/esp32c5/ble.c index 7b50ca8ce9..caa8d85543 100644 --- a/components/bt/controller/esp32c5/ble.c +++ b/components/bt/controller/esp32c5/ble.c @@ -38,9 +38,11 @@ void pcl_stack_enableSetRssiThreshVsCmd(bool en); void chanSel_stack_enableSetCsaVsCmd(bool en); void log_stack_enableLogsRelatedVsCmd(bool en); void hci_stack_enableSetVsEvtMaskVsCmd(bool en); +void winWiden_stack_enableSetConstPeerScaVsCmd(bool en); void adv_stack_enableScanReqRxdVsEvent(bool en); void conn_stack_enableChanMapUpdCompVsEvent(bool en); +void sleep_stack_enableWakeupVsEvent(bool en); #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) /* Local functions definition @@ -57,12 +59,17 @@ void ble_stack_enableVsCmds(bool en) chanSel_stack_enableSetCsaVsCmd(en); log_stack_enableLogsRelatedVsCmd(en); hci_stack_enableSetVsEvtMaskVsCmd(en); + winWiden_stack_enableSetConstPeerScaVsCmd(en); } void ble_stack_enableVsEvents(bool en) { adv_stack_enableScanReqRxdVsEvent(en); conn_stack_enableChanMapUpdCompVsEvent(en); + +#if CONFIG_BT_LE_SLEEP_ENABLE + sleep_stack_enableWakeupVsEvent(en); +#endif // CONFIG_BT_LE_SLEEP_ENABLE } #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) diff --git a/components/bt/controller/esp32c5/bt.c b/components/bt/controller/esp32c5/bt.c index 9dd91b04bd..c9fdc89100 100644 --- a/components/bt/controller/esp32c5/bt.c +++ b/components/bt/controller/esp32c5/bt.c @@ -54,6 +54,11 @@ #include "hal/efuse_hal.h" #include "soc/rtc.h" + +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED +#include "ble_log/ble_log_spi_out.h" +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + /* Macro definition ************************************************************************ */ @@ -97,7 +102,7 @@ struct ext_funcs_t { }; #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -typedef void (*interface_func_t) (uint32_t len, const uint8_t*addr, bool end); +typedef void (*interface_func_t) (uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* External functions or variables @@ -107,8 +112,10 @@ extern int ble_osi_coex_funcs_register(struct osi_coex_funcs_t *coex_funcs); extern int r_ble_controller_init(esp_bt_controller_config_t *cfg); extern void esp_ble_controller_info_capture(uint32_t cycle_times); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -extern int r_ble_log_init_async(interface_func_t bt_controller_log_interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); +extern int r_ble_log_init_async(interface_func_t interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); extern int r_ble_log_deinit_async(void); +extern int r_ble_log_init_simple(interface_func_t interface, void *handler); +extern void r_ble_log_deinit_simple(void); extern void r_ble_log_async_select_dump_buffers(uint8_t buffers); extern void r_ble_log_async_output_dump_all(bool output); extern void esp_panic_handler_feed_wdts(void); @@ -177,57 +184,41 @@ static int esp_ecc_gen_key_pair(uint8_t *pub, uint8_t *priv); static int esp_ecc_gen_dh_key(const uint8_t *peer_pub_key_x, const uint8_t *peer_pub_key_y, const uint8_t *our_priv_key, uint8_t *out_dhkey); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end); +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE static void esp_bt_ctrl_log_partition_get_and_erase_first_block(void); -#endif // #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* Local variable definition *************************************************************************** */ /* Static variable declare */ static DRAM_ATTR esp_bt_controller_status_t ble_controller_status = ESP_BT_CONTROLLER_STATUS_IDLE; + #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED const static uint32_t log_bufs_size[] = {CONFIG_BT_LE_LOG_CTRL_BUF1_SIZE, CONFIG_BT_LE_LOG_HCI_BUF_SIZE, CONFIG_BT_LE_LOG_CTRL_BUF2_SIZE}; -enum log_out_mode { - LOG_DUMP_MEMORY, - LOG_ASYNC_OUT, - LOG_STORAGE_TO_FLASH, -}; +static bool log_is_inited = false; -bool log_is_inited = false; -#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY -uint8_t log_output_mode = LOG_DUMP_MEMORY; -#else -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -uint8_t log_output_mode = LOG_STORAGE_TO_FLASH; -#else -uint8_t log_output_mode = LOG_ASYNC_OUT; -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -#endif // CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY - -void esp_bt_log_output_mode_set(uint8_t output_mode) +esp_err_t esp_bt_controller_log_init(void) { - log_output_mode = output_mode; -} - -uint8_t esp_bt_log_output_mode_get(void) -{ - return log_output_mode; -} - -esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) -{ - esp_err_t ret = ESP_OK; - interface_func_t bt_controller_log_interface; - bt_controller_log_interface = esp_bt_controller_log_interface; - bool task_create; - uint8_t buffers = 0; - if (log_is_inited) { - return ret; + return ESP_OK; } +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + if (ble_log_spi_out_init() != 0) { + goto spi_out_init_failed; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + if (r_ble_log_init_simple(ble_log_spi_out_ll_write, ble_log_spi_out_ll_log_ev_proc) != 0) { + goto log_init_failed; + } +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + uint8_t buffers = 0; #if CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED buffers |= ESP_BLE_LOG_BUF_CONTROLLER; #endif // CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED @@ -235,38 +226,50 @@ esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) buffers |= ESP_BLE_LOG_BUF_HCI; #endif // CONFIG_BT_LE_CONTROLLER_LOG_HCI_ENABLED - switch (log_output_mode) { - case LOG_DUMP_MEMORY: - task_create = false; - break; - case LOG_ASYNC_OUT: - case LOG_STORAGE_TO_FLASH: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - if (log_output_mode == LOG_STORAGE_TO_FLASH) { - esp_bt_ctrl_log_partition_get_and_erase_first_block(); - } -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - break; - default: - assert(0); - } + bool task_create = true; +#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY + task_create = false; +#elif CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + esp_bt_ctrl_log_partition_get_and_erase_first_block(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ret = r_ble_log_init_async(bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size); - if (ret != ESP_OK) { - return ret; + if (r_ble_log_init_async(esp_bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size) != 0) { + goto log_init_failed; } +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ret = r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH); - if (ret == ESP_OK) { - log_is_inited = true; + if (r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH) != ESP_OK) { + goto ctrl_level_init_failed; } - return ret; + log_is_inited = true; + return ESP_OK; + +ctrl_level_init_failed: +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +log_init_failed: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +spi_out_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + return ESP_FAIL; } -void esp_bt_ontroller_log_deinit(void) +void esp_bt_controller_log_deinit(void) { +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + log_is_inited = false; } @@ -360,7 +363,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) portENTER_CRITICAL_SAFE(&spinlock); esp_panic_handler_feed_wdts(); r_ble_log_async_output_dump_all(true); - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); stop_write = true; buffer = (const uint8_t *)mapped_ptr; @@ -387,7 +390,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) esp_rom_printf(":DUMP_END]\r\n"); portEXIT_CRITICAL_SAFE(&spinlock); esp_partition_munmap(mmap_handle); - err = esp_bt_controller_log_init(log_output_mode); + err = esp_bt_controller_log_init(); assert(err == ESP_OK); } #endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE @@ -915,7 +918,7 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) #endif // CONFIG_SW_COEXIST_ENABLE #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - ret = esp_bt_controller_log_init(log_output_mode); + ret = esp_bt_controller_log_init(); if (ret != ESP_OK) { ESP_LOGW(NIMBLE_PORT_LOG_TAG, "ble_controller_log_init failed %d", ret); goto modem_deint; @@ -984,7 +987,7 @@ free_controller: modem_deint: esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED esp_phy_modem_deinit(); // modem_clock_deselect_lp_clock_source(PERIPH_BT_MODULE); @@ -1021,7 +1024,7 @@ esp_err_t esp_bt_controller_deinit(void) r_ble_controller_deinit(); esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED #if CONFIG_BT_NIMBLE_ENABLED @@ -1369,42 +1372,45 @@ esp_power_level_t esp_ble_tx_power_get_enhanced(esp_ble_enhanced_power_type_t po } #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end) +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { + bool end = flag ? true : false; #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_controller_log_storage(len, addr, end); -#endif //CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - for (int i = 0; i < len; i++) { - esp_rom_printf("%02x ", addr[i]); - } - - if (end) { - esp_rom_printf("\n"); - } - portEXIT_CRITICAL_SAFE(&spinlock); + esp_bt_controller_log_storage(len, addr, end); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + for (int i = 0; i < len; i++) { + esp_rom_printf("%02x ", addr[i]); } + + if (end) { + esp_rom_printf("\n"); + } + portEXIT_CRITICAL_SAFE(&spinlock); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE } +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED void esp_ble_controller_log_dump_all(bool output) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_dump_all(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_read_ctrl_log_from_flash(output); -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - BT_ASSERT_PRINT("\r\n[DUMP_START:"); - r_ble_log_async_output_dump_all(output); - BT_ASSERT_PRINT(":DUMP_END]\r\n"); - portEXIT_CRITICAL_SAFE(&spinlock); - } + esp_bt_read_ctrl_log_from_flash(output); +#elif !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + BT_ASSERT_PRINT("\r\n[DUMP_START:"); + r_ble_log_async_output_dump_all(output); + BT_ASSERT_PRINT(":DUMP_END]\r\n"); + portEXIT_CRITICAL_SAFE(&spinlock); +#endif } #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED diff --git a/components/bt/controller/esp32c5/esp_bt_cfg.h b/components/bt/controller/esp32c5/esp_bt_cfg.h index 3d8edd55de..6621c28cb4 100644 --- a/components/bt/controller/esp32c5/esp_bt_cfg.h +++ b/components/bt/controller/esp32c5/esp_bt_cfg.h @@ -204,6 +204,12 @@ extern "C" { #define DEFAULT_BT_LE_VHCI_ENABLED (0) #endif +#ifdef CONFIG_BT_LE_PTR_CHECK_ENABLED +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (CONFIG_BT_LE_PTR_CHECK_ENABLED) +#else +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (0) +#endif + #ifdef CONFIG_BT_LE_SLEEP_ENABLE #define NIMBLE_SLEEP_ENABLE CONFIG_BT_LE_SLEEP_ENABLE #else diff --git a/components/bt/controller/esp32c6/Kconfig.in b/components/bt/controller/esp32c6/Kconfig.in index 18b4039895..a9e59ae032 100644 --- a/components/bt/controller/esp32c6/Kconfig.in +++ b/components/bt/controller/esp32c6/Kconfig.in @@ -1,6 +1,5 @@ menu "HCI Config" - choice BT_LE_HCI_INTERFACE prompt "HCI mode" default BT_LE_HCI_INTERFACE_USE_RAM @@ -444,6 +443,10 @@ menu "Controller debug features" default n help Retain scene with GDB to capture info, requires disabling WDT (CONFIG_ESP_INT_WDT, CONFIG_ESP_TASK_WDT_EN). + + config BT_LE_PTR_CHECK_ENABLED + bool "Enable boundary check for internal memory" + default n endmenu config BT_LE_LL_RESOLV_LIST_SIZE diff --git a/components/bt/controller/esp32c6/ble.c b/components/bt/controller/esp32c6/ble.c index 7b50ca8ce9..f93f15e9b8 100644 --- a/components/bt/controller/esp32c6/ble.c +++ b/components/bt/controller/esp32c6/ble.c @@ -38,9 +38,14 @@ void pcl_stack_enableSetRssiThreshVsCmd(bool en); void chanSel_stack_enableSetCsaVsCmd(bool en); void log_stack_enableLogsRelatedVsCmd(bool en); void hci_stack_enableSetVsEvtMaskVsCmd(bool en); +void winWiden_stack_enableSetConstPeerScaVsCmd(bool en); +#if CONFIG_IDF_TARGET_ESP32C61_ECO3 +void conn_stack_enableSetPrefTxRxCntVsCmd(bool en); +#endif // CONFIG_IDF_TARGET_ESP32C61_ECO3 void adv_stack_enableScanReqRxdVsEvent(bool en); void conn_stack_enableChanMapUpdCompVsEvent(bool en); +void sleep_stack_enableWakeupVsEvent(bool en); #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) /* Local functions definition @@ -57,12 +62,20 @@ void ble_stack_enableVsCmds(bool en) chanSel_stack_enableSetCsaVsCmd(en); log_stack_enableLogsRelatedVsCmd(en); hci_stack_enableSetVsEvtMaskVsCmd(en); + winWiden_stack_enableSetConstPeerScaVsCmd(en); +#if CONFIG_IDF_TARGET_ESP32C61_ECO3 + conn_stack_enableSetPrefTxRxCntVsCmd(en); +#endif // CONFIG_IDF_TARGET_ESP32C61_ECO3 } void ble_stack_enableVsEvents(bool en) { adv_stack_enableScanReqRxdVsEvent(en); conn_stack_enableChanMapUpdCompVsEvent(en); + +#if CONFIG_BT_LE_SLEEP_ENABLE + sleep_stack_enableWakeupVsEvent(en); +#endif // CONFIG_BT_LE_SLEEP_ENABLE } #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) diff --git a/components/bt/controller/esp32c6/bt.c b/components/bt/controller/esp32c6/bt.c index 291fc2a2ad..9e3253d4c6 100644 --- a/components/bt/controller/esp32c6/bt.c +++ b/components/bt/controller/esp32c6/bt.c @@ -58,11 +58,9 @@ #include "hal/efuse_hal.h" #include "soc/rtc.h" -#if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED #include "ble_log/ble_log_spi_out.h" -#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -#endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED /* Macro definition ************************************************************************ @@ -107,7 +105,7 @@ struct ext_funcs_t { }; #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -typedef void (*interface_func_t) (uint32_t len, const uint8_t*addr, bool end); +typedef void (*interface_func_t) (uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* External functions or variables @@ -117,8 +115,10 @@ extern int ble_osi_coex_funcs_register(struct osi_coex_funcs_t *coex_funcs); extern int r_ble_controller_init(esp_bt_controller_config_t *cfg); extern void esp_ble_controller_info_capture(uint32_t cycle_times); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -extern int r_ble_log_init_async(interface_func_t bt_controller_log_interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); +extern int r_ble_log_init_async(interface_func_t interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); extern int r_ble_log_deinit_async(void); +extern int r_ble_log_init_simple(interface_func_t interface, void *handler); +extern void r_ble_log_deinit_simple(void); extern void r_ble_log_async_select_dump_buffers(uint8_t buffers); extern void r_ble_log_async_output_dump_all(bool output); extern void esp_panic_handler_feed_wdts(void); @@ -187,60 +187,41 @@ static int esp_ecc_gen_key_pair(uint8_t *pub, uint8_t *priv); static int esp_ecc_gen_dh_key(const uint8_t *peer_pub_key_x, const uint8_t *peer_pub_key_y, const uint8_t *our_priv_key, uint8_t *out_dhkey); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end); +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE static void esp_bt_ctrl_log_partition_get_and_erase_first_block(void); -#endif // #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* Local variable definition *************************************************************************** */ /* Static variable declare */ static DRAM_ATTR esp_bt_controller_status_t ble_controller_status = ESP_BT_CONTROLLER_STATUS_IDLE; + #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED const static uint32_t log_bufs_size[] = {CONFIG_BT_LE_LOG_CTRL_BUF1_SIZE, CONFIG_BT_LE_LOG_HCI_BUF_SIZE, CONFIG_BT_LE_LOG_CTRL_BUF2_SIZE}; -enum log_out_mode { - LOG_DUMP_MEMORY, - LOG_ASYNC_OUT, - LOG_STORAGE_TO_FLASH, - LOG_SPI_OUT, -}; +static bool log_is_inited = false; -bool log_is_inited = false; -#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY -uint8_t log_output_mode = LOG_DUMP_MEMORY; -#else -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -uint8_t log_output_mode = LOG_STORAGE_TO_FLASH; -#elif CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -uint8_t log_output_mode = LOG_SPI_OUT; -#else -uint8_t log_output_mode = LOG_ASYNC_OUT; -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -#endif // CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY - -void esp_bt_log_output_mode_set(uint8_t output_mode) +esp_err_t esp_bt_controller_log_init(void) { - log_output_mode = output_mode; -} - -uint8_t esp_bt_log_output_mode_get(void) -{ - return log_output_mode; -} - -esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) -{ - esp_err_t ret = ESP_OK; - interface_func_t bt_controller_log_interface; - bt_controller_log_interface = esp_bt_controller_log_interface; - bool task_create; - uint8_t buffers = 0; - if (log_is_inited) { - return ret; + return ESP_OK; } +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + if (ble_log_spi_out_init() != 0) { + goto spi_out_init_failed; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + if (r_ble_log_init_simple(ble_log_spi_out_ll_write, ble_log_spi_out_ll_log_ev_proc) != 0) { + goto log_init_failed; + } +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + uint8_t buffers = 0; #if CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED buffers |= ESP_BLE_LOG_BUF_CONTROLLER; #endif // CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED @@ -248,48 +229,50 @@ esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) buffers |= ESP_BLE_LOG_BUF_HCI; #endif // CONFIG_BT_LE_CONTROLLER_LOG_HCI_ENABLED - switch (log_output_mode) { - case LOG_DUMP_MEMORY: - task_create = false; - break; - case LOG_ASYNC_OUT: - case LOG_STORAGE_TO_FLASH: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - if (log_output_mode == LOG_STORAGE_TO_FLASH) { - esp_bt_ctrl_log_partition_get_and_erase_first_block(); - } -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - break; - case LOG_SPI_OUT: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ble_log_spi_out_init(); - bt_controller_log_interface = ble_log_spi_out_write_esp; + bool task_create = true; +#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY + task_create = false; +#elif CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + esp_bt_ctrl_log_partition_get_and_erase_first_block(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - break; - default: - assert(0); - } - ret = r_ble_log_init_async(bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size); - if (ret != ESP_OK) { - return ret; + if (r_ble_log_init_async(esp_bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size) != 0) { + goto log_init_failed; } +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ret = r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH); - if (ret == ESP_OK) { - log_is_inited = true; + if (r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH) != ESP_OK) { + goto ctrl_level_init_failed; } - return ret; + log_is_inited = true; + return ESP_OK; + +ctrl_level_init_failed: +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +log_init_failed: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +spi_out_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + return ESP_FAIL; } -void esp_bt_ontroller_log_deinit(void) +void esp_bt_controller_log_deinit(void) { - r_ble_log_deinit_async(); -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED ble_log_spi_out_deinit(); -#endif +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + log_is_inited = false; } @@ -383,7 +366,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) portENTER_CRITICAL_SAFE(&spinlock); esp_panic_handler_feed_wdts(); r_ble_log_async_output_dump_all(true); - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); stop_write = true; buffer = (const uint8_t *)mapped_ptr; @@ -953,7 +936,7 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) #endif // CONFIG_SW_COEXIST_ENABLE #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - ret = esp_bt_controller_log_init(log_output_mode); + ret = esp_bt_controller_log_init(); if (ret != ESP_OK) { ESP_LOGW(NIMBLE_PORT_LOG_TAG, "ble_controller_log_init failed %d", ret); goto modem_deint; @@ -1025,7 +1008,7 @@ free_controller: modem_deint: esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED esp_phy_modem_deinit(); modem_clock_deselect_lp_clock_source(PERIPH_BT_MODULE); @@ -1062,7 +1045,7 @@ esp_err_t esp_bt_controller_deinit(void) r_ble_controller_deinit(); esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED #if CONFIG_BT_NIMBLE_ENABLED @@ -1410,42 +1393,45 @@ esp_power_level_t esp_ble_tx_power_get_enhanced(esp_ble_enhanced_power_type_t po } #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end) +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { + bool end = flag ? true : false; #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_controller_log_storage(len, addr, end); -#endif //CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - for (int i = 0; i < len; i++) { - esp_rom_printf("%02x ", addr[i]); - } - - if (end) { - esp_rom_printf("\n"); - } - portEXIT_CRITICAL_SAFE(&spinlock); + esp_bt_controller_log_storage(len, addr, end); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + for (int i = 0; i < len; i++) { + esp_rom_printf("%02x ", addr[i]); } + + if (end) { + esp_rom_printf("\n"); + } + portEXIT_CRITICAL_SAFE(&spinlock); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE } +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED void esp_ble_controller_log_dump_all(bool output) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_dump_all(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_read_ctrl_log_from_flash(output); -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - BT_ASSERT_PRINT("\r\n[DUMP_START:"); - r_ble_log_async_output_dump_all(output); - BT_ASSERT_PRINT(":DUMP_END]\r\n"); - portEXIT_CRITICAL_SAFE(&spinlock); - } + esp_bt_read_ctrl_log_from_flash(output); +#elif !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + BT_ASSERT_PRINT("\r\n[DUMP_START:"); + r_ble_log_async_output_dump_all(output); + BT_ASSERT_PRINT(":DUMP_END]\r\n"); + portEXIT_CRITICAL_SAFE(&spinlock); +#endif } #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED diff --git a/components/bt/controller/esp32c6/esp_bt_cfg.h b/components/bt/controller/esp32c6/esp_bt_cfg.h index 3d8edd55de..6621c28cb4 100644 --- a/components/bt/controller/esp32c6/esp_bt_cfg.h +++ b/components/bt/controller/esp32c6/esp_bt_cfg.h @@ -204,6 +204,12 @@ extern "C" { #define DEFAULT_BT_LE_VHCI_ENABLED (0) #endif +#ifdef CONFIG_BT_LE_PTR_CHECK_ENABLED +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (CONFIG_BT_LE_PTR_CHECK_ENABLED) +#else +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (0) +#endif + #ifdef CONFIG_BT_LE_SLEEP_ENABLE #define NIMBLE_SLEEP_ENABLE CONFIG_BT_LE_SLEEP_ENABLE #else diff --git a/components/bt/controller/esp32h2/Kconfig.in b/components/bt/controller/esp32h2/Kconfig.in index 858a772217..b07e4783a8 100644 --- a/components/bt/controller/esp32h2/Kconfig.in +++ b/components/bt/controller/esp32h2/Kconfig.in @@ -1,6 +1,5 @@ menu "HCI Config" - choice BT_LE_HCI_INTERFACE prompt "HCI mode" default BT_LE_HCI_INTERFACE_USE_RAM @@ -438,6 +437,10 @@ menu "Controller debug features" default n help Retain scene with GDB to capture info, requires disabling WDT (CONFIG_ESP_INT_WDT, CONFIG_ESP_TASK_WDT_EN). + + config BT_LE_PTR_CHECK_ENABLED + bool "Enable boundary check for internal memory" + default n endmenu config BT_LE_LL_RESOLV_LIST_SIZE diff --git a/components/bt/controller/esp32h2/ble.c b/components/bt/controller/esp32h2/ble.c index 7b50ca8ce9..caa8d85543 100644 --- a/components/bt/controller/esp32h2/ble.c +++ b/components/bt/controller/esp32h2/ble.c @@ -38,9 +38,11 @@ void pcl_stack_enableSetRssiThreshVsCmd(bool en); void chanSel_stack_enableSetCsaVsCmd(bool en); void log_stack_enableLogsRelatedVsCmd(bool en); void hci_stack_enableSetVsEvtMaskVsCmd(bool en); +void winWiden_stack_enableSetConstPeerScaVsCmd(bool en); void adv_stack_enableScanReqRxdVsEvent(bool en); void conn_stack_enableChanMapUpdCompVsEvent(bool en); +void sleep_stack_enableWakeupVsEvent(bool en); #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) /* Local functions definition @@ -57,12 +59,17 @@ void ble_stack_enableVsCmds(bool en) chanSel_stack_enableSetCsaVsCmd(en); log_stack_enableLogsRelatedVsCmd(en); hci_stack_enableSetVsEvtMaskVsCmd(en); + winWiden_stack_enableSetConstPeerScaVsCmd(en); } void ble_stack_enableVsEvents(bool en) { adv_stack_enableScanReqRxdVsEvent(en); conn_stack_enableChanMapUpdCompVsEvent(en); + +#if CONFIG_BT_LE_SLEEP_ENABLE + sleep_stack_enableWakeupVsEvent(en); +#endif // CONFIG_BT_LE_SLEEP_ENABLE } #endif // (CONFIG_BT_NIMBLE_ENABLED || CONFIG_BT_BLUEDROID_ENABLED) diff --git a/components/bt/controller/esp32h2/bt.c b/components/bt/controller/esp32h2/bt.c index 147f1818e7..e5894ecd22 100644 --- a/components/bt/controller/esp32h2/bt.c +++ b/components/bt/controller/esp32h2/bt.c @@ -54,11 +54,9 @@ #include "esp_sleep.h" #include "soc/rtc.h" -#if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED #include "ble_log/ble_log_spi_out.h" -#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -#endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED /* Macro definition ************************************************************************ @@ -103,7 +101,7 @@ struct ext_funcs_t { }; #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -typedef void (*interface_func_t) (uint32_t len, const uint8_t*addr, bool end); +typedef void (*interface_func_t) (uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* External functions or variables ************************************************************************ @@ -112,8 +110,10 @@ extern int ble_osi_coex_funcs_register(struct osi_coex_funcs_t *coex_funcs); extern int r_ble_controller_init(esp_bt_controller_config_t *cfg); extern void esp_ble_controller_info_capture(uint32_t cycle_times); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -extern int r_ble_log_init_async(interface_func_t bt_controller_log_interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); +extern int r_ble_log_init_async(interface_func_t interface, bool task_create, uint8_t buffers, uint32_t *bufs_size); extern int r_ble_log_deinit_async(void); +extern int r_ble_log_init_simple(interface_func_t interface, void *handler); +extern void r_ble_log_deinit_simple(void); extern void r_ble_log_async_select_dump_buffers(uint8_t buffers); extern void r_ble_log_async_output_dump_all(bool output); extern void esp_panic_handler_feed_wdts(void); @@ -185,60 +185,41 @@ static int esp_ecc_gen_key_pair(uint8_t *pub, uint8_t *priv); static int esp_ecc_gen_dh_key(const uint8_t *peer_pub_key_x, const uint8_t *peer_pub_key_y, const uint8_t *our_priv_key, uint8_t *out_dhkey); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end); +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag); +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE static void esp_bt_ctrl_log_partition_get_and_erase_first_block(void); -#endif // #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED /* Local variable definition *************************************************************************** */ /* Static variable declare */ static DRAM_ATTR esp_bt_controller_status_t ble_controller_status = ESP_BT_CONTROLLER_STATUS_IDLE; + #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED const static uint32_t log_bufs_size[] = {CONFIG_BT_LE_LOG_CTRL_BUF1_SIZE, CONFIG_BT_LE_LOG_HCI_BUF_SIZE, CONFIG_BT_LE_LOG_CTRL_BUF2_SIZE}; -enum log_out_mode { - LOG_DUMP_MEMORY, - LOG_ASYNC_OUT, - LOG_STORAGE_TO_FLASH, - LOG_SPI_OUT, -}; +static bool log_is_inited = false; -bool log_is_inited = false; -#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY -uint8_t log_output_mode = LOG_DUMP_MEMORY; -#else -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -uint8_t log_output_mode = LOG_STORAGE_TO_FLASH; -#elif CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED -uint8_t log_output_mode = LOG_SPI_OUT; -#else -uint8_t log_output_mode = LOG_ASYNC_OUT; -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE -#endif // CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY - -void esp_bt_log_output_mode_set(uint8_t output_mode) +esp_err_t esp_bt_controller_log_init(void) { - log_output_mode = output_mode; -} - -uint8_t esp_bt_log_output_mode_get(void) -{ - return log_output_mode; -} - -esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) -{ - esp_err_t ret = ESP_OK; - interface_func_t bt_controller_log_interface; - bt_controller_log_interface = esp_bt_controller_log_interface; - bool task_create; - uint8_t buffers = 0; - if (log_is_inited) { - return ret; + return ESP_OK; } +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + if (ble_log_spi_out_init() != 0) { + goto spi_out_init_failed; + } +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + if (r_ble_log_init_simple(ble_log_spi_out_ll_write, ble_log_spi_out_ll_log_ev_proc) != 0) { + goto log_init_failed; + } +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + uint8_t buffers = 0; #if CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED buffers |= ESP_BLE_LOG_BUF_CONTROLLER; #endif // CONFIG_BT_LE_CONTROLLER_LOG_CTRL_ENABLED @@ -246,48 +227,50 @@ esp_err_t esp_bt_controller_log_init(uint8_t log_output_mode) buffers |= ESP_BLE_LOG_BUF_HCI; #endif // CONFIG_BT_LE_CONTROLLER_LOG_HCI_ENABLED - switch (log_output_mode) { - case LOG_DUMP_MEMORY: - task_create = false; - break; - case LOG_ASYNC_OUT: - case LOG_STORAGE_TO_FLASH: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - if (log_output_mode == LOG_STORAGE_TO_FLASH) { - esp_bt_ctrl_log_partition_get_and_erase_first_block(); - } -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - break; - case LOG_SPI_OUT: - task_create = true; -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ble_log_spi_out_init(); - bt_controller_log_interface = ble_log_spi_out_write_esp; + bool task_create = true; +#if CONFIG_BT_LE_CONTROLLER_LOG_DUMP_ONLY + task_create = false; +#elif CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + esp_bt_ctrl_log_partition_get_and_erase_first_block(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - break; - default: - assert(0); - } - ret = r_ble_log_init_async(bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size); - if (ret != ESP_OK) { - return ret; + if (r_ble_log_init_async(esp_bt_controller_log_interface, task_create, buffers, (uint32_t *)log_bufs_size) != 0) { + goto log_init_failed; } +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED - ret = r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH); - if (ret == ESP_OK) { - log_is_inited = true; + if (r_ble_log_ctrl_level_and_mod(CONFIG_BT_LE_CONTROLLER_LOG_OUTPUT_LEVEL, CONFIG_BT_LE_CONTROLLER_LOG_MOD_OUTPUT_SWITCH) != ESP_OK) { + goto ctrl_level_init_failed; } - return ret; + log_is_inited = true; + return ESP_OK; + +ctrl_level_init_failed: +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +log_init_failed: +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_deinit(); +spi_out_init_failed: +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + return ESP_FAIL; } -void esp_bt_ontroller_log_deinit(void) +void esp_bt_controller_log_deinit(void) { - r_ble_log_deinit_async(); -#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED ble_log_spi_out_deinit(); -#endif +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + +#if CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_simple(); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + r_ble_log_deinit_async(); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED + log_is_inited = false; } @@ -381,7 +364,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) portENTER_CRITICAL_SAFE(&spinlock); esp_panic_handler_feed_wdts(); r_ble_log_async_output_dump_all(true); - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); stop_write = true; buffer = (const uint8_t *)mapped_ptr; @@ -408,7 +391,7 @@ void esp_bt_read_ctrl_log_from_flash(bool output) esp_rom_printf(":DUMP_END]\r\n"); portEXIT_CRITICAL_SAFE(&spinlock); esp_partition_munmap(mmap_handle); - err = esp_bt_controller_log_init(log_output_mode); + err = esp_bt_controller_log_init(); assert(err == ESP_OK); } #endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE @@ -929,7 +912,7 @@ esp_err_t esp_bt_controller_init(esp_bt_controller_config_t *cfg) #endif // CONFIG_SW_COEXIST_ENABLE #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - ret = esp_bt_controller_log_init(log_output_mode); + ret = esp_bt_controller_log_init(); if (ret != ESP_OK) { ESP_LOGW(NIMBLE_PORT_LOG_TAG, "ble_controller_log_init failed %d", ret); goto modem_deint; @@ -1001,7 +984,7 @@ free_controller: modem_deint: esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED modem_clock_deselect_lp_clock_source(PERIPH_BT_MODULE); modem_clock_module_disable(PERIPH_BT_MODULE); @@ -1036,7 +1019,7 @@ esp_err_t esp_bt_controller_deinit(void) r_ble_controller_deinit(); esp_ble_unregister_bb_funcs(); #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED - esp_bt_ontroller_log_deinit(); + esp_bt_controller_log_deinit(); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED #if CONFIG_BT_NIMBLE_ENABLED @@ -1384,41 +1367,45 @@ esp_power_level_t esp_ble_tx_power_get_enhanced(esp_ble_enhanced_power_type_t po } #if CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, bool end) +#if !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED +static void esp_bt_controller_log_interface(uint32_t len, const uint8_t *addr, uint32_t len_append, const uint8_t *addr_append, uint32_t flag) { - if (log_output_mode == LOG_STORAGE_TO_FLASH) { + bool end = flag ? true : false; #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - esp_bt_controller_log_storage(len, addr, end); -#endif //CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE - } else { - portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); - esp_panic_handler_feed_wdts(); - for (int i = 0; i < len; i++) { - esp_rom_printf("%02x ", addr[i]); - } - - if (end) { - esp_rom_printf("\n"); - } - portEXIT_CRITICAL_SAFE(&spinlock); + esp_bt_controller_log_storage(len, addr, end); +#else // !CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE + portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; + portENTER_CRITICAL_SAFE(&spinlock); + esp_panic_handler_feed_wdts(); + for (int i = 0; i < len; i++) { + esp_rom_printf("%02x ", addr[i]); } + + if (end) { + esp_rom_printf("\n"); + } + portEXIT_CRITICAL_SAFE(&spinlock); +#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE } +#endif // !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED void esp_ble_controller_log_dump_all(bool output) { +#if CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + ble_log_spi_out_dump_all(); +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_ENABLED + #if CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE esp_bt_read_ctrl_log_from_flash(output); -#else +#elif !CONFIG_BT_LE_CONTROLLER_LOG_SPI_OUT_ENABLED portMUX_TYPE spinlock = portMUX_INITIALIZER_UNLOCKED; - portENTER_CRITICAL_SAFE(&spinlock); esp_panic_handler_feed_wdts(); BT_ASSERT_PRINT("\r\n[DUMP_START:"); r_ble_log_async_output_dump_all(output); BT_ASSERT_PRINT(":DUMP_END]\r\n"); portEXIT_CRITICAL_SAFE(&spinlock); -#endif // CONFIG_BT_LE_CONTROLLER_LOG_STORAGE_ENABLE +#endif } #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED diff --git a/components/bt/controller/esp32h2/esp_bt_cfg.h b/components/bt/controller/esp32h2/esp_bt_cfg.h index 3d8edd55de..6621c28cb4 100644 --- a/components/bt/controller/esp32h2/esp_bt_cfg.h +++ b/components/bt/controller/esp32h2/esp_bt_cfg.h @@ -204,6 +204,12 @@ extern "C" { #define DEFAULT_BT_LE_VHCI_ENABLED (0) #endif +#ifdef CONFIG_BT_LE_PTR_CHECK_ENABLED +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (CONFIG_BT_LE_PTR_CHECK_ENABLED) +#else +#define DEFAULT_BT_LE_PTR_CHECK_ENABLED (0) +#endif + #ifdef CONFIG_BT_LE_SLEEP_ENABLE #define NIMBLE_SLEEP_ENABLE CONFIG_BT_LE_SLEEP_ENABLE #else diff --git a/components/bt/controller/lib_esp32c2/esp32c2-bt-lib b/components/bt/controller/lib_esp32c2/esp32c2-bt-lib index 1e88fa4606..c0d98a9a03 160000 --- a/components/bt/controller/lib_esp32c2/esp32c2-bt-lib +++ b/components/bt/controller/lib_esp32c2/esp32c2-bt-lib @@ -1 +1 @@ -Subproject commit 1e88fa4606b62faf7350ac12d4317ab4d1cd286d +Subproject commit c0d98a9a03c266828a25bed38c0174ecfc882aea diff --git a/components/bt/controller/lib_esp32c5/esp32c5-bt-lib b/components/bt/controller/lib_esp32c5/esp32c5-bt-lib index a1edef01cb..4ff56a052a 160000 --- a/components/bt/controller/lib_esp32c5/esp32c5-bt-lib +++ b/components/bt/controller/lib_esp32c5/esp32c5-bt-lib @@ -1 +1 @@ -Subproject commit a1edef01cbbbc99126e8233a44e97f752bc93a0e +Subproject commit 4ff56a052ab888be3b4abe548f86052fa314d10c diff --git a/components/bt/controller/lib_esp32c6/esp32c6-bt-lib b/components/bt/controller/lib_esp32c6/esp32c6-bt-lib index b75747061f..246541ab93 160000 --- a/components/bt/controller/lib_esp32c6/esp32c6-bt-lib +++ b/components/bt/controller/lib_esp32c6/esp32c6-bt-lib @@ -1 +1 @@ -Subproject commit b75747061f79a6eb070b5b0f96ebda79bffee485 +Subproject commit 246541ab93e853eba1591784a5253b219c0414f9 diff --git a/components/bt/controller/lib_esp32h2/esp32h2-bt-lib b/components/bt/controller/lib_esp32h2/esp32h2-bt-lib index cd36ec849c..a3192174a9 160000 --- a/components/bt/controller/lib_esp32h2/esp32h2-bt-lib +++ b/components/bt/controller/lib_esp32h2/esp32h2-bt-lib @@ -1 +1 @@ -Subproject commit cd36ec849cbfc8cef8dd48228ca70fffc1e240a3 +Subproject commit a3192174a9aef015a9ceca983acdb9fd1a198445 diff --git a/components/bt/host/bluedroid/api/esp_bluedroid_hci.c b/components/bt/host/bluedroid/api/esp_bluedroid_hci.c index 1676ae8824..0e6baf1118 100644 --- a/components/bt/host/bluedroid/api/esp_bluedroid_hci.c +++ b/components/bt/host/bluedroid/api/esp_bluedroid_hci.c @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2015-2023 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -16,6 +16,10 @@ #define LOG_TAG "HCI_API" +#if CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#include "ble_log/ble_log_spi_out.h" +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED + static esp_bluedroid_hci_driver_operations_t s_hci_driver_ops = { 0 }; esp_err_t esp_bluedroid_attach_hci_driver(const esp_bluedroid_hci_driver_operations_t *p_ops) @@ -63,6 +67,9 @@ void hci_host_send_packet(uint8_t *data, uint16_t len) #if (BT_HCI_LOG_INCLUDED == TRUE) bt_hci_log_record_hci_data(data[0], &data[1], len - 1); #endif +#if (BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) + ble_log_spi_out_write_with_ts(BLE_LOG_SPI_OUT_SOURCE_HCI_DOWNSTREAM, data, len); +#endif // (BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) #if (BT_CONTROLLER_INCLUDED == TRUE) esp_vhci_host_send_packet(data, len); #else /* BT_CONTROLLER_INCLUDED == TRUE */ diff --git a/components/bt/host/bluedroid/common/include/common/bt_trace.h b/components/bt/host/bluedroid/common/include/common/bt_trace.h index 74b7f10574..8a115ae02a 100644 --- a/components/bt/host/bluedroid/common/include/common/bt_trace.h +++ b/components/bt/host/bluedroid/common/include/common/bt_trace.h @@ -25,6 +25,9 @@ #include "stack/bt_types.h" #include "bt_common.h" +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) +#include "ble_log/ble_log_spi_out.h" +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) static inline void trc_dump_buffer(const char *prefix, uint8_t *data, uint16_t len) { uint16_t i; @@ -217,20 +220,83 @@ static inline void trc_dump_buffer(const char *prefix, uint8_t *data, uint16_t l /* Define tracing for BTM */ +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + +#define BTM_TRACE_ERROR(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_ERROR, "BT_BTM", fmt, ## args); \ + if (btm_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(BTM, ERROR)) BT_PRINT_E("BT_BTM", fmt, ## args); \ +} + +#define BTM_TRACE_WARNING(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_WARN, "BT_BTM", fmt, ## args); \ + if (btm_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(BTM, WARNING)) BT_PRINT_W("BT_BTM", fmt, ## args); \ +} + +#define BTM_TRACE_API(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_INFO, "BT_BTM", fmt, ## args); \ + if (btm_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(BTM, API)) BT_PRINT_I("BT_BTM", fmt, ## args); \ +} + +#define BTM_TRACE_EVENT(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_BTM", fmt, ## args); \ + if (btm_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(BTM, EVENT)) BT_PRINT_D("BT_BTM", fmt, ## args); \ +} + +#define BTM_TRACE_DEBUG(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_BTM", fmt, ## args); \ + if (btm_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(BTM, DEBUG)) BT_PRINT_D("BT_BTM", fmt, ## args); \ +} + +#else + #define BTM_TRACE_ERROR(fmt, args...) {if (btm_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(BTM, ERROR)) BT_PRINT_E("BT_BTM", fmt, ## args);} #define BTM_TRACE_WARNING(fmt, args...) {if (btm_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(BTM, WARNING)) BT_PRINT_W("BT_BTM", fmt, ## args);} #define BTM_TRACE_API(fmt, args...) {if (btm_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(BTM,API)) BT_PRINT_I("BT_BTM", fmt, ## args);} #define BTM_TRACE_EVENT(fmt, args...) {if (btm_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(BTM,EVENT)) BT_PRINT_D("BT_BTM", fmt, ## args);} #define BTM_TRACE_DEBUG(fmt, args...) {if (btm_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(BTM,DEBUG)) BT_PRINT_D("BT_BTM", fmt, ## args);} +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + /* Define tracing for the L2CAP unit */ +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + +#define L2CAP_TRACE_ERROR(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_ERROR, "BT_L2CAP", fmt, ## args); \ + if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(L2CAP, ERROR)) BT_PRINT_E("BT_L2CAP", fmt, ## args); \ +} + +#define L2CAP_TRACE_WARNING(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_WARN, "BT_L2CAP", fmt, ## args); \ + if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(L2CAP, WARNING)) BT_PRINT_W("BT_L2CAP", fmt, ## args); \ +} + +#define L2CAP_TRACE_API(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_INFO, "BT_L2CAP", fmt, ## args); \ + if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(L2CAP, API)) BT_PRINT_I("BT_L2CAP", fmt, ## args); \ +} + +#define L2CAP_TRACE_EVENT(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_L2CAP", fmt, ## args); \ + if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(L2CAP, EVENT)) BT_PRINT_D("BT_L2CAP", fmt, ## args); \ +} + +#define L2CAP_TRACE_DEBUG(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_L2CAP", fmt, ## args); \ + if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(L2CAP, DEBUG)) BT_PRINT_D("BT_L2CAP", fmt, ## args); \ +} + +#else + #define L2CAP_TRACE_ERROR(fmt, args...) {if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(L2CAP, ERROR)) BT_PRINT_E("BT_L2CAP", fmt, ## args);} #define L2CAP_TRACE_WARNING(fmt, args...) {if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(L2CAP, WARNING)) BT_PRINT_W("BT_L2CAP", fmt, ## args);} #define L2CAP_TRACE_API(fmt, args...) {if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(L2CAP,API)) BT_PRINT_I("BT_L2CAP", fmt, ## args);} #define L2CAP_TRACE_EVENT(fmt, args...) {if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(L2CAP,EVENT)) BT_PRINT_D("BT_L2CAP", fmt, ## args);} #define L2CAP_TRACE_DEBUG(fmt, args...) {if (l2cb.l2cap_trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(L2CAP,DEBUG)) BT_PRINT_D("BT_L2CAP", fmt, ## args);} +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + + /* Define tracing for the SDP unit */ #define SDP_TRACE_ERROR(fmt, args...) {if (sdp_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(SDP, ERROR)) BT_PRINT_E("BT_SDP", fmt, ## args);} @@ -248,11 +314,38 @@ static inline void trc_dump_buffer(const char *prefix, uint8_t *data, uint16_t l #define RFCOMM_TRACE_DEBUG(fmt, args...) {if (rfc_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(RFCOMM,DEBUG)) BT_PRINT_D("BT_RFCOMM", fmt, ## args);} /* Generic Access Profile traces */ +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + +#define GAP_TRACE_ERROR(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_ERROR, "BT_GAP", fmt, ## args); \ + if (gap_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(GAP, ERROR)) BT_PRINT_E("BT_GAP", fmt, ## args); \ +} + +#define GAP_TRACE_WARNING(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_WARN, "BT_GAP", fmt, ## args); \ + if (gap_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(GAP, WARNING)) BT_PRINT_W("BT_GAP", fmt, ## args); \ +} + +#define GAP_TRACE_API(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_INFO, "BT_GAP", fmt, ## args); \ + if (gap_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(GAP, API)) BT_PRINT_I("BT_GAP", fmt, ## args); \ +} + +#define GAP_TRACE_EVENT(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_GAP", fmt, ## args); \ + if (gap_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(GAP, EVENT)) BT_PRINT_D("BT_GAP", fmt, ## args); \ +} + +#else + #define GAP_TRACE_ERROR(fmt, args...) {if (gap_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(GAP, ERROR)) BT_PRINT_E("BT_GAP", fmt, ## args);} #define GAP_TRACE_API(fmt, args...) {if (gap_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(GAP,API)) BT_PRINT_I("BT_GAP", fmt, ## args);} #define GAP_TRACE_EVENT(fmt, args...) {if (gap_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(GAP,EVENT)) BT_PRINT_D("BT_GAP", fmt, ## args);} #define GAP_TRACE_WARNING(fmt, args...) {if (gap_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(GAP, WARNING)) BT_PRINT_W("BT_GAP", fmt, ## args);} +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + + /* define traces for HID Host */ #define HIDH_TRACE_ERROR(fmt, args...) {if (hh_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(HIDH, ERROR)) BT_PRINT_E("BT_HIDH", fmt, ## args);} #define HIDH_TRACE_WARNING(fmt, args...) {if (hh_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(HIDH, WARNING)) BT_PRINT_W("BT_HIDH", fmt, ## args);} @@ -347,20 +440,81 @@ static inline void trc_dump_buffer(const char *prefix, uint8_t *data, uint16_t l /* Define tracing for the ATT/GATT unit */ +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + +#define GATT_TRACE_ERROR(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_ERROR, "BT_GATT", fmt, ## args); \ + if (gatt_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(GATT, ERROR)) BT_PRINT_E("BT_GATT", fmt, ## args); \ +} + +#define GATT_TRACE_WARNING(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_WARN, "BT_GATT", fmt, ## args); \ + if (gatt_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(GATT, WARNING)) BT_PRINT_W("BT_GATT", fmt, ## args); \ +} + +#define GATT_TRACE_API(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_INFO, "BT_GATT", fmt, ## args); \ + if (gatt_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(GATT, API)) BT_PRINT_I("BT_GATT", fmt, ## args); \ +} + +#define GATT_TRACE_EVENT(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_GATT", fmt, ## args); \ + if (gatt_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(GATT, EVENT)) BT_PRINT_D("BT_GATT", fmt, ## args); \ +} + +#define GATT_TRACE_DEBUG(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_GATT", fmt, ## args); \ + if (gatt_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(GATT, DEBUG)) BT_PRINT_D("BT_GATT", fmt, ## args); \ +} + +#else + #define GATT_TRACE_ERROR(fmt, args...) {if (gatt_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(GATT, ERROR)) BT_PRINT_E("BT_GATT", fmt, ## args);} #define GATT_TRACE_WARNING(fmt, args...) {if (gatt_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(GATT, WARNING)) BT_PRINT_W("BT_GATT", fmt, ## args);} #define GATT_TRACE_API(fmt, args...) {if (gatt_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(GATT,API)) BT_PRINT_I("BT_GATT", fmt, ## args);} #define GATT_TRACE_EVENT(fmt, args...) {if (gatt_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(GATT,EVENT)) BT_PRINT_D("BT_GATT", fmt, ## args);} #define GATT_TRACE_DEBUG(fmt, args...) {if (gatt_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(GATT,DEBUG)) BT_PRINT_D("BT_GATT", fmt, ## args);} +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + /* Define tracing for the SMP unit */ +#if (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) + +#define SMP_TRACE_ERROR(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_ERROR, "BT_SMP", fmt, ## args); \ + if (smp_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(SMP, ERROR)) BT_PRINT_E("BT_SMP", fmt, ## args); \ +} + +#define SMP_TRACE_WARNING(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_WARN, "BT_SMP", fmt, ## args); \ + if (smp_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(SMP, WARNING)) BT_PRINT_W("BT_SMP", fmt, ## args); \ +} + +#define SMP_TRACE_API(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_INFO, "BT_SMP", fmt, ## args); \ + if (smp_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(SMP, API)) BT_PRINT_I("BT_SMP", fmt, ## args); \ +} + +#define SMP_TRACE_EVENT(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_SMP", fmt, ## args); \ + if (smp_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(SMP, EVENT)) BT_PRINT_D("BT_SMP", fmt, ## args); \ +} + +#define SMP_TRACE_DEBUG(fmt, args...) { \ + ble_log_spi_out_printf_enh(BLE_LOG_SPI_OUT_SOURCE_BLUEDROID, BLE_LOG_SPI_OUT_LEVEL_DEBUG, "BT_SMP", fmt, ## args); \ + if (smp_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(SMP, DEBUG)) BT_PRINT_D("BT_SMP", fmt, ## args); \ +} + +#else + #define SMP_TRACE_ERROR(fmt, args...) {if (smp_cb.trace_level >= BT_TRACE_LEVEL_ERROR && BT_LOG_LEVEL_CHECK(SMP, ERROR)) BT_PRINT_E("BT_SMP", fmt, ## args);} #define SMP_TRACE_WARNING(fmt, args...) {if (smp_cb.trace_level >= BT_TRACE_LEVEL_WARNING && BT_LOG_LEVEL_CHECK(SMP, WARNING)) BT_PRINT_W("BT_SMP", fmt, ## args);} #define SMP_TRACE_API(fmt, args...) {if (smp_cb.trace_level >= BT_TRACE_LEVEL_API && BT_LOG_LEVEL_CHECK(SMP,API)) BT_PRINT_I("BT_SMP", fmt, ## args);} #define SMP_TRACE_EVENT(fmt, args...) {if (smp_cb.trace_level >= BT_TRACE_LEVEL_EVENT && BT_LOG_LEVEL_CHECK(SMP,EVENT)) BT_PRINT_D("BT_SMP", fmt, ## args);} #define SMP_TRACE_DEBUG(fmt, args...) {if (smp_cb.trace_level >= BT_TRACE_LEVEL_DEBUG && BT_LOG_LEVEL_CHECK(SMP,DEBUG)) BT_PRINT_D("BT_SMP", fmt, ## args);} +#endif // (BT_BLE_LOG_SPI_OUT_HOST_ENABLED && !CLASSIC_BT_INCLUDED) extern UINT8 btif_trace_level; diff --git a/components/bt/host/bluedroid/hci/hci_hal_h4.c b/components/bt/host/bluedroid/hci/hci_hal_h4.c index 4c23f71bf9..a5b90a6901 100644 --- a/components/bt/host/bluedroid/hci/hci_hal_h4.c +++ b/components/bt/host/bluedroid/hci/hci_hal_h4.c @@ -41,6 +41,10 @@ #include "stack/hcimsgs.h" #include "hci_log/bt_hci_log.h" +#if CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#include "ble_log/ble_log_spi_out.h" +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED + #define HCI_BLE_EVENT 0x3e #define PACKET_TYPE_TO_INBOUND_INDEX(type) ((type) - 2) #define PACKET_TYPE_TO_INDEX(type) ((type) - 1) @@ -567,6 +571,9 @@ void bt_record_hci_data(uint8_t *data, uint16_t len) static int host_recv_pkt_cb(uint8_t *data, uint16_t len) { +#if (BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) + ble_log_spi_out_write_with_ts(BLE_LOG_SPI_OUT_SOURCE_HCI_UPSTREAM, data, len); +#endif // (BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) //Target has packet to host, malloc new buffer for packet BT_HDR *pkt = NULL; #if (BLE_42_SCAN_EN == TRUE) diff --git a/components/bt/host/nimble/esp-hci/src/esp_nimble_hci.c b/components/bt/host/nimble/esp-hci/src/esp_nimble_hci.c index 3c21ba9081..bc263d4b74 100644 --- a/components/bt/host/nimble/esp-hci/src/esp_nimble_hci.c +++ b/components/bt/host/nimble/esp-hci/src/esp_nimble_hci.c @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2015-2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2015-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -24,6 +24,10 @@ #include "bt_common.h" #include "hci_log/bt_hci_log.h" +#if CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED +#include "ble_log/ble_log_spi_out.h" +#endif // CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED + #define NIMBLE_VHCI_TIMEOUT_MS 2000 #define BLE_HCI_EVENT_HDR_LEN (2) #define BLE_HCI_CMD_HDR_LEN (3) @@ -68,6 +72,9 @@ void esp_vhci_host_send_packet_wrapper(uint8_t *data, uint16_t len) #if (BT_HCI_LOG_INCLUDED == TRUE) bt_hci_log_record_hci_data(data[0], &data[1], len - 1); #endif +#if (CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) + ble_log_spi_out_write_with_ts(BLE_LOG_SPI_OUT_SOURCE_HCI_DOWNSTREAM, data, len); +#endif // (CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) esp_vhci_host_send_packet(data, len); } @@ -219,6 +226,10 @@ static int dummy_host_rcv_pkt(uint8_t *data, uint16_t len) */ static int host_rcv_pkt(uint8_t *data, uint16_t len) { +#if (CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) + ble_log_spi_out_write_with_ts(BLE_LOG_SPI_OUT_SOURCE_HCI_UPSTREAM, data, len); +#endif // (CONFIG_BT_BLE_LOG_SPI_OUT_HCI_ENABLED && !SOC_ESP_NIMBLE_CONTROLLER) + bt_record_hci_data(data, len); if(!ble_hs_enabled_state) { diff --git a/components/bt/include/esp32c2/include/esp_bt.h b/components/bt/include/esp32c2/include/esp_bt.h index 3b4d5973a7..262c411470 100644 --- a/components/bt/include/esp32c2/include/esp_bt.h +++ b/components/bt/include/esp32c2/include/esp_bt.h @@ -228,6 +228,9 @@ typedef struct { uint8_t ignore_wl_for_direct_adv; /*!< Ignore the white list for directed advertising */ uint8_t csa2_select; /*!< Select CSA#2 */ uint8_t ble_aa_check; /*!< True if adds a verification step for the Access Address within the CONNECT_IND PDU; false otherwise. Configurable in menuconfig */ + uint8_t ble_llcp_disc_flag; /*!< Flag indicating whether the Controller disconnects after Instant Passed (0x28) error occurs. Configurable in menuconfig. + - The Controller does not disconnect after Instant Passed (0x28) by default. */ + uint16_t scan_backoff_upperlimitmax; /*!< The value of upperlimitmax is 2^n, The maximum value is 256 */ uint8_t vhci_enabled; /*!< VHCI mode is enabled */ uint32_t config_magic; /*!< Configuration magic value */ } esp_bt_controller_config_t; @@ -276,6 +279,8 @@ typedef struct { .ignore_wl_for_direct_adv = 0, \ .csa2_select = DEFAULT_BT_LE_50_FEATURE_SUPPORT, \ .ble_aa_check = DEFAULT_BT_LE_CTRL_CHECK_CONNECT_IND_ACCESS_ADDRESS, \ + .ble_llcp_disc_flag = BT_LE_CTRL_LLCP_DISC_FLAG, \ + .scan_backoff_upperlimitmax = BT_CTRL_SCAN_BACKOFF_UPPERLIMITMAX, \ .vhci_enabled = DEFAULT_BT_LE_VHCI_ENABLED, \ .config_magic = CONFIG_MAGIC, \ } diff --git a/components/bt/include/esp32c5/include/esp_bt.h b/components/bt/include/esp32c5/include/esp_bt.h index fae1c316cc..ec292a573d 100644 --- a/components/bt/include/esp32c5/include/esp_bt.h +++ b/components/bt/include/esp32c5/include/esp_bt.h @@ -225,6 +225,7 @@ typedef struct { - 0 - Disable (default) - 1 - Enable */ uint8_t vhci_enabled; /*!< VHCI mode is enabled */ + uint8_t ptr_check_enabled; /*!< Enable boundary check for internal memory. */ uint32_t config_magic; /*!< Magic number for configuration validation */ } esp_bt_controller_config_t; @@ -279,6 +280,7 @@ typedef struct { .ble_chan_ass_en = DEFAULT_BT_LE_CTRL_CHAN_ASS_EN, \ .ble_data_lenth_zero_aux = DEFAULT_BT_LE_CTRL_ADV_DATA_LENGTH_ZERO_AUX, \ .vhci_enabled = DEFAULT_BT_LE_VHCI_ENABLED, \ + .ptr_check_enabled = DEFAULT_BT_LE_PTR_CHECK_ENABLED, \ .config_magic = CONFIG_MAGIC, \ } @@ -435,11 +437,9 @@ extern int esp_ble_hw_get_static_addr(esp_ble_addr_t *addr); void esp_ble_controller_log_dump_all(bool output); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_PM_ENABLE modem_clock_lpclk_src_t esp_bt_get_lpclk_src(void); void esp_bt_set_lpclk_src(modem_clock_lpclk_src_t clk_src); -#endif // CONFIG_PM_ENABLE #ifdef __cplusplus } diff --git a/components/bt/include/esp32c6/include/esp_bt.h b/components/bt/include/esp32c6/include/esp_bt.h index 1362f104a8..9da4cbe8f4 100644 --- a/components/bt/include/esp32c6/include/esp_bt.h +++ b/components/bt/include/esp32c6/include/esp_bt.h @@ -225,6 +225,7 @@ typedef struct { - 0 - Disable (default) - 1 - Enable */ uint8_t vhci_enabled; /*!< VHCI mode is enabled */ + uint8_t ptr_check_enabled; /*!< Enable boundary check for internal memory. */ uint32_t config_magic; /*!< Magic number for configuration validation */ } esp_bt_controller_config_t; @@ -282,6 +283,7 @@ typedef struct { .ble_chan_ass_en = DEFAULT_BT_LE_CTRL_CHAN_ASS_EN, \ .ble_data_lenth_zero_aux = DEFAULT_BT_LE_CTRL_ADV_DATA_LENGTH_ZERO_AUX, \ .vhci_enabled = DEFAULT_BT_LE_VHCI_ENABLED, \ + .ptr_check_enabled = DEFAULT_BT_LE_PTR_CHECK_ENABLED, \ .config_magic = CONFIG_MAGIC, \ } #elif CONFIG_IDF_TARGET_ESP32C61 @@ -336,6 +338,7 @@ typedef struct { .ble_chan_ass_en = DEFAULT_BT_LE_CTRL_CHAN_ASS_EN, \ .ble_data_lenth_zero_aux = DEFAULT_BT_LE_CTRL_ADV_DATA_LENGTH_ZERO_AUX, \ .vhci_enabled = DEFAULT_BT_LE_VHCI_ENABLED, \ + .ptr_check_enabled = DEFAULT_BT_LE_PTR_CHECK_ENABLED, \ .config_magic = CONFIG_MAGIC, \ } #endif @@ -493,11 +496,9 @@ extern int esp_ble_hw_get_static_addr(esp_ble_addr_t *addr); void esp_ble_controller_log_dump_all(bool output); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_PM_ENABLE modem_clock_lpclk_src_t esp_bt_get_lpclk_src(void); void esp_bt_set_lpclk_src(modem_clock_lpclk_src_t clk_src); -#endif // CONFIG_PM_ENABLE #ifdef __cplusplus } diff --git a/components/bt/include/esp32h2/include/esp_bt.h b/components/bt/include/esp32h2/include/esp_bt.h index 565f43f848..6b412834c0 100644 --- a/components/bt/include/esp32h2/include/esp_bt.h +++ b/components/bt/include/esp32h2/include/esp_bt.h @@ -227,6 +227,7 @@ typedef struct { - 0 - Disable (default) - 1 - Enable */ uint8_t vhci_enabled; /*!< VHCI is enabled */ + uint8_t ptr_check_enabled; /*!< Enable boundary check for internal memory. */ uint32_t config_magic; /*!< Configuration magic value */ } esp_bt_controller_config_t; @@ -282,6 +283,7 @@ typedef struct { .ble_chan_ass_en = DEFAULT_BT_LE_CTRL_CHAN_ASS_EN, \ .ble_data_lenth_zero_aux = DEFAULT_BT_LE_CTRL_ADV_DATA_LENGTH_ZERO_AUX, \ .vhci_enabled = DEFAULT_BT_LE_VHCI_ENABLED, \ + .ptr_check_enabled = DEFAULT_BT_LE_PTR_CHECK_ENABLED, \ .config_magic = CONFIG_MAGIC, \ } @@ -438,11 +440,9 @@ extern int esp_ble_hw_get_static_addr(esp_ble_addr_t *addr); void esp_ble_controller_log_dump_all(bool output); #endif // CONFIG_BT_LE_CONTROLLER_LOG_ENABLED -#if CONFIG_PM_ENABLE modem_clock_lpclk_src_t esp_bt_get_lpclk_src(void); void esp_bt_set_lpclk_src(modem_clock_lpclk_src_t clk_src); -#endif // CONFIG_PM_ENABLE #ifdef __cplusplus } diff --git a/components/esp_rom/esp32c2/ld/esp32c2.rom.ble-eco4.ld b/components/esp_rom/esp32c2/ld/esp32c2.rom.ble-eco4.ld index ed08b1a83c..2281a139cc 100644 --- a/components/esp_rom/esp32c2/ld/esp32c2.rom.ble-eco4.ld +++ b/components/esp_rom/esp32c2/ld/esp32c2.rom.ble-eco4.ld @@ -144,7 +144,7 @@ r_ble_ll_adv_reset = 0x40000c88; r_ble_ll_adv_rpa_timeout = 0x40000c8c; r_ble_ll_adv_rpa_update = 0x40000c90; r_ble_ll_adv_rx_pkt_in = 0x40000c94; -r_ble_ll_adv_scan_req_rxd = 0x40000c98; +//r_ble_ll_adv_scan_req_rxd = 0x40000c98; r_ble_ll_adv_scan_rsp_legacy_pdu_make = 0x40000c9c; r_ble_ll_adv_scan_rsp_pdu_make = 0x40000ca0; r_ble_ll_adv_scheduled = 0x40000ca4; @@ -257,7 +257,7 @@ r_ble_ll_conn_tx_pkt_in = 0x40000e4c; r_ble_ll_conn_update_eff_data_len = 0x40000e50; r_ble_ll_ctrl_chanmap_req_make = 0x40000e54; r_ble_ll_ctrl_chk_proc_start = 0x40000e58; -r_ble_ll_ctrl_conn_param_pdu_make = 0x40000e5c; +//r_ble_ll_ctrl_conn_param_pdu_make = 0x40000e5c; r_ble_ll_ctrl_conn_param_pdu_proc = 0x40000e60; r_ble_ll_ctrl_conn_param_reply = 0x40000e64; r_ble_ll_ctrl_conn_upd_make = 0x40000e68; @@ -284,7 +284,7 @@ r_ble_ll_ctrl_proc_unk_rsp = 0x40000eb8; r_ble_ll_ctrl_proc_with_instant_initiated = 0x40000ebc; r_ble_ll_ctrl_rej_ext_ind_make = 0x40000ec0; r_ble_ll_ctrl_reject_ind_send = 0x40000ec4; -r_ble_ll_ctrl_rx_chanmap_req = 0x40000ec8; +//r_ble_ll_ctrl_rx_chanmap_req = 0x40000ec8; r_ble_ll_ctrl_rx_conn_param_req = 0x40000ecc; //r_ble_ll_ctrl_rx_conn_param_rsp = 0x40000ed0; //r_ble_ll_ctrl_rx_conn_update = 0x40000ed4; @@ -298,7 +298,7 @@ r_ble_ll_ctrl_rx_pdu = 0x40000ef0; r_ble_ll_ctrl_rx_periodic_sync_ind = 0x40000ef4; r_ble_ll_ctrl_rx_phy_req = 0x40000ef8; r_ble_ll_ctrl_rx_phy_rsp = 0x40000efc; -r_ble_ll_ctrl_rx_phy_update_ind = 0x40000f00; +//r_ble_ll_ctrl_rx_phy_update_ind = 0x40000f00; r_ble_ll_ctrl_rx_ping_rsp = 0x40000f04; r_ble_ll_ctrl_rx_reject_ind = 0x40000f08; r_ble_ll_ctrl_rx_sca_req = 0x40000f0c; @@ -346,7 +346,7 @@ r_ble_ll_hci_cmd_rx = 0x40000fb0; r_ble_ll_hci_ctlr_bb_cmd_proc = 0x40000fb4; r_ble_ll_hci_deinit = 0x40000fb8; r_ble_ll_hci_disconnect = 0x40000fbc; -r_ble_ll_hci_env_init = 0x40000fc0; +//r_ble_ll_hci_env_init = 0x40000fc0; r_ble_ll_hci_ev_conn_update = 0x40000fc4; r_ble_ll_hci_ev_databuf_overflow = 0x40000fc8; r_ble_ll_hci_ev_datalen_chg = 0x40000fcc; @@ -755,7 +755,7 @@ r_ble_lll_hci_dtm_tx_test_v2 = 0x40001614; r_ble_lll_hci_dtm_tx_test_v2_ext = 0x40001618; r_ble_lll_init = 0x4000161c; r_ble_lll_init_pre_process = 0x40001620; -r_ble_lll_init_rx_pkt_isr = 0x40001624; +//r_ble_lll_init_rx_pkt_isr = 0x40001624; r_ble_lll_per_adv_coex_dpc_calc_pti_update_itvl = 0x40001628; r_ble_lll_per_adv_coex_dpc_process = 0x4000162c; r_ble_lll_per_adv_coex_dpc_pti_get = 0x40001630; @@ -805,7 +805,7 @@ r_ble_lll_scan_npl_store = 0x400016dc; r_ble_lll_scan_period_timer_cb = 0x400016e0; r_ble_lll_scan_process_adv_in_isr = 0x400016e4; r_ble_lll_scan_process_rsp_in_isr = 0x400016e8; -r_ble_lll_scan_req_backoff = 0x400016ec; +//r_ble_lll_scan_req_backoff = 0x400016ec; r_ble_lll_scan_restart = 0x400016f0; r_ble_lll_scan_rx_isr_on_aux = 0x400016f4; r_ble_lll_scan_rx_isr_on_legacy = 0x400016f8; @@ -1216,7 +1216,7 @@ r_ble_lll_scan_filter_out_useless_adv = 0x40002ff4; r_ble_hw_whitelist_check_in_wl = 0x40002ff8; r_ble_phy_stats_reset = 0x40002ffc; r_ble_phy_ramup_time_set = 0x40003000; -r_ble_lll_rfmgmt_should_skip_light_sleep_check = 0x40003004; +//r_ble_lll_rfmgmt_should_skip_light_sleep_check = 0x40003004; r_ble_phy_rx_err_record = 0x40003008; r_ble_lll_rfmgmt_wake_up_overhead_set = 0x4000300c; //r_ble_lll_conn_event_delete_and_reschedule = 0x40003010; diff --git a/components/esp_rom/esp32c2/ld/esp32c2.rom.ble.ld b/components/esp_rom/esp32c2/ld/esp32c2.rom.ble.ld index 71cc8a7744..1ff67da39f 100644 --- a/components/esp_rom/esp32c2/ld/esp32c2.rom.ble.ld +++ b/components/esp_rom/esp32c2/ld/esp32c2.rom.ble.ld @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2021-2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2021-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -118,7 +118,7 @@ r_ble_ll_adv_rd_sup_adv_sets = 0x40000c7c; r_ble_ll_adv_read_txpwr = 0x40000c80; r_ble_ll_adv_rpa_timeout = 0x40000c8c; r_ble_ll_adv_rpa_update = 0x40000c90; -r_ble_ll_adv_scan_req_rxd = 0x40000c98; +//r_ble_ll_adv_scan_req_rxd = 0x40000c98; r_ble_ll_adv_scan_rsp_legacy_pdu_make = 0x40000c9c; r_ble_ll_adv_scan_rsp_pdu_make = 0x40000ca0; r_ble_ll_adv_scheduled = 0x40000ca4; @@ -202,7 +202,7 @@ r_ble_ll_conn_sm_get = 0x40000e3c; r_ble_ll_conn_tx_pkt_in = 0x40000e4c; r_ble_ll_conn_update_eff_data_len = 0x40000e50; r_ble_ll_ctrl_chanmap_req_make = 0x40000e54; -r_ble_ll_ctrl_conn_param_pdu_make = 0x40000e5c; +//r_ble_ll_ctrl_conn_param_pdu_make = 0x40000e5c; r_ble_ll_ctrl_conn_param_pdu_proc = 0x40000e60; r_ble_ll_ctrl_conn_param_reply = 0x40000e64; r_ble_ll_ctrl_datalen_upd_make = 0x40000e6c; @@ -224,7 +224,7 @@ r_ble_ll_ctrl_proc_stop = 0x40000eb4; r_ble_ll_ctrl_proc_with_instant_initiated = 0x40000ebc; r_ble_ll_ctrl_rej_ext_ind_make = 0x40000ec0; r_ble_ll_ctrl_reject_ind_send = 0x40000ec4; -r_ble_ll_ctrl_rx_chanmap_req = 0x40000ec8; +//r_ble_ll_ctrl_rx_chanmap_req = 0x40000ec8; r_ble_ll_ctrl_rx_conn_param_req = 0x40000ecc; r_ble_ll_ctrl_rx_enc_req = 0x40000ed8; r_ble_ll_ctrl_rx_enc_rsp = 0x40000edc; @@ -234,7 +234,7 @@ r_ble_ll_ctrl_rx_pause_enc_rsp = 0x40000eec; r_ble_ll_ctrl_rx_periodic_sync_ind = 0x40000ef4; r_ble_ll_ctrl_rx_phy_req = 0x40000ef8; r_ble_ll_ctrl_rx_phy_rsp = 0x40000efc; -r_ble_ll_ctrl_rx_phy_update_ind = 0x40000f00; +//r_ble_ll_ctrl_rx_phy_update_ind = 0x40000f00; r_ble_ll_ctrl_rx_ping_rsp = 0x40000f04; r_ble_ll_ctrl_rx_reject_ind = 0x40000f08; r_ble_ll_ctrl_rx_sca_req = 0x40000f0c; @@ -636,7 +636,7 @@ r_ble_lll_scan_npl_restore = 0x400016d8; r_ble_lll_scan_npl_store = 0x400016dc; r_ble_lll_scan_period_timer_cb = 0x400016e0; r_ble_lll_scan_process_adv_in_isr = 0x400016e4; -r_ble_lll_scan_req_backoff = 0x400016ec; +//r_ble_lll_scan_req_backoff = 0x400016ec; r_ble_lll_scan_sched_next_aux = 0x40001700; r_ble_lll_scan_sched_remove = 0x40001704; r_ble_lll_scan_start = 0x40001708;