赞
踩
最近开发一个项目,发现wincap会有丢包现象,与wincap的具体应用是这样的,一个接收线程,采用pcap_loop接收网络中的数据包,一个发送线程,采用pcap_sendqueue_transmit的方式发送数据包,pcap_loop接收包速率大约为34k/s(包数大约150包每秒), pcap_sendqueue_transmit发送包的速率大约为每秒100包,在网上查了下wincap性能分析的文章,大多说收包率200M/s才有可能会引起丢包,而我的收包频率才34k,与200M相差甚远,怎么还会丢包呢?
下面是我对为什么丢包的分析步骤:
1.首先想到的是不是我的代码出了问题,我把几个影响系统性能的地方执行时间都打印了出来,发现执行时间都很合理,没有什么异常。
2.会不会是wincap的缓冲区的问题,wincap有两种缓冲区,用户缓冲区默认为256k,内核缓冲区为1M,按理来说,在我的这个应用环境,采用默认缓冲区是不会有任何问题的,但是还是抱着怀疑一切的想法,我还是重新设置了wincap的缓冲区,将用户缓冲区和内核缓冲区都设为10M,如果这个缓冲配置还会丢包的话,那就没天理了,但运行结果依然还是丢包,悲情了。
3.最后一道槛是我最不想怀疑的地方,那就是与我通信的设备了,首先还是来说说我的程序是怎么与设备通信的接口吧,pc通过网口连接到交换机,交换机之间通过级联的方式相连,总共4台二层交换机(都是100M的交换速率),每个交换机24个端口,这四台交换机上共连有77台设备,我的程序负责接收这77台设备的数据(通过上面讲的pcap_loop),以及对设备进行控制(pcap_sendqueue_transmit),难道是交换机处理不过来,导致数据在交换机上就丢失了,为了验证是否是该情况,我只与一台交换机通信,该台交换机上只连有14台设备,测式结果还是会有丢包。 一切都怀疑了,但问题依旧没有发现,呜呜。
最后又理了理自己的思路,难道是1中我测是性能出了问题,哦,在测试是的时候忘了测pcap_sendqueue_transmit 的时间,因为我把这个设为异步发送的方式,本以为这样做应该这个部分会立即返回,不会占太多的cpu时间,但事与愿违,经测发现该函数还是很占cpu时间的,队列数长1的时候,我测了12个小时,发现最长的包发送时间为104ms,由于我的队列长度一般是8,但一旦出现发送包超过100ms时,因为数据挤压没有来得及发送,可能会使发送队列的长度会有一个迅速增加,最大可以达到38,这时pcap_sendqueue_transmit的发送时间可能会很长,超过5S,因为这从而导致pcap_loop不能及时收到数据,从而导致数据丢失。
为了解决上面的问题,我将pcap_sendqueue_transmit改为pcap_send的发送方式,虽然内核切换牺牲了一些性能,但丢包问题得到解决,采用pcap_send发送,测试发现发送包也会有超过100ms,但由于是单包发送,100ms还不至于引起丢包。
问题总算找到了,我不得其解的是,为什么发送会影响接收?这是wincap驱动的原因吗?
在写此篇博文之前,我在看wincap驱动,希望能找出为什么wincap发送会如此占cpu时间,为什么发送会影响接收,难道wincap不支持全双工模式吗?有对这方面了解的朋友,希望能给我一些指点,我将感激不尽。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。