I'm trying to learn the ELF format and am implementing an ELF parser. So far, I've implemented the ELF header parser, and I'm working on parsing segments, especially the .text segment. I'm stuck here because of the following reasons:
When I build a go binary, the program header with
LOADtype with readable and executable flags (which to my understanding points to the.textsegment has a p_offset of 0). It must mean that the entire file is readable and executable (as thep_fileszis almost the same size as that of the binary.)When I compile a C or Rust program, the problem is not there and the
p_offsetfield is properly set with a non-zero value.I don't want to use the section information to parse the
.textsegment from the go binary as it works with all the sections information stripped, so I must be missing something.
In short, How do I find the .text segment in a ELF binary with p_offset value 0 in a loadable program header with readable and executable flags.
Also, here is the abridged readelf dump of the go binary that I'm working with:
Program Headers:
Type Offset VirtAddr PhysAddr
FileSiz MemSiz Flags Align
PHDR 0x0000000000000040 0x0000000000400040 0x0000000000400040
0x0000000000000150 0x0000000000000150 R 0x1000
NOTE 0x0000000000000f9c 0x0000000000400f9c 0x0000000000400f9c
0x0000000000000064 0x0000000000000064 R 0x4
LOAD 0x0000000000000000 0x0000000000400000 0x0000000000400000
0x000000000007adfa 0x000000000007adfa R E 0x1000
Thanks!
I've tried reading the System V ELF specification, the x86-64 supplement, tried looking for articles on this topic and asked help from ChatGPT and Bard.
There is not a
.textsegment -- it simply doesn't exist (.textsection does, but you are not interested in it).Instead, multiple sections are grouped together, and are "covered" by a single
LOADsegment.Yes, it means exactly that, and there is nothing wrong with that. The linker chose to put everything into one segment (you can see section to segment mapping in
readelf -Wl a.outoutput).See also this answer.