2017-05-08 13 views
6

説明はここから始まります:SDL2&GDB:プログラム受信信号?、不明な信号

WindowsでSDL2ライブラリで再生しています。私はそれを使ってプログラムをコンパイルすることができ、.exeを実行するとうまく動作します。 GDBを使用してデバッグしようとすると問題が発生します。コードがSDL_InitまたはSDL_OpenAudio関数(新しいスレッドを作成する可能性がある)に来ると、GDBは停止し、「プログラム受信シグナル?未知信号」メッセージを表示し、実行を再開します。プログラムがクラッシュします。

明らかにスレッド命名に関連するGDB(https://www.mail-archive.com/[email protected]/msg149735.html)のバグがあります.GDBバージョン7.11.1-1で修正する必要があります。

最初はGDB 5.1.0(TDM)をGDB 7.6.1で使用していましたので、私は新しいバージョンに更新することにしました。私はMinGW-w64をインストールしました(私は今は覚えていませんが、GDBのバージョン7.11だったかもしれません)。TDMは約2年前からアップデートを提供していないようです。助けてくれなかった、GDBスチールクラッシュ。

次は、GDBの新しいバージョンを検索し、7.12(wwwドット式ドットコム/サーブレット/ equation.cmd?fa = gdb)が見つかりました。うまく動作しませんでした、おそらく修正は、このバージョンにしなかった。

明らかにこのバグはGDBのx86版にのみ存在するはずなので、x64版のTDM(GCC 5.1.0とGDB 7.9.1)をインストールしました。プログラムはうまくコンパイルされましたが、GDBはまだ未知のシグナルやプログラムのクラッシュをキャッチしています。

今はSDL2を使用しているプログラムを効果的にデバッグできません。それで、質問は、私はそれを再び働かせるために何ができるのですか?


考えられる解決策:

  • 使用Visual Studioの - 私は、Eclipseが好き(とそれは私が、私はそれで好きではない事を容認し始め意味)と本当に新しい全体勉強したくありませんIDEですが、私は最後のオプションとしてそれを保持します。
  • GDBをコンパイルしてみました。うまくいきませんでした.Windowsでのコンパイルがほとんど役に立たず、GDB 7.12でもこのバグがありました。
  • Linuxに切り替える - Visual Studioに移行するよりもさらに抜本的な選択肢です。
  • SDL 1.2にフォールバックしました。 - それ以前はもっと簡単でした...
  • 他のライブラリに切り替えてください...彼らがGDBと協力してくれることを願っています。それは本当に解決策のようには聞こえません。
  • 別のコンパイラに切り替えますか?
  • スレッドの名前付けを無効にしますか?

コードサンプル:

#include <SDL2/SDL.h> 

// Normally I'd use #undef main 
int WinMain(int, char**) 
    { 
    SDL_Init(SDL_INIT_EVERYTHING); 

    return 0; 
    } 

編集:G ++ gdbtest.cpp -lSDL2main -lSDL2

SDL2バージョン:2.0.5(Windowsの、MinGWのための最新のビルド、32bit版)


通常の実行:a。exeファイル

結果:プログラムが起動し、GDBを実行して正常に

を終了します。Console log

結果:GDBは、未知の信号を受信したが、プログラムはあなたの新しい情報に基づいて

+0

これ以上続くことはありません。私たちが理解するのに役立つ最小限のコードを投稿できますか?あなたの環境についての詳細 - 投稿したライブラリ、コンパイルやリンクに使用されるコマンドライン引数など。 – Leonardo

+0

完了コードは最小限に抑えられます。 – crueltear

答えて

3

私はこれに対処する2つの方法を見つけたと思います。問題の原因は、GDBがスレッドネーミングをどのように扱うか(または少なくとも処理することになっているか)です。スレッドに名前を付けるには、特定の属性で例外を発生させる必要があります。 SDL2がSDL2-2.0.5/srcに/スレッド/窓/ SDL_systhread.cに位置SDL_SYS_SetupThread機能でこれを行います。168:

RaiseException(0x406D1388, 0, sizeof(inf)/sizeof(ULONG), (const ULONG_PTR*) &inf); 

最初のオプションは(この行をコメントしてライブラリを再コンパイルすることであるだけでなく、それをコンパイルしますそれ自体の問題です)。 2番目のオプションは、追加することです:

SDL_SetHint(SDL_HINT_WINDOWS_DISABLE_THREAD_NAMING, "1"); 

どこか早いコードで - SDL_SYS_SetupThread機能にSDL_HINT_WINDOWS _...がfalseの場合、何もせずに命名関数から返すSDL_GetHintBooleanへの呼び出しがあります。

しかし、このバグを回避していても、スレッドの名前を付ける他のライブラリから私が出入りすることはありません。

3

がクラッシュし、私は正常にあなたの問題を再現できそれの原因を絞り込むことができました(しかし根本的な原因や問題はありません)。しかし、最初に、あなたがあなたのプログラムをコンパイルとリンクしている方法についていくつかの考察:

  • #include <SDL2/SDL.h>:私は#include "SDL.h"にそれを変更し、あなたがSDLの含まれたフォルダを指すように-Iとパスを含め調整したいです。 sdl2-configコマンドがコンパイラに渡すべきフラグを出力し、-Iがそれらの1つであるため、この方法でコードを移植性が向上します。
  • // Normally I'd use #undef main:これをしないでください。必要ありません。リンクを調整してオプションをコンパイルするだけです。 SDL2の "メイントリッキー"は、期待通りに動作する必要があります。
  • g++ gdbtest.cpp -lSDL2main -lSDL2:Windows用の正しいリンクフラグは、通常、this wiki entry-lmingw32 -lSDL2main -lSDL2 -mwindowsと指摘されています。
  • return 0:お申し込みの最後にSDL_Quit()に電話することを忘れないでください。

さて、あなたは抱えている問題はSDL_Init原因gdbに渡された特定のフラグが失敗するということである(過去に、私はそれらのいくつかは、UPSをハングアップにつながっていることを覚えて、それはもはやそうではありません)。通常

SDL_INIT_TIMER | SDL_INIT_JOYSTICK | SDL_INIT_GAMECONTROLLER 

gdb a.exe実行:代わりにSDL_INIT_EVERYTHINGを渡すので、直接あなたの問題を解決するために、私は次を除外

SDL_INIT_AUDIO | SDL_INIT_VIDEO | SDL_INIT_HAPTIC | SDL_INIT_HAPTIC | SDL_INIT_EVENTS 

を可決しました。

私が以前に言ったように、なぜGDBが失敗するのかをさらに調べることはしませんでしたが、これは報告する価値のあるバグです。私はhttps://bugzilla.libsdl.org/に行き、それにバグsimillarを検索し、見つからなければ作成します。

+0

これらのフラグを残すとサンプルプログラムが修正されますが、SDL_OpenAudioまたはMIX_OpenAudioを追加するとクラッシュします。これは、スレッドが作成され、名前が付けられるたびに発生しているようです(SDL_INIT_TIMERが起動すると思います)。試したGDBのすべてのバージョンはそれをサポートしていないようです。 – crueltear

関連する問題