FreeRTOS系列(二) 我的“1”出来了

上回说到我的任务1不见了,只有任务2,这次要找它出来!

上篇链接:https://blog.csdn.net/so_cracy/article/details/80246414

找出来的方式有很多种,先说说抢占式调度(CubeMx默认设置是这个)

一、抢占式调度

还是先来看看osThreadDef的定义:


上一章我们大概清楚了第一个参数 name 的作用,os_thread_def_##name 是声明了一个变量,#name是把这么宏参数变为字符串,用作任务的名称!

第二个参数 thread 就是任务的具体函数了

第三个参数 priority 看注释知道是任务的优先级,通过默认函数的第三个参数 osPriorityNormal,跳转到定义:


可以看到,osPriorityNormal 实际上就是0,看注释也可以知道,数值越大,优先级也越高(如果不知道优先级是什么东西,那就先去看看优先级吧),注意了

FreeRTOS中,数值越大,优先级也越高,FreeRTOS总是运行优先级最高的任务(抢占式)

优先级的设定就相当于普通会员和VIP会员,不用想都知道是先服务VIP会员再服务普通会员,可以猜想一下,如果任务1的优先级比任务2的高,是不是说任务1就会比任务2先执行呢?把任务1弄成VIP会员,来实验一下就知道了



结果显示,任务1真的出来了,果然会员是很有用的,但是任务2却不见了,这又是为何?

二、任务状态

嵌入式操作系统中,每一个任务都是有状态的,FreeRTOS 的运行支持以下四种状态

Running—运行态
Ready—就绪态
Blocked—阻塞态
Suspended—挂起态

运行态就是说任务现在正在运行,就绪态是指任务可以运行了,但是还没开始运行,就比如在银行排队取钱一样,你已经准备好取钱了,但是前面有人也在取钱,你得排队!那么有没有不排队的方法?有,VIP会员!哈哈!后面再说!

就绪态就是再排队取钱的人,运行态就是正在取钱的人,代码里的 printf("StartDefaultTask1 \r\n"); 就是取钱的这个动作!而柜台妹妹,就相当于是内核/调度器!


任务1由于是一个死循环,就相当于是一直都在取钱,一直霸占着柜台妹妹,那么柜台妹妹就永远都服务不到后面的人了!所以任务2就打印不出来了,怎么解救柜台妹妹,让她服务我们呢?有几种方法,我们先说高尚一点的做法,任务1主动让出柜台妹妹:

不是取钱吗?取了一笔钱,那我先数一会钱吧,柜台妹妹先借给你们用用呗!
osDelay(100)实际就是把任务的状态切换到阻塞态,让出CPU占用,让CPU服务其它任务。但是有借有还,我数完钱了,我又会把柜台妹妹抢回来的,为什么我可以抢?因为我是VIP(优先级较高)。

任务2也是个死循环,也是一直霸占着柜台妹妹,做人要厚道一点,也先数一会钱吧!

(为了方便显示,我把调试信息改了一下)

这下1和2都出来了:


三、时间片调度

想一下,加入任务2也是个VIP呢?


想必也肯定是某一个被抢占了柜台妹妹,那柜台妹妹有没有主动权呢?先服务一下任务1,再服务一下任务2(难道是传说中的3P大战=_=!!),这个还是可以有的:

改一下代码,便于显示:


注意这里的延时函数是自己写的,里面是一个死循环,这里的m_delay(100)是延时100ms,而不是osDelay();

然后把时钟频率改为100HZ,这样,时间片就会变成10ms一个时间片:


这样的话,时间片的时长就是10m了,看看结果:


可以是着把m_delay改成osDelay()看看效果,Task1 和Task2,几乎是同时输出的(目前市面上的串口调试工具可能看不到这样的结果)

还可以把时间片修改为其它值,看看效果!



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章