예제 #1
0
    def _phdr_hack2(self):
        '''
        Try to repurpose the GNU_STACK entry. I.e., delete it, freeing room for one additional entry.
        At one point I was convinced that in most cases, this entry is not needed. Could be wrong.
        '''
        logger.info("Trying method 2...")
        if self.num_adtl_segments != 1:
            logger.info(
                "Method 2 does not apply: Would only provide one additional segment"
            )
            return False

        for idx, segment in enumerate(self.elf.iter_segments()):
            # TODO: why are we not calling self._update_phdr_entry like in Method 1??
            if describe_p_type(segment['p_type']) == "GNU_STACK":
                # keep the old base and max number of entries
                self.phdrs['base'] = self.ehdr['e_phoff']
                self.phdrs['max_num'] = len(self.phdrs['entries'])
                # remove this entry, freeing up room for one user defined entry
                logger.debug("removing GNU_STACK pdhr entry")
                del self.phdrs['entries'][idx]
                self.ehdr['e_phnum'] -= 1

                # assert describe_p_type(gnu_stack_entry.p_type) == "GNU_STACK"
                logger.info("should have room to add one section/segment")
                return True
        else:
            logger.info("Method 2 does not apply: No GNU_STACK entry")
        return False
예제 #2
0
파일: utils.py 프로젝트: zha0/qiling
    def elf_program_headers(self):
        program_headers = []

        def add_info(dic):
            program_headers.append(dic)

        if self.elffile.num_segments() == 0:
            return None

        for segment in self.elffile.iter_segments():
            program_hdr = {}
            program_hdr['Type'] = describe_p_type(segment['p_type'])
            program_hdr['Offset'] = self._format_hex(segment['p_offset'],
                                                     fieldsize=6)
            program_hdr['VirtAddr'] = self._format_hex(segment['p_vaddr'],
                                                       fullhex=True)
            program_hdr['PhysAddr'] = self._format_hex(segment['p_paddr'],
                                                       fullhex=True)
            program_hdr['FileSiz'] = self._format_hex(segment['p_filesz'],
                                                      fieldsize=5)
            program_hdr['MemSiz'] = self._format_hex(segment['p_memsz'],
                                                     fieldsize=5)
            program_hdr['Flg'] = describe_p_flags(segment['p_flags'])
            program_hdr['Align'] = self._format_hex(segment['p_align'])

            add_info(program_hdr)

        return program_headers
예제 #3
0
    def run(self, args):
        file_path = idaapi.get_input_file_path()

        if not file_path:
            print('Input file path was not found')
            return

        try:
            fd = open(file_path, "rb")
            elf = ELFFile(fd)
        except Exception as x:
            print(x)
            return

        eh_frame_phdr = next(
            (segment for segment in elf.iter_segments() if describe_p_type(segment['p_type']) == 'GNU_EH_FRAME'),
            None)

        if not eh_frame_phdr:
            print("[-] Executable was not compiled with exception unwinding information")
            return

        eh_frame_hdr_data = EhFrameHdr(eh_frame_phdr, elf)
        fde_count = eh_frame_hdr_data.decode_pointer(eh_frame_hdr_data.fde_count_enc, eh_frame_hdr_data.fde_count, pc=eh_frame_phdr['p_vaddr'] + 8)
        block_map = []

        for i in range(0, fde_count):
            (initial_loc, fde_entry_offset) = unpack("2I", GetManyBytes(eh_frame_hdr_data.fde_table_vaddr + 8 * i, 8))
            (function_vaddr, function_size) = eh_frame_hdr_data.decode_pointer(eh_frame_hdr_data.table_enc, initial_loc, fde_entry_offset)
            block_map.append({'function_address': function_vaddr, 'function_size': function_size})
        block_form = BlockForm0(block_map)
        block_form.Show('GNU_EH_FRAME functions')
예제 #4
0
 def _get_program_headers(self) -> List[Dict[str, str]]:
     return [
         {
             "type": describe_p_type(segment["p_type"]),
             "addr": self._print_addr(segment["p_vaddr"]),
             "flags": describe_p_flags(segment["p_flags"]).strip(),
             "size": segment["p_memsz"],
         }
         for segment in self.elf.iter_segments()
     ]
