Example #1
0
def create_emulator(arch, mode, state) -> IEmuHelper:
    """
    Factory method for constructing the appropriate IEmuHelper
    """
    from unicorn import Uc, UC_ARCH_ARM, UC_ARCH_MIPS, UC_ARCH_X86
    from unicorn.unicorn import UcError

    try:
        uc = Uc(arch, mode)
        arch = uc._arch
        if arch == UC_ARCH_X86 and state.bits == 32:
            from .x86 import x86EmuHelper

            return x86EmuHelper(uc, state)
        if arch == UC_ARCH_X86 and state.bits == 64:
            from .x86 import x86_64EmuHelper

            return x86_64EmuHelper(uc, state)
        elif arch == UC_ARCH_ARM:
            from .arm import ArmEmuHelper

            return ArmEmuHelper(uc, state)
        elif arch == UC_ARCH_MIPS:
            from .mips import MipsEmuHelper

            return MipsEmuHelper(uc, state)
        else:
            raise ZelosLoadException(
                f"Unsupported architecture {arch} {state.bits}")
    except UcError:
        raise ZelosLoadException(
            f"Custom unicorn does not support the arch/mode/bits" +
            f" {arch}/{mode}/{state.bits}")
Example #2
0
 def _load_module(self, elf, module_name):
     module_path, normalized_module_name = self._get_module_name(
         module_name)
     data = bytearray(elf.Data)
     base = self.memory._alloc_at(
         "",
         "main",
         basename(normalized_module_name),
         elf.ImageBase,
         elf.VirtualSize,
     )
     self.memory.write(base, bytes(data))
     # Set proper permissions for each section of the module
     for s in elf.Sections:
         try:
             self.memory.protect(
                 s.Address,
                 align(s.VirtualSize, s.Alignment),
                 s.Permissions,
                 # s.Name,
                 # "main",
                 # module_name=basename(module_path),
             )
         except Exception:
             raise ZelosLoadException(
                 f"Bad section {hex(s.Address)}  {hex(s.VirtualSize)}")
     return base
Example #3
0
    def _initialize_zelos(self, binary=None):
        self.state = State(self, binary, self.date)

        cs_arch_mode_sm_dict = {
            "x86": (CS_ARCH_X86, CS_MODE_32),
            "x86_64": (CS_ARCH_X86, CS_MODE_64),
            "arm": (CS_ARCH_ARM, CS_MODE_ARM),
            "mips": (CS_ARCH_MIPS, CS_MODE_MIPS32),
        }

        arch = self.state.arch
        (cs_arch, cs_mode) = cs_arch_mode_sm_dict[arch]

        endianness = self.state.endianness
        if endianness == "little":
            cs_mode |= CS_MODE_LITTLE_ENDIAN
        elif endianness == "big":
            cs_mode |= CS_MODE_BIG_ENDIAN
        else:
            raise ZelosLoadException(f"Unsupported endianness {endianness}")
        self.cs = Cs(cs_arch, cs_mode)
        self.cs.detail = True

        self.logger.debug(
            f"Initialized {arch} {self.state.bits} emulator/disassembler")

        self.triggers = Triggers(self)
        self.processes.set_architecture(self.state)

        self.network = Network(self.helpers, self.files, None)

        self.processes._create_first_process(self.main_module_name)
        p = self.current_process
        p.cmdline_args = self.cmdline_args
        p.environment_variables = self.config.env_vars
        p.virtual_filename = self.config.virtual_filename
        p.virtual_path = self.config.virtual_path

        if hasattr(unicorn.unicorn, "WITH_ZEROPOINT_PATCH"):

            def process_switch_wrapper(*args, **kwargs):
                # Block count interrupt. Fires every 2^N blocks executed
                # Use this as an opportunity to swap threads.
                self.logger.info(">>> Tracing Thread Swap Opportunity")
                self.processes.schedule_next()

            self.interrupt_handler.register_interrupt_handler(
                0xF8F8F8F8, process_switch_wrapper)

        if self.config.filename is not None and self.config.filename != "":
            if (self.config.virtual_filename is not None
                    and self.config.virtual_filename != ""):
                self.files.add_file(self.config.filename,
                                    self.config.virtual_filename)
            else:
                self.files.add_file(self.config.filename)

        # TODO: SharedSection needs to be removed
        self.processes.handles.new("section", "\\Windows\\SharedSection")
Example #4
0
    def _create_emulator(self) -> IEmuHelper:
        arch = self.state.arch

        uc_arch_mode_dict = {
            "x86": (uc.UC_ARCH_X86, uc.UC_MODE_32),
            "x86_64": (uc.UC_ARCH_X86, uc.UC_MODE_64),
            "arm": (uc.UC_ARCH_ARM, uc.UC_MODE_ARM),
            "mips": (uc.UC_ARCH_MIPS, uc.UC_MODE_MIPS32),
        }

        (uc_arch, uc_mode) = uc_arch_mode_dict[arch]

        endianness = self.state.endianness
        if endianness == "little":
            uc_mode |= uc.UC_MODE_LITTLE_ENDIAN
        elif endianness == "big":
            uc_mode |= uc.UC_MODE_BIG_ENDIAN
        else:
            raise ZelosLoadException(f"Unsupported endianness {endianness}")

        return create_emulator(uc_arch, uc_mode, self.state)
Example #5
0
 def _load_module(self, elf, module_name):
     module_path, normalized_module_name = self._get_module_name(
         module_name)
     data = bytearray(elf.Data)
     base = self.memory.map_anywhere(
         elf.VirtualSize,
         preferred_address=elf.ImageBase,
         name="",
         kind="main",
         module_name=basename(normalized_module_name),
     )
     self.memory.write(base, bytes(data))
     # Set proper permissions for each section of the module
     for s in elf.Sections:
         try:
             self.memory.protect(s.Address, align(s.VirtualSize,
                                                  s.Alignment),
                                 s.Permissions)
         except Exception:
             raise ZelosLoadException(
                 f"Bad section {hex(s.Address)}  {hex(s.VirtualSize)}")
     return base