From a03086a91fdf037f48463038b1a3f4dba7d80800 Mon Sep 17 00:00:00 2001 From: richardbarry Date: Mon, 18 Feb 2013 11:20:29 +0000 Subject: [PATCH] Add default definition for configUSE_QUEUE_SETS. Add eTaskConfirmSleepModeStatus() (not yet tested). Only call prvQueueUnregisterQueue() when a queue or semaphore is deleted if configQUEUE_REGISTRY_SIZE > 0. Back out change that checks the configUSE_PORT_OPTMISED_TASK_SELECTION value before uxPriorityUsedOnEntry is set in vTaskPrioritySet as it generated more warnings (with other compilers) than it fixed. git-svn-id: https://svn.code.sf.net/p/freertos/code/trunk@1828 1d2547de-c912-0410-9cb9-b8ca96c0e9e2 --- FreeRTOS/Source/include/FreeRTOS.h | 30 ++++++++------- FreeRTOS/Source/include/task.h | 50 +++++++++++++++++------- FreeRTOS/Source/queue.c | 6 ++- FreeRTOS/Source/tasks.c | 62 +++++++++++++++++++++++++----- 4 files changed, 112 insertions(+), 36 deletions(-) diff --git a/FreeRTOS/Source/include/FreeRTOS.h b/FreeRTOS/Source/include/FreeRTOS.h index a84be03c0..52c09a897 100644 --- a/FreeRTOS/Source/include/FreeRTOS.h +++ b/FreeRTOS/Source/include/FreeRTOS.h @@ -1,7 +1,7 @@ /* FreeRTOS V7.3.0 - Copyright (C) 2012 Real Time Engineers Ltd. - FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME. PLEASE VISIT + FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME. PLEASE VISIT http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION. *************************************************************************** @@ -42,7 +42,7 @@ FreeRTOS WEB site. 1 tab == 4 spaces! - + *************************************************************************** * * * Having a problem? Start by reading the FAQ "My application does * @@ -52,17 +52,17 @@ * * *************************************************************************** - - http://www.FreeRTOS.org - Documentation, training, latest versions, license - and contact details. - + + http://www.FreeRTOS.org - Documentation, training, latest versions, license + and contact details. + http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products, including FreeRTOS+Trace - an indispensable productivity tool. - Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell - the code with commercial support, indemnification, and middleware, under + Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell + the code with commercial support, indemnification, and middleware, under the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also - provide a safety engineered and independently SIL3 certified version under + provide a safety engineered and independently SIL3 certified version under the SafeRTOS brand: http://www.SafeRTOS.com. */ @@ -129,11 +129,11 @@ typedef portBASE_TYPE (*pdTASK_HOOK_CODE)( void * ); #error Missing definition: INCLUDE_uxTaskPriorityGet should be defined in FreeRTOSConfig.h as either 1 or 0. See the Configuration section of the FreeRTOS API documentation for details. #endif -#ifndef INCLUDE_vTaskDelete +#ifndef INCLUDE_vTaskDelete #error Missing definition: INCLUDE_vTaskDelete should be defined in FreeRTOSConfig.h as either 1 or 0. See the Configuration section of the FreeRTOS API documentation for details. #endif -#ifndef INCLUDE_vTaskSuspend +#ifndef INCLUDE_vTaskSuspend #error Missing definition: INCLUDE_vTaskSuspend should be defined in FreeRTOSConfig.h as either 1 or 0. See the Configuration section of the FreeRTOS API documentation for details. #endif @@ -320,7 +320,7 @@ typedef portBASE_TYPE (*pdTASK_HOOK_CODE)( void * ); #ifndef traceTASK_PRIORITY_DISINHERIT /* Called when a task releases a mutex, the holding of which had resulted in - the task inheriting the priority of a higher priority task. + the task inheriting the priority of a higher priority task. pxTCBOfMutexHolder is a pointer to the TCB of the task that is releasing the mutex. uxOriginalPriority is the task's configured (base) priority. */ #define traceTASK_PRIORITY_DISINHERIT( pxTCBOfMutexHolder, uxOriginalPriority ) @@ -352,7 +352,7 @@ typedef portBASE_TYPE (*pdTASK_HOOK_CODE)( void * ); #define traceMOVED_TASK_TO_READY_STATE( pxTCB ) #endif -#ifndef traceQUEUE_CREATE +#ifndef traceQUEUE_CREATE #define traceQUEUE_CREATE( pxNewQueue ) #endif @@ -558,6 +558,10 @@ typedef portBASE_TYPE (*pdTASK_HOOK_CODE)( void * ); #define configPOST_SLEEP_PROCESSING( x ) #endif +#ifndef configUSE_QUEUE_SETS + #define configUSE_QUEUE_SETS 0 +#endif + /* For backward compatability. */ #define eTaskStateGet eTaskGetState diff --git a/FreeRTOS/Source/include/task.h b/FreeRTOS/Source/include/task.h index b54d21e3b..9aa7ed51b 100644 --- a/FreeRTOS/Source/include/task.h +++ b/FreeRTOS/Source/include/task.h @@ -41,7 +41,7 @@ 1 tab == 4 spaces! - + *************************************************************************** * * * Having a problem? Start by reading the FAQ "My application does * @@ -51,17 +51,17 @@ * * *************************************************************************** - - http://www.FreeRTOS.org - Documentation, training, latest information, + + http://www.FreeRTOS.org - Documentation, training, latest information, license and contact details. - + http://www.FreeRTOS.org/plus - Selection of FreeRTOS ecosystem products, including FreeRTOS+Trace - an indispensable productivity tool. - Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell - the code with commercial support, indemnification, and middleware, under + Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell + the code with commercial support, indemnification, and middleware, under the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also - provide a safety engineered and independently SIL3 certified version under + provide a safety engineered and independently SIL3 certified version under the SafeRTOS brand: http://www.SafeRTOS.com. */ @@ -141,6 +141,15 @@ typedef enum eDeleted /* The task being queried has been deleted, but its TCB has not yet been freed. */ } eTaskState; +/* Possible return values for eTaskConfirmSleepModeStatus(). */ +typedef enum +{ + eAbortSleep = 0, /* A task has been made ready or a context switch pended since portSUPPORESS_TICKS_AND_SLEEP() was called - abort entering a sleep mode. */ + eStandardSleep, /* Enter a sleep mode that will not last any longer than the expected idle time. */ + eNoTasksWaitingTimeout /* No tasks are waiting for a timeout so it is safe to enter a sleep mode that can only be exited by an external interrupt. */ +} eSleepModeStatus; + + /* * Defines the priority used by the idle task. This must not be modified. * @@ -332,7 +341,7 @@ static const xTaskParameters xCheckTaskParameters = // the task, with appropriate access permissions. Different processors have // different memory alignment requirements - refer to the FreeRTOS documentation // for full information. - { + { // Base address Length Parameters { cReadWriteArray, 32, portMPU_REGION_READ_WRITE }, { cReadOnlyArray, 32, portMPU_REGION_READ_ONLY }, @@ -383,7 +392,7 @@ xTaskHandle xHandle; // ucOneKByte array. The other two of the maximum 3 definable regions are // unused so set to zero. static const xMemoryRegion xAltRegions[ portNUM_CONFIGURABLE_REGIONS ] = -{ +{ // Base address Length Parameters { ucOneKByte, 1024, portMPU_REGION_READ_WRITE }, { 0, 0, 0 }, @@ -399,7 +408,7 @@ void vATask( void *pvParameters ) // for this purpose. NULL is used as the task handle to indicate that this // function should modify the MPU regions of the calling task. vTaskAllocateMPURegions( NULL, xAltRegions ); - + // Now the task can continue its function, but from this point on can only // access its stack and the ucOneKByte array (unless any other statically // defined or shared regions have been declared elsewhere). @@ -618,7 +627,7 @@ unsigned portBASE_TYPE uxTaskPriorityGet( xTaskHandle xTask ) PRIVILEGED_FUNCTIO * INCLUDE_eTaskGetState must be defined as 1 for this function to be available. * See the configuration section for more information. * - * Obtain the state of any task. States are encoded by the eTaskState + * Obtain the state of any task. States are encoded by the eTaskState * enumerated type. * * @param xTask Handle of the task to be queried. @@ -1174,7 +1183,7 @@ constant. */ portBASE_TYPE xTaskCallApplicationTaskHook( xTaskHandle xTask, void *pvParameter ) PRIVILEGED_FUNCTION; /** - * xTaskGetIdleTaskHandle() is only available if + * xTaskGetIdleTaskHandle() is only available if * INCLUDE_xTaskGetIdleTaskHandle is set to 1 in FreeRTOSConfig.h. * * Simply returns the handle of the idle task. It is not valid to call @@ -1314,7 +1323,7 @@ signed portBASE_TYPE xTaskGenericCreate( pdTASK_CODE pxTaskCode, const signed ch */ unsigned portBASE_TYPE uxTaskGetTaskNumber( xTaskHandle xTask ); -/* +/* * Set the uxTCBNumber of the task referenced by the xTask parameter to * ucHandle. */ @@ -1329,6 +1338,21 @@ void vTaskSetTaskNumber( xTaskHandle xTask, unsigned portBASE_TYPE uxHandle ); */ void vTaskStepTick( portTickType xTicksToJump ); +/* + * Provided for use within portSUPPRESS_TICKS_AND_SLEEP() to allow the port + * specific sleep function to determine if it is ok to proceed with the sleep, + * and if it is ok to proceed, if it is ok to sleep indefinitely. + * + * This function is necessary because portSUPPRESS_TICKS_AND_SLEEP() is only + * called with the scheduler suspended, not from within a critical section. It + * is therefore possible for an interrupt to request a context switch between + * portSUPPRESS_TICKS_AND_SLEEP() and the low power mode actually being + * entered. eTaskConfirmSleepModeStatus() should be called from a short + * critical section between the timer being stopped and the sleep mode being + * entered to ensure it is ok to proceed into the sleep mode. + */ +eSleepModeStatus eTaskConfirmSleepModeStatus( void ); + #ifdef __cplusplus } #endif diff --git a/FreeRTOS/Source/queue.c b/FreeRTOS/Source/queue.c index a97f868c1..1dadf763a 100644 --- a/FreeRTOS/Source/queue.c +++ b/FreeRTOS/Source/queue.c @@ -1251,7 +1251,11 @@ xQUEUE *pxQueue; configASSERT( pxQueue ); traceQUEUE_DELETE( pxQueue ); - prvQueueUnregisterQueue( pxQueue ); + #if ( configQUEUE_REGISTRY_SIZE > 0 ) + { + prvQueueUnregisterQueue( pxQueue ); + } + #endif vPortFree( pxQueue->pcHead ); vPortFree( pxQueue ); } diff --git a/FreeRTOS/Source/tasks.c b/FreeRTOS/Source/tasks.c index 854251261..f1d1a0c0e 100644 --- a/FreeRTOS/Source/tasks.c +++ b/FreeRTOS/Source/tasks.c @@ -84,6 +84,13 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +/* Sanity check the configuration. */ +#if configUSE_TICKLESS_IDLE != 0 + #if INCLUDE_vTaskSuspend != 1 + #error INCLUDE_vTaskSuspend must be set to 1 if configUSE_TICKLESS_IDLE is not set to 0 + #endif /* INCLUDE_vTaskSuspend */ +#endif /* configUSE_TICKLESS_IDLE */ + /* * Defines the size, in words, of the stack allocated to the idle task. */ @@ -602,13 +609,14 @@ tskTCB * pxNewTCB; uxTopUsedPriority = pxNewTCB->uxPriority; } + uxTaskNumber++; + #if ( configUSE_TRACE_FACILITY == 1 ) { /* Add a counter into the TCB for tracing only. */ pxNewTCB->uxTCBNumber = uxTaskNumber; } #endif /* configUSE_TRACE_FACILITY */ - uxTaskNumber++; traceTASK_CREATE( pxNewTCB ); prvAddTaskToReadyQueue( pxNewTCB ); @@ -974,11 +982,7 @@ tskTCB * pxNewTCB; /* Remember the ready list the task might be referenced from before its uxPriority member is changed so the taskRESET_READY_PRIORITY() macro can function correctly. */ - #if ( configUSE_PORT_OPTIMISED_TASK_SELECTION != 0 ) - { - uxPriorityUsedOnEntry = pxTCB->uxPriority; - } - #endif /* configUSE_PORT_OPTIMISED_TASK_SELECTION */ + uxPriorityUsedOnEntry = pxTCB->uxPriority; #if ( configUSE_MUTEXES == 1 ) { @@ -1280,7 +1284,7 @@ portBASE_TYPE xReturn; } else { - /* This line will only be reached if the kernel could not be started, + /* This line will only be reached if the kernel could not be started, because there was not enough FreeRTOS heap to create the idle task or the timer task. */ configASSERT( xReturn ); @@ -2171,6 +2175,46 @@ static portTASK_FUNCTION( prvIdleTask, pvParameters ) } /*lint !e715 pvParameters is not accessed but all task functions require the same prototype. */ /*-----------------------------------------------------------*/ +#if configUSE_TICKLESS_IDLE != 0 + + eSleepModeStatus eTaskConfirmSleepModeStatus( void ) + { + eSleepModeStatus eReturn = eStandardSleep; + + if( listCURRENT_LIST_LENGTH( &xPendingReadyList ) != 0 ) + { + /* A task was made ready while the scheduler was suspended. */ + eReturn = eAbortSleep; + } + else if( xMissedYield != pdFALSE ) + { + /* A yield was pended while the scheduler was suspended. */ + eReturn = eAbortSleep; + } + else + { + #if configUSE_TIMERS == 0 + { + /* The idle task exists in addition to the application tasks. */ + const unsigned portBASE_TYPE uxNonApplicationTasks = 1; + + /* If timers are not being used and all the tasks are in the + suspended list (which might mean they have an infinite block + time rather than actually being suspended) then it is safe to + turn all clocks off and just wait for external initerrupts. */ + if( listCURRENT_LIST_LENGTH( &xSuspendedTasksList ) == ( uxCurrentNumberOfTasks - uxNonApplicationTasks ) ) + { + eReturn = eNoTasksWaitingTimeout; + } + } + #endif /* configUSE_TIMERS */ + } + + return eReturn; + } +#endif /* configUSE_TICKLESS_IDLE */ +/*-----------------------------------------------------------*/ + static void prvInitialiseTCBVariables( tskTCB *pxTCB, const signed char * const pcName, unsigned portBASE_TYPE uxPriority, const xMemoryRegion * const xRegions, unsigned short usStackDepth ) { /* Store the function name in the TCB. */ @@ -2254,7 +2298,7 @@ static void prvInitialiseTCBVariables( tskTCB *pxTCB, const signed char * const vPortStoreTaskMPUSettings( &( pxTCB->xMPUSettings ), xRegions, NULL, 0 ); } - + #endif /* portUSING_MPU_WRAPPERS */ /*-----------------------------------------------------------*/ @@ -2700,7 +2744,7 @@ tskTCB *pxNewTCB; } } } - } + } #endif /* portCRITICAL_NESTING_IN_TCB */ /*-----------------------------------------------------------*/ -- 2.39.5