0

説明できない非常に奇妙な状況があります。コード内:

Env = Global.Queue2Ctrl.FIFO(100);//Wait for a msg for 100ms
if (Env == 0) continue; //Timeout
printf("i=%d %x\n",++i, (Env->Msg));
if (!Env->Msg)
  BreakP();
....

この問題の目的: 100 ミリ秒ごとに他のスレッドがプールから取得し、Env 構造体 (メッセージへのポインターを含む) を埋めます。次に、FIFO 経由で Env ポインタを送信します。このスレッドは Env を処理し、それをプールに返します。

数十万サイクルに一度、私はブレークポイントに落ちます - まあ、私が探しているバグがあるかもしれないことを理解しています。Env-Msg変数でgdbを(ステップなしで!)見ると、IT IS NOT ZERO !!!! Printf はゼロを出力し、if 句を入力しますが、gdb は「通常の」値を示します。5〜7分に1回状況を再現でき、常にgdbは適切な値を示しますか? これが競合状態である場合、両方のスレッドがタイムアウトに基づいている場合、これが 1 つのアセンブラー コマンドでどのように正確になるのでしょうか?

4

1 に答える 1

0

gdb はすべてのスレッドをすぐに停止しますか

いいえ。Linux では、1 つのスレッドがSIGTRAP(ブレークポイントの起動により) を受信すると、GDB は他のすべてのスレッドを停止する必要があります (GDB が認識しているスレッドのリストを繰り返し処理し、SIGSTOPそれぞれに送信することによって)。

Envが 2 つのスレッド間で共有されている場合、条件が評価されたときに が存在する可能性はEnv->Msg十分にありますが、GDB がプロンプトを表示するまでに非になるNULL可能性があります。ifNULL

于 2012-07-02T05:05:26.413 に答える