pjsip消息在模块与实例间的流动

一个模块会有多个实例,模块更像一个部门,而实例就是部门里的人。比如user_agent模块中有多个dlg实例。目前涉及的模块优先级有高到低依次是transaction, user_agent(dlg),mod_inv(inv), application。 

首先,每隔模块都有一个回调函数on_rx_request(), 该函数返回bool型的值,表示该模块是否处理了该数据。当收到消息时,endpoint会依次按模块优先级把消息传给注册到该endpoint上模块,直到有个模块返回ture为止。 比如user_agent模块的on_rx_request()返回true后,该消息就不会由endpoint传给mod_inv模块和application模块了;当然有可能会由user_agent模块中的dlg实例传给mod_inv模块中的某个inv实例(dlg和inv一一对应)。 以上可阅读《pjsip_dev_guide》。 

下面以第一次收到request(数据为rdata)为例(也就是说消息会传到application模块), 说明各个模块和实例间消息的流动。 首先,endpoint收到消息后先传给模块transaction,注意是模块。 transaction模块有个哈希表,保存了所有的transaction实例。transction模块首先根据rdata计算出一个key,如果transtation模块有rdata对应的transaction实例,可以通过这个key得到。 如果该消息时符合rfc3261的,那么key是由branch参数计算的来的,而branch参数是可以唯一标示某个transaction实例的。如果消息时符合rfc2543的,这个key则由唯一标识transaction实例的数据得来。总之,这个key和transaction实例是一一对应的, 不管transaction模块中有没有对应的transaction实例。如果找到对应的transaction实例(还要求该transaction没处于terminated的状态,以后只说明主要流程,这类细节不在详述),transaction模块的on_rx_request()将返回true,endpoint将停止对消息的传送, 接下来由对应的transaction实例传送消息。transaction实例怎么传送消息,后面再做论述。 

按前面的假设,transaction模块没找到对应的transaction实例,transaction模块的on_rx_request()将返回false,消息将再传给user_agent模块。user_agent模块和transaction模块有些类似,也有自己的hash表来保存现有的dlg实例。同样的,user_agent也会根据rdata中的 数据(比如from tag, to tag)计算出key来查找有无对应的dlg。dlg实例传送消息和transaction实例类似,也在后面论述。同样的,user_agent模块的on_rx_request()也返回false,消息传到mod_inv模块。mod_inv模块位于pjsip中的pjsip_ua项目,它只接受来自dlg实例的请求,即它会根据rdata中endpt_info中的mod_data[mod_ua.id]中对应dlg的指针是否为NULL,判断是否返回false。如果为NULL,则返回false。至于为什么根据mod_data[mod_ua.id]来判断,后面再介绍。如果该指针不为NULL,mod_inv模块并不立刻返回true,而再根据rdata中的method等条件判断,具体的这里不再详述。

在本例中,那个指针为NULL,mod_inv模块的on_rx_request()将返回false。 最后,endpoint将消息传到application模块。application模块是开发者自己写的,其on_rx_request()的返回值自己判断,如果还是返回false,endpoint的行为我还没看,以后再介绍。估计是丢弃消息,或是返回5xx消息。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值