Je travaille sur une application multithread et je souhaite la déboguer à l'aide de GDB.
Le problème est que l'un de mes fils continue de mourir avec le message:
pure virtual method called
terminate called without an active exception
Abort
Je connais la cause de ce message, mais je ne sais pas où dans mon fil il se produit. Un retour en arrière serait vraiment utile.
Lorsque j'exécute mon application dans GDB, elle s'interrompt chaque fois qu'un thread est suspendu ou repris. Je veux que mon application continue de fonctionner normalement jusqu'à ce que l'un des threads meure avec cette exception, auquel point tout devrait s'arrêter pour que je puisse obtenir une trace arrière.
handle SIGUSR1 pass noprint nostop
Réponses:
Vous pouvez essayer d'utiliser un "catchpoint" (
catch throw
) pour arrêter le débogueur au point où l'exception est générée.L' extrait suivant du manuel gdb décrit la fonction de point de capture.
5.1.3 Définition des points de capture
Vous pouvez utiliser des points de capture pour provoquer l'arrêt du débogueur pour certains types d'événements de programme, tels que les exceptions C ++ ou le chargement d'une bibliothèque partagée. Utilisez la commande catch pour définir un point de capture.
événement de capture
jeter
capture
exec
fourchette
vfork
charger ou charger libname
décharger ou décharger libname
événement tcatch
Utilisez la
info break
commande pour répertorier les points de capture actuels.Il existe actuellement quelques limitations à la gestion des exceptions C ++ (catch throw et catch catch) dans GDB:
Si vous appelez une fonction de manière interactive, GDB vous renvoie normalement le contrôle lorsque la fonction a fini de s'exécuter. Si l'appel lève une exception, cependant, l'appel peut contourner le mécanisme qui vous renvoie le contrôle et provoquer l'abandon ou la poursuite de l'exécution de votre programme jusqu'à ce qu'il atteigne un point d'arrêt, capte un signal que GDB écoute ou quitte. C'est le cas même si vous définissez un point de capture pour l'exception; les points de capture sur les exceptions sont désactivés dans les appels interactifs.
Vous ne pouvez pas déclencher une exception de manière interactive.
Vous ne pouvez pas installer un gestionnaire d'exceptions de manière interactive.
Parfois, catch n'est pas le meilleur moyen de déboguer la gestion des exceptions: si vous avez besoin de savoir exactement où une exception est déclenchée, il est préférable de s'arrêter avant que le gestionnaire d'exceptions ne soit appelé, car vous pouvez ainsi voir la pile avant tout déroulement. Si vous définissez un point d'arrêt dans un gestionnaire d'exceptions à la place, il peut ne pas être facile de savoir où l'exception a été déclenchée.
Pour arrêter juste avant l'appel d'un gestionnaire d'exceptions, vous devez connaître l'implémentation. Dans le cas de GNU C ++, les exceptions sont levées en appelant une fonction de bibliothèque nommée __raise_exception qui a l'interface ANSI C suivante:
Pour que le débogueur intercepte toutes les exceptions avant tout déroulement de la pile, définissez un point d'arrêt sur __raise_exception (voir la section Points d'arrêt; points de surveillance; et exceptions).
Avec un point d'arrêt conditionnel (voir la section Conditions de rupture) qui dépend de la valeur de id, vous pouvez arrêter votre programme lorsqu'une exception spécifique est déclenchée. Vous pouvez utiliser plusieurs points d'arrêt conditionnels pour arrêter votre programme lorsqu'une des nombreuses exceptions est déclenchée.
la source
catch throw std::runtime_exception
.Définir un point d'arrêt sur __pure_virtual
la source
FWIW, apparemment, dans gcc 4.1, le nom de la fonction appropriée a changé et il faut définir un point d'arrêt dans cette fonction.
__cxa_pure_virtual
la source
Seulement en dessous d'un a fonctionné pour moi avec gdb 8.3:
"catch throw" ou "break __cxx_throw" ne fonctionnait pas pour moi.
la source