Make xTaskIsTaskSuspended() a private function as it should only be called from within critical sections.

Fix issue in and simplify the xTaskRemoveFromUnorderedEventList() function.  The function is new to the V8 release candidates so does not effect official released code.
pull/1/head
Richard Barry 11 years ago
parent eea669240b
commit 84f4ae9aa0

@ -84,7 +84,6 @@ only for ports that are using the MPU. */
#define vTaskPrioritySet MPU_vTaskPrioritySet #define vTaskPrioritySet MPU_vTaskPrioritySet
#define eTaskGetState MPU_eTaskGetState #define eTaskGetState MPU_eTaskGetState
#define vTaskSuspend MPU_vTaskSuspend #define vTaskSuspend MPU_vTaskSuspend
#define xTaskIsTaskSuspended MPU_xTaskIsTaskSuspended
#define vTaskResume MPU_vTaskResume #define vTaskResume MPU_vTaskResume
#define vTaskSuspendAll MPU_vTaskSuspendAll #define vTaskSuspendAll MPU_vTaskSuspendAll
#define xTaskResumeAll MPU_xTaskResumeAll #define xTaskResumeAll MPU_xTaskResumeAll

@ -173,8 +173,8 @@ typedef void * QueueSetMemberHandle_t;
* <pre> * <pre>
BaseType_t xQueueSendToToFront( BaseType_t xQueueSendToToFront(
QueueHandle_t xQueue, QueueHandle_t xQueue,
const void * pvItemToQueue, const void *pvItemToQueue,
TickType_t xTicksToWait TickType_t xTicksToWait
); );
* </pre> * </pre>
* *

@ -1028,17 +1028,6 @@ void vTaskSuspendAll( void ) PRIVILEGED_FUNCTION;
*/ */
BaseType_t xTaskResumeAll( void ) PRIVILEGED_FUNCTION; BaseType_t xTaskResumeAll( void ) PRIVILEGED_FUNCTION;
/**
* task. h
* <pre>BaseType_t xTaskIsTaskSuspended( const TaskHandle_t xTask );</pre>
*
* Utility task that simply returns pdTRUE if the task referenced by xTask is
* currently in the Suspended state, or pdFALSE if the task referenced by xTask
* is in any other state.
*
*/
BaseType_t xTaskIsTaskSuspended( const TaskHandle_t xTask ) PRIVILEGED_FUNCTION;
/*----------------------------------------------------------- /*-----------------------------------------------------------
* TASK UTILITIES * TASK UTILITIES
*----------------------------------------------------------*/ *----------------------------------------------------------*/