예제 #5
0
파일: static.py 프로젝트: ptcNOP/cuckoo
 def _get_program_headers(self):
     program_headers = []
     for segment in self.elf.iter_segments():
         program_headers.append({
             "type": describe_p_type(segment["p_type"]),
             "addr": self._print_addr(segment["p_vaddr"]),
             "flags": describe_p_flags(segment["p_flags"]).strip(),
             "size": segment["p_memsz"],
         })
     return program_headers
예제 #6
0
 def _get_program_headers(self):
     program_headers = []
     for segment in self.elf.iter_segments():
         program_headers.append({
             "type": describe_p_type(segment["p_type"]),
             "addr": self._print_addr(segment["p_vaddr"]),
             "flags": describe_p_flags(segment["p_flags"]).strip(),
             "size": segment["p_memsz"],
         })
     return program_headers
예제 #7
0
    def get_program_header(self):
        header = []
        if self._elf.num_segments() == 0:
            return []

        for segment in self._elf.iter_segments():
            result = {}
            result['p_type'] = describe_p_type(segment['p_type'])

            if self._elf.elfclass == 32:
                result['p_offset'] = segment['p_offset']
                result['p_vaddr'] = segment['p_vaddr']
                result['p_paddr'] = segment['p_paddr']
                result['p_filesz'] = segment['p_filesz']
                result['p_memsz'] = segment['p_memsz']
                result['p_flags'] = describe_p_flags(segment['p_flags'])
                result['p_align'] = segment['p_align']
            else:  # 64
                result['p_offset'] = segment['p_offset']
                result['p_vaddr'] = segment['p_vaddr']
                result['p_paddr'] = segment['p_paddr']
                result['p_filesz'] = segment['p_filesz']
                result['p_memsz'] = segment['p_memsz']
                result['p_flags'] = describe_p_flags(segment['p_flags'])
                result['p_align'] = segment['p_align']
            if isinstance(segment, InterpSegment):
                result['interp_name'] = segment.get_interp_name()
            result['include_section'] = []
            for section in self._elf.iter_sections():
                if (not section.is_null()
                        and segment.section_in_segment(section)):
                    result['include_section'].append(section.name)

            #NoteSegment
            if isinstance(segment, NoteSegment):
                result['special_type'] = 'note'
                result['note'] = []
                for note in segment.iter_notes():
                    note_dic = {}
                    note_dic['n_offset'] = note['n_offset']
                    note_dic['n_size'] = note['n_size']
                    note_dic['n_name'] = note['n_name']
                    note_dic['n_descsz'] = note['n_descsz']
                    note_dic['note'] = describe_note(note)
                    result['note'].append(note_dic)

            header.append(result)

        return header
예제 #8
0
def load_elf_and_run(f):
    elffile = ELFFile(f)

    for segment in elffile.iter_segments():
        t = describe_p_type(segment['p_type'])
        print "Program Header: Size: %d, Virtual Address: 0x%x, Type: %s" % (
            segment['p_filesz'], segment['p_vaddr'], t)
        if not (segment['p_vaddr'] & 0x80000000):
            continue
        if segment['p_filesz'] == 0 or segment['p_vaddr'] == 0:
            print "Skipped"
            continue
        write_ram(0xa0000000 | segment['p_vaddr'], segment.data(), True)

    print "Entry: 0x%x" % elffile['e_entry']
    go_ram(elffile['e_entry'])
예제 #9
0
파일: elf2bin.py 프로젝트: 7h3rAm/Shellcode
def main():
	if(len(sys.argv)!=3):
		print "Usage: %s <ELF filename> <output filename>" % sys.argv[0]
		return	
	
	print "Opening ELF file: %s" % sys.argv[1] 
	elffile = ELFFile(open(sys.argv[1],'r'))
	print "Entry point: 0x%x" % elffile.header['e_entry']
		
	loadsegments = list()
	for segment in elffile.iter_segments():
		segtype = describe_p_type(segment['p_type'])
		if(segtype=="LOAD"):
			loadsegments.append(segment)
			
	imgsize = 0
	for segment in loadsegments:
		if(elffile.elfclass == 32):
			print "Load offset " + str(describe_p_flags(segment['p_flags'])) + \
			" 0x%08x at 0x%08x, align 0x%0x" % \
			(segment['p_offset'], segment['p_vaddr'], segment['p_align'])
		else:
			print "Load offset " + str(describe_p_flags(segment['p_flags'])) + \
			" 0x%016x at 0x%016x, align 0x%0x" % \
			(segment['p_offset'], segment['p_vaddr'], segment['p_align'])		
		print "\tFile size: 0x%x\tMem size: 0x%x" % (segment['p_filesz'], segment['p_memsz'])
		imgsize = max(imgsize,segment['p_vaddr']+segment['p_memsz'])
	print "Image size: 0x%x" % imgsize 
	
	buf = ctypes.create_string_buffer(imgsize)
	for segment in loadsegments:
		offset = segment['p_vaddr']
		data = segment.data()
		for i in range(len(segment.data())):
			buf[offset+i] = data[i]
	
	outfile = file(sys.argv[2],'w')
	for char in buf:
		outfile.write(char)
