From 1620d97299b758a27d9ec57b5c6f439e1425c4cc Mon Sep 17 00:00:00 2001 From: Darian Leung Date: Tue, 1 Aug 2023 12:40:01 +0200 Subject: [PATCH] change(freertos): Optimized xTaskRemoveFromEventList() This commit optimizes xTaskRemoveFromEventList() by removing the listLIST_IS_EMPTY() check from single core builds. The scenario of the event list being empty when the function is called can only occur on multi-core builds. --- components/freertos/FreeRTOS-Kernel/tasks.c | 44 +++++++++++---------- 1 file changed, 23 insertions(+), 21 deletions(-) diff --git a/components/freertos/FreeRTOS-Kernel/tasks.c b/components/freertos/FreeRTOS-Kernel/tasks.c index 2a28dc6e7b..4a851872af 100644 --- a/components/freertos/FreeRTOS-Kernel/tasks.c +++ b/components/freertos/FreeRTOS-Kernel/tasks.c @@ -3932,23 +3932,31 @@ BaseType_t xTaskRemoveFromEventList( const List_t * const pxEventList ) } #endif /* configNUM_CORES > 1 */ { - /* Before taking the kernel lock, another task/ISR could have already - * emptied the pxEventList. So we insert a check here to see if - * pxEventList is empty before attempting to remove an item from it. */ - if( listLIST_IS_EMPTY( pxEventList ) == pdFALSE ) + /* The event list is sorted in priority order, so the first in the list can + * be removed as it is known to be the highest priority. Remove the TCB from + * the delayed list, and add it to the ready list. */ + #if ( configNUM_CORES > 1 ) + /* Before taking the kernel lock, another task/ISR could have already + * emptied the pxEventList. So we insert a check here to see if + * pxEventList is empty before attempting to remove an item from it. */ + if( listLIST_IS_EMPTY( pxEventList ) == pdTRUE ) + { + /* The pxEventList was emptied before we entered the critical section, + * Nothing to do except return pdFALSE. */ + xReturn = pdFALSE; + } + else + #else /* configNUM_CORES > 1 */ + /* If an event is for a queue that is locked then this function will never + * get called - the lock count on the queue will get modified instead. This + * means exclusive access to the event list is guaranteed here. + * + * This function assumes that a check has already been made to ensure that + * pxEventList is not empty. */ + #endif /* configNUM_CORES > 1 */ { BaseType_t xCurCoreID = xPortGetCoreID(); - /* The event list is sorted in priority order, so the first in the list can - * be removed as it is known to be the highest priority. Remove the TCB from - * the delayed list, and add it to the ready list. - * - * If an event is for a queue that is locked then this function will never - * get called - the lock count on the queue will get modified instead. This - * means exclusive access to the event list is guaranteed here. - * - * This function assumes that a check has already been made to ensure that - * pxEventList is not empty. */ pxUnblockedTCB = listGET_OWNER_OF_HEAD_ENTRY( pxEventList ); /*lint !e9079 void * is used as this macro is used with timers and co-routines too. Alignment is known to be fine as the type of the pointer stored and retrieved is the same. */ configASSERT( pxUnblockedTCB ); ( void ) uxListRemove( &( pxUnblockedTCB->xEventListItem ) ); @@ -4013,12 +4021,6 @@ BaseType_t xTaskRemoveFromEventList( const List_t * const pxEventList ) xReturn = pdFALSE; } } - else - { - /* The pxEventList was emptied before we entered the critical section, - * Nothing to do except return pdFALSE. */ - xReturn = pdFALSE; - } } #if ( configNUM_CORES > 1 ) /* Release the previously taken kernel lock. */ @@ -4133,7 +4135,7 @@ void vTaskRemoveFromUnorderedEventList( ListItem_t * pxEventListItem, * a context switch is required. This function is called with the * scheduler suspended so xYieldPending is set so the context switch * occurs immediately that the scheduler is resumed (unsuspended). */ - xYieldPending = pdTRUE; + xYieldPending[ xCurCoreID ] = pdTRUE; } } }