Wie kann man den Stack-Trace (vom Kernel oder Core-Dump) sinnvoll nutzen?
Lesezeit: 4 Minuten
Shahbaz
Wenn Sie Glück haben, wenn Ihr Kernel-Modul abstürzt, erhalten Sie ein oops mit einem Protokoll mit vielen Informationen, wie Werten in den Registern usw. Eine solche Information ist der Stack-Trace (dasselbe gilt für Core-Dumps, aber ich hatte dies ursprünglich für Kernel-Module gefragt). Nehmen Sie dieses Beispiel:
Meine Vermutung ist, dass die +<number1>/<number2> hat etwas mit dem Offset von der Funktion zu tun, in der der Fehler aufgetreten ist. Das heißt, durch Überprüfen dieser Nummer, vielleicht durch Betrachten der Assembly-Ausgabe, sollte ich in der Lage sein, die Zeile (besser noch Anweisung) herauszufinden, in der dieser Fehler aufgetreten ist. Ist das korrekt?
Meine Frage ist, was sind diese beiden Zahlen genau? Wie nutzen Sie sie?
Pavan Manjunath
skink_free_devices+0x32/0xb0
Dies bedeutet, dass die beleidigende Anweisung ist 0x32 Bytes ab Beginn der Funktion skink_free_devices() welches ist 0xB0 Bytes lang insgesamt.
Wenn Sie Ihren Kernel mit kompilieren -g aktiviert, dann können Sie die Zeilennummer innerhalb von Funktionen abrufen, bei denen die Steuerung mit dem Tool gesprungen ist addr2line oder unsere gute alte gdb
Etwas wie das
$ addr2line -e ./vmlinux 0xc01cf0d1
/mnt/linux-2.5.26/include/asm/bitops.h:244
or
$ gdb ./vmlinux
...
(gdb) l *0xc01cf0d1
0xc01cf0d1 is in read_chan (include/asm/bitops.h:244).
(...)
244 return ((1UL << (nr & 31)) & (((const volatile unsigned int *) addr)[nr >> 5])) != 0;
(...)
Geben Sie also einfach die Adresse an, an der Sie die Inspektion durchführen möchten addr2line oder gdb und sie sollen Ihnen die Zeilennummer in der Quelldatei mitteilen, in der die anstößige Funktion vorhanden ist. Siehe Dies Artikel für alle Details
BEARBEITEN:vmlinux ist die unkomprimierte Version des Kernels, die zum Debuggen verwendet wird und im Allgemeinen @ gefunden wird /lib/modules/$(uname -r)/build/vmlinux vorausgesetzt, Sie haben Ihren Kernel aus Quellen gebaut. vmlinuz die Sie finden bei /boot ist der komprimierte Kernel und ist beim Debuggen möglicherweise nicht so nützlich
Ich wusste NICHT, dass Sie Linux selbst gdb können! Das ist fantastisch!
– Shahbaz
16. April 2012 um 12:13 Uhr
Wo ist vmlinux obwohl? Ich dachte, das wäre der Linux-Kernel selbst (in /boot), aber das ist es vmlinuz ... und addr2line sagt “Dateiformat nicht erkannt” Aber keine große Sache, da ich mich mehr für meine eigenen Module interessiere.
– Shahbaz
16. April 2012 um 12:15 Uhr
@Shahbaz vmlinuz ist nur die komprimierte und/oder gestrippte Version von vmlinux. BEIDE werden in der Regel im herumliegen /boot Mappe. Ich habe meine Linux-Box nicht dabei, um sie jetzt zu überprüfen. Googeln Sie nach den beiden 🙂 Hier sind einige Vorspeisen. Einer und Zwei
– Pavan Manjunath
16. April 2012 um 12:23 Uhr
@Shahbaz Schau hier nach vmlinux Datei /lib/modules/$(uname -r)/build/vmlinux vorausgesetzt, Sie haben Ihren Kernel aus Quellen auf derselben Maschine erstellt. Ansonsten siehe Dies posten, wie man den unkomprimierten Kernel auf Ubuntu erhält
– Pavan Manjunath
17. April 2012 um 8:57 Uhr
Groß! Ich habe meine Antwort bearbeitet, um diese Informationen auch hinzuzufügen, damit sie anderen in Zukunft helfen
– Pavan Manjunath
17. April 2012 um 9:16 Uhr
Für Emacs-Benutzer: hier‘s ist ein wichtiger Modus, um innerhalb des Stack-Trace einfach herumzuspringen (benutzt addr2line im Inneren).