def memory_search( pid, bytes ): # Instance a Process object. process = Process( pid ) # Search for the string in the process memory. for address in process.search_bytes( bytes ): # Print the memory address where it was found. print HexDump.address( address )
def handler(self, event): if ( event.get_event_code() == win32.EXCEPTION_DEBUG_EVENT and event.get_exception_code() != win32.STATUS_BREAKPOINT and (event.is_last_chance() or event.get_exception_code() in self.alwaysCatchExceptions) ): crash = Crash(event) report = CrashReport() crash = Crash(event) (exploitable, type, info) = crash.isExploitable() try: report.code = event.get_thread().disassemble(crash.pc, 0x10)[0][2] except: report.code = "Could not disassemble" if crash.faultAddress is None or MemoryAddresses.align_address_to_page_start(crash.faultAddress) == 0: report.nearNull = True else: report.nearNull = False report.type = type lib = event.get_thread().get_process().get_module_at_address(crash.pc) if lib != None: report.location = lib.get_label_at_address(crash.pc) else: report.location = HexDump.address(crash.pc, event.get_thread().get_process().get_bits())[-4:] if crash.faultAddress == None: crash.faultAddress = 0 report.faultAddr = HexDump.address(crash.faultAddress, event.get_thread().get_process().get_bits()) report.stack = "" stList = self.getStackTraceRelList(event.get_thread()) if len(stList) > 0: for ra in stList: lib = event.get_thread().get_process().get_module_at_address(ra) if lib != None: report.stack += ( lib.get_label_at_address(ra) + " " + HexDump.address(ra, event.get_thread().get_process().get_bits()) + "\n" ) else: report.stack += HexDump.address(ra, event.get_thread().get_process().get_bits()) + "\n" if report.stack == "": report.stack = "NO_STACK" report.info = crash.fullReport() return report return None
def do(self, arg): ".exchain - Show the SEH chain" thread = self.get_thread_from_prefix() print("Exception handlers for thread %d" % thread.get_tid()) table = Table() table.addRow("Block", "Function") bits = thread.get_bits() for (seh, seh_func) in thread.get_seh_chain(): if seh is not None: seh = HexDump.address(seh, bits) if seh_func is not None: seh_func = HexDump.address(seh_func, bits) table.addRow(seh, seh_func) print(table.getOutput())
def single_step( self, event ): # Show the user where we're running. thread = event.get_thread() pc = thread.get_pc() code = thread.disassemble( pc, 0x10 ) [0] bits = event.get_process().get_bits() print "%s: %s" % ( HexDump.address(code[0], bits), code[2].lower() )
def log_eip_callback(event): ''' This will be called when our breakpoint is hit. It writes the current EIP. @param event: Event information, dough! ''' address = event.get_thread().get_pc() fd.write(HexDump.address(address) + '\n')
def single_step(self, event): thread = event.get_thread() pc = thread.get_pc() code = thread.disassemble(pc, 0x10)[0] trace_file = open(os.path.join(TRACE_PATH, "%s.csv" % event.get_pid()), "a") trace_file.write("\"0x%s\",\"%s\"\n" % (HexDump.address(code[0]), code[2])) trace_file.close()
def my_event_handler( event ): # Get the event name. name = event.get_event_name() # Get the event code. code = event.get_event_code() # Get the process ID where the event occured. pid = event.get_pid() # Get the thread ID where the event occured. tid = event.get_tid() # Get the value of EIP at the thread. pc = event.get_thread().get_pc() # Show something to the user. bits = event.get_process().get_bits() format_string = "%s (%s) at address %s, process %d, thread %d" message = format_string % ( name, HexDump.integer(code, bits), HexDump.address(pc, bits), pid, tid ) print message # If the event is a crash... if code == win32.EXCEPTION_DEBUG_EVENT and event.is_last_chance(): print "Crash detected, storing crash dump in database..." # Generate a minimal crash dump. crash = Crash( event ) # You can turn it into a full crash dump (recommended). # crash.fetch_extra_data( event, takeMemorySnapshot = 0 ) # no memory dump # crash.fetch_extra_data( event, takeMemorySnapshot = 1 ) # small memory dump crash.fetch_extra_data( event, takeMemorySnapshot = 2 ) # full memory dump # Connect to the database. You can use any URL supported by SQLAlchemy. # For more details see the reference documentation. dao = CrashDAO( "sqlite:///crashes.sqlite" ) #dao = CrashDAO( "mysql+MySQLdb://root:toor@localhost/crashes" ) # Store the crash dump in the database. dao.add( crash ) # If you do this instead, heuristics are used to detect duplicated # crashes so they aren't added to the database. # dao.add( crash, allow_duplicates = False ) # You can also launch the interactive debugger from here. Try it! :) # event.debug.interactive() # Kill the process. event.get_process().kill()
def my_event_handler( event ): # Get the process ID where the event occured. pid = event.get_pid() # Get the thread ID where the event occured. tid = event.get_tid() # Find out if it's a 32 or 64 bit process. bits = event.get_process().get_bits() # Get the value of EIP at the thread. address = event.get_thread().get_pc() # Get the event name. name = event.get_event_name() # Get the event code. code = event.get_event_code() # If the event is an exception... if code == win32.EXCEPTION_DEBUG_EVENT: # Get the exception user-friendly description. name = event.get_exception_description() # Get the exception code. code = event.get_exception_code() # Get the address where the exception occurred. try: address = event.get_fault_address() except NotImplementedError: address = event.get_exception_address() # If the event is a process creation or destruction, # or a DLL being loaded or unloaded... elif code in ( win32.CREATE_PROCESS_DEBUG_EVENT, win32.EXIT_PROCESS_DEBUG_EVENT, win32.LOAD_DLL_DEBUG_EVENT, win32.UNLOAD_DLL_DEBUG_EVENT ): # Get the filename. filename = event.get_filename() if filename: name = "%s [%s]" % ( name, filename ) # Show a descriptive message to the user. print "-" * 79 format_string = "%s (0x%s) at address 0x%s, process %d, thread %d" message = format_string % ( name, HexDump.integer(code, bits), HexDump.address(address, bits), pid, tid ) print message
def strings( pid ): # Instance a Process object. process = Process( pid ) # For each ASCII string found in the process memory... for address, size, data in process.strings(): # Print the string and the memory address where it was found. print "%s: %s" % ( HexDump.address(address), data )
def accessed( self, event ): # Show the user where we're running. thread = event.get_thread() pc = thread.get_pc() code = thread.disassemble( pc, 0x10 ) [0] print "%s: %s" % ( HexDump.address(code[0], thread.get_bits()), code[2].lower() )
def entering( event ): # Get the thread object. thread = event.get_thread() # Get the thread ID. tid = thread.get_tid() # Get the return address location (the top of the stack). stack_top = thread.get_sp() # Get the return address and the parameters from the stack. bits = event.get_process().get_bits() if bits == 32: return_address, hModule, lpProcName = thread.read_stack_dwords( 3 ) else: return_address = thread.read_stack_qwords( 1 ) registers = thread.get_context() hModule = registers['Rcx'] lpProcName = registers['Rdx'] # Get the string from the process memory. procedure_name = event.get_process().peek_string( lpProcName ) # Show a message to the user. message = "%s: GetProcAddress(%s, %r);" print message % ( HexDump.address(return_address, bits), HexDump.address(hModule, bits), procedure_name ) # Watch the DWORD at the top of the stack. try: event.debug.stalk_variable( tid, stack_top, 4, returning ) #event.debug.watch_variable( tid, stack_top, 4, returning ) # If no more slots are available, set a code breakpoint at the return address. except RuntimeError: event.debug.stalk_at( event.get_pid(), return_address, returning_2 )
def print_threads_and_modules(pid): # Instance a Process object. process = Process(pid) print "Process %d" % process.get_pid() # Now we can enumerate the threads in the process... print "Threads:" for thread in process.iter_threads(): print "\t%d" % thread.get_tid() # ...and the modules in the process. print "Modules:" bits = process.get_bits() for module in process.iter_modules(): print "\t%s\t%s" % (HexDump.address(module.get_base(), bits), module.get_filename())
def print_threads_and_modules(pid): process = Process(pid) print "Process %d" % process.get_pid() print "Threads:" for thread in process.iter_threads(): print "\t %d" % thread.get_tid() print "Modules:" bits = process.get_bits() for module in process.iter_modules(): print "\t%s\t%s" % (HexDump.address(module.get_base(), bits), module.get_filename())
def entering(event): # Get the thread object. thread = event.get_thread() # Get the thread ID. tid = thread.get_tid() # Get the return address location (the top of the stack). stack_top = thread.get_sp() # Get the return address and the parameters from the stack. bits = event.get_process().get_bits() if bits == 32: return_address, hModule, lpProcName = thread.read_stack_dwords(3) else: return_address = thread.read_stack_qwords(1) registers = thread.get_context() hModule = registers['Rcx'] lpProcName = registers['Rdx'] # Get the string from the process memory. procedure_name = event.get_process().peek_string(lpProcName) # Show a message to the user. message = "%s: GetProcAddress(%s, %r);" print(message % (HexDump.address( return_address, bits), HexDump.address(hModule, bits), procedure_name)) # Watch the DWORD at the top of the stack. try: event.debug.stalk_variable(tid, stack_top, 4, returning) #event.debug.watch_variable( tid, stack_top, 4, returning ) # If no more slots are available, set a code breakpoint at the return address. except RuntimeError: event.debug.stalk_at(event.get_pid(), return_address, returning_2)
def print_threads_and_modules( pid ): # Instance a Process object. process = Process( pid ) print "Process %d" % process.get_pid() # Now we can enumerate the threads in the process... print "Threads:" for thread in process.iter_threads(): print "\t%d" % thread.get_tid() # ...and the modules in the process. print "Modules:" bits = process.get_bits() for module in process.iter_modules(): print "\t%s\t%s" % ( HexDump.address( module.get_base(), bits ), module.get_filename() )
def message(self, pid, address, data=None): if self.start < 0: raise StopIteration count = self.count + 1 # NOQA address = address + self.start where = HexDump.address(address) # NOQA size = self.end - self.start # NOQA msg = self.showfmt % vars() if data is not None: msg += "\n" p = self.start & (~0xF) q = (self.end & (~0xF)) + 0x10 msg += HexDump.hexblock(data[p:q], address & (~0xF)) if msg.endswith('\n'): msg = msg[:-len('\n')] return msg
def action_callback( event ): process = event.get_process() thread = event.get_thread() # Get the address of the top of the stack. stack = thread.get_sp() # Get the return address of the call. address = process.read_pointer( stack ) # Get the process and thread IDs. pid = event.get_pid() tid = event.get_tid() # Show a message to the user. message = "kernel32!CreateFileW called from %s by thread %d at process %d" print message % ( HexDump.address(address, process.get_bits()), tid, pid )
def action_callback(event): process = event.get_process() thread = event.get_thread() # Get the address of the top of the stack. stack = thread.get_sp() # Get the return address of the call. address = process.read_pointer(stack) # Get the process and thread IDs. pid = event.get_pid() tid = event.get_tid() # Show a message to the user. message = "kernel32!CreateFileW called from %s by thread %d at process %d" print message % (HexDump.address(address, process.get_bits()), tid, pid)
def print_threads_and_modules(pid, debug): # Instance a Process object. process = Process(pid) print "Process %d" % process.get_pid() # Now we can enumerate the threads in the process... print "Threads:" for thread in process.iter_threads(): print "\t%d" % thread.get_tid() # ...and the modules in the process. print "Modules:" bits = process.get_bits() for module in process.iter_modules(): print "\thas module: %s\t%s" % (HexDump.address( module.get_base(), bits), module.get_filename()) print "Breakpoints:" for i in debug.get_all_breakpoints(): bp = i[2] print "breakpoint: %s %x" % (bp.get_state_name(), bp.get_address())
def print_alnum_jump_addresses(pid): # Request debug privileges so we can inspect the memory of services too. System.request_debug_privileges() # Suspend the process so there are no malloc's and free's while iterating. process = Process(pid) process.suspend() try: # For each executable alphanumeric address... for address, packed, module in iterate_alnum_jump_addresses(process): # Format the address for printing. numeric = HexDump.address(address, process.get_bits()) ascii = repr(packed) # Format the module name for printing. if module: modname = module.get_name() else: modname = "" # Try to disassemble the code at this location. try: code = process.disassemble(address, 16)[0][2] except NotImplementedError: code = "" # Print it. print numeric, ascii, modname, code # Resume the process when we're done. # This is inside a "finally" block, so if the program is interrupted # for any reason we don't leave the process suspended. finally: process.resume()
def print_threads_and_modules( pid, debug ): # Instance a Process object. process = Process( pid ) print "Process %d" % process.get_pid() # Now we can enumerate the threads in the process... print "Threads:" for thread in process.iter_threads(): print "\t%d" % thread.get_tid() # ...and the modules in the process. print "Modules:" bits = process.get_bits() for module in process.iter_modules(): print "\thas module: %s\t%s" % ( HexDump.address( module.get_base(), bits ), module.get_filename() ) print "Breakpoints:" for i in debug.get_all_breakpoints(): bp = i[2] print "breakpoint: %s %x" % (bp.get_state_name(), bp.get_address())
def strings(pid): process = Process(pid) for address, size, data in process.strings(): print "%s: %s" % (HexDump.address(address), data)
def hexaddr(address, bits): return HexDump.address(address, bits)
pid = HexInput.integer(sys.argv[1]) except Exception, e: s = System() s.scan_processes() pl = s.find_processes_by_filename(sys.argv[1]) if not pl: print "Process not found: %s" % sys.argv[1] return if len(pl) > 1: print "Multiple processes found for %s" % sys.argv[1] for p, n in pl: print "\t%s: %s" % (p.get_pid(), n) return pid = pl[0][0].get_pid() s.clear() del s p = Process(pid) for address, size, data in p.strings(): if data.endswith('\0'): data = data[:-1] print "%s: %r" % (HexDump.address(address), data) if __name__ == '__main__': try: import psyco psyco.bind(main) except ImportError: pass main()
s = System() s.scan_processes() pl = s.find_processes_by_filename(sys.argv[1]) if not pl: print "Process not found: %s" % sys.argv[1] return if len(pl) > 1: print "Multiple processes found for %s" % sys.argv[1] for p, n in pl: print "\t%s: %s" % (p.get_pid(), n) return pid = pl[0][0].get_pid() s.clear() del s p = Process(pid) for address, size, data in p.strings(): if data.endswith("\0"): data = data[:-1] print "%s: %r" % (HexDump.address(address), data) if __name__ == "__main__": try: import psyco psyco.bind(main) except ImportError: pass main()
def do_search(self): # For each target process... for self.pid in self.targets: # Try to open the process, skip on error try: self.process = Process(self.pid) self.process.get_handle() except WindowsError: print("Can't open process %d, skipping" % self.pid) if self.options.verbose: print continue # Get a list of allocated memory regions memory = list() for mbi in self.process.get_memory_map(): if mbi.State == win32.MEM_COMMIT and \ not mbi.Protect & win32.PAGE_GUARD: memory.append((mbi.BaseAddress, mbi.RegionSize)) # If no allocation limit is set, # read entire regions and search on them if self.options.memory_pages <= 0: for (address, size) in memory: try: data = self.process.read(address, size) except WindowsError as e: begin = HexDump.address(address) end = HexDump.address(address + size) msg = "Error reading %s-%s: %s" msg = msg % (begin, end, str(e)) print(msg) if self.options.verbose: print continue self.search_block(data, address, 0) # If an allocation limit is set, # read blocks within regions to search else: step = self.system.pageSize size = step * self.options.memory_pages for (address, total_size) in memory: try: end = address + total_size shift = 0 buffer = self.process.read(address, min(size, total_size)) while 1: self.search_block(buffer, address, shift) shift = step address = address + step if address >= end: break buffer = buffer[step:] buffer = buffer + self.process.read(address, step) except WindowsError as e: begin = HexDump.address(address) end = HexDump.address(address + total_size) msg = "Error reading %s-%s: %s" msg = msg % (begin, end, str(e)) print(msg) if self.options.verbose: print
base_addr = mM.baseAddress reg_size = mM.RegionSize #pattern = "00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ?0 ?4 ?? 00 ?? 00 00 00" pattern = "00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ?0 ?4 ?? 00 ?? 00 00 00 ?? ?? ?? ?? ?? ?? ?? ??" f_data = process.search_hexa(pattern, base_addr, base_addr + reg_size) try: enc_con_addr = f_data.next()[0] + 0x18 except: print "Not found" exit() print "[*] Encrypted config address: 0x%s" % HexDump.address( enc_con_addr, 32) enc_con = process.read(enc_con_addr, 0x2EF) RC4_key = process.read(enc_con_addr + 0x2EF, 0x39).rstrip('\x00') print "[*] RC4 key: %s" % RC4_key dec_con = RC4_dec(RC4_key, enc_con) conf = re.split("\x00+", dec_con) print "[*] Config: " for s in conf: print s print "[*] Dumping PE" PE_dump_path = "tmp_pe_dump" PE_dump = process.read(base_addr, reg_size) tmp_file = open(PE_dump_path, "wb+") tmp_file.write(PE_dump) tmp_file.close()
def action_callback_create_process(event): print('hit break') global c2_list, cfg, rsa_pub_key process = event.get_process() thread = event.get_thread() # Get the address of the top of the stack. stack = thread.get_sp() # Get the return address of the call. ret_address = process.read_pointer(stack) print('caller addr:{:08x}'.format(ret_address)) # Get the process and thread IDs. pid = event.get_pid() tid = event.get_tid() extract_done = False failed_reason = 'unknown' max_c2_counter = 400 shell_data = 0 sig_addr_list = [] for address, data in process.search_hexa('68 00 80 00 00 6a 6a 68'): # Print a hex dump for each memory location found. if ret_address & 0xFFFF0000 == address & 0xFFFF0000: print('hit sig at:') print(HexDump.hexblock(data, address=address)) sig_addr_list.append(address) memoryMap = process.get_memory_map() mappedFilenames = process.get_mapped_filenames(memoryMap) # For each memory block in the map... for mbi in memoryMap: # Address and size of memory block. BaseAddress = mbi.BaseAddress RegionSize = mbi.RegionSize for address in sig_addr_list: if address > BaseAddress and address < BaseAddress + RegionSize: print('Hit shell code block!\n{:08x}\t{:08x}'.format( BaseAddress, RegionSize)) shell_data = process.read(BaseAddress, RegionSize) # no hit, just kill and return if shell_data != 0: # dump shell code block print('dump shell code!') with open('shell.dump', 'wb') as fh: fh.write(shell_data) # dump final payload dump_pe_path = 'pe.dump' pe_offset = shell_data.find('\x4D\x5A\x90') print('dump final payload!') with open(dump_pe_path, 'wb') as fh: fh.write(shell_data[pe_offset:]) print('\n-----------------------------') c2_list, rsa_pub_key = extract_ioc(dump_pe_path, 0x400000) print('\nc2 list:') for c2 in c2_list: print('{}'.format(c2)) print('\nrsa key:\n{}'.format(rsa_pub_key)) # Show a message to the user. message = "kernel32!CreateProcessW called from %s by thread %d at process %d" print message % (HexDump.address(ret_address, process.get_bits()), tid, pid) process.kill()
def openProc(pid): ''' return proc maps ''' process = Process(pid) fileName = process.get_filename() memoryMap = process.get_memory_map() mappedFilenames = process.get_mapped_filenames() # 08048000-080b0000 r-xp 0804d000 fe:01 3334030 /usr/myfile lines = [] for mbi in memoryMap: if not mbi.is_readable(): continue addr = '' perm = '--- ' offset = '' device = '' inode = '' filename = '' # Address and size of memory block. BaseAddress = HexDump.address(mbi.BaseAddress) RegionSize = HexDump.address(mbi.RegionSize) # State (free or allocated). mbiState = mbi.State if mbiState == win32.MEM_RESERVE: State = "Reserved" elif mbiState == win32.MEM_COMMIT: State = "Commited" elif mbiState == win32.MEM_FREE: State = "Free" else: State = "Unknown" # Page protection bits (R/W/X/G). if mbiState != win32.MEM_COMMIT: Protect = "--- " else: mbiProtect = mbi.Protect if mbiProtect & win32.PAGE_NOACCESS: Protect = "--- " elif mbiProtect & win32.PAGE_READONLY: Protect = "R-- " elif mbiProtect & win32.PAGE_READWRITE: Protect = "RW- " elif mbiProtect & win32.PAGE_WRITECOPY: Protect = "RC- " elif mbiProtect & win32.PAGE_EXECUTE: Protect = "--X " elif mbiProtect & win32.PAGE_EXECUTE_READ: Protect = "R-X " elif mbiProtect & win32.PAGE_EXECUTE_READWRITE: Protect = "RWX " elif mbiProtect & win32.PAGE_EXECUTE_WRITECOPY: Protect = "RCX " else: Protect = "??? " ''' if mbiProtect & win32.PAGE_GUARD: Protect += "G" #else: # Protect += "-" if mbiProtect & win32.PAGE_NOCACHE: Protect += "N" #else: # Protect += "-" if mbiProtect & win32.PAGE_WRITECOMBINE: Protect += "W" #else: # Protect += "-" ''' perm = Protect # Type (file mapping, executable image, or private memory). mbiType = mbi.Type if mbiType == win32.MEM_IMAGE: Type = "Image" elif mbiType == win32.MEM_MAPPED: Type = "Mapped" elif mbiType == win32.MEM_PRIVATE: Type = "Private" elif mbiType == 0: Type = "" else: Type = "Unknown" log.debug(BaseAddress) addr = '%08x-%08x' % (int(BaseAddress, 16), int(BaseAddress, 16) + int(RegionSize, 16)) perm = perm.lower() offset = '00000000' device = 'fe:01' inode = 24422442 filename = mappedFilenames.get(mbi.BaseAddress, ' ') # 08048000-080b0000 r-xp 0804d000 fe:01 3334030 /usr/myfile lines.append( '%s %s %s %s %s %s\n' % (addr, perm, offset, device, inode, filename)) log.debug( '%s %s %s %s %s %s\n' % (addr, perm, offset, device, inode, filename)) ##generate_memory_snapshot(self, minAddr=None, maxAddr=None) return lines # process.suspend() # try: # snapshot = process.generate_memory_snapshot() # for mbi in snapshot: # print HexDump.hexblock(mbi.content, mbi.BaseAddress) # finally: # process.resume() # process.read_structure() process = Process(pid) fileName = process.get_filename() memoryMap = process.get_memory_map() mappedFilenames = process.get_mapped_filenames() if fileName: log.debug("MemoryHandler map for %d (%s):" % (pid, fileName)) else: log.debug("MemoryHandler map for %d:" % pid) log.debug('%d filenames' % len(mappedFilenames)) log.debug('') log.debug('%d memorymap' % len(memoryMap)) readable = 0 writeable = 0 executable = 0 private = 0 mapped = 0 image = 0 total = 0 for mbi in memoryMap: size = mbi.RegionSize if not mbi.is_free(): total += size if mbi.is_readable(): readable += size if mbi.is_writeable(): writeable += size if mbi.is_executable(): executable += size if mbi.is_private(): private += size if mbi.is_mapped(): mapped += size if mbi.is_image(): image += size width = len(str(total)) log.debug(" %%%ds bytes of readable memory" % width) % int(readable) log.debug(" %%%ds bytes of writeable memory" % width) % int(writeable) log.debug(" %%%ds bytes of executable memory" % width) % int(executable) log.debug(" %%%ds bytes of private memory" % width) % int(private) log.debug(" %%%ds bytes of mapped memory" % width) % int(mapped) log.debug(" %%%ds bytes of image memory" % width) % int(image) log.debug(" %%%ds bytes of total memory" % width) % int(total) log.debug('') return
def print_memory_map( pid ): # Instance a Process object. process = Process( pid ) # Find out if it's a 32 or 64 bit process. bits = process.get_bits() # Get the process memory map. memoryMap = process.get_memory_map() # Now you could do this... # # from winappdbg import CrashDump # print CrashDump.dump_memory_map( memoryMap ), # # ...but let's do it the hard way: # For each memory block in the map... print "Address \tSize \tState \tAccess \tType" for mbi in memoryMap: # Address and size of memory block. BaseAddress = HexDump.address(mbi.BaseAddress, bits) RegionSize = HexDump.address(mbi.RegionSize, bits) # State (free or allocated). if mbi.State == win32.MEM_RESERVE: State = "Reserved " elif mbi.State == win32.MEM_COMMIT: State = "Commited " elif mbi.State == win32.MEM_FREE: State = "Free " else: State = "Unknown " # Page protection bits (R/W/X/G). if mbi.State != win32.MEM_COMMIT: Protect = " " else: ## Protect = "0x%.08x" % mbi.Protect if mbi.Protect & win32.PAGE_NOACCESS: Protect = "--- " elif mbi.Protect & win32.PAGE_READONLY: Protect = "R-- " elif mbi.Protect & win32.PAGE_READWRITE: Protect = "RW- " elif mbi.Protect & win32.PAGE_WRITECOPY: Protect = "RC- " elif mbi.Protect & win32.PAGE_EXECUTE: Protect = "--X " elif mbi.Protect & win32.PAGE_EXECUTE_READ: Protect = "R-X " elif mbi.Protect & win32.PAGE_EXECUTE_READWRITE: Protect = "RWX " elif mbi.Protect & win32.PAGE_EXECUTE_WRITECOPY: Protect = "RCX " else: Protect = "??? " if mbi.Protect & win32.PAGE_GUARD: Protect += "G" else: Protect += "-" if mbi.Protect & win32.PAGE_NOCACHE: Protect += "N" else: Protect += "-" if mbi.Protect & win32.PAGE_WRITECOMBINE: Protect += "W" else: Protect += "-" Protect += " " # Type (file mapping, executable image, or private memory). if mbi.Type == win32.MEM_IMAGE: Type = "Image " elif mbi.Type == win32.MEM_MAPPED: Type = "Mapped " elif mbi.Type == win32.MEM_PRIVATE: Type = "Private " elif mbi.Type == 0: Type = "Free " else: Type = "Unknown " # Print the memory block information. fmt = "%s\t%s\t%s\t%s\t%s" print fmt % ( BaseAddress, RegionSize, State, Protect, Type )
def print_memory_map(pid): process = Process(pid) bits = process.get_bits() memoryMap = process.get_memory_map() #print CrashDump.dump_memory_dump(memoryMap) print "Address \tSize \tState \tAccess \Type" for mbi in memoryMap: # Address and size of memory block BaseAddress = HexDump.address(mbi.BaseAddress, bits) RegionSize = HexDump.address(mbi.RegionSize, bits) if mbi.State == win32.MEM_RESERVE: State = "Reserved " elif mbi.State == win32.MEM_COMMIT: State = "commited " elif mbi.State == win32.MEM_FREE: State = "Free " else: State = "Unknown " if mbi.State != win32.MEM_COMMIT: Protect = " " else: ## Protect = "0x%.08x" % mbi.Protect if mbi.Protect & win32.PAGE_NOACCESS: Protect = "--- " elif mbi.Protect & win32.PAGE_READONLY: Protect = "R-- " elif mbi.Protect & win32.PAGE_READWRITE: Protect = "RW- " elif mbi.Protect & win32.PAGE_WRITECOPY: Protect = "RC- " elif mbi.Protect & win32.PAGE_EXECUTE: Protect = "--X " elif mbi.Protect & win32.PAGE_EXECUTE_READ: Protect = "R-X " elif mbi.Protect & win32.PAGE_EXECUTE_READWRITE: Protect = "RWX " elif mbi.Protect & win32.PAGE_EXECUTE_WRITECOPY: Protect = "RCX " else: Protect = "??? " if mbi.Protect & win32.PAGE_GUARD: Protect += "G" else: Protect += "-" if mbi.Protect & win32.PAGE_NOCACHE: Protect += "N" else: Protect += "-" if mbi.Protect & win32.PAGE_WRITECOMBINE: Protect += "W" else: Protect += "-" Protect += " " # Type (file mapping, executable image, or private memory). if mbi.Type == win32.MEM_IMAGE: Type = "Image " elif mbi.Type == win32.MEM_MAPPED: Type = "Mapped " elif mbi.Type == win32.MEM_PRIVATE: Type = "Private " elif mbi.Type == 0: Type = "Free " else: Type = "Unknown " # Print the memory block information. fmt = "%s\t%s\t%s\t%s\t%s" print fmt % (BaseAddress, RegionSize, State, Protect, Type)
def print_memory_map(pid): # Instance a Process object. process = Process(pid) # Find out if it's a 32 or 64 bit process. bits = process.get_bits() # Get the process memory map. memoryMap = process.get_memory_map() # Now you could do this... # # from winappdbg import CrashDump # print CrashDump.dump_memory_map( memoryMap ), # # ...but let's do it the hard way: # For each memory block in the map... print("Address \tSize \tState \tAccess \tType") for mbi in memoryMap: # Address and size of memory block. BaseAddress = HexDump.address(mbi.BaseAddress, bits) RegionSize = HexDump.address(mbi.RegionSize, bits) # State (free or allocated). if mbi.State == win32.MEM_RESERVE: State = "Reserved " elif mbi.State == win32.MEM_COMMIT: State = "Commited " elif mbi.State == win32.MEM_FREE: State = "Free " else: State = "Unknown " # Page protection bits (R/W/X/G). if mbi.State != win32.MEM_COMMIT: Protect = " " else: ## Protect = "0x%.08x" % mbi.Protect if mbi.Protect & win32.PAGE_NOACCESS: Protect = "--- " elif mbi.Protect & win32.PAGE_READONLY: Protect = "R-- " elif mbi.Protect & win32.PAGE_READWRITE: Protect = "RW- " elif mbi.Protect & win32.PAGE_WRITECOPY: Protect = "RC- " elif mbi.Protect & win32.PAGE_EXECUTE: Protect = "--X " elif mbi.Protect & win32.PAGE_EXECUTE_READ: Protect = "R-X " elif mbi.Protect & win32.PAGE_EXECUTE_READWRITE: Protect = "RWX " elif mbi.Protect & win32.PAGE_EXECUTE_WRITECOPY: Protect = "RCX " else: Protect = "??? " if mbi.Protect & win32.PAGE_GUARD: Protect += "G" else: Protect += "-" if mbi.Protect & win32.PAGE_NOCACHE: Protect += "N" else: Protect += "-" if mbi.Protect & win32.PAGE_WRITECOMBINE: Protect += "W" else: Protect += "-" Protect += " " # Type (file mapping, executable image, or private memory). if mbi.Type == win32.MEM_IMAGE: Type = "Image " elif mbi.Type == win32.MEM_MAPPED: Type = "Mapped " elif mbi.Type == win32.MEM_PRIVATE: Type = "Private " elif mbi.Type == 0: Type = "Free " else: Type = "Unknown " # Print the memory block information. fmt = "%s\t%s\t%s\t%s\t%s" print(fmt % (BaseAddress, RegionSize, State, Protect, Type))
def memory_search( process, bytes, ): # Search for the string in the process memory. for address in process.search_bytes( bytes ): # Print the memory address where it was found. print HexDump.address( address )
def openProc(pid): ''' return proc maps ''' process = Process(pid) fileName = process.get_filename() memoryMap = process.get_memory_map() mappedFilenames = process.get_mapped_filenames() # 08048000-080b0000 r-xp 0804d000 fe:01 3334030 /usr/myfile lines = [] for mbi in memoryMap: if not mbi.is_readable(): continue addr = '' perm = '--- ' offset = '' device = '' inode = '' filename = '' # Address and size of memory block. BaseAddress = HexDump.address(mbi.BaseAddress) RegionSize = HexDump.address(mbi.RegionSize) # State (free or allocated). mbiState = mbi.State if mbiState == win32.MEM_RESERVE: State = "Reserved" elif mbiState == win32.MEM_COMMIT: State = "Commited" elif mbiState == win32.MEM_FREE: State = "Free" else: State = "Unknown" # Page protection bits (R/W/X/G). if mbiState != win32.MEM_COMMIT: Protect = "--- " else: mbiProtect = mbi.Protect if mbiProtect & win32.PAGE_NOACCESS: Protect = "--- " elif mbiProtect & win32.PAGE_READONLY: Protect = "R-- " elif mbiProtect & win32.PAGE_READWRITE: Protect = "RW- " elif mbiProtect & win32.PAGE_WRITECOPY: Protect = "RC- " elif mbiProtect & win32.PAGE_EXECUTE: Protect = "--X " elif mbiProtect & win32.PAGE_EXECUTE_READ: Protect = "R-X " elif mbiProtect & win32.PAGE_EXECUTE_READWRITE: Protect = "RWX " elif mbiProtect & win32.PAGE_EXECUTE_WRITECOPY: Protect = "RCX " else: Protect = "??? " ''' if mbiProtect & win32.PAGE_GUARD: Protect += "G" #else: # Protect += "-" if mbiProtect & win32.PAGE_NOCACHE: Protect += "N" #else: # Protect += "-" if mbiProtect & win32.PAGE_WRITECOMBINE: Protect += "W" #else: # Protect += "-" ''' perm = Protect # Type (file mapping, executable image, or private memory). mbiType = mbi.Type if mbiType == win32.MEM_IMAGE: Type = "Image" elif mbiType == win32.MEM_MAPPED: Type = "Mapped" elif mbiType == win32.MEM_PRIVATE: Type = "Private" elif mbiType == 0: Type = "" else: Type = "Unknown" log.debug(BaseAddress) addr = '%08x-%08x' % (int( BaseAddress, 16), int(BaseAddress, 16) + int(RegionSize, 16)) perm = perm.lower() offset = '00000000' device = 'fe:01' inode = 24422442 filename = mappedFilenames.get(mbi.BaseAddress, ' ') # 08048000-080b0000 r-xp 0804d000 fe:01 3334030 /usr/myfile lines.append('%s %s %s %s %s %s\n' % (addr, perm, offset, device, inode, filename)) log.debug('%s %s %s %s %s %s\n' % (addr, perm, offset, device, inode, filename)) ##generate_memory_snapshot(self, minAddr=None, maxAddr=None) return lines # process.suspend() # try: # snapshot = process.generate_memory_snapshot() # for mbi in snapshot: # print HexDump.hexblock(mbi.content, mbi.BaseAddress) # finally: # process.resume() # process.read_structure() process = Process(pid) fileName = process.get_filename() memoryMap = process.get_memory_map() mappedFilenames = process.get_mapped_filenames() if fileName: log.debug("MemoryHandler map for %d (%s):" % (pid, fileName)) else: log.debug("MemoryHandler map for %d:" % pid) log.debug('%d filenames' % len(mappedFilenames)) log.debug('') log.debug('%d memorymap' % len(memoryMap)) readable = 0 writeable = 0 executable = 0 private = 0 mapped = 0 image = 0 total = 0 for mbi in memoryMap: size = mbi.RegionSize if not mbi.is_free(): total += size if mbi.is_readable(): readable += size if mbi.is_writeable(): writeable += size if mbi.is_executable(): executable += size if mbi.is_private(): private += size if mbi.is_mapped(): mapped += size if mbi.is_image(): image += size width = len(str(total)) log.debug(" %%%ds bytes of readable memory" % width) % int(readable) log.debug( " %%%ds bytes of writeable memory" % width) % int(writeable) log.debug( " %%%ds bytes of executable memory" % width) % int(executable) log.debug(" %%%ds bytes of private memory" % width) % int(private) log.debug(" %%%ds bytes of mapped memory" % width) % int(mapped) log.debug(" %%%ds bytes of image memory" % width) % int(image) log.debug(" %%%ds bytes of total memory" % width) % int(total) log.debug('') return
def memory_search(pid, bytes): process = Process(pid) for address in process.search_bytes( bytes): #process.search_text, process.search_hexa print HexDump.address(address)
if (version.major, version.minor, version.micro) != (2, 7, 6): print("Error: This program is written for Python 2.7.6") print("You are running:", version.major, ".", version.minor, ".", version.micro) exit(1) # Retrieves system snapshot and iterates through running tasks system = System() for task in system: task_name = task.get_filename() if task_name is None: continue if (task_name.find("firefox.exe") != -1) or (task_name.find("chrome.exe") != -1): # Obtains memory information about currently running browser process = Process(task.get_pid()) filename = "" if task_name.find("firefox.exe") != -1: filename = "firefox_output.txt" else: filename = "chrome_output.txt" with open(filename, "w") as f: # Extracts all string literals from memory # All strings are logged, while URLs are printed to terminal for address, size, data in process.strings(): tuple = (HexDump.address(address), HexDump.printable(data)) f.write(tuple[0] + "\t" + tuple[1] + "\n") if tuple[1].startswith( (r"http://", r"https://", r"HTTP-memory-only")): print tuple[0], "\t", tuple[1]