コード例 #1
0
	def search_for_history_in_task_memory(self, malloc_tiny_list, pm_cr3, mempath):
		proc_pae = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)
		
		history_list = []
		
		ptr_size = 8
		unpack_int = '=QQ'
		
		#print ''
		
		for vm_address in malloc_tiny_list:
			#print '[*] Search for keys in range 0x%.8x-0x%.8x'%(vm_address[0], vm_address[1])
			
			for vm_offset in range(vm_address[0], vm_address[1], ptr_size*2):
				
				if proc_pae.is_valid_address(vm_offset):
					pointer_set = proc_pae.read(vm_offset, ptr_size*2)
					value = struct.unpack(unpack_int, pointer_set)
					
					# brute-force
					# value[0] = line pointer, value[1] = timestamp pointer
					if ((value[0] & value[1]) >= vm_address[0]) and ((value[0] & value[1]) < vm_address[1]):
						#print 'timestamp: %x, line: %x'%(value[1], value[0])
						try:
							csharp = struct.unpack('c', proc_pae.read(value[1], 1))[0]
						except struct.error:
							continue
						if '#' == csharp: # timestamp signature
							#print 'got it'
							# get timestamp
							timebuf = ''
							linebuf = ''
							temp_list = []
							for byte in range(value[1]+1, vm_address[1], 1): # remove singature '#'
								buf = proc_pae.read(byte, 1)
								if struct.unpack('b', buf)[0] == 0:
									break
								timebuf += struct.unpack('c', buf)[0]

							if timebuf != '':
								for byte in range(value[0], vm_address[1], 1):
									buf = proc_pae.read(byte, 1)
									try:
										if struct.unpack('b', buf)[0] == 0:
											break
										linebuf += struct.unpack('c', buf)[0]
									except struct.error:
										continue
							temp_list.append(long(timebuf))
							temp_list.append(linebuf)

							history_list.append(temp_list)
			
			#print history_list
		
		return history_list
コード例 #2
0
    def search_for_keys_in_task_memory(self, malloc_tiny_list, pm_cr3,
                                       mempath):
        proc_pae = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)

        candidate_key_list = []

        ptr_size = 0
        unpack_int = ''

        if self.arch == 32:
            ptr_size = 4
            unpack_int = '=I'
        elif self.arch == 64:
            ptr_size = 8
            unpack_int = '=Q'
        else:
            ptr_size = 4
            unpack_int = '=I'

        print ''

        for vm_address in malloc_tiny_list:
            print '[*] Search for keys in range 0x%.8x-0x%.8x' % (
                vm_address[0], vm_address[1]),

            for vm_offset in range(vm_address[0], vm_address[1], ptr_size):

                if proc_pae.is_valid_address(vm_offset):
                    signature = proc_pae.read(vm_offset, ptr_size)

                    if KEY_SIZE == struct.unpack(
                            unpack_int, signature
                    )[0]:  # find specific hex code(0x00000018)
                        #print signature.encode('hex')
                        key_buf = proc_pae.read(vm_offset + ptr_size, ptr_size)
                        key_buf_ptr = struct.unpack(unpack_int, key_buf)[0]

                        if key_buf_ptr >= vm_address[
                                0] and key_buf_ptr <= vm_address[
                                    1]:  # check vma between vm.start and vm.stop
                            candidate_key = proc_pae.read(
                                key_buf_ptr, KEY_SIZE)
                            candidate_key_list.append(
                                candidate_key)  # append to candidate key list

            print 'complete. master key candidates : %d' % len(
                candidate_key_list)

        return candidate_key_list
コード例 #3
0
    def get_proc_dump(self, vm_list, vm_struct, process_name, mempath):

        pm_cr3 = self.get_proc_cr3(vm_list, vm_struct)

        print '[+] Resetting the Page Mapping Table: 0x%x' % pm_cr3

        proc_pae = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)

        print '[+] Process Dump Start'

        for vme_info in vm_list:
            #print proc_pae.vtop(vme_info[0])
            #print vme_info[1]

            nop_code = 0x00
            pk_nop_code = struct.pack('=B', nop_code)
            nop = pk_nop_code * 0x1000

            file = open('%s-%x-%x' % (process_name, vme_info[0], vme_info[1]),
                        mode="wb")

            nop_flag = 0
            for i in range(vme_info[0], vme_info[1], 0x1000):
                raw_data = 0x00
                if not (proc_pae.is_valid_address(i)):
                    if nop_flag == 1:
                        raw_data = nop
                        file.write(raw_data)
                    continue
                raw_data = proc_pae.read(i, 0x1000)
                if raw_data is None:
                    if nop_flag == 1:
                        raw_data = nop
                        file.write(raw_data)
                    continue
                file.write(raw_data)
                nop_flag = 1
            file.close()
            size = os.path.getsize('%s-%x-%x' %
                                   (process_name, vme_info[0], vme_info[1]))
            if size == 0:
                os.remove('%s-%x-%x' %
                          (process_name, vme_info[0], vme_info[1]))
            else:
                print ' [-] [DUMP] Image Name: %s-%x-%x' % (
                    process_name, vme_info[0], vme_info[1])
        print '[+] Process Dump End'
        return
