昨天练习了一天异步式网络通讯编程,在一个使用WSAAsyncSelect模式的程序中出现了问题,问题出现的很蹊跷,客户端可以和服务端连上,但就是触发不了服务器的自定义事件,但是如果手动用SendMessage去触发事件的话,一切正常,最初怀疑是代码问题,检查了好多遍,换了很多种方法,都没用,最后网上查了好多资料,代码改了又改,还是有问题,最后监视网络、抓包、查内存,反汇编。。。全用上了,但就是解决不了问题,无论怎么看,代码都是没问题的,最后无奈之中开了虚拟机,在虚拟机里的Red Hat和Windows Xp里分别尝试,郁闷的是在这两个OS里,程序运行一切正常,如果是这样的话,那就可以排除代码本身的问题了,肯定是开发环境的问题。首先反应的就是网络防火墙,但是防火墙却是关闭状态,最后进入高级防火墙,发现只有4个程序处于block状态,但是和我写的程序完全无关。
最后去查系统服务,用最笨的方法,把虚拟机里的XP和我用的win7的服务逐项对比,发现了win7中一个服务似乎和程序相关,服务名叫System event notification,这个服务的作用是监视事件,并通知COM+事件订阅控件,而且在官方的说明文档里明确说了这个服务和Syncronized Message相关,但问题是这个服务在我机器上居然启动不了。最后上网查了下,发现要重置winsock目录才能重新启动,而重置的方法是用NETSH命令,这个命令我过去没接触过,查阅了下,发现这个命令真是个万能网络命令,可以用这个命令执行所有的网络配置操作。而如果要重置winsock的话,则需要执行netsh winsock reset,执行之后需要重启,然后打开服务。
到此为止,问题算是解决了,自己也算得到了一些经验。在涉及操作系统组件的程序中,由于用户操作系统环境五花八门,因此程序的错误未必一定是程序本身的逻辑错误,而很有可能是操作系统本身组件的缺失或者服务设置等原因造成的,因此面对这种情况,最好在虚拟机里干净的系统测试一下软件,以减少不同环境对程序的影响,也可以避免走弯路。