def find_main_task(base_ea):
    du_ea = ida_search.find_text(base_ea, 1, 1, "debug-uarts",
                                 ida_search.SEARCH_DOWN)

    if du_ea != ida_idaapi.BADADDR:
        for xref in idautils.XrefsTo(du_ea):
            func = idaapi.get_func(xref.frm)
            mt_ea = 0

            if not func:
                mt_ea = ida_search.find_binary(xref.frm, base_ea, prologues[0],
                                               16, ida_search.SEARCH_UP)

                if mt_ea == ida_idaapi.BADADDR:
                    mt_ea = ida_search.find_binary(xref.frm, base_ea,
                                                   "FF ?? ?? D1", 16,
                                                   ida_search.SEARCH_UP)
            else:
                mt_ea = func.start_ea

            print("\t[+] _main_task = 0x%x" % (mt_ea))
            idc.set_name(mt_ea, "_main_task", idc.SN_CHECK)
            return mt_ea

    print("\t[-] _main_task = not found")
    return ida_idaapi.BADADDR
Example #2
0
def find_do_go(base_ea):
    str_ea = idc.get_name_ea_simple("aCebilefciladrm")

    if str_ea != ida_idaapi.BADADDR:
        for xref in idautils.XrefsTo(str_ea):
            # IDA messes up this function, so I find it this way:
            func = idaapi.get_func(xref.frm)
            dg_ea = 0

            if func != none:
                dg_ea = ida_search.find_binary(xref.frm, func.start_ea,
                                               prologues[0], 16,
                                               ida_search.SEARCH_UP)

                if dg_ea == ida_idaapi.BADADDR:
                    dg_ea = ida_search.find_binary(xref.frm, func.start_ea,
                                                   "FF ?? ?? D1", 16,
                                                   ida_search.SEARCH_UP)

            else:
                dg_ea = ida_search.find_binary(xref.frm, base_ea,
                                               "FF ?? ?? D1", 16,
                                               ida_search.SEARCH_UP)

            ida_funcs.add_func(dg_ea)
            print("\t[+] _do_go = 0x%x" % (dg_ea))
            idc.set_name(dg_ea, "_do_go", idc.SN_CHECK)
            return dg_ea

    print("\t[-] _do_go = not found")
    return ida_idaapi.BADADDR
Example #3
0
def process_strings(segm):
    # If you jump to the bottom of the file and search upwards for this hex, you'll get the string section start
    string_addr = find_probable_string_start(segm)
    if string_addr == BADADDR:
        print(
            "[-] Failed to find string information. Not much info can be pulled."
        )
        return BADADDR, ida_search.find_binary(0x0, segm.end_ea,
                                               "41 70 70 6C 65 20 49", 16,
                                               ida_search.SEARCH_DOWN)

    strend = ida_search.find_binary(string_addr, segm.end_ea,
                                    "41 70 70 6C 65 20 49", 16,
                                    ida_search.SEARCH_DOWN)  # 'Apple, I'
    ea = string_addr
    if strend == BADADDR:
        strend = string_addr + 0xFF

    # Best we can do here is just tell ida to make every single byte, individually, a string; it figures it out.
    for i in range(ea, strend):
        idc.create_strlit(i, BADADDR)

    idc.create_strlit(strend, BADADDR)  # Create the "Apple, Inc." String

    return string_addr, strend
Example #4
0
def find_hex_string(start_ea, stop_ea, hex_string):
    curr_ea = ida_search.find_binary(start_ea, stop_ea, hex_string, 16,
                                     ida_search.SEARCH_DOWN)
    while curr_ea != BADADDR:
        yield curr_ea
        curr_ea = ida_search.find_binary(curr_ea + len(hex_string), stop_ea,
                                         hex_string, 16,
                                         ida_search.SEARCH_DOWN)
Example #5
0
def findGoPcLn():
    possible_loc = ida_search.find_binary(0, idc.BADADDR, lookup, 16, idc.SEARCH_DOWN) #header of gopclntab
    while possible_loc != idc.BADADDR:
        if check_is_gopclntab(possible_loc):
            return possible_loc
        else:
            #keep searching till we reach end of binary
            possible_loc = ida_search.find_binary(possible_loc+1, idc.BADADDR, lookup, 16, idc.SEARCH_DOWN)
    return None
