Forgive me as I'm pretty new here, but I am trying to debug the x86 assembly with gdb.
ex10.asm
global main
extern printf
section .data
msg db "Testing %i...", 0x0a, 0x00
main:
push ebp
mov ebp, esp
push 123
push msg
call printf
mov eax, 0
mov esp, ebp
pop ebp
ret
compiled and linked with below:
nasm -f elf32 -F dwarf -g ex10.asm -o ex10.o
gcc -m32 -gdwarf ex10.o -o ex10
ex10.o appears to have debug symbols
$ objdump --syms ./ex10.o | grep debug
00000000 l d .debug_info 00000000 .debug_info
00000000 l d .debug_abbrev 00000000 .debug_abbrev
00000000 l d .debug_line 00000000 .debug_line
ex10 appears to have no debug symbols
$ objdump --syms ./ex10 | grep debug
----returns nothing----
gdb ./ex10 returns below
$ gdb ./ex10
GNU gdb (Ubuntu 9.2-0ubuntu1~20.04.1) 9.2
This GDB was configured as "x86_64-linux-gnu".
Reading symbols from ./ex10...
(No debugging symbols found in ./ex10)
After this, I'm not quite sure to look.Any suggestions or info i should provide?
also, nasm version
$ apt list --installed | grep nasm
nasm/focal,now 2.14.02-1 amd64 [installed]
Reproduced with NASM version 2.15.05.
Without section .text (suggested by ssbssa):
readelf -w ex10.o
Section '.debug_aranges' has no debugging data.
Section '.debug_pubnames' has no debugging data.
Section '.debug_info' has no debugging data.
Section '.debug_abbrev' has no debugging data.
Section '.debug_line' has no debugging data.
Section '.debug_frame' has no debugging data.
Section '.debug_loc' has no debugging data.
so naturally you get nothing in the final link output.
Adding section .text before main solves the problem.
Note: you are expecting output from objdump --syms ./ex10 | grep debug, but that is the wrong thing to expect:
there are no symbols named *debug* in your file
you should ~never look at ELF files with objdump. Use readelf instead.
If you insist on using objdump, do this:
objdump -g ex10 | grep debug
Contents of the .debug_aranges section (loaded from ex10):
Offset into .debug_info: 0x0
Contents of the .debug_info section (loaded from ex10):
Contents of the .debug_abbrev section (loaded from ex10):
Raw dump of debug contents of section .debug_line (loaded from ex10):
Related
I'm trying to solve a linker error on some third party code. I have the following:
/builddir/obj.o: undefined reference to foo
If I do an objdump on obj.o, foo does not show up in the disassembly, but it does show up as an undefined object:
> objdump -S /builddir/obj.o | grep foo
> objdump -t /builddir/obj.o | grep foo
0000000000000000 *UND* 0000000000000000 foo
So what would cause a symbol to me marked as undefined when there is no reference to it in the disassembly?
Note: obj.o was not stripped, and shows other symbols
I use objcopy -S -g -O binary test.elf test.bin to get a .bin file from .elf.
$ ll test.bin
-rwxr-xr-x 1 hongzhuwang md_psw 1472320 Oct 28 19:07 test.bin
$ size test.elf
text data bss dec hex filename
173062 6328 6605424 6784814 67872e test.elf
The size of test.bin is apparently larger than the sum of text and data in test.elf. Why is there such a huge difference? Which sections will objcopy copy from .elf into .bin?
I found some NOBITSsections between PROGBITS sections in the linker script. The binary file will occupy a continuous address space, so the NOBITS sections' space are filled by zero by objcopy. I think that's the root cause for the difference.
If I load a library in to gdb and do info symbol 0xB0153C I get something like function + offset
Is there a way to get this same information without gdb? Like some readelf/objdump option?
Thanks
Is there a way to get this same information without gdb?
I don't know of any tool that will print function+offset.
Use addr2line to get the enclosing function name:
(gdb) info sym 0x108a
main + 10 in section .text
addr2line -fe a.out 0x108a
main
??:?
Or use objdump -d with scripting to compute the offset (here 0x108a - 0x1080):
objdump -d a.out | egrep '>:| 108a:' | grep -B1 '108a:'
0000000000001080 <main>:
108a: 48 83 ec 38 sub $0x38,%rsp
I'm trying to put together a GNU linker script that places two types of sections:
the normal sections at fixed and predefined addresses. .text at 0x100000, .data at 0x200000, .bss at 0x300000 and so on
special sections according to their name. for example __at_0x13370000 should be placed at address 0x13370000
the first type is trivial and is explained everywhere. no problem there.
the issue that I have is with the second type. I can't figure out how to process a section's name to turn it into the address at which it is placed. the __at_ prefix used in the example above could be chosen freely.
I was previously using the ARM RVCT linker (armlink) where any section named in the schema of .ARM.__at_xxxxxx (where xxxxxx is a decimal or hexadecimal value) was placed at the corresponding address.
http://infocenter.arm.com/help/topic/com.arm.doc.dui0803e/pge1362066000571.html
I would like to switch to the GCC toolchain and the GNU linker, but in order for that to be possible, I need to somehow replicate this behaviour.
Thanks
You can extract section addresses from object files before linking and generate a small addend for linker script:
readelf -t *.o \
| grep -o '^ *\[ *[0-9]\+\] \.[a-zA-Z_0-9]\+_at_[x0-9]\+' \
| sed 's!.*\(\..*\)_at_\([x0-9]\+\).*!\1_at_\2 \2!' \
| sort -u \
| while read name addr; do
cat <<EOF
$name $addr:
{
KEEP(*($name)) ;
}
EOF
done > fixed.lds
fixed.lds can now be INCLUDEd into main linker script.
I have Linux Kernel with me and trying to generate ELF Header on it using objcopy tool,
Below is the first step
objcopy -I binary -B i386 -O elf32-i386 --rename-section .data=.text linux_kernel.bin main.o
And after this I wanted to read symbol table using readelf -s main.o ,but getting strange symbols, below is output
Symbol table '.symtab' contains 5 entries:
Num: Value Size Type Bind Vis Ndx Name
0: 00000000 0 NOTYPE LOCAL DEFAULT UND
1: 00000000 0 SECTION LOCAL DEFAULT 1
2: 00000000 0 NOTYPE GLOBAL DEFAULT 1 _binary_linux_kernel_bin_
3: 004df650 0 NOTYPE GLOBAL DEFAULT 1 _binary_linux_kernel_bin_
4: 004df650 0 NOTYPE GLOBAL DEFAULT ABS _binary_linux_kernel_bin_
Now should be able to see symbols like
_binary_linux_kernel_bin_start
_binary_linux_kernel_bin__end
_binary_linux_kernel_bin_size
Can any body let me know where I am doing wrong?? or is it expected one??
Why I wanted to see proper symbol because have to do something like below one
--entry_point=_binary_linux_kernel_bin_start
You can use the readelf -W -s main.o command, where the -W tells readelf not to truncate the output to 80-character width.
It is simply that the string is too long and readelf is truncating. Try objdump -x main.o.