#define configTOTAL_HEAP_SIZE ( ( size_t ) 32768 )\r
#define configMAX_TASK_NAME_LEN ( 16 )\r
#define configIDLE_SHOULD_YIELD 1\r
-#define configGENERATE_RUN_TIME_STATS 1\r
+#define configGENERATE_RUN_TIME_STATS 0\r
#define configUSE_MALLOC_FAILED_HOOK 1\r
\r
#define configCHECK_FOR_STACK_OVERFLOW 2\r
\r
/* Mutexes */\r
#define configUSE_MUTEXES 1\r
-#define configUSE_RECURSIVE_MUTEXES 0\r
+#define configUSE_RECURSIVE_MUTEXES 1\r
\r
/* Semaphores */\r
#define configUSE_COUNTING_SEMAPHORES 1\r
/* Set the following definitions to 1 to include the API function, or zero to exclude the API function. */\r
#define INCLUDE_vTaskPrioritySet 1\r
#define INCLUDE_uxTaskPriorityGet 1\r
-#define INCLUDE_vTaskDelete 0\r
+#define INCLUDE_vTaskDelete 1\r
#define INCLUDE_vTaskCleanUpResources 0\r
#define INCLUDE_vTaskSuspend 1\r
#define INCLUDE_xTaskResumeFromISR 0\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ * Creates six tasks that operate on three queues as follows:\r
+ *\r
+ * The first two tasks send and receive an incrementing number to/from a queue.\r
+ * One task acts as a producer and the other as the consumer. The consumer is a\r
+ * higher priority than the producer and is set to block on queue reads. The queue\r
+ * only has space for one item - as soon as the producer posts a message on the\r
+ * queue the consumer will unblock, pre-empt the producer, and remove the item.\r
+ *\r
+ * The second two tasks work the other way around. Again the queue used only has\r
+ * enough space for one item. This time the consumer has a lower priority than the\r
+ * producer. The producer will try to post on the queue blocking when the queue is\r
+ * full. When the consumer wakes it will remove the item from the queue, causing\r
+ * the producer to unblock, pre-empt the consumer, and immediately re-fill the\r
+ * queue.\r
+ *\r
+ * The last two tasks use the same queue producer and consumer functions. This time the queue has\r
+ * enough space for lots of items and the tasks operate at the same priority. The\r
+ * producer will execute, placing items into the queue. The consumer will start\r
+ * executing when either the queue becomes full (causing the producer to block) or\r
+ * a context switch occurs (tasks of the same priority will time slice).\r
+ *\r
+ */\r
+\r
+/*\r
+\r
+Changes from V4.1.1\r
+\r
+ + The second set of tasks were created the wrong way around. This has been\r
+ corrected.\r
+*/\r
+\r
+\r
+#include <stdlib.h>\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "queue.h"\r
+\r
+/* Demo program include files. */\r
+#include "BlockQ.h"\r
+\r
+#define blckqSTACK_SIZE configMINIMAL_STACK_SIZE\r
+#define blckqNUM_TASK_SETS ( 3 )\r
+\r
+/* Structure used to pass parameters to the blocking queue tasks. */\r
+typedef struct BLOCKING_QUEUE_PARAMETERS\r
+{\r
+ xQueueHandle xQueue; /*< The queue to be used by the task. */\r
+ portTickType xBlockTime; /*< The block time to use on queue reads/writes. */\r
+ volatile short *psCheckVariable; /*< Incremented on each successful cycle to check the task is still running. */\r
+} xBlockingQueueParameters;\r
+\r
+/* Task function that creates an incrementing number and posts it on a queue. */\r
+static portTASK_FUNCTION_PROTO( vBlockingQueueProducer, pvParameters );\r
+\r
+/* Task function that removes the incrementing number from a queue and checks that\r
+it is the expected number. */\r
+static portTASK_FUNCTION_PROTO( vBlockingQueueConsumer, pvParameters );\r
+\r
+/* Variables which are incremented each time an item is removed from a queue, and\r
+found to be the expected value.\r
+These are used to check that the tasks are still running. */\r
+static volatile short sBlockingConsumerCount[ blckqNUM_TASK_SETS ] = { ( unsigned short ) 0, ( unsigned short ) 0, ( unsigned short ) 0 };\r
+\r
+/* Variable which are incremented each time an item is posted on a queue. These\r
+are used to check that the tasks are still running. */\r
+static volatile short sBlockingProducerCount[ blckqNUM_TASK_SETS ] = { ( unsigned short ) 0, ( unsigned short ) 0, ( unsigned short ) 0 };\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vStartBlockingQueueTasks( unsigned portBASE_TYPE uxPriority )\r
+{\r
+xBlockingQueueParameters *pxQueueParameters1, *pxQueueParameters2;\r
+xBlockingQueueParameters *pxQueueParameters3, *pxQueueParameters4;\r
+xBlockingQueueParameters *pxQueueParameters5, *pxQueueParameters6;\r
+const unsigned portBASE_TYPE uxQueueSize1 = 1, uxQueueSize5 = 5;\r
+const portTickType xBlockTime = ( portTickType ) 1000 / portTICK_RATE_MS;\r
+const portTickType xDontBlock = ( portTickType ) 0;\r
+\r
+ /* Create the first two tasks as described at the top of the file. */\r
+ \r
+ /* First create the structure used to pass parameters to the consumer tasks. */\r
+ pxQueueParameters1 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+\r
+ /* Create the queue used by the first two tasks to pass the incrementing number.\r
+ Pass a pointer to the queue in the parameter structure. */\r
+ pxQueueParameters1->xQueue = xQueueCreate( uxQueueSize1, ( unsigned portBASE_TYPE ) sizeof( unsigned short ) );\r
+\r
+ /* The consumer is created first so gets a block time as described above. */\r
+ pxQueueParameters1->xBlockTime = xBlockTime;\r
+\r
+ /* Pass in the variable that this task is going to increment so we can check it\r
+ is still running. */\r
+ pxQueueParameters1->psCheckVariable = &( sBlockingConsumerCount[ 0 ] );\r
+ \r
+ /* Create the structure used to pass parameters to the producer task. */\r
+ pxQueueParameters2 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+\r
+ /* Pass the queue to this task also, using the parameter structure. */\r
+ pxQueueParameters2->xQueue = pxQueueParameters1->xQueue;\r
+\r
+ /* The producer is not going to block - as soon as it posts the consumer will\r
+ wake and remove the item so the producer should always have room to post. */\r
+ pxQueueParameters2->xBlockTime = xDontBlock;\r
+\r
+ /* Pass in the variable that this task is going to increment so we can check\r
+ it is still running. */\r
+ pxQueueParameters2->psCheckVariable = &( sBlockingProducerCount[ 0 ] );\r
+\r
+\r
+ /* Note the producer has a lower priority than the consumer when the tasks are\r
+ spawned. */\r
+ xTaskCreate( vBlockingQueueConsumer, ( signed char * ) "QConsB1", blckqSTACK_SIZE, ( void * ) pxQueueParameters1, uxPriority, NULL );\r
+ xTaskCreate( vBlockingQueueProducer, ( signed char * ) "QProdB2", blckqSTACK_SIZE, ( void * ) pxQueueParameters2, tskIDLE_PRIORITY, NULL );\r
+\r
+ \r
+\r
+ /* Create the second two tasks as described at the top of the file. This uses\r
+ the same mechanism but reverses the task priorities. */\r
+\r
+ pxQueueParameters3 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+ pxQueueParameters3->xQueue = xQueueCreate( uxQueueSize1, ( unsigned portBASE_TYPE ) sizeof( unsigned short ) );\r
+ pxQueueParameters3->xBlockTime = xDontBlock;\r
+ pxQueueParameters3->psCheckVariable = &( sBlockingProducerCount[ 1 ] );\r
+\r
+ pxQueueParameters4 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+ pxQueueParameters4->xQueue = pxQueueParameters3->xQueue;\r
+ pxQueueParameters4->xBlockTime = xBlockTime;\r
+ pxQueueParameters4->psCheckVariable = &( sBlockingConsumerCount[ 1 ] );\r
+\r
+ xTaskCreate( vBlockingQueueConsumer, ( signed char * ) "QConsB3", blckqSTACK_SIZE, ( void * ) pxQueueParameters3, tskIDLE_PRIORITY, NULL );\r
+ xTaskCreate( vBlockingQueueProducer, ( signed char * ) "QProdB4", blckqSTACK_SIZE, ( void * ) pxQueueParameters4, uxPriority, NULL );\r
+\r
+\r
+\r
+ /* Create the last two tasks as described above. The mechanism is again just\r
+ the same. This time both parameter structures are given a block time. */\r
+ pxQueueParameters5 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+ pxQueueParameters5->xQueue = xQueueCreate( uxQueueSize5, ( unsigned portBASE_TYPE ) sizeof( unsigned short ) );\r
+ pxQueueParameters5->xBlockTime = xBlockTime;\r
+ pxQueueParameters5->psCheckVariable = &( sBlockingProducerCount[ 2 ] );\r
+\r
+ pxQueueParameters6 = ( xBlockingQueueParameters * ) pvPortMalloc( sizeof( xBlockingQueueParameters ) );\r
+ pxQueueParameters6->xQueue = pxQueueParameters5->xQueue;\r
+ pxQueueParameters6->xBlockTime = xBlockTime;\r
+ pxQueueParameters6->psCheckVariable = &( sBlockingConsumerCount[ 2 ] ); \r
+\r
+ xTaskCreate( vBlockingQueueProducer, ( signed char * ) "QProdB5", blckqSTACK_SIZE, ( void * ) pxQueueParameters5, tskIDLE_PRIORITY, NULL );\r
+ xTaskCreate( vBlockingQueueConsumer, ( signed char * ) "QConsB6", blckqSTACK_SIZE, ( void * ) pxQueueParameters6, tskIDLE_PRIORITY, NULL );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vBlockingQueueProducer, pvParameters )\r
+{\r
+unsigned short usValue = 0;\r
+xBlockingQueueParameters *pxQueueParameters;\r
+short sErrorEverOccurred = pdFALSE;\r
+\r
+ pxQueueParameters = ( xBlockingQueueParameters * ) pvParameters;\r
+\r
+ for( ;; )\r
+ { \r
+ if( xQueueSend( pxQueueParameters->xQueue, ( void * ) &usValue, pxQueueParameters->xBlockTime ) != pdPASS )\r
+ {\r
+ sErrorEverOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ /* We have successfully posted a message, so increment the variable\r
+ used to check we are still running. */\r
+ if( sErrorEverOccurred == pdFALSE )\r
+ {\r
+ ( *pxQueueParameters->psCheckVariable )++;\r
+ }\r
+\r
+ /* Increment the variable we are going to post next time round. The\r
+ consumer will expect the numbers to follow in numerical order. */\r
+ ++usValue;\r
+ }\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vBlockingQueueConsumer, pvParameters )\r
+{\r
+unsigned short usData, usExpectedValue = 0;\r
+xBlockingQueueParameters *pxQueueParameters;\r
+short sErrorEverOccurred = pdFALSE;\r
+\r
+ pxQueueParameters = ( xBlockingQueueParameters * ) pvParameters;\r
+\r
+ for( ;; )\r
+ { \r
+ if( xQueueReceive( pxQueueParameters->xQueue, &usData, pxQueueParameters->xBlockTime ) == pdPASS )\r
+ {\r
+ if( usData != usExpectedValue )\r
+ {\r
+ /* Catch-up. */\r
+ usExpectedValue = usData;\r
+\r
+ sErrorEverOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ /* We have successfully received a message, so increment the\r
+ variable used to check we are still running. */ \r
+ if( sErrorEverOccurred == pdFALSE )\r
+ {\r
+ ( *pxQueueParameters->psCheckVariable )++;\r
+ }\r
+ \r
+ /* Increment the value we expect to remove from the queue next time\r
+ round. */\r
+ ++usExpectedValue;\r
+ } \r
+ } \r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that all the created tasks are still running. */\r
+portBASE_TYPE xAreBlockingQueuesStillRunning( void )\r
+{\r
+static short sLastBlockingConsumerCount[ blckqNUM_TASK_SETS ] = { ( unsigned short ) 0, ( unsigned short ) 0, ( unsigned short ) 0 };\r
+static short sLastBlockingProducerCount[ blckqNUM_TASK_SETS ] = { ( unsigned short ) 0, ( unsigned short ) 0, ( unsigned short ) 0 };\r
+portBASE_TYPE xReturn = pdPASS, xTasks;\r
+\r
+ /* Not too worried about mutual exclusion on these variables as they are 16\r
+ bits and we are only reading them. We also only care to see if they have\r
+ changed or not.\r
+ \r
+ Loop through each check variable to and return pdFALSE if any are found not\r
+ to have changed since the last call. */\r
+\r
+ for( xTasks = 0; xTasks < blckqNUM_TASK_SETS; xTasks++ )\r
+ {\r
+ if( sBlockingConsumerCount[ xTasks ] == sLastBlockingConsumerCount[ xTasks ] )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ sLastBlockingConsumerCount[ xTasks ] = sBlockingConsumerCount[ xTasks ];\r
+\r
+\r
+ if( sBlockingProducerCount[ xTasks ] == sLastBlockingProducerCount[ xTasks ] )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ sLastBlockingProducerCount[ xTasks ] = sBlockingProducerCount[ xTasks ];\r
+ }\r
+\r
+ return xReturn;\r
+}\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef BLOCK_Q_H\r
+#define BLOCK_Q_H\r
+\r
+void vStartBlockingQueueTasks( unsigned portBASE_TYPE uxPriority );\r
+portBASE_TYPE xAreBlockingQueuesStillRunning( void );\r
+\r
+#endif\r
+\r
+\r
/*\r
- FreeRTOS V7.0.2 - Copyright (C) 2011 Real Time Engineers Ltd.\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
\r
\r
***************************************************************************\r
FreeRTOS WEB site.\r
\r
1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
\r
- http://www.FreeRTOS.org - Documentation, latest information, license and\r
- contact details.\r
-\r
- http://www.SafeRTOS.com - A version that is certified for use in safety\r
- critical systems.\r
-\r
- http://www.OpenRTOS.com - Commercial support, development, porting,\r
- licensing and training services.\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
*/\r
\r
\r
/* Create the demo task and pass it the queue just created. We are\r
passing the queue handle by value so it does not matter that it is\r
declared on the stack here. */\r
- xTaskCreate( prvSendFrontAndBackTest, ( signed portCHAR * )"GenQ ", configMINIMAL_STACK_SIZE, ( void * ) xQueue, uxPriority, NULL );\r
+ xTaskCreate( prvSendFrontAndBackTest, ( signed portCHAR * )"GenQ", configMINIMAL_STACK_SIZE, ( void * ) xQueue, uxPriority, NULL );\r
\r
/* Create the mutex used by the prvMutexTest task. */\r
xMutex = xSemaphoreCreateMutex();\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ * This version of PollQ. c is for use on systems that have limited stack\r
+ * space and no display facilities. The complete version can be found in\r
+ * the Demo/Common/Full directory.\r
+ *\r
+ * Creates two tasks that communicate over a single queue. One task acts as a\r
+ * producer, the other a consumer.\r
+ *\r
+ * The producer loops for three iteration, posting an incrementing number onto the\r
+ * queue each cycle. It then delays for a fixed period before doing exactly the\r
+ * same again.\r
+ *\r
+ * The consumer loops emptying the queue. Each item removed from the queue is\r
+ * checked to ensure it contains the expected value. When the queue is empty it\r
+ * blocks for a fixed period, then does the same again.\r
+ *\r
+ * All queue access is performed without blocking. The consumer completely empties\r
+ * the queue each time it runs so the producer should never find the queue full.\r
+ *\r
+ * An error is flagged if the consumer obtains an unexpected value or the producer\r
+ * find the queue is full.\r
+ */\r
+\r
+/*\r
+Changes from V2.0.0\r
+\r
+ + Delay periods are now specified using variables and constants of\r
+ portTickType rather than unsigned long.\r
+*/\r
+\r
+#include <stdlib.h>\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "queue.h"\r
+\r
+/* Demo program include files. */\r
+#include "PollQ.h"\r
+\r
+#define pollqSTACK_SIZE configMINIMAL_STACK_SIZE\r
+#define pollqQUEUE_SIZE ( 10 )\r
+#define pollqPRODUCER_DELAY ( ( portTickType ) 200 / portTICK_RATE_MS )\r
+#define pollqCONSUMER_DELAY ( pollqPRODUCER_DELAY - ( portTickType ) ( 20 / portTICK_RATE_MS ) )\r
+#define pollqNO_DELAY ( ( portTickType ) 0 )\r
+#define pollqVALUES_TO_PRODUCE ( ( signed portBASE_TYPE ) 3 )\r
+#define pollqINITIAL_VALUE ( ( signed portBASE_TYPE ) 0 )\r
+\r
+/* The task that posts the incrementing number onto the queue. */\r
+static portTASK_FUNCTION_PROTO( vPolledQueueProducer, pvParameters );\r
+\r
+/* The task that empties the queue. */\r
+static portTASK_FUNCTION_PROTO( vPolledQueueConsumer, pvParameters );\r
+\r
+/* Variables that are used to check that the tasks are still running with no\r
+errors. */\r
+static volatile signed portBASE_TYPE xPollingConsumerCount = pollqINITIAL_VALUE, xPollingProducerCount = pollqINITIAL_VALUE;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vStartPolledQueueTasks( unsigned portBASE_TYPE uxPriority )\r
+{\r
+static xQueueHandle xPolledQueue;\r
+\r
+ /* Create the queue used by the producer and consumer. */\r
+ xPolledQueue = xQueueCreate( pollqQUEUE_SIZE, ( unsigned portBASE_TYPE ) sizeof( unsigned short ) );\r
+\r
+ /* vQueueAddToRegistry() adds the queue to the queue registry, if one is\r
+ in use. The queue registry is provided as a means for kernel aware \r
+ debuggers to locate queues and has no purpose if a kernel aware debugger\r
+ is not being used. The call to vQueueAddToRegistry() will be removed\r
+ by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is \r
+ defined to be less than 1. */\r
+ vQueueAddToRegistry( xPolledQueue, ( signed char * ) "Poll_Test_Queue" );\r
+\r
+ /* Spawn the producer and consumer. */\r
+ xTaskCreate( vPolledQueueConsumer, ( signed char * ) "QConsNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( xTaskHandle * ) NULL );\r
+ xTaskCreate( vPolledQueueProducer, ( signed char * ) "QProdNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( xTaskHandle * ) NULL );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vPolledQueueProducer, pvParameters )\r
+{\r
+unsigned short usValue = ( unsigned short ) 0;\r
+signed portBASE_TYPE xError = pdFALSE, xLoop;\r
+\r
+ for( ;; )\r
+ { \r
+ for( xLoop = 0; xLoop < pollqVALUES_TO_PRODUCE; xLoop++ )\r
+ {\r
+ /* Send an incrementing number on the queue without blocking. */\r
+ if( xQueueSend( *( ( xQueueHandle * ) pvParameters ), ( void * ) &usValue, pollqNO_DELAY ) != pdPASS )\r
+ {\r
+ /* We should never find the queue full so if we get here there\r
+ has been an error. */\r
+ xError = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ if( xError == pdFALSE )\r
+ {\r
+ /* If an error has ever been recorded we stop incrementing the\r
+ check variable. */\r
+ portENTER_CRITICAL();\r
+ xPollingProducerCount++;\r
+ portEXIT_CRITICAL();\r
+ }\r
+\r
+ /* Update the value we are going to post next time around. */\r
+ usValue++;\r
+ }\r
+ }\r
+\r
+ /* Wait before we start posting again to ensure the consumer runs and\r
+ empties the queue. */\r
+ vTaskDelay( pollqPRODUCER_DELAY );\r
+ }\r
+} /*lint !e818 Function prototype must conform to API. */\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vPolledQueueConsumer, pvParameters )\r
+{\r
+unsigned short usData, usExpectedValue = ( unsigned short ) 0;\r
+signed portBASE_TYPE xError = pdFALSE;\r
+\r
+ for( ;; )\r
+ { \r
+ /* Loop until the queue is empty. */\r
+ while( uxQueueMessagesWaiting( *( ( xQueueHandle * ) pvParameters ) ) )\r
+ {\r
+ if( xQueueReceive( *( ( xQueueHandle * ) pvParameters ), &usData, pollqNO_DELAY ) == pdPASS )\r
+ {\r
+ if( usData != usExpectedValue )\r
+ {\r
+ /* This is not what we expected to receive so an error has\r
+ occurred. */\r
+ xError = pdTRUE;\r
+\r
+ /* Catch-up to the value we received so our next expected\r
+ value should again be correct. */\r
+ usExpectedValue = usData;\r
+ }\r
+ else\r
+ {\r
+ if( xError == pdFALSE )\r
+ {\r
+ /* Only increment the check variable if no errors have\r
+ occurred. */\r
+ portENTER_CRITICAL();\r
+ xPollingConsumerCount++;\r
+ portEXIT_CRITICAL();\r
+ }\r
+ }\r
+\r
+ /* Next time round we would expect the number to be one higher. */\r
+ usExpectedValue++;\r
+ }\r
+ }\r
+\r
+ /* Now the queue is empty we block, allowing the producer to place more\r
+ items in the queue. */\r
+ vTaskDelay( pollqCONSUMER_DELAY );\r
+ }\r
+} /*lint !e818 Function prototype must conform to API. */\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that all the created tasks are still running with no errors. */\r
+portBASE_TYPE xArePollingQueuesStillRunning( void )\r
+{\r
+portBASE_TYPE xReturn;\r
+\r
+ /* Check both the consumer and producer poll count to check they have both\r
+ been changed since out last trip round. We do not need a critical section\r
+ around the check variables as this is called from a higher priority than\r
+ the other tasks that access the same variables. */\r
+ if( ( xPollingConsumerCount == pollqINITIAL_VALUE ) ||\r
+ ( xPollingProducerCount == pollqINITIAL_VALUE )\r
+ )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ else\r
+ {\r
+ xReturn = pdTRUE;\r
+ }\r
+\r
+ /* Set the check variables back down so we know if they have been\r
+ incremented the next time around. */\r
+ xPollingConsumerCount = pollqINITIAL_VALUE;\r
+ xPollingProducerCount = pollqINITIAL_VALUE;\r
+\r
+ return xReturn;\r
+}\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef POLLED_Q_H\r
+#define POLLED_Q_H\r
+\r
+void vStartPolledQueueTasks( unsigned portBASE_TYPE uxPriority );\r
+portBASE_TYPE xArePollingQueuesStillRunning( void );\r
+\r
+#endif\r
+\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ * This file contains some test scenarios that ensure tasks do not exit queue\r
+ * send or receive functions prematurely. A description of the tests is\r
+ * included within the code.\r
+ */\r
+\r
+/* Kernel includes. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "queue.h"\r
+\r
+/* Demo includes. */\r
+#include "blocktim.h"\r
+\r
+/* Task priorities. Allow these to be overridden. */\r
+#ifndef bktPRIMARY_PRIORITY\r
+ #define bktPRIMARY_PRIORITY ( configMAX_PRIORITIES - 3 )\r
+#endif\r
+\r
+#ifndef bktSECONDARY_PRIORITY\r
+ #define bktSECONDARY_PRIORITY ( configMAX_PRIORITIES - 4 )\r
+#endif\r
+\r
+/* Task behaviour. */\r
+#define bktQUEUE_LENGTH ( 5 )\r
+#define bktSHORT_WAIT ( ( ( portTickType ) 20 ) / portTICK_RATE_MS )\r
+#define bktPRIMARY_BLOCK_TIME ( 10 )\r
+#define bktALLOWABLE_MARGIN ( 15 )\r
+#define bktTIME_TO_BLOCK ( 175 )\r
+#define bktDONT_BLOCK ( ( portTickType ) 0 )\r
+#define bktRUN_INDICATOR ( ( unsigned portBASE_TYPE ) 0x55 )\r
+\r
+/* The queue on which the tasks block. */\r
+static xQueueHandle xTestQueue;\r
+\r
+/* Handle to the secondary task is required by the primary task for calls\r
+to vTaskSuspend/Resume(). */\r
+static xTaskHandle xSecondary;\r
+\r
+/* Used to ensure that tasks are still executing without error. */\r
+static volatile portBASE_TYPE xPrimaryCycles = 0, xSecondaryCycles = 0;\r
+static volatile portBASE_TYPE xErrorOccurred = pdFALSE;\r
+\r
+/* Provides a simple mechanism for the primary task to know when the\r
+secondary task has executed. */\r
+static volatile unsigned portBASE_TYPE xRunIndicator;\r
+\r
+/* The two test tasks. Their behaviour is commented within the files. */\r
+static void vPrimaryBlockTimeTestTask( void *pvParameters );\r
+static void vSecondaryBlockTimeTestTask( void *pvParameters );\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vCreateBlockTimeTasks( void )\r
+{\r
+ /* Create the queue on which the two tasks block. */\r
+ xTestQueue = xQueueCreate( bktQUEUE_LENGTH, sizeof( portBASE_TYPE ) );\r
+\r
+ /* vQueueAddToRegistry() adds the queue to the queue registry, if one is\r
+ in use. The queue registry is provided as a means for kernel aware\r
+ debuggers to locate queues and has no purpose if a kernel aware debugger\r
+ is not being used. The call to vQueueAddToRegistry() will be removed\r
+ by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is\r
+ defined to be less than 1. */\r
+ vQueueAddToRegistry( xTestQueue, ( signed char * ) "Block_Time_Queue" );\r
+\r
+ /* Create the two test tasks. */\r
+ xTaskCreate( vPrimaryBlockTimeTestTask, ( signed char * )"BTest1", configMINIMAL_STACK_SIZE, NULL, bktPRIMARY_PRIORITY, NULL );\r
+ xTaskCreate( vSecondaryBlockTimeTestTask, ( signed char * )"BTest2", configMINIMAL_STACK_SIZE, NULL, bktSECONDARY_PRIORITY, &xSecondary );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void vPrimaryBlockTimeTestTask( void *pvParameters )\r
+{\r
+portBASE_TYPE xItem, xData;\r
+portTickType xTimeWhenBlocking;\r
+portTickType xTimeToBlock, xBlockedTime;\r
+\r
+ ( void ) pvParameters;\r
+\r
+ for( ;; )\r
+ {\r
+ /*********************************************************************\r
+ Test 1\r
+\r
+ Simple block time wakeup test on queue receives. */\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ /* The queue is empty. Attempt to read from the queue using a block\r
+ time. When we wake, ensure the delta in time is as expected. */\r
+ xTimeToBlock = bktPRIMARY_BLOCK_TIME << xItem;\r
+\r
+ xTimeWhenBlocking = xTaskGetTickCount();\r
+\r
+ /* We should unblock after xTimeToBlock having not received\r
+ anything on the queue. */\r
+ if( xQueueReceive( xTestQueue, &xData, xTimeToBlock ) != errQUEUE_EMPTY )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* How long were we blocked for? */\r
+ xBlockedTime = xTaskGetTickCount() - xTimeWhenBlocking;\r
+\r
+ if( xBlockedTime < xTimeToBlock )\r
+ {\r
+ /* Should not have blocked for less than we requested. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ if( xBlockedTime > ( xTimeToBlock + bktALLOWABLE_MARGIN ) )\r
+ {\r
+ /* Should not have blocked for longer than we requested,\r
+ although we would not necessarily run as soon as we were\r
+ unblocked so a margin is allowed. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ }\r
+\r
+ /*********************************************************************\r
+ Test 2\r
+\r
+ Simple block time wakeup test on queue sends.\r
+\r
+ First fill the queue. It should be empty so all sends should pass. */\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ if( xQueueSend( xTestQueue, &xItem, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ #if configUSE_PREEMPTION == 0\r
+ taskYIELD();\r
+ #endif\r
+ }\r
+\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ /* The queue is full. Attempt to write to the queue using a block\r
+ time. When we wake, ensure the delta in time is as expected. */\r
+ xTimeToBlock = bktPRIMARY_BLOCK_TIME << xItem;\r
+\r
+ xTimeWhenBlocking = xTaskGetTickCount();\r
+\r
+ /* We should unblock after xTimeToBlock having not received\r
+ anything on the queue. */\r
+ if( xQueueSend( xTestQueue, &xItem, xTimeToBlock ) != errQUEUE_FULL )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* How long were we blocked for? */\r
+ xBlockedTime = xTaskGetTickCount() - xTimeWhenBlocking;\r
+\r
+ if( xBlockedTime < xTimeToBlock )\r
+ {\r
+ /* Should not have blocked for less than we requested. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ if( xBlockedTime > ( xTimeToBlock + bktALLOWABLE_MARGIN ) )\r
+ {\r
+ /* Should not have blocked for longer than we requested,\r
+ although we would not necessarily run as soon as we were\r
+ unblocked so a margin is allowed. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ }\r
+\r
+ /*********************************************************************\r
+ Test 3\r
+\r
+ Wake the other task, it will block attempting to post to the queue.\r
+ When we read from the queue the other task will wake, but before it\r
+ can run we will post to the queue again. When the other task runs it\r
+ will find the queue still full, even though it was woken. It should\r
+ recognise that its block time has not expired and return to block for\r
+ the remains of its block time.\r
+\r
+ Wake the other task so it blocks attempting to post to the already\r
+ full queue. */\r
+ xRunIndicator = 0;\r
+ vTaskResume( xSecondary );\r
+\r
+ /* We need to wait a little to ensure the other task executes. */\r
+ while( xRunIndicator != bktRUN_INDICATOR )\r
+ {\r
+ /* The other task has not yet executed. */\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ }\r
+ /* Make sure the other task is blocked on the queue. */\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ xRunIndicator = 0;\r
+\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ /* Now when we make space on the queue the other task should wake\r
+ but not execute as this task has higher priority. */\r
+ if( xQueueReceive( xTestQueue, &xData, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Now fill the queue again before the other task gets a chance to\r
+ execute. If the other task had executed we would find the queue\r
+ full ourselves, and the other task have set xRunIndicator. */\r
+ if( xQueueSend( xTestQueue, &xItem, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ if( xRunIndicator == bktRUN_INDICATOR )\r
+ {\r
+ /* The other task should not have executed. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Raise the priority of the other task so it executes and blocks\r
+ on the queue again. */\r
+ vTaskPrioritySet( xSecondary, bktPRIMARY_PRIORITY + 2 );\r
+\r
+ /* The other task should now have re-blocked without exiting the\r
+ queue function. */\r
+ if( xRunIndicator == bktRUN_INDICATOR )\r
+ {\r
+ /* The other task should not have executed outside of the\r
+ queue function. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Set the priority back down. */\r
+ vTaskPrioritySet( xSecondary, bktSECONDARY_PRIORITY );\r
+ }\r
+\r
+ /* Let the other task timeout. When it unblockes it will check that it\r
+ unblocked at the correct time, then suspend itself. */\r
+ while( xRunIndicator != bktRUN_INDICATOR )\r
+ {\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ }\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ xRunIndicator = 0;\r
+\r
+\r
+ /*********************************************************************\r
+ Test 4\r
+\r
+ As per test 3 - but with the send and receive the other way around.\r
+ The other task blocks attempting to read from the queue.\r
+\r
+ Empty the queue. We should find that it is full. */\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ if( xQueueReceive( xTestQueue, &xData, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ }\r
+\r
+ /* Wake the other task so it blocks attempting to read from the\r
+ already empty queue. */\r
+ vTaskResume( xSecondary );\r
+\r
+ /* We need to wait a little to ensure the other task executes. */\r
+ while( xRunIndicator != bktRUN_INDICATOR )\r
+ {\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ }\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ xRunIndicator = 0;\r
+\r
+ for( xItem = 0; xItem < bktQUEUE_LENGTH; xItem++ )\r
+ {\r
+ /* Now when we place an item on the queue the other task should\r
+ wake but not execute as this task has higher priority. */\r
+ if( xQueueSend( xTestQueue, &xItem, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Now empty the queue again before the other task gets a chance to\r
+ execute. If the other task had executed we would find the queue\r
+ empty ourselves, and the other task would be suspended. */\r
+ if( xQueueReceive( xTestQueue, &xData, bktDONT_BLOCK ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ if( xRunIndicator == bktRUN_INDICATOR )\r
+ {\r
+ /* The other task should not have executed. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Raise the priority of the other task so it executes and blocks\r
+ on the queue again. */\r
+ vTaskPrioritySet( xSecondary, bktPRIMARY_PRIORITY + 2 );\r
+\r
+ /* The other task should now have re-blocked without exiting the\r
+ queue function. */\r
+ if( xRunIndicator == bktRUN_INDICATOR )\r
+ {\r
+ /* The other task should not have executed outside of the\r
+ queue function. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ vTaskPrioritySet( xSecondary, bktSECONDARY_PRIORITY );\r
+ }\r
+\r
+ /* Let the other task timeout. When it unblockes it will check that it\r
+ unblocked at the correct time, then suspend itself. */\r
+ while( xRunIndicator != bktRUN_INDICATOR )\r
+ {\r
+ vTaskDelay( bktSHORT_WAIT );\r
+ }\r
+ vTaskDelay( bktSHORT_WAIT );\r
+\r
+ xPrimaryCycles++;\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void vSecondaryBlockTimeTestTask( void *pvParameters )\r
+{\r
+portTickType xTimeWhenBlocking, xBlockedTime;\r
+portBASE_TYPE xData;\r
+\r
+ ( void ) pvParameters;\r
+\r
+ for( ;; )\r
+ {\r
+ /*********************************************************************\r
+ Test 1 and 2\r
+\r
+ This task does does not participate in these tests. */\r
+ vTaskSuspend( NULL );\r
+\r
+ /*********************************************************************\r
+ Test 3\r
+\r
+ The first thing we do is attempt to read from the queue. It should be\r
+ full so we block. Note the time before we block so we can check the\r
+ wake time is as per that expected. */\r
+ xTimeWhenBlocking = xTaskGetTickCount();\r
+\r
+ /* We should unblock after bktTIME_TO_BLOCK having not sent\r
+ anything to the queue. */\r
+ xData = 0;\r
+ xRunIndicator = bktRUN_INDICATOR;\r
+ if( xQueueSend( xTestQueue, &xData, bktTIME_TO_BLOCK ) != errQUEUE_FULL )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* How long were we inside the send function? */\r
+ xBlockedTime = xTaskGetTickCount() - xTimeWhenBlocking;\r
+\r
+ /* We should not have blocked for less time than bktTIME_TO_BLOCK. */\r
+ if( xBlockedTime < bktTIME_TO_BLOCK )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* We should of not blocked for much longer than bktALLOWABLE_MARGIN\r
+ either. A margin is permitted as we would not necessarily run as\r
+ soon as we unblocked. */\r
+ if( xBlockedTime > ( bktTIME_TO_BLOCK + bktALLOWABLE_MARGIN ) )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Suspend ready for test 3. */\r
+ xRunIndicator = bktRUN_INDICATOR;\r
+ vTaskSuspend( NULL );\r
+\r
+ /*********************************************************************\r
+ Test 4\r
+\r
+ As per test three, but with the send and receive reversed. */\r
+ xTimeWhenBlocking = xTaskGetTickCount();\r
+\r
+ /* We should unblock after bktTIME_TO_BLOCK having not received\r
+ anything on the queue. */\r
+ xRunIndicator = bktRUN_INDICATOR;\r
+ if( xQueueReceive( xTestQueue, &xData, bktTIME_TO_BLOCK ) != errQUEUE_EMPTY )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ xBlockedTime = xTaskGetTickCount() - xTimeWhenBlocking;\r
+\r
+ /* We should not have blocked for less time than bktTIME_TO_BLOCK. */\r
+ if( xBlockedTime < bktTIME_TO_BLOCK )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* We should of not blocked for much longer than bktALLOWABLE_MARGIN\r
+ either. A margin is permitted as we would not necessarily run as soon\r
+ as we unblocked. */\r
+ if( xBlockedTime > ( bktTIME_TO_BLOCK + bktALLOWABLE_MARGIN ) )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ xRunIndicator = bktRUN_INDICATOR;\r
+\r
+ xSecondaryCycles++;\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+portBASE_TYPE xAreBlockTimeTestTasksStillRunning( void )\r
+{\r
+static portBASE_TYPE xLastPrimaryCycleCount = 0, xLastSecondaryCycleCount = 0;\r
+portBASE_TYPE xReturn = pdPASS;\r
+\r
+ /* Have both tasks performed at least one cycle since this function was\r
+ last called? */\r
+ if( xPrimaryCycles == xLastPrimaryCycleCount )\r
+ {\r
+ xReturn = pdFAIL;\r
+ }\r
+\r
+ if( xSecondaryCycles == xLastSecondaryCycleCount )\r
+ {\r
+ xReturn = pdFAIL;\r
+ }\r
+\r
+ if( xErrorOccurred == pdTRUE )\r
+ {\r
+ xReturn = pdFAIL;\r
+ }\r
+\r
+ xLastSecondaryCycleCount = xSecondaryCycles;\r
+ xLastPrimaryCycleCount = xPrimaryCycles;\r
+\r
+ return xReturn;\r
+}\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef BLOCK_TIME_TEST_H\r
+#define BLOCK_TIME_TEST_H\r
+\r
+void vCreateBlockTimeTasks( void );\r
+portBASE_TYPE xAreBlockTimeTestTasksStillRunning( void );\r
+\r
+#endif\r
+\r
+\r
/*\r
- FreeRTOS V7.0.2 - Copyright (C) 2011 Real Time Engineers Ltd.\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
\r
\r
***************************************************************************\r
FreeRTOS WEB site.\r
\r
1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
\r
- http://www.FreeRTOS.org - Documentation, latest information, license and\r
- contact details.\r
-\r
- http://www.SafeRTOS.com - A version that is certified for use in safety\r
- critical systems.\r
-\r
- http://www.OpenRTOS.com - Commercial support, development, porting,\r
- licensing and training services.\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
*/\r
\r
\r
if( ( xParameters[ 0 ].xSemaphore != NULL ) || ( xParameters[ 1 ].xSemaphore != NULL ) )\r
{\r
/* Create the demo tasks, passing in the semaphore to use as the parameter. */\r
- xTaskCreate( prvCountingSemaphoreTask, ( signed portCHAR * ) "CNT1...", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 0 ] ), tskIDLE_PRIORITY, NULL );\r
- xTaskCreate( prvCountingSemaphoreTask, ( signed portCHAR * ) "CNT2...", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 1 ] ), tskIDLE_PRIORITY, NULL );\r
+ xTaskCreate( prvCountingSemaphoreTask, ( signed portCHAR * ) "CNT1", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 0 ] ), tskIDLE_PRIORITY, NULL );\r
+ xTaskCreate( prvCountingSemaphoreTask, ( signed portCHAR * ) "CNT2", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 1 ] ), tskIDLE_PRIORITY, NULL ); \r
}\r
}\r
/*-----------------------------------------------------------*/\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/**\r
+ * Create a single persistent task which periodically dynamically creates another\r
+ * two tasks. The original task is called the creator task, the two tasks it\r
+ * creates are called suicidal tasks.\r
+ *\r
+ * One of the created suicidal tasks kill one other suicidal task before killing\r
+ * itself - leaving just the original task remaining.\r
+ *\r
+ * The creator task must be spawned after all of the other demo application tasks\r
+ * as it keeps a check on the number of tasks under the scheduler control. The\r
+ * number of tasks it expects to see running should never be greater than the\r
+ * number of tasks that were in existence when the creator task was spawned, plus\r
+ * one set of four suicidal tasks. If this number is exceeded an error is flagged.\r
+ *\r
+ * \page DeathC death.c\r
+ * \ingroup DemoFiles\r
+ * <HR>\r
+ */\r
+\r
+/*\r
+Changes from V3.0.0\r
+ + CreationCount sizes changed from unsigned portBASE_TYPE to\r
+ unsigned short to minimize the risk of overflowing.\r
+ \r
+ + Reset of usLastCreationCount added\r
+ \r
+Changes from V3.1.0\r
+ + Changed the dummy calculation to use variables of type long, rather than\r
+ float. This allows the file to be used with ports that do not support\r
+ floating point.\r
+\r
+*/\r
+\r
+#include <stdlib.h>\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+\r
+/* Demo program include files. */\r
+#include "death.h"\r
+\r
+#define deathSTACK_SIZE ( configMINIMAL_STACK_SIZE + 60 )\r
+\r
+/* The task originally created which is responsible for periodically dynamically\r
+creating another four tasks. */\r
+static portTASK_FUNCTION_PROTO( vCreateTasks, pvParameters );\r
+\r
+/* The task function of the dynamically created tasks. */\r
+static portTASK_FUNCTION_PROTO( vSuicidalTask, pvParameters );\r
+\r
+/* A variable which is incremented every time the dynamic tasks are created. This\r
+is used to check that the task is still running. */\r
+static volatile unsigned short usCreationCount = 0;\r
+\r
+/* Used to store the number of tasks that were originally running so the creator\r
+task can tell if any of the suicidal tasks have failed to die.\r
+*/\r
+static volatile unsigned portBASE_TYPE uxTasksRunningAtStart = 0;\r
+\r
+/* Tasks are deleted by the idle task. Under heavy load the idle task might\r
+not get much processing time, so it would be legitimate for several tasks to\r
+remain undeleted for a short period. */\r
+static const unsigned portBASE_TYPE uxMaxNumberOfExtraTasksRunning = 3;\r
+\r
+/* Used to store a handle to the task that should be killed by a suicidal task,\r
+before it kills itself. */\r
+xTaskHandle xCreatedTask;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vCreateSuicidalTasks( unsigned portBASE_TYPE uxPriority )\r
+{\r
+unsigned portBASE_TYPE *puxPriority;\r
+\r
+ /* Create the Creator tasks - passing in as a parameter the priority at which\r
+ the suicidal tasks should be created. */\r
+ puxPriority = ( unsigned portBASE_TYPE * ) pvPortMalloc( sizeof( unsigned portBASE_TYPE ) );\r
+ *puxPriority = uxPriority;\r
+\r
+ xTaskCreate( vCreateTasks, ( signed char * ) "CREATOR", deathSTACK_SIZE, ( void * ) puxPriority, uxPriority, NULL );\r
+\r
+ /* Record the number of tasks that are running now so we know if any of the\r
+ suicidal tasks have failed to be killed. */\r
+ uxTasksRunningAtStart = ( unsigned portBASE_TYPE ) uxTaskGetNumberOfTasks();\r
+ \r
+ /* FreeRTOS.org versions before V3.0 started the idle-task as the very\r
+ first task. The idle task was then already included in uxTasksRunningAtStart.\r
+ From FreeRTOS V3.0 on, the idle task is started when the scheduler is\r
+ started. Therefore the idle task is not yet accounted for. We correct\r
+ this by increasing uxTasksRunningAtStart by 1. */\r
+ uxTasksRunningAtStart++;\r
+ \r
+ /* From FreeRTOS version 7.0.0 can optionally create a timer service task. \r
+ If this is done, then uxTasksRunningAtStart needs incrementing again as that\r
+ too is created when the scheduler is started. */\r
+ #if configUSE_TIMERS == 1\r
+ uxTasksRunningAtStart++;\r
+ #endif\r
+}\r
+/*-----------------------------------------------------------*/\r
+ \r
+static portTASK_FUNCTION( vSuicidalTask, pvParameters )\r
+{\r
+volatile long l1, l2;\r
+xTaskHandle xTaskToKill;\r
+const portTickType xDelay = ( portTickType ) 200 / portTICK_RATE_MS;\r
+\r
+ if( pvParameters != NULL )\r
+ {\r
+ /* This task is periodically created four times. Two created tasks are\r
+ passed a handle to the other task so it can kill it before killing itself.\r
+ The other task is passed in null. */\r
+ xTaskToKill = *( xTaskHandle* )pvParameters;\r
+ }\r
+ else\r
+ {\r
+ xTaskToKill = NULL;\r
+ }\r
+\r
+ for( ;; )\r
+ {\r
+ /* Do something random just to use some stack and registers. */\r
+ l1 = 2;\r
+ l2 = 89;\r
+ l2 *= l1;\r
+ vTaskDelay( xDelay );\r
+\r
+ if( xTaskToKill != NULL )\r
+ {\r
+ /* Make sure the other task has a go before we delete it. */\r
+ vTaskDelay( ( portTickType ) 0 );\r
+\r
+ /* Kill the other task that was created by vCreateTasks(). */\r
+ vTaskDelete( xTaskToKill );\r
+\r
+ /* Kill ourselves. */\r
+ vTaskDelete( NULL );\r
+ }\r
+ }\r
+}/*lint !e818 !e550 Function prototype must be as per standard for task functions. */\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vCreateTasks, pvParameters )\r
+{\r
+const portTickType xDelay = ( portTickType ) 1000 / portTICK_RATE_MS;\r
+unsigned portBASE_TYPE uxPriority;\r
+\r
+ uxPriority = *( unsigned portBASE_TYPE * ) pvParameters;\r
+ vPortFree( pvParameters );\r
+\r
+ for( ;; )\r
+ {\r
+ /* Just loop round, delaying then creating the four suicidal tasks. */\r
+ vTaskDelay( xDelay );\r
+\r
+ xCreatedTask = NULL;\r
+\r
+ xTaskCreate( vSuicidalTask, ( signed char * ) "SUICID1", configMINIMAL_STACK_SIZE, NULL, uxPriority, &xCreatedTask );\r
+ xTaskCreate( vSuicidalTask, ( signed char * ) "SUICID2", configMINIMAL_STACK_SIZE, &xCreatedTask, uxPriority, NULL );\r
+\r
+ ++usCreationCount;\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that the creator task is still running and that there\r
+are not any more than four extra tasks. */\r
+portBASE_TYPE xIsCreateTaskStillRunning( void )\r
+{\r
+static unsigned short usLastCreationCount = 0xfff;\r
+portBASE_TYPE xReturn = pdTRUE;\r
+static unsigned portBASE_TYPE uxTasksRunningNow;\r
+\r
+ if( usLastCreationCount == usCreationCount )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ else\r
+ {\r
+ usLastCreationCount = usCreationCount;\r
+ }\r
+ \r
+ uxTasksRunningNow = ( unsigned portBASE_TYPE ) uxTaskGetNumberOfTasks();\r
+\r
+ if( uxTasksRunningNow < uxTasksRunningAtStart )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ else if( ( uxTasksRunningNow - uxTasksRunningAtStart ) > uxMaxNumberOfExtraTasksRunning )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+ else\r
+ {\r
+ /* Everything is okay. */\r
+ }\r
+\r
+ return xReturn;\r
+}\r
+\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef SUICIDE_TASK_H\r
+#define SUICIDE_TASK_H\r
+\r
+void vCreateSuicidalTasks( unsigned portBASE_TYPE uxPriority );\r
+portBASE_TYPE xIsCreateTaskStillRunning( void );\r
+\r
+#endif\r
+\r
+\r
/*\r
- FreeRTOS V7.0.2 - Copyright (C) 2011 Real Time Engineers Ltd.\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
\r
\r
***************************************************************************\r
FreeRTOS WEB site.\r
\r
1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
\r
- http://www.FreeRTOS.org - Documentation, latest information, license and\r
- contact details.\r
-\r
- http://www.SafeRTOS.com - A version that is certified for use in safety\r
- critical systems.\r
-\r
- http://www.OpenRTOS.com - Commercial support, development, porting,\r
- licensing and training services.\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
*/\r
\r
/*\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ * This version of integer. c is for use on systems that have limited stack\r
+ * space and no display facilities. The complete version can be found in\r
+ * the Demo/Common/Full directory.\r
+ *\r
+ * As with the full version, the tasks created in this file are a good test \r
+ * of the scheduler context switch mechanism. The processor has to access \r
+ * 32bit variables in two or four chunks (depending on the processor). The low \r
+ * priority of these tasks means there is a high probability that a context \r
+ * switch will occur mid calculation. See flop. c documentation for \r
+ * more information.\r
+ *\r
+ */\r
+\r
+/*\r
+Changes from V1.2.1\r
+\r
+ + The constants used in the calculations are larger to ensure the\r
+ optimiser does not truncate them to 16 bits.\r
+\r
+Changes from V1.2.3\r
+\r
+ + uxTaskCheck is now just used as a boolean. Instead of incrementing\r
+ the variable each cycle of the task, the variable is simply set to\r
+ true. sAreIntegerMathsTaskStillRunning() sets it back to false and\r
+ expects it to have been set back to true by the time it is called\r
+ again.\r
+ + A division has been included in the calculation.\r
+*/\r
+\r
+#include <stdlib.h>\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+\r
+/* Demo program include files. */\r
+#include "integer.h"\r
+\r
+/* The constants used in the calculation. */\r
+#define intgCONST1 ( ( long ) 123 )\r
+#define intgCONST2 ( ( long ) 234567 )\r
+#define intgCONST3 ( ( long ) -3 )\r
+#define intgCONST4 ( ( long ) 7 )\r
+#define intgEXPECTED_ANSWER ( ( ( intgCONST1 + intgCONST2 ) * intgCONST3 ) / intgCONST4 )\r
+\r
+#define intgSTACK_SIZE configMINIMAL_STACK_SIZE\r
+\r
+/* As this is the minimal version, we will only create one task. */\r
+#define intgNUMBER_OF_TASKS ( 1 )\r
+\r
+/* The task function. Repeatedly performs a 32 bit calculation, checking the\r
+result against the expected result. If the result is incorrect then the\r
+context switch must have caused some corruption. */\r
+static portTASK_FUNCTION_PROTO( vCompeteingIntMathTask, pvParameters );\r
+\r
+/* Variables that are set to true within the calculation task to indicate\r
+that the task is still executing. The check task sets the variable back to\r
+false, flagging an error if the variable is still false the next time it\r
+is called. */\r
+static volatile signed portBASE_TYPE xTaskCheck[ intgNUMBER_OF_TASKS ] = { ( signed portBASE_TYPE ) pdFALSE };\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vStartIntegerMathTasks( unsigned portBASE_TYPE uxPriority )\r
+{\r
+short sTask;\r
+\r
+ for( sTask = 0; sTask < intgNUMBER_OF_TASKS; sTask++ )\r
+ {\r
+ xTaskCreate( vCompeteingIntMathTask, ( signed char * ) "IntMath", intgSTACK_SIZE, ( void * ) &( xTaskCheck[ sTask ] ), uxPriority, ( xTaskHandle * ) NULL );\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( vCompeteingIntMathTask, pvParameters )\r
+{\r
+/* These variables are all effectively set to constants so they are volatile to\r
+ensure the compiler does not just get rid of them. */\r
+volatile long lValue;\r
+short sError = pdFALSE;\r
+volatile signed portBASE_TYPE *pxTaskHasExecuted;\r
+\r
+ /* Set a pointer to the variable we are going to set to true each\r
+ iteration. This is also a good test of the parameter passing mechanism\r
+ within each port. */\r
+ pxTaskHasExecuted = ( volatile signed portBASE_TYPE * ) pvParameters;\r
+\r
+ /* Keep performing a calculation and checking the result against a constant. */\r
+ for( ;; )\r
+ {\r
+ /* Perform the calculation. This will store partial value in\r
+ registers, resulting in a good test of the context switch mechanism. */\r
+ lValue = intgCONST1;\r
+ lValue += intgCONST2;\r
+\r
+ /* Yield in case cooperative scheduling is being used. */\r
+ #if configUSE_PREEMPTION == 0\r
+ {\r
+ taskYIELD();\r
+ }\r
+ #endif\r
+\r
+ /* Finish off the calculation. */\r
+ lValue *= intgCONST3;\r
+ lValue /= intgCONST4;\r
+\r
+ /* If the calculation is found to be incorrect we stop setting the \r
+ TaskHasExecuted variable so the check task can see an error has \r
+ occurred. */\r
+ if( lValue != intgEXPECTED_ANSWER ) /*lint !e774 volatile used to prevent this being optimised out. */\r
+ {\r
+ sError = pdTRUE;\r
+ }\r
+\r
+ if( sError == pdFALSE )\r
+ {\r
+ /* We have not encountered any errors, so set the flag that show\r
+ we are still executing. This will be periodically cleared by\r
+ the check task. */\r
+ portENTER_CRITICAL();\r
+ *pxTaskHasExecuted = pdTRUE;\r
+ portEXIT_CRITICAL();\r
+ }\r
+\r
+ /* Yield in case cooperative scheduling is being used. */\r
+ #if configUSE_PREEMPTION == 0\r
+ {\r
+ taskYIELD();\r
+ }\r
+ #endif\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that all the created tasks are still running. */\r
+portBASE_TYPE xAreIntegerMathsTaskStillRunning( void )\r
+{\r
+portBASE_TYPE xReturn = pdTRUE;\r
+short sTask;\r
+\r
+ /* Check the maths tasks are still running by ensuring their check variables \r
+ are still being set to true. */\r
+ for( sTask = 0; sTask < intgNUMBER_OF_TASKS; sTask++ )\r
+ {\r
+ if( xTaskCheck[ sTask ] == pdFALSE )\r
+ {\r
+ /* The check has not incremented so an error exists. */\r
+ xReturn = pdFALSE;\r
+ }\r
+\r
+ /* Reset the check variable so we can tell if it has been set by\r
+ the next time around. */\r
+ xTaskCheck[ sTask ] = pdFALSE;\r
+ }\r
+\r
+ return xReturn;\r
+}\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef INTEGER_TASKS_H\r
+#define INTEGER_TASKS_H\r
+\r
+void vStartIntegerMathTasks( unsigned portBASE_TYPE uxPriority );\r
+portBASE_TYPE xAreIntegerMathsTaskStillRunning( void );\r
+\r
+#endif\r
+\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ The tasks defined on this page demonstrate the use of recursive mutexes.\r
+\r
+ For recursive mutex functionality the created mutex should be created using\r
+ xSemaphoreCreateRecursiveMutex(), then be manipulated\r
+ using the xSemaphoreTakeRecursive() and xSemaphoreGiveRecursive() API\r
+ functions.\r
+\r
+ This demo creates three tasks all of which access the same recursive mutex:\r
+\r
+ prvRecursiveMutexControllingTask() has the highest priority so executes \r
+ first and grabs the mutex. It then performs some recursive accesses - \r
+ between each of which it sleeps for a short period to let the lower \r
+ priority tasks execute. When it has completed its demo functionality\r
+ it gives the mutex back before suspending itself.\r
+\r
+ prvRecursiveMutexBlockingTask() attempts to access the mutex by performing\r
+ a blocking 'take'. The blocking task has a lower priority than the \r
+ controlling task so by the time it executes the mutex has already been\r
+ taken by the controlling task, causing the blocking task to block. It \r
+ does not unblock until the controlling task has given the mutex back, \r
+ and it does not actually run until the controlling task has suspended \r
+ itself (due to the relative priorities). When it eventually does obtain\r
+ the mutex all it does is give the mutex back prior to also suspending \r
+ itself. At this point both the controlling task and the blocking task are \r
+ suspended.\r
+\r
+ prvRecursiveMutexPollingTask() runs at the idle priority. It spins round\r
+ a tight loop attempting to obtain the mutex with a non-blocking call. As\r
+ the lowest priority task it will not successfully obtain the mutex until\r
+ both the controlling and blocking tasks are suspended. Once it eventually \r
+ does obtain the mutex it first unsuspends both the controlling task and\r
+ blocking task prior to giving the mutex back - resulting in the polling\r
+ task temporarily inheriting the controlling tasks priority.\r
+*/\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "semphr.h"\r
+\r
+/* Demo app include files. */\r
+#include "recmutex.h"\r
+\r
+/* Priorities assigned to the three tasks. */\r
+#define recmuCONTROLLING_TASK_PRIORITY ( tskIDLE_PRIORITY + 2 )\r
+#define recmuBLOCKING_TASK_PRIORITY ( tskIDLE_PRIORITY + 1 )\r
+#define recmuPOLLING_TASK_PRIORITY ( tskIDLE_PRIORITY + 0 )\r
+\r
+/* The recursive call depth. */\r
+#define recmuMAX_COUNT ( 10 )\r
+\r
+/* Misc. */\r
+#define recmuSHORT_DELAY ( 20 / portTICK_RATE_MS )\r
+#define recmuNO_DELAY ( ( portTickType ) 0 )\r
+#define recmuTWO_TICK_DELAY ( ( portTickType ) 2 )\r
+\r
+/* The three tasks as described at the top of this file. */\r
+static void prvRecursiveMutexControllingTask( void *pvParameters );\r
+static void prvRecursiveMutexBlockingTask( void *pvParameters );\r
+static void prvRecursiveMutexPollingTask( void *pvParameters );\r
+\r
+/* The mutex used by the demo. */\r
+static xSemaphoreHandle xMutex;\r
+\r
+/* Variables used to detect and latch errors. */\r
+static volatile portBASE_TYPE xErrorOccurred = pdFALSE, xControllingIsSuspended = pdFALSE, xBlockingIsSuspended = pdFALSE;\r
+static volatile unsigned portBASE_TYPE uxControllingCycles = 0, uxBlockingCycles = 0, uxPollingCycles = 0;\r
+\r
+/* Handles of the two higher priority tasks, required so they can be resumed \r
+(unsuspended). */\r
+static xTaskHandle xControllingTaskHandle, xBlockingTaskHandle;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vStartRecursiveMutexTasks( void )\r
+{\r
+ /* Just creates the mutex and the three tasks. */\r
+\r
+ xMutex = xSemaphoreCreateRecursiveMutex();\r
+\r
+ /* vQueueAddToRegistry() adds the mutex to the registry, if one is\r
+ in use. The registry is provided as a means for kernel aware \r
+ debuggers to locate mutex and has no purpose if a kernel aware debugger\r
+ is not being used. The call to vQueueAddToRegistry() will be removed\r
+ by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is \r
+ defined to be less than 1. */\r
+ vQueueAddToRegistry( ( xQueueHandle ) xMutex, ( signed portCHAR * ) "Recursive_Mutex" );\r
+\r
+\r
+ if( xMutex != NULL )\r
+ {\r
+ xTaskCreate( prvRecursiveMutexControllingTask, ( signed portCHAR * ) "Rec1", configMINIMAL_STACK_SIZE, NULL, recmuCONTROLLING_TASK_PRIORITY, &xControllingTaskHandle );\r
+ xTaskCreate( prvRecursiveMutexBlockingTask, ( signed portCHAR * ) "Rec2", configMINIMAL_STACK_SIZE, NULL, recmuBLOCKING_TASK_PRIORITY, &xBlockingTaskHandle );\r
+ xTaskCreate( prvRecursiveMutexPollingTask, ( signed portCHAR * ) "Rec3", configMINIMAL_STACK_SIZE, NULL, recmuPOLLING_TASK_PRIORITY, NULL );\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvRecursiveMutexControllingTask( void *pvParameters )\r
+{\r
+unsigned portBASE_TYPE ux;\r
+\r
+ /* Just to remove compiler warning. */\r
+ ( void ) pvParameters;\r
+\r
+ for( ;; )\r
+ {\r
+ /* Should not be able to 'give' the mutex, as we have not yet 'taken'\r
+ it. The first time through, the mutex will not have been used yet,\r
+ subsequent times through, at this point the mutex will be held by the\r
+ polling task. */\r
+ if( xSemaphoreGiveRecursive( xMutex ) == pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ for( ux = 0; ux < recmuMAX_COUNT; ux++ )\r
+ {\r
+ /* We should now be able to take the mutex as many times as\r
+ we like.\r
+ \r
+ The first time through the mutex will be immediately available, on\r
+ subsequent times through the mutex will be held by the polling task\r
+ at this point and this Take will cause the polling task to inherit\r
+ the priority of this task. In this case the block time must be\r
+ long enough to ensure the polling task will execute again before the\r
+ block time expires. If the block time does expire then the error\r
+ flag will be set here. */\r
+ if( xSemaphoreTakeRecursive( xMutex, recmuTWO_TICK_DELAY ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Ensure the other task attempting to access the mutex (and the\r
+ other demo tasks) are able to execute to ensure they either block\r
+ (where a block time is specified) or return an error (where no \r
+ block time is specified) as the mutex is held by this task. */\r
+ vTaskDelay( recmuSHORT_DELAY );\r
+ }\r
+\r
+ /* For each time we took the mutex, give it back. */\r
+ for( ux = 0; ux < recmuMAX_COUNT; ux++ )\r
+ {\r
+ /* Ensure the other task attempting to access the mutex (and the\r
+ other demo tasks) are able to execute. */\r
+ vTaskDelay( recmuSHORT_DELAY );\r
+\r
+ /* We should now be able to give the mutex as many times as we\r
+ took it. When the mutex is available again the Blocking task\r
+ should be unblocked but not run because it has a lower priority\r
+ than this task. The polling task should also not run at this point\r
+ as it too has a lower priority than this task. */\r
+ if( xSemaphoreGiveRecursive( xMutex ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ }\r
+\r
+ /* Having given it back the same number of times as it was taken, we\r
+ should no longer be the mutex owner, so the next give sh ould fail. */\r
+ if( xSemaphoreGiveRecursive( xMutex ) == pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Keep count of the number of cycles this task has performed so a \r
+ stall can be detected. */\r
+ uxControllingCycles++;\r
+\r
+ /* Suspend ourselves to the blocking task can execute. */\r
+ xControllingIsSuspended = pdTRUE;\r
+ vTaskSuspend( NULL );\r
+ xControllingIsSuspended = pdFALSE;\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvRecursiveMutexBlockingTask( void *pvParameters )\r
+{\r
+ /* Just to remove compiler warning. */\r
+ ( void ) pvParameters;\r
+\r
+ for( ;; )\r
+ {\r
+ /* This task will run while the controlling task is blocked, and the\r
+ controlling task will block only once it has the mutex - therefore\r
+ this call should block until the controlling task has given up the \r
+ mutex, and not actually execute past this call until the controlling \r
+ task is suspended. */\r
+ if( xSemaphoreTakeRecursive( xMutex, portMAX_DELAY ) == pdPASS )\r
+ {\r
+ if( xControllingIsSuspended != pdTRUE )\r
+ {\r
+ /* Did not expect to execute until the controlling task was\r
+ suspended. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ /* Give the mutex back before suspending ourselves to allow\r
+ the polling task to obtain the mutex. */\r
+ if( xSemaphoreGiveRecursive( xMutex ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ xBlockingIsSuspended = pdTRUE;\r
+ vTaskSuspend( NULL );\r
+ xBlockingIsSuspended = pdFALSE;\r
+ }\r
+ }\r
+ else\r
+ {\r
+ /* We should not leave the xSemaphoreTakeRecursive() function\r
+ until the mutex was obtained. */\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* The controlling and blocking tasks should be in lock step. */\r
+ if( uxControllingCycles != ( uxBlockingCycles + 1 ) )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+\r
+ /* Keep count of the number of cycles this task has performed so a \r
+ stall can be detected. */\r
+ uxBlockingCycles++;\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvRecursiveMutexPollingTask( void *pvParameters )\r
+{\r
+ /* Just to remove compiler warning. */\r
+ ( void ) pvParameters;\r
+\r
+ for( ;; )\r
+ {\r
+ /* Keep attempting to obtain the mutex. We should only obtain it when\r
+ the blocking task has suspended itself, which in turn should only\r
+ happen when the controlling task is also suspended. */\r
+ if( xSemaphoreTakeRecursive( xMutex, recmuNO_DELAY ) == pdPASS )\r
+ {\r
+ /* Is the blocking task suspended? */\r
+ if( ( xBlockingIsSuspended != pdTRUE ) || ( xControllingIsSuspended != pdTRUE ) )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ /* Keep count of the number of cycles this task has performed \r
+ so a stall can be detected. */\r
+ uxPollingCycles++;\r
+\r
+ /* We can resume the other tasks here even though they have a\r
+ higher priority than the polling task. When they execute they\r
+ will attempt to obtain the mutex but fail because the polling\r
+ task is still the mutex holder. The polling task (this task)\r
+ will then inherit the higher priority. The Blocking task will\r
+ block indefinitely when it attempts to obtain the mutex, the\r
+ Controlling task will only block for a fixed period and an\r
+ error will be latched if the polling task has not returned the\r
+ mutex by the time this fixed period has expired. */\r
+ vTaskResume( xBlockingTaskHandle );\r
+ vTaskResume( xControllingTaskHandle );\r
+ \r
+ /* The other two tasks should now have executed and no longer\r
+ be suspended. */\r
+ if( ( xBlockingIsSuspended == pdTRUE ) || ( xControllingIsSuspended == pdTRUE ) )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ } \r
+ \r
+ /* Release the mutex, disinheriting the higher priority again. */\r
+ if( xSemaphoreGiveRecursive( xMutex ) != pdPASS )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ }\r
+ }\r
+\r
+ #if configUSE_PREEMPTION == 0\r
+ {\r
+ taskYIELD();\r
+ }\r
+ #endif\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that all the created tasks are still running. */\r
+portBASE_TYPE xAreRecursiveMutexTasksStillRunning( void )\r
+{\r
+portBASE_TYPE xReturn;\r
+static unsigned portBASE_TYPE uxLastControllingCycles = 0, uxLastBlockingCycles = 0, uxLastPollingCycles = 0;\r
+\r
+ /* Is the controlling task still cycling? */\r
+ if( uxLastControllingCycles == uxControllingCycles )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ uxLastControllingCycles = uxControllingCycles;\r
+ }\r
+\r
+ /* Is the blocking task still cycling? */\r
+ if( uxLastBlockingCycles == uxBlockingCycles )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ uxLastBlockingCycles = uxBlockingCycles;\r
+ }\r
+\r
+ /* Is the polling task still cycling? */\r
+ if( uxLastPollingCycles == uxPollingCycles )\r
+ {\r
+ xErrorOccurred = pdTRUE;\r
+ }\r
+ else\r
+ {\r
+ uxLastPollingCycles = uxPollingCycles;\r
+ }\r
+\r
+ if( xErrorOccurred == pdTRUE )\r
+ {\r
+ xReturn = pdFAIL;\r
+ }\r
+ else\r
+ {\r
+ xReturn = pdTRUE;\r
+ }\r
+\r
+ return xReturn;\r
+}\r
+\r
+\r
+\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef RECURSIVE_MUTEX_TEST_H\r
+#define RECURSIVE_MUTEX_TEST_H\r
+\r
+void vStartRecursiveMutexTasks( void );\r
+portBASE_TYPE xAreRecursiveMutexTasksStillRunning( void );\r
+\r
+#endif\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/*\r
+ * Creates two sets of two tasks. The tasks within a set share a variable, access \r
+ * to which is guarded by a semaphore.\r
+ * \r
+ * Each task starts by attempting to obtain the semaphore. On obtaining a \r
+ * semaphore a task checks to ensure that the guarded variable has an expected \r
+ * value. It then clears the variable to zero before counting it back up to the \r
+ * expected value in increments of 1. After each increment the variable is checked \r
+ * to ensure it contains the value to which it was just set. When the starting \r
+ * value is again reached the task releases the semaphore giving the other task in \r
+ * the set a chance to do exactly the same thing. The starting value is high \r
+ * enough to ensure that a tick is likely to occur during the incrementing loop.\r
+ *\r
+ * An error is flagged if at any time during the process a shared variable is \r
+ * found to have a value other than that expected. Such an occurrence would \r
+ * suggest an error in the mutual exclusion mechanism by which access to the \r
+ * variable is restricted.\r
+ *\r
+ * The first set of two tasks poll their semaphore. The second set use blocking \r
+ * calls.\r
+ *\r
+ */\r
+\r
+\r
+#include <stdlib.h>\r
+\r
+/* Scheduler include files. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "semphr.h"\r
+\r
+/* Demo app include files. */\r
+#include "semtest.h"\r
+\r
+/* The value to which the shared variables are counted. */\r
+#define semtstBLOCKING_EXPECTED_VALUE ( ( unsigned long ) 0xfff )\r
+#define semtstNON_BLOCKING_EXPECTED_VALUE ( ( unsigned long ) 0xff )\r
+\r
+#define semtstSTACK_SIZE configMINIMAL_STACK_SIZE\r
+\r
+#define semtstNUM_TASKS ( 4 )\r
+\r
+#define semtstDELAY_FACTOR ( ( portTickType ) 10 )\r
+\r
+/* The task function as described at the top of the file. */\r
+static portTASK_FUNCTION_PROTO( prvSemaphoreTest, pvParameters );\r
+\r
+/* Structure used to pass parameters to each task. */\r
+typedef struct SEMAPHORE_PARAMETERS\r
+{\r
+ xSemaphoreHandle xSemaphore;\r
+ volatile unsigned long *pulSharedVariable;\r
+ portTickType xBlockTime;\r
+} xSemaphoreParameters;\r
+\r
+/* Variables used to check that all the tasks are still running without errors. */\r
+static volatile short sCheckVariables[ semtstNUM_TASKS ] = { 0 };\r
+static volatile short sNextCheckVariable = 0;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vStartSemaphoreTasks( unsigned portBASE_TYPE uxPriority )\r
+{\r
+xSemaphoreParameters *pxFirstSemaphoreParameters, *pxSecondSemaphoreParameters;\r
+const portTickType xBlockTime = ( portTickType ) 100;\r
+\r
+ /* Create the structure used to pass parameters to the first two tasks. */\r
+ pxFirstSemaphoreParameters = ( xSemaphoreParameters * ) pvPortMalloc( sizeof( xSemaphoreParameters ) );\r
+\r
+ if( pxFirstSemaphoreParameters != NULL )\r
+ {\r
+ /* Create the semaphore used by the first two tasks. */\r
+ vSemaphoreCreateBinary( pxFirstSemaphoreParameters->xSemaphore );\r
+\r
+ if( pxFirstSemaphoreParameters->xSemaphore != NULL )\r
+ {\r
+ /* Create the variable which is to be shared by the first two tasks. */\r
+ pxFirstSemaphoreParameters->pulSharedVariable = ( unsigned long * ) pvPortMalloc( sizeof( unsigned long ) );\r
+\r
+ /* Initialise the share variable to the value the tasks expect. */\r
+ *( pxFirstSemaphoreParameters->pulSharedVariable ) = semtstNON_BLOCKING_EXPECTED_VALUE;\r
+\r
+ /* The first two tasks do not block on semaphore calls. */\r
+ pxFirstSemaphoreParameters->xBlockTime = ( portTickType ) 0;\r
+\r
+ /* Spawn the first two tasks. As they poll they operate at the idle priority. */\r
+ xTaskCreate( prvSemaphoreTest, ( signed char * ) "PolSEM1", semtstSTACK_SIZE, ( void * ) pxFirstSemaphoreParameters, tskIDLE_PRIORITY, ( xTaskHandle * ) NULL );\r
+ xTaskCreate( prvSemaphoreTest, ( signed char * ) "PolSEM2", semtstSTACK_SIZE, ( void * ) pxFirstSemaphoreParameters, tskIDLE_PRIORITY, ( xTaskHandle * ) NULL );\r
+ }\r
+ }\r
+\r
+ /* Do exactly the same to create the second set of tasks, only this time \r
+ provide a block time for the semaphore calls. */\r
+ pxSecondSemaphoreParameters = ( xSemaphoreParameters * ) pvPortMalloc( sizeof( xSemaphoreParameters ) );\r
+ if( pxSecondSemaphoreParameters != NULL )\r
+ {\r
+ vSemaphoreCreateBinary( pxSecondSemaphoreParameters->xSemaphore );\r
+\r
+ if( pxSecondSemaphoreParameters->xSemaphore != NULL )\r
+ {\r
+ pxSecondSemaphoreParameters->pulSharedVariable = ( unsigned long * ) pvPortMalloc( sizeof( unsigned long ) );\r
+ *( pxSecondSemaphoreParameters->pulSharedVariable ) = semtstBLOCKING_EXPECTED_VALUE;\r
+ pxSecondSemaphoreParameters->xBlockTime = xBlockTime / portTICK_RATE_MS;\r
+\r
+ xTaskCreate( prvSemaphoreTest, ( signed char * ) "BlkSEM1", semtstSTACK_SIZE, ( void * ) pxSecondSemaphoreParameters, uxPriority, ( xTaskHandle * ) NULL );\r
+ xTaskCreate( prvSemaphoreTest, ( signed char * ) "BlkSEM2", semtstSTACK_SIZE, ( void * ) pxSecondSemaphoreParameters, uxPriority, ( xTaskHandle * ) NULL );\r
+ }\r
+ }\r
+\r
+ /* vQueueAddToRegistry() adds the semaphore to the registry, if one is\r
+ in use. The registry is provided as a means for kernel aware \r
+ debuggers to locate semaphores and has no purpose if a kernel aware debugger\r
+ is not being used. The call to vQueueAddToRegistry() will be removed\r
+ by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is \r
+ defined to be less than 1. */\r
+ vQueueAddToRegistry( ( xQueueHandle ) pxFirstSemaphoreParameters->xSemaphore, ( signed char * ) "Counting_Sem_1" );\r
+ vQueueAddToRegistry( ( xQueueHandle ) pxSecondSemaphoreParameters->xSemaphore, ( signed char * ) "Counting_Sem_2" );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portTASK_FUNCTION( prvSemaphoreTest, pvParameters )\r
+{\r
+xSemaphoreParameters *pxParameters;\r
+volatile unsigned long *pulSharedVariable, ulExpectedValue;\r
+unsigned long ulCounter;\r
+short sError = pdFALSE, sCheckVariableToUse;\r
+\r
+ /* See which check variable to use. sNextCheckVariable is not semaphore \r
+ protected! */\r
+ portENTER_CRITICAL();\r
+ sCheckVariableToUse = sNextCheckVariable;\r
+ sNextCheckVariable++;\r
+ portEXIT_CRITICAL();\r
+\r
+ /* A structure is passed in as the parameter. This contains the shared \r
+ variable being guarded. */\r
+ pxParameters = ( xSemaphoreParameters * ) pvParameters;\r
+ pulSharedVariable = pxParameters->pulSharedVariable;\r
+\r
+ /* If we are blocking we use a much higher count to ensure loads of context\r
+ switches occur during the count. */\r
+ if( pxParameters->xBlockTime > ( portTickType ) 0 )\r
+ {\r
+ ulExpectedValue = semtstBLOCKING_EXPECTED_VALUE;\r
+ }\r
+ else\r
+ {\r
+ ulExpectedValue = semtstNON_BLOCKING_EXPECTED_VALUE;\r
+ }\r
+\r
+ for( ;; )\r
+ {\r
+ /* Try to obtain the semaphore. */\r
+ if( xSemaphoreTake( pxParameters->xSemaphore, pxParameters->xBlockTime ) == pdPASS )\r
+ {\r
+ /* We have the semaphore and so expect any other tasks using the\r
+ shared variable to have left it in the state we expect to find\r
+ it. */\r
+ if( *pulSharedVariable != ulExpectedValue )\r
+ {\r
+ sError = pdTRUE;\r
+ }\r
+ \r
+ /* Clear the variable, then count it back up to the expected value\r
+ before releasing the semaphore. Would expect a context switch or\r
+ two during this time. */\r
+ for( ulCounter = ( unsigned long ) 0; ulCounter <= ulExpectedValue; ulCounter++ )\r
+ {\r
+ *pulSharedVariable = ulCounter;\r
+ if( *pulSharedVariable != ulCounter )\r
+ {\r
+ sError = pdTRUE;\r
+ }\r
+ }\r
+\r
+ /* Release the semaphore, and if no errors have occurred increment the check\r
+ variable. */\r
+ if( xSemaphoreGive( pxParameters->xSemaphore ) == pdFALSE )\r
+ {\r
+ sError = pdTRUE;\r
+ }\r
+\r
+ if( sError == pdFALSE )\r
+ {\r
+ if( sCheckVariableToUse < semtstNUM_TASKS )\r
+ {\r
+ ( sCheckVariables[ sCheckVariableToUse ] )++;\r
+ }\r
+ }\r
+\r
+ /* If we have a block time then we are running at a priority higher\r
+ than the idle priority. This task takes a long time to complete\r
+ a cycle (deliberately so to test the guarding) so will be starving\r
+ out lower priority tasks. Block for some time to allow give lower\r
+ priority tasks some processor time. */\r
+ vTaskDelay( pxParameters->xBlockTime * semtstDELAY_FACTOR );\r
+ }\r
+ else\r
+ {\r
+ if( pxParameters->xBlockTime == ( portTickType ) 0 )\r
+ {\r
+ /* We have not got the semaphore yet, so no point using the\r
+ processor. We are not blocking when attempting to obtain the\r
+ semaphore. */\r
+ taskYIELD();\r
+ }\r
+ }\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+/* This is called to check that all the created tasks are still running. */\r
+portBASE_TYPE xAreSemaphoreTasksStillRunning( void )\r
+{\r
+static short sLastCheckVariables[ semtstNUM_TASKS ] = { 0 };\r
+portBASE_TYPE xTask, xReturn = pdTRUE;\r
+\r
+ for( xTask = 0; xTask < semtstNUM_TASKS; xTask++ )\r
+ {\r
+ if( sLastCheckVariables[ xTask ] == sCheckVariables[ xTask ] )\r
+ {\r
+ xReturn = pdFALSE;\r
+ }\r
+\r
+ sLastCheckVariables[ xTask ] = sCheckVariables[ xTask ];\r
+ }\r
+\r
+ return xReturn;\r
+}\r
+\r
+\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+ \r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+#ifndef SEMAPHORE_TEST_H\r
+#define SEMAPHORE_TEST_H\r
+\r
+void vStartSemaphoreTasks( unsigned portBASE_TYPE uxPriority );\r
+portBASE_TYPE xAreSemaphoreTasksStillRunning( void );\r
+\r
+#endif\r
+\r
function. */\r
#include "partest.h"\r
\r
+/* Library includes. */\r
+#include "het.h"\r
+\r
/* Set mainCREATE_SIMPLE_BLINKY_DEMO_ONLY to one to run the simple blinky demo,\r
or 0 to run the more comprehensive test and demo application. */\r
-#define mainCREATE_SIMPLE_BLINKY_DEMO_ONLY 1\r
+#define mainCREATE_SIMPLE_BLINKY_DEMO_ONLY 0\r
\r
/*-----------------------------------------------------------*/\r
\r
--- /dev/null
+/*\r
+ FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+\r
+\r
+ ***************************************************************************\r
+ * *\r
+ * FreeRTOS tutorial books are available in pdf and paperback. *\r
+ * Complete, revised, and edited pdf reference manuals are also *\r
+ * available. *\r
+ * *\r
+ * Purchasing FreeRTOS documentation will not only help you, by *\r
+ * ensuring you get running as quickly as possible and with an *\r
+ * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+ * the FreeRTOS project to continue with its mission of providing *\r
+ * professional grade, cross platform, de facto standard solutions *\r
+ * for microcontrollers - completely free of charge! *\r
+ * *\r
+ * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+ * *\r
+ * Thank you for using FreeRTOS, and thank you for your support! *\r
+ * *\r
+ ***************************************************************************\r
+\r
+\r
+ This file is part of the FreeRTOS distribution.\r
+\r
+ FreeRTOS is free software; you can redistribute it and/or modify it under\r
+ the terms of the GNU General Public License (version 2) as published by the\r
+ Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+ >>>NOTE<<< The modification to the GPL is included to allow you to\r
+ distribute a combined work that includes FreeRTOS without being obliged to\r
+ provide the source code for proprietary components outside of the FreeRTOS\r
+ kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+ WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+ or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+ more details. You should have received a copy of the GNU General Public\r
+ License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+ can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+ by writing to Richard Barry, contact details for whom are available on the\r
+ FreeRTOS WEB site.\r
+\r
+ 1 tab == 4 spaces!\r
+ \r
+ ***************************************************************************\r
+ * *\r
+ * Having a problem? Start by reading the FAQ "My application does *\r
+ * not run, what could be wrong? *\r
+ * *\r
+ * http://www.FreeRTOS.org/FAQHelp.html *\r
+ * *\r
+ ***************************************************************************\r
+\r
+ \r
+ http://www.FreeRTOS.org - Documentation, training, latest information, \r
+ license and contact details.\r
+ \r
+ http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+ including FreeRTOS+Trace - an indispensable productivity tool.\r
+\r
+ Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+ the code with commercial support, indemnification, and middleware, under \r
+ the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+ provide a safety engineered and independently SIL3 certified version under \r
+ the SafeRTOS brand: http://www.SafeRTOS.com.\r
+*/\r
+\r
+/******************************************************************************\r
+ * NOTE 1: This project provides two demo applications. A simple blinky style\r
+ * project, and a more comprehensive test and demo application. The\r
+ * mainCREATE_SIMPLE_BLINKY_DEMO_ONLY setting in main.c is used to select\r
+ * between the two. See the notes on using mainCREATE_SIMPLE_BLINKY_DEMO_ONLY\r
+ * in main.c. This file implements the comprehensive test and demo version.\r
+ *\r
+ * NOTE 2: This file only contains the source code that is specific to the\r
+ * full demo. Generic functions, such FreeRTOS hook functions, and functions\r
+ * required to configure the hardware, are defined in main.c.\r
+ ******************************************************************************\r
+ *\r
+ * main_full() creates all the demo application tasks and a software timer, then\r
+ * starts the scheduler. The web documentation provides more details of the \r
+ * standard demo application tasks, which provide no particular functionality, \r
+ * but do provide a good example of how to use the FreeRTOS API.\r
+ *\r
+ * In addition to the standard demo tasks, the following tasks and tests are\r
+ * defined and/or created within this file:\r
+ *\r
+ * "Check" timer - The check software timer period is initially set to three\r
+ * seconds. The callback function associated with the check software timer\r
+ * checks that all the standard demo tasks are not only still executing, but \r
+ * are executing without reporting any errors. If the check software timer \r
+ * discovers that a task has either stalled, or reported an error, then it \r
+ * changes its own execution period from the initial three seconds, to just \r
+ * 200ms. The check software timer callback function also toggles the green \r
+ * LED each time it is called. This provides a visual indication of the system \r
+ * status: If the green LED toggles every three seconds, then no issues have \r
+ * been discovered. If the green LED toggles every 200ms, then an issue has \r
+ * been discovered with at least one task.\r
+ *\r
+ * See the documentation page for this demo on the FreeRTOS.org web site for\r
+ * full information, including hardware setup requirements. \r
+ */\r
+\r
+/* Standard includes. */\r
+#include <stdio.h>\r
+\r
+/* Kernel includes. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+#include "timers.h"\r
+#include "semphr.h"\r
+\r
+/* Standard demo application includes. */\r
+#include "integer.h"\r
+#include "PollQ.h"\r
+#include "semtest.h"\r
+#include "dynamic.h"\r
+#include "BlockQ.h"\r
+#include "blocktim.h"\r
+#include "countsem.h"\r
+#include "GenQTest.h"\r
+#include "recmutex.h"\r
+#include "death.h"\r
+#include "partest.h"\r
+\r
+/* Priorities for the demo application tasks. */\r
+#define mainQUEUE_POLL_PRIORITY ( tskIDLE_PRIORITY + 2UL )\r
+#define mainSEM_TEST_PRIORITY ( tskIDLE_PRIORITY + 1UL )\r
+#define mainBLOCK_Q_PRIORITY ( tskIDLE_PRIORITY + 2UL )\r
+#define mainCREATOR_TASK_PRIORITY ( tskIDLE_PRIORITY + 3UL )\r
+#define mainFLOP_TASK_PRIORITY ( tskIDLE_PRIORITY )\r
+#define mainCOM_TEST_PRIORITY ( tskIDLE_PRIORITY + 2 )\r
+\r
+/* A block time of zero simply means "don't block". */\r
+#define mainDONT_BLOCK ( 0UL )\r
+\r
+/* The period after which the check timer will expire, converted to ticks. */\r
+#define mainCHECK_TIMER_PERIOD_MS ( 3000UL / portTICK_RATE_MS )\r
+\r
+/* The period after which the LED timer will expire, converted to ticks. */\r
+#define mainLED_TIMER_PERIOD_MS ( 75UL / portTICK_RATE_MS )\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/*\r
+ * The check timer callback function, as described at the top of this file.\r
+ */\r
+static void prvCheckTimerCallback( xTimerHandle xTimer );\r
+\r
+/*\r
+ * The LED timer callback function, as described at the top of this file.\r
+ */\r
+static void prvLEDTimerCallback( xTimerHandle xTimer );\r
+\r
+/*\r
+ * The reg test tasks, as described at the top of this file.\r
+ */\r
+extern void vRegTestTask1( void *pvParameters );\r
+extern void vRegTestTask2( void *pvParameters );\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/* Variables that are incremented on each iteration of the reg test tasks -\r
+provided the tasks have not reported any errors. The check task inspects these\r
+variables to ensure they are still incrementing as expected. If a variable\r
+stops incrementing then it is likely that its associate task has stalled. */\r
+volatile unsigned long ulRegTest1Counter = 0, ulRegTest2Counter = 0;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void main_full( void )\r
+{\r
+xTimerHandle xTimer = NULL;\r
+\r
+ /* Start all the standard demo/test tasks. These have not particular\r
+ functionality, but do demonstrate how to use the FreeRTOS API, and test the\r
+ kernel port. */\r
+ vStartIntegerMathTasks( tskIDLE_PRIORITY );\r
+ vStartDynamicPriorityTasks();\r
+ vStartBlockingQueueTasks( mainBLOCK_Q_PRIORITY );\r
+ vCreateBlockTimeTasks();\r
+ vStartCountingSemaphoreTasks();\r
+ vStartGenericQueueTasks( tskIDLE_PRIORITY );\r
+ vStartRecursiveMutexTasks();\r
+ vStartPolledQueueTasks( mainQUEUE_POLL_PRIORITY );\r
+ vStartSemaphoreTasks( mainSEM_TEST_PRIORITY );\r
+\r
+ /* Create the register test tasks, as described at the top of this file. */\r
+ xTaskCreate(vRegTestTask1, ( const signed char * ) "Reg1...", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL );\r
+ xTaskCreate(vRegTestTask2, ( const signed char * ) "Reg2...", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL );\r
+ \r
+ /* Create the software timer that performs the 'check' functionality,\r
+ as described at the top of this file. */\r
+ xTimer = xTimerCreate( ( const signed char * ) "CheckTimer",/* A text name, purely to help debugging. */\r
+ ( mainCHECK_TIMER_PERIOD_MS ), /* The timer period, in this case 3000ms (3s). */\r
+ pdTRUE, /* This is an auto-reload timer, so xAutoReload is set to pdTRUE. */\r
+ ( void * ) 0, /* The ID is not used, so can be set to anything. */\r
+ prvCheckTimerCallback /* The callback function that inspects the status of all the other tasks. */\r
+ );\r
+ \r
+ if( xTimer != NULL )\r
+ {\r
+ xTimerStart( xTimer, mainDONT_BLOCK );\r
+ }\r
+\r
+ /* Create the software timer that performs the 'LED toggle' functionality,\r
+ as described at the top of this file. */\r
+ xTimer = xTimerCreate( ( const signed char * ) "LEDTimer", /* A text name, purely to help debugging. */\r
+ ( mainLED_TIMER_PERIOD_MS ), /* The timer period, in this case 75ms. */\r
+ pdTRUE, /* This is an auto-reload timer, so xAutoReload is set to pdTRUE. */\r
+ ( void * ) 0, /* The ID is not used, so can be set to anything. */\r
+ prvLEDTimerCallback /* The callback function that toggles the white LEDs. */\r
+ );\r
+\r
+ if( xTimer != NULL )\r
+ {\r
+ xTimerStart( xTimer, mainDONT_BLOCK );\r
+ }\r
+\r
+ /* The set of tasks created by the following function call have to be \r
+ created last as they keep account of the number of tasks they expect to see \r
+ running. */\r
+ vCreateSuicidalTasks( mainCREATOR_TASK_PRIORITY );\r
+\r
+ /* Start the scheduler. */\r
+ vTaskStartScheduler();\r
+ \r
+ /* If all is well, the scheduler will now be running, and the following line\r
+ will never be reached. If the following line does execute, then there was\r
+ insufficient FreeRTOS heap memory available for the idle and/or timer tasks\r
+ to be created. See the memory management section on the FreeRTOS web site\r
+ for more details. */\r
+ for( ;; ); \r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvCheckTimerCallback( xTimerHandle xTimer )\r
+{\r
+static long lChangeToRedLEDsAlready = pdFALSE;\r
+static unsigned long ulLastRegTest1Counter = 0, ulLastRegTest2Counter = 0;\r
+unsigned long ulErrorFound = pdFALSE;\r
+/* LEDs are defaulted to use the Green LEDs. The Red LEDs are used if an error\r
+is found. */\r
+static unsigned long ulLED1 = 8, ulLED2 = 11;\r
+const unsigned long ulRedLED1 = 6, ulRedLED2 = 9;\r
+\r
+ /* Check all the demo tasks (other than the flash tasks) to ensure\r
+ they are all still running, and that none have detected an error. */\r
+\r
+ if( xAreIntegerMathsTaskStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( xAreDynamicPriorityTasksStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( xAreBlockingQueuesStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if ( xAreBlockTimeTestTasksStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if ( xAreGenericQueueTasksStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if ( xAreRecursiveMutexTasksStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( xIsCreateTaskStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( xArePollingQueuesStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( xAreSemaphoreTasksStillRunning() != pdTRUE )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+ \r
+ /* Check the reg test tasks are still cycling. They will stop\r
+ incrementing their loop counters if they encounter an error. */\r
+ if( ulRegTest1Counter == ulLastRegTest1Counter )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ if( ulRegTest2Counter == ulLastRegTest2Counter )\r
+ {\r
+ ulErrorFound = pdTRUE;\r
+ }\r
+\r
+ ulLastRegTest1Counter = ulRegTest1Counter;\r
+ ulLastRegTest2Counter = ulRegTest2Counter;\r
+\r
+ /* Toggle the check LEDs to give an indication of the system status. If\r
+ the green LEDs are toggling, then no errors have been detected. If the red\r
+ LEDs are toggling, then an error has been reported in at least one task. */\r
+ vParTestToggleLED( ulLED1 );\r
+ vParTestToggleLED( ulLED2 );\r
+ \r
+ /* Have any errors been latch in ulErrorFound? If so, ensure the gree LEDs\r
+ are off, then switch to using the red LEDs. */\r
+ if( ulErrorFound != pdFALSE )\r
+ {\r
+ if( lChangeToRedLEDsAlready == pdFALSE )\r
+ {\r
+ lChangeToRedLEDsAlready = pdTRUE;\r
+ \r
+ /* An error has been found. Switch to use the red LEDs. */\r
+ vParTestSetLED( ulLED1, pdFALSE );\r
+ vParTestSetLED( ulLED2, pdFALSE );\r
+ ulLED1 = ulRedLED1;\r
+ ulLED2 = ulRedLED2;\r
+ }\r
+ }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvLEDTimerCallback( xTimerHandle xTimer )\r
+{\r
+const unsigned long ulNumWhiteLEDs = 6;\r
+static unsigned long ulLit1 = 2, ulLit2 = 1;\r
+\r
+ vParTestSetLED( ulLit2, pdFALSE );\r
+\r
+ ulLit2 = ulLit1;\r
+ ulLit1++;\r
+\r
+ if( ulLit1 >= ulNumWhiteLEDs )\r
+ {\r
+ ulLit1 = 0;\r
+ }\r
+\r
+ vParTestSetLED( ulLit1, pdTRUE );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
--- /dev/null
+;/*\r
+; FreeRTOS V7.2.0 - Copyright (C) 2012 Real Time Engineers Ltd.\r
+;\r
+;\r
+; ***************************************************************************\r
+; * *\r
+; * FreeRTOS tutorial books are available in pdf and paperback. *\r
+; * Complete, revised, and edited pdf reference manuals are also *\r
+; * available. *\r
+; * *\r
+; * Purchasing FreeRTOS documentation will not only help you, by *\r
+; * ensuring you get running as quickly as possible and with an *\r
+; * in-depth knowledge of how to use FreeRTOS, it will also help *\r
+; * the FreeRTOS project to continue with its mission of providing *\r
+; * professional grade, cross platform, de facto standard solutions *\r
+; * for microcontrollers - completely free of charge! *\r
+; * *\r
+; * >>> See http://www.FreeRTOS.org/Documentation for details. <<< *\r
+; * *\r
+; * Thank you for using FreeRTOS, and thank you for your support! *\r
+; * *\r
+; ***************************************************************************\r
+;\r
+;\r
+; This file is part of the FreeRTOS distribution.\r
+;\r
+; FreeRTOS is free software; you can redistribute it and/or modify it under\r
+; the terms of the GNU General Public License (version 2) as published by the\r
+; Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+; >>>NOTE<<< The modification to the GPL is included to allow you to\r
+; distribute a combined work that includes FreeRTOS without being obliged to\r
+; provide the source code for proprietary components outside of the FreeRTOS\r
+; kernel. FreeRTOS is distributed in the hope that it will be useful, but\r
+; WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\r
+; or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for\r
+; more details. You should have received a copy of the GNU General Public\r
+; License and the FreeRTOS license exception along with FreeRTOS; if not it\r
+; can be viewed here: http://www.freertos.org/a00114.html and also obtained\r
+; by writing to Richard Barry, contact details for whom are available on the\r
+; FreeRTOS WEB site.\r
+;\r
+; 1 tab == 4 spaces!\r
+; \r
+; ***************************************************************************\r
+; * *\r
+; * Having a problem? Start by reading the FAQ "My application does *\r
+; * not run, what could be wrong? *\r
+; * *\r
+; * http://www.FreeRTOS.org/FAQHelp.html *\r
+; * *\r
+; ***************************************************************************\r
+;\r
+; \r
+; http://www.FreeRTOS.org - Documentation, training, latest information, \r
+; license and contact details.\r
+; \r
+; http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+; including FreeRTOS+Trace - an indispensable productivity tool.\r
+;\r
+; Real Time Engineers ltd license FreeRTOS to High Integrity Systems, who sell \r
+; the code with commercial support, indemnification, and middleware, under \r
+; the OpenRTOS brand: http://www.OpenRTOS.com. High Integrity Systems also\r
+; provide a safety engineered and independently SIL3 certified version under \r
+; the SafeRTOS brand: http://www.SafeRTOS.com.\r
+;*/\r
+\r
+;-------------------------------------------------\r
+;\r
+ .def vRegTestTask1\r
+ .ref ulRegTest1Counter\r
+ .text\r
+ .arm\r
+\r
+vRegTestTask1:\r
+ ; Fill each general purpose register with a known value.\r
+ mov r0, #0xFF\r
+ mov r1, #0x11\r
+ mov r2, #0x22\r
+ mov r3, #0x33\r
+ mov r4, #0x44 \r
+ mov r5, #0x55\r
+ mov r6, #0x66\r
+ mov r7, #0x77\r
+ mov r8, #0x88\r
+ mov r9, #0x99\r
+ mov r10, #0xAA\r
+ mov r11, #0xBB\r
+ mov r12, #0xCC\r
+ mov r14, #0xEE\r
+ \r
+vRegTestLoop1:\r
+\r
+ ; Force yeild\r
+ swi #0\r
+\r
+ ; Test each general purpose register to check that it still contains the\r
+ ; expected known value, jumping to vRegTestError1 if any register contains\r
+ ; an unexpected value.\r
+ cmp r0, #0xFF\r
+ bne vRegTestError1 \r
+ cmp r1, #0x11\r
+ bne vRegTestError1 \r
+ cmp r2, #0x22\r
+ bne vRegTestError1 \r
+ cmp r3, #0x33\r
+ bne vRegTestError1 \r
+ cmp r4, #0x44\r
+ bne vRegTestError1 \r
+ cmp r5, #0x55\r
+ bne vRegTestError1 \r
+ cmp r6, #0x66\r
+ bne vRegTestError1 \r
+ cmp r7, #0x77\r
+ bne vRegTestError1 \r
+ cmp r8, #0x88\r
+ bne vRegTestError1 \r
+ cmp r9, #0x99\r
+ bne vRegTestError1 \r
+ cmp r10, #0xAA\r
+ bne vRegTestError1 \r
+ cmp r11, #0xBB\r
+ bne vRegTestError1 \r
+ cmp r12, #0xCC\r
+ bne vRegTestError1 \r
+ cmp r14, #0xEE\r
+ bne vRegTestError1 \r
+ \r
+ ; This task is still running without jumping to vRegTestError1, so increment\r
+ ; the loop counter so the check task knows the task is running error free.\r
+ stmfd sp!, { r0-r1 }\r
+ ldr r0, Count1Const\r
+ ldr r1, [r0]\r
+ add r1, r1, #1\r
+ str r1, [r0]\r
+ ldmfd sp!, { r0-r1 }\r
+ \r
+ ; Loop again, performing the same tests.\r
+ b vRegTestLoop1\r
+\r
+Count1Const .word ulRegTest1Counter\r
+ \r
+vRegTestError1:\r
+ b vRegTestError1\r
+\r
+\r
+;-------------------------------------------------\r
+;\r
+ .def vRegTestTask2\r
+ .ref ulRegTest2Counter\r
+ .text\r
+ .arm\r
+;\r
+vRegTestTask2:\r
+ ; Fill each general purpose register with a known value.\r
+ mov r0, #0xFF000000\r
+ mov r1, #0x11000000\r
+ mov r2, #0x22000000\r
+ mov r3, #0x33000000\r
+ mov r4, #0x44000000 \r
+ mov r5, #0x55000000\r
+ mov r6, #0x66000000\r
+ mov r7, #0x77000000\r
+ mov r8, #0x88000000\r
+ mov r9, #0x99000000\r
+ mov r10, #0xAA000000\r
+ mov r11, #0xBB000000\r
+ mov r12, #0xCC000000\r
+ mov r14, #0xEE000000\r
+ \r
+vRegTestLoop2:\r
+\r
+ ; Test each general purpose register to check that it still contains the\r
+ ; expected known value, jumping to vRegTestError2 if any register contains\r
+ ; an unexpected value.\r
+ cmp r0, #0xFF000000\r
+ bne vRegTestError2 \r
+ cmp r1, #0x11000000\r
+ bne vRegTestError2 \r
+ cmp r2, #0x22000000\r
+ bne vRegTestError2 \r
+ cmp r3, #0x33000000\r
+ bne vRegTestError2 \r
+ cmp r4, #0x44000000\r
+ bne vRegTestError2 \r
+ cmp r5, #0x55000000\r
+ bne vRegTestError2 \r
+ cmp r6, #0x66000000\r
+ bne vRegTestError2 \r
+ cmp r7, #0x77000000\r
+ bne vRegTestError2 \r
+ cmp r8, #0x88000000\r
+ bne vRegTestError2 \r
+ cmp r9, #0x99000000\r
+ bne vRegTestError2 \r
+ cmp r10, #0xAA000000\r
+ bne vRegTestError2 \r
+ cmp r11, #0xBB000000\r
+ bne vRegTestError2 \r
+ cmp r12, #0xCC000000\r
+ bne vRegTestError2 \r
+ cmp r14, #0xEE000000\r
+ bne vRegTestError2 \r
+ \r
+ ; This task is still running without jumping to vRegTestError2, so increment\r
+ ; the loop counter so the check task knows the task is running error free.\r
+ stmfd sp!, { r0-r1 }\r
+ ldr r0, Count2Const\r
+ ldr r1, [r0]\r
+ add r1, r1, #1\r
+ str r1, [r0]\r
+ ldmfd sp!, { r0-r1 }\r
+ \r
+ ; Loop again, performing the same tests.\r
+ b vRegTestLoop2\r
+\r
+Count2Const .word ulRegTest2Counter\r
+ \r
+vRegTestError2:\r
+ b vRegTestError2\r
+\r
+;-------------------------------------------------\r
+ \r
+ \r
+ \r
;-------------------------------------------------------------------------------\r
; interrupt vectors\r
\r
- b _c_int00\r
- b #-8\r
- b vPortYieldProcessor\r
- b #-8\r
- b #-8\r
- b #-8\r
- ldr pc,[pc,#-0x1b0]\r
- ldr pc,[pc,#-0x1b0]\r
+ b _c_int00 ; reset\r
+ b #-8 ; undefined instruction\r
+ b vPortYieldProcessor ; software interrupt\r
+ b #-8 ; Abort (prefetch)\r
+ b #-8 ; Abort (data)\r
+ b #-8 ; Reserved\r
+ ldr pc,[pc,#-0x1b0] ; IRQ\r
+ ldr pc,[pc,#-0x1b0] ; FIQ\r
\r
\r
;-------------------------------------------------------------------------------\r