4.物联网操作系统多任务使用

一。临界段的应用

临界段的作用

临界段API

临界段应用

1.什么是临界段?

在程序访问资源时,不希望被其他任务或者中断打断,这段要执行的代码,称为临界代码段

 2.不想被打断访问的资源

(1)读取或者修改变量(全局变量)

(2)调用公共函数的代码(不可重入函数)

(3)使用硬件资源(外设)

(4)对时序有精准要求的操作

(5)用户不想被打断的代码

3.临界段API

 

 

 4.临界段的应用

(1)功能要求

1、分别修改Usart_Task、DelayTask任务

2、配置延时周期为50ms打印一次运行状态,观察现象,是否出现,资源冲突问题

3、通过临界段解决共享资源冲突问题

(2)不修改Cubemx创建工程

(3)如果把延迟时间缩少,串口可能会发生问题,任务同时想占用资源导致冲突。

 (4)解决方法

     taskENTER_CRITICAL();
     printf("DelayTask is Runing!\r\n");
     taskEXIT_CRITICAL();

在串口输出之间使用开关中断管理。

二。临界段实现的原理

三。任务大小的确定

四。实验:堆栈检测应用

1.实验要求

1、打开栈溢出检测方案(共二种)

2、修改Usart_Task任务

3、在任务内模拟栈溢出,分析实验结果

2.Cubemx创建工程

注意:配置上述之后会在FREERTOS.c中出现判断溢出的回调函数 ,如下图所示。

3.检测溢出

《1》第一种检测溢出方式

 (1)使用溢出回调函数,输出提示。

	printf("%s is Stack OverFlow\r\n",pcTaskName);

(2)自己写一个溢出的函数,在任务中使用

void vStackOverFlowTest(void){
	uint8_t u8TestBuff[128];
	int16_t i;
	(void)u8TestBuff;
	for(i=360;i>=0;i--){
		u8TestBuff[i]=0x88;
	}
}

输出结果

《2》第二种检测方法

修改了什么位置的宏定义,效果就是在上一个检测的基础上多了一些未知东西。

补充实验:获取任务状态方案

1.实验要求

1、打开任务状态配置

2、修改key_Task任务

3、当检测按键按下时,打印任务状态信息

2.Cubemx创建工程

        FREERTOS中Configure中使能两个Run Time的内容(原因应该是打开获取任务状态方法) 

3.步骤: 

//用来接受信息的字符串
uint8_t u8TaskListBuff[400];
//在按钮处
memset(u8TaskListBuff,0,400);
vTaskList((char*)u8TaskListBuff);
printf("Name      State    Priority    Stack   Num\r\n");
printf("******************************************************\r\n");
printf("%s",u8TaskListBuff);
printf("******************************************************\r\n");

4.结果

 实验:CPU效率统计应用

1.cubemx创建工程(在计算堆栈的工程基础上)

(1)进入FREERTOS

(2)配置Tim6

 Tim6的中断配置

 2.步骤

(0)定义计时数据 uint32_t u32TimeCount;

注意:《1》tim.c中为最终数据,其余为extern(main.c中,FREERTOS.c中)

《2》注意头文件的加入

uint32_t u32TimeCount;

(1)在FREERTOS.c中生成了

实现前:

实现后:

 复制版:

__weak void configureTimerForRunTimeStats(void)
{
	//¿ªÆô¶¨Ê±Æ÷µÄÖжϣ¬Æô¶¯¶¨Ê±Æ÷
	//¶¨Ê±Æ÷ͳ¼ÆÖµ£¬³õʼ»¯Îª0
	HAL_TIM_Base_Start_IT(&htim6);
	u32TimeCount = 0ul;
}

__weak unsigned long getRunTimeCounterValue(void)
{
return u32TimeCount;
}

 (2)在main.c的时间中断函数中加入Tim6中断处理

	if (htim->Instance == TIM6) {
    u32TimeCount++;
  }

(3)在以前的按钮下加入

vTaskGetRunTimeStats((char*)u8TaskListBuff);
printf("Name      Abs Time        Time\r\n");

3.结果

综上可知:vTaskGetRunTimeStats()需要使用高精度的定时器计数。这里使用的是Tim6,在一个FREERTOS.c中的回调函数中使能定时器与返回计数的数据,在main.c中的定时器中断回调函数中计数。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值