【FreeRTOS】小白进阶之如何使用FreeRTOS二值信号量(一)

介绍信号量使用基础。

1、头文件声明

#include "FreeRTOS.h"
#include "task.h"
#include "semphr.h"
#include "supporting_functions.h"

#define mainINTERRUPT_NUMBER	3

static void vHandlerTask( void *pvParameters );
static void vPeriodicTask( void *pvParameters );

// 仿真中断
static uint32_t ulExampleInterruptHandler( void );

// 二值信号量定义
SemaphoreHandle_t xBinarySemaphore;

2、启动任务

任务 vPeriodicRask 用于启动模拟中断。

int main( void )
{
    // 二值信号量创建
    xBinarySemaphore = xSemaphoreCreateBinary();

	if( xBinarySemaphore != NULL )
	{
		xTaskCreate( vHandlerTask, "Handler", 1000, NULL, 3, NULL );

		xTaskCreate( vPeriodicTask, "Periodic", 1000, NULL, 1, NULL );

		vPortSetInterruptHandler( mainINTERRUPT_NUMBER, ulExampleInterruptHandler );

		vTaskStartScheduler();
	}

	for( ;; );
	return 0;
}

3、任务实现

static void vHandlerTask( void *pvParameters )
{
	for( ;; )
	{
		// block 等待中断同步
		xSemaphoreTake( xBinarySemaphore, portMAX_DELAY );

		vPrintString( "Handler task - Processing event.\r\n" );
	}
}

static void vPeriodicTask( void *pvParameters )
{
	const TickType_t xDelay500ms = pdMS_TO_TICKS( 500UL );

	for( ;; )
	{
		vTaskDelay( xDelay500ms );

		vPrintString( "Periodic task - About to generate an interrupt.\r\n" );
		
		// 获取中断
		vPortGenerateSimulatedInterrupt( mainINTERRUPT_NUMBER );
		vPrintString( "Periodic task - Interrupt generated.\r\n\r\n\r\n" );
	}
}

static uint32_t ulExampleInterruptHandler( void )
{
    BaseType_t xHigherPriorityTaskWoken;

	// 解锁信号量
	xSemaphoreGiveFromISR( xBinarySemaphore, &xHigherPriorityTaskWoken );
	
	portYIELD_FROM_ISR( xHigherPriorityTaskWoken );
}

 

你可能感兴趣的:(FreeRTOS系统开发)