From d0787ae64002660560b884421d5e7777ab894f72 Mon Sep 17 00:00:00 2001 From: Alex Franchuk Date: Mon, 29 Jan 2024 19:19:45 +0000 Subject: [PATCH] Bug 1875097 - Port the mozwer-rust crate to windows-sys r=gsvelto,glandium This exchanges `winapi` functions/types for equivalent `windows-sys` ones. Some basic types (e.g. `PBOOL`) don't exist in `windows-sys`, and I added `type` items for them (though those could be removed and the types inlined; that's what `windows-sys` does itself). The `psapi` library needed to be added for GetModuleFileNameExW; I guess previously `winapi` was linking it? Almost all manual definitions of types (`winapi::ENUM!` and `winapi::STRUCT!`) were no longer needed because `windows-sys` has them. Only the version of `RTL_USER_PROCESS_PARAMETERS` with undocumented fields was still needed. Differential Revision: https://phabricator.services.mozilla.com/D199111 --- Cargo.lock | 2 +- build/workspace-hack/Cargo.toml | 15 +- toolkit/crashreporter/mozwer-rust/Cargo.toml | 22 +- toolkit/crashreporter/mozwer-rust/lib.rs | 347 +++++-------------- 4 files changed, 123 insertions(+), 263 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 59949efc02698..3d1bb86782a3d 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -3749,7 +3749,7 @@ dependencies = [ "serde", "serde_json", "uuid", - "winapi", + "windows-sys 0.52.0", ] [[package]] diff --git a/build/workspace-hack/Cargo.toml b/build/workspace-hack/Cargo.toml index ffdd4d68dadca..6e3243d2112b1 100644 --- a/build/workspace-hack/Cargo.toml +++ b/build/workspace-hack/Cargo.toml @@ -160,15 +160,26 @@ features = [ version = "0.52" optional = true features = [ + "Wdk_System_Threading", + "Win32_Foundation", "Win32_Security", "Win32_Storage_FileSystem", "Win32_System_Com", + "Win32_System_Diagnostics_Debug", + "Win32_System_ErrorReporting", + "Win32_System_Kernel", + "Win32_System_LibraryLoader", "Win32_System_Memory", "Win32_System_Pipes", + "Win32_System_ProcessStatus", + "Win32_System_SystemInformation", "Win32_System_SystemServices", - "Win32_System_Threading" + "Win32_System_Threading", + "Win32_UI_Shell", + "Win32_UI_WindowsAndMessaging", ] + [features] builtins-static = ["dep:bindgen", "dep:bitflags", "dep:memchr", "dep:nom", "dep:regex", "dep:smallvec"] geckodriver = ["dep:bitflags", "dep:bytes", "dep:cc", "dep:chrono", "dep:flate2", "dep:futures-channel", "dep:futures-core", "dep:futures-sink", "dep:futures-util", "dep:getrandom", "dep:hashbrown", "dep:hyper", "dep:indexmap", "dep:log", "dep:memchr", "dep:mio", "dep:num-integer", "dep:num-traits", "dep:once_cell", "dep:regex", "dep:semver", "dep:serde_json", "dep:smallvec", "dep:time", "dep:tokio", "dep:tokio-util", "dep:tracing", "dep:url", "dep:uuid", "dep:windows-sys"] @@ -177,5 +188,5 @@ gkrust-gtest = ["gkrust"] http3server = ["dep:arrayvec", "dep:bindgen", "dep:bitflags", "dep:bytes", "dep:chrono", "dep:env_logger", "dep:futures-channel", "dep:futures-core", "dep:futures-sink", "dep:futures-util", "dep:getrandom", "dep:hashbrown", "dep:hyper", "dep:indexmap", "dep:log", "dep:memchr", "dep:mio", "dep:nom", "dep:num-integer", "dep:num-traits", "dep:once_cell", "dep:regex", "dep:serde_json", "dep:smallvec", "dep:time", "dep:tokio", "dep:tokio-util", "dep:tracing", "dep:url", "dep:windows-sys"] ipcclientcerts-static = ["dep:bindgen", "dep:bitflags", "dep:memchr", "dep:nom", "dep:regex"] jsrust = ["dep:arrayvec", "dep:cc", "dep:env_logger", "dep:getrandom", "dep:hashbrown", "dep:indexmap", "dep:log", "dep:memchr", "dep:num-traits", "dep:once_cell", "dep:semver", "dep:smallvec", "dep:url"] -mozwer_s = ["dep:getrandom", "dep:hashbrown", "dep:indexmap", "dep:once_cell", "dep:serde_json", "dep:uuid"] +mozwer_s = ["dep:getrandom", "dep:hashbrown", "dep:indexmap", "dep:once_cell", "dep:serde_json", "dep:uuid", "dep:windows-sys"] osclientcerts-static = ["dep:bindgen", "dep:bitflags", "dep:env_logger", "dep:log", "dep:memchr", "dep:nom", "dep:regex"] diff --git a/toolkit/crashreporter/mozwer-rust/Cargo.toml b/toolkit/crashreporter/mozwer-rust/Cargo.toml index 4a3e976229e1e..14d16ff9a6778 100644 --- a/toolkit/crashreporter/mozwer-rust/Cargo.toml +++ b/toolkit/crashreporter/mozwer-rust/Cargo.toml @@ -12,7 +12,27 @@ rust-ini = "0.10" serde = { version = "1.0", features = ["derive"] } serde_json = { version = "1.0" } uuid = { version = "1.0", features = ["v4"] } -winapi = { version = "0.3", features = ["basetsd", "combaseapi", "handleapi", "impl-default", "knownfolders", "memoryapi", "minwinbase", "minwindef", "ntdef", "ntstatus", "processthreadsapi", "psapi", "shlobj", "synchapi", "winbase", "winerror"] } + +[dependencies.windows-sys] +version = "0.52" +features = [ + "Wdk_System_Threading", + "Win32_Foundation", + "Win32_Security", + "Win32_Storage_FileSystem", + "Win32_System_Com", + "Win32_System_Diagnostics_Debug", + "Win32_System_ErrorReporting", + "Win32_System_Kernel", + "Win32_System_LibraryLoader", + "Win32_System_Memory", + "Win32_System_ProcessStatus", + "Win32_System_SystemInformation", + "Win32_System_SystemServices", + "Win32_System_Threading", + "Win32_UI_Shell", + "Win32_UI_WindowsAndMessaging", +] [lib] name = "mozwer_s" diff --git a/toolkit/crashreporter/mozwer-rust/lib.rs b/toolkit/crashreporter/mozwer-rust/lib.rs index 7774f90273117..c056f7816c24c 100644 --- a/toolkit/crashreporter/mozwer-rust/lib.rs +++ b/toolkit/crashreporter/mozwer-rust/lib.rs @@ -2,15 +2,12 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ -extern crate ini; -extern crate winapi; - use ini::Ini; use libc::time; use serde::Serialize; use serde_json::ser::to_writer; use std::convert::TryInto; -use std::ffi::OsString; +use std::ffi::{c_void, OsString}; use std::fs::{read_to_string, File}; use std::io::{BufRead, BufReader, Write}; use std::mem::{size_of, zeroed}; @@ -20,36 +17,49 @@ use std::path::{Path, PathBuf}; use std::ptr::{addr_of_mut, null, null_mut}; use std::slice::from_raw_parts; use uuid::Uuid; -use winapi::shared::basetsd::{SIZE_T, ULONG_PTR}; -use winapi::shared::minwindef::{ - BOOL, BYTE, DWORD, FALSE, FILETIME, LPVOID, MAX_PATH, PBOOL, PDWORD, PULONG, TRUE, ULONG, WORD, -}; -use winapi::shared::ntdef::{NTSTATUS, STRING, UNICODE_STRING}; -use winapi::shared::ntstatus::STATUS_SUCCESS; -use winapi::shared::winerror::{E_UNEXPECTED, S_OK}; -use winapi::um::combaseapi::CoTaskMemFree; -use winapi::um::handleapi::CloseHandle; -use winapi::um::knownfolders::FOLDERID_RoamingAppData; -use winapi::um::memoryapi::{ReadProcessMemory, WriteProcessMemory}; -use winapi::um::minwinbase::{EXCEPTION_BREAKPOINT, LPTHREAD_START_ROUTINE}; -use winapi::um::processthreadsapi::{ - CreateProcessW, CreateRemoteThread, GetProcessId, GetProcessTimes, GetThreadContext, - GetThreadId, OpenProcess, OpenThread, TerminateProcess, PROCESS_INFORMATION, STARTUPINFOW, -}; -use winapi::um::psapi::K32GetModuleFileNameExW; -use winapi::um::shlobj::SHGetKnownFolderPath; -use winapi::um::synchapi::WaitForSingleObject; -use winapi::um::winbase::{ - VerifyVersionInfoW, CREATE_NO_WINDOW, CREATE_UNICODE_ENVIRONMENT, NORMAL_PRIORITY_CLASS, - WAIT_OBJECT_0, -}; -use winapi::um::winnt::{ - VerSetConditionMask, CONTEXT, DWORDLONG, EXCEPTION_POINTERS, EXCEPTION_RECORD, HANDLE, HRESULT, - LIST_ENTRY, LPOSVERSIONINFOEXW, OSVERSIONINFOEXW, PCWSTR, PEXCEPTION_POINTERS, - PROCESS_ALL_ACCESS, PVOID, PWSTR, THREAD_GET_CONTEXT, VER_GREATER_EQUAL, VER_MAJORVERSION, - VER_MINORVERSION, VER_SERVICEPACKMAJOR, VER_SERVICEPACKMINOR, +use windows_sys::core::{HRESULT, PWSTR}; +use windows_sys::Wdk::System::Threading::{NtQueryInformationProcess, ProcessBasicInformation}; +use windows_sys::Win32::{ + Foundation::{ + CloseHandle, BOOL, EXCEPTION_BREAKPOINT, E_UNEXPECTED, FALSE, FILETIME, HANDLE, HWND, + LPARAM, MAX_PATH, STATUS_SUCCESS, S_OK, TRUE, UNICODE_STRING, WAIT_OBJECT_0, + }, + System::Com::CoTaskMemFree, + System::Diagnostics::Debug::{ + GetThreadContext, MiniDumpWithFullMemoryInfo, MiniDumpWithIndirectlyReferencedMemory, + MiniDumpWithProcessThreadData, MiniDumpWithUnloadedModules, MiniDumpWriteDump, + ReadProcessMemory, WriteProcessMemory, EXCEPTION_POINTERS, MINIDUMP_EXCEPTION_INFORMATION, + MINIDUMP_TYPE, + }, + System::ErrorReporting::WER_RUNTIME_EXCEPTION_INFORMATION, + System::Kernel::STRING, + System::ProcessStatus::K32GetModuleFileNameExW, + System::SystemInformation::{ + VerSetConditionMask, VerifyVersionInfoW, OSVERSIONINFOEXW, VER_MAJORVERSION, + VER_MINORVERSION, VER_SERVICEPACKMAJOR, VER_SERVICEPACKMINOR, + }, + System::SystemServices::VER_GREATER_EQUAL, + System::Threading::{ + CreateProcessW, CreateRemoteThread, GetProcessId, GetProcessTimes, GetThreadId, + OpenProcess, OpenThread, TerminateProcess, WaitForSingleObject, CREATE_NO_WINDOW, + CREATE_UNICODE_ENVIRONMENT, LPTHREAD_START_ROUTINE, NORMAL_PRIORITY_CLASS, PEB, + PROCESS_ALL_ACCESS, PROCESS_BASIC_INFORMATION, PROCESS_INFORMATION, STARTUPINFOW, + THREAD_GET_CONTEXT, + }, + UI::Shell::{FOLDERID_RoamingAppData, SHGetKnownFolderPath}, + UI::WindowsAndMessaging::{EnumWindows, GetWindowThreadProcessId, IsHungAppWindow}, }; -use winapi::STRUCT; + +type WORD = u16; +type DWORD = u32; +type ULONG = u32; +type DWORDLONG = u64; +type LPVOID = *mut c_void; +type PVOID = LPVOID; +type PBOOL = *mut BOOL; +type PDWORD = *mut DWORD; +#[allow(non_camel_case_types)] +type PWER_RUNTIME_EXCEPTION_INFORMATION = *mut WER_RUNTIME_EXCEPTION_INFORMATION; /* The following struct must be kept in sync with the identically named one in * nsExceptionHandler.h. There is one copy of this structure for every child @@ -152,7 +162,7 @@ fn out_of_process_exception_event_callback( // This is all best-effort, so don't return errors (just fall through to the // Ok return). let thread_handle = unsafe { OpenThread(THREAD_GET_CONTEXT, FALSE, thread_id) }; - if thread_handle != std::ptr::null_mut() + if thread_handle != 0 && unsafe { GetThreadContext(thread_handle, &mut exception_information.context) } @@ -195,9 +205,6 @@ fn out_of_process_exception_event_callback( /// Find whether the given process has a hung window, and return the thread id related to the /// window. fn find_hung_window_thread(process: HANDLE) -> Result { - use winapi::shared::{minwindef::LPARAM, windef::HWND}; - use winapi::um::winuser::{EnumWindows, GetWindowThreadProcessId, IsHungAppWindow}; - let process_id = get_process_id(process)?; struct WindowSearch { @@ -268,7 +275,7 @@ fn read_from_process(process: HANDLE, data_ptr: *mut T) -> Result { process, data_ptr as *mut _, addr_of_mut!(data) as *mut _, - size_of::() as SIZE_T, + size_of::(), null_mut(), ) } @@ -281,7 +288,7 @@ fn read_array_from_process( count: usize, ) -> Result> { let mut array = vec![Default::default(); count]; - let size = size_of::() as SIZE_T; + let size = size_of::(); let size = size.checked_mul(count).ok_or(())?; unsafe { ReadProcessMemory( @@ -301,7 +308,7 @@ fn write_to_process(process: HANDLE, mut data: T, data_ptr: *mut T) -> Result process, data_ptr as LPVOID, addr_of_mut!(data) as *mut _, - size_of::() as SIZE_T, + size_of::(), null_mut(), ) } @@ -325,7 +332,7 @@ fn notify_main_process( ) }; - if thread == null_mut() { + if thread == 0 { return Err(()); } @@ -339,10 +346,14 @@ fn notify_main_process( } fn get_startup_time(process: HANDLE) -> Result { - let mut create_time: FILETIME = Default::default(); - let mut exit_time: FILETIME = Default::default(); - let mut kernel_time: FILETIME = Default::default(); - let mut user_time: FILETIME = Default::default(); + const ZERO_FILETIME: FILETIME = FILETIME { + dwLowDateTime: 0, + dwHighDateTime: 0, + }; + let mut create_time: FILETIME = ZERO_FILETIME; + let mut exit_time: FILETIME = ZERO_FILETIME; + let mut kernel_time: FILETIME = ZERO_FILETIME; + let mut user_time: FILETIME = ZERO_FILETIME; unsafe { if GetProcessTimes( process, @@ -389,7 +400,7 @@ fn get_process_id(process: HANDLE) -> Result { fn get_process_handle(pid: DWORD) -> Result { let handle = unsafe { OpenProcess(PROCESS_ALL_ACCESS, FALSE, pid) }; - if handle != null_mut() { + if handle != 0 { Ok(handle) } else { Err(()) @@ -411,10 +422,10 @@ fn launch_crash_reporter_client( cmd_line.push("\"\0"); let mut cmd_line: Vec = cmd_line.encode_wide().collect(); - let mut pi: PROCESS_INFORMATION = Default::default(); + let mut pi = unsafe { zeroed::() }; let mut si = STARTUPINFOW { cb: size_of::().try_into().unwrap(), - ..Default::default() + ..unsafe { zeroed() } }; unsafe { @@ -571,11 +582,11 @@ impl ApplicationInformation { } fn get_application_path(process: HANDLE) -> Result { - let mut path: [u16; MAX_PATH + 1] = [0; MAX_PATH + 1]; + let mut path: [u16; MAX_PATH as usize + 1] = [0; MAX_PATH as usize + 1]; unsafe { let res = K32GetModuleFileNameExW( process, - null_mut(), + 0, (&mut path).as_mut_ptr(), (MAX_PATH + 1) as DWORD, ); @@ -606,7 +617,7 @@ impl ApplicationInformation { let res = SHGetKnownFolderPath( &FOLDERID_RoamingAppData as *const _, 0, - null_mut(), + 0, &mut psz_path as *mut _, ); @@ -778,18 +789,19 @@ fn is_windows8_or_later() -> bool { dwOSVersionInfoSize: size_of::().try_into().unwrap(), dwMajorVersion: 6, dwMinorVersion: 2, - ..Default::default() + ..unsafe { zeroed() } }; unsafe { let mut mask: DWORDLONG = 0; - mask = VerSetConditionMask(mask, VER_MAJORVERSION, VER_GREATER_EQUAL); - mask = VerSetConditionMask(mask, VER_MINORVERSION, VER_GREATER_EQUAL); - mask = VerSetConditionMask(mask, VER_SERVICEPACKMAJOR, VER_GREATER_EQUAL); - mask = VerSetConditionMask(mask, VER_SERVICEPACKMINOR, VER_GREATER_EQUAL); + let ge: u8 = VER_GREATER_EQUAL.try_into().unwrap(); + mask = VerSetConditionMask(mask, VER_MAJORVERSION, ge); + mask = VerSetConditionMask(mask, VER_MINORVERSION, ge); + mask = VerSetConditionMask(mask, VER_SERVICEPACKMAJOR, ge); + mask = VerSetConditionMask(mask, VER_SERVICEPACKMINOR, ge); VerifyVersionInfoW( - &mut info as LPOSVERSIONINFOEXW, + &mut info, VER_MAJORVERSION | VER_MINORVERSION | VER_SERVICEPACKMAJOR | VER_SERVICEPACKMINOR, mask, ) @@ -841,7 +853,9 @@ fn read_command_line(process: HANDLE) -> Result { String::from_utf16(&command_line).map_err(|_err| ()) } -fn read_user_process_parameters(process: HANDLE) -> Result { +fn read_user_process_parameters( + process: HANDLE, +) -> Result { let mut pbi: PROCESS_BASIC_INFORMATION = unsafe { zeroed() }; let mut length: ULONG = 0; let result = unsafe { @@ -862,159 +876,30 @@ fn read_user_process_parameters(process: HANDLE) -> Result(process, peb.ProcessParameters) -} - -/****************************************************************************** - * The stuff below should be migrated to the winapi crate, see bug 1696414 * - ******************************************************************************/ - -// we can't use winapi's ENUM macro directly because it doesn't support -// attributes, so let's define this one here until we migrate this code -macro_rules! ENUM { - {enum $name:ident { $($variant:ident = $value:expr,)+ }} => { - #[allow(non_camel_case_types)] pub type $name = u32; - $(#[allow(non_upper_case_globals)] pub const $variant: $name = $value;)+ - }; -} - -// winapi doesn't export the FN macro, so we duplicate it here -macro_rules! FN { - (stdcall $func:ident($($t:ty,)*) -> $ret:ty) => ( - #[allow(non_camel_case_types)] pub type $func = Option $ret>; - ); - (stdcall $func:ident($($p:ident: $t:ty,)*) -> $ret:ty) => ( - #[allow(non_camel_case_types)] pub type $func = Option $ret>; - ); -} - -// From um/WerApi.h - -STRUCT! {#[allow(non_snake_case)] struct WER_RUNTIME_EXCEPTION_INFORMATION -{ - dwSize: DWORD, - hProcess: HANDLE, - hThread: HANDLE, - exceptionRecord: EXCEPTION_RECORD, - context: CONTEXT, - pwszReportId: PCWSTR, - bIsFatal: BOOL, - dwReserved: DWORD, -}} - -#[allow(non_camel_case_types)] -pub type PWER_RUNTIME_EXCEPTION_INFORMATION = *mut WER_RUNTIME_EXCEPTION_INFORMATION; - -// From minidumpapiset.hProcess - -STRUCT! {#[allow(non_snake_case)] #[repr(packed(4))] struct MINIDUMP_EXCEPTION_INFORMATION { - ThreadId: DWORD, - ExceptionPointers: PEXCEPTION_POINTERS, - ClientPointers: BOOL, -}} - -#[allow(non_camel_case_types)] -pub type PMINIDUMP_EXCEPTION_INFORMATION = *mut MINIDUMP_EXCEPTION_INFORMATION; - -ENUM! { enum MINIDUMP_TYPE { - MiniDumpNormal = 0x00000000, - MiniDumpWithDataSegs = 0x00000001, - MiniDumpWithFullMemory = 0x00000002, - MiniDumpWithHandleData = 0x00000004, - MiniDumpFilterMemory = 0x00000008, - MiniDumpScanMemory = 0x00000010, - MiniDumpWithUnloadedModules = 0x00000020, - MiniDumpWithIndirectlyReferencedMemory = 0x00000040, - MiniDumpFilterModulePaths = 0x00000080, - MiniDumpWithProcessThreadData = 0x00000100, - MiniDumpWithPrivateReadWriteMemory = 0x00000200, - MiniDumpWithoutOptionalData = 0x00000400, - MiniDumpWithFullMemoryInfo = 0x00000800, - MiniDumpWithThreadInfo = 0x00001000, - MiniDumpWithCodeSegs = 0x00002000, - MiniDumpWithoutAuxiliaryState = 0x00004000, - MiniDumpWithFullAuxiliaryState = 0x00008000, - MiniDumpWithPrivateWriteCopyMemory = 0x00010000, - MiniDumpIgnoreInaccessibleMemory = 0x00020000, - MiniDumpWithTokenInformation = 0x00040000, - MiniDumpWithModuleHeaders = 0x00080000, - MiniDumpFilterTriage = 0x00100000, - MiniDumpWithAvxXStateContext = 0x00200000, - MiniDumpWithIptTrace = 0x00400000, - MiniDumpScanInaccessiblePartialPages = 0x00800000, - MiniDumpValidTypeFlags = 0x00ffffff, -}} - -// We don't actually need the following three structs so we use placeholders -STRUCT! {#[allow(non_snake_case)] struct MINIDUMP_CALLBACK_INPUT { - dummy: u32, -}} - -#[allow(non_camel_case_types)] -pub type PMINIDUMP_CALLBACK_INPUT = *const MINIDUMP_CALLBACK_INPUT; - -STRUCT! {#[allow(non_snake_case)] struct MINIDUMP_USER_STREAM_INFORMATION { - dummy: u32, -}} - -#[allow(non_camel_case_types)] -pub type PMINIDUMP_USER_STREAM_INFORMATION = *const MINIDUMP_USER_STREAM_INFORMATION; - -STRUCT! {#[allow(non_snake_case)] struct MINIDUMP_CALLBACK_OUTPUT { - dummy: u32, -}} - -#[allow(non_camel_case_types)] -pub type PMINIDUMP_CALLBACK_OUTPUT = *const MINIDUMP_CALLBACK_OUTPUT; - -// MiniDumpWriteDump() function and structs -FN! {stdcall MINIDUMP_CALLBACK_ROUTINE( -CallbackParam: PVOID, -CallbackInput: PMINIDUMP_CALLBACK_INPUT, -CallbackOutput: PMINIDUMP_CALLBACK_OUTPUT, -) -> BOOL} - -STRUCT! {#[allow(non_snake_case)] #[repr(packed(4))] struct MINIDUMP_CALLBACK_INFORMATION { - CallbackRoutine: MINIDUMP_CALLBACK_ROUTINE, - CallbackParam: PVOID, -}} - -#[allow(non_camel_case_types)] -pub type PMINIDUMP_CALLBACK_INFORMATION = *const MINIDUMP_CALLBACK_INFORMATION; - -extern "system" { - pub fn MiniDumpWriteDump( - hProcess: HANDLE, - ProcessId: DWORD, - hFile: HANDLE, - DumpType: MINIDUMP_TYPE, - Exceptionparam: PMINIDUMP_EXCEPTION_INFORMATION, - UserStreamParam: PMINIDUMP_USER_STREAM_INFORMATION, - CallbackParam: PMINIDUMP_CALLBACK_INFORMATION, - ) -> BOOL; + read_from_process( + process, + peb.ProcessParameters as *mut RTL_USER_PROCESS_PARAMETERS_UNDOCUMENTED, + ) } -// From um/winternl.h - -STRUCT! {#[allow(non_snake_case)] struct PEB_LDR_DATA { - Reserved1: [BYTE; 8], - Reserved2: [PVOID; 3], - InMemoryOrderModuleList: LIST_ENTRY, -}} - -#[allow(non_camel_case_types)] -pub type PPEB_LDR_DATA = *mut PEB_LDR_DATA; +// The below structs encompass undocumented fields. -STRUCT! {#[allow(non_snake_case)] struct RTL_DRIVE_LETTER_CURDIR { +#[repr(C)] +#[allow(non_snake_case)] +struct RTL_DRIVE_LETTER_CURDIR { Flags: WORD, Length: WORD, TimeStamp: ULONG, DosPath: STRING, -}} +} -STRUCT! {#[allow(non_snake_case)] struct RTL_USER_PROCESS_PARAMETERS { - Reserved1: [BYTE; 16], - Reserved2: [PVOID; 10], +#[repr(C)] +#[allow(non_snake_case)] +struct RTL_USER_PROCESS_PARAMETERS_UNDOCUMENTED { + // These first 4 members are copied from + // `windows_sys::Win32::System::Threading::RTL_USER_PROCESS_PARAMETERS`. + Reserved1: [u8; 16], + Reserved2: [*mut c_void; 10], ImagePathName: UNICODE_STRING, CommandLine: UNICODE_STRING, // Everything below this point is undocumented @@ -1034,60 +919,4 @@ STRUCT! {#[allow(non_snake_case)] struct RTL_USER_PROCESS_PARAMETERS { RuntimeData: UNICODE_STRING, CurrentDirectores: [RTL_DRIVE_LETTER_CURDIR; 32], EnvironmentSize: ULONG, -}} - -#[allow(non_camel_case_types)] -pub type PRTL_USER_PROCESS_PARAMETERS = *mut RTL_USER_PROCESS_PARAMETERS; - -FN! {stdcall PPS_POST_PROCESS_INIT_ROUTINE() -> ()} - -STRUCT! {#[allow(non_snake_case)] struct PEB { - Reserved1: [BYTE; 2], - BeingDebugged: BYTE, - Reserved2: [BYTE; 1], - Reserved3: [PVOID; 2], - Ldr: PPEB_LDR_DATA, - ProcessParameters: PRTL_USER_PROCESS_PARAMETERS, - Reserved4: [PVOID; 3], - AtlThunkSListPtr: PVOID, - Reserved5: PVOID, - Reserved6: ULONG, - Reserved7: PVOID, - Reserved8: ULONG, - AtlThunkSListPtr32: ULONG, - Reserved9: [PVOID; 45], - Reserved10: [BYTE; 96], - PostProcessInitRoutine: PPS_POST_PROCESS_INIT_ROUTINE, - Reserved11: [BYTE; 128], - Reserved12: [PVOID; 1], - SessionId: ULONG, -}} - -#[allow(non_camel_case_types)] -pub type PPEB = *mut PEB; - -STRUCT! {#[allow(non_snake_case)] struct PROCESS_BASIC_INFORMATION { - Reserved1: PVOID, - PebBaseAddress: PPEB, - Reserved2: [PVOID; 2], - UniqueProcessId: ULONG_PTR, - Reserved3: PVOID, -}} - -ENUM! {enum PROCESSINFOCLASS { - ProcessBasicInformation = 0, - ProcessDebugPort = 7, - ProcessWow64Information = 26, - ProcessImageFileName = 27, - ProcessBreakOnTermination = 29, -}} - -extern "system" { - pub fn NtQueryInformationProcess( - ProcessHandle: HANDLE, - ProcessInformationClass: PROCESSINFOCLASS, - ProcessInformation: PVOID, - ProcessInformationLength: ULONG, - ReturnLength: PULONG, - ) -> NTSTATUS; }