Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python Windows API dump process in buffer then REGEX search

Tags:

python

winapi

I have the following Python code using the Windows APIs to do a minidump of a process, works ok dumping to a file but I need a way to keep the dump in a memory buffer then do a REGEX search against it. Couldn't come out with a way other than dumping to a file. Any idea?

import win32security, win32con, win32api, win32file, ctypes
import re
from constants.structures import MINIDUMP_TYPES_CLASS

dbghelp = ctypes.windll.dbghelp 

def adjustPrivilege(priv):
    flags = win32security.TOKEN_ADJUST_PRIVILEGES | win32security.TOKEN_QUERY
    htoken =  win32security.OpenProcessToken(win32api.GetCurrentProcess(), flags)
    id = win32security.LookupPrivilegeValue(None, priv)
    newPrivileges = [(id, win32security.SE_PRIVILEGE_ENABLED)]
    win32security.AdjustTokenPrivileges(htoken, 0, newPrivileges)

def createMiniDump(pid, file_name):
    # Adjust privileges.
    #adjustPrivilege(win32security.SE_DEBUG_NAME)
    adjustPrivilege("seDebugPrivilege")
    pHandle = win32api.OpenProcess(
                win32con.PROCESS_VM_READ | win32con.PROCESS_QUERY_INFORMATION,
                0, pid)
    print 'pHandle Status: ', win32api.FormatMessage(win32api.GetLastError())
    fHandle = win32file.CreateFile(file_name,
                               win32file.GENERIC_READ | win32file.GENERIC_WRITE,
                               win32file.FILE_SHARE_READ | win32file.FILE_SHARE_WRITE,
                               None,
                               win32file.CREATE_ALWAYS,
                               win32file.FILE_ATTRIBUTE_NORMAL,
                               None)

    print 'fHandle Status: ', win32api.FormatMessage(win32api.GetLastError())
    success = dbghelp.MiniDumpWriteDump(pHandle.handle,   # Process handle
                                     pid,                 # Process ID
                                     fHandle.handle,      # File handle
                                     MINIDUMP_TYPES_CLASS.MiniDumpWithFullMemory,      # Dump type - MiniDumpNormal
                                     None,      # Exception parameter
                                     None,      # User stream parameter
                                     None,      # Callback parameter
                                     )

    #res_rx1 = ["REGEX_STRING"]
    #found_rx1 = []
    #for regex in res_rx1:
    #    found_rx1 += re.findall(regex, buffer, re.DOTALL|re.UNICODE)
    #    found_rx1 = list(set(found_rx1))
    #if len(found_rx1)>0:
    #    for line in found_rx1:
    #        print line
    print 'MiniDump Status: ', win32api.FormatMessage(win32api.GetLastError())
    return success

createMiniDump(1280, "1280.dmp")
like image 599
bsteo Avatar asked Feb 19 '26 03:02

bsteo


1 Answers

Found a way! For anyone interested:

from ctypes import sizeof
from ctypes import byref
import re
from ctypes import c_ulong, create_string_buffer

from constants.defines import READ_PROCESS_MEMORY
from constants.defines import VIRTUALQUERYEX
from constants.structures import SYSTEM_INFO
from constants.structures import MEMORY_BASIC_INFORMATION

import win32security, win32con, win32api, pywintypes
import sys
import os

rules = None

def AdjustPrivilege( priv ):
    flags = win32security.TOKEN_ADJUST_PRIVILEGES | win32security.TOKEN_QUERY
    htoken =  win32security.OpenProcessToken(win32api.GetCurrentProcess(), flags)
    id = win32security.LookupPrivilegeValue(None, priv)
    newPrivileges = [(id, win32security.SE_PRIVILEGE_ENABLED)]
    win32security.AdjustTokenPrivileges(htoken, 0, newPrivileges)

def ReadProcessMemory(ProcessID, rules):
    base = 0
    memory_basic_information = MEMORY_BASIC_INFORMATION()
    AdjustPrivilege("seDebugPrivilege")
    #pHandle = win32api.OpenProcess(win32con.PROCESS_QUERY_INFORMATION | win32con.PROCESS_VM_READ | win32con.PROCESS_VM_OPERATION , 0, ProcessID)
    pHandle = win32api.OpenProcess(win32con.PROCESS_VM_READ | win32con.PROCESS_QUERY_INFORMATION, 0, ProcessID)

    while VIRTUALQUERYEX(pHandle.handle, base, byref(memory_basic_information), sizeof(memory_basic_information)) > 0:
        count = c_ulong(0)
        #MEM_COMMIT && MEM_PRIVATE
        #if memory_basic_information.State == 0x1000 and memory_basic_information.Type == 0x20000:
        try:
            buff = create_string_buffer(memory_basic_information.RegionSize)
            if READ_PROCESS_MEMORY(pHandle.handle, base, buff, memory_basic_information.RegionSize, byref(count)):
                #print buff.raw
                res_rx1 = ["REGEX_STRING"]
                found_rx1 = []
                for regex in res_rx1:
                    found_rx1 += re.findall(regex, buff.raw, re.DOTALL|re.UNICODE)
                    found_rx1 = list(set(found_rx1))
                if len(found_rx1)>0:
                    for line in found_rx1:
                        print line
                #matches = rules.match(data=buff.raw)
                #for m in matches:
                #    print m, "0x%x" % memory_basic_information.BaseAddress
        except:
            pass
        base += memory_basic_information.RegionSize

    win32api.CloseHandle(pHandle)
    #base += system_info.dwPageSize

ReadProcessMemory(1280, rules)
like image 99
bsteo Avatar answered Feb 20 '26 16:02

bsteo



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!