Mosquitto-1.5.4源码分析,PUBLISH的实现及函数跳转关系

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/libaineu2004/article/details/84944106

客户端向服务器发送数据包(packet)时,首先将数据包放到改发送队列中,并不真实发送数据,而是发送数据就绪信号,等待loop事件循环调用的函数db__message_write根据网络连接情况来处理发送请求;该队列为单链表存储结构,每次有新数据包需要发送时,将新数据包插入到链表尾部;真正发送数据时从链表头部开始发送数据包。

阶段1、准备好需要发送的数据包,参见截图1的上半部分的单步断点处,非常关键,inflight_msgs就是在此处赋值的。

截图1的下半部分,每一个函数的跳转关系一目了然。

截图1

阶段2、在loop.c的事件循环里面,一直在调用函数db__message_write,通过它实现真正的发送,

/* Local bridges never time out in this fashion. */
				if(!(context->keepalive)
						|| context->bridge
						|| now - context->last_msg_in <= (time_t)(context->keepalive)*3/2){

                    if(db__message_write(db, context) == MOSQ_ERR_SUCCESS){ //firecat,real_send_publish

该函数体在database.c定义,它反复在判断inflight_msgs是否为空。不为空表示有待发送的数据包。

截图2

个人建议:

在单步调试,查看业务主题消息流程时,建议把系统主题的消息屏蔽掉。方法如下:

1、/src/mosquitto.c,第294行,代码注释掉

#ifdef WITH_SYS_TREE
    //sys_tree__init(&int_db);//firecat,SYS,"$SYS/broker/#"
#endif

2、/src/loop.c,第204行,代码注释掉

 if(db->config->sys_interval > 0){
       //sys_tree__update(db, db->config->sys_interval, start_time);//firecat,SYS,"$SYS/broker/#"
}

或者干脆一点,在CMakeLists直接把宏WITH_SYS_TREE设置成未定义。

猜你喜欢

转载自blog.csdn.net/libaineu2004/article/details/84944106