Dies ist eine alte Version des Dokuments!
QuickLinks
Der GNU Debugger erlaubt es, zu sehen, was in einem Programm während der Ausführung passiert oder was ein Programm zuletzt gemacht vor einem Absturz.
Die vier Hauptfunktionen von GDB sind:
GDB ist in vielen IDEs (wie z.B. Eclipse) integriert und wird über das GUI bedient. Alternativ kann GDB auch über die Kommandozeile gestartet werden:
gdb executable_name
Programm starten:
run arg1 arg2 arg3
Programm beenden:
kill
GDB beenden:
quit
Alle GDB Befehle können mit der GDB-Hilfefunktion aufgelistet werden:
help
STABS (symbol tables) ist das Format in welchem das Program für den Debugger beschrieben wird. Der GCC Compiler kompiliert C-Programme (.c) in Assembler-Programme (.s), welche vom Assembler in Objekt-Dateien (.o) kompiliert werden, die dann vom Linker und anderen Objekt-Dateien zu einem ausführbarem Programm verlinkt werden.
Mit der Option '-g' des GCC Compilers wird in die .s-Dateien zusätzliche Information eingefügt. Diese Information beschreibt Eigenschaften der Source-Datei, wie z.B. Zeilennummern, Typen, Scope der Variable, Funktionsnamen, usw.
Beispiel: C Source, ASM Source mit STAB
GDB kann auch Programme debuggen, die nicht lokal ausgeführt werden. Auf dem Target muss aber ein RSP-Server lauften, der mit dem GDB kommunizieren kann. Die Kommunikation läuft über das Remote Serial Protokoll.
In der Zukunft sollte der Deep-Compiler zwei Files generieren. Das Image-File, welches direkt auf den MPC5200 geladen und ausgeführt wird, und ein ELF-File, welches zusammen mit den Java-Sourcen vom GDB Debugger benutzt werden können, um den MPC5200 zu debuggen.
Im ELF-File stehen die Debug-Information (STABS), die es GDB erlauben das Java-Program zu debuggen. In einer ersten Version werden die STABS manuell in ein Assembler-Programm eingefügt und mit dem GCC-Assembler übersetzt.
Um das Beispiel noch zu vereinfachen wird eine Endlos-Schleife ans Ende der reset()-Methode eingefügt:
static void reset() { int stackOffset = US.GET4(sysTabBaseAddr + stStackOffset); int stackBase = US.GET4(sysTabBaseAddr + stackOffset + 4); int stackSize = US.GET4(sysTabBaseAddr + stackOffset + 8); US.PUTGPR(1, stackBase + stackSize - 4); // set stack pointer int kernelClinitAddr = US.GET4(sysTabBaseAddr + stKernelClinitAddr); US.PUTSPR(SRR0, kernelClinitAddr); US.PUTSPR(SRR1, SRR1init); //US.ASM("rfi"); int x = 4; x ^= 0x55; US.PUTGPR(R27, x); while (true); }
Der Assembler-Code (test.S) sieht wie folgt aus:
.org 0x400100 reset: li r2, 16388 lwz r4, 0(r2) addi r2, r4, 16384 addi r3, r2, 4 lwz r5, 0(r3) addi r2, r4, 16384 addi r3, r2, 8 lwz r4, 0(r3) add r2, r5, r4 addi r3, r2, -4 mr r1, r3 li r2, 16396 lwz r4, 0(r2) mr r0, r4 mtspr SRR0, r0 li r2, 14338 mr r0, r2 mtspr SRR1, r0 li r2, 4 xori r3, r2, 0x55 xoris r3, r3, 0x0 mr r27, r2 b 0
Kompiliert wird mit folgendem Befehl:
$ powerpc-linux-gnu-as -mppc32 -mregnames -be test.S
Das ELF-File a.out wird erstellt. Dieses File kann durch folgenden Befehl disassembliert werden:
$ powerpc-linux-gnu-objdump -d -EB -G -mpowerpc a.out
Der Assembler-Code (test.S) mit den Debug-Informationen sieht wie folgt aus:
.include "stabs.include" .stabs "void:t1=1",N_LSYM,0,0,0 .stabs "int:t2=r2;-2147483648;2147483647;",N_LSYM,0,0,0 .data .org 0x100000 .stabs "targetCommand:G2",N_GSYM,0,0,0 .global targetCommand targetCommand: .int 0 .org 0x400100 .stabs "/home/abajric/ntb/deep/ws/runtime-library/",N_SO,0,0,Ltext0 .stabs "src/ch/ntb/inf/deep/runtime/mpc555/Reset.java",N_SO,0,0,Ltext0 .text Ltext0: reset: .stabn N_SLINE, 0, 38, LM1 LM1: li r2, 16388 lwz r4, 0(r2) addi r2, r4, 16384 addi r3, r2, 4 lwz r5, 0(r3) addi r2, r4, 16384 addi r3, r2, 8 lwz r4, 0(r3) add r2, r5, r4 addi r3, r2, -4 .stabn N_SLINE, 0, 41, LM5 LM6: mr r1, r3 li r2, 16396 lwz r4, 0(r2) mr r0, r4 mtspr SRR0, r0 li r2, 14338 mr r0, r2 mtspr SRR1, r0 .stabn N_SLINE, 0, 47, LM4 LM4: li r2, 4 .stabs "x:r2;-2147483648;2147483647;",N_RSYM,0,4,2 .stabn N_SLINE, 0, 48, LM5 LM5: xori r3, r2, 0x55 .stabs "x:r2;-2147483648;2147483647;",N_RSYM,0,4,3 xoris r3, r3, 0x0 .stabn N_SLINE, 0, 50, LM2 LM2: mr r27, r2 .stabs "x:r2;-2147483648;2147483647;",N_RSYM,0,4,27 .stabn N_SLINE, 0, 51, LM3 LM3: b 0 .stabs "ch::ntb::inf::deep::runtime::mpc555::Reset::reset:F1",N_FUN,0,0,reset .stabn N_SLINE, 0, 37, reset .stabn N_LBRAC, 0, 0, LM1 .stabn N_RBRAC, 0, 0, LM3
Im File stabs.include stehen Definitionen der STABS Symboltypen:
# non-stab symbol types .set N_UNDF, 0x0 .set N_EXT, 0x1 .set N_ABS, 0x2 .set N_TEXT, 0x4 .set N_DATA, 0x6 .set N_BSS, 0x8 .set N_FN_SEQ, 0x0c .set N_INDR, 0x0a .set N_COMM, 0x12 .set N_SETA, 0x14 .set N_SETT, 0x16 .set N_SETD, 0x18 .set N_SETB, 0x1a .set N_SETV, 0x1c .set N_WARNING, 0x1e .set N_FN, 0x1f # stab symbol types .set N_GSYM, 0x20 .set N_FNAME, 0x22 .set N_FUN, 0x24 .set N_STSYM, 0x26 .set N_LCSYM, 0x28 .set N_MAIN, 0x2a .set N_ROSYM, 0x2c .set N_PC, 0x30 .set N_NSYMS, 0x32 .set N_NOMAP, 0x34 .set N_MAC_DEFINE, 0x36 .set N_OBJ, 0x38 .set N_MAC_UNDEF, 0x3a .set N_OPT, 0x3c .set N_RSYM, 0x40 .set N_M2C, 0x42 .set N_SLINE, 0x44 .set N_DSLINE, 0x46 .set N_BSLINE, 0x48 .set N_BROWS, 0x48 .set N_DEFD, 0x4a .set N_FLINE, 0x4c .set N_EHDECL, 0x50 .set N_MOD2, 0x50 .set N_CATCH, 0x54 .set N_SSYM, 0x60 .set N_ENDM, 0x62 .set N_SO, 0x64 .set N_LSYM, 0x80 .set N_BINCL, 0x82 .set N_SOL, 0x84 .set N_PSYM, 0xa0 .set N_EINCL, 0xa2 .set N_ENTRY, 0xa4 .set N_LBRAC, 0xc0 .set N_EXCL, 0xc2 .set N_SCOPE, 0xc4 .set N_RBRAC, 0xe0 .set N_BCOMM, 0xe2 .set N_ECOMM, 0xe4 .set N_ECOML, 0xe8 .set N_WITH, 0xea .set N_NBTEXT, 0xf0 .set N_NBDATA, 0xf2 .set N_NBBSS, 0xf4 .set N_NBSTS, 0xf6 .set N_NBLCS, 0xf8
Online Doku von GDB:
Definition von Typen (String-Field):
.stabs "void:t1=1",N_LSYM,0,0,0 .stabs "int:t2=r2;-2147483648;2147483647;",N_LSYM,0,0,0
Definition von globalen Variablen in der .data Section Global Variables:
.data .org 0x100000 .stabs "targetCommand:G2",N_GSYM,0,0,0 .global targetCommand targetCommand: .int 0
Damit ein PowerPC Target debugged werden kann muss GDB mit PowerPC Support installiert werden:
$ sudo apt-get install gdb-multiarch
Bevor GDB gestarted wird, muss das Image-File auf den MPC5200 geladen werden:
$ telnet bdi3000inf01 pcm5200io> load 0x400000 pub/abajric/test.bin bin pcm5200io> rm pc 0x400100
GDB starten:
$ gdb-multiarch
PowerPC Architektur auswählen:
(gdb) set arch powerpc:common
ELF-File mit Debug-Informationen auswählen:
(gdb) file ./a.out
GDB mit Abatron BDI3000 verbinden:
(gdb) target remote bdi3000inf01:2001
GDB TUI aktivieren und Layout umstellen:
(gdb) layout split (gdb) focus cmd
Alternativ kann ein File (gdb.cmd) mit diesen GDB-Kommandos erstellt werden:
set arch powerpc:common file ./a.out target remote bdi3000inf01:2001 layout split focus cmd
Beim Ausführen von GDB muss dieses File angegeben werden, damit alle Kommandos im File ausgeführt werden:
$ gdb-multiarch -x ./gdb.cmd
Mit dem folgenden Befehl kann der Java-Sourcecode angezeigt werden:
(gdb) list
Mit dem folgenden Befehl wird eine Assembler-Instruktion ausgeführt:
(gdb) stepi
Mit dem folgenden Befehl wird Code ausgeführt, bis eine neue Source-Zeile erreicht wurde:
(gdb) next
Mit dem folgenden Befehl wird eine definierte Variable ausgegeben:
(gdb) print x
Mit dem folgenden Befehl wird eine definierte Variable geändert:
(gdb) set var x = 12345
Mit dem folgenden Befehl kann im Memory geschrieben werden:
(gdb) set var *0x100000 = 12345