Created
June 25, 2017 17:20
-
-
Save wb4r/95e61c502ec8be4b922f23d1223bb344 to your computer and use it in GitHub Desktop.
The original script can be found here: https://github.com/psychomario/pyinject/blob/master/dllinject.py
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Original project at https://github.com/psychomario/pyinject | |
# The project is licensed under the terms of the MIT license; see | |
# accompanying LICENSE.md for details. | |
import ctypes | |
import ctypes.wintypes as wintypes | |
wintypes.LPTSTR = ctypes.POINTER(ctypes.c_char) | |
wintypes.LPBYTE = ctypes.POINTER(ctypes.c_ubyte) | |
wintypes.HANDLE = ctypes.c_void_p | |
wintypes.LPDWORD = ctypes.POINTER(wintypes.DWORD) | |
wintypes.LPCTSTR = ctypes.POINTER(ctypes.c_char) | |
wintypes.PHANDLE = ctypes.POINTER(wintypes.HANDLE) | |
class __LUID(ctypes.Structure): | |
"""see: | |
http://msdn.microsoft.com/en-us/library/windows/desktop/aa379261(v=vs.85).aspx | |
""" | |
_fields_ = [("LowPart", wintypes.DWORD), | |
("HighPart", wintypes.LONG),] | |
wintypes.LUID = __LUID | |
wintypes.PLUID = wintypes.POINTER(wintypes.LUID) | |
class __LUID_AND_ATTRIBUTES(ctypes.Structure): | |
"""see: | |
http://msdn.microsoft.com/en-us/library/windows/desktop/aa379263(v=vs.85).aspx | |
""" | |
_fields_ = [("Luid", wintypes.LUID), | |
("Attributes", wintypes.DWORD),] | |
wintypes.LUID_AND_ATTRIBUTES = __LUID_AND_ATTRIBUTES | |
wintypes.PLUID_AND_ATTRIBUTES = wintypes.POINTER(wintypes.LUID_AND_ATTRIBUTES) | |
class __TOKEN_PRIVILEGES(ctypes.Structure): | |
"""see: | |
http://msdn.microsoft.com/en-us/library/windows/desktop/aa379630(v=vs.85).aspx | |
""" | |
_fields_ = [("PrivilegeCount", wintypes.DWORD), | |
("Privileges", wintypes.LUID_AND_ATTRIBUTES),] | |
wintypes.TOKEN_PRIVILEGES = __TOKEN_PRIVILEGES | |
wintypes.PTOKEN_PRIVILEGES = wintypes.POINTER(wintypes.TOKEN_PRIVILEGES) | |
class __STARTUPINFO(ctypes.Structure): | |
"""see: | |
http://msdn.microsoft.com/en-us/library/windows/desktop/ms686331(v=vs.85).aspx | |
""" | |
_fields_ = [("cb", wintypes.DWORD), | |
("lpReserved", wintypes.LPTSTR), | |
("lpDesktop", wintypes.LPTSTR), | |
("lpTitle", wintypes.LPTSTR), | |
("dwX", wintypes.DWORD), | |
("dwY", wintypes.DWORD), | |
("dwXSize", wintypes.DWORD), | |
("dwYSize", wintypes.DWORD), | |
("dwXCountChars", wintypes.DWORD), | |
("dwYCountChars", wintypes.DWORD), | |
("dwFillAttribute",wintypes.DWORD), | |
("dwFlags", wintypes.DWORD), | |
("wShowWindow", wintypes.WORD), | |
("cbReserved2", wintypes.WORD), | |
("lpReserved2", wintypes.LPBYTE), | |
("hStdInput", wintypes.HANDLE), | |
("hStdOutput", wintypes.HANDLE), | |
("hStdError", wintypes.HANDLE),] | |
wintypes.STARTUPINFO = __STARTUPINFO | |
wintypes.LPSTARTUPINFO = wintypes.POINTER(wintypes.STARTUPINFO) | |
class __PROCESS_INFORMATION(ctypes.Structure): | |
"""see: | |
http://msdn.microsoft.com/en-us/library/windows/desktop/ms684873(v=vs.85).aspx | |
""" | |
_fields_ = [("hProcess", wintypes.HANDLE), | |
("hThread", wintypes.HANDLE), | |
("dwProcessId", wintypes.DWORD), | |
("dwThreadId", wintypes.DWORD),] | |
wintypes.PROCESS_INFORMATION = __PROCESS_INFORMATION | |
wintypes.LPPROCESS_INFORMATION = wintypes.POINTER(wintypes.PROCESS_INFORMATION) | |
class __SYSTEM_MODULE_INFORMATION(ctypes.Structure): | |
_fields_ = [("ModuleCount", wintypes.ULONG), | |
("WhoCares", ctypes.c_void_p * 2), | |
("BaseAddress", ctypes.c_void_p), | |
("Size", wintypes.ULONG), | |
("MoarStuff", wintypes.ULONG), | |
("MoarMoar", wintypes.USHORT), | |
("HeyThere", wintypes.USHORT), | |
("Pwned", wintypes.USHORT), | |
("W00t", wintypes.USHORT), | |
("ImageName", ctypes.c_char * 256),] | |
wintypes.SYSTEM_MODULE_INFORMATION = __SYSTEM_MODULE_INFORMATION | |
wintypes.PSYSTEM_MODULE_INFORMATION = wintypes.POINTER(wintypes.SYSTEM_MODULE_INFORMATION) | |
class __IMAGE_DOS_HEADER(ctypes.Structure): | |
_fields_ = [("e_magic", wintypes.WORD), | |
("e_cblp", wintypes.WORD), | |
("e_cp", wintypes.WORD), | |
("e_crlc", wintypes.WORD), | |
("e_cparhdr", wintypes.WORD), | |
("e_minalloc", wintypes.WORD), | |
("e_maxalloc", wintypes.WORD), | |
("e_ss", wintypes.WORD), | |
("e_sp", wintypes.WORD), | |
("e_csum", wintypes.WORD), | |
("e_ip", wintypes.WORD), | |
("e_cs", wintypes.WORD), | |
("e_lfarlc", wintypes.WORD), | |
("e_ovno", wintypes.WORD), | |
("e_res", wintypes.WORD * 4), | |
("e_oemid", wintypes.WORD), | |
("e_oeminfo", wintypes.WORD), | |
("e_res2", wintypes.WORD * 10), | |
("e_lfanew", wintypes.LONG),] | |
wintypes.IMAGE_DOS_HEADER = __IMAGE_DOS_HEADER | |
wintypes.PIMAGES_DOS_HEADER = wintypes.POINTER(wintypes.IMAGE_DOS_HEADER) | |
class __IMAGE_FILE_HEADER(ctypes.Structure): | |
_fields_ = [("Machine", wintypes.WORD), | |
("NumberOfSections", wintypes.WORD), | |
("TimeDateStamp", wintypes.DWORD), | |
("PointerToSymbolTable", wintypes.DWORD), | |
("NumberOfSymbols", wintypes.DWORD), | |
("SizeOfOptionalHeader", wintypes.WORD), | |
("Characteristics", wintypes.WORD),] | |
wintypes.IMAGE_FILE_HEADER = __IMAGE_FILE_HEADER | |
wintypes.PIMAGE_FILE_HEADER = wintypes.POINTER(wintypes.IMAGE_FILE_HEADER) | |
class __IMAGE_DATA_DIRECTORY(ctypes.Structure): | |
_fields_ = [("VirtualAddress", wintypes.DWORD), | |
("Size", wintypes.DWORD),] | |
wintypes.IMAGE_DATA_DIRECTORY = __IMAGE_DATA_DIRECTORY | |
wintypes.PIMAGE_DATA_DIRECTORY = wintypes.POINTER(wintypes.IMAGE_DATA_DIRECTORY) | |
class __IMAGE_OPTIONAL_HEADER(ctypes.Structure): | |
_fields_ = [("Magic", wintypes.WORD), | |
("MajorLinkerVersion", wintypes.BYTE), | |
("MinorLinkerVersion", wintypes.BYTE), | |
("SizeOfCode", wintypes.DWORD), | |
("SizeOfInitializedData", wintypes.DWORD), | |
("SizeOfUninitializedData", wintypes.DWORD), | |
("AddressOfEntryPoint", wintypes.DWORD), | |
("BaseOfCode", wintypes.DWORD), | |
("BaseOfData", wintypes.DWORD), | |
("ImageBase", wintypes.DWORD), | |
("SectionAlignment", wintypes.DWORD), | |
("FileAlignment", wintypes.DWORD), | |
("MajorOperatingSystemVersion", wintypes.WORD), | |
("MinorOperatingSystemVersion", wintypes.WORD), | |
("MajorImageVersion", wintypes.WORD), | |
("MinorImageVersion", wintypes.WORD), | |
("MajorSubsystemVersion", wintypes.WORD), | |
("MinorSubsystemVersion", wintypes.WORD), | |
("Win32VersionValue", wintypes.DWORD), | |
("SizeOfImage", wintypes.DWORD), | |
("SizeOfHeaders", wintypes.DWORD), | |
("CheckSum", wintypes.DWORD), | |
("Subsystem", wintypes.WORD), | |
("DllCharacteristics", wintypes.WORD), | |
("SizeOfStackReserve", wintypes.DWORD), | |
("SizeOfStackCommit", wintypes.DWORD), | |
("SizeOfHeapReserve", wintypes.DWORD), | |
("SizeOfHeapCommit", wintypes.DWORD), | |
("LoaderFlags", wintypes.DWORD), | |
("NumberOfRvaAndSizes", wintypes.DWORD), | |
("DataDirectory", wintypes.IMAGE_DATA_DIRECTORY * 16),] | |
wintypes.IMAGE_OPTIONAL_HEADER = __IMAGE_OPTIONAL_HEADER | |
wintypes.PIMAGE_OPTIONAL_HEADER = wintypes.POINTER(wintypes.IMAGE_OPTIONAL_HEADER) | |
class __IMAGE_NT_HEADER(ctypes.Structure): | |
_fields_ = [("Signature", wintypes.DWORD), | |
("FileHeader", wintypes.IMAGE_FILE_HEADER), | |
("OptionalHeader", wintypes.IMAGE_OPTIONAL_HEADER),] | |
wintypes.IMAGE_NT_HEADER = __IMAGE_NT_HEADER | |
wintypes.PIMAGE_NT_HEADER = wintypes.POINTER(wintypes.IMAGE_NT_HEADER) | |
class SECURITY_ATTRIBUTES(ctypes.Structure): | |
_fields_ = [("nLength", wintypes.DWORD), | |
("lpSecurityDescriptor", wintypes.LPVOID), | |
("bInheritHandle", wintypes.BOOL)] | |
LPSECURITY_ATTRIBUTES = wintypes.POINTER(SECURITY_ATTRIBUTES) | |
wintypes.LPTHREAD_START_ROUTINE = wintypes.LPVOID | |
class Process(): | |
"""x""" | |
def __init__(self, pid=None, pe=None, handle=None): | |
self.kernel32 = ctypes.windll.kernel32 | |
self.PROCESS_ALL_ACCESS = (0x000F0000L|0x00100000L|0xFFF) | |
self.SE_DEBUG_NAME = "SeDebugPrivilege" | |
self.TOKEN_ADJUST_PRIVILEGES = 0x20 | |
self.SE_PRIVILEGE_ENABLED = 0x00000002 | |
self.request_debug_privileges() | |
if pid: #attach to current file | |
self.kernel32.OpenProcess.restype = wintypes.HANDLE | |
self.kernel32.OpenProcess.argtypes = [ wintypes.DWORD, | |
wintypes.BOOL, | |
wintypes.DWORD ] | |
result = self.handle = self.kernel32.OpenProcess( | |
self.PROCESS_ALL_ACCESS, | |
False, | |
pid | |
) | |
self.get_last_error("OpenProcess", result) | |
self.pid = pid | |
elif pe: #create new process | |
startupinfo = wintypes.STARTUPINFO() | |
process_information = wintypes.PROCESS_INFORMATION() | |
startupinfo.dwFlags = 0x1 | |
startupinfo.wShowWindow = 0x0 | |
startupinfo.cb = ctypes.sizeof(startupinfo) | |
self.kernel32.CreateProcessA.restype = wintypes.BOOL | |
self.kernel32.CreateProcessA.argtypes = [ wintypes.LPCSTR, | |
wintypes.LPTSTR, | |
LPSECURITY_ATTRIBUTES, | |
LPSECURITY_ATTRIBUTES, | |
wintypes.BOOL, | |
wintypes.DWORD, | |
wintypes.LPVOID, | |
wintypes.LPCTSTR, | |
wintypes.LPSTARTUPINFO, | |
wintypes.LPPROCESS_INFORMATION ] | |
result = self.kernel32.CreateProcessA( | |
pe, | |
None, | |
None, | |
None, | |
True, | |
0, | |
None, | |
None, | |
ctypes.byref(startupinfo), | |
ctypes.byref(process_information) | |
) | |
self.get_last_error("CreateProcessA", result) | |
if result == 0 : | |
print "CreateProcessA Failed!" | |
return None | |
self.handle = process_information.hProcess | |
self.pid = process_information.dwProcessId | |
elif handle: | |
self.handle = handle | |
self.pid = None | |
else: | |
return None | |
# x86 architecture | |
self.addrlen = 4 | |
# x86_64 architecture | |
# self.addrlen = 8 | |
def get_last_error(self, desc, val): | |
return # Comment out the return to see return and error values | |
print "%s=0x%x, GetCurrentError=0x%x (%d)" % (desc, val, self.kernel32.GetLastError(), self.kernel32.GetLastError()) | |
def request_debug_privileges(self): | |
"""Adds SeDebugPrivilege to current process for various needs""" | |
privs = wintypes.LUID() | |
ctypes.windll.advapi32.LookupPrivilegeValueA.restype = wintypes.BOOL | |
ctypes.windll.advapi32.LookupPrivilegeValueA.argtypes = [ wintypes.LPCTSTR, | |
wintypes.LPCTSTR, | |
wintypes.PLUID ] | |
result = ctypes.windll.advapi32.LookupPrivilegeValueA( | |
None, | |
self.SE_DEBUG_NAME, | |
ctypes.byref(privs) | |
) | |
self.get_last_error("LookupPrivilegeValueA",result) | |
token = wintypes.TOKEN_PRIVILEGES( | |
1, | |
wintypes.LUID_AND_ATTRIBUTES( | |
privs, | |
self.SE_PRIVILEGE_ENABLED | |
) | |
) | |
hToken = wintypes.HANDLE() | |
ctypes.windll.advapi32.OpenProcessToken.restype = wintypes.BOOL | |
ctypes.windll.advapi32.OpenProcessToken.argtypes = [ wintypes.HANDLE, | |
wintypes.DWORD, | |
wintypes.PHANDLE ] | |
result = ctypes.windll.advapi32.OpenProcessToken( | |
wintypes.HANDLE(self.kernel32.GetCurrentProcess()), | |
self.TOKEN_ADJUST_PRIVILEGES, | |
ctypes.byref(hToken) | |
) | |
self.get_last_error("OpenProcessToken",result) | |
ctypes.windll.advapi32.AdjustTokenPrivileges.restype = wintypes.BOOL | |
ctypes.windll.advapi32.AdjustTokenPrivileges.argtypes = [ wintypes.HANDLE, | |
wintypes.BOOL, | |
wintypes.PTOKEN_PRIVILEGES, | |
wintypes.DWORD, | |
wintypes.PTOKEN_PRIVILEGES, | |
wintypes.LPDWORD ] | |
result = ctypes.windll.advapi32.AdjustTokenPrivileges( | |
hToken, | |
False, | |
ctypes.byref(token), | |
0x0, | |
None, | |
None | |
) | |
self.get_last_error("AdjustTokenPrivileges",result) | |
ctypes.windll.kernel32.CloseHandle.restype = wintypes.BOOL | |
ctypes.windll.kernel32.CloseHandle.argtypes = [ wintypes.HANDLE ] | |
result = ctypes.windll.kernel32.CloseHandle(hToken) | |
self.get_last_error("CloseHandle", result) | |
def injectshellcode(self, shellcode): | |
"""This function merely executes what it is given""" | |
self.kernel32.VirtualAllocEx.restype = wintypes.LPVOID | |
self.kernel32.VirtualAllocEx.argtypes = [ wintypes.HANDLE, | |
wintypes.LPVOID, | |
ctypes.c_size_t, | |
wintypes.DWORD, | |
wintypes.DWORD ] | |
shellcodeaddress = self.kernel32.VirtualAllocEx( | |
self.handle, | |
None, | |
len(shellcode), | |
0x1000, # MEM_COMMIT | |
0x40 # PAGE_EXECUTE_READWRITE | |
) | |
self.get_last_error("VirtualAllocEx", shellcodeaddress) | |
self.kernel32.WriteProcessMemory.restype = wintypes.BOOL | |
self.kernel32.WriteProcessMemory.argtypes = [ wintypes.HANDLE, | |
wintypes.LPVOID, | |
wintypes.LPCVOID, | |
ctypes.c_size_t, | |
ctypes.POINTER(ctypes.c_size_t) ] | |
result = self.kernel32.WriteProcessMemory( | |
self.handle, | |
shellcodeaddress, | |
shellcode, | |
len(shellcode), | |
None | |
) | |
self.get_last_error("WriteProcessMemory", result); | |
self.kernel32.CreateRemoteThread.restype = wintypes.HANDLE | |
self.kernel32.CreateRemoteThread.argtypes = [ wintypes.HANDLE, | |
LPSECURITY_ATTRIBUTES, | |
ctypes.c_size_t, | |
wintypes.LPTHREAD_START_ROUTINE, | |
wintypes.LPVOID, | |
wintypes.DWORD, | |
wintypes.LPVOID ] | |
thread = self.kernel32.CreateRemoteThread( | |
self.handle, | |
None, | |
0, | |
shellcodeaddress, | |
None, | |
0, | |
None | |
) | |
self.get_last_error("CreateRemoteThread", thread); | |
def terminate(self, code=0): | |
"""This function terminates the process from the current handle""" | |
self.kernel32.TerminateProcess.restype = wintypes.BOOL | |
self.kernel32.TerminateProcess.argtypes = [wintypes.HANDLE, wintypes.UINT] | |
result = self.kernel32.TerminateProcess( | |
self.handle, | |
code | |
) | |
self.get_last_error("TerminateProcess",result) | |
self.kernel32.CloseHandle(self.handle) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment