/*\r
- FreeRTOS V7.0.2 - Copyright (C) 2011 Real Time Engineers Ltd.\r
+ FreeRTOS V7.1.0 - Copyright (C) 2011 Real Time Engineers Ltd.\r
\r
\r
***************************************************************************\r
#endif\r
\r
#if ( configUSE_TRACE_FACILITY == 1 )\r
- unsigned portBASE_TYPE uxTCBNumber; /*< This is used for tracing the scheduler and making debugging easier only. */\r
+ unsigned portBASE_TYPE uxTCBNumber; /*< This stores a number that increments each time a TCB is created. It allows debuggers to determine when a task has been deleted and then recreated. */\r
+ unsigned portBASE_TYPE uxTaskNumber; /*< This stores a number specifically for use by third party trace code. */\r
#endif\r
\r
#if ( configUSE_MUTEXES == 1 )\r
PRIVILEGED_DATA static volatile unsigned portBASE_TYPE uxMissedTicks = ( unsigned portBASE_TYPE ) 0U;\r
PRIVILEGED_DATA static volatile portBASE_TYPE xMissedYield = ( portBASE_TYPE ) pdFALSE;\r
PRIVILEGED_DATA static volatile portBASE_TYPE xNumOfOverflows = ( portBASE_TYPE ) 0;\r
-PRIVILEGED_DATA static unsigned portBASE_TYPE uxTaskNumber = ( unsigned portBASE_TYPE ) 0U;\r
+PRIVILEGED_DATA static unsigned portBASE_TYPE uxTCBNumber = ( unsigned portBASE_TYPE ) 0U;\r
PRIVILEGED_DATA static portTickType xNextTaskUnblockTime = ( portTickType ) portMAX_DELAY;\r
\r
#if ( configGENERATE_RUN_TIME_STATS == 1 )\r
#define tskDELETED_CHAR ( ( signed char ) 'D' )\r
#define tskSUSPENDED_CHAR ( ( signed char ) 'S' )\r
\r
-/*\r
- * Macros and private variables used by the trace facility.\r
- */\r
-#if ( configUSE_TRACE_FACILITY == 1 )\r
-\r
- #define tskSIZE_OF_EACH_TRACE_LINE ( ( unsigned long ) ( sizeof( unsigned long ) + sizeof( unsigned long ) ) )\r
- PRIVILEGED_DATA static volatile signed char * volatile pcTraceBuffer;\r
- PRIVILEGED_DATA static signed char *pcTraceBufferStart;\r
- PRIVILEGED_DATA static signed char *pcTraceBufferEnd;\r
- PRIVILEGED_DATA static signed portBASE_TYPE xTracing = pdFALSE;\r
- static unsigned portBASE_TYPE uxPreviousTask = 255U;\r
- PRIVILEGED_DATA static char pcStatusString[ 50 ];\r
-\r
-#endif\r
-\r
-/*-----------------------------------------------------------*/\r
-\r
-/*\r
- * Macro that writes a trace of scheduler activity to a buffer. This trace\r
- * shows which task is running when and is very useful as a debugging tool.\r
- * As this macro is called each context switch it is a good idea to undefine\r
- * it if not using the facility.\r
- */\r
-#if ( configUSE_TRACE_FACILITY == 1 )\r
-\r
- #define vWriteTraceToBuffer() \\r
- { \\r
- if( xTracing != pdFALSE ) \\r
- { \\r
- if( uxPreviousTask != pxCurrentTCB->uxTCBNumber ) \\r
- { \\r
- if( ( pcTraceBuffer + tskSIZE_OF_EACH_TRACE_LINE ) < pcTraceBufferEnd ) \\r
- { \\r
- uxPreviousTask = pxCurrentTCB->uxTCBNumber; \\r
- *( unsigned long * ) pcTraceBuffer = ( unsigned long ) xTickCount; \\r
- pcTraceBuffer += sizeof( unsigned long ); \\r
- *( unsigned long * ) pcTraceBuffer = ( unsigned long ) uxPreviousTask; \\r
- pcTraceBuffer += sizeof( unsigned long ); \\r
- } \\r
- else \\r
- { \\r
- xTracing = pdFALSE; \\r
- } \\r
- } \\r
- } \\r
- }\r
-\r
-#else\r
-\r
- #define vWriteTraceToBuffer()\r
-\r
-#endif\r
/*-----------------------------------------------------------*/\r
\r
/*\r
#endif\r
\r
/* Check the alignment of the initialised stack. */\r
- configASSERT( ( ( ( unsigned long ) pxNewTCB->pxTopOfStack & ( unsigned long ) portBYTE_ALIGNMENT_MASK ) == 0UL ) );\r
+ portALIGNMENT_ASSERT_pxCurrentTCB( ( ( ( unsigned long ) pxNewTCB->pxTopOfStack & ( unsigned long ) portBYTE_ALIGNMENT_MASK ) == 0UL ) );\r
\r
if( ( void * ) pxCreatedTask != NULL )\r
{\r
#if ( configUSE_TRACE_FACILITY == 1 )\r
{\r
/* Add a counter into the TCB for tracing only. */\r
- pxNewTCB->uxTCBNumber = uxTaskNumber;\r
+ pxNewTCB->uxTCBNumber = uxTCBNumber;\r
}\r
#endif\r
- uxTaskNumber++;\r
+ uxTCBNumber++;\r
\r
prvAddTaskToReadyQueue( pxNewTCB );\r
\r
\r
/* Increment the uxTaskNumberVariable also so kernel aware debuggers\r
can detect that the task lists need re-generating. */\r
- uxTaskNumber++;\r
+ uxTCBNumber++;\r
\r
traceTASK_DELETE( pxTCB );\r
}\r
priority of the calling function. */\r
pxTCB = prvGetTCBFromHandle( pxTask );\r
\r
- traceTASK_PRIORITY_SET( pxTask, uxNewPriority );\r
+ traceTASK_PRIORITY_SET( pxTCB, uxNewPriority );\r
\r
#if ( configUSE_MUTEXES == 1 )\r
{\r
{\r
portBASE_TYPE xYieldRequired = pdFALSE;\r
tskTCB *pxTCB;\r
+ unsigned portBASE_TYPE uxSavedInterruptStatus;\r
\r
configASSERT( pxTaskToResume );\r
\r
pxTCB = ( tskTCB * ) pxTaskToResume;\r
\r
- if( xTaskIsTaskSuspended( pxTCB ) == pdTRUE )\r
+ uxSavedInterruptStatus = portSET_INTERRUPT_MASK_FROM_ISR();\r
{\r
- traceTASK_RESUME_FROM_ISR( pxTCB );\r
-\r
- if( uxSchedulerSuspended == ( unsigned portBASE_TYPE ) pdFALSE )\r
- {\r
- xYieldRequired = ( pxTCB->uxPriority >= pxCurrentTCB->uxPriority );\r
- vListRemove( &( pxTCB->xGenericListItem ) );\r
- prvAddTaskToReadyQueue( pxTCB );\r
- }\r
- else\r
+ if( xTaskIsTaskSuspended( pxTCB ) == pdTRUE )\r
{\r
- /* We cannot access the delayed or ready lists, so will hold this\r
- task pending until the scheduler is resumed, at which point a\r
- yield will be performed if necessary. */\r
- vListInsertEnd( ( xList * ) &( xPendingReadyList ), &( pxTCB->xEventListItem ) );\r
+ traceTASK_RESUME_FROM_ISR( pxTCB );\r
+\r
+ if( uxSchedulerSuspended == ( unsigned portBASE_TYPE ) pdFALSE )\r
+ {\r
+ xYieldRequired = ( pxTCB->uxPriority >= pxCurrentTCB->uxPriority );\r
+ vListRemove( &( pxTCB->xGenericListItem ) );\r
+ prvAddTaskToReadyQueue( pxTCB );\r
+ }\r
+ else\r
+ {\r
+ /* We cannot access the delayed or ready lists, so will hold this\r
+ task pending until the scheduler is resumed, at which point a\r
+ yield will be performed if necessary. */\r
+ vListInsertEnd( ( xList * ) &( xPendingReadyList ), &( pxTCB->xEventListItem ) );\r
+ }\r
}\r
}\r
+ portCLEAR_INTERRUPT_MASK_FROM_ISR( uxSavedInterruptStatus );\r
\r
return xYieldRequired;\r
}\r
#endif\r
/*----------------------------------------------------------*/\r
\r
-#if ( configUSE_TRACE_FACILITY == 1 )\r
-\r
- void vTaskStartTrace( signed char * pcBuffer, unsigned long ulBufferSize )\r
- {\r
- configASSERT( pcBuffer );\r
- configASSERT( ulBufferSize );\r
-\r
- taskENTER_CRITICAL();\r
- {\r
- pcTraceBuffer = ( signed char * )pcBuffer;\r
- pcTraceBufferStart = pcBuffer;\r
- pcTraceBufferEnd = pcBuffer + ( ulBufferSize - tskSIZE_OF_EACH_TRACE_LINE );\r
- xTracing = pdTRUE;\r
- }\r
- taskEXIT_CRITICAL();\r
- }\r
-\r
-#endif\r
-/*----------------------------------------------------------*/\r
-\r
-#if ( configUSE_TRACE_FACILITY == 1 )\r
-\r
- unsigned long ulTaskEndTrace( void )\r
- {\r
- unsigned long ulBufferLength;\r
-\r
- taskENTER_CRITICAL();\r
- xTracing = pdFALSE;\r
- taskEXIT_CRITICAL();\r
-\r
- ulBufferLength = ( unsigned long ) ( pcTraceBuffer - pcTraceBufferStart );\r
-\r
- return ulBufferLength;\r
- }\r
-\r
-#endif\r
-/*----------------------------------------------------------*/\r
-\r
#if ( INCLUDE_xTaskGetIdleTaskHandle == 1 )\r
\r
xTaskHandle xTaskGetIdleTaskHandle( void )\r
listGET_OWNER_OF_NEXT_ENTRY( pxCurrentTCB, &( pxReadyTasksLists[ uxTopReadyPriority ] ) );\r
\r
traceTASK_SWITCHED_IN();\r
- vWriteTraceToBuffer();\r
}\r
}\r
/*-----------------------------------------------------------*/\r
{\r
xMissedYield = pdTRUE;\r
}\r
+/*-----------------------------------------------------------*/\r
+\r
+#if ( configUSE_TRACE_FACILITY == 1 )\r
+ unsigned portBASE_TYPE uxTaskGetTaskNumber( xTaskHandle xTask )\r
+ {\r
+ unsigned portBASE_TYPE uxReturn;\r
+ tskTCB *pxTCB;\r
+ \r
+ if( xTask != NULL )\r
+ {\r
+ pxTCB = ( tskTCB * ) xTask;\r
+ uxReturn = pxTCB->uxTaskNumber;\r
+ }\r
+ else\r
+ {\r
+ uxReturn = 0U;\r
+ }\r
+ \r
+ return uxReturn;\r
+ }\r
+#endif\r
+/*-----------------------------------------------------------*/\r
+\r
+#if ( configUSE_TRACE_FACILITY == 1 )\r
+ void vTaskSetTaskNumber( xTaskHandle xTask, unsigned portBASE_TYPE uxHandle )\r
+ {\r
+ tskTCB *pxTCB;\r
+ \r
+ if( xTask != NULL )\r
+ {\r
+ pxTCB = ( tskTCB * ) xTask;\r
+ pxTCB->uxTaskNumber = uxHandle;\r
+ }\r
+ }\r
+#endif\r
+\r
\r
/*\r
* -----------------------------------------------------------\r
{\r
volatile tskTCB *pxNextTCB, *pxFirstTCB;\r
unsigned short usStackRemaining;\r
+ PRIVILEGED_DATA static char pcStatusString[ 50 ];\r
\r
/* Write the details of all the TCB's in pxList into the buffer. */\r
listGET_OWNER_OF_NEXT_ENTRY( pxFirstTCB, pxList );\r
\r
static void prvDeleteTCB( tskTCB *pxTCB )\r
{\r
+ /* This call is required specifically for the TriCore port. It must be\r
+ above the vPortFree() calls. */\r
+ portCLEAN_UP_TCB( pxTCB );\r
+\r
/* Free up the memory allocated by the scheduler for the task. It is up to\r
the task to free any memory allocated at the application level. */\r
vPortFreeAligned( pxTCB->pxStack );\r
/* Just inherit the priority. */\r
pxTCB->uxPriority = pxCurrentTCB->uxPriority;\r
}\r
+\r
+ traceTASK_PRIORITY_INHERIT( pxTCB, pxCurrentTCB->uxPriority );\r
}\r
}\r
\r
Remove ourselves from the ready list we currently appear in. */\r
vListRemove( &( pxTCB->xGenericListItem ) );\r
\r
- /* Disinherit the priority before adding ourselves into the new\r
+ /* Disinherit the priority before adding the task into the new\r
ready list. */\r
+ traceTASK_PRIORITY_DISINHERIT( pxTCB, pxTCB->uxBasePriority );\r
pxTCB->uxPriority = pxTCB->uxBasePriority;\r
listSET_LIST_ITEM_VALUE( &( pxTCB->xEventListItem ), configMAX_PRIORITIES - ( portTickType ) pxTCB->uxPriority );\r
prvAddTaskToReadyQueue( pxTCB );\r