@ -179,7 +179,6 @@ UBaseType_t MPU_uxTaskPriorityGet( TaskHandle_t pxTask );
void MPU_vTaskPrioritySet( TaskHandle_t pxTask, UBaseType_t uxNewPriority ); void MPU_vTaskPrioritySet( TaskHandle_t pxTask, UBaseType_t uxNewPriority );
eTaskState MPU_eTaskGetState( TaskHandle_t pxTask ); eTaskState MPU_eTaskGetState( TaskHandle_t pxTask );
void MPU_vTaskSuspend( TaskHandle_t pxTaskToSuspend ); void MPU_vTaskSuspend( TaskHandle_t pxTaskToSuspend );
BaseType_t MPU_xTaskIsTaskSuspended( TaskHandle_t xTask );
void MPU_vTaskResume( TaskHandle_t pxTaskToResume ); void MPU_vTaskResume( TaskHandle_t pxTaskToResume );
void MPU_vTaskSuspendAll( void ); void MPU_vTaskSuspendAll( void );
BaseType_t MPU_xTaskResumeAll( void ); BaseType_t MPU_xTaskResumeAll( void );
@ -787,19 +786,6 @@ BaseType_t xRunningPrivileged = prvRaisePrivilege();
#endif #endif
/*-----------------------------------------------------------*/ /*-----------------------------------------------------------*/
#if ( INCLUDE_vTaskSuspend == 1 )
BaseType_t MPU_xTaskIsTaskSuspended( TaskHandle_t xTask )
{
BaseType_t xReturn;
BaseType_t xRunningPrivileged = prvRaisePrivilege();
xReturn = xTaskIsTaskSuspended( xTask );
portRESET_PRIVILEGE( xRunningPrivileged );
return xReturn;
}
#endif
/*-----------------------------------------------------------*/
#if ( INCLUDE_vTaskSuspend == 1 ) #if ( INCLUDE_vTaskSuspend == 1 )
void MPU_vTaskResume( TaskHandle_t pxTaskToResume ) void MPU_vTaskResume( TaskHandle_t pxTaskToResume )
{ {

@ -86,7 +86,7 @@ privileged Vs unprivileged linkage and placement. */
#undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE /*lint !e961 !e750. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE /*lint !e961 !e750. */
/* Constants used with the cRxLock and xTxLock structure members. */ /* Constants used with the xRxLock and xTxLock structure members. */
#define queueUNLOCKED ( ( BaseType_t ) -1 ) #define queueUNLOCKED ( ( BaseType_t ) -1 )
#define queueLOCKED_UNMODIFIED ( ( BaseType_t ) 0 ) #define queueLOCKED_UNMODIFIED ( ( BaseType_t ) 0 )
@ -1038,11 +1038,11 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue;
link: http://www.freertos.org/RTOS-Cortex-M3-M4.html */ link: http://www.freertos.org/RTOS-Cortex-M3-M4.html */
portASSERT_IF_INTERRUPT_PRIORITY_INVALID(); portASSERT_IF_INTERRUPT_PRIORITY_INVALID();
/* Similar to xQueueGenericSend, except we don't block if there is no room /* Similar to xQueueGenericSend, except without blocking if there is no room
in the queue. Also we don't directly wake a task that was blocked on a in the queue. Also don't directly wake a task that was blocked on a queue
queue read, instead we return a flag to say whether a context switch is read, instead return a flag to say whether a context switch is required or
required or not (i.e. has a task with a higher priority than us been woken not (i.e. has a task with a higher priority than us been woken by this
by this post). */ post). */
uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR(); uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();
{ {
if( ( pxQueue->uxMessagesWaiting < pxQueue->uxLength ) || ( xCopyPosition == queueOVERWRITE ) ) if( ( pxQueue->uxMessagesWaiting < pxQueue->uxLength ) || ( xCopyPosition == queueOVERWRITE ) )
@ -1051,7 +1051,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue;
prvCopyDataToQueue( pxQueue, pvItemToQueue, xCopyPosition ); prvCopyDataToQueue( pxQueue, pvItemToQueue, xCopyPosition );
/* If the queue is locked we do not alter the event list. This will /* The event list is not altered if the queue is locked. This will
be done when the queue is unlocked later. */ be done when the queue is unlocked later. */
if( pxQueue->xTxLock == queueUNLOCKED ) if( pxQueue->xTxLock == queueUNLOCKED )
{ {
@ -2349,6 +2349,8 @@ BaseType_t xReturn;
Queue_t *pxQueueSetContainer = pxQueue->pxQueueSetContainer; Queue_t *pxQueueSetContainer = pxQueue->pxQueueSetContainer;
BaseType_t xReturn = pdFALSE; BaseType_t xReturn = pdFALSE;
/* This function must be called form a critical section. */
configASSERT( pxQueueSetContainer ); configASSERT( pxQueueSetContainer );
configASSERT( pxQueueSetContainer->uxMessagesWaiting < pxQueueSetContainer->uxLength ); configASSERT( pxQueueSetContainer->uxMessagesWaiting < pxQueueSetContainer->uxLength );

@ -214,13 +214,22 @@ PRIVILEGED_DATA static volatile UBaseType_t uxCurrentNumberOfTasks = ( UBaseTyp
PRIVILEGED_DATA static volatile TickType_t xTickCount = ( TickType_t ) 0U; PRIVILEGED_DATA static volatile TickType_t xTickCount = ( TickType_t ) 0U;
PRIVILEGED_DATA static volatile UBaseType_t uxTopReadyPriority = tskIDLE_PRIORITY; PRIVILEGED_DATA static volatile UBaseType_t uxTopReadyPriority = tskIDLE_PRIORITY;
PRIVILEGED_DATA static volatile BaseType_t xSchedulerRunning = pdFALSE; PRIVILEGED_DATA static volatile BaseType_t xSchedulerRunning = pdFALSE;
PRIVILEGED_DATA static volatile UBaseType_t uxSchedulerSuspended = ( UBaseType_t ) pdFALSE;
PRIVILEGED_DATA static volatile UBaseType_t uxPendedTicks = ( UBaseType_t ) 0U; PRIVILEGED_DATA static volatile UBaseType_t uxPendedTicks = ( UBaseType_t ) 0U;
PRIVILEGED_DATA static volatile BaseType_t xYieldPending = pdFALSE; PRIVILEGED_DATA static volatile BaseType_t xYieldPending = pdFALSE;
PRIVILEGED_DATA static volatile BaseType_t xNumOfOverflows = ( BaseType_t ) 0; PRIVILEGED_DATA static volatile BaseType_t xNumOfOverflows = ( BaseType_t ) 0;
PRIVILEGED_DATA static UBaseType_t uxTaskNumber = ( UBaseType_t ) 0U; PRIVILEGED_DATA static UBaseType_t uxTaskNumber = ( UBaseType_t ) 0U;
PRIVILEGED_DATA static volatile TickType_t xNextTaskUnblockTime = portMAX_DELAY; PRIVILEGED_DATA static volatile TickType_t xNextTaskUnblockTime = portMAX_DELAY;
/* Context switches are held pending while the scheduler is suspended. Also,
interrupts must not manipulate the xStateListItem of a TCB, or any of the
lists the xStateListItem can be referenced from, if the scheduler is suspended.
If an interrupt needs to unblock a task while the scheduler is suspended then it
moves the task's event list item into the xPendingReadyList, ready for the
kernel to move the task from the pending ready list into the real ready list
when the scheduler is unsuspended. The pending ready list itself can only be
accessed from a critical section. */
PRIVILEGED_DATA static volatile UBaseType_t uxSchedulerSuspended = ( UBaseType_t ) pdFALSE;
#if ( configGENERATE_RUN_TIME_STATS == 1 ) #if ( configGENERATE_RUN_TIME_STATS == 1 )
PRIVILEGED_DATA static uint32_t ulTaskSwitchedInTime = 0UL; /*< Holds the value of a timer/counter the last time a task was switched in. */ PRIVILEGED_DATA static uint32_t ulTaskSwitchedInTime = 0UL; /*< Holds the value of a timer/counter the last time a task was switched in. */
@ -393,6 +402,13 @@ to its original value when it is released. */
*/ */
static void prvInitialiseTCBVariables( TCB_t * const pxTCB, const char * const pcName, UBaseType_t uxPriority, const MemoryRegion_t * const xRegions, const uint16_t usStackDepth ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ static void prvInitialiseTCBVariables( TCB_t * const pxTCB, const char * const pcName, UBaseType_t uxPriority, const MemoryRegion_t * const xRegions, const uint16_t usStackDepth ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */
/**
* Utility task that simply returns pdTRUE if the task referenced by xTask is
* currently in the Suspended state, or pdFALSE if the task referenced by xTask
* is in any other state.
*/
static BaseType_t prvTaskIsTaskSuspended( const TaskHandle_t xTask ) PRIVILEGED_FUNCTION;
/* /*
* Utility to ready all the lists used by the scheduler. This is called * Utility to ready all the lists used by the scheduler. This is called
* automatically upon the creation of the first task. * automatically upon the creation of the first task.
@ -806,9 +822,8 @@ TCB_t * pxNewTCB;
{ {
traceTASK_DELAY_UNTIL(); traceTASK_DELAY_UNTIL();
/* We must remove ourselves from the ready list before adding /* Remove the task from the ready list before adding it to the
ourselves to the blocked list as the same list item is used for blocked list as the same list item is used for both lists. */
both lists. */
if( uxListRemove( &( pxCurrentTCB->xGenericListItem ) ) == ( UBaseType_t ) 0 ) if( uxListRemove( &( pxCurrentTCB->xGenericListItem ) ) == ( UBaseType_t ) 0 )
{ {
/* The current task must be in a ready list, so there is /* The current task must be in a ready list, so there is
@ -1254,25 +1269,25 @@ TCB_t * pxNewTCB;
#if ( INCLUDE_vTaskSuspend == 1 ) #if ( INCLUDE_vTaskSuspend == 1 )
BaseType_t xTaskIsTaskSuspended( const TaskHandle_t xTask ) static BaseType_t prvTaskIsTaskSuspended( const TaskHandle_t xTask )
{ {
BaseType_t xReturn = pdFALSE; BaseType_t xReturn = pdFALSE;
const TCB_t * const pxTCB = ( TCB_t * ) xTask; const TCB_t * const pxTCB = ( TCB_t * ) xTask;
/* Accesses xPendingReadyList so must be called from a critical
section. */
/* It does not make sense to check if the calling task is suspended. */ /* It does not make sense to check if the calling task is suspended. */
configASSERT( xTask ); configASSERT( xTask );
/* Is the task we are attempting to resume actually in the /* Is the task being resumed actually in the suspended list? */
suspended list? */
if( listIS_CONTAINED_WITHIN( &xSuspendedTaskList, &( pxTCB->xGenericListItem ) ) != pdFALSE ) if( listIS_CONTAINED_WITHIN( &xSuspendedTaskList, &( pxTCB->xGenericListItem ) ) != pdFALSE )
{ {
/* Has the task already been resumed from within an ISR? */ /* Has the task already been resumed from within an ISR? */
if( listIS_CONTAINED_WITHIN( &xPendingReadyList, &( pxTCB->xEventListItem ) ) == pdFALSE ) if( listIS_CONTAINED_WITHIN( &xPendingReadyList, &( pxTCB->xEventListItem ) ) == pdFALSE )
{ {
/* Is it in the suspended list because it is in the /* Is it in the suspended list because it is in the Suspended
Suspended state? It is possible to be in the suspended state, or because is is blocked with no timeout? */
list because it is blocked on a task with no timeout
specified. */
if( listIS_CONTAINED_WITHIN( NULL, &( pxTCB->xEventListItem ) ) != pdFALSE ) if( listIS_CONTAINED_WITHIN( NULL, &( pxTCB->xEventListItem ) ) != pdFALSE )
{ {
xReturn = pdTRUE; xReturn = pdTRUE;
@ -1313,7 +1328,7 @@ TCB_t * pxNewTCB;
{ {
taskENTER_CRITICAL(); taskENTER_CRITICAL();
{ {
if( xTaskIsTaskSuspended( pxTCB ) == pdTRUE ) if( prvTaskIsTaskSuspended( pxTCB ) == pdTRUE )
{ {
traceTASK_RESUME( pxTCB ); traceTASK_RESUME( pxTCB );
@ -1382,12 +1397,15 @@ TCB_t * pxNewTCB;
uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR(); uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();
{ {
if( xTaskIsTaskSuspended( pxTCB ) == pdTRUE ) if( prvTaskIsTaskSuspended( pxTCB ) == pdTRUE )
{ {
traceTASK_RESUME_FROM_ISR( pxTCB ); traceTASK_RESUME_FROM_ISR( pxTCB );
/* Check the ready lists can be accessed. */
if( uxSchedulerSuspended == ( UBaseType_t ) pdFALSE ) if( uxSchedulerSuspended == ( UBaseType_t ) pdFALSE )
{ {
/* Ready lists can be accessed so move the task from the
suspended list to the ready list directly. */
if( pxTCB->uxPriority >= pxCurrentTCB->uxPriority ) if( pxTCB->uxPriority >= pxCurrentTCB->uxPriority )
{ {
xYieldRequired = pdTRUE; xYieldRequired = pdTRUE;
@ -1402,9 +1420,9 @@ TCB_t * pxNewTCB;
} }
else else
{ {
/* We cannot access the delayed or ready lists, so will hold this /* The delayed or ready lists cannot be accessed so the task
task pending until the scheduler is resumed, at which point a is held in the pending ready list until the scheduler is
yield will be performed if necessary. */ unsuspended. */
vListInsertEnd( &( xPendingReadyList ), &( pxTCB->xEventListItem ) ); vListInsertEnd( &( xPendingReadyList ), &( pxTCB->xEventListItem ) );
} }
} }
@ -2144,17 +2162,18 @@ TickType_t xTimeToWake;
configASSERT( pxEventList ); configASSERT( pxEventList );
/* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE /* THIS FUNCTION MUST BE CALLED WITH EITHER INTERRUPTS DISABLED OR THE
SCHEDULER SUSPENDED. */ SCHEDULER SUSPENDED AND THE QUEUE BEING ACCESSED LOCKED. */
/* Place the event list item of the TCB in the appropriate event list. /* Place the event list item of the TCB in the appropriate event list.
This is placed in the list in priority order so the highest priority task This is placed in the list in priority order so the highest priority task
is the first to be woken by the event. */ is the first to be woken by the event. The queue that contains the event
list is locked, preventing simultaneous access from interrupts. */
vListInsert( pxEventList, &( pxCurrentTCB->xEventListItem ) ); vListInsert( pxEventList, &( pxCurrentTCB->xEventListItem ) );
/* We must remove ourselves from the ready list before adding ourselves /* The task must be removed from from the ready list before it is added to
to the blocked list as the same list item is used for both lists. We have the blocked list as the same list item is used for both lists. Exclusive
exclusive access to the ready lists as the scheduler is locked. */ access to the ready lists guaranteed because the scheduler is locked. */
if( uxListRemove( &( pxCurrentTCB->xGenericListItem ) ) == ( UBaseType_t ) 0 ) if( uxListRemove( &( pxCurrentTCB->xGenericListItem ) ) == ( UBaseType_t ) 0 )
{ {
/* The current task must be in a ready list, so there is no need to /* The current task must be in a ready list, so there is no need to
@ -2170,15 +2189,16 @@ TickType_t xTimeToWake;
{ {
if( xTicksToWait == portMAX_DELAY ) if( xTicksToWait == portMAX_DELAY )
{ {
/* Add ourselves to the suspended task list instead of a delayed task /* Add the task to the suspended task list instead of a delayed task
list to ensure we are not woken by a timing event. We will block list to ensure the task is not woken by a timing event. It will
indefinitely. */ block indefinitely. */
vListInsertEnd( &xSuspendedTaskList, &( pxCurrentTCB->xGenericListItem ) ); vListInsertEnd( &xSuspendedTaskList, &( pxCurrentTCB->xGenericListItem ) );
} }
else else
{ {
/* Calculate the time at which the task should be woken if the event does /* Calculate the time at which the task should be woken if the event
not occur. This may overflow but this doesn't matter. */ does not occur. This may overflow but this doesn't matter, the
scheduler will handle it. */
xTimeToWake = xTickCount + xTicksToWait; xTimeToWake = xTickCount + xTicksToWait;
prvAddCurrentTaskToDelayedList( xTimeToWake ); prvAddCurrentTaskToDelayedList( xTimeToWake );
} }
@ -2186,7 +2206,8 @@ TickType_t xTimeToWake;
#else /* INCLUDE_vTaskSuspend */ #else /* INCLUDE_vTaskSuspend */
{ {
/* Calculate the time at which the task should be woken if the event does /* Calculate the time at which the task should be woken if the event does
not occur. This may overflow but this doesn't matter. */ not occur. This may overflow but this doesn't matter, the scheduler
will handle it. */
xTimeToWake = xTickCount + xTicksToWait; xTimeToWake = xTickCount + xTicksToWait;
prvAddCurrentTaskToDelayedList( xTimeToWake ); prvAddCurrentTaskToDelayedList( xTimeToWake );
} }
@ -2200,14 +2221,20 @@ TickType_t xTimeToWake;
configASSERT( pxEventList ); configASSERT( pxEventList );
/* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE /* THIS FUNCTION MUST BE CALLED WITH THE SCHEDULER SUSPENDED. It is used by
SCHEDULER SUSPENDED. */ the event groups implementation. */
configASSERT( uxSchedulerSuspended != 0 );
/* Store the item value in the event list item. */ /* Store the item value in the event list item. It is safe to access the
event list item here as interrupts won't access the event list item of a
task that is not in the Blocked state. */
listSET_LIST_ITEM_VALUE( &( pxCurrentTCB->xEventListItem ), xItemValue | taskEVENT_LIST_ITEM_VALUE_IN_USE ); listSET_LIST_ITEM_VALUE( &( pxCurrentTCB->xEventListItem ), xItemValue | taskEVENT_LIST_ITEM_VALUE_IN_USE );
/* Place the event list item of the TCB at the end of the appropriate event /* Place the event list item of the TCB at the end of the appropriate event
list. */ list. It is safe to access the event list here because it is part of an
event group implementation - and interrupts don't access event groups
directly (instead they access them indirectly by pending function calls to
the task level). */
vListInsertEnd( pxEventList, &( pxCurrentTCB->xEventListItem ) ); vListInsertEnd( pxEventList, &( pxCurrentTCB->xEventListItem ) );
/* The task must be removed from the ready list before it is added to the /* The task must be removed from the ready list before it is added to the
@ -2235,8 +2262,9 @@ TickType_t xTimeToWake;
} }
else else
{ {
/* Calculate the time at which the task should be woken if the event does /* Calculate the time at which the task should be woken if the event
not occur. This may overflow but this doesn't matter. */ does not occur. This may overflow but this doesn't matter, the
kernel will manage it correctly. */
xTimeToWake = xTickCount + xTicksToWait; xTimeToWake = xTickCount + xTicksToWait;
prvAddCurrentTaskToDelayedList( xTimeToWake ); prvAddCurrentTaskToDelayedList( xTimeToWake );
} }
@ -2244,7 +2272,8 @@ TickType_t xTimeToWake;
#else /* INCLUDE_vTaskSuspend */ #else /* INCLUDE_vTaskSuspend */
{ {
/* Calculate the time at which the task should be woken if the event does /* Calculate the time at which the task should be woken if the event does
not occur. This may overflow but this doesn't matter. */ not occur. This may overflow but this doesn't matter, the kernel
will manage it correctly. */
xTimeToWake = xTickCount + xTicksToWait; xTimeToWake = xTickCount + xTicksToWait;
prvAddCurrentTaskToDelayedList( xTimeToWake ); prvAddCurrentTaskToDelayedList( xTimeToWake );
} }
@ -2302,16 +2331,16 @@ BaseType_t xTaskRemoveFromEventList( const List_t * const pxEventList )
TCB_t *pxUnblockedTCB; TCB_t *pxUnblockedTCB;
BaseType_t xReturn; BaseType_t xReturn;
/* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE /* THIS FUNCTION MUST BE CALLED FROM A CRITICAL SECTION. It can also be
SCHEDULER SUSPENDED. It can also be called from within an ISR. */ called from a critical section within an ISR. */
/* The event list is sorted in priority order, so we can remove the /* The event list is sorted in priority order, so the first in the list can
first in the list, remove the TCB from the delayed list, and add be removed as it is known to be the highest priority. Remove the TCB from
it to the ready list. 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 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 get called - the lock count on the queue will get modified instead. This
means we can always expect exclusive access to the event list here. means exclusive access to the event list is guaranteed here.
This function assumes that a check has already been made to ensure that This function assumes that a check has already been made to ensure that
pxEventList is not empty. */ pxEventList is not empty. */
@ -2333,10 +2362,9 @@ BaseType_t xReturn;
if( pxUnblockedTCB->uxPriority > pxCurrentTCB->uxPriority ) if( pxUnblockedTCB->uxPriority > pxCurrentTCB->uxPriority )
{ {
/* Return true if the task removed from the event list has /* Return true if the task removed from the event list has a higher
a higher priority than the calling task. This allows priority than the calling task. This allows the calling task to know if
the calling task to know if it should force a context it should force a context switch now. */
switch now. */
xReturn = pdTRUE; xReturn = pdTRUE;
/* Mark that a yield is pending in case the user is not using the /* Mark that a yield is pending in case the user is not using the
@ -2357,29 +2385,24 @@ BaseType_t xTaskRemoveFromUnorderedEventList( ListItem_t * pxEventListItem, cons
TCB_t *pxUnblockedTCB; TCB_t *pxUnblockedTCB;
BaseType_t xReturn; BaseType_t xReturn;
/* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE /* THIS FUNCTION MUST BE CALLED WITH THE SCHEDULER SUSPENDED. It is used by
SCHEDULER SUSPENDED. It can also be called from within an ISR. */ the event flags implementation. */
configASSERT( uxSchedulerSuspended != pdFALSE );
/* Store the new item value in the event list. */ /* Store the new item value in the event list. */
listSET_LIST_ITEM_VALUE( pxEventListItem, xItemValue | taskEVENT_LIST_ITEM_VALUE_IN_USE ); listSET_LIST_ITEM_VALUE( pxEventListItem, xItemValue | taskEVENT_LIST_ITEM_VALUE_IN_USE );
/* Remove the TCB from the delayed list, and add it to the ready list. */ /* Remove the event list form the event flag. Interrupts do not access
event flags. */
pxUnblockedTCB = ( TCB_t * ) listGET_LIST_ITEM_OWNER( pxEventListItem ); pxUnblockedTCB = ( TCB_t * ) listGET_LIST_ITEM_OWNER( pxEventListItem );
configASSERT( pxUnblockedTCB ); configASSERT( pxUnblockedTCB );
( void ) uxListRemove( pxEventListItem ); ( void ) uxListRemove( pxEventListItem );
if( uxSchedulerSuspended == ( UBaseType_t ) pdFALSE ) /* Remove the task from the delayed list and add it to the ready list. The
{ scheduler is suspended so interrupts will not be accessing the ready
( void ) uxListRemove( &( pxUnblockedTCB->xGenericListItem ) ); lists. */
prvAddTaskToReadyList( pxUnblockedTCB ); ( void ) uxListRemove( &( pxUnblockedTCB->xGenericListItem ) );
} prvAddTaskToReadyList( pxUnblockedTCB );
else
{
/* Cannot access the delayed or ready lists, so will hold this task
pending until the scheduler is resumed. */
vListInsertEnd( &( xPendingReadyList ), pxEventListItem );
}
if( pxUnblockedTCB->uxPriority > pxCurrentTCB->uxPriority ) if( pxUnblockedTCB->uxPriority > pxCurrentTCB->uxPriority )
{ {
@ -2812,7 +2835,9 @@ static void prvCheckTasksWaitingTermination( void )
while( uxTasksDeleted > ( UBaseType_t ) 0U ) while( uxTasksDeleted > ( UBaseType_t ) 0U )
{ {
vTaskSuspendAll(); vTaskSuspendAll();
{
xListIsEmpty = listLIST_IS_EMPTY( &xTasksWaitingTermination ); xListIsEmpty = listLIST_IS_EMPTY( &xTasksWaitingTermination );
}
( void ) xTaskResumeAll(); ( void ) xTaskResumeAll();
if( xListIsEmpty == pdFALSE ) if( xListIsEmpty == pdFALSE )
@ -2932,6 +2957,21 @@ TCB_t *pxNewTCB;
pxTaskStatusArray[ uxTask ].eCurrentState = eState; pxTaskStatusArray[ uxTask ].eCurrentState = eState;
pxTaskStatusArray[ uxTask ].uxCurrentPriority = pxNextTCB->uxPriority; pxTaskStatusArray[ uxTask ].uxCurrentPriority = pxNextTCB->uxPriority;
#if ( INCLUDE_vTaskSuspend == 1 )
{
/* If the task is in the suspended list then there is a chance
it is actually just blocked indefinitely - so really it should
be reported as being in the Blocked state. */
if( eState == eSuspended )
{
if( listLIST_ITEM_CONTAINER( &( pxNextTCB->xEventListItem ) ) != NULL )
{
pxTaskStatusArray[ uxTask ].eCurrentState = eBlocked;
}
}
}
#endif /* INCLUDE_vTaskSuspend */
#if ( configUSE_MUTEXES == 1 ) #if ( configUSE_MUTEXES == 1 )
{ {
pxTaskStatusArray[ uxTask ].uxBasePriority = pxNextTCB->uxBasePriority; pxTaskStatusArray[ uxTask ].uxBasePriority = pxNextTCB->uxBasePriority;

Loading…
Cancel
Save