1
mirror of https://github.com/DarkFlippers/unleashed-firmware.git synced 2025-12-12 04:34:43 +04:00

Prevent idle priority threads from potentially starving the FreeRTOS idle task (#3909)

* FuriThread: Make FuriThreadPriorityIdle equal to the FreeRTOS one, remove FuriThreadPriorityNone
  This magic constant was meaningless,
  FuriThreadPriorityNormal is now assigned by default instead.
* Make furi_thread_list_process private
  Its 'runtime' parameter is to be obtained from FreeRTOS,
  which means apps cannot do it.
* DirectDraw: Remove an useless include and fix memory leak
  Makes this debug app compileable with uFBT out of the box

Co-authored-by: あく <alleteam@gmail.com>
This commit is contained in:
Silent
2024-10-02 19:11:13 +02:00
committed by GitHub
parent 7fc209f001
commit 56d2923f1f
8 changed files with 35 additions and 25 deletions

View File

@@ -1,5 +1,5 @@
#include "thread.h"
#include "thread_list.h"
#include "thread_list_i.h"
#include "kernel.h"
#include "memmgr.h"
#include "memmgr_heap.h"
@@ -65,6 +65,9 @@ struct FuriThread {
// IMPORTANT: container MUST be the FIRST struct member
static_assert(offsetof(FuriThread, container) == 0);
// Our idle priority should be equal to the one from FreeRTOS
static_assert(FuriThreadPriorityIdle == tskIDLE_PRIORITY);
static size_t __furi_thread_stdout_write(FuriThread* thread, const char* data, size_t size);
static int32_t __furi_thread_stdout_flush(FuriThread* thread);
@@ -145,6 +148,8 @@ static void furi_thread_init_common(FuriThread* thread) {
furi_thread_set_appid(thread, "driver");
}
thread->priority = FuriThreadPriorityNormal;
FuriHalRtcHeapTrackMode mode = furi_hal_rtc_get_heap_track_mode();
if(mode == FuriHalRtcHeapTrackModeAll) {
thread->heap_trace_enabled = true;
@@ -269,7 +274,7 @@ void furi_thread_set_context(FuriThread* thread, void* context) {
void furi_thread_set_priority(FuriThread* thread, FuriThreadPriority priority) {
furi_check(thread);
furi_check(thread->state == FuriThreadStateStopped);
furi_check(priority >= FuriThreadPriorityIdle && priority <= FuriThreadPriorityIsr);
furi_check(priority <= FuriThreadPriorityIsr);
thread->priority = priority;
}
@@ -281,9 +286,7 @@ FuriThreadPriority furi_thread_get_priority(FuriThread* thread) {
void furi_thread_set_current_priority(FuriThreadPriority priority) {
furi_check(priority <= FuriThreadPriorityIsr);
UBaseType_t new_priority = priority ? priority : FuriThreadPriorityNormal;
vTaskPrioritySet(NULL, new_priority);
vTaskPrioritySet(NULL, priority);
}
FuriThreadPriority furi_thread_get_current_priority(void) {
@@ -345,7 +348,6 @@ void furi_thread_start(FuriThread* thread) {
furi_thread_set_state(thread, FuriThreadStateStarting);
uint32_t stack_depth = thread->stack_size / sizeof(StackType_t);
UBaseType_t priority = thread->priority ? thread->priority : FuriThreadPriorityNormal;
thread->is_active = true;
@@ -355,7 +357,7 @@ void furi_thread_start(FuriThread* thread) {
thread->name,
stack_depth,
thread,
priority,
thread->priority,
thread->stack_buffer,
&thread->container) == (TaskHandle_t)thread);
}

View File

@@ -30,11 +30,10 @@ typedef enum {
* @brief Enumeration of possible FuriThread priorities.
*/
typedef enum {
FuriThreadPriorityNone = 0, /**< Uninitialized, choose system default */
FuriThreadPriorityIdle = 1, /**< Idle priority */
FuriThreadPriorityIdle = 0, /**< Idle priority */
FuriThreadPriorityLowest = 14, /**< Lowest */
FuriThreadPriorityLow = 15, /**< Low */
FuriThreadPriorityNormal = 16, /**< Normal */
FuriThreadPriorityNormal = 16, /**< Normal, system default */
FuriThreadPriorityHigh = 17, /**< High */
FuriThreadPriorityHighest = 18, /**< Highest */
FuriThreadPriorityIsr =

View File

@@ -84,7 +84,7 @@ FuriThreadListItem* furi_thread_list_get_or_insert(FuriThreadList* instance, Fur
}
void furi_thread_list_process(FuriThreadList* instance, uint32_t runtime, uint32_t tick) {
furi_check(instance);
furi_assert(instance);
instance->runtime_previous = instance->runtime_current;
instance->runtime_current = runtime;

View File

@@ -68,14 +68,6 @@ FuriThreadListItem* furi_thread_list_get_at(FuriThreadList* instance, size_t pos
*/
FuriThreadListItem* furi_thread_list_get_or_insert(FuriThreadList* instance, FuriThread* thread);
/** Process items in the FuriThreadList instance
*
* @param instance The instance
* @param[in] runtime The runtime of the system since start
* @param[in] tick The tick when processing happened
*/
void furi_thread_list_process(FuriThreadList* instance, uint32_t runtime, uint32_t tick);
/** Get percent of time spent in ISR
*
* @param instance The instance

19
furi/core/thread_list_i.h Normal file
View File

@@ -0,0 +1,19 @@
#pragma once
#include "thread_list.h"
#ifdef __cplusplus
extern "C" {
#endif
/** Process items in the FuriThreadList instance
*
* @param instance The instance
* @param[in] runtime The runtime of the system since start
* @param[in] tick The tick when processing happened
*/
void furi_thread_list_process(FuriThreadList* instance, uint32_t runtime, uint32_t tick);
#ifdef __cplusplus
}
#endif