コード例 #4
0
    def search_for_keys_in_task_memory(self, vmaddr, pm_cr3, mempath):
        proc_pae = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)

        print '[*] Search for keys in range 0x%.8x-0x%.8x'%(vmaddr[0], vmaddr[1])

        if proc_pae.is_valid_address(vmaddr[0]):
            fvVer = struct.unpack('=I', proc_pae.read(vmaddr[0], 4))[0] # maybe 2
            keylen = struct.unpack('=I', proc_pae.read(vmaddr[0]+4, 4))[0] # maybe 0x10
            if not keylen == 0x10:
                return
            
            Key = struct.unpack('=16s', proc_pae.read(vmaddr[0]+8, keylen))[0] # maybe 0x10

            Vmk1 = proc_pae.read(vmaddr[0]+0x90, 16)
            Vmk2 = proc_pae.read(vmaddr[0]+0x430+0x90, 16)

            if not Key or Key != Vmk1[:keylen]:
                return
            if Vmk1 == Vmk2:
                self.candidate_key_list.append(proc_pae.read(vmaddr[0]+0x90, 16*11))
コード例 #5
0
    def get_mach_dump(self, vm_list, vm_struct, pid_process_name, mempath, pm_cr3):

        #print '[+] Resetting the Page Mapping Table: 0x%x'%pm_cr3
        
        # init page table
        procmem = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)

        dump_start = 0

        mach_vme_list = []
        for vme_info in vm_list:

            if procmem.is_valid_address(vme_info[0]):
                mach_header = _procmemcpy(procmem, vme_info[0], _MACH_HEADER)
            else:
                continue


            if mach_header.MH_MAGIC_X86 == mach_header.magic and FILE_MACH_EXECUTE == int(mach_header.filetype):
                print ' [-] Find 32 bit Mach-O signature at %.8x'%vme_info[0]
                
                self.mach_32bit = 1

            elif mach_header.MH_MAGIC_X64 == mach_header.magic and FILE_MACH_EXECUTE == int(mach_header.filetype):
                print ' [-] Find 64 bit Mach-O signature at %.8x'%vme_info[0]

                self.mach_32bit = 0

            else:
                print ' [-] Invalid Header at %.8x'%vme_info[0]
                continue

            fileoff = vme_info[0]
            
            # dump start offset
            dump_start = vme_info[0]

            # get load command offset
            loadcmdoff = 0
            if self.mach_32bit:
                loadcmdoff = fileoff + sizeof(_MACH_HEADER)
            else:
                loadcmdoff = fileoff + sizeof(_MACH_HEADER_64)

            #loadcommand_offset = file_offset+SIZEOFMACHOHEADER

            for cmdcount in xrange(0, mach_header.ncmds):
                if self.mach_32bit:
                    segment_command = _procmemcpy(procmem, loadcmdoff, _SEGMENT_COMMAND)
                else:
                    segment_command = _procmemcpy(procmem, loadcmdoff, _SEGMENT_COMMAND_64)

                if str(segment_command.segname).split('\x00')[0] == '__PAGEZERO':
                    self.difference = fileoff - segment_command.vmsize
                    loadcmdoff = loadcmdoff + segment_command.cmdsize
                    continue

                if segment_command.cmd == TYPE_SEGMENT or segment_command.cmd == TYPE_SEGMENT64:
                    if str(segment_command.segname).split('\x00')[0] == '__PAGEZERO':
                        self.difference = fileoff - segment_command.vmsize
                        loadcmdoff = loadcmdoff + segment_command.cmdsize
                        continue
                    
                    #mach_vme_info = []
                    vmstart = segment_command.vmaddr+self.difference
                    vmend = segment_command.vmsize+segment_command.vmaddr+self.difference

                    mach_vme_list.append([vmstart, vmend])

                loadcmdoff = loadcmdoff + segment_command.cmdsize
            break

        dumpfilename = '%s-%x'%(pid_process_name, dump_start)
        file = open(dumpfilename, mode="wb")
        for vme in mach_vme_list:
            print ' [-] from %.8x to %.8x'%(vme[0], vme[1])
            nop_code = 0x00
            pk_nop_code = struct.pack('=B', nop_code)
            nop = pk_nop_code*0x1000

            nop_flag = 1
            writebuf = ''
            for i in xrange(vme[0], vme[1], 0x1000):
                raw_data = 0x00
                if not(procmem.is_valid_address(i)):
                    if nop_flag == 1:
                        raw_data = nop
                        writebuf += raw_data
                    continue
                raw_data = procmem.read(i, 0x1000)
                if raw_data is None:
                    if nop_flag == 1:
                        raw_data = nop
                        writebuf += raw_data
                    continue
                writebuf += raw_data
                nop_flag = 1
            file.write(writebuf[:vme[1] - vme[0]])
        
        file.close()   
        
        print ' [-] [DUMP] Image Name: %s-%x'%(pid_process_name, dump_start)
        print '[+] Process Dump End'

        self.reloc(dumpfilename)

        return
