符号名冲突BUG
还是新旧版更新时发现的,
1-之前老的start平台没有问题,
2-使用驱动提供的pag/samples例子也没有问题
换了sapp就不行,一跑就死!
看core的栈是libpag.so的一个memset(), 应该是内存越界了,
gdb运行,断到memset()函数, 输入n继续执行,大约2-3秒程序才死,按现在CPU和内存的速度,说明memset了一个超级大的内存空间,
因为看不到libpag.so的代码,也不知道memset了个什么东西,但这么大块内存,猜想应该是收包缓冲区。
但start平台一样也调用这个初始化函数,怎么就没事呢?
经过各种猜测、尝试 ......(中间过程有点走偏了,不详述了),
最后定位,是sapp和libpag.so有个全局变量名冲突了,都叫stream_info,
用readelf -a libpag.so | grep stream_info
readelf -a sapp | grep stream_info,
可证明此问题。
因为是纯C语言写的,这类冲突没有警告,仍悄无声息的运行!
现在可以解释一下为什么了:
演示代码:
libpag.c:
struct xxx stream_info = malloc(1024 * 1024 * 1024 * sizeof(struct xxx));
memset(stream_info, 0, sizeof(struct xxx) * 1024 * 1024 * 1024);
sapp:
struct yyy stream_info = malloc(sizeof(struct yyy) * 10000);
sapp里实际stream_info所占内存比libpag的stream_info小的多,
因为sapp的stream_info是强符号,链接时,就把libpag中的stream_info替换了,
导致libpag实际memset的是sapp里的内存,但长度却是个巨大的值,就导致coredump了。
发现问题后,解决的办法就有很多了:
1--fvisibility=hidden隐藏符号名
2--源代码加static修饰
3--改名
……
那么,这个问题出了,怎么保证以后不再跟别的.so冲突呢?
对此,平台增加了初始化阶段,检测所有全局符号名冲突的功能,如果有冲突,会打印黄色字体的警告!
看到这些,应该立即用上述办法解决。
但是,可是,然而,but......
现在很多时候平台打出了这些黄色字体警告,大家都习以为常了!