Example #6
0
def find_hex_string(start_ea, stop_ea, hex_string):
    ea = ida_search.find_binary(start_ea, stop_ea, hex_string, 16, ida_search.SEARCH_DOWN)
    while ea != BADADDR:
        yield ea
        ea = ida_search.find_binary(
            ea,
            stop_ea,
            hex_string,
            16,
            ida_search.SEARCH_DOWN | ida_search.SEARCH_NEXT,
        )
Example #7
0
def iter_find_query(query, start=None, end=None, down=True):
    start, end = fix_addresses(start, end)

    if down:
        direction = ida_search.SEARCH_DOWN
    else:
        direction = ida_search.SEARCH_UP

    current = ida_search.find_binary(start, end, query, 16, direction)
    while current < end:
        yield current
        current = ida_search.find_binary(current + 1, end, query, 16,
                                         direction)
Example #8
0
def create_func_by_prefix(func_name, prefix, force=False):
    addrs = []
    start_addr = 0
    func_addr = 0
    while func_addr != idc.BADADDR:
        func_addr = ida_search.find_binary(start_addr, idc.BADADDR, prefix, 16,
                                           idc.SEARCH_DOWN)
        if func_addr == idc.BADADDR:
            break

        # already existing function but it is not the right prefix
        addr = idc.get_func_attr(func_addr, idc.FUNCATTR_START)
        if addr != idc.BADADDR and func_addr != addr:
            if not force:
                start_addr = func_addr + 4
                continue

            idc.del_func(addr)
            idc.del_items(func_addr)

        # add_func is not applied to the existing function
        idc.add_func(func_addr)

        func_name = set_entry_name(func_addr, func_name)
        print("%s: 0x%x" % (func_name, func_addr))

        addrs.append(func_addr)
        start_addr = func_addr + 4

    return addrs
Example #9
0
File: ESigs.py Project: newmsk/ESig
def get_E_main():
    # .text:00485090 55                          push    ebp
    # .text:00485091 8B EC                       mov     ebp, esp
    # .text:00485093 51                          push    ecx
    # .text:00485094 53                          push    ebx
    # .text:00485095 56                          push    esi
    # .text:00485096 8B F1                       mov     esi, ecx
    # .text:00485098 57                          push    edi
    # .text:00485099 8B 4E 68                    mov     ecx, [esi+68h]
    # .text:0048509C 8D 86 D8 00 00 00           lea     eax, [esi+0D8h]
    # .text:004850A2 50                          push    eax             ; int
    # .text:004850A3 51                          push    ecx             ; hModule
    # .text:004850A4 E8 C7 D3 00 00              call    krnln_?GetInstancePath@@YAXPAUHINSTANCE__@@AAVCString@@@Z
    E_main_pat = "55 8B EC 51 53 56 8B F1 57 8B 4E 68 8D 86 D8 00 00 00 50 51 E8"
    E_main_call_ins_offset = 0x37

    E_main_func_ea = 0
    code_segs = get_code_segs()
    for seg in code_segs:
        start_ea = seg.start_ea
        end_ea = seg.end_ea
        E_main_pat_ea = ida_search.find_binary(start_ea, end_ea, E_main_pat,
                                               16, ida_search.SEARCH_DOWN)
        if E_main_pat_ea != idaapi.BADADDR:
            call_ins_ea = E_main_pat_ea + E_main_call_ins_offset
            addr_off = ida_bytes.get_dword(call_ins_ea + 1)
            E_main_func_ea = call_ins_ea + 5 + idaapi.as_int32(addr_off)
            print("Find E_main addr 0x%X" % (E_main_func_ea))
            break

    return E_main_func_ea
def find_do_printf(base_ea, base_end_ea):
    str_ea = ida_search.find_text(base_ea, 1, 1, "<ptr>",
                                  ida_search.SEARCH_DOWN)

    if str_ea != ida_idaapi.BADADDR:
        for xref in idautils.XrefsTo(str_ea):
            func = idaapi.get_func(xref.frm)

            if not func:
                break

            print("\t[+] _do_printf = 0x%x" % (func.start_ea))
            idc.set_name(func.start_ea, "_do_printf", idc.SN_CHECK)
            return func.start_ea

    cmp_ea = ida_search.find_binary(base_ea, base_end_ea, "3F 94 00 71", 16,
                                    ida_search.SEARCH_DOWN)

    if cmp_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(cmp_ea)

        if not func:
            print("\t[-] _do_printf = not found")
            return ida_idaapi.BADADDR

        print("\t[+] _do_printf = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_do_printf", idc.SN_CHECK)
        return func.start_ea

    print("\t[-] _do_printf = not found")
    return ida_idaapi.BADADDR
