5

Android のネイティブ アプリで segfault をデバッグしようとしています。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))
4

3 に答える 3

5

必要な情報があまりありません。アドレス指定に注意する以外に、メモリの破損を避けるための一般的なルールはありません。

floatしかし、偽のアドレスは、GDB によって報告された他の値と一致する妥当な値に0xbfcc6744 等しいため、s の配列をオーバーフローさせたように見えます。float-1.597

戻りアドレスを上書きすると、実行がその値にジャンプする原因となったので、WWMath::unProjectその戻りアドレスの前にローカルがある function の呼び出し元を具体的に見て、問題のあるバッファーを見つけます。(そして今、私たちはそれを手に入れnearました。)

于 2012-08-07T11:28:46.693 に答える
2

でコンパイルする--fstack-protector-allと、スタックを破損する関数から戻ったときにプログラムが異常終了します (その破損に戻りアドレスの周りのスタック領域が含まれる場合)。

Stack-protector-all は優れたデバッグ ツールではありませんが、試すのは簡単で、このような問題をキャッチすることもあります。問題の原因となった行を特定することはできませんが、少なくとも 1 つの機能に絞り込むことができます。その情報を取得したら、問題の行を特定するために GDB でそれをステップ実行できます。

于 2012-08-07T11:51:49.227 に答える
0

疑わしいコードの先頭から 1 行ずつステップ実行し、スタックが破損する瞬間を探すだけで、この問題を解決しました (2 次元配列でのポインタ演算は醜いものでした)。

そして、別の方法があったようです。すべてをヒープに入れてみて、誤った操作でセグメンテーション違反が発生することを願っています。

于 2012-08-08T19:24:29.860 に答える