开发bug之udp报文冲垮交换机网络


新年刚开始就遇到这怪事,本来集群测试的好好的,两个星期都啥事的,早上来一误操作,导致某服务msgrcv的消息队列id被删除了,而机器上有多个这样的进程同时在阻塞等待消息队列上的数据。。。。


代码逻辑如下

while (1) {

  ret = msgrcv(id, msg, 0, 0);

  if (ret < 0) {

       dog_write(warn, "msgrcv error %d", ret);

       continue;

    }

  ...

}

这下懵逼了,十个进程疯狂的打日志,而且还把机器的cpu吃满了,xshell根本连接不上,运维的人说服务在不断的像外部网络发很大的包,导致外部网络的网关卡死了。。

简直是一团乱麻,只能屁颠屁颠的跑到物理机房,从管理端登录虚拟机,看看发现的现象就是这十个进程把cpu吃满了,而且环境上当时也不知道怎么tcpdump抓包,事后才知道

/usr/sbin下面有tcpdump,iptop什么的需要另外安装。。

定位到程序代码其实就已经离本质原因不远了,但是刚开始遇到这么奇葩的问题,只是胡乱的猜测,其实机器上还有另外一个非正常的现象就是,两个不同的服务在这台机器上启动了,一个为服务端一个为客户端,自己连接了自己,所以就什么也没去测试验证,就推测认为网关被搞挂的原因是机器上有自己连接自己的socket连接,外部机器发来的数据在网络内部循环,导致网络挤压。。。现在想来,自己确实不够务实,投机取巧的躲避其本质原因。。凡事一定要what、how、why,最后的why是如此的重要,又一次被粗心的我忽略,不过当时的环境和情景也是没有办法,时间紧,心里压力大,工具命令又没有,也不熟悉。。。

好了,揭开谜底原因吧。。

一,代码调整

while (1) {

  ret = msgrcv(id, msg, 0, 0);

  if (ret < 0) {

       dog_write(warn, "msgrcv error %d", ret);

       sleep(1);//睡眠一下,代码里面不要出现while(1)的死循环,cpu不吃满才怪

       continue;

    }

  ...

}

二,找到谁在往外网发包,为什么会发包

这个藏的也是够深的,有个dog_write看到没,原来,日志模块使用的是第三方的东西,里面会配置一个远程服务ip,错误的日志都会通过发送给这个ip,除了写本地磁盘以外,配置的时候没有关闭掉然后去测试,导致当消息队列的id被删除以后,程序就疯狂地写日志,而这些日志数据又疯狂的发向网络,日志模块采用了udp的方式,没有建立连接,只管发,而实际配置的日志服务器ip根本就没有提供服务,于是。。

你可能感兴趣的:(bug实战)