def FindInstructions(instr, asm_where=None):
    """
    Finds instructions/opcodes
    @return: Returns a tuple(True, [ ea, ... ]) or a tuple(False, "error message")
    """
    if not asm_where:
        # get first segment
        seg = ida_segment.get_first_seg()
        asm_where = seg.start_ea if seg else ida_idaapi.BADADDR
        if asm_where == ida_idaapi.BADADDR:
            return (False, "No segments defined")

    # regular expression to distinguish between opcodes and instructions
    re_opcode = re.compile('^[0-9a-f]{2} *', re.I)

    # split lines
    lines = instr.split(";")

    # all the assembled buffers (for each instruction)
    bufs = []
    for line in lines:
        if re_opcode.match(line):
            # convert from hex string to a character list then join the list to form one string
            buf = bytes(bytearray([int(x, 16) for x in line.split()]))
        else:
            # assemble the instruction
            ret, buf = idautils.Assemble(asm_where, line)
            if not ret:
                return (False, "Failed to assemble:" + line)
        # add the assembled buffer
        bufs.append(buf)

    # join the buffer into one string
    buf = b''.join(bufs)

    # take total assembled instructions length
    tlen = len(buf)

    # convert from binary string to space separated hex string
    bin_str = ' '.join(
        ["%02X" % (ord(x) if sys.version_info.major < 3 else x) for x in buf])

    # find all binary strings
    print("Searching for: [%s]" % bin_str)
    ea = ida_ida.cvar.inf.min_ea
    ret = []
    while True:
        ea = ida_search.find_binary(ea, ida_idaapi.BADADDR, bin_str, 16,
                                    ida_search.SEARCH_DOWN)
        if ea == ida_idaapi.BADADDR:
            break
        ret.append(ea)
        ida_kernwin.msg(".")
        ea += tlen
    if not ret:
        return (False, "Could not match [%s]" % bin_str)
    ida_kernwin.msg("\n")
    return (True, ret)
Example #12
0
def resolve_loops():

    PATTERNS = ["81 FB ?? ?? ?? ?? 75"]

    count_patched = 0
    count_not_patched = 0

    for pattern in PATTERNS:

        ea = 0

        while ea != BADADDR:
            '''
             pattern: 81 FB ?? ?? ?? ?? 75
            .text:00406AA0 01 C7                add     edi, eax
            .text:00406AA2 66 41                inc     cx
            .text:00406AA4 43                   inc     ebx
            .text:00406AA5 81 FB A6 01 00 00    cmp     ebx, 1A6h
            .text:00406AAB 75 F3                jnz     short loc_406AA0

            patched:
            .text:00406AA0 01 C7                add     edi, eax
            .text:00406AA2 66 41                inc     cx
            .text:00406AA4 43                   inc     ebx
            .text:00406AA5 90                   nop
            .text:00406AA6 90                   nop
            .text:00406AA7 90                   nop
            .text:00406AA8 90                   nop
            .text:00406AA9 90                   nop
            .text:00406AAA 90                   nop
            .text:00406AAB 90                   nop
            .text:00406AAC 90                   nop
            '''

            ea = ida_search.find_binary(
                ea, BADADDR, pattern, 16,
                SEARCH_NEXT | SEARCH_DOWN | SEARCH_CASE)

            if ea_in_bounds(ea):

                # Patch CMP and conditional jmp instructions in order to remove the loop
                ida_bytes.patch_byte(ea + 0, 0x90)
                ida_bytes.patch_byte(ea + 1, 0x90)
                ida_bytes.patch_byte(ea + 2, 0x90)
                ida_bytes.patch_byte(ea + 3, 0x90)
                ida_bytes.patch_byte(ea + 4, 0x90)
                ida_bytes.patch_byte(ea + 5, 0x90)
                ida_bytes.patch_byte(ea + 6, 0x90)
                ida_bytes.patch_byte(ea + 7, 0x90)

                idc.create_insn(ea)

                count_patched += 1

    print("\tPatched resolve_loops: {0}".format(count_patched))
    print("\tNot Patched resolve_loops: {0}".format(count_not_patched))
