其他分享
首页 > 其他分享> > eCos Mbox机制

eCos Mbox机制

作者:互联网

背景

总结下 ecos mbox这个通信机制。
ecos下面的通信机制真的很少,没有信号、消息队列、信号量、unix域…, 当然,我看到里面不少地方用到了 网络socket,如DHCP客户端的开启和关闭。
mbox我理解上应该就是Linux下消息队列吧,但是BRCM下面的 rc 中,用到的非常简单,仅仅使用这种机制来传递一个整数,哈哈,真是蛋碎。
经过扩展后,能传递字符串了。下面,走进去看下。

mbox的实现

tapf_sys_init->sys_main->(*sys_msg_init)() 这个函数指针封装的,目前未发现有什么备用选择。
->msg_init->cyg_mbox_create关键就是这个函数了,其它封装后面说。
函数原型这样,很简单,一个ID, 一个结构体。

externC void cyg_mbox_create(cyg_handle_t        *handle,cyg_mbox            *mbox) __THROW{CYG_ASSERT_SIZES( cyg_mbox, Cyg_Mbox );
    Cyg_Mbox *t = new((void *)mbox) Cyg_Mbox();t=t;CYG_CHECK_DATA_PTR( handle, "Bad handle pointer" );*handle = (cyg_handle_t)mbox;}

这函数很坑,

  1. CYG_ASSERT_SIZES这宏检查下C中的这个结构体与 C++中的类大小是否相同。(类中的大小,就是成员变量的大小之各,这个类中使用模板创建的成员。)
  2. 实际上t就是mbox的一个别名,空间不是new出来的,而是直接使用这个结构体的地址空间。
    3)handle保存mbox的地址,完全没必要在这赋值啊。
    估计是一些设计上的兼容性,才导致了这么奇怪的写法。

第一个对象出场:Cyg_Mbox

构造函数为空,但它调用了模板类 Cyg_Mboxt2,
Cyg_Mboxt2<void *, CYGNUM_KERNEL_SYNCH_MBOX_QUEUE_SIZE> m;
这个模板中成员与C结构中的成员一致,其构建函数对 base , count成员赋 0 (mboxt2.inl) 。

获取mbox

cyg_mbox_get(rc_mbox_handle) & 0xffff) -> ((Cyg_Mbox *)mbox)->get()

为啥&0xffff, 把get出来的结果 取 低16位。
-> m.get( p ) 再调用模板方法。
get与set都是使用模板中方法实现的。
对于其中的每个条目操作,又有点环形队列 了。
这里很简单,仅仅是存储指针数组,然后返回其中的一个原素。

put时,找到一个位置,然后插入进去。
当然实现中会有些PV操作保证原子性、还有阻塞唤醒层面的操作。

再回头看现有的封装实现 。

struct msg_struct{
	cyg_handle_t mbox_msg_id;
	cyg_mbox mbox;
	PIU8 mbox_tag;
	PI8 msg_info[MAX_MBOX_MSG_NUM][MAX_MBOX_MSG_LEN];};

id / mbox同原来的调用函数。 msg_info用于存储传递的字符串,二维的个数等同于系统中 mbox的存储个数。
在操作时,要考虑获取到的消息与msg_info中的对应关系。
这种感觉,就像体制外,硬生生的附加上,当然它能work well ,但缺少层次。

思考

  1. 变长与定长 ,加入消息头(类UDP)。
    消息仅传递malloc的指针,指向存储的消息,通过头部中的字段指定长度,来提取消息,完成后释放。不知为什么,很多人(包括我)都会觉得ecos下面使用动态内容就不安全,会产生莫名其妙的问题?会么?缺少独立进程、互不影响的分离机制(有了可能就不叫ecos了,会增加复杂度),导致其它任何一处的有问题,必将坏掉一锅汤。
    但绝对不能“一朝被蛇咬,十年怕井绳”,这个机制是没有问题的。并且这样地是发挥了mbox的作用。(在机制上进行设计)

  2. 如何把存储空间放到消息对象的内部,减少 申请与释放内容的动作。
    好吧,就能存储10条消息、定长,那么就去扩展struct 及class吧,注意其它使用mbox的地方。

标签:handle,Mbox,cyg,eCos,msg,Cyg,机制,mbox
来源: https://blog.51cto.com/u_7777817/2708285