2017-05-08 3 views
6

Commençons par la description ce qui se passe:SDL2 & GDB: programme signal reçu, signal inconnu

Je joue avec la bibliothèque SDL2 sous Windows. Je peux compiler des programmes en l'utilisant, et quand je cours le .exe cela fonctionne très bien. Des problèmes surviennent lorsque j'essaie de le déboguer en utilisant GDB - quand le code arrive aux fonctions SDL_Init ou SDL_OpenAudio (qui créent éventuellement de nouveaux threads), GDB s'arrête, affiche le message "signal reçu du programme?, Signal inconnu", et quand je reprends l'exécution programme se bloque.

Apparemment, il existe un bogue dans GDB (https://www.mail-archive.com/[email protected]/msg149735.html) lié à un nom de thread, et il devrait être corrigé dans GDB version 7.11.1-1. Au début, j'utilisais GCC 5.1.0 (TDM) avec GDB 7.6.1, donc j'ai décidé de mettre à jour vers une version plus récente. Il semble que TDM ne fournisse aucune mise à jour depuis environ deux ans, j'ai donc installé MinGW-w64 (je ne m'en souviens pas maintenant, mais il pourrait s'agir de la version 7.11 de GDB). N'a pas aidé, GDB still se bloque.

Ensuite, j'ai recherché une version plus récente de GDB, et trouvé 7,12 (www équation point dot com/servlet/équation.cmd? Fa = gdb). N'a pas fonctionné, aussi, peut-être corriger n'a pas réussi à cette version.

Apparemment, ce bogue ne devrait être présent que dans la version x86 de GDB, j'ai donc installé la version x64 de TDM (GCC 5.1.0 et GDB 7.9.1). Le programme a bien été compilé, mais GDB capte toujours les signaux inconnus et les plantages du programme.

À l'heure actuelle, je ne peux effectivement déboguer aucun programme utilisant SDL2. Donc, la question est, que puis-je faire pour le faire fonctionner à nouveau?


solutions possibles:

  • Utilisez Visual Studio - J'aime Eclipse (et cela signifie que j'ai commencé à tolérer des choses que je n'aime pas) et il ne veux pas vraiment apprendre tout nouveau IDE, mais je vais garder cela comme dernière option.
  • Compiler GDB - essayé que, ne fonctionnait pas, compiler des choses sur Windows ne fonctionne presque jamais pour moi, et GDB 7.12 avait aussi ce bug.
  • Passer à Linux - Option encore plus radicale que de passer à Visual Studio.
  • Retour à SDL 1.2 - Les choses étaient plus faciles à l'époque ...
  • Basculez vers n'importe quelle autre bibliothèque - ... et espérons qu'ils coopéreront avec GDB. Cela ne ressemble pas vraiment à une solution.
  • Basculer vers un autre compilateur?
  • Désactiver la dénomination de thread?

Exemple de code:

#include <SDL2/SDL.h> 

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

    return 0; 
    } 

Compilation: g ++ gdbtest.cpp -lSDL2main -lSDL2

SDL2 version: 2.0.5 (dernière version pour Windows, MinGW, version 32 bits)


Exécution normale: a.exe

Résultats: début du programme et se termine normalement

en cours avec GDB: Console log

Résultats: GDB reçoit un signal inconnu, le plantage programme

+0

Il n'y a pas grand-chose à faire. Pouvez-vous poster un code minimal pour nous aider à comprendre? En savoir plus sur votre environnement - les bibliothèques exactes que vous avez utilisées, les arguments de la ligne de commande utilisés pour compiler et lier, etc ... – Leonardo

+0

Terminé - le code est aussi minimal que possible. – crueltear

Répondre

3

Ok, je pense que j'ai trouvé deux façons de traiter cette question. La source du problème réside dans la manière dont GDB gère (ou du moins est supposé gérer) le nommage des threads. Pour nommer un thread, il faut lever l'exception avec des attributs spécifiques. SDL2 le fait en fonction SDL_SYS_SetupThread situé dans SDL2-2.0.5/src/fil/windows/SDL_systhread.c: 168:

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

La première option est de commenter cette ligne et recompiler la bibliothèque (bien, compiler est un problème en soi). Deuxième option est d'ajouter:

SDL_SetHint(SDL_HINT_WINDOWS_DISABLE_THREAD_NAMING, "1"); 

quelque part au début du code - en fonction SDL_SYS_SetupThread il y a un appel à SDL_GetHintBoolean qui retourne de la fonction sans nommer quoi que ce soit si SDL_HINT_WINDOWS _... est faux.Pourtant, trouver un moyen de contourner ce bug ne veut pas dire qu'il ne reviendra pas me hanter d'une autre bibliothèque nommant ses threads.

3

Sur la base de vos nouvelles informations, je pourrais reproduire votre problème avec succès et a réussi à affiner la cause de celui-ci (mais pas la cause ou le problème). Mais d'abord, une certaine considération sur la façon dont vous compiler et lier votre programme:

  • #include <SDL2/SDL.h>: Je changerais que pour #include "SDL.h" et ajuster votre include_path avec -I pour pointer vers le répertoire include de SDL. De cette façon, votre code est plus portable, car la commande sdl2-config génère des indicateurs qui doivent être transmis au compilateur et -I en fait partie.
  • // Normally I'd use #undef main: Ne fais pas ça, il est pas nécessaire. Ce que vous devez faire est d'ajuster votre lien et de compiler les options. "principale tricherie" de SDL2 "doit fonctionner comme ils l'attendent. Les indicateurs de liaison corrects pour Windows sont généralement, comme indiqué par this wiki entry: -lmingw32 -lSDL2main -lSDL2 -mwindows. S'il vous plaît n'oubliez pas d'appeler SDL_Quit() à la fin de votre demande.

Maintenant, le problème que vous rencontrez est que certains drapeaux transmis à SDL_Init les causes gdb à l'échec (dans le passé, je me souviens que certains d'entre eux ont conduit à accrocher ups, il est plus le cas). Ainsi, pour résoudre votre problème directement, au lieu de passer SDL_INIT_EVERYTHING, je suis passé

SDL_INIT_AUDIO | SDL_INIT_VIDEO | SDL_INIT_HAPTIC | SDL_INIT_HAPTIC | SDL_INIT_EVENTS 

laissant les opérations suivantes:

SDL_INIT_TIMER | SDL_INIT_JOYSTICK | SDL_INIT_GAMECONTROLLER 

et gdb a.exe fonctionne normalement.

Comme je l'ai déjà dit, je ne suis pas allé plus loin pour vérifier pourquoi GDB échoue, mais c'est sûrement un bug qui mérite d'être signalé. Je voudrais aller à https://bugzilla.libsdl.org/, rechercher un bug similaire à celui-ci et créer si non trouvé.

+0

Laisser ces drapeaux corrige en effet mon programme d'exemple, mais il plante quand j'ajoute SDL_OpenAudio ou MIX_OpenAudio. Cela semble se produire chaque fois qu'un thread est créé et nommé (je suppose que SDL_INIT_TIMER en démarre un). Chaque version de GDB que j'ai essayé ne semble pas supporter cela. – crueltear