From 57590447c7eb3c7046d6473b14b761a72b19c2ef Mon Sep 17 00:00:00 2001 From: mio Date: Thu, 15 May 2025 21:01:18 +0800 Subject: [PATCH 01/10] Add android CI --- .github/workflows/build_and_test.yml | 21 +++++++++++++++++++++ 1 file changed, 21 insertions(+) diff --git a/.github/workflows/build_and_test.yml b/.github/workflows/build_and_test.yml index 53389b5e2b..9d023be8d2 100644 --- a/.github/workflows/build_and_test.yml +++ b/.github/workflows/build_and_test.yml @@ -112,6 +112,27 @@ jobs: # --- miri undefined behavior test -- - name: Run miri tests run: RUST_BACKTRACE=1 MIRIFLAGS="-Zmiri-disable-isolation" cargo +nightly miri test + + ubuntu-ndk-x86_64: + runs-on: ubuntu-24.04 + steps: + - uses: actions/checkout@v4 + - uses: ./.github/workflows/ubuntu-prepare + - uses: Swatinem/rust-cache@v2 + - uses: nttld/setup-ndk@v1 + id: setup-ndk + with: + ndk-version: r26d + add-to-path: false + - name: cargo-ndk + run: cargo install cargo-ndk + - name: cargo android targets + run: | + rustup target add x86_64-linux-android + - name: Build Android + env: + ANDROID_NDK_HOME: ${{ steps.setup-ndk.outputs.ndk-path }} + run: cargo ndk -t x86_64 build ubuntu: runs-on: ubuntu-24.04 From 9bf7b068856248fc271ed8fbcbf06d7463374f30 Mon Sep 17 00:00:00 2001 From: mio Date: Thu, 15 May 2025 21:11:48 +0800 Subject: [PATCH 02/10] update --- .github/workflows/build_and_test.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/build_and_test.yml b/.github/workflows/build_and_test.yml index 9d023be8d2..288efa91b0 100644 --- a/.github/workflows/build_and_test.yml +++ b/.github/workflows/build_and_test.yml @@ -122,7 +122,7 @@ jobs: - uses: nttld/setup-ndk@v1 id: setup-ndk with: - ndk-version: r26d + ndk-version: r27c add-to-path: false - name: cargo-ndk run: cargo install cargo-ndk @@ -132,6 +132,7 @@ jobs: - name: Build Android env: ANDROID_NDK_HOME: ${{ steps.setup-ndk.outputs.ndk-path }} + ANDROID_NDK_ROOT: ${{ steps.setup-ndk.outputs.ndk-path }} run: cargo ndk -t x86_64 build ubuntu: From a3753aa404ea3748d710d67a267df1458c2d4d4f Mon Sep 17 00:00:00 2001 From: mio Date: Fri, 16 May 2025 15:06:04 +0800 Subject: [PATCH 03/10] Move together --- .github/workflows/build_and_test.yml | 45 ++++++++++++++-------------- 1 file changed, 22 insertions(+), 23 deletions(-) diff --git a/.github/workflows/build_and_test.yml b/.github/workflows/build_and_test.yml index 288efa91b0..5168a93ed3 100644 --- a/.github/workflows/build_and_test.yml +++ b/.github/workflows/build_and_test.yml @@ -112,28 +112,6 @@ jobs: # --- miri undefined behavior test -- - name: Run miri tests run: RUST_BACKTRACE=1 MIRIFLAGS="-Zmiri-disable-isolation" cargo +nightly miri test - - ubuntu-ndk-x86_64: - runs-on: ubuntu-24.04 - steps: - - uses: actions/checkout@v4 - - uses: ./.github/workflows/ubuntu-prepare - - uses: Swatinem/rust-cache@v2 - - uses: nttld/setup-ndk@v1 - id: setup-ndk - with: - ndk-version: r27c - add-to-path: false - - name: cargo-ndk - run: cargo install cargo-ndk - - name: cargo android targets - run: | - rustup target add x86_64-linux-android - - name: Build Android - env: - ANDROID_NDK_HOME: ${{ steps.setup-ndk.outputs.ndk-path }} - ANDROID_NDK_ROOT: ${{ steps.setup-ndk.outputs.ndk-path }} - run: cargo ndk -t x86_64 build ubuntu: runs-on: ubuntu-24.04 @@ -658,7 +636,7 @@ jobs: - name: Clippy run: cargo +nightly clippy --tests --all --exclude libafl_nyx --exclude symcc_runtime --exclude runtime_test - android: + ubuntu-cross-android-arm64: runs-on: ubuntu-24.04 steps: - uses: dtolnay/rust-toolchain@stable @@ -674,6 +652,27 @@ jobs: - name: Build Android run: cd libafl && PYO3_CROSS_PYTHON_VERSION=$(python3 -c "print('{}.{}'.format(__import__('sys').version_info.major, __import__('sys').version_info.minor))") cargo ndk -t arm64-v8a build --release + ubuntu-cross-android-x86_64: + runs-on: ubuntu-24.04 + steps: + - uses: actions/checkout@v4 + - uses: ./.github/workflows/ubuntu-prepare + - uses: Swatinem/rust-cache@v2 + - uses: nttld/setup-ndk@v1 + id: setup-ndk + with: + ndk-version: r27c + add-to-path: false + - name: cargo-ndk + run: cargo install cargo-ndk + - name: cargo android targets + run: | + rustup target add x86_64-linux-android + - name: Build Android + env: + ANDROID_NDK_HOME: ${{ steps.setup-ndk.outputs.ndk-path }} + ANDROID_NDK_ROOT: ${{ steps.setup-ndk.outputs.ndk-path }} + run: cargo ndk -t x86_64 build #run: cargo build --target aarch64-linux-android # TODO: Figure out how to properly build stuff with clang #- name: Add clang path to $PATH env From f50a366500a693cb25bdd7da1b07aaf20797bb1c Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Sun, 18 May 2025 19:50:55 +0800 Subject: [PATCH 04/10] Use shmem for forkserver several pointers --- .../forkserver_libafl_cc/src/lib.rs | 9 +- .../fuzzbench_forkserver_sand/src/lib.rs | 9 +- libafl/src/executors/forkserver.rs | 8 +- libafl_bolts/src/shmem.rs | 9 ++ libafl_targets/src/forkserver.rs | 133 +++++++++--------- 5 files changed, 98 insertions(+), 70 deletions(-) diff --git a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs index ac4b7e54fb..f53c74b0f1 100644 --- a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs +++ b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs @@ -1,15 +1,20 @@ +use libafl_bolts::shmem::StdShMemProvider; use libafl_targets::{ map_input_shared_memory, map_shared_memory, start_forkserver, MaybePersistentForkserverParent, }; #[no_mangle] pub extern "C" fn libafl_start_forkserver() { + let Ok(mut shm_provider) = StdShMemProvider::new() else { + std::process::exit(1); + }; + // Map shared memory region for the edge coverage map - if map_shared_memory().is_err() { + if map_shared_memory(&mut shm_provider).is_err() { std::process::exit(1); } // Map shared memory region for input and its len - if map_input_shared_memory().is_err() { + if map_input_shared_memory(&mut shm_provider).is_err() { std::process::exit(1); }; // Start the forkserver diff --git a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs index ac4b7e54fb..f53c74b0f1 100644 --- a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs +++ b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs @@ -1,15 +1,20 @@ +use libafl_bolts::shmem::StdShMemProvider; use libafl_targets::{ map_input_shared_memory, map_shared_memory, start_forkserver, MaybePersistentForkserverParent, }; #[no_mangle] pub extern "C" fn libafl_start_forkserver() { + let Ok(mut shm_provider) = StdShMemProvider::new() else { + std::process::exit(1); + }; + // Map shared memory region for the edge coverage map - if map_shared_memory().is_err() { + if map_shared_memory(&mut shm_provider).is_err() { std::process::exit(1); } // Map shared memory region for input and its len - if map_input_shared_memory().is_err() { + if map_input_shared_memory(&mut shm_provider).is_err() { std::process::exit(1); }; // Start the forkserver diff --git a/libafl/src/executors/forkserver.rs b/libafl/src/executors/forkserver.rs index 0a82553223..f1b19667ee 100644 --- a/libafl/src/executors/forkserver.rs +++ b/libafl/src/executors/forkserver.rs @@ -143,9 +143,11 @@ fn report_error_and_exit(status: i32) -> Result<(), Error> { } /// The length of header bytes which tells shmem size -const SHMEM_FUZZ_HDR_SIZE: usize = 4; -const MAX_INPUT_SIZE_DEFAULT: usize = 1024 * 1024; -const MIN_INPUT_SIZE_DEFAULT: usize = 1; +pub const SHMEM_FUZZ_HDR_SIZE: usize = 4; +/// Maximum default length for input +pub const MAX_INPUT_SIZE_DEFAULT: usize = 1024 * 1024; +/// Minimum default length for input +pub const MIN_INPUT_SIZE_DEFAULT: usize = 1; /// Environment variable key for shared memory id for input and its len pub const SHM_FUZZ_ENV_VAR: &str = "__AFL_SHM_FUZZ_ID"; /// Environment variable key for the page size (at least/usually `testcase_size_max + sizeof::()`) diff --git a/libafl_bolts/src/shmem.rs b/libafl_bolts/src/shmem.rs index 4be592bfdd..9d2dd86a95 100644 --- a/libafl_bolts/src/shmem.rs +++ b/libafl_bolts/src/shmem.rs @@ -247,6 +247,15 @@ pub trait ShMem: Sized + Debug + Clone + DerefMut { } } + /// Consume current shared memory structure, and get the raw pointer to + /// this shared memory. + /// + /// Note that calling this method will result in a memory leak. + fn into_raw(self) -> *mut T { + let mut manually_dropped = ManuallyDrop::new(self); + manually_dropped.as_mut_ptr().cast() + } + /// Get the description of the shared memory mapping fn description(&self) -> ShMemDescription { ShMemDescription { diff --git a/libafl_targets/src/forkserver.rs b/libafl_targets/src/forkserver.rs index 3c9d8e41be..eade7ea448 100644 --- a/libafl_targets/src/forkserver.rs +++ b/libafl_targets/src/forkserver.rs @@ -6,24 +6,31 @@ use std::{ sync::OnceLock, }; +#[cfg(any(target_os = "linux", target_vendor = "apple"))] +use libafl::executors::forkserver::FS_NEW_OPT_AUTODTCT; +#[cfg(feature = "cmplog")] +use libafl::executors::forkserver::SHM_CMPLOG_ENV_VAR; use libafl::{ Error, executors::forkserver::{ - FORKSRV_FD, FS_ERROR_SHM_OPEN, FS_NEW_OPT_AUTODTCT, FS_NEW_OPT_MAPSIZE, - FS_NEW_OPT_SHDMEM_FUZZ, FS_NEW_VERSION_MAX, FS_OPT_ERROR, SHM_CMPLOG_ENV_VAR, SHM_ENV_VAR, - SHM_FUZZ_ENV_VAR, + AFL_MAP_SIZE_ENV_VAR, FORKSRV_FD, FS_ERROR_SHM_OPEN, FS_NEW_OPT_MAPSIZE, + FS_NEW_OPT_SHDMEM_FUZZ, FS_NEW_VERSION_MAX, FS_OPT_ERROR, MAX_INPUT_SIZE_DEFAULT, + SHM_ENV_VAR, SHM_FUZZ_ENV_VAR, SHM_FUZZ_MAP_SIZE_ENV_VAR, SHMEM_FUZZ_HDR_SIZE, }, }; -use libafl_bolts::os::{ChildHandle, ForkResult}; +use libafl_bolts::{ + os::{ChildHandle, ForkResult}, + shmem::{ShMem, ShMemId, ShMemProvider}, +}; use nix::{ sys::signal::{SigHandler, Signal}, unistd::Pid, }; -#[cfg(feature = "cmplog")] -use crate::cmps::CMPLOG_MAP_PTR; #[cfg(feature = "cmplog_extended_instrumentation")] use crate::cmps::EXTENDED_CMPLOG_MAP_PTR; +#[cfg(feature = "cmplog")] +use crate::cmps::{AflppCmpLogMap, CMPLOG_MAP_PTR}; use crate::coverage::{__afl_map_size, EDGES_MAP_PTR, INPUT_LENGTH_PTR, INPUT_PTR, SHM_FUZZING}; #[cfg(any(target_os = "linux", target_vendor = "apple"))] @@ -54,6 +61,7 @@ fn write_to_forkserver(message: &[u8]) -> Result<(), Error> { } Ok(()) } +#[cfg(any(target_os = "linux", target_vendor = "apple"))] fn write_all_to_forkserver(message: &[u8]) -> Result<(), Error> { let mut remain_len = message.len(); while remain_len > 0 { @@ -89,6 +97,30 @@ fn read_u32_from_forkserver() -> Result { Ok(u32::from_ne_bytes(buf)) } +fn map_shared_memory_common( + shmem_provider: &mut SHM, + map_env_var: &str, + map_size_env_var: &str, + map_size_default_fallback: usize, +) -> Result<*mut u8, Error> { + let Ok(id_str) = std::env::var(map_env_var) else { + write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; + return Err(Error::illegal_argument(format!( + "Error: shared memory variable {map_env_var} is not set" + ))); + }; + let map_size = if let Ok(map_size_str) = std::env::var(map_size_env_var) { + map_size_str + .parse() + .map_err(|_| Error::illegal_argument(format!("Invalid {map_size_env_var} value")))? + } else { + map_size_default_fallback + }; + let shmem = shmem_provider.shmem_from_id_and_size(ShMemId::from_string(&id_str), map_size)?; + + Ok(shmem.into_raw()) +} + /// Guard [`map_shared_memory`] is invoked only once static SHM_MAP_GUARD: OnceLock<()> = OnceLock::new(); @@ -97,31 +129,18 @@ static SHM_MAP_GUARD: OnceLock<()> = OnceLock::new(); /// /// If anything failed, the forkserver will be notified with /// [`FS_ERROR_SHM_OPEN`]. -pub fn map_shared_memory() -> Result<(), Error> { +pub fn map_shared_memory(shmem_provider: &mut SHM) -> Result<(), Error> { if SHM_MAP_GUARD.set(()).is_err() { return Err(Error::illegal_state("shared memory has been mapped before")); } - map_shared_memory_internal() + map_shared_memory_internal(shmem_provider) } -fn map_shared_memory_internal() -> Result<(), Error> { - let Ok(id_str) = std::env::var(SHM_ENV_VAR) else { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument( - "Error: variable for edge coverage shared memory is not set", - )); - }; - let Ok(shm_id) = id_str.parse() else { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument("Invalid __AFL_SHM_ID value")); - }; - let map = unsafe { libc::shmat(shm_id, core::ptr::null(), 0) }; - if map.is_null() || core::ptr::eq(map, libc::MAP_FAILED) { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_state("shmat for map")); - } +fn map_shared_memory_internal(shmem_provider: &mut SHM) -> Result<(), Error> { + let target_ptr = + map_shared_memory_common(shmem_provider, SHM_ENV_VAR, AFL_MAP_SIZE_ENV_VAR, 65536)?; unsafe { - EDGES_MAP_PTR = map.cast(); + EDGES_MAP_PTR = target_ptr; } Ok(()) } @@ -134,32 +153,23 @@ static INPUT_SHM_MAP_GUARD: OnceLock<()> = OnceLock::new(); /// /// If anything failed, the forkserver will be notified with /// [`FS_ERROR_SHM_OPEN`]. -pub fn map_input_shared_memory() -> Result<(), Error> { +pub fn map_input_shared_memory(shmem_provider: &mut SHM) -> Result<(), Error> { if INPUT_SHM_MAP_GUARD.set(()).is_err() { return Err(Error::illegal_state("shared memory has been mapped before")); } - map_input_shared_memory_internal() + map_input_shared_memory_internal(shmem_provider) } -fn map_input_shared_memory_internal() -> Result<(), Error> { - let Ok(id_str) = std::env::var(SHM_FUZZ_ENV_VAR) else { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument( - "Error: variable for fuzzing shared memory is not set", - )); - }; - let Ok(shm_id) = id_str.parse() else { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument("Invalid __AFL_SHM_FUZZ_ID value")); - }; - let map = unsafe { libc::shmat(shm_id, core::ptr::null(), 0) }; - if map.is_null() || core::ptr::eq(map, libc::MAP_FAILED) { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_state( - "Could not access fuzzing shared memory", - )); - } - let map: *mut u32 = map.cast(); +fn map_input_shared_memory_internal( + shmem_provider: &mut SHM, +) -> Result<(), Error> { + let target_ptr = map_shared_memory_common( + shmem_provider, + SHM_FUZZ_ENV_VAR, + SHM_FUZZ_MAP_SIZE_ENV_VAR, + MAX_INPUT_SIZE_DEFAULT + SHMEM_FUZZ_HDR_SIZE, + )?; + let map: *mut u32 = target_ptr.cast(); unsafe { INPUT_LENGTH_PTR = map; INPUT_PTR = map.add(1).cast(); @@ -177,36 +187,33 @@ static CMPLOG_SHM_MAP_GUARD: OnceLock<()> = OnceLock::new(); /// If anything failed, the forkserver will be notified with /// [`FS_ERROR_SHM_OPEN`]. #[cfg(feature = "cmplog")] -pub fn map_cmplog_shared_memory() -> Result<(), Error> { +pub fn map_cmplog_shared_memory(shmem_provider: &mut SHM) -> Result<(), Error> { if CMPLOG_SHM_MAP_GUARD.set(()).is_err() { return Err(Error::illegal_state("shared memory has been mapped before")); } - map_cmplog_shared_memory_internal() + map_cmplog_shared_memory_internal(shmem_provider) } #[cfg(feature = "cmplog")] -fn map_cmplog_shared_memory_internal() -> Result<(), Error> { +fn map_cmplog_shared_memory_internal( + shmem_provider: &mut SHM, +) -> Result<(), Error> { let Ok(id_str) = std::env::var(SHM_CMPLOG_ENV_VAR) else { write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument( - "Error: variable for cmplog shared memory is not set", - )); - }; - let Ok(shm_id) = id_str.parse() else { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_argument("Invalid __AFL_CMPLOG_SHM_ID value")); + return Err(Error::illegal_argument(format!( + "Error: shared memory variable {SHM_CMPLOG_ENV_VAR} is not set" + ))); }; - let map = unsafe { libc::shmat(shm_id, core::ptr::null(), 0) }; - if map.is_null() || core::ptr::eq(map, libc::MAP_FAILED) { - write_error_to_forkserver(FS_ERROR_SHM_OPEN)?; - return Err(Error::illegal_state("shmat for map")); - } + let map_size = size_of::(); + let shmem = shmem_provider.shmem_from_id_and_size(ShMemId::from_string(&id_str), map_size)?; + + let target_ptr = shmem.into_raw(); unsafe { - CMPLOG_MAP_PTR = map.cast(); + CMPLOG_MAP_PTR = target_ptr; } #[cfg(feature = "cmplog_extended_instrumentation")] unsafe { - EXTENDED_CMPLOG_MAP_PTR = map.cast(); + EXTENDED_CMPLOG_MAP_PTR = target_ptr; } Ok(()) } From 88c550f36f5a9057f65d62ab31ef255004dde02e Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Sun, 18 May 2025 19:56:43 +0800 Subject: [PATCH 05/10] Fix clippy --- libafl_bolts/src/shmem.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/libafl_bolts/src/shmem.rs b/libafl_bolts/src/shmem.rs index 9d2dd86a95..4341a8eb93 100644 --- a/libafl_bolts/src/shmem.rs +++ b/libafl_bolts/src/shmem.rs @@ -4,10 +4,10 @@ #[cfg(feature = "alloc")] use alloc::{rc::Rc, string::ToString, vec::Vec}; #[cfg(feature = "alloc")] -use core::{cell::RefCell, fmt, fmt::Display, mem::ManuallyDrop}; +use core::{cell::RefCell, fmt, fmt::Display}; use core::{ fmt::Debug, - mem::size_of, + mem::{ManuallyDrop, size_of}, ops::{Deref, DerefMut}, }; #[cfg(feature = "std")] From f04e8457b7cda3c12e5fcdbe45203b6220389c79 Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Sun, 18 May 2025 20:02:36 +0800 Subject: [PATCH 06/10] Fix --- fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs | 2 +- fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs index f53c74b0f1..34da6d2728 100644 --- a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs +++ b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs @@ -1,4 +1,4 @@ -use libafl_bolts::shmem::StdShMemProvider; +use libafl_bolts::shmem::{ShMemProvider, StdShMemProvider}; use libafl_targets::{ map_input_shared_memory, map_shared_memory, start_forkserver, MaybePersistentForkserverParent, }; diff --git a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs index f53c74b0f1..34da6d2728 100644 --- a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs +++ b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs @@ -1,4 +1,4 @@ -use libafl_bolts::shmem::StdShMemProvider; +use libafl_bolts::shmem::{ShMemProvider, StdShMemProvider}; use libafl_targets::{ map_input_shared_memory, map_shared_memory, start_forkserver, MaybePersistentForkserverParent, }; From 1a3fe98d55458abbb7c52f10747e061c13b99ac9 Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Mon, 19 May 2025 16:44:29 +0800 Subject: [PATCH 07/10] Make shmem's into_raw private --- libafl_bolts/src/shmem.rs | 9 --------- libafl_targets/src/forkserver.rs | 13 +++++++++++-- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/libafl_bolts/src/shmem.rs b/libafl_bolts/src/shmem.rs index 4341a8eb93..084490b975 100644 --- a/libafl_bolts/src/shmem.rs +++ b/libafl_bolts/src/shmem.rs @@ -247,15 +247,6 @@ pub trait ShMem: Sized + Debug + Clone + DerefMut { } } - /// Consume current shared memory structure, and get the raw pointer to - /// this shared memory. - /// - /// Note that calling this method will result in a memory leak. - fn into_raw(self) -> *mut T { - let mut manually_dropped = ManuallyDrop::new(self); - manually_dropped.as_mut_ptr().cast() - } - /// Get the description of the shared memory mapping fn description(&self) -> ShMemDescription { ShMemDescription { diff --git a/libafl_targets/src/forkserver.rs b/libafl_targets/src/forkserver.rs index eade7ea448..5ee68e65da 100644 --- a/libafl_targets/src/forkserver.rs +++ b/libafl_targets/src/forkserver.rs @@ -97,6 +97,15 @@ fn read_u32_from_forkserver() -> Result { Ok(u32::from_ne_bytes(buf)) } +/// Consume current shared memory structure, and get the raw pointer to +/// this shared memory. +/// +/// Note that calling this method will result in a memory leak. +fn shmem_into_raw(shmem: impl ShMem) -> *mut T { + let mut manually_dropped = std::mem::ManuallyDrop::new(shmem); + manually_dropped.as_mut_ptr().cast() +} + fn map_shared_memory_common( shmem_provider: &mut SHM, map_env_var: &str, @@ -118,7 +127,7 @@ fn map_shared_memory_common( }; let shmem = shmem_provider.shmem_from_id_and_size(ShMemId::from_string(&id_str), map_size)?; - Ok(shmem.into_raw()) + Ok(shmem_into_raw(shmem)) } /// Guard [`map_shared_memory`] is invoked only once @@ -207,7 +216,7 @@ fn map_cmplog_shared_memory_internal( let map_size = size_of::(); let shmem = shmem_provider.shmem_from_id_and_size(ShMemId::from_string(&id_str), map_size)?; - let target_ptr = shmem.into_raw(); + let target_ptr = shmem_into_raw(shmem); unsafe { CMPLOG_MAP_PTR = target_ptr; } From cf1ceb58471c9bcf88d8ea5319f30e5dd4b9a8cc Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Mon, 19 May 2025 17:03:08 +0800 Subject: [PATCH 08/10] Log error message in forkserver --- .../forkserver_libafl_cc/src/lib.rs | 21 ++++++++++++------- .../fuzzbench_forkserver_sand/src/lib.rs | 21 ++++++++++++------- 2 files changed, 28 insertions(+), 14 deletions(-) diff --git a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs index 34da6d2728..22ad657413 100644 --- a/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs +++ b/fuzzers/forkserver/forkserver_libafl_cc/src/lib.rs @@ -5,20 +5,27 @@ use libafl_targets::{ #[no_mangle] pub extern "C" fn libafl_start_forkserver() { - let Ok(mut shm_provider) = StdShMemProvider::new() else { - std::process::exit(1); + let mut shm_provider = match StdShMemProvider::new() { + Ok(shm_provider) => shm_provider, + Err(err) => { + eprintln!("Forkserver failed to create shared memory provider: {err}"); + std::process::exit(1); + } }; // Map shared memory region for the edge coverage map - if map_shared_memory(&mut shm_provider).is_err() { + if let Err(err) = map_shared_memory(&mut shm_provider) { + eprintln!("Forkserver failed to create edge map: {err}"); std::process::exit(1); } // Map shared memory region for input and its len - if map_input_shared_memory(&mut shm_provider).is_err() { + if let Err(err) = map_input_shared_memory(&mut shm_provider) { + eprintln!("Forkserver failed to create input map: {err}"); std::process::exit(1); - }; + } // Start the forkserver - if start_forkserver(&mut MaybePersistentForkserverParent::new()).is_err() { + if let Err(err) = start_forkserver(&mut MaybePersistentForkserverParent::new()) { + eprintln!("Forkserver unexpected error: {err}"); std::process::exit(1); - }; + } } diff --git a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs index 34da6d2728..22ad657413 100644 --- a/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs +++ b/fuzzers/forkserver/fuzzbench_forkserver_sand/src/lib.rs @@ -5,20 +5,27 @@ use libafl_targets::{ #[no_mangle] pub extern "C" fn libafl_start_forkserver() { - let Ok(mut shm_provider) = StdShMemProvider::new() else { - std::process::exit(1); + let mut shm_provider = match StdShMemProvider::new() { + Ok(shm_provider) => shm_provider, + Err(err) => { + eprintln!("Forkserver failed to create shared memory provider: {err}"); + std::process::exit(1); + } }; // Map shared memory region for the edge coverage map - if map_shared_memory(&mut shm_provider).is_err() { + if let Err(err) = map_shared_memory(&mut shm_provider) { + eprintln!("Forkserver failed to create edge map: {err}"); std::process::exit(1); } // Map shared memory region for input and its len - if map_input_shared_memory(&mut shm_provider).is_err() { + if let Err(err) = map_input_shared_memory(&mut shm_provider) { + eprintln!("Forkserver failed to create input map: {err}"); std::process::exit(1); - }; + } // Start the forkserver - if start_forkserver(&mut MaybePersistentForkserverParent::new()).is_err() { + if let Err(err) = start_forkserver(&mut MaybePersistentForkserverParent::new()) { + eprintln!("Forkserver unexpected error: {err}"); std::process::exit(1); - }; + } } From 259730f0e3914eabe75d971a64868b0ca5bffb60 Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Mon, 19 May 2025 17:06:19 +0800 Subject: [PATCH 09/10] Fix clippy --- libafl_bolts/src/shmem.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/libafl_bolts/src/shmem.rs b/libafl_bolts/src/shmem.rs index 084490b975..4be592bfdd 100644 --- a/libafl_bolts/src/shmem.rs +++ b/libafl_bolts/src/shmem.rs @@ -4,10 +4,10 @@ #[cfg(feature = "alloc")] use alloc::{rc::Rc, string::ToString, vec::Vec}; #[cfg(feature = "alloc")] -use core::{cell::RefCell, fmt, fmt::Display}; +use core::{cell::RefCell, fmt, fmt::Display, mem::ManuallyDrop}; use core::{ fmt::Debug, - mem::{ManuallyDrop, size_of}, + mem::size_of, ops::{Deref, DerefMut}, }; #[cfg(feature = "std")] From 69236644d0759d005c2108591e9f61a26e8d4c33 Mon Sep 17 00:00:00 2001 From: Evian-Zhang Date: Mon, 19 May 2025 17:17:07 +0800 Subject: [PATCH 10/10] Fix clippy --- libafl_targets/src/forkserver.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libafl_targets/src/forkserver.rs b/libafl_targets/src/forkserver.rs index 5ee68e65da..738f374c8c 100644 --- a/libafl_targets/src/forkserver.rs +++ b/libafl_targets/src/forkserver.rs @@ -102,7 +102,7 @@ fn read_u32_from_forkserver() -> Result { /// /// Note that calling this method will result in a memory leak. fn shmem_into_raw(shmem: impl ShMem) -> *mut T { - let mut manually_dropped = std::mem::ManuallyDrop::new(shmem); + let mut manually_dropped = core::mem::ManuallyDrop::new(shmem); manually_dropped.as_mut_ptr().cast() }