예제 #10
0
    def display_program_headers(self, show_heading=True):
        """ Display the ELF program headers.
            If show_heading is True, displays the heading for this information
            (Elf file type is...)
        """
        self._emitline()
        if self.elffile.num_segments() == 0:
            self._emitline('There are no program headers in this file.')
            return

        elfheader = self.elffile.header
        if show_heading:
            self._emitline('Elf file type is %s' %
                           describe_e_type(elfheader['e_type']))
            self._emitline('Entry point is %s' %
                           self._format_hex(elfheader['e_entry']))
            # readelf weirness - why isn't e_phoff printed as hex? (for section
            # headers, it is...)
            self._emitline(
                'There are %s program headers, starting at offset %s' %
                (elfheader['e_phnum'], elfheader['e_phoff']))
            self._emitline()

        self._emitline('Program Headers:')

        # Now comes the table of program headers with their attributes. Note
        # that due to different formatting constraints of 32-bit and 64-bit
        # addresses, there are some conditions on elfclass here.
        #
        # First comes the table heading
        #
        if self.elffile.elfclass == 32:
            self._emitline(
                '  Type           Offset   VirtAddr   PhysAddr   FileSiz MemSiz  Flg Align'
            )
        else:
            self._emitline(
                '  Type           Offset             VirtAddr           PhysAddr'
            )
            self._emitline(
                '                 FileSiz            MemSiz              Flags  Align'
            )

        # Now the entries
        #
        for segment in self.elffile.iter_segments():
            self._emit('  %-14s ' % describe_p_type(segment['p_type']))

            if self.elffile.elfclass == 32:
                self._emitline(
                    '%s %s %s %s %s %-3s %s' %
                    (self._format_hex(segment['p_offset'], fieldsize=6),
                     self._format_hex(segment['p_vaddr'], fullhex=True),
                     self._format_hex(segment['p_paddr'], fullhex=True),
                     self._format_hex(segment['p_filesz'], fieldsize=5),
                     self._format_hex(segment['p_memsz'], fieldsize=5),
                     describe_p_flags(segment['p_flags']),
                     self._format_hex(segment['p_align'])))
            else:  # 64
                self._emitline(
                    '%s %s %s' %
                    (self._format_hex(segment['p_offset'], fullhex=True),
                     self._format_hex(segment['p_vaddr'], fullhex=True),
                     self._format_hex(segment['p_paddr'], fullhex=True)))
                self._emitline('                 %s %s  %-3s    %s' % (
                    self._format_hex(segment['p_filesz'], fullhex=True),
                    self._format_hex(segment['p_memsz'], fullhex=True),
                    describe_p_flags(segment['p_flags']),
                    # lead0x set to False for p_align, to mimic readelf.
                    # No idea why the difference from 32-bit mode :-|
                    self._format_hex(segment['p_align'], lead0x=False)))

            if isinstance(segment, InterpSegment):
                self._emitline('      [Requesting program interpreter: %s]' %
                               bytes2str(segment.get_interp_name()))

        # Sections to segments mapping
        #
        if self.elffile.num_sections() == 0:
            # No sections? We're done
            return

        self._emitline('\n Section to Segment mapping:')
        self._emitline('  Segment Sections...')

        for nseg, segment in enumerate(self.elffile.iter_segments()):
            self._emit('   %2.2d     ' % nseg)

            for section in self.elffile.iter_sections():
                if (not section.is_null()
                        and segment.section_in_segment(section)):
                    self._emit('%s ' % bytes2str(section.name))

            self._emitline('')