コード例 #6
0
ファイル: machdump.py プロジェクト: ohio813/volafox
    def get_mach_dump(self, vm_list, vm_struct, pid_process_name, mempath,
                      pm_cr3):

        #print '[+] Resetting the Page Mapping Table: 0x%x'%pm_cr3

        proc_pae = IA32PML4MemoryPae(FileAddressSpace(mempath), pm_cr3)

        #print '[+] Process Dump Start'
        MH_MAGIC_X86 = 'feedface'
        MH_MAGIC_X64 = 'feedfacf'

        MACHHEADER_32 = 'IIIIIII'
        SIZEOFMACHOHEADER_32 = 28  # bytes
        MACHHEADER_64 = 'IIIIIIII'
        SIZEOFMACHOHEADER_64 = 32  # bytes
        MACHHEADER = MACHHEADER_32
        SIZEOFMACHOHEADER = SIZEOFMACHOHEADER_32

        COMMAND_32 = 'II16sIIII'
        COMMAND_64 = 'II16sQQQQ'
        SIZEOFCOMMAND_32 = 40  # bytes
        SIZEOFCOMMAND_64 = 56  # bytes
        TYPE_SEGMENT = 0x01
        TYPE_SEGMENT64 = 0x19
        FILE_MACH_EXECUTE = 0x02

        dump_start = 0
        difference = 0
        mach_vme_list = []
        for vme_info in vm_list:
            try:
                machoheader_t = proc_pae.read(
                    vme_info[0], SIZEOFMACHOHEADER)  # read 0x1c bytes
                machoheader = struct.unpack(MACHHEADER, machoheader_t)
            except:
                continue
            strHex = '%x' % machoheader[0]
            if MH_MAGIC_X86 == strHex and FILE_MACH_EXECUTE == machoheader[3]:
                print ' [-] Find 32 bit Mach-O signature at %.8x' % vme_info[0]
                COMMAND = COMMAND_32
                SIZEOFCOMMAND = SIZEOFCOMMAND_32
                MACHHEADER = MACHHEADER_32
                SIZEOFMACHOHEADER = SIZEOFMACHOHEADER_32

            elif MH_MAGIC_X64 == strHex and FILE_MACH_EXECUTE == machoheader[3]:
                print ' [-] Find 64 bit Mach-O signature at %.8x' % vme_info[0]
                COMMAND = COMMAND_64
                SIZEOFCOMMAND = SIZEOFCOMMAND_64
                MACHHEADER = MACHHEADER_64
                SIZEOFMACHOHEADER = SIZEOFMACHOHEADER_64

            else:
                continue

            file_offset = vme_info[0]
            dump_start = file_offset
            loadcommand_offset = file_offset + SIZEOFMACHOHEADER

            for num_load_command in range(0, machoheader[4]):
                loadcommand_t = proc_pae.read(loadcommand_offset,
                                              SIZEOFCOMMAND)  # 'II16sII'
                loadcommand = struct.unpack(COMMAND, loadcommand_t)
                if loadcommand[2].split('\x00')[0] == '__PAGEZERO':
                    difference = dump_start - loadcommand[4]
                    loadcommand_offset = loadcommand_offset + loadcommand[1]
                    continue
                if loadcommand[0] == TYPE_SEGMENT or loadcommand[
                        0] == TYPE_SEGMENT64:
                    if loadcommand[2].split('\x00')[0] == '__PAGEZERO':
                        difference = dump_start - loadcommand[4]
                        loadcommand_offset = loadcommand_offset + loadcommand[1]
                        continue
                    mach_vme_info = []
                    mach_vme_info.append(loadcommand[3] + difference)
                    mach_vme_info.append(loadcommand[6] + loadcommand[3] +
                                         difference)
                    mach_vme_list.append(mach_vme_info)
                loadcommand_offset = loadcommand_offset + loadcommand[1]
            break

        file = open('%s-%x' % (pid_process_name, dump_start), mode="wb")
        for mach_vme_info in mach_vme_list:
            print ' [-] from %.8x to %.8x' % (mach_vme_info[0],
                                              mach_vme_info[1])
            nop_code = 0x00
            pk_nop_code = struct.pack('=B', nop_code)
            nop = pk_nop_code * 0x1000

            nop_flag = 0
            writebuf = ''
            for i in range(mach_vme_info[0], mach_vme_info[1], 0x1000):
                raw_data = 0x00
                if not (proc_pae.is_valid_address(i)):
                    if nop_flag == 1:
                        raw_data = nop
                        writebuf += raw_data
                    continue
                raw_data = proc_pae.read(i, 0x1000)
                if raw_data is None:
                    if nop_flag == 1:
                        raw_data = nop
                        writebuf += raw_data
                    continue
                writebuf += raw_data
                nop_flag = 1
            file.write(writebuf[:mach_vme_info[1] - mach_vme_info[0]])

        file.close()

        print ' [-] [DUMP] Image Name: %s-%x' % (pid_process_name, dump_start)
        print '[+] Process Dump End'
        return