gdb: get symbols working!!!
This commit is contained in:
18
Makefile
18
Makefile
@@ -2,6 +2,7 @@
|
||||
|
||||
COMMON ?= common.h
|
||||
DOC_OUT = README.html
|
||||
ELF_EXT = .elf
|
||||
LD ?= ld
|
||||
LINKER_SCRIPT ?= linker.ld
|
||||
# Use gcc so that the preprocessor will run first.
|
||||
@@ -10,7 +11,7 @@ GAS_EXT ?= .S
|
||||
NASM_EXT ?= .asm
|
||||
OBJ_EXT ?= .o
|
||||
OUT_EXT ?= .img
|
||||
QEMU ?= qemu-system-i386
|
||||
QEMU ?= qemu-system-i386 -drive 'file=$(RUN_FILE),format=raw' -smp 2
|
||||
RUN ?= bios_hello_world
|
||||
RUN_ARGS ?= -soundhw pcspk
|
||||
RUN_SERIAL ?= bios_hello_world_serial
|
||||
@@ -25,12 +26,11 @@ RUN_FILE_SERIAL := $(RUN_SERIAL)$(OUT_EXT)
|
||||
all: $(OUTS)
|
||||
|
||||
%$(OUT_EXT): %$(OBJ_EXT) $(LINKER_SCRIPT)
|
||||
@# Failed attempt at getting debug symbols.
|
||||
@#$(LD) -melf_i386 -o '$(@:$(OUT_EXT)=.elf)' -T '$(LINKER_SCRIPT)' '$<'
|
||||
$(LD) --oformat binary -o '$@' -T '$(LINKER_SCRIPT)' '$<'
|
||||
$(LD) -melf_i386 -nostdlib -o '$(@:$(OUT_EXT)=$(ELF_EXT))' -T '$(LINKER_SCRIPT)' '$<'
|
||||
objcopy -O binary '$(@:$(OUT_EXT)=.elf)' '$@'
|
||||
|
||||
%$(OBJ_EXT): %$(GAS_EXT) $(COMMON)
|
||||
$(GAS) -c -g -o '$@' '$<'
|
||||
$(GAS) -m32 -c -ggdb3 -o '$@' '$<'
|
||||
|
||||
%$(OUT_EXT): %$(NASM_EXT)
|
||||
nasm -f bin -o '$@' '$<'
|
||||
@@ -39,14 +39,14 @@ all: $(OUTS)
|
||||
$(COMMON):
|
||||
|
||||
clean:
|
||||
rm -fr '$(DOC_OUT)' *$(OBJ_EXT) *$(OUT_EXT) *$(TMP_EXT)
|
||||
rm -fr '$(DOC_OUT)' *$(ELF_EXT) *$(OBJ_EXT) *$(OUT_EXT) *$(TMP_EXT)
|
||||
|
||||
run: $(RUN_FILE)
|
||||
$(QEMU) -drive 'file=$(RUN_FILE),format=raw' -smp 2 $(RUN_ARGS)
|
||||
$(QEMU) $(RUN_ARGS)
|
||||
|
||||
debug: $(RUN_FILE)
|
||||
$(QEMU) -hda '$(RUN_FILE)' -S -s &
|
||||
gdb -x gdb.gdb
|
||||
$(QEMU) -S -s &
|
||||
gdb -quiet -x gdb.gdb '$(<:$(OUT_EXT)=$(ELF_EXT))'
|
||||
|
||||
bochs: $(RUN_FILE)
|
||||
# Supposes size is already multiples of 512.
|
||||
|
||||
73
README.adoc
73
README.adoc
@@ -180,15 +180,21 @@ It should also be possible to run a GUI inside the container, but I haven't test
|
||||
|
||||
=== GDB step debug
|
||||
|
||||
TODO get it working nicely:
|
||||
To GDB step debug the program, run it with:
|
||||
|
||||
....
|
||||
./run bios_hello_world debug
|
||||
....
|
||||
|
||||
This will only cover specifics, you have to know GDB debugging already.
|
||||
This will leave you at the very first instruction executed by QEMU, which is the beginning of our `BEGIN` macro.
|
||||
|
||||
How to have debug symbols: https://stackoverflow.com/questions/32955887/how-to-disassemble-16-bit-x86-boot-sector-code-in-gdb-with-x-i-pc-it-gets-tr/32960272#32960272 TODO implement here. Needs to point GDB to an ELF file in addition to the remote listen.
|
||||
You can then basically debug as you would a normal userland program, notably:
|
||||
|
||||
* I then highly recommend that you use https://github.com/cyrus-and/gdb-dashboard[GDB Dashboard] to see what is going on.
|
||||
* `n` skips over macros
|
||||
* `ni` steps within macros. But you will need to enable the printing of assembly code on GDB Dashboard to see where you are at
|
||||
|
||||
Debug symbols are obtained by first linking ELF files, and then using `objcopy` on them to generate the final image. We then pass the ELF files with the debug information to GDB: https://stackoverflow.com/questions/32955887/how-to-disassemble-16-bit-x86-boot-sector-code-in-gdb-with-x-i-pc-it-gets-tr/32960272#32960272
|
||||
|
||||
How to step over `int` calls: http://stackoverflow.com/questions/24491516/how-to-step-over-interrupt-calls-when-debugging-a-bootloader-bios-with-gdb-and-q
|
||||
|
||||
@@ -2104,6 +2110,38 @@ But I have since change my mind, and if I ever touch this again seriously, I wou
|
||||
|
||||
If this is done, we this repo should then be merged into: https://github.com/cirosantilli/linux-kernel-module-cheat/tree/87e846fc1f9c57840e143513ebd69c638bd37aa8#baremetal-setup together with the ARM Newlib baremetal setups present there.
|
||||
|
||||
=== Serial UART
|
||||
|
||||
What the heck is a serial in the real world: https://unix.stackexchange.com/questions/307390/what-is-the-difference-between-ttys0-ttyusb0-and-ttyama0-in-linux/367882#367882
|
||||
|
||||
Currently all text output is done the display, and that was a newbie design choice from before I knew the serial existed. The serial is just generally more minimal and elegant than the display, and should have been used instead.
|
||||
|
||||
TODO: get working on QEMU, working on Bochs:
|
||||
|
||||
....
|
||||
./run bios_hello_world_serial bochs
|
||||
cat bios_hello_world_serial.tmp.serial
|
||||
....
|
||||
|
||||
The file content:
|
||||
|
||||
....
|
||||
hello world
|
||||
....
|
||||
|
||||
Source: link:bios_hello_world_serial.S[]
|
||||
|
||||
Bibliography:
|
||||
|
||||
* https://stackoverflow.com/questions/22571379/intel-galileo-bare-metal-uart
|
||||
* https://stackoverflow.com/questions/27594297/how-to-print-a-string-to-the-terminal-in-x86-64-assembly-nasm-without-syscall
|
||||
|
||||
This would open up:
|
||||
|
||||
* gem5 benchmarking and exploration, currently blocked on https://stackoverflow.com/questions/50364863/how-to-get-graphical-gui-output-and-user-touch-keyboard-mouse-input-in-a-ful/50364864#50364864
|
||||
* automated unit tests. Ha, like I'm gonna be that diligent!
|
||||
* easily working on ARM in a more uniform way
|
||||
|
||||
=== Macros vs functions
|
||||
|
||||
Using macros for now on link:common.h[] instead of functions because it simplifies the linker script.
|
||||
@@ -2165,35 +2203,6 @@ Knowing the following will help a lot:
|
||||
|
||||
While it is possible to learn those topics as you go along, and it is almost certain that you will end up learning more about them, we will not explain them here in detail.
|
||||
|
||||
== TODO
|
||||
|
||||
=== Serial UART
|
||||
|
||||
TODO: get working on QEMU, working on Bochs:
|
||||
|
||||
....
|
||||
./run bios_hello_world_serial bochs
|
||||
cat bios_hello_world_serial.tmp.serial
|
||||
....
|
||||
|
||||
File content:
|
||||
|
||||
....
|
||||
hello world
|
||||
....
|
||||
|
||||
Source: link:bios_hello_world_serial.S[]
|
||||
|
||||
Bibliography:
|
||||
|
||||
* https://stackoverflow.com/questions/22571379/intel-galileo-bare-metal-uart
|
||||
* https://stackoverflow.com/questions/27594297/how-to-print-a-string-to-the-terminal-in-x86-64-assembly-nasm-without-syscall
|
||||
|
||||
This would open up:
|
||||
|
||||
* gem5 benchmarking and exploration, currently blocked on https://stackoverflow.com/questions/50364863/how-to-get-graphical-gui-output-and-user-touch-keyboard-mouse-input-in-a-ful/50364864#50364864
|
||||
* automated unit tests. Ha, like I'm gonna be that dilligent!
|
||||
|
||||
== Bibliography
|
||||
|
||||
=== Intel manual
|
||||
|
||||
@@ -2,7 +2,6 @@
|
||||
|
||||
#include "common.h"
|
||||
BEGIN
|
||||
DBG
|
||||
mov $msg, %si
|
||||
mov $0x0e, %ah
|
||||
loop:
|
||||
|
||||
4
common.h
4
common.h
@@ -7,10 +7,6 @@
|
||||
|
||||
/* Helpers */
|
||||
|
||||
.macro DBG
|
||||
mov %ax, 0x9000
|
||||
.endm
|
||||
|
||||
/* Push registers ax, bx, cx and dx. Lightweight `pusha`. */
|
||||
.macro PUSH_ADX
|
||||
push %ax
|
||||
|
||||
8
gdb.gdb
8
gdb.gdb
@@ -14,13 +14,7 @@ end
|
||||
break *0x7c00
|
||||
continue
|
||||
|
||||
# Magic address. Add a:
|
||||
#
|
||||
# mov %ax, 0x9000
|
||||
#
|
||||
# to your program to break there. Shortcut macro on common.h:
|
||||
#
|
||||
# DBG
|
||||
# https://cirosantilli.com/x86-bare-metal-examples#gdb-step-debug
|
||||
awatch *0x9000
|
||||
commands
|
||||
silent
|
||||
|
||||
@@ -3,7 +3,6 @@
|
||||
#include "common.h"
|
||||
BEGIN
|
||||
CLEAR
|
||||
DBG
|
||||
/* Set address of the handler for interrupt 0. */
|
||||
movw $handler, 0x00
|
||||
/* Set code segment of the handler for interrupt 0. */
|
||||
|
||||
Reference in New Issue
Block a user