Debugger

Willemers Informatik-Ecke

Kontrollierter Ablauf von Programmen

Ein Debugger ist ein Programm, das den Programmierer dabei unterstützen soll, Programmfehler zu finden. Diese Fehler werden als Bug (engl. für Wanze oder Käfer) bezeichnet. Entsprechend ist der Debugger ein "Entwanzer". Ein Debugger lässt das zu untersuchende Programm unter seiner Kontrolle ablaufen. Man kann das Programm an bestimmten Punkten stoppen lassen und im Einzelschritt verfolgen. Dabei lassen sich Variableninhalte anzeigen. Damit das erzeugte Programm dem Debugger etwas zu sagen hat, muss es mit dem Flag -g compiliert worden sein.

Start in den Tod

Ist das Problem ein Programmabsturz, so wird man typischerweise das Programm im Debugger einfach starten und in die Situation des Zusammenbruchs laufen lassen. Sobald das Programm zusammenbricht, fängt der Debugger es auf und meldet, an welcher Stelle der frühe Tod zu vermelden war.

Breakpoints bis zum Übelwerden

Schwieriger ist es schon, wenn das Programm durchaus läuft, aber die Ergebnisse nicht die erwarteten sind. In solchen Fällen wird man vor dem Start des Programms an den Stellen, wo man Probleme vermutet jeweils einen Breakpoint setzen. Nach dem Start des Programmes wird dieses normal laufen, bis es einen Breakpoint erreicht. Dort wird das Programm anhalten. Man kann sich die Variablen anzeigen lassen und Schritt für Schritt weitergehen.

Prozesse kapern

Moderne Debugger sind sogar in der Lage, einen bereits laufenden Prozess unter ihre Kontrolle zu bekommen. Das ist besonders deswegen interessant, weil es ansonsten gar keine Möglichkeit gäbe, beispielsweise Dämonen zu überwachen.

Analyse des core dump

Der Debugger ist bei der Analyse eines core dump hilfreich. Ein core dump entsteht dann, wenn das Programm vom Betriebssystem die Arbeitserlaubnis entzogen bekommen hat, weil es beispielsweise versucht hat, in Speicherbereiche zu greifen, die ihm nicht gehören. Dabei enthält der core dump den Abzug des Speichers des Prozesses in jenem Moment. Ein Debugger kann mit Hilfe dieser Datei feststellen, an welcher Zeile der Absturz erfolgt ist und welche Funktionen das Programm durchlaufen wurden, um an diese Stelle zu kommen. Da der Debugger auch in der Lage ist, die Variableninhalte anzuzeigen, kann man mit dieser Information recht gut feststellen, was die Ursache war.

Grafische Oberfläche

Für die Debugger gibt es teilweise auch grafische Oberflächen. Vom Prinzip her arbeiten diese natürlich gleich, sind aber teilweise etwas leichtfüßiger zu bedienen.

dbx

Der Debugger dbx läuft auf diversen Plattformen wie Sun oder AIX. Beim Aufruf des Debuggers kann als Parameter ein ausführbares Programm angegeben werden. Als dritter Parameter kann noch ein core angegeben werden.

dbx Programm
dbx Programm core

Programm ist das zu untersuchende Programm. core heißt die Datei, die UNIX bei einem Programmzusammenbruch erzeugt. Dieser so genannte coredump enthält den Inhalt des Speichers zum Zeitpunkt des Zusammenbruchs und ermöglicht mit Hilfe des Debuggers die Analyse, wo der Absturz stattfand. Innerhalb des Debuggers können die folgenden Befehle gegeben werden:

where
zeigt den Stack der aufgerufenen Funktionen an. Das funktioniert auch, wenn man einen core dump geladen hat. Damit wissen Sie, wo das Programm zusammengebrochen ist.
stop
Mit dem Befehl stop werden Breakpoints gesetzt. Dabei gibt es zwei Formen. stop at erwartet als Parameter eine Zeile und stop in eine Funktion.
delete
Der Befehl delete entfernt einen Breakpoint.
run
run startet das geladene Programm.
cont
cont setzt den Lauf fort, wenn das Programm durch einen Breakpoint gestoppt worden war.
step
Durchläuft schrittweise das Programm und zeigt immer die aktuelle Sourcecodezeile
display variable
Beobachtet Variablen. Nach jedem step wird die Variable mit ihrem neuen Wert angezeigt
quit
Verlasse den Debugger