Example #13
0
def FindInstructions(instr, asm_where=None):
    """
    Finds instructions/opcodes
    @return: Returns a tuple(True, [ ea, ... ]) or a tuple(False, "error message")
    """
    if not asm_where:
        # get first segment
        seg = ida_segment.get_first_seg()
        asm_where = seg.start_ea if seg else ida_idaapi.BADADDR
        if asm_where == ida_idaapi.BADADDR:
            return (False, "No segments defined")

    # regular expression to distinguish between opcodes and instructions
    re_opcode = re.compile('^[0-9a-f]{2} *', re.I)

    # split lines
    lines = instr.split(";")

    # all the assembled buffers (for each instruction)
    bufs = []
    for line in lines:
        if re_opcode.match(line):
            # convert from hex string to a character list then join the list to form one string
            buf = ''.join([chr(int(x, 16)) for x in line.split()])
        else:
            # assemble the instruction
            ret, buf = idautils.Assemble(asm_where, line)
            if not ret:
                return (False, "Failed to assemble:"+line)
        # add the assembled buffer
        bufs.append(buf)

    # join the buffer into one string
    buf = ''.join(bufs)

    # take total assembled instructions length
    tlen = len(buf)

    # convert from binary string to space separated hex string
    bin_str = ' '.join(["%02X" % ord(x) for x in buf])

    # find all binary strings
    print("Searching for: [%s]" % bin_str)
    ea = ida_ida.cvar.inf.min_ea
    ret = []
    while True:
        ea = ida_search.find_binary(ea, ida_idaapi.BADADDR, bin_str, 16, ida_search.SEARCH_DOWN)
        if ea == ida_idaapi.BADADDR:
            break
        ret.append(ea)
        ida_kernwin.msg(".")
        ea += tlen
    if not ret:
        return (False, "Could not match [%s]" % bin_str)
    ida_kernwin.msg("\n")
    return (True, ret)
Example #14
0
def find_boot_check_panic(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "1F ?? 03 71", 16, ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _boot_check_panic = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_boot_check_panic", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #15
0
def find_platform_early_init(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "60 02 40 39", 16,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _platform_early_init = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_platform_early_init", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #16
0
def find_macho_valid(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "49 01 8B 9A", 16,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _macho_valid = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_macho_valid", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #17
0
def find_aes_crypto_cmd(base_ea, base_end_ea):
    aes_ea = ida_search.find_binary(base_ea, base_end_ea, "89 2C 00 72", 16,
                                    ida_search.SEARCH_DOWN)

    if aes_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(aes_ea)
        print("\t[+] _aes_crypto_cmd = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_aes_crypto_cmd", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #18
0
def find_chipid_get_chip_revision(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "00 21 06 33", 16,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _chipid_get_chip_revision = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_chipid_get_chip_revision", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #19
0
def function64(base_ea, base_end_ea, name, sequence):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, sequence, 0x10,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("  [sephelper]: %s = 0x%x" % (name, func.start_ea))
        idc.set_name(func.start_ea, name, idc.SN_CHECK)
        return func.start_ea

    print("  [sephelper]: %s = NULL" % name)
    return ida_idaapi.BADADDR
Example #20
0
def find_putchar(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea,
                                    "A0 01 80 52 ?? ?? FF 97 E0", 16,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _putchar = 0x%x" % (func.start_ea))
        idc.set_name(func.start_ea, "_putchar", idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #21
0
def find_image4_validate_property_callback(base_ea, base_end_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "?? 77 00 51", 16,
                                    ida_search.SEARCH_DOWN)

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
        print("\t[+] _image4_validate_property_callback = 0x%x" %
              (func.start_ea))
        idc.set_name(func.start_ea, "_image4_validate_property_callback",
                     idc.SN_CHECK)
        return func.start_ea

    return ida_idaapi.BADADDR
Example #22
0
    def __search_resultcount(self, signature):
        search_addr = ida_ida.cvar.inf.min_ea
        search_results = 0

        while search_results < 2:
            search_addr = ida_search.find_binary(
                search_addr, ida_ida.cvar.inf.max_ea, signature, 16,
                ida_search.SEARCH_DOWN | ida_search.SEARCH_NEXT)
            if search_addr == ida_idaapi.BADADDR:
                break
            search_results += 1

        return search_results
Example #23
0
def findGoPcLn():
    possible_loc = ida_search.find_binary(
        0, idc.BADADDR, lookup, 16, idc.SEARCH_DOWN)  #header of gopclntab
    while possible_loc != idc.BADADDR:
        if check_is_gopclntab(possible_loc):
            return possible_loc
        else:
            #keep searching till we reach end of binary
            possible_loc = ida_search.find_binary(possible_loc + 1,
                                                  idc.BADADDR, lookup, 16,
                                                  idc.SEARCH_DOWN)
    possible_loc = ida_search.find_binary(
        0, idc.BADADDR, lookup16, 16, idc.SEARCH_DOWN)  #header of gopclntab
    while possible_loc != idc.BADADDR:
        print(f"found possible 1.16 gopclntab")
        if check_is_gopclntab16(possible_loc):
            print("Looks like this is go1.16 binary")
            return possible_loc
        else:
            #keep searching till we reach end of binary
            possible_loc = ida_search.find_binary(possible_loc + 1,
                                                  idc.BADADDR, lookup16, 16,
                                                  idc.SEARCH_DOWN)
    return None
Example #24
0
def locate_functions(segm):
    ss = find_probable_string_start(segm)
    print("[+] Strings = %s" % ss)
    for i in ["7F 23 03 D5", "BD A9", "BF A9"]:
        ea = segm.start_ea
        while ea != BADADDR:
            ea = ida_search.find_binary(ea, segm.end_ea, i, 16,
                                        ida_search.SEARCH_DOWN)
            if ea != BADADDR and ea <= ss:
                ea -= 2

                if (ea % 4) == 0 and idaapi.get_full_flags(ea) < 0x200:
                    # print("[+] Defining a function at 0x%x" % (ea))
                    ida_funcs.add_func(ea)

                ea += 4
Example #25
0
    def search_bytes_addr(byt,
                          start_ea=None,
                          end_ea=None,
                          down=True,
                          nxt=True):
        """
            Static method for searching a sequence of bytes. This will search
            for the bytes which ever the data type is.

            This is a wrapper on the ``ida_search.find_binary`` (previously
            ``FindBinary``) function from IDA with a radix of 16.

            The byte should be represented in hexadecimal seperated by space.
            A ``?`` can be put for replacing a byte, for example:
            ``41 8B 44 ? 20``.

            :param byt: A string representing a sequence of byte.
            :param start_ea: The address at which to start the search, if
                ``None`` the current address will be used.
            :param end_ea: The address at which to stop the search, if
                ``None`` the maximum or minimum (depending of searching up or
                down) will be used.
            :param down: If True (the default) search below the given
                address, if False search above.
            :param nxt: If True (the default) the current element will not
                be included in the search.
            :return: The address at which the byte sequence is present or
                ``None`` if no element were found during the search.
        """
        if start_ea is None:
            start_ea = ida_kernwin.get_screen_ea()
        if down:
            fl = ida_search.SEARCH_DOWN
            if end_ea is None:
                end_ea = idc.get_inf_attr(idc.INF_MAX_EA)
        else:
            fl = ida_search.SEARCH_UP
            if end_ea is None:
                end_ea = idc.get_inf_attr(idc.INF_MIN_EA)
        if nxt:
            fl |= ida_search.SEARCH_NEXT
        r = ida_search.find_binary(start_ea, end_ea, byt, 16, fl)
        if r == idc.BADADDR:
            return None
        else:
            return r
def find_img4decodeinit(base_ea):
    cur_ea = base_ea

    while true:
        ea_list = ida_search.find_imm(cur_ea, ida_search.SEARCH_DOWN, 0x494D)

        if ea_list[0] == ida_idaapi.BADADDR:
            ea_list = ida_search.find_imm(cur_ea, ida_search.SEARCH_DOWN,
                                          0x494D0000)

        if ea_list[0] != ida_idaapi.BADADDR:
            ea = ea_list[0]
            func = ida_funcs.get_func(ea)
            func_ea = 0

            if not func:
                func_ea = ida_search.find_binary(ea, base_ea, "?? ?? BD A9",
                                                 16, ida_search.SEARCH_UP)

                if func_ea != ida_idaapi.BADADDR:
                    ida_funcs.add_func(func_ea)
                else:
                    print("\t[-] _Img4DecodeInit = not found")
                    return ida_idaapi.BADADDR
            else:
                func_ea = func.start_ea

            ea_func_list = list(idautils.XrefsTo(func_ea))

            if not ea_func_list:
                cur_ea = ea + 4
                continue

            if ea_func_list[0].frm != ida_idaapi.BADADDR:
                try:
                    i4d_ea = ida_funcs.get_func(ea_func_list[0].frm).start_ea
                    print("\t[+] _Img4DecodeInit = 0x%x" % (i4d_ea))
                    idc.set_name(i4d_ea, "_Img4DecodeInit", idc.SN_CHECK)
                    return i4d_ea
                except:
                    break

        cur_ea = ea + 4

    print("\t[-] _Img4DecodeInit = not found")
    return ida_idaapi.BADADDR
Example #27
0
def masked_search(start_addr: int, end_addr: int, bytes_data: bytes, masks_data: bytes) -> Tuple[int, Optional[bytes]]:
    def prepare_first_search(bd: bytes, md: bytes) -> bytes:
        bd_str = binascii.hexlify(bd, ' ').split(b' ')
        md_str = binascii.hexlify(md, ' ').split(b' ')

        for ii, md_token in enumerate(md_str):
            if md_token != b'ff':
                bd_str[ii] = b'?'

        bd_str = b' '.join(bd_str)

        return bd_str

    len_bytes = len(bytes_data)

    bytes_data_prep = prepare_first_search(bytes_data, masks_data)

    if idaapi.IDA_SDK_VERSION >= 760:
        patterns = ida_bytes.compiled_binpat_vec_t()
        idaapi.parse_binpat_str(patterns, start_addr, bytes_data_prep.decode(), 16)
        ea = ida_bytes.bin_search(start_addr, end_addr, patterns,
                                  ida_bytes.BIN_SEARCH_FORWARD |
                                  ida_bytes.BIN_SEARCH_NOBREAK |
                                  ida_bytes.BIN_SEARCH_NOSHOW)
    else:
        ea = ida_search.find_binary(start_addr, end_addr, bytes_data_prep.decode(), 16, idaapi.SEARCH_DOWN)

    if ea == idaapi.BADADDR:
        return idaapi.BADADDR, None

    found_bytes = idaapi.get_bytes(ea, len_bytes)

    equal = True
    for i in range(len_bytes):
        m = masks_data[i]
        if found_bytes[i] & m != bytes_data[i] & m:
            equal = False
            break

    if equal:
        return ea, found_bytes

    return idaapi.BADADDR, None
Example #28
0
def resolve_opaque_push_retn():

    PATTERNS = ["68 ?? ?? ?? ?? C3"]

    count_patched = 0

    for pattern in PATTERNS:

        ea = 0

        while ea != BADADDR:
            ea = ida_search.find_binary(
                ea, BADADDR, pattern, 16,
                SEARCH_NEXT | SEARCH_DOWN | SEARCH_CASE)
            ''' 
            pattern: 68 ?? ?? ?? ?? C3
            .text:00406922 68 B2 6A 00 10       push    0x10006ab2
            .text:00406927 C3                   retn
            
            patched:
            .text:00406922 E9 B2 6A 00 10       jmp     0x10006ab2
            .text:00406927 90                   nop
            '''

            if ea_in_bounds(ea):
                j_pos = ea
                pos_jmp = idc.get_wide_dword(j_pos + 1)  # absolute address

                offset = pos_jmp - 5 - j_pos

                # Patch the push and retn instructions with NOPs (6 bytes)
                for i in range(0, 6):
                    ida_bytes.patch_byte(j_pos + i, 0x90)

                ida_bytes.patch_byte(j_pos, 0xE9)
                ida_bytes.patch_dword(j_pos + 0x1, offset)

                idc.create_insn(ea)

                count_patched += 1

    print("\tPatched resolve_opaque_push_retn: {0}".format(count_patched))
Example #29
0
def find_image4_validate_property_callback(base_ea, base_end_ea, ptr_ea):
    seq_ea = ida_search.find_binary(base_ea, base_end_ea, "?? 77 00 51", 16,
                                    ida_search.SEARCH_DOWN)
    func = none

    if seq_ea != ida_idaapi.BADADDR:
        func = idaapi.get_func(seq_ea)
    else:
        for xref in idautils.XrefsTo(ptr_ea):
            func = idaapi.get_func(xref.frm)
            break

    if func:
        print("\t[+] _image4_validate_property_callback = 0x%x" %
              (func.start_ea))
        idc.set_name(func.start_ea, "_image4_validate_property_callback",
                     idc.SN_CHECK)
        return func.start_ea

    print("\t[-] _image4_validate_property_callback = not found")
    return ida_idaapi.BADADDR
Example #30
0
File: ESigs.py Project: newmsk/ESig
def get_E_info_entry():
    # .text:004AE780 50                            push    eax
    # .text:004AE781 64 89 25 00 00 00 00          mov     large fs:0, esp
    # .text:004AE788 81 EC AC 01 00 00             sub     esp, 1ACh
    # .text:004AE78E 53                            push    ebx
    # .text:004AE78F 56                            push    esi
    # .text:004AE790 57                            push    edi
    E_lib_pat = "50 64 89 25 00 00 00 00 81 ec ac 01 00 00 53 56 57"
    E_lib_addr_offset = 0x25

    E_lib_infos_ea = 0
    code_segs = get_code_segs()

    for seg in code_segs:
        start_ea = seg.start_ea
        end_ea = seg.end_ea
        E_lib_pat_ea = ida_search.find_binary(start_ea, end_ea, E_lib_pat, 16,
                                              ida_search.SEARCH_DOWN)
        if E_lib_pat_ea != idaapi.BADADDR:
            mov_ins_ea = E_lib_pat_ea + E_lib_addr_offset
            E_lib_infos_ea = ida_bytes.get_dword(mov_ins_ea + 1)
            break

    return E_lib_infos_ea
Example #31
0
def load_file(fd, neflags, format):
    global prologues
    global br_flag
    size = 0
    base_addr = 0
    ea = 0
    nfunc = 0

    idaapi.set_processor_type("arm", ida_idp.SETPROC_LOADER_NON_FATAL)
    idaapi.get_inf_structure().lflags |= idaapi.LFLG_64BIT

    if (neflags & idaapi.NEF_RELOAD) != 0:
        return 1

    fd.seek(0, idaapi.SEEK_END)
    size = fd.tell()

    segm = idaapi.segment_t()
    segm.bitness = 2  # 64-bit
    segm.start_ea = 0
    segm.end_ea = size

    if br_flag == false:
        idaapi.add_segm_ex(segm, "iBoot", "CODE", idaapi.ADDSEG_OR_DIE)
    else:
        idaapi.add_segm_ex(segm, "SecureROM", "CODE", idaapi.ADDSEG_OR_DIE)

    fd.seek(0)
    fd.file2base(0, 0, size, false)

    idaapi.add_entry(0, 0, "start", 1)
    ida_funcs.add_func(ea)

    print("[+] Marked as code")

    # heuristic
    while (true):
        mnemonic = idc.print_insn_mnem(ea)

        if "LDR" in mnemonic:
            base_str = idc.print_operand(ea, 1)
            base_addr = int(base_str.split("=")[1], 16)

            break

        ea += 4

    print("[+] Rebasing to address 0x%x" % (base_addr))
    idaapi.rebase_program(base_addr, idc.MSF_NOFIX)

    segment_start = base_addr
    segment_end = idc.get_segm_attr(segment_start, idc.SEGATTR_END)

    ea = segment_start

    print("[+] Searching and defining functions")

    for prologue in prologues:
        while ea != ida_idaapi.BADADDR:
            ea = ida_search.find_binary(ea, segment_end, prologue, 16,
                                        ida_search.SEARCH_DOWN)

            if ea != ida_idaapi.BADADDR:
                if len(prologue) < 8:
                    ea = ea - 2

                if (ea % 4) == 0 and ida_bytes.get_full_flags(ea) < 0x200:
                    # print("[+] Defining a function at 0x%x" % (ea))
                    ida_funcs.add_func(ea)
                    nfunc = nfunc + 1

                ea = ea + 4

    idc.plan_and_wait(segment_start, segment_end)

    print("[+] Identified %d new functions" % (nfunc))

    print("[+] Looking for interesting functions")
    find_interesting(segment_start, segment_end)

    return 1