历史上的今天
返回首页

历史上的今天

今天是:2025年04月25日(星期五)

正在发生

2019年04月25日 | UCOSIII任务间的通信

2019-04-25 来源:eefocus

1、UCOSIII任务间通信

       1.1、任务间通信

一个任务或者中断服务程序有时候需要和另一个任务交流信息,这个就是消息传递的过程就叫做任务间通信;任务间的消息传递可以通过2种途径:一是通过全局变量,二是通过发布消息。


       使用全局变量的时候每个任务或者中断服务程序都必须保证其对全局变量的独占访问。消息也可以通过消息队列作为中介发布给任务。


       1.2 什么是消息?

       消息包含一下几个部分:指向数据的指针,数据的长度和记录消息发布时刻的时间戳,指针指向的可以是一块数据区域或者甚至是一个函数。  消息的内容必须一直保持可见性,可见性是指代表消息的变量必须在接收消息的任务代码范围内有效。这是因为发布的数据采用的是指针传递,也就是引用传递,并不是值传递。也就是说,发布的消息本身并不产生拷贝,我们可以使用动态内存分配的方式来给消息分配一个内存块,或者,也可以传递一个指向全局变量、全局数据结构、全局数组或者函数的指针。


2、UCOSIII消息队列

2.1消息队列的操作:

中断服务程序只能使用OSQPost()函数,在UCOSIII中对于消息队列的读取是先进先出FIFO,也可以后进先出LIFO的方式,采用后进先出的方式发布的消息会绕过其他所有位于消息队列中的消息而最先传递给任务。


       小沙漏表示任务指定一个超时时间,如果任务在这段时间内没接收到消息就会唤醒任务,并返回错误码告诉UCOIII任务是被超时而唤醒的不是因为接收到了消息。超时时间设置为0那任务就会一直等待下去,知道接收到消息。


消息队列中有一个列表,就是消息队列记录了所有正在等待获得消息的任务,当一则消息发布到队列中时,最高优先级任务获得该消息,发布方也可以向消息队列中所有等待的任务广播一则消息。


2.2 消息队列是UCOSIII中的一个内核对象,为结构体OS_Q。

struct  os_q {

OS_OBJ_TYPE                Type;

CPU_CHAR                *NamePtr;

OS_PEND_LIST             PendList;                         

#if OS_CFG_DBG_EN > 0u

    OS_Q                *DbgPrevPtr;

    OS_Q                *DbgNextPtr;

    CPU_CHAR            *DbgNamePtr;

#endif

OS_MSG_Q               MsgQ     //消息列表

};

OS_MSG_Q也是一个结构体,如下:


struct  os_msg_q {                                          

OS_MSG              *InPtr;  

OS_MSG              *OutPtr;

OS_MSG_QTY           NbrEntriesSize;

OS_MSG_QTY           NbrEntries;

OS_MSG_QTY           NbrEntriesMax;

};

消息发布以后会被存放在OS_MSG类型的数据结构中,OS_MSG如下:


struct  os_msg {

OS_MSG              *NextPtr;                           

void                *MsgPtr;

OS_MSG_SIZE          MsgSize;

CPU_TS               MsgTS;

};

2.3 消息队列API函数


2.3.1 创建消息队列

void  OSQCreate (OS_Q        *p_q,           //指向一个消息队列,采用OS_Q Msg_Que定//义一个消息队列

                 CPU_CHAR    *p_name,  //消息队列的名字

                 OS_MSG_QTY   max_qty, //消息队列的长度,必须大于0

                 OS_ERR      *p_err)        //保存错误码

2.3.2 等待消息队列

void  *OSQPend (OS_Q         *p_q,//指向一个消息队列

                OS_TICK       timeout,//等待消息的超时时间

                OS_OPT        opt,//选择是否使用阻塞模式,有2个选项

                OS_MSG_SIZE  *p_msg_size,//指向一个变量用来表示接收到消息长度

                CPU_TS       *p_ts,//指向一个时间戳,表明什么时候接收到消息

                OS_ERR       *p_err)

2.3.3 向消息队列发送消息

void  OSQPost (OS_Q         *p_q,//指向一个消息队列

               void         *p_void,//指向实际发送的内容

               OS_MSG_SIZE   msg_size,//设定消息的大小,字节数

               OS_OPT        opt,//选择消息发送操作的类型,基本有四种也可结合

               OS_ERR       *p_err)

3、UCOSIII任务内建消息队列

同任务内嵌信号量一样,UCOSIII的每个任务中也有内建消息队列。而且多个任务等待同一个消息队列的应用很少见,UCOSIII中每个任务多有其内建消息队列的话用户可以不用通过外部的消息队列而直接向任务发布消息。


   如果需要使用任务内建消息队列功能的时候需要将宏OS_CFG_TASK_Q_EN置1来使能相关的代码。


任务内建消息队列的函数在os_task.c中

3.1等待任务内建消息

void  *OSTaskQPend (OS_TICK       timeout,//等待消息的超时时间

                    OS_OPT        opt,//是否使用阻塞模式

                    OS_MSG_SIZE  *p_msg_size,//存放消息大小的变量

                    CPU_TS       *p_ts,//时间戳

                    OS_ERR       *p_err)

3.2 发送任务内建消息

void  OSTaskQPost (OS_TCB       *p_tcb,//指向接收消息任务的TCB

                   void         *p_void,//发送给一个任务的消息

                   OS_MSG_SIZE   msg_size,//消息的大小

                   OS_OPT        opt,//发送操作类型:LIFO和FIFO

                   OS_ERR       *p_err)

 


推荐阅读

史海拾趣

Collins Electronics Corp公司的发展小趣事