adb (System V)

adb ist ein älterer Debugger, der bei System V mitgeliefert wird. Der Debugger verwendet Buchstaben als Kommandos. Auch mit dem adb läßt sich ein coredump analysieren. Der Aufruf ist wie bei anderen Debuggern mit dem Programm und dem core dump als Parameter. Anschließend wird mit c die Liste der Aufrufe erzeugt und mit q kann der Debugger verlassen werden. Einen Breakpoint setzt man, indem man zunächst die Adresse, an der der Breakpoint sein soll nennt, dann ein Doppelpunkt und das Kommando b. Die Adresse kann ein Funktionsname mit einem Offset oder eine hexadezimale Position sein. Beispiel:

tausche+0x26:b

Der Befehl b allein zeigt die Liste der definierten Haltepunkte an. Mit dem Befehl r wird das geladene Programm gestartet. Das Programm läuft dann bis zum nächsten Haltepunkt. Dort kann man mit c weiterlaufen, mit s schrittweise weitergehen oder mit k stoppen.
Kommando Wirkung
b zeige die break points
r starte das Programm
c weiterlaufen (continue), bei core dump: Anzeige der Aufruffolge
s schrittweise ablaufen lassen
k stoppe das Programm

gdb GNU debug

Der GNU Debugger gdb wird normalerweise mit dem zu untersuchenden Programm als Parameter gestartet. Als weiterer Parameter kann auch hier ein core dump angegeben werden.

Laufende Prozesse kapern

gdb kann ein laufendes Programm unter seine Fittiche nehmen. Dazu wird der gdb gestartet und der Befehl at oder attach abgesetzt. Der Prozess wird gestoppt und mit dem gdb verbunden.

attach PID

Starten und Stoppen

Im Debugger gibt es diverse Befehle. Mit run kann man das geladene Programm starten, mit dem Befehl kill wieder stoppen. Mit quit kann man den Debugger verlassen.

Breakpoint setzen

Um an den kritischen Stellen den Programmablauf unterbrechen zu können, muss man einen Breakpoint setzen. Der Befehl break erwartet als Parameter die Zeilenzahl im Listing oder ein Funktionsname. Die Zeilennummer ermittelt man durch Auflisten des Programms, was gdb durch den Befehl list ausführt.

Schritt für Schritt

Hat man den Breakpoint erreicht, kann man mit den Befehlen step oder next Schritt für Schritt das Programm durchlaufen. Dabei wird step in aufgerufene Funktionen hinuntersteigen, was next nicht tut. Mit continue lässt man das Programm weiterlaufen.

Variablen durchleuchten

Will man einen Blick auf Variablen werfen, ist print dazu der einfachste Befehl. Mit dem Befehl watch kann man Variablen unter Bewachung stellen. Dieser Befehl zeigt den Inhalt, sobald er sich ändert.
Kommando Aktion
quit Debugger verlassen
run das geladene Programm starten
kill stoppen des laufenden Programms
print Variable Inhalt der Variablen anzeigen
watch Variable Variable beobachten
list zeigt einen Ausschnitt aus dem Sourcelisting
break Funktionsname setzen eines Breakpoints
break Zeilennummer setzen eines Breakpoints
clear Funktionsname löscht einen Breakpoint
clear Zeilennummer löscht einen Breakpoint
next eine Zeile weitergehen
step eine Zeile weiter und ggf. in eine Funktion hinein
continue fortsetzen des angehaltenen Prozesses

Diese Seite basiert auf Inhalten aus dem Buch Arnold Willemer: Wie werde ich UNIX-Guru
Verlagsrechte bei galileo computing


Homepage (C) Copyright 2002 Arnold Willemer