如何防止堆栈损坏?

时间:2012-08-07 11:08:44

标签: c++ android-ndk gdb

我正在尝试在原生app中调试segfault for android。 GDB显示以下内容:

Program received signal SIGSEGV, Segmentation fault.
[Switching to Thread 5200]
0xbfcc6744 in ?? ()
(gdb) bt
#0  0xbfcc6744 in ?? ()
#1  0x5cfb5458 in WWMath::unProject (x=2.1136094475592566, y=472.2994384765625, z=0, mvpMatrix=@0x0, 
    viewport=@0x0, result=@0x0) at jni/src/core/util/WWMath.cpp:118
#2  0x00000000 in ?? ()

是否有可能获得良好的筹码?或者找到堆栈已损坏的地方?

UPD: 提到的功能参考:

bool WWMath::unProject(double x, double y, double z, const Matrix &mvpMatrix,
         const Rect& viewport, Vec4& result)

对简单局部变量的引用作为最后一个参数传递:

Vec4 far, near;
if (!unProject(x, y, 0, tMvp, viewport, near))

3 个答案:

答案 0 :(得分:4)

我们没有太多信息要去!除了小心处理之外,没有一般规则可以避免内存损坏。

但在我看来,你感到满满的是float s,因为虚假地址0xbfcc6744 equates为合理的float-1.597符合GDB报告的其他值。

覆盖返回地址导致执行跳转到该值,因此请特别注意函数WWMath::unProject的调用者,其函数的返回地址在其返回地址之前,以查找有问题的缓冲区。 (现在我们拥有它,near。)

答案 1 :(得分:1)

使用--fstack-protector-all进行编译将导致程序在从损坏堆栈的函数返回时中止(使用信号SIGABRT),如果该损坏包括返回地址周围的堆栈区域。

Stack-protector-all不是一个很好的调试工具,但它很容易尝试,有时会遇到像这样的问题。虽然它不会指向哪一行导致问题,但它至少会将其缩小到单个函数。获得该信息后,您可以在GDB中逐步查看,以便查明相关行。

答案 2 :(得分:0)

只能通过从可疑代码的开头逐行逐步解决这个问题,并在堆栈损坏时查看。(这是用二维数组进行丑陋的指针算法。)

似乎还有另一种方法:尝试将所有内容放入堆中,并希望不正确的操作会导致段错误。