Skip to content

Commit

Permalink
elf: fixed .text not allocated at 0
Browse files Browse the repository at this point in the history
  • Loading branch information
DanielBotnik committed Oct 4, 2024
1 parent 2bec0d8 commit db7d881
Showing 1 changed file with 32 additions and 10 deletions.
42 changes: 32 additions & 10 deletions cle/backends/elf/elf.py
Original file line number Diff line number Diff line change
Expand Up @@ -1199,29 +1199,51 @@ def ___segments_overlap(seg1, seg2):
# segment.
segment_relro.flags = overlapping_segments[0].flags & ~2

def __register_section(self, section_readelf, remap_offset, section_list):
section = ELFSection(section_readelf, remap_offset)

section_list.append((section_readelf, section))
# Register sections first, process later - this is required by relocatable objects
self.sections.append(section)
self.sections_map[section.name] = section

def __calculate_section_alignment(self, section_readelf, address) -> int:
align = section_readelf.header["sh_addralign"]
if align > 0:
return (address + (align - 1)) // align * align
return address

def __register_sections(self):
new_addr = 0
remap_offset = 0
sec_list = []
alloc_at_end_sections = []

for sec_readelf in self._reader.iter_sections():
remap_offset = 0
if self.is_relocatable and sec_readelf.header["sh_flags"] & 2: # alloc flag
# Relocatable objects' section addresses are meaningless (they are meant to be relocated anyway)
# We thus have to map them manually to valid virtual addresses to emulate a linker's behaviour.
sh_addr = sec_readelf.header["sh_addr"]
align = sec_readelf.header["sh_addralign"]
if align > 0:
new_addr = (new_addr + (align - 1)) // align * align
new_addr = self.__calculate_section_alignment(sec_readelf, new_addr)

remap_offset = new_addr - sh_addr
new_addr += sec_readelf.header["sh_size"] # address for next section
if sec_readelf.name == ".reginfo" and sh_addr == 0:
alloc_at_end_sections.append(sec_readelf)
continue
elif sec_readelf.header["sh_type"] == "SHT_NOTE":
pass # This section is not allocated, so no increment
else:
new_addr += sec_readelf.header["sh_size"] # address for next section

self.__register_section(sec_readelf, remap_offset, sec_list)

for sec_readelf in alloc_at_end_sections:
new_addr = self.__calculate_section_alignment(sec_readelf, new_addr)

section = ELFSection(sec_readelf, remap_offset=remap_offset)
sec_list.append((sec_readelf, section))
remap_offset = new_addr - sh_addr
new_addr += sec_readelf.header["sh_size"] # address for next section

# Register sections first, process later - this is required by relocatable objects
self.sections.append(section)
self.sections_map[section.name] = section
self.__register_section(sec_readelf, remap_offset, sec_list)

for sec_readelf, section in sec_list:
if isinstance(sec_readelf, elffile.SymbolTableSection):
Expand Down

0 comments on commit db7d881

Please sign in to comment.