Collins Electronics Corp的创始人在电子领域拥有深厚的背景和丰富的经验。在公司创立初期,他们发现市场上的电子设备在性能和稳定性上存在巨大的提升空间。于是,他们决定创立一家公司,专注于研发和生产高品质的电子设备。经过多次试验和改进,Collins Electronics Corp推出了他们的首款产品,一款高性能的信号放大器。这款产品凭借其卓越的性能和稳定性,在市场上获得了极大的成功,也为公司的后续发展奠定了坚实的基础。

General Industrial Controls ( GIC )公司的发展小趣事
内部集成频率补偿和固定频率发生器,开关频率为150kHz,相比低频开关调节器,可以使用更小规格的滤波元件。
Diconex公司的发展小趣事

在电子行业中,Diconex公司始终坚持以客户需求为导向的市场定位策略。公司深入调研市场需求,针对不同客户群体推出定制化解决方案。这种精准的市场定位使得Diconex的产品能够更好地满足客户需求,赢得了客户的信任和忠诚。同时,公司还积极拓展国际市场,与全球知名企业建立了长期稳定的合作关系。

CTC [Compact Technology Corp.]公司的发展小趣事

CTC公司在创立初期便致力于半导体技术的研发。一次偶然的实验中,公司团队成功研发出了一种新型的晶体管结构,这一创新使得晶体管的工作效率大大提升,同时降低了能耗。这一技术突破迅速引起了行业的关注,CTC公司的名字开始在电子行业中崭露头角。随着该技术的普及和应用,CTC公司的业务逐渐扩大,奠定了在电子行业的重要地位。

Aimtec公司的发展小趣事

Aimtec公司自成立以来,一直致力于电子转换技术的研发与创新。在某个关键时期,公司研发团队成功开发出一种新型的DC-DC转换器,其转换效率较市场同类产品提高了近20%。这一技术突破迅速得到了业界的关注,不仅帮助Aimtec在市场上取得了竞争优势,也为客户的产品带来了更高的性能。随着该技术的普及应用,Aimtec的品牌知名度逐渐提升,公司在电子行业中崭露头角。

智浦欣(Chipstar)公司的发展小趣事

在2010年4月的上海张江高科技园区,一群志同道合的工程师和创业者聚集在一起,共同创立了上海智浦欣微电子有限公司。他们怀揣着对模拟及数模混合IC技术的深厚理解和热爱,立志要在消费类电子市场占据一席之地。起初,公司面临着资金紧张、技术挑战和市场压力等多重困难,但团队成员凭借对技术的执着和对市场的敏锐洞察,逐步攻克难题,研发出了几款性能优越的音频放大器和电源管理产品,为公司赢得了初步的市场认可。

问答坊 | AI 解惑

加快电源启动的分流稳压器

在特定应用中,设计要求可能  需要系统的开关模式电源比普通电源能更迅速地提供输出。图 1 显示了这种电源的自举(或称启动)电路。在开关模式电源的 PFC(功率因数校正)预稳压器中,电路的 PWM(脉宽调制器),即 IC1,从辅助绕组 L1 ...…

查看全部问答>

ARM9 2440读取SHT11失败,全是0XFF,原因会有哪些呢?

ARM9 2440读取SHT11失败,全是0XFF;2440发送命令后,在第九个时钟没有检测到ACK信号。 硬件上应该是没有问题的,同一个传感器在其他处理器平台上正常运行。 软件上哪些地方容易出问题? 现在打算从头开始检查,我怎么样来测SHT11已经对处理器的 ...…

查看全部问答>

下面的汇编语言程序怎么分析

STACK  SEGMENT STACK        DB 1024 DUP(0) STACK  ENDS DATA   SEGMENT TABF   DW   262,350,352,350,441,393,350,393,441        DW  & ...…

查看全部问答>

在WINCE5中打开串口错误?

我写了一个串口程序,在模拟器PPC2003上调试是可以的,能正常的打开串口并收发数据,但部署到真机(WINCE5)串口都打不开,代码如下:                 try          &n ...…

查看全部问答>

//---------TCPMP如何指定从哪帧开始播放,播放到哪帧停止--------

TCPMP如何指定从哪帧开始播放,播放到哪帧停止. 在我的项目中,使用的视频文件是AVI格式的,打算用TCPMP实现,要准确的定位播放起始帧与结束帧,并播放从起始帧到结束帧之间的视频段。 跪求高人指点。…

查看全部问答>

用pl2303做了一个USB转串口,电脑检测不到。

用pl2303做了一个USB转串口,可是电脑怎么都检测不到。只有当我将万用表接到17脚和地时,电脑才能检测到。查了好几天了,请各位老师帮我看看。D:\\网址\\44.jpg…

查看全部问答>

做逻辑的难点在于系统结构设计和仿真验证

刚去公司的时候BOSS就和我讲,做逻辑的难点不在于RTL级代码的设计,而在于系统结构设计和仿真验证方面。目前国内对可综合的设计强调的比较多,而对系统结构设计和仿真验证方面似乎还没有什么资料,这或许也从一个侧面反映了国内目前的设计水平还比 ...…

查看全部问答>

新手提问,多多帮忙啊!!

我刚接触到TI公司的2000系列DSP,我装好CCS2000后,启动SetUpCCS2000后,在configurition里我选择的是F2812Device Sumilator,保存后启动CCS,可在打开和新建工程的时候都有问题,具体的时在新建工程的对话框里Target一栏里没有可选项,所以就不能建 ...…

查看全部问答>

zstack的时钟

使用cc2530,timer2是mac timer。某些资料上面说周期是320us。但是不明白函数osalTimeUpdate()里边的操作 tmp = (ticks320us * 8) + remUsTicks; 以及osalTimeUpdate()调用的函数 CONVERT_320US_TO_MS_ELAPSED_REMINDER( tmp, elapsedMSec, r ...…

查看全部问答>