mirror of
https://github.com/espressif/esp-idf.git
synced 2026-09-22 13:01:16 +03:00
feat(bluedroid): Add config to place btu and hci task stack in psram
- Also adjust the osi_thread_stop implementation.
This commit is contained in:
@@ -543,7 +543,7 @@ bt_status_t btc_init(void)
|
||||
{
|
||||
const size_t workqueue_len[] = {BTC_TASK_WORKQUEUE0_LEN, BTC_TASK_WORKQUEUE1_LEN};
|
||||
btc_thread = osi_thread_create(BTC_TASK_NAME, BTC_TASK_STACK_SIZE, BTC_TASK_PRIO, BTC_TASK_PINNED_TO_CORE,
|
||||
BTC_TASK_WORKQUEUE_NUM, workqueue_len);
|
||||
BTC_TASK_WORKQUEUE_NUM, workqueue_len, false);
|
||||
if (btc_thread == NULL) {
|
||||
return BT_STATUS_NOMEM;
|
||||
}
|
||||
|
||||
@@ -36,10 +36,11 @@ typedef enum {
|
||||
* param stack_size: thread stack size
|
||||
* param priority: thread priority
|
||||
* param core: the CPU core which this thread run, OSI_THREAD_CORE_AFFINITY means unspecific CPU core
|
||||
* param work_queue_num: speicify queue number, the queue[0] has highest priority, and the priority is decrease by index
|
||||
* param work_queue_num: specify queue number, the queue[0] has highest priority, and the priority is decrease by index
|
||||
* param in_psram: place the task in PSRAM
|
||||
* return : if create successfully, return thread handler; otherwise return NULL.
|
||||
*/
|
||||
osi_thread_t *osi_thread_create(const char *name, size_t stack_size, int priority, osi_thread_core_t core, uint8_t work_queue_num, const size_t work_queue_len[]);
|
||||
osi_thread_t *osi_thread_create(const char *name, size_t stack_size, int priority, osi_thread_core_t core, uint8_t work_queue_num, const size_t work_queue_len[], bool in_psram);
|
||||
|
||||
/*
|
||||
* brief: Destroy a thread or task
|
||||
|
||||
@@ -43,6 +43,10 @@ struct osi_thread {
|
||||
struct work_queue **work_queues; /*!< Point to queue array, and the priority inverse array index */
|
||||
osi_sem_t work_sem;
|
||||
osi_sem_t stop_sem;
|
||||
#if (CONFIG_BT_BLUEDROID_TASK_STACK_IN_EXT_MEM)
|
||||
StackType_t *stack;
|
||||
StaticTask_t *task;
|
||||
#endif
|
||||
};
|
||||
|
||||
struct osi_thread_start_arg {
|
||||
@@ -179,10 +183,9 @@ static void osi_thread_run(void *arg)
|
||||
}
|
||||
}
|
||||
|
||||
thread->thread_handle = NULL;
|
||||
osi_sem_give(&thread->stop_sem);
|
||||
|
||||
vTaskDelete(NULL);
|
||||
vTaskSuspend(NULL);
|
||||
}
|
||||
|
||||
static int osi_thread_join(osi_thread_t *thread, uint32_t wait_ms)
|
||||
@@ -204,14 +207,20 @@ static void osi_thread_stop(osi_thread_t *thread)
|
||||
//join
|
||||
ret = osi_thread_join(thread, 1000); //wait 1000ms
|
||||
|
||||
//if join failed, delete the task here
|
||||
if (ret != 0 && thread->thread_handle) {
|
||||
//delete the task here
|
||||
if (thread->thread_handle) {
|
||||
if (ret == 0) {
|
||||
while (eTaskGetState(thread->thread_handle) != eSuspended) {
|
||||
vTaskDelay(1);
|
||||
}
|
||||
}
|
||||
vTaskDelete(thread->thread_handle);
|
||||
thread->thread_handle = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
//in linux, the stack_size, priority and core may not be set here, the code will be ignore the arguments
|
||||
osi_thread_t *osi_thread_create(const char *name, size_t stack_size, int priority, osi_thread_core_t core, uint8_t work_queue_num, const size_t work_queue_len[])
|
||||
osi_thread_t *osi_thread_create(const char *name, size_t stack_size, int priority, osi_thread_core_t core, uint8_t work_queue_num, const size_t work_queue_len[], bool in_psram)
|
||||
{
|
||||
int ret;
|
||||
struct osi_thread_start_arg start_arg = {0};
|
||||
@@ -257,9 +266,32 @@ osi_thread_t *osi_thread_create(const char *name, size_t stack_size, int priorit
|
||||
if (ret != 0) {
|
||||
goto _err;
|
||||
}
|
||||
|
||||
if (xTaskCreatePinnedToCore(osi_thread_run, name, stack_size, &start_arg, priority, &thread->thread_handle, core) != pdPASS) {
|
||||
if (in_psram) {
|
||||
#if (CONFIG_BT_BLUEDROID_TASK_STACK_IN_EXT_MEM)
|
||||
thread->task = heap_caps_calloc(1, sizeof(StaticTask_t), MALLOC_CAP_INTERNAL|MALLOC_CAP_8BIT);
|
||||
if (thread->task == NULL) {
|
||||
goto _err;
|
||||
}
|
||||
thread->stack = heap_caps_calloc_prefer(1, stack_size * sizeof(StackType_t),
|
||||
2, MALLOC_CAP_SPIRAM|MALLOC_CAP_8BIT,
|
||||
MALLOC_CAP_INTERNAL|MALLOC_CAP_8BIT);
|
||||
if (thread->stack == NULL) {
|
||||
goto _err;
|
||||
}
|
||||
thread->thread_handle = xTaskCreateStaticPinnedToCore(osi_thread_run, name,
|
||||
stack_size, &start_arg,
|
||||
priority, thread->stack,
|
||||
thread->task, core);
|
||||
if (thread->thread_handle == NULL) {
|
||||
goto _err;
|
||||
}
|
||||
#else
|
||||
goto _err;
|
||||
#endif
|
||||
}else{
|
||||
if (xTaskCreatePinnedToCore(osi_thread_run, name, stack_size, &start_arg, priority, &thread->thread_handle, core) != pdPASS) {
|
||||
goto _err;
|
||||
}
|
||||
}
|
||||
|
||||
osi_sem_take(&start_arg.start_sem, OSI_SEM_MAX_TIMEOUT);
|
||||
@@ -297,6 +329,16 @@ _err:
|
||||
if (thread->stop_sem) {
|
||||
osi_sem_free(&thread->stop_sem);
|
||||
}
|
||||
#if (CONFIG_BT_BLUEDROID_TASK_STACK_IN_EXT_MEM)
|
||||
if (thread->stack) {
|
||||
heap_caps_free(thread->stack);
|
||||
thread->stack = NULL;
|
||||
}
|
||||
if (thread->task) {
|
||||
heap_caps_free(thread->task);
|
||||
thread->task = NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
osi_free(thread);
|
||||
}
|
||||
@@ -330,6 +372,16 @@ void osi_thread_free(osi_thread_t *thread)
|
||||
if (thread->stop_sem) {
|
||||
osi_sem_free(&thread->stop_sem);
|
||||
}
|
||||
#if (CONFIG_BT_BLUEDROID_TASK_STACK_IN_EXT_MEM)
|
||||
if (thread->stack) {
|
||||
heap_caps_free(thread->stack);
|
||||
thread->stack = NULL;
|
||||
}
|
||||
if (thread->task) {
|
||||
heap_caps_free(thread->task);
|
||||
thread->task = NULL;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
osi_free(thread);
|
||||
|
||||
@@ -1279,6 +1279,34 @@ config BT_ALLOCATION_FROM_SPIRAM_FIRST
|
||||
help
|
||||
This select can save the internal RAM if there have the PSRAM
|
||||
|
||||
config BT_BLUEDROID_TASK_STACK_IN_EXT_MEM
|
||||
bool "Place BT task stack in external memory"
|
||||
depends on FREERTOS_TASK_CREATE_ALLOW_EXT_MEM && (!IDF_TARGET_ESP32 || SPIRAM_CACHE_WORKAROUND)
|
||||
default n
|
||||
help
|
||||
Common prerequisites for placing Bluedroid host
|
||||
task stacks in PSRAM.
|
||||
|
||||
config BT_BLUEDROID_BTU_TASK_STACK_IN_EXT_MEM
|
||||
bool "Place BTU task stack in external memory"
|
||||
depends on BT_BLUEDROID_TASK_STACK_IN_EXT_MEM
|
||||
default n
|
||||
help
|
||||
Allocate BTU_TASK stack from external SPIRAM using static task
|
||||
allocation. TCB remains in internal DRAM.
|
||||
|
||||
BTU does not perform NVS operations directly.
|
||||
|
||||
config BT_BLUEDROID_HCI_TASK_STACK_IN_EXT_MEM
|
||||
bool "Place HCI host task stack in external memory"
|
||||
depends on BT_BLUEDROID_TASK_STACK_IN_EXT_MEM
|
||||
default n
|
||||
help
|
||||
Allocate HCI host task (hciT) stack from external SPIRAM using
|
||||
static task allocation. TCB remains in internal DRAM.
|
||||
|
||||
HCI does not perform NVS operations.
|
||||
|
||||
config BT_BLE_DYNAMIC_ENV_MEMORY
|
||||
bool "Use dynamic memory allocation in BT/BLE stack"
|
||||
depends on BT_BLUEDROID_ENABLED
|
||||
|
||||
@@ -114,8 +114,13 @@ int hci_start_up(void)
|
||||
}
|
||||
|
||||
const size_t workqueue_len[] = {HCI_HOST_TASK_WORKQUEUE0_LEN, HCI_HOST_TASK_WORKQUEUE1_LEN};
|
||||
#if (!CONFIG_BT_BLUEDROID_HCI_TASK_STACK_IN_EXT_MEM)
|
||||
hci_host_thread = osi_thread_create(HCI_HOST_TASK_NAME, HCI_HOST_TASK_STACK_SIZE, HCI_HOST_TASK_PRIO, HCI_HOST_TASK_PINNED_TO_CORE,
|
||||
HCI_HOST_TASK_WORKQUEUE_NUM, workqueue_len);
|
||||
HCI_HOST_TASK_WORKQUEUE_NUM, workqueue_len, false);
|
||||
#else
|
||||
hci_host_thread = osi_thread_create(HCI_HOST_TASK_NAME, HCI_HOST_TASK_STACK_SIZE, HCI_HOST_TASK_PRIO, HCI_HOST_TASK_PINNED_TO_CORE,
|
||||
HCI_HOST_TASK_WORKQUEUE_NUM, workqueue_len, true);
|
||||
#endif
|
||||
if (hci_host_thread == NULL) {
|
||||
goto error;
|
||||
}
|
||||
|
||||
@@ -195,8 +195,13 @@ bool BTU_StartUp(void)
|
||||
osi_mutex_new(&btu_l2cap_alarm_lock);
|
||||
|
||||
const size_t workqueue_len[] = {BTU_TASK_WORKQUEUE0_LEN};
|
||||
#if (!CONFIG_BT_BLUEDROID_BTU_TASK_STACK_IN_EXT_MEM)
|
||||
btu_thread = osi_thread_create(BTU_TASK_NAME, BTU_TASK_STACK_SIZE, BTU_TASK_PRIO, BTU_TASK_PINNED_TO_CORE,
|
||||
BTU_TASK_WORKQUEUE_NUM, workqueue_len);
|
||||
BTU_TASK_WORKQUEUE_NUM, workqueue_len, false);
|
||||
#else
|
||||
btu_thread = osi_thread_create(BTU_TASK_NAME, BTU_TASK_STACK_SIZE, BTU_TASK_PRIO, BTU_TASK_PINNED_TO_CORE,
|
||||
BTU_TASK_WORKQUEUE_NUM, workqueue_len, true);
|
||||
#endif
|
||||
if (btu_thread == NULL) {
|
||||
goto error_exit;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user