Esempio n. 1
0
    def install_hook(self, mod_name, new_address, name=None, ordinal=None):
        if not (bool(name) ^ bool(ordinal)):
            raise ValueError('must select either name or ordinal, not both')
        image_import_descriptors = self.get_proc_attribute('image_import_descriptor')
        image_dos_header_addr = self.get_proc_attribute('image_dos_header_addr')
        is_ordinal = lambda x: bool(x & 0x80000000)

        for iid in image_import_descriptors:
            cur_mod_name = self._get_name_for_image_import_descriptor(iid)
            if cur_mod_name.lower() != mod_name.lower():
                continue
            ilt = self._get_ilt_for_image_import_descriptor(iid)
            iat = self._get_iat_for_image_import_descriptor(iid)

            for idx in range(len(ilt)):
                if ilt[idx] is None:
                    continue
                hook_it = False
                if not is_ordinal(ilt[idx]) and name:
                    cur_func_name = self._get_name_for_ilt_entry(ilt[idx])
                    if cur_func_name == name:
                        hook_it = True
                elif is_ordinal(ilt[idx]) and ordinal:
                    cur_func_ordinal = self._get_ordinal_for_ilt_entry(ilt[idx])
                    if cur_func_ordinal == ordinal:
                        hook_it = True
                if hook_it:
                    old_address = iat[idx]

                    iat_ent_addr = image_dos_header_addr
                    iat_ent_addr += iid.FirstThunk
                    iat_ent_addr += (ctypes.sizeof(ctypes.c_void_p) * idx)

                    new_addr = ctypes.c_void_p()
                    new_addr.value = new_address
                    written = wintypes.DWORD()
                    if self.k32.WriteProcessMemory(self.handle, iat_ent_addr, ctypes.byref(new_addr),
                                                   ctypes.sizeof(new_addr), ctypes.byref(written)) == 0:
                        errno = self.k32.GetLastError()
                        if errno == 998:
                            errno = 0
                            old_permissions = wintypes.DWORD()
                            if (self.k32.VirtualProtectEx(self.handle, iat_ent_addr, 0x400, flags('PAGE_READWRITE'),
                                                          ctypes.byref(old_permissions)) == 0):
                                raise WindowsProcessError('Error: VirtualProtectEx',
                                                          get_last_error=self.k32.GetLastError())
                            if self.k32.WriteProcessMemory(self.handle, iat_ent_addr, ctypes.byref(new_addr),
                                                           ctypes.sizeof(new_addr), ctypes.byref(written)) == 0:
                                errno = self.k32.GetLastError()
                            self.protect(iat_ent_addr, permissions=old_permissions)
                        if errno:
                            raise WindowsProcessError('Error: WriteProcessMemory', get_last_error=errno)
                    hook = Hook('iat', iat_ent_addr, old_address, new_address)
                    self._installed_hooks.append(hook)
                    return hook
        raise ProcessError('failed to find location to install hook')
Esempio n. 2
0
	def install_hook(self, mod_name, new_address, name=None, ordinal=None):
		if architecture_is_32bit(self.__arch__):
			lm_struct = elf.Elf32_Link_Map
			dyn_struct = elf.Elf32_Dyn
			sym_struct = elf.Elf32_Sym
		elif architecture_is_64bit(self.__arch__):
			lm_struct = elf.Elf64_Link_Map
			dyn_struct = elf.Elf64_Dyn
			sym_struct = elf.Elf64_Sym
		else:
			raise LinuxProcessError('unsupported architecture: ' + repr(self.__arch__))
		if ordinal:
			raise NotImplementedError('an ordinal is not supported for this implementation')
		if not name:
			raise RuntimeError('a name is required for this implementation')
		lm = self._read_structure_from_memory(self.get_proc_attribute('link_map_addr'), lm_struct)
		if os.path.isabs(mod_name):
			validate_name = lambda lm: bool(self.read_memory_string(lm.l_name) == mod_name)
		else:
			validate_name = lambda lm: bool(os.path.split(self.read_memory_string(lm.l_name))[-1].startswith(mod_name))
		while not validate_name(lm):
			if lm.l_next == 0:
				raise ProcessError('unable to locate shared library')
			lm = self._read_structure_from_memory(lm.l_next, lm_struct)
		idx = 0
		dyn = self._read_structure_from_memory(lm.l_ld, dyn_struct)
		nchains = 0
		strtab = 0
		symtab = 0
		while dyn.d_tag:
			idx += 1
			if dyn.d_tag == elf.constants.DT_HASH:
				#nchains = struct.unpack('I', self.read_memory(dyn.d_un.d_ptr + lm.l_addr + ctypes.sizeof(ctypes.c_int), ctypes.sizeof(ctypes.c_int)))[0]
				nchains = struct.unpack('I', self.read_memory(dyn.d_un.d_ptr + ctypes.sizeof(ctypes.c_int), ctypes.sizeof(ctypes.c_int)))[0]
			elif dyn.d_tag == elf.constants.DT_STRTAB:
				strtab = dyn.d_un.d_ptr
			elif dyn.d_tag == elf.constants.DT_SYMTAB:
				symtab = dyn.d_un.d_ptr
			dyn = self._read_structure_from_memory(lm.l_ld + (ctypes.sizeof(dyn_struct) * idx), dyn_struct)
		for idx in xrange(0, nchains):
			sym = self._read_structure_from_memory(symtab + (ctypes.sizeof(sym_struct) * idx), sym_struct)
			if (sym.st_info & 0xf) != elf.constants.STT_FUNC:
				continue
			if self.read_memory_string(strtab + sym.st_name) == name:
				sym_addr = (symtab + (ctypes.sizeof(sym_struct) * idx))
				old_address = lm.l_addr + sym.st_value
				sym.st_value = (lm.l_addr - new_address)
				self.write_memory(sym_addr, struct_pack(sym))
				hook = Hook('eat', (sym_addr + sym_struct.st_value.offset), old_address, new_address)
				self._installed_hooks.append(hook)
				return hook
		raise ProcessError('unable to locate function')