diff --git a/libafl/Cargo.toml b/libafl/Cargo.toml index 0cd388683e..ff2afac779 100644 --- a/libafl/Cargo.toml +++ b/libafl/Cargo.toml @@ -112,10 +112,10 @@ grammartec = { version = "0.3", optional = true } libc = "0.2" # For (*nix) libc [target.'cfg(windows)'.dependencies] -windows = { version = "0.44", features = ["Win32_Foundation", "Win32_System_Threading", "Win32_System_Diagnostics_Debug", "Win32_System_Kernel", "Win32_System_Memory", "Win32_Security", "Win32_System_SystemInformation"] } +windows = { version = "0.51.1", features = ["Win32_Foundation", "Win32_System_Threading", "Win32_System_Diagnostics_Debug", "Win32_System_Kernel", "Win32_System_Memory", "Win32_Security", "Win32_System_SystemInformation"] } [target.'cfg(windows)'.build-dependencies] -windows = "0.44" +windows = "0.51.1" #[profile.release] #lto = true diff --git a/libafl/src/executors/inprocess.rs b/libafl/src/executors/inprocess.rs index 20a8597eae..591dd9b9b6 100644 --- a/libafl/src/executors/inprocess.rs +++ b/libafl/src/executors/inprocess.rs @@ -43,6 +43,8 @@ use nix::{ }; #[cfg(windows)] use windows::Win32::System::Threading::SetThreadStackGuarantee; +#[cfg(all(windows, feature = "std"))] +use windows::Win32::System::Threading::PTP_TIMER; use crate::{ events::{EventFirer, EventRestarter}, @@ -208,7 +210,7 @@ where This number 0x20000 could vary depending on the compilers optimization for future compression library changes. */ let mut stack_reserved = 0x20000; - SetThreadStackGuarantee(&mut stack_reserved); + SetThreadStackGuarantee(&mut stack_reserved)?; } Ok(Self { harness_fn, @@ -443,7 +445,7 @@ pub(crate) struct InProcessExecutorHandlerData { timeout_handler: *const c_void, #[cfg(all(windows, feature = "std"))] - pub(crate) tp_timer: *mut c_void, + pub(crate) ptp_timer: Option, #[cfg(all(windows, feature = "std"))] pub(crate) in_target: u64, #[cfg(all(windows, feature = "std"))] @@ -530,7 +532,7 @@ pub(crate) static mut GLOBAL_STATE: InProcessExecutorHandlerData = InProcessExec #[cfg(any(unix, feature = "std"))] timeout_handler: ptr::null(), #[cfg(all(windows, feature = "std"))] - tp_timer: null_mut(), + ptp_timer: None, #[cfg(all(windows, feature = "std"))] in_target: 0, #[cfg(all(windows, feature = "std"))] @@ -956,13 +958,10 @@ mod unix_signal_handler { #[cfg(all(windows, feature = "std"))] pub mod windows_asan_handler { use alloc::string::String; - use core::{ - ptr, - sync::atomic::{compiler_fence, Ordering}, - }; + use core::sync::atomic::{compiler_fence, Ordering}; use windows::Win32::System::Threading::{ - EnterCriticalSection, LeaveCriticalSection, RTL_CRITICAL_SECTION, + EnterCriticalSection, LeaveCriticalSection, CRITICAL_SECTION, }; use crate::{ @@ -993,18 +992,18 @@ pub mod windows_asan_handler { let data = &mut GLOBAL_STATE; data.set_in_handler(true); // Have we set a timer_before? - if !(data.tp_timer as *mut windows::Win32::System::Threading::TP_TIMER).is_null() { + if data.ptp_timer.is_some() { /* We want to prevent the timeout handler being run while the main thread is executing the crash handler Timeout handler runs if it has access to the critical section or data.in_target == 0 Writing 0 to the data.in_target makes the timeout handler makes the timeout handler invalid. */ compiler_fence(Ordering::SeqCst); - EnterCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + EnterCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); data.in_target = 0; compiler_fence(Ordering::SeqCst); - LeaveCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + LeaveCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); } @@ -1029,9 +1028,9 @@ pub mod windows_asan_handler { } else { let executor = data.executor_mut::(); // reset timer - if !data.tp_timer.is_null() { + if data.ptp_timer.is_some() { executor.post_run_reset(); - data.tp_timer = ptr::null_mut(); + data.ptp_timer = None; } let state = data.state_mut::(); @@ -1075,7 +1074,7 @@ mod windows_exception_handler { ExceptionCode, Handler, CRASH_EXCEPTIONS, EXCEPTION_HANDLERS_SIZE, EXCEPTION_POINTERS, }; use windows::Win32::System::Threading::{ - EnterCriticalSection, ExitProcess, LeaveCriticalSection, RTL_CRITICAL_SECTION, + EnterCriticalSection, ExitProcess, LeaveCriticalSection, CRITICAL_SECTION, }; use crate::{ @@ -1143,18 +1142,18 @@ mod windows_exception_handler { let in_handler = data.set_in_handler(true); // Have we set a timer_before? unsafe { - if !(data.tp_timer as *mut windows::Win32::System::Threading::TP_TIMER).is_null() { + if data.ptp_timer.is_some() { /* We want to prevent the timeout handler being run while the main thread is executing the crash handler Timeout handler runs if it has access to the critical section or data.in_target == 0 Writing 0 to the data.in_target makes the timeout handler makes the timeout handler invalid. */ compiler_fence(Ordering::SeqCst); - EnterCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + EnterCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); data.in_target = 0; compiler_fence(Ordering::SeqCst); - LeaveCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + LeaveCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); } } @@ -1204,22 +1203,14 @@ mod windows_exception_handler { let data: &mut InProcessExecutorHandlerData = &mut *(global_state as *mut InProcessExecutorHandlerData); compiler_fence(Ordering::SeqCst); - EnterCriticalSection( - (data.critical as *mut RTL_CRITICAL_SECTION) - .as_mut() - .unwrap(), - ); + EnterCriticalSection((data.critical as *mut CRITICAL_SECTION).as_mut().unwrap()); compiler_fence(Ordering::SeqCst); if !data.timeout_executor_ptr.is_null() && data.timeout_executor_mut::().handle_timeout(data) { compiler_fence(Ordering::SeqCst); - LeaveCriticalSection( - (data.critical as *mut RTL_CRITICAL_SECTION) - .as_mut() - .unwrap(), - ); + LeaveCriticalSection((data.critical as *mut CRITICAL_SECTION).as_mut().unwrap()); compiler_fence(Ordering::SeqCst); return; @@ -1256,11 +1247,7 @@ mod windows_exception_handler { } } compiler_fence(Ordering::SeqCst); - LeaveCriticalSection( - (data.critical as *mut RTL_CRITICAL_SECTION) - .as_mut() - .unwrap(), - ); + LeaveCriticalSection((data.critical as *mut CRITICAL_SECTION).as_mut().unwrap()); compiler_fence(Ordering::SeqCst); // log::info!("TIMER INVOKED!"); } @@ -1280,18 +1267,18 @@ mod windows_exception_handler { + HasScheduler, { // Have we set a timer_before? - if !(data.tp_timer as *mut windows::Win32::System::Threading::TP_TIMER).is_null() { + if data.ptp_timer.is_some() { /* We want to prevent the timeout handler being run while the main thread is executing the crash handler Timeout handler runs if it has access to the critical section or data.in_target == 0 Writing 0 to the data.in_target makes the timeout handler makes the timeout handler invalid. */ compiler_fence(Ordering::SeqCst); - EnterCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + EnterCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); data.in_target = 0; compiler_fence(Ordering::SeqCst); - LeaveCriticalSection(data.critical as *mut RTL_CRITICAL_SECTION); + LeaveCriticalSection(data.critical as *mut CRITICAL_SECTION); compiler_fence(Ordering::SeqCst); } @@ -1348,9 +1335,9 @@ mod windows_exception_handler { } else { let executor = data.executor_mut::(); // reset timer - if !data.tp_timer.is_null() { + if data.ptp_timer.is_some() { executor.post_run_reset(); - data.tp_timer = ptr::null_mut(); + data.ptp_timer = None; } let state = data.state_mut::(); diff --git a/libafl/src/executors/timeout.rs b/libafl/src/executors/timeout.rs index b285eeb7b0..be10241473 100644 --- a/libafl/src/executors/timeout.rs +++ b/libafl/src/executors/timeout.rs @@ -26,8 +26,8 @@ use windows::Win32::{ Foundation::FILETIME, System::Threading::{ CreateThreadpoolTimer, EnterCriticalSection, InitializeCriticalSection, - LeaveCriticalSection, SetThreadpoolTimer, RTL_CRITICAL_SECTION, TP_CALLBACK_ENVIRON_V3, - TP_CALLBACK_INSTANCE, TP_TIMER, + LeaveCriticalSection, SetThreadpoolTimer, CRITICAL_SECTION, PTP_CALLBACK_INSTANCE, + PTP_TIMER, TP_CALLBACK_ENVIRON_V3, }, }; @@ -92,9 +92,9 @@ pub struct TimeoutExecutor { #[cfg(windows)] milli_sec: i64, #[cfg(windows)] - tp_timer: *mut TP_TIMER, + ptp_timer: PTP_TIMER, #[cfg(windows)] - critical: RTL_CRITICAL_SECTION, + critical: CRITICAL_SECTION, exec_tmout: Duration, @@ -148,9 +148,9 @@ impl Debug for TimeoutExecutor { #[cfg(windows)] #[allow(non_camel_case_types)] type PTP_TIMER_CALLBACK = unsafe extern "system" fn( - param0: *mut TP_CALLBACK_INSTANCE, + param0: PTP_CALLBACK_INSTANCE, param1: *mut c_void, - param2: *mut TP_TIMER, + param2: PTP_TIMER, ); #[cfg(target_os = "linux")] @@ -326,14 +326,15 @@ impl TimeoutExecutor { let milli_sec = exec_tmout.as_millis() as i64; let timeout_handler: PTP_TIMER_CALLBACK = unsafe { std::mem::transmute(executor.inprocess_handlers().timeout_handler) }; - let tp_timer = unsafe { + let ptp_timer = unsafe { CreateThreadpoolTimer( Some(timeout_handler), Some(addr_of_mut!(GLOBAL_STATE) as *mut c_void), Some(&TP_CALLBACK_ENVIRON_V3::default()), ) - }; - let mut critical = RTL_CRITICAL_SECTION::default(); + } + .expect("CreateThreadpoolTimer failed!"); + let mut critical = CRITICAL_SECTION::default(); unsafe { InitializeCriticalSection(&mut critical); @@ -342,7 +343,7 @@ impl TimeoutExecutor { Self { executor, milli_sec, - tp_timer, + ptp_timer, critical, exec_tmout, batch_mode: false, @@ -394,7 +395,7 @@ where self as *mut _ as *mut c_void, ); - write_volatile(&mut data.tp_timer, self.tp_timer as *mut _ as *mut c_void); + write_volatile(&mut data.ptp_timer, Some(self.ptp_timer)); write_volatile( &mut data.critical, addr_of_mut!(self.critical) as *mut c_void, @@ -417,7 +418,7 @@ where LeaveCriticalSection(&mut self.critical); compiler_fence(Ordering::SeqCst); - SetThreadpoolTimer(self.tp_timer, Some(&ft), 0, 0); + SetThreadpoolTimer(self.ptp_timer, Some(&ft), 0, 0); let ret = self.executor.run_target(fuzzer, state, mgr, input); @@ -442,7 +443,7 @@ where /// Will dereference the given `tp_timer` pointer, unchecked. fn post_run_reset(&mut self) { unsafe { - SetThreadpoolTimer(self.tp_timer, None, 0, 0); + SetThreadpoolTimer(self.ptp_timer, None, 0, 0); } self.executor.post_run_reset(); } diff --git a/libafl_bolts/Cargo.toml b/libafl_bolts/Cargo.toml index b8eed90850..f006168f02 100644 --- a/libafl_bolts/Cargo.toml +++ b/libafl_bolts/Cargo.toml @@ -76,10 +76,10 @@ libc = "0.2" # For (*nix) libc uds = { version = "0.4", optional = true, default_features = false } [target.'cfg(windows)'.dependencies] -windows = { version = "0.44", features = ["Win32_Foundation", "Win32_System_Threading", "Win32_System_Diagnostics_Debug", "Win32_System_Kernel", "Win32_System_Memory", "Win32_Security", "Win32_System_SystemInformation"] } +windows = { version = "0.51.1", features = ["Win32_Foundation", "Win32_System_Threading", "Win32_System_Diagnostics_Debug", "Win32_System_Kernel", "Win32_System_Memory", "Win32_Security", "Win32_System_SystemInformation"] } [target.'cfg(windows)'.build-dependencies] -windows = "0.44" +windows = "0.51.1" #[profile.release] #lto = true diff --git a/libafl_bolts/src/shmem.rs b/libafl_bolts/src/shmem.rs index cd346f12b6..940544747d 100644 --- a/libafl_bolts/src/shmem.rs +++ b/libafl_bolts/src/shmem.rs @@ -1268,7 +1268,7 @@ pub mod win32_shmem { Foundation::{CloseHandle, BOOL, HANDLE}, System::Memory::{ CreateFileMappingA, MapViewOfFile, OpenFileMappingA, UnmapViewOfFile, - FILE_MAP_ALL_ACCESS, PAGE_READWRITE, + FILE_MAP_ALL_ACCESS, MEMORY_MAPPED_VIEW_ADDRESS, PAGE_READWRITE, }, }, }; @@ -1309,7 +1309,8 @@ pub mod win32_shmem { PCSTR(map_str_bytes.as_mut_ptr()), )?; - let map = MapViewOfFile(handle, FILE_MAP_ALL_ACCESS, 0, 0, map_size) as *mut u8; + let map = + MapViewOfFile(handle, FILE_MAP_ALL_ACCESS, 0, 0, map_size).Value as *mut u8; if map.is_null() { return Err(Error::unknown(format!( "Cannot map shared memory {}", @@ -1336,7 +1337,8 @@ pub mod win32_shmem { PCSTR(map_str_bytes.as_ptr() as *mut _), )?; - let map = MapViewOfFile(handle, FILE_MAP_ALL_ACCESS, 0, 0, map_size) as *mut u8; + let map = + MapViewOfFile(handle, FILE_MAP_ALL_ACCESS, 0, 0, map_size).Value as *mut u8; if map.is_null() { return Err(Error::unknown(format!( "Cannot map shared memory {}", @@ -1380,8 +1382,18 @@ pub mod win32_shmem { impl Drop for Win32ShMem { fn drop(&mut self) { unsafe { - UnmapViewOfFile(self.map as *mut c_void); - CloseHandle(self.handle); + let res = UnmapViewOfFile(MEMORY_MAPPED_VIEW_ADDRESS { + Value: self.map as *mut c_void, + }); + if let Err(err) = res { + // ignore result: nothing we can do if this goes wrong.. + log::warn!("Failed to unmap memory at {:?}: {err}", self.map); + } + let res = CloseHandle(self.handle); + if let Err(err) = res { + // ignore result: nothing we can do if this goes wrong.. + log::warn!("Failed to close mem handle {:?}: {err}", self.handle); + } } } }