Ich arbeite an einer Multithread-Anwendung und möchte sie mit GDB debuggen.
Das Problem ist, einer meiner Threads stirbt immer wieder mit der Nachricht:
pure virtual method called
terminate called without an active exception
Abort
Ich kenne die Ursache dieser Nachricht, habe aber keine Ahnung, wo sie in meinem Thread auftritt. Eine Rückverfolgung wäre wirklich hilfreich.
Wenn ich meine App in GDB ausführe, wird sie jedes Mal angehalten, wenn ein Thread angehalten oder fortgesetzt wird. Ich möchte, dass meine App normal weiterläuft, bis einer der Threads mit dieser Ausnahme stirbt. An diesem Punkt sollte alles angehalten werden, damit ich eine Rückverfolgung erhalten kann.
handle SIGUSR1 pass noprint nostop
Antworten:
Sie können versuchen,
catch throw
den Debugger mit einem "catchpoint" ( ) an dem Punkt zu stoppen, an dem die Ausnahme generiert wird.Der folgende Auszug aus dem GDB-Handbuch beschreibt die Catchpoint-Funktion.
5.1.3 Fangpunkte setzen
Sie können Catchpoints verwenden, um den Debugger für bestimmte Arten von Programmereignissen anzuhalten, z. B. für C ++ - Ausnahmen oder das Laden einer gemeinsam genutzten Bibliothek. Verwenden Sie den Befehl catch, um einen catchpoint festzulegen.
Ereignis fangen
werfen
Fang
exec
Gabel
vfork
Laden oder Laden von libname
libname entladen oder entladen
tcatch Ereignis
Verwenden Sie den
info break
Befehl, um die aktuellen Fangpunkte aufzulisten.Derzeit gibt es einige Einschränkungen bei der Behandlung von C ++ - Ausnahmen (Catch Throw und Catch Catch) in GDB:
Wenn Sie eine Funktion interaktiv aufrufen, gibt GDB normalerweise die Kontrolle an Sie zurück, wenn die Ausführung der Funktion abgeschlossen ist. Wenn der Aufruf jedoch eine Ausnahme auslöst, kann der Aufruf den Mechanismus umgehen, der Ihnen die Kontrolle zurückgibt, und dazu führen, dass Ihr Programm entweder abgebrochen wird oder einfach weiter ausgeführt wird, bis es einen Haltepunkt erreicht, ein Signal abfängt, auf das GDB wartet, oder beendet wird. Dies ist auch dann der Fall, wenn Sie einen Catchpoint für die Ausnahme festlegen. Fangpunkte für Ausnahmen sind in interaktiven Anrufen deaktiviert.
Sie können eine Ausnahme nicht interaktiv auslösen.
Sie können einen Ausnahmebehandler nicht interaktiv installieren.
Manchmal ist catch nicht der beste Weg, um die Ausnahmebehandlung zu debuggen: Wenn Sie genau wissen müssen, wo eine Ausnahme ausgelöst wird, sollten Sie anhalten, bevor der Ausnahmebehandler aufgerufen wird, da Sie auf diese Weise den Stapel sehen können, bevor ein Abwickeln stattfindet. Wenn Sie stattdessen einen Haltepunkt in einem Ausnahmehandler festlegen, ist es möglicherweise nicht einfach herauszufinden, wo die Ausnahme ausgelöst wurde.
Um zu stoppen, bevor ein Ausnahmebehandler aufgerufen wird, benötigen Sie einige Kenntnisse über die Implementierung. Im Fall von GNU C ++ werden Ausnahmen durch Aufrufen einer Bibliotheksfunktion mit dem Namen __raise_exception ausgelöst, die über die folgende ANSI C-Schnittstelle verfügt:
Setzen Sie einen Haltepunkt auf __raise_exception, damit der Debugger alle Ausnahmen abfängt, bevor ein Stapel abgewickelt wird (siehe Abschnitt Haltepunkte, Überwachungspunkte und Ausnahmen).
Mit einem bedingten Haltepunkt (siehe Abschnitt Unterbrechungsbedingungen), der vom Wert von id abhängt, können Sie Ihr Programm stoppen, wenn eine bestimmte Ausnahme ausgelöst wird. Sie können mehrere bedingte Haltepunkte verwenden, um Ihr Programm zu stoppen, wenn eine Reihe von Ausnahmen ausgelöst wird.
quelle
catch throw std::runtime_exception
.Setzen Sie einen Haltepunkt auf __pure_virtual
quelle
FWIW hat sich anscheinend in gcc 4.1 der entsprechende Funktionsname geändert und man muss in dieser Funktion einen Haltepunkt setzen.
__cxa_pure_virtual
quelle
Nur unten hat einer mit gdb 8.3 für mich gearbeitet:
"catch throw" oder "break __cxx_throw" hat bei mir nicht funktioniert.
quelle