[ElfLoader] added bounds check to elf loader and casting binary data to bytearray

kernel-mode
Anton Lydike 4 years ago
parent 55be71dcc3
commit ed6912a060

@ -1,20 +1,17 @@
from ..Executable import Executable, MemorySection, MemoryFlags, LoadedExecutable, LoadedMemorySection
from ..Exceptions import RiscemuBaseException
from ..helpers import FMT_PARSE, FMT_NONE
from ..colors import FMT_GREEN, FMT_BOLD
FMT_ELF = FMT_GREEN + FMT_BOLD
from .Exceptions import *
from dataclasses import dataclass from dataclasses import dataclass
from typing import List, Dict, Union from typing import List, Dict, Union
from elftools.elf.elffile import ELFFile from elftools.elf.elffile import ELFFile
from elftools.elf.sections import Section, SymbolTableSection from elftools.elf.sections import Section, SymbolTableSection
from .Exceptions import *
from ..Exceptions import RiscemuBaseException
from ..Executable import MemoryFlags, LoadedMemorySection
from ..decoder import decode from ..decoder import decode
from ..helpers import FMT_PARSE, FMT_NONE, FMT_GREEN, FMT_BOLD
FMT_ELF = FMT_GREEN + FMT_BOLD
# This requires pyelftools package! # This requires pyelftools package!
@ -52,13 +49,11 @@ class ElfExecutable:
if sec.name not in INCLUDE_SEC: if sec.name not in INCLUDE_SEC:
continue continue
sec_ = self._lms_from_elf_sec(sec, 'kernel') self.add_sec(self._lms_from_elf_sec(sec, 'kernel'))
self.sections.append(sec_)
self.sections_by_name[sec.name] = sec_
def _lms_from_elf_sec(self, sec: Section, owner: str): def _lms_from_elf_sec(self, sec: Section, owner: str):
is_code = sec.name in ('.text',) is_code = sec.name in ('.text',)
data = sec.data() data = bytearray(sec.data())
flags = MemoryFlags(is_code, is_code) flags = MemoryFlags(is_code, is_code)
print(FMT_ELF + "[ElfLoader] Section {} at: {:X}".format(sec.name, sec.header.sh_addr) + FMT_NONE) print(FMT_ELF + "[ElfLoader] Section {} at: {:X}".format(sec.name, sec.header.sh_addr) + FMT_NONE)
return ElfLoadedMemorySection( return ElfLoadedMemorySection(
@ -75,8 +70,18 @@ class ElfExecutable:
sym.name: sym.entry.st_value for sym in symtab.iter_symbols() if sym.name sym.name: sym.entry.st_value for sym in symtab.iter_symbols() if sym.name
} }
def load_user_elf(self, name: str): def add_sec(self, new_sec: 'ElfLoadedMemorySection'):
pass for sec in self.sections:
if sec.base < sec.end <= new_sec.base or sec.end > sec.base >= new_sec.end:
continue
else:
print(FMT_ELF + "[ElfLoader] Invalid elf layout: Two sections overlap: \n\t{}\n\t{}".format(
sec, new_sec
) + FMT_NONE)
raise RuntimeError("Cannot load elf with overlapping sections!")
self.sections.append(new_sec)
self.sections_by_name[new_sec.name] = new_sec
class InvalidElfException(RiscemuBaseException): class InvalidElfException(RiscemuBaseException):
@ -117,3 +122,7 @@ class ElfLoadedMemorySection(LoadedMemorySection):
if offset % 4 != 0: if offset % 4 != 0:
raise InstructionAddressMisalignedTrap(offset + self.base) raise InstructionAddressMisalignedTrap(offset + self.base)
return ElfInstruction(*decode(self.content[offset:offset + 4])) return ElfInstruction(*decode(self.content[offset:offset + 4]))
@property
def end(self):
return self.size + self.base

Loading…
Cancel
Save