예제 #11
0
    def display_program_headers(self, show_heading=True):
        """ Display the ELF program headers.
            If show_heading is True, displays the heading for this information
            (Elf file type is...)
        """
        self._emitline()
        if self.elffile.num_segments() == 0:
            self._emitline('There are no program headers in this file.')
            return

        elfheader = self.elffile.header
        if show_heading:
            self._emitline('Elf file type is %s' %
                describe_e_type(elfheader['e_type']))
            self._emitline('Entry point is %s' %
                self._format_hex(elfheader['e_entry']))
            # readelf weirness - why isn't e_phoff printed as hex? (for section
            # headers, it is...)
            self._emitline('There are %s program headers, starting at offset %s' % (
                elfheader['e_phnum'], elfheader['e_phoff']))
            self._emitline()

        self._emitline('Program Headers:')

        # Now comes the table of program headers with their attributes. Note
        # that due to different formatting constraints of 32-bit and 64-bit
        # addresses, there are some conditions on elfclass here.
        #
        # First comes the table heading
        #
        if self.elffile.elfclass == 32:
            self._emitline('  Type           Offset   VirtAddr   PhysAddr   FileSiz MemSiz  Flg Align')
        else:
            self._emitline('  Type           Offset             VirtAddr           PhysAddr')
            self._emitline('                 FileSiz            MemSiz              Flags  Align')

        # Now the entries
        #
        for segment in self.elffile.iter_segments():
            self._emit('  %-14s ' % describe_p_type(segment['p_type']))

            if self.elffile.elfclass == 32:
                self._emitline('%s %s %s %s %s %-3s %s' % (
                    self._format_hex(segment['p_offset'], fieldsize=6),
                    self._format_hex(segment['p_vaddr'], fullhex=True),
                    self._format_hex(segment['p_paddr'], fullhex=True),
                    self._format_hex(segment['p_filesz'], fieldsize=5),
                    self._format_hex(segment['p_memsz'], fieldsize=5),
                    describe_p_flags(segment['p_flags']),
                    self._format_hex(segment['p_align'])))
            else: # 64
                self._emitline('%s %s %s' % (
                    self._format_hex(segment['p_offset'], fullhex=True),
                    self._format_hex(segment['p_vaddr'], fullhex=True),
                    self._format_hex(segment['p_paddr'], fullhex=True)))
                self._emitline('                 %s %s  %-3s    %s' % (
                    self._format_hex(segment['p_filesz'], fullhex=True),
                    self._format_hex(segment['p_memsz'], fullhex=True),
                    describe_p_flags(segment['p_flags']),
                    # lead0x set to False for p_align, to mimic readelf.
                    # No idea why the difference from 32-bit mode :-|
                    self._format_hex(segment['p_align'], lead0x=False)))

            if isinstance(segment, InterpSegment):
                self._emitline('      [Requesting program interpreter: %s]' %
                    bytes2str(segment.get_interp_name()))

        # Sections to segments mapping
        #
        if self.elffile.num_sections() == 0:
            # No sections? We're done
            return

        self._emitline('\n Section to Segment mapping:')
        self._emitline('  Segment Sections...')

        for nseg, segment in enumerate(self.elffile.iter_segments()):
            self._emit('   %2.2d     ' % nseg)

            for section in self.elffile.iter_sections():
                if (    not section.is_null() and
                        segment.section_in_segment(section)):
                    self._emit('%s ' % bytes2str(section.name))

            self._emitline('')
예제 #12
0
with open(sys.argv[1], "rb") as file_handle:
    binary_content = file_handle.read()
    elf_file       = ELFFile(file_handle)
    entry_point    = elf_file['e_entry']
    #print(entry_point)
    print("Entry point: %08X\n" % (entry_point))
    print("Retrieving appropriated offset...")
    start_offset = -1
    for segment in elf_file.iter_segments():

        start = segment['p_vaddr']
        size  = segment['p_filesz']

        print("Segment '%s' starting at %08X with size of %d bytes" %
            (describe_p_type(segment['p_type']), segment['p_vaddr'], segment['p_filesz']))

        if(entry_point >= start and entry_point < (start+size)):
            print("\t*** Entry point is located here! ***")
            start_offset = segment['p_offset'] + (entry_point - start)

    if start_offset >= 0:
        print("Start offset computed at %08X" % (start_offset))

    with open("%s.asm" % (sys.argv[1]), "w") as output_asm_file:
        output_asm_file.write("bits 32\n\n")
        i = 0
        for c in binary_content:
            if i == start_offset:
                output_asm_file.write("_start:\n")
            output_asm_file.write("\tdb 0x%02X\n" % (c & 0xff))