def search_retns(self):

        if not self.debug: print("found %d modules" % len(self.modules))
        for m in self.modules:

            # Iterate over segments in the module
            # BUG: Iterating over all loaded segments is more stable than looking up by address
            if not self.debug: print("found %d segments" % idaapi.get_segm_qty())
            for n in xrange(idaapi.get_segm_qty()):
                seg = idaapi.getnseg(n)

                # Locate executable segments in a selected modules
                # NOTE: Each module may have multiple executable segments
                if seg and seg.startEA >= m.addr and seg.endEA <= (m.addr + m.size):
                    # If the debugger is attached then we can check if the segment is executable, else
                    # just check if it is code or not.
                    if idaapi.dbg_can_query() and idaapi.get_process_state() < 0:
                        if seg.perm & idaapi.SEGPERM_EXEC == 0:
                            continue
                    elif seg.type & idaapi.SEG_CODE == 0:
                        continue

                    #######################################################
                    # Search for ROP gadgets
                    if self.searchRop:

                        #Search all instances of BLR
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "4E 80 00 20", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break

                            self.retns.append((ea, m.file))

                        # Search all instances of BTCTR
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "4E 80 04 20", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break

                            self.retns.append((ea, m.file))

                        # Search all instances of BTCTRL
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "4E 80 04 21", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break

                            self.retns.append((ea, m.file))
Exemple #2
0
 def PopulateTree(self):
     self.tree.clear()
     executable_segments = [(idc.SegName(idaapi.getnseg(x).startEA), 0!=(idaapi.getnseg(x).perm & idaapi.SEGPERM_EXEC)) for x in range(idaapi.get_segm_qty())]
     for segment in executable_segments:
         if not segment[1]:
             continue
         caves = self.findCodeCavez(segment[0])
         for cave in caves:
             self.addEntryToTree(segment[0], cave[0], cave[1])
Exemple #3
0
 def __init__(self):
     self.sym_file_path = idc.AskFile(0, "*.map;*.txt", "open symbol file")
     self.sym_file = None
     self.seg = idaapi.get_segm_by_name(".text")
     if self.seg is None:
         self.seg = idaapi.getnseg(0)
     self.base = self.seg.startEA
Exemple #4
0
    def __init__(self, ea=UseCurrentAddress, name=None, index=None):
        """Wrapper around IDA segments.

        There are 3 ways to get a segment - by name, ea or index. Only use one.

        Args:
            ea - address in the segment
            name - name of the segment
            index - index of the segment
        """
        if sum((ea not in (self.UseCurrentAddress, None), name is not None, index is not None,)) > 1:
            raise ValueError(
                "Expected only one (ea, name or index). Got (ea={!r}, name={!r}, index={!r})".format(ea, name, index))

        elif name is not None:
            seg = idaapi.get_segm_by_name(name)

        elif index is not None:
            seg = idaapi.getnseg(index)

        elif ea == self.UseCurrentAddress:
            seg = idaapi.getseg(idc.here())

        elif ea is None:
            raise ValueError("`None` is not a valid address. To use the current screen ea, "
                             "use `Function(ea=Function.UseCurrentAddress)` or supply no `ea`.")

        else:
            seg = idaapi.getseg(ea)

        self._segment = seg
Exemple #5
0
def processDataSegments(M, new_eas):
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        ea = seg.startEA
        segtype = idc.GetSegmentAttr(ea, idc.SEGATTR_TYPE)
        if segtype in [idc.SEG_DATA, idc.SEG_BSS]:
            start = idc.SegStart(ea)
            end = idc.SegEnd(ea)
            addDataSegment(M, start, end, new_eas)
def search_binary(binary_string):
    for i in range(idaapi.get_segm_qty()):
        segm = idaapi.getnseg(i)
        current_ea = segm.startEA
        while True:
            current_ea = idaapi.find_binary(current_ea + 1, segm.endEA, binary_string, 16, idaapi.SEARCH_DOWN)
            if current_ea == idaapi.BADADDR:
                break
            return current_ea
    return 0
Exemple #7
0
	def AnalyzeAllSections( self ):
		BlockData = {}
		Map = []
		CurrentAddress = idc.MinEA()

		i = 0
		while i < idaapi.get_segm_qty():
			seg = idaapi.getnseg( i )
	 		self.AnalyzeRange( seg.startEA, seg.endEA )
			i+=1
Exemple #8
0
def Segments():
    """
    Get list of segments (sections) in the binary image

    @return: List of segment start addresses.
    """
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        if seg:
            yield seg.startEA
Exemple #9
0
    def get_padded_bytes(self, count):
        result = "\x00" * count
        ranges_left = [MemoryRange(self.address, self.address + count)]

        segment_count = idaapi.get_segm_qty()
        valid_memory_ranges = []
        for i in range(segment_count):
            segment = idaapi.getnseg(i)
            # Skip segments with unstable data
            if segment.type == idaapi.SEG_XTRN:
                continue
            valid_memory_ranges.append(
                MemoryRange(segment.startEA, segment.endEA))

        while len(ranges_left) > 0:
            # Get a requested memory range and remove it from the list
            current_range = ranges_left.pop()

            intersection = None
            for memory_range in valid_memory_ranges:
                start = max(current_range.start, memory_range.start)
                end = min(current_range.end, memory_range.end)
                if end > start:
                    intersection = MemoryRange(start, end)
                    break

            # No segment can satisfy any part of requested range
            if intersection is None:
                continue

            chunk = idc.GetManyBytes(
                intersection.start,
                intersection.end - intersection.start)
            if chunk is None:
                print('[librgb] Some bytes are unreadable in %s..%s' % (
                    idc.atoa(intersection.start),
                    idc.atoa(intersection.end)))
                continue

            result = \
                result[0:intersection.start - self.address] \
                + chunk \
                + result[intersection.end - self.address:]
            assert(len(result) == count)

            # If necessary, enqueue ranges unsatisfied by chosen mem segment
            range1 = MemoryRange(current_range.start, intersection.start)
            range2 = MemoryRange(intersection.end, current_range.end)
            if range1.length > 0:
                ranges_left.append(range1)
            if range2.length > 0:
                ranges_left.append(range2)

        assert(len(result) == count)
        return result
def get_functions_ida():
  #Repeat for list of segments
  for n in xrange(idaapi.get_segm_qty()):
    #Get number of segments
    seg = idaapi.getnseg(n)
    if seg:
      #Get list of functions in that segment
      funcs=idautils.Functions(seg.startEA, seg.endEA)
      for funcname in funcs:
        name = GetFunctionName(funcname)
        print name
Exemple #11
0
def rename_functions_ida():
    # Repeat for list of segments
    for n in xrange(idaapi.get_segm_qty()):
        # Get number of segments
        seg = idaapi.getnseg(n)
        if seg:
            # Get list of functions in that segment
            funcs = idautils.Functions(seg.startEA, seg.endEA)
            for funcaddress in funcs:
                name = GetFunctionName(funcaddress)
                if name in functions_in_library:
                    MakeNameEx(funcaddress, "glibc_" + name, SN_NOWARN)
Exemple #12
0
def code_segments_iter():
    """Iterates over the possible code sections within an input binary."""
    for i in range(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(i)

        if not seg: continue
        seg_class = idaapi.get_segm_class(seg)

        if seg_class != "CODE": continue
        seg_name = idaapi.get_segm_name(seg.startEA)

        yield seg.startEA, seg.endEA, seg_name
def rename_functions_ida(func_library_map):
  print func_library_map.keys()
  #Repeat for list of segments
  for n in xrange(idaapi.get_segm_qty()):
    #Get number of segments
    seg = idaapi.getnseg(n)
    if seg:
      #Get list of functions in that segment
      funcs=idautils.Functions(seg.startEA, seg.endEA)
      for funcaddress in funcs:
        name=GetFunctionName(funcaddress)
        if func_library_map.has_key(name):
          MakeNameEx(funcaddress,func_library_map[name][1:]+"_"+name,SN_NOWARN)
Exemple #14
0
def rename_functions_ida():
    #Get number of segments
    seg = idaapi.getnseg(0)
    if seg:
        #Get list of functions in that segment
        funcs = idautils.Functions(seg.startEA, seg.endEA)
        for funcaddress in funcs:
            f_name = GetFunctionName(funcaddress)
            if f_name == 'giant_keyloggercase_structure':
                for address in Heads(funcaddress, FindFuncEnd(funcaddress)):
                    if GetMnem(address) == 'call':
                        t1 = GetOpnd(address, 0)
                        if t1.startswith('sub_'):
                            t2 = t1.split('_')
                            MakeNameEx(int(t2[1], 16),
                                       "keylog_charbychar_" + t2[1], SN_NOWARN)
Exemple #15
0
def get_segments_info(seg_names=default_seg_names):
    res = {}
    for name in seg_names:
        seg = idaapi.get_segm_by_name(name)
        if not seg:
            continue
        res[name] = {}
        res[name]['startEA'] = seg.startEA
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        for name, d in res.items():
            if d['startEA'] == seg.startEA:
                res[name][
                    'ID'] = seg.name  # this is an ID, not a name, kthx IDA :(
                res[name]['endEA'] = seg.endEA
    return res
Exemple #16
0
def tag_functions():
    seg = idaapi.getnseg(0)
    min = seg.start_ea
    max = seg.end_ea
    if min > 0:
        min = min - 1
    curaddr = ida_search.find_not_func(min, SEARCH_DOWN)
    while curaddr < max:
        idc.create_insn(curaddr)
        line_asm = idc.generate_disasm_line(curaddr, 0)
## If you need to bypass the padding instructions, use this:
#        if "se_or" in line_asm:
#            curaddr = curaddr + 2
        if ida_funcs.add_func(curaddr) != True:
            idc.create_insn(curaddr)
        curaddr = ida_search.find_not_func(curaddr, SEARCH_DOWN)
Exemple #17
0
    def __init__(self,
                 ea=UseCurrentAddress,
                 name=None,
                 index=None,
                 segment_t=None):
        """Wrapper around IDA segments.

        There are 3 ways to get a segment - by name, ea or index. Only use one.

        Args:
            ea - address in the segment
            name - name of the segment
            index - index of the segment
        """
        if sum((
                ea not in (self.UseCurrentAddress, None),
                name is not None,
                index is not None,
                segment_t is not None,
        )) > 1:
            raise ValueError(
                ("Expected only one (ea, name, index or segment_t)."
                 " Got (ea={!r}, name={!r}, index={!r}, segment_t={!r})"
                 ).format(ea, name, index, segment_t))

        elif segment_t is not None:
            seg = segment_t

        elif name is not None:
            seg = idaapi.get_segm_by_name(name)

        elif index is not None:
            seg = idaapi.getnseg(index)

        elif ea == self.UseCurrentAddress:
            seg = idaapi.getseg(idc.here())

        elif ea is None:
            raise ValueError(
                "`None` is not a valid address. To use the current screen ea, "
                "use `Function(ea=Function.UseCurrentAddress)` or supply no `ea`."
            )

        else:
            seg = idaapi.getseg(ea)

        self._segment = seg
Exemple #18
0
def code_segments_iter():
    """Iterates over the possible code sections within an input binary."""

    for i in range(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(i)

        if not seg:
            continue

        seg_class = idaapi.get_segm_class(seg)

        if seg_class != "CODE":
            continue

        seg_name = idaapi.get_segm_name(seg.startEA)

        yield seg.startEA, seg.endEA, seg_name
def Segments():
    """
    Get list of segments (sections) in the binary image

    @return: List of segment start addresses.
    """
    seglist = []

    for n in range(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)

        if not seg:
            break
        else:
            seglist.append(seg.startEA)
    
    return seglist
Exemple #20
0
def processpltSegs():
    funcdata = {}
    datafunc = {}
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        ea = seg.startEA
        segname = idc.get_segm_name(ea)  #SegName(ea)
        if segname in ['.plt', 'extern', '.MIPS.stubs']:
            start = seg.startEA
            end = seg.endEA
            cur = start
            while cur < end:
                name = get_unified_funcname(cur)
                funcdata[name] = hex(cur)
                datafunc[cur] = name
                cur = idc.next_head(cur)
    return funcdata, datafunc
def Segments():
    """
    Get list of segments (sections) in the binary image

    @return: List of segment start addresses.
    """
    seglist = []

    for n in range(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)

        if not seg:
            break
        else:
            seglist.append(seg.startEA)

    return seglist
Exemple #22
0
def analyze_qwords():
    # Get kernel boundaries
    kernel_start = BADADDR
    kernel_stop = 0x0
    seg_count = 0
    for ea in Segments():
        seg_count += 1
        kernel_start = min(kernel_start, SegStart(ea))
        kernel_stop = max(kernel_stop, SegEnd(ea))

    # Transform every potential kernel pointer to a qword
    for i in range(seg_count):
        seg = idaapi.getnseg(i)
        for ea in range(seg.startEA, seg.endEA, 8):
            if get_item_size(ea) >= 8:
                continue
            value = get_qword(ea)
            if kernel_start <= value < kernel_stop:
                create_qword(ea)
Exemple #23
0
def analyze_qwords():
    # Get user boundaries
    user_start = BADADDR
    user_stop = 0x0
    seg_count = 0
    for ea in Segments():
        seg_count += 1
        user_start = min(user_start, SegStart(ea))
        user_stop = max(user_stop, SegEnd(ea))

    # Transform every potential user pointer to a qword
    for i in range(seg_count):
        seg = idaapi.getnseg(i)
        for ea in range(seg.startEA, seg.endEA, 8):
            if get_item_size(ea) >= 8:
                continue
            value = get_qword(ea)
            if user_start <= value < user_stop:
                create_qword(ea)
Exemple #24
0
def get_extrn_funcs():
	exfunclist = []
	for n in xrange(idaapi.get_segm_qty()):
		print n
		seg = idaapi.getnseg(n)
		start = seg.startEA
		segname = idc.SegName(start)
		if segname == 'extern':
			cur = start
			end = seg.endEA
			while cur <= end:
				externfunc = GetFunctionName(cur)
				if '@' in externfunc:
					externfunc = externfunc.split('@')[0]
					exfunclist.append(externfunc)
				else:
					exfunclist.append(externfunc)
				cur = NextHead(cur)
	return exfunclist
Exemple #25
0
def analyze_qwords():
    # Get kernel boundaries
    kernel_start = NOT_FOUND
    kernel_stop = 0x0
    seg_count = 0
    for ea in Segments():
        seg_count += 1
        kernel_start = min(kernel_start, SegStart(ea))
        kernel_stop = max(kernel_stop, SegEnd(ea))

    # Transform every potential kernel pointer to a qword
    for i in range(seg_count):
        seg = idaapi.getnseg(i)
        for ea in range(seg.startEA, seg.endEA, 8):
            if get_item_size(ea) >= 8:
                continue
            value = get_qword(ea)
            if kernel_start <= value < kernel_stop:
                create_qword(ea)
Exemple #26
0
def tag_code():
    seg = idaapi.getnseg(0)
    min = seg.start_ea
    max = seg.end_ea
    if min > 0:
        min = min - 1
    curaddr = ida_search.find_unknown(min, idc.SEARCH_DOWN)
    while curaddr < max:
        idc.create_insn(curaddr)
        line_asm = idc.generate_disasm_line(curaddr, 0)
## If you need to bypass the padding instructions, use this:
#        if "se_or" in line_asm:
#            curaddr = curaddr + 2
        if ida_funcs.add_func(curaddr) != True:
            idc.create_insn(curaddr)
        curaddr = ida_search.find_unknown(curaddr, idc.SEARCH_DOWN)
    print("Waiting for auto-analysis to finish")
    ida_auto.auto_wait()
    save_functions()
    print("Done.")
Exemple #27
0
def get_segments_info():
    # Note this must match the list of segments in the current file
    seg_names = [".init", ".plt", ".text", ".fini", ".rodata", ".eh_frame_hdr",
                 "eh_frame", ".gcc_except_table", ".tdata", ".ctors", ".dtors",
                 ".jcr", ".got", ".got.plt", ".data", "freq_data_section",
                 ".bss", "extern", "abs", ".rdata"]
    res = {}
    for name in seg_names:
        seg = idaapi.get_segm_by_name(name)
        if not seg:
            continue
        res[name] = {}
        res[name]['startEA'] = seg.startEA
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        for name,d in res.items():
            if d['startEA'] == seg.startEA:
                res[name]['ID'] = seg.name # this is an ID, not a name, kthx IDA :(
                res[name]['endEA'] = seg.endEA
    return res
def search_for_vuln_api():
  #Repeat for list of segments
  for n in xrange(idaapi.get_segm_qty()):
    #Get number of segments
    seg = idaapi.getnseg(n)
    if seg:
      #Get list of functions in that segment
      funcs=idautils.Functions(seg.startEA, seg.endEA)
      #Search for vuln functions inside binary and print occurences to output file. This is NOT to be directly reported; perform manual analysis before doing so.
      if funcs:
        for name in funcs:
  	  each_function_disassembly = list(idautils.FuncItems(name))
  	  for e in each_function_disassembly:
  	    for vulnfunc in vuln_function_list:
  	      pattern=vulnfunc+r'$'
  	      m=re.search(pattern,idc.GetDisasm(e))
  	      if m:
  	        f.write(idc.GetFuncOffset(e)+' --> '+idc.GetDisasm(e)+'\n\n')
      else:
        f.write('Failed to get function names and hence cannot parse stuff\n')
def get_sreg_base_x64(name):
    sdb = idaapi.dbg_get_thread_sreg_base(idc.GetCurrentThreadId(),
                                          int(getattr(cpu, name)))
    if not sdb:
        for n in xrange(idaapi.get_segm_qty()):
            seg = idaapi.getnseg(n)
            sgname = idaapi.get_segm_name(seg, 0)
            if sgname.startswith('TIB['):
                _sdb = seg.startEA + 0x1000
                sdb_self = int(
                    base64.b16encode(
                        idaapi.dbg_read_memory(_sdb + 0x30, 8)[::-1]), 16)
                if (sdb_self == _sdb):
                    sdb = _sdb
                    print("\nwarning: the segname:%s is zero,I give %016x" %
                          (name, sdb))
                break
    if not sdb:
        print(
            "\n\nwarning: the segname:%s is zero, U need set it by yourself\n"
            % (name))
    return sdb
Exemple #30
0
def search_for_vuln_api():
    #Repeat for list of segments
    for n in xrange(idaapi.get_segm_qty()):
        #Get number of segments
        seg = idaapi.getnseg(n)
        if seg:
            #Get list of functions in that segment
            funcs = idautils.Functions(seg.startEA, seg.endEA)
            #Search for vuln functions inside binary and print occurences to output file. This is NOT to be directly reported; perform manual analysis before doing so.
            if funcs:
                for name in funcs:
                    each_function_disassembly = list(idautils.FuncItems(name))
                    for e in each_function_disassembly:
                        for vulnfunc in vuln_function_list:
                            pattern = vulnfunc + r'$'
                            m = re.search(pattern, idc.GetDisasm(e))
                            if m:
                                f.write(
                                    idc.GetFuncOffset(e) + ' --> ' +
                                    idc.GetDisasm(e) + '\n\n')
            else:
                f.write(
                    'Failed to get function names and hence cannot parse stuff\n'
                )
Exemple #31
0
def analyze_code():
    seg = idaapi.getnseg(0)
    for ea in range(seg.startEA, seg.endEA, 1):
        MakeCode(ea)
Exemple #32
0
def iterate():
    '''Iterate through each segment_t defined in the database'''
    for n in xrange(idaapi.get_segm_qty()):
        yield idaapi.getnseg(n)
    return
    def writeMem(self, binfile):
        regs = self.getRegs()
        segm = self.init_segm_mem()
        idaapi.refresh_debugger_memory()
        print(
            "+-------------------+----------------------+--------------------+----------+--------+"
        )
        print(
            "|      segment      |          VA          |        size        |   flag   | status |"
        )
        print(
            "+-------------------+----------------------+--------------------+----------+--------+"
        )

        for n in xrange(idaapi.get_segm_qty()):
            seg = idaapi.getnseg(n)
            if seg:
                name = Dump.getSegName(seg, segm)
                address = seg.startEA
                length = seg.endEA - seg.startEA

                db_data = idaapi.dbg_read_memory(address, length)
                print("| %-17s |  %18x  | %8x -> %5dkb|    %2d    |   " %
                      (name, address, length, length / 1024, seg.flags),
                      end="")
                if db_data:
                    segm[name] = [address, length, db_data]
                    print('ok   |')
                    length = len(db_data)
                    segm[name] = [address, length, db_data]
                else:
                    if (length >= 0x400):
                        print(
                            "war  |\n+-------------------+----------------------+--------------------+----------+--------+"
                        )
                        data = Dump.getDbgMemPage(address, length)
                        data.append([b"", 0, 0])
                        is_unmap = False
                        tmp = b''
                        begin = address
                        fbegin = address
                        fsize = 0
                        for i, d in enumerate(data):
                            db, ea, size = d
                            if is_unmap:
                                if db:  # 0 1
                                    is_unmap = False
                                    begin = ea
                                    tmp = db
                                    print(
                                        "| %-17s |  %18x  | %8x -> %5dkb|    %2d    |  faild |"
                                        % (name, fbegin, fsize, fsize / 1024,
                                           seg.flags))
                                else:  # 0 0
                                    fsize += size
                                    if (i == len(data) - 1):
                                        print(
                                            "| %-17s |  %18x  | %8x -> %5dkb|    %2d    |  faild |"
                                            % (name, fbegin, fsize,
                                               fsize / 1024, seg.flags))
                                    pass
                            else:
                                if db:  # 1 1
                                    is_unmap = False
                                    tmp += db
                                else:  # 1 0
                                    fbegin = ea
                                    fsize = size
                                    is_unmap = True
                                    if tmp:
                                        name = Dump.getSegName(seg, segm)
                                        segm[name] = [begin, len(tmp), tmp]
                                        print(
                                            "| %-17s |  %18x  | %8x -> %5dkb|    %2d    |   ok   |"
                                            % (name, begin, len(tmp),
                                               len(tmp) / 1024, seg.flags))
                                    else:
                                        print(
                                            "| %-17s |  %18x  | %8x -> %5dkb|    %2d    |  faild |"
                                            % (name, fbegin, fsize,
                                               fsize / 1024, seg.flags))
                                        break

                        print(
                            "+-------------------+----------------------+--------------------+----------+--------+"
                        )
                    else:
                        print('  faild')
                    continue

        print(
            "+-------------------+----------------------+--------------------+----------+--------+"
        )
        # GetBptQty() GetBptEA(n):
        nameoffset_p = 0
        dataoffset_p = 0
        all_ab_name = 0

        for regAddress in regs:
            INT = regs[regAddress]
            regName = self.register_names[regAddress]
            size = self.registers[regName][1]
            up = None
            if INT < 0:
                up = lambda x: x.lower()
            else:
                up = lambda x: x

            try:
                if size == 1:
                    db_data = struct.pack(up("<B"), INT)
                elif size == 2:
                    db_data = struct.pack(up("<H"), INT)
                elif size == 4:
                    db_data = struct.pack(up("<I"), INT)
                elif size == 8:
                    db_data = struct.pack(up("<Q"), INT)
                elif size == 16:
                    db_data = struct.pack(up("<QQ"),
                                          int(INT & 0xffffffffffffffff),
                                          int(INT >> 64))
                elif size == 32:
                    db_data = struct.pack(up("<QQQQ"),
                                          INT & 0xffffffffffffffff,
                                          (INT >> 64) & 0xffffffffffffffff,
                                          (INT >> 128) & 0xffffffffffffffff,
                                          INT >> 192)
                else:
                    continue
                segm['registers' +
                     str(regAddress)] = [regAddress,
                                         len(db_data), db_data]
                print(" (%-10s IR_offset: %-5d) (regValue: %-32x nb: %2d) " %
                      (regName, regAddress, (INT), len(db_data)))
            except Exception as e:
                print("-=1-=1-=1-=1- error:", e, regName, hex(INT), size,
                      "-=1-=1-=1-=1- ")

        def find_segm(va, length, bpt_l):
            global BPNORMAL
            for ea, bptype, hwtype_hwsize, code in bpt_l:
                if va <= ea and ea < va + length:
                    if bptype == BPNORMAL:
                        yield (code, ea - va)

        bpt_list = [i for i in Breakpoints()]
        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            all_ab_name += len(ab_name)
            # 将软件断点pass掉
            len_db_data = len(db_data)
            for code, offset in find_segm(address, length, bpt_list):
                db_data = db_data[:offset] + struct.pack(
                    up("<H"), code) + db_data[offset + 2:]
                segm[name] = [address, length, db_data]
                assert (len(db_data) == len_db_data)
                print("bkp found: address: %x code: %s" %
                      (address + offset,
                       base64.b16encode(struct.pack(up("<H"), code))))

        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            nameoffset = len(segm) * 32 + nameoffset_p
            dataoffset = len(segm) * 32 + all_ab_name + dataoffset_p
            db1 = struct.pack("<Q", nameoffset)
            db2 = struct.pack("<Q", address)
            db3 = struct.pack("<Q", length)
            db4 = struct.pack("<Q", dataoffset)
            self.mem_mmap[name] = [address, dataoffset, length]
            binfile.write(db1)
            binfile.write(db2)
            binfile.write(db3)
            binfile.write(db4)
            nameoffset_p += len(ab_name)
            dataoffset_p += length
        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            binfile.write(ab_name)
        for name in segm:
            address, length, db_data = segm[name]
            binfile.write(db_data)
Exemple #34
0
def writeMem(binfile, regs):
    segm = {}
    for n in xrange(idaapi.get_segm_qty()):
        seg = idaapi.getnseg(n)
        if seg:
            count = 0
            h = ''
            while (idaapi.get_segm_name(seg, 0) + h) in segm.keys():
                count += 1
                h = str(count)
            name = idaapi.get_segm_name(seg, 0) + h
            address = seg.startEA
            length = seg.endEA - seg.startEA

            db_data = idaapi.dbg_read_memory(address, length)
            if db_data:
                print('ok   ', name, seg.flags, length, 'bytes', length / 1024,
                      'kb')
                segm[name] = [address, length, db_data]
            else:
                print('faild', name, seg.flags, length, 'bytes', length / 1024,
                      'kb')
                pass
    nameoffset_p = 0
    dataoffset_p = 0
    all_ab_name = 0

    register_names = {
        16: 'rax',
        24: 'rcx',
        32: 'rdx',
        40: 'rbx',
        48: 'rsp',
        56: 'rbp',
        64: 'rsi',
        72: 'rdi',
        80: 'r8',
        88: 'r9',
        96: 'r10',
        104: 'r11',
        112: 'r12',
        120: 'r13',
        128: 'r14',
        136: 'r15',
        144: 'cc_op',
        152: 'cc_dep1',
        160: 'cc_dep2',
        168: 'cc_ndep',
        176: 'd',
        184: 'rip',
        192: 'ac',
        200: 'id',
        208: 'fs',
        216: 'sseround',
        224: 'ymm0',
        256: 'ymm1',
        288: 'ymm2',
        320: 'ymm3',
        352: 'ymm4',
        384: 'ymm5',
        416: 'ymm6',
        448: 'ymm7',
        480: 'ymm8',
        512: 'ymm9',
        544: 'ymm10',
        576: 'ymm11',
        608: 'ymm12',
        640: 'ymm13',
        672: 'ymm14',
        704: 'ymm15',
        736: 'ymm16',
        768: 'ftop',
        776: 'mm0',
        784: "mm1",
        792: "mm2",
        800: "mm3",
        808: "mm4",
        816: "mm5",
        824: "mm6",
        832: "mm7",
        840: 'fptag',
        848: 'fpround',
        856: 'fc3210',
        864: 'emnote',
        872: 'cmstart',
        880: 'cmlen',
        888: 'nraddr',
        904: 'gs',
        912: 'ip_at_syscall'
    }
    registers = {
        'rax': (16, 8),
        'eax': (16, 4),
        'ax': (16, 2),
        'al': (16, 1),
        'ah': (17, 1),
        'rcx': (24, 8),
        'ecx': (24, 4),
        'cx': (24, 2),
        'cl': (24, 1),
        'ch': (25, 1),
        'rdx': (32, 8),
        'edx': (32, 4),
        'dx': (32, 2),
        'dl': (32, 1),
        'dh': (33, 1),
        'rbx': (40, 8),
        'ebx': (40, 4),
        'bx': (40, 2),
        'bl': (40, 1),
        'bh': (41, 1),
        'rsp': (48, 8),
        'sp': (48, 8),
        'esp': (48, 4),
        'rbp': (56, 8),
        'bp': (56, 8),
        'ebp': (56, 4),
        'rsi': (64, 8),
        'esi': (64, 4),
        'si': (64, 2),
        'sil': (64, 1),
        'sih': (65, 1),
        'rdi': (72, 8),
        'edi': (72, 4),
        'di': (72, 2),
        'dil': (72, 1),
        'dih': (73, 1),
        'r8': (80, 8),
        'r9': (88, 8),
        'r10': (96, 8),
        'r11': (104, 8),
        'r12': (112, 8),
        'r13': (120, 8),
        'r14': (128, 8),
        'r15': (136, 8),
        'cc_op': (144, 8),
        'cc_dep1': (152, 8),
        'cc_dep2': (160, 8),
        'cc_ndep': (168, 8),
        'd': (176, 8),
        'dflag': (176, 8),
        'rip': (184, 8),
        'ip': (184, 8),
        'pc': (184, 8),
        'ac': (192, 8),
        'acflag': (192, 8),
        'id': (200, 8),
        'idflag': (200, 8),
        'fs': (208, 8),
        'fs_const': (208, 8),
        'sseround': (216, 8),
        'ymm0': (224, 32),
        'xmm0': (224, 16),
        'ymm1': (256, 32),
        'xmm1': (256, 16),
        'ymm2': (288, 32),
        'xmm2': (288, 16),
        'ymm3': (320, 32),
        'xmm3': (320, 16),
        'ymm4': (352, 32),
        'xmm4': (352, 16),
        'ymm5': (384, 32),
        'xmm5': (384, 16),
        'ymm6': (416, 32),
        'xmm6': (416, 16),
        'ymm7': (448, 32),
        'xmm7': (448, 16),
        'ymm8': (480, 32),
        'xmm8': (480, 16),
        'ymm9': (512, 32),
        'xmm9': (512, 16),
        'ymm10': (544, 32),
        'xmm10': (544, 16),
        'ymm11': (576, 32),
        'xmm11': (576, 16),
        'ymm12': (608, 32),
        'xmm12': (608, 16),
        'ymm13': (640, 32),
        'xmm13': (640, 16),
        'ymm14': (672, 32),
        'xmm14': (672, 16),
        'ymm15': (704, 32),
        'xmm15': (704, 16),
        'ymm16': (736, 32),
        'xmm16': (736, 16),
        'ftop': (768, 4),
        'fpreg': (776, 64),
        'fpu_regs': (776, 64),
        'mm0': (776, 8),
        'mm1': (784, 8),
        'mm2': (792, 8),
        'mm3': (800, 8),
        'mm4': (808, 8),
        'mm5': (816, 8),
        'mm6': (824, 8),
        'mm7': (832, 8),
        'fptag': (840, 8),
        'fpu_tags': (840, 8),
        'fpround': (848, 8),
        'fc3210': (856, 8),
        'emnote': (864, 4),
        'cmstart': (872, 8),
        'cmlen': (880, 8),
        'nraddr': (888, 8),
        'gs': (904, 8),
        'gs_const': (904, 8),
        'ip_at_syscall': (912, 8)
    }

    for regAddress in regs:
        INT = regs[regAddress]
        regName = register_names[regAddress]
        size = registers[regName][1]
        if size == 1:
            db_data = struct.pack("<B", INT)
        elif size == 2:
            db_data = struct.pack("<H", INT)
        elif size == 4:
            db_data = struct.pack("<I", INT)
        elif size == 8:
            db_data = struct.pack("<Q", INT)
        elif size == 16:
            db_data = struct.pack("<QQ", int(INT & 0xffffffffffffffff),
                                  int(INT >> 64))
        elif size == 32:
            db_data = struct.pack("<QQQQ", INT & 0xffffffffffffffff,
                                  (INT >> 64) & 0xffffffffffffffff,
                                  (INT >> 128) & 0xffffffffffffffff,
                                  INT >> 192)
        else:
            continue
        segm['registers' +
             str(regAddress)] = [regAddress, len(db_data), db_data]

    for name in segm:
        address, length, db_data = segm[name]
        ab_name = (name + '\x00').encode('utf-8')
        all_ab_name += len(ab_name)
    for name in segm:
        address, length, db_data = segm[name]
        ab_name = (name + '\x00').encode('utf-8')
        nameoffset = len(segm) * 32 + nameoffset_p
        dataoffset = len(segm) * 32 + all_ab_name + dataoffset_p
        db1 = struct.pack("<Q", nameoffset)
        db2 = struct.pack("<Q", address)
        db3 = struct.pack("<Q", length)
        db4 = struct.pack("<Q", dataoffset)
        binfile.write(db1)
        binfile.write(db2)
        binfile.write(db3)
        binfile.write(db4)
        nameoffset_p += len(ab_name)
        dataoffset_p += length
    for name in segm:
        address, length, db_data = segm[name]
        ab_name = (name + '\x00').encode('utf-8')
        binfile.write(ab_name)
    for name in segm:
        address, length, db_data = segm[name]
        binfile.write(db_data)
Exemple #35
0
    def search_pointers(self):

        # HACK: A separate flag is used to track user canceling the search,
        #       because multiple calls to idaapi.wasBreak() do not properly
        #       detect cancellations.
        breakFlag = False

        # Show wait dialog
        idaapi.show_wait_box("Searching writable function pointers...")

        for m in self.modules:

            ###################################################################
            # Locate all of the CALL and JMP instructions in the current module
            # which use an immediate operand.

            # List of call/jmp pointer calls in a given module
            ptr_calls = list()

            # Iterate over segments in the module
            # BUG: Iterating over all loaded segments is more stable than looking up by address
            for n in xrange(idaapi.get_segm_qty()):
                seg = idaapi.getnseg(n)

                # Segment in a selected modules
                if seg and seg.startEA >= m.addr and seg.endEA <= (m.addr + m.size):

                    # Locate executable segments
                    # NOTE: Each module may have multiple executable segments
                    # TODO: Search for "MOV REG, PTR # CALL REG"
                    if seg.perm & idaapi.SEGPERM_EXEC:

                        # Search all instances of CALL /2 imm32/64 - FF 15
                        # TODO: Alternative pointer calls using SIB: FF 14 E5 11 22 33 44 - call dword/qword ptr [0x44332211]
                        #                                            FF 14 65 11 22 33 44
                        #                                            FF 14 25 11 22 33 44
                        call_ea = seg.startEA
                        while True:
                            call_ea = idaapi.find_binary(call_ea + 1, seg.endEA, "FF 15", 16, idaapi.SEARCH_DOWN)
                            if call_ea == idaapi.BADADDR: break
                            ptr_calls.append(call_ea)

                        # Search all instances of JMP /2 imm32/64 - FF 25
                        # TODO: Alternative pointer calls using SIB: FF 24 E5 11 22 33 44 - jmp dword/qword ptr [0x44332211]
                        #                                            FF 24 65 11 22 33 44
                        #                                            FF 24 25 11 22 33 44
                        call_ea = seg.startEA
                        while True:
                            call_ea = idaapi.find_binary(call_ea + 1, seg.endEA, "FF 25", 16, idaapi.SEARCH_DOWN)
                            if call_ea == idaapi.BADADDR: break
                            ptr_calls.append(call_ea)

            ###################################################################
            # Extract all of the function pointers and make sure they are
            # are writable.

            # List of writable function pointer objects in a given module
            ptrs = list()

            for call_ea in ptr_calls:

                # Decode CALL/JMP instruction
                # NOTE: May result in invalid disassembly of split instructions
                insn_size = idaapi.decode_insn(call_ea)

                if insn_size:

                    insn = idaapi.cmd
                    insn_op1 = insn.Operands[0].type

                    # Verify first operand is a direct memory reference
                    if insn.Operands[0].type == idaapi.o_mem:

                        # Get operand address
                        ptr_ea = insn.Operands[0].addr

                        # Apply pointer offset
                        ptr_ea -= self.ptrOffset

                        # Locate segment where the pointer is located
                        ptr_seg = idaapi.getseg(ptr_ea)

                        # Make sure a valid segment writeable segment was found
                        if ptr_seg and ptr_seg.perm & idaapi.SEGPERM_WRITE:

                            # Get pointer charset
                            ptr_charset = self.sploiter.get_ptr_charset(ptr_ea)

                            # Filter the pointer
                            if not self.filterP2P:
                                if ptr_charset == None:                                    continue
                                if self.ptrNonull and not "nonull" in ptr_charset: continue
                                if self.ptrUnicode and not "unicode" in ptr_charset: continue
                                if self.ptrAscii and not "ascii" in ptr_charset: continue
                                if self.ptrAsciiPrint and not "asciiprint" in ptr_charset: continue
                                if self.ptrAlphaNum and not "alphanum" in ptr_charset: continue
                                if self.ptrNum and not "numeric" in ptr_charset: continue
                                if self.ptrAlpha and not "alpha" in ptr_charset: continue

                            # Increment the fptr counter

                            # Get pointer disassembly
                            insn_disas = idc.GetDisasmEx(call_ea, idaapi.GENDSM_FORCE_CODE)

                            # Add pointer to the list
                            ptr = Ptr(m.file, ptr_ea, self.ptrOffset, ptr_charset, call_ea, insn_disas)
                            ptrs.append(ptr)

            ###################################################################
            # Cache Pointers to Pointers

            ptr_ea_prefix_cache = dict()

            if self.searchP2P:

                # CACHE: Running repeated searches over the entire memory space is
                #        very expensive. Let's cache all of the addresses containing
                #        bytes corresponding to discovered function pointers in a
                #        single search and simply reference this cache for each
                #        function pointer. Specifically running idaapi.find_binary()
                #        is much more expensive than idaapi.dbg_read_memory().
                #
                # NOTE:  For performance considerations, the cache works on a per
                #        module basis, but could be expanded for the entire memory
                #        space.
                #
                # prefix_offset - how many bytes of discovered function
                #        pointers to cache.
                #
                #        Example: For function pointers 0x00401234, 0x00404321, 0x000405678
                #        we are going to use prefix_offset 2, so we will cache all of the
                #        values located at addresses 0x0040XXXX

                if self.sploiter.addr64:
                    pack_format = "<Q"
                    addr_bytes = 8
                    prefix_offset = 6
                else:
                    pack_format = "<I"
                    addr_bytes = 4
                    prefix_offset = 2

                # Set of unique N-byte address prefixes to search in memory
                ea_prefix_set = set()

                for ptr in ptrs:
                    ptr_ea = ptr.ptr_ea

                    ptr_bytes = struct.pack(pack_format, ptr_ea)
                    ptr_bytes = ptr_bytes[-prefix_offset:]

                    ea_prefix_set.add(ptr_bytes)

                # Search the module for all bytes corresponding to the prefix
                # and use them as candidates for pointers-to-pointers

                for ea_prefix in ea_prefix_set:

                    # NOTE: Make sure you search using 44 33 22 11 format and not 11223344
                    ea_prefix_str = " ".join(["%02x" % ord(b) for b in ea_prefix])

                    # Initialize search parameters for a given module
                    ea = m.addr
                    maxea = m.addr + m.size

                    while True:
                        ea = idaapi.find_binary(ea + 1, maxea, ea_prefix_str, 16, idaapi.SEARCH_DOWN)
                        if ea == idaapi.BADADDR: break

                        p2p_ea = ea - (addr_bytes - prefix_offset)

                        dbg_mem = read_module_memory(p2p_ea, addr_bytes)
                        ptr_ea_prefix = unpack(pack_format, dbg_mem)[0]

                        if ptr_ea_prefix in ptr_ea_prefix_cache:
                            ptr_ea_prefix_cache[ptr_ea_prefix].add(p2p_ea)
                        else:
                            ptr_ea_prefix_cache[ptr_ea_prefix] = set([p2p_ea, ])

                        # Detect search cancellation, but allow the loop below
                        # to run to create already cached/found function pointers

                        # Canceled
                        if breakFlag or idaapi.wasBreak():
                            breakFlag = True
                            break

                    # Canceled
                    if breakFlag or idaapi.wasBreak():
                        breakFlag = True
                        break

            ###################################################################
            # Locate Pointer to Pointers

            for ptr in ptrs:

                ptr_ea = ptr.ptr_ea

                # Locate pointers-to-pointers for a given function pointer in the cache
                if self.searchP2P and ptr_ea in ptr_ea_prefix_cache:

                    for p2p_ea in ptr_ea_prefix_cache[ptr_ea]:

                        # Apply pointer-to-pointer offset
                        p2p_ea -= self.p2pOffset

                        p2p_charset = self.sploiter.get_ptr_charset(p2p_ea)

                        # Filter the pointer
                        if self.filterP2P:
                            if p2p_charset == None:                                    continue
                            if self.ptrNonull and not "nonull" in p2p_charset: continue
                            if self.ptrUnicode and not "unicode" in p2p_charset: continue
                            if self.ptrAscii and not "ascii" in p2p_charset: continue
                            if self.ptrAsciiPrint and not "asciiprint" in p2p_charset: continue
                            if self.ptrAlphaNum and not "alphanum" in p2p_charset: continue
                            if self.ptrNum and not "numeric" in p2p_charset: continue
                            if self.ptrAlpha and not "alpha" in p2p_charset: continue

                        # Copy existing pointer object to modify it for the particular p
                        p2p = copy.copy(ptr)
                        p2p.p2p_ea = p2p_ea
                        p2p.p2p_offset = self.p2pOffset
                        p2p.p2p_charset = p2p_charset

                        # Apppend p2p specific pointer object to the global list
                        self.ptrs.append(p2p)

                        # Exceeded maximum number of pointers
                        if self.maxPtrs and len(self.ptrs) >= self.maxPtrs:
                            breakFlag = True
                            print "[idasploiter] Maximum number of pointers exceeded."
                            break

                # Simply append pointer object to the global list
                else:
                    self.ptrs.append(ptr)

                    # Exceeded maximum number of pointers
                    if self.maxPtrs and len(self.ptrs) >= self.maxPtrs:
                        breakFlag = True
                        print "[idasploiter] Maximum number of pointers exceeded."
                        break

                if breakFlag or idaapi.wasBreak():
                    breakFlag = True
                    break

            # Canceled
            # NOTE: Only works when started from GUI not script.
            if breakFlag or idaapi.wasBreak():
                breakFlag = True
                print "[idasploiter] Canceled."
                break

        print "[idasploiter] Found %d total pointers." % len(self.ptrs)
        idaapi.hide_wait_box()
Exemple #36
0
    def search_retns(self):

        if not self.debug: print("found %d modules" % len(self.modules))
        for m in self.modules:

            # Iterate over segments in the module
            # BUG: Iterating over all loaded segments is more stable than looking up by address
            if not self.debug: print("found %d segments" % idaapi.get_segm_qty())
            for n in xrange(idaapi.get_segm_qty()):
                seg = idaapi.getnseg(n)

                # Locate executable segments in a selected modules
                # NOTE: Each module may have multiple executable segments
                if seg and seg.startEA >= m.addr and seg.endEA <= (m.addr + m.size):
                    # If the debugger is attached then we can check if the segment is executable, else
                    # just check if it is code or not.
                    if idaapi.dbg_can_query() and idaapi.get_process_state() < 0:
                        if seg.perm & idaapi.SEGPERM_EXEC == 0:
                            continue
                    elif seg.type & idaapi.SEG_CODE == 0:
                        continue

                    #######################################################
                    # Search for ROP gadgets
                    if self.searchRop:

                        # Search all instances of RETN
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "C3", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break
                            self.retns.append((ea, m.file))

                        # Search all instances of RETN imm16
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "C2", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break

                            # Read imm16 value and filter large values
                            retn_imm16 = read_module_memory(ea + 1, 0x2)
                            retn_imm16 = unpack("<H", retn_imm16)[0]

                            if retn_imm16 <= self.maxRetnImm:
                                self.retns.append((ea, m.file))

                    #######################################################
                    # Search for JOP gadgets
                    if self.searchJop:

                        # Search all instances of JMP reg (FF /4) and CALL reg (FF /2)
                        ea = seg.startEA
                        while True:
                            ea = idaapi.find_binary(ea + 1, seg.endEA, "FF", 16, idaapi.SEARCH_DOWN)
                            if ea == idaapi.BADADDR: break

                            # Read possible ModR/M, SIB, and IMM8/IMM32 bytes
                            jop = read_module_memory(ea + 1, 0x6)
                            if jop == None or len(jop) == 0:
                                continue

                            ###################################################
                            # JMP/CALL reg
                            if jop[0] in ["\xe0", "\xe1", "\xe2", "\xe3", "\xe4", "\xe5", "\xe6", "\xe7",
                                          "\xd0", "\xd1", "\xd2", "\xd3", "\xd4", "\xd5", "\xd6", "\xd7"]:
                                self.retns.append((ea, m.file))

                            ###################################################
                            # JMP/CALL [reg] no SIB
                            # NOTE: Do not include pure [disp] instruction.

                            # JMP/CALL [reg] no *SP,*BP
                            elif jop[0] in ["\x20", "\x21", "\x22", "\x23", "\x26", "\x27",
                                            "\x10", "\x11", "\x12", "\x13", "\x16", "\x17"]:
                                self.retns.append((ea, m.file))

                            # JMP/CALL [reg + imm8] no *SP
                            elif jop[0] in ["\x60", "\x61", "\x62", "\x63", "\x65", "\x66", "\x67",
                                            "\x50", "\x51", "\x52", "\x53", "\x55", "\x56", "\x57"]:
                                jop_imm8 = jop[1]
                                jop_imm8 = unpack("b", jop_imm8)[0]  # signed

                                if jop_imm8 <= self.maxJopImm:
                                    self.retns.append((ea, m.file))


                            # JMP/CALL [reg + imm32] no *SP
                            elif jop[0] in ["\xa0", "\xa1", "\xa2", "\xa3", "\xa5", "\xa6", "\xa7",
                                            "\x90", "\x91", "\x92", "\x93", "\x95", "\x96", "\x97"]:
                                jop_imm32 = jop[1:5]
                                jop_imm32 = unpack("<i", jop_imm32)[0]  # signed

                                if jop_imm32 <= self.maxJopImm:
                                    self.retns.append((ea, m.file))

                            ###################################################
                            # JMP/CALL [reg] with SIB
                            # NOTE: Do no include pure [disp] instructions in SIB ([*] - none)
                            elif (jop[0] in ["\x24", "\x64", "\xa4"] and not jop[1] in ["\x25", "\x65", "\xad",
                                                                                        "\xe5"]) or \
                                    (jop[0] in ["\x14", "\x54", "\x94"] and not jop[1] in ["\x25", "\x65", "\xad",
                                                                                           "\xe5"]):

                                # Check for displacement
                                if jop[0] in ["\x64", "\x54"]:
                                    jop_imm8 = jop[2]
                                    jop_imm8 = unpack("b", jop_imm8)[0]  # signed

                                    if jop_imm8 <= self.maxJopImm:
                                        self.retns.append((ea, m.file))

                                elif jop[0] in ["\xa4", "\x94"]:
                                    jop_imm32 = jop[2:6]
                                    jop_imm32 = unpack("<i", jop_imm32)[0]  # signed

                                    if jop_imm32 <= self.maxJopImm:
                                        self.retns.append((ea, m.file))

                                else:
                                    self.retns.append((ea, m.file))

        print "[idasploiter] Found %d returns" % len(self.retns)
Exemple #37
0
    def writeMem(self, binfile):
        regs = self.getRegs()
        segm = self.init_segm_mem()
        for n in xrange(idaapi.get_segm_qty()):
            seg = idaapi.getnseg(n)
            if seg:
                count = 0
                h = ''
                while (idaapi.get_segm_name(seg, 0) + h) in segm.keys():
                    count += 1
                    h = str(count)
                name = idaapi.get_segm_name(seg, 0) + h
                address = seg.startEA
                length = seg.endEA - seg.startEA

                db_data = idaapi.dbg_read_memory(address, length)
                if db_data:
                    print('ok   ', name, seg.flags, length, 'bytes',
                          length / 1024, 'kb')
                    segm[name] = [address, length, db_data]
                else:
                    print('faild', name, seg.flags, length, 'bytes',
                          length / 1024, 'kb')
                    pass
        nameoffset_p = 0
        dataoffset_p = 0
        all_ab_name = 0

        for regAddress in regs:
            INT = regs[regAddress]
            regName = self.register_names[regAddress]
            size = self.registers[regName][1]
            try:
                if size == 1:
                    db_data = struct.pack("<B", INT)
                elif size == 2:
                    db_data = struct.pack("<H", INT)
                elif size == 4:
                    db_data = struct.pack("<I", INT)
                elif size == 8:
                    db_data = struct.pack("<Q", INT)
                elif size == 16:
                    db_data = struct.pack("<QQ", int(INT & 0xffffffffffffffff),
                                          int(INT >> 64))
                elif size == 32:
                    db_data = struct.pack("<QQQQ", INT & 0xffffffffffffffff,
                                          (INT >> 64) & 0xffffffffffffffff,
                                          (INT >> 128) & 0xffffffffffffffff,
                                          INT >> 192)
                else:
                    continue
                segm['registers' +
                     str(regAddress)] = [regAddress,
                                         len(db_data), db_data]
                print(" (%-10s : %-5d) (%-x) (%d)" % (regName, regAddress,
                                                      (INT), len(db_data)))
            except Exception as e:
                print("--------- error:", e, regName, hex(INT), size,
                      "--------- ")

        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            all_ab_name += len(ab_name)
        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            nameoffset = len(segm) * 32 + nameoffset_p
            dataoffset = len(segm) * 32 + all_ab_name + dataoffset_p
            db1 = struct.pack("<Q", nameoffset)
            db2 = struct.pack("<Q", address)
            db3 = struct.pack("<Q", length)
            db4 = struct.pack("<Q", dataoffset)
            binfile.write(db1)
            binfile.write(db2)
            binfile.write(db3)
            binfile.write(db4)
            nameoffset_p += len(ab_name)
            dataoffset_p += length
        for name in segm:
            address, length, db_data = segm[name]
            ab_name = (name + '\x00').encode('utf-8')
            binfile.write(ab_name)
        for name in segm:
            address, length, db_data = segm[name]
            binfile.write(db_data)
Exemple #38
0
 def newsegment(index):
     res = idaapi.getnseg(index)
     res.index = index
     return res
Exemple #39
0
def iterate():
    '''Iterate through each segment_t defined in the database'''
    for n in xrange(idaapi.get_segm_qty()):
        yield idaapi.getnseg(n)
    return
 def newsegment(index):
     seg = idaapi.getnseg(index)
     seg.index, _ = index, ui.navigation.set(interface.range.start(seg))
     return seg
Exemple #41
0
 def __init__(self):
     self.segs = []
     for i in range(idaapi.get_segm_qty()):
         self.segs.append(create_segment_node(idaapi.getnseg(i)))
Exemple #42
0
def analyze_code():
    seg = idaapi.getnseg(0)
    for ea in range(seg.startEA, seg.endEA, 1):
        MakeCode(ea)
Exemple #43
0
 def newsegment(index):
     res = idaapi.getnseg(index)
     res.index = index
     return res
Exemple #44
0
def get_current_segment(ea):
    '''Gets the segment start ea of the current segment'''
    for index in xrange(idaapi.get_segm_qty()):
        segm = idaapi.getnseg(index)
        if segm.startEA <= ea < segm.endEA:
            return segm.startEA
Exemple #45
0
 def __init__(self):
     self.segs = []
     for i in range(idaapi.get_segm_qty()):
         self.segs.append(create_segment_node(idaapi.getnseg(i)))