1、背景
最近在一个项目的GB28181客户端程序中,当GB程序开始拉流时,就会出现死机(应用同一份代码在其他平台正常)。根据这段时间的排查记录,将这些排查手段进行记录。
2、排查手段
下面是设备进行拉流时,设备死机的日志:
[15:38:51:702][GB28181]DBG (Trunk/src/gb28181_client.c|gb28181_parse_invitebody|1261): ip<->port:172.16.10.23:44134, ichn:0, realplay_did:2
[15:38:51:702]u32MediaPort:44134
[15:38:51:702]setNeedForceIFrame ichn:0, onoff:1
[15:38:51:703]setNeedForceIFrame1 ichn:0, onoff:1
[15:38:51:720]setNeedForceIFrame ichn:0, onoff:1
[15:38:51:720]setNeedForceIFrame1 ichn:0, onoff:1
[15:38:51:720]setNeedForceIFrame ichn:0, onoff:0
[15:38:51:720]svcmgr: service 'BinderServiceMedia' died
[15:38:51:720]svcmgr: service 'venc_service' died
[15:38:51:721]svcmgr: service 'aud_service' died
[15:38:51:723]svcmgr: service 'fire_service' died
[15:38:51:733]svcmgr: service 'iva_service' died
[15:38:51:733]svcmgr: service 'vi_service' died
(1)定位死机打印附近的代码
从日志上看,死机时打印setNeedForceIFrame ichn:0, onoff:0,那么在出现死机时打印的地方先定位代码编码是否存在问题,一般可以采用注释函数调用和走读代码发现问题。
(2)找出差异
由于当前死机的平台上,GB28181的SIP库换成了libexosip2-5.2.0和libosip2-5.2.0(以前的平台上军是libeXosip2-3.6.0和libosip2-3.6.0),因此为了控制变量,想办法在当前平台上也使用libeXosip2-3.6.0和libosip2-3.6.0,这个过程遇到一些编译问题,编译问题可参考编译问题–arm_linux编译问题记录
但是当使用这个版本的库时,问题还没有得到解决,设备照样死机。
(3)修改线程栈的大小
由于上述办法都没有解决问题,因此可以先想办法获取当前死机线程的剩余线程栈大小(比如使用pthread相关函数),但是我们的这个内核这个用不了,因此可以采取一些曲线办法,比如在函数里面定义一个数组。通过这个办法看起来,线程栈的大小也比较大。
(4)使用GDB
在上述办法没有定位出问题后,我们采用了GDB调试,但是GDB有很多功能用不了,由于对GDB不熟悉,没有深究不能使用的功能。
(5)修改编译的优化选项
比如你的代码存在-O2的优化选项,那么将其去掉,看看设备是否存在死机问题。
(5)使用内存定位工具
目前在移植valgrind,这个工具是一款功能比较多的工具,后面移植成功,再将移植过程写出来。