#include "CorDrv.hpp" #include #include #include #include // Process lookup static bool FindProcessByName(const char* ProcName, DWORD* OutPid, uint64_t* OutBase) { *OutPid = 0; *OutBase = 0; // Convert name to wide + add .exe if omitted wchar_t wname[MAX_PATH] = {}; MultiByteToWideChar(CP_ACP, 0, ProcName, -1, wname, MAX_PATH); if (!wcschr(wname, L'.')) wcsncat_s(wname, L".exe", _TRUNCATE); // Enumerate processes HANDLE snap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0); if (snap == INVALID_HANDLE_VALUE) return false; PROCESSENTRY32W pe = {}; pe.dwSize = sizeof(pe); bool found = false; if (Process32FirstW(snap, &pe)) { do { if (_wcsicmp(pe.szExeFile, wname) == 0) { *OutPid = pe.th32ProcessID; found = true; break; } } while (Process32NextW(snap, &pe)); } CloseHandle(snap); if (!found) return false; // Get base address (first module = main exe) HANDLE msnap = CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, *OutPid); if (msnap != INVALID_HANDLE_VALUE) { MODULEENTRY32W me = {}; me.dwSize = sizeof(me); if (Module32FirstW(msnap, &me)) *OutBase = reinterpret_cast(me.modBaseAddr); CloseHandle(msnap); } return true; } // Hex dump static void HexDump(const uint8_t* Data, size_t Size, uint64_t BaseAddr = 0) { for (size_t i = 0; i < Size; i++) { if (i % 16 == 0) printf(" %llX: ", (unsigned long long)(BaseAddr + i)); printf("%02X ", Data[i]); if (i % 16 == 15) printf("\n"); } if (Size % 16 != 0) printf("\n"); } // Helpers static void Pause() { printf("\nAppuyez sur une touche pour quitter...\n"); getchar(); } static void PrintUsage(const char* argv0) { printf("Usage:\n"); printf(" %s [size] [--hide] auto-mode\n", argv0); printf(" %s
[size] [--hide] manual mode\n\n", argv0); printf(" process.exe : name of the target process\n"); printf(" pid : process ID (decimal)\n"); printf(" address : virtual address (hex, e.g. 0x7FF700000000)\n"); printf(" size : bytes to dump (default 256, max 1048576)\n"); printf(" Run with no arguments for interactive mode.\n"); } // Entry point int main(int argc, char* argv[]) { DWORD targetPid = 0; uint64_t targetVA = 0; size_t dumpSize = 256; bool doHide = false; char procName[MAX_PATH] = {}; // Parse arguments if (argc == 1) { // Interactive mode printf("cormem-read interactive\n\n"); printf("Process name: "); fgets(procName, sizeof(procName), stdin); procName[strcspn(procName, "\n")] = 0; char sizeStr[32] = {}; printf("Bytes to dump [256]: "); fgets(sizeStr, sizeof(sizeStr), stdin); if (sizeStr[0] != '\n' && sizeStr[0] != '\0') dumpSize = (size_t)strtoull(sizeStr, nullptr, 10); printf("\n"); } else { // Scan args for (int i = 1; i < argc; i++) { if (strncmp(argv[i], "0x", 2) == 0 || strncmp(argv[i], "0X", 2) == 0) { // Hex address → manual mode targetVA = strtoull(argv[i], nullptr, 16); } else if (isalpha((unsigned char)argv[i][0]) || strchr(argv[i], '.')) { // Process name strncpy_s(procName, argv[i], _TRUNCATE); } else { // Numeric → PID or size uint64_t val = strtoull(argv[i], nullptr, 10); if (targetPid == 0 && val > 0 && val < 65536) targetPid = (DWORD)val; else dumpSize = (size_t)val; } } if (procName[0] == 0 && targetPid == 0 && targetVA == 0) { PrintUsage(argv[0]); Pause(); return 1; } } if (dumpSize == 0 || dumpSize > 0x100000) dumpSize = 256; // Resolve process name if needed if (procName[0] != 0) { printf("[*] Looking for process: %s\n", procName); if (!FindProcessByName(procName, &targetPid, &targetVA)) { printf("[-] Process not found. Is it running?\n"); Pause(); return 1; } printf("[+] PID : %u\n", targetPid); printf("[+] Base : 0x%llX\n\n", (unsigned long long)targetVA); } // targetVA is populated by FindProcessByName if procName is used if (targetPid == 0) { printf("[-] Invalid PID.\n"); Pause(); return 1; } if (targetVA == 0) { printf("[-] Warning: Base address is 0x0. Make sure you are running as Admin.\n"); } printf("[*] Target PID : %u\n", targetPid); printf("[*] Target address : 0x%llX\n", (unsigned long long)targetVA); printf("[*] Dump size : %zu bytes\n\n", dumpSize); // Init driver CorDrv drv; printf("[*] Initializing CorDrv...\n"); if (!drv.Initialize()) { printf("[-] Failed. Is CORMEM.SYS loaded?\n"); Pause(); return 1; } printf("[+] Driver initialized.\n\n"); // Find system DTB printf("[*] Finding system DTB...\n"); uint64_t sysDTB = drv.FindSystemDTB(); if (!sysDTB) { printf("[-] Failed to find system DTB.\n"); Pause(); return 1; } printf("[+] System DTB: 0x%llX\n\n", (unsigned long long)sysDTB); // DKOM hide (DISABLED - Causes PatchGuard BSOD) if (doHide) { printf("[*] Hiding CORMEM from PsLoadedModuleList is DISABLED (prevents KPP BSOD).\n"); printf("[+] Proceeding without hiding.\n\n"); } // Find process DTB printf("[*] Searching EPROCESS list for PID %u...\n", targetPid); uint64_t procDTB = drv.FindProcessDTB(targetPid); if (!procDTB) { printf("[-] Failed to find DTB for PID %u.\n", targetPid); Pause(); return 1; } printf("[+] Process DTB: 0x%llX\n\n", (unsigned long long)procDTB); // Translate VA uint64_t phys = drv.TranslateVirtualAddress(procDTB, targetVA); if (!phys) { printf("[-] Page table walk failed for 0x%llX.\n", (unsigned long long)targetVA); Pause(); return 1; } printf("[+] VA 0x%llX -> PA 0x%llX\n\n", (unsigned long long)targetVA, (unsigned long long)phys); // Read & dump uint8_t* buf = new uint8_t[dumpSize](); if (!drv.ReadProcessMemory(procDTB, targetVA, buf, dumpSize)) { printf("[-] ReadProcessMemory failed.\n"); delete[] buf; Pause(); return 1; } printf("Memory dump (0x%llX, %zu bytes):\n", (unsigned long long)targetVA, dumpSize); HexDump(buf, dumpSize, targetVA); delete[] buf; printf("\n[+] Done.\n"); Pause(); return 0; }