diff --git a/fuzzers/wcet_qemu_sys/src/sysstate/feedbacks.rs b/fuzzers/wcet_qemu_sys/src/sysstate/feedbacks.rs index 988ba3eb37..e2838bab94 100644 --- a/fuzzers/wcet_qemu_sys/src/sysstate/feedbacks.rs +++ b/fuzzers/wcet_qemu_sys/src/sysstate/feedbacks.rs @@ -213,6 +213,8 @@ impl HitSysStateFeedback { pub struct DumpSystraceFeedback { dumpfile: Option, + dump_metadata: bool, + last_trace: Option>, } impl Feedback for DumpSystraceFeedback @@ -239,9 +241,28 @@ where std::fs::write(s,ron::to_string(&observer.last_run).expect("Error serializing hashmap")).expect("Can not dump to file"); self.dumpfile = None }, - None => println!("{:?}",observer.last_run), + None => if !self.dump_metadata {println!("{:?}",observer.last_run);} }; - Ok(true) + if self.dump_metadata {self.last_trace=Some(observer.last_run.clone());} + Ok(!self.dump_metadata) + } + /// Append to the testcase the generated metadata in case of a new corpus item + #[inline] + fn append_metadata(&mut self, _state: &mut S, testcase: &mut Testcase) -> Result<(), Error> { + if !self.dump_metadata {return Ok(());} + let a = self.last_trace.take(); + match a { + Some(s) => testcase.metadata_mut().insert(FreeRTOSSystemStateMetadata::new(s)), + None => (), + } + Ok(()) + } + + /// Discard the stored metadata in case that the testcase is not added to the corpus + #[inline] + fn discard_metadata(&mut self, _state: &mut S, _input: &I) -> Result<(), Error> { + self.last_trace = None; + Ok(()) } } @@ -258,9 +279,12 @@ impl DumpSystraceFeedback /// Creates a new [`DumpSystraceFeedback`] #[must_use] pub fn new() -> Self { - Self {dumpfile: None} + Self {dumpfile: None, dump_metadata: false, last_trace: None} } pub fn with_dump(dumpfile: Option) -> Self { - Self {dumpfile: dumpfile} + Self {dumpfile: dumpfile, dump_metadata: false, last_trace: None} + } + pub fn metadata_only() -> Self { + Self {dumpfile: None, dump_metadata: true, last_trace: None} } } \ No newline at end of file diff --git a/fuzzers/wcet_qemu_sys/src/worst.rs b/fuzzers/wcet_qemu_sys/src/worst.rs index 3bd837a9e0..dba07641a8 100644 --- a/fuzzers/wcet_qemu_sys/src/worst.rs +++ b/fuzzers/wcet_qemu_sys/src/worst.rs @@ -82,7 +82,7 @@ where impl HasLen for QemuHashMapObserver where - M: MapObserver, + M: MapObserver, T: PrimInt + Default + Copy + 'static + Serialize + serde::de::DeserializeOwned + Debug, { #[inline] @@ -91,18 +91,18 @@ where } } -impl MapObserver for QemuHashMapObserver +impl MapObserver for QemuHashMapObserver where - M: MapObserver, + M: MapObserver, T: PrimInt + Default + Copy + 'static + Serialize + serde::de::DeserializeOwned + Debug, { #[inline] - fn map(&self) -> Option<&[u8]> { + fn map(&self) -> Option<&[T]> { self.base.map() } #[inline] - fn map_mut(&mut self) -> Option<&mut [u8]> { + fn map_mut(&mut self) -> Option<&mut [T]> { self.base.map_mut() } @@ -112,17 +112,17 @@ where } #[inline] - fn initial(&self) -> u8 { + fn initial(&self) -> T { self.base.initial() } #[inline] - fn initial_mut(&mut self) -> &mut u8 { + fn initial_mut(&mut self) -> &mut T { self.base.initial_mut() } #[inline] - fn set_initial(&mut self, initial: u8) { + fn set_initial(&mut self, initial: T) { self.base.set_initial(initial); } } @@ -364,6 +364,23 @@ where } //=========================== Debugging Feedback +#[derive(Debug, Default, Serialize, Deserialize, Clone)] +pub struct DumpEdgesMapMetadata +{ + pub map: HashMap<(u64, u64), usize>, +} + +impl DumpEdgesMapMetadata +{ + #[must_use] + pub fn new(input: HashMap<(u64,u64),usize>) -> Self { + Self { + map: input, + } + } +} + +libafl::impl_serdeany!(DumpEdgesMapMetadata); /// A [`Feedback`] meant to dump the edgemap for debugging. #[derive(Debug)] pub struct DumpMapFeedback @@ -373,6 +390,8 @@ where { dumpfile: Option, phantom: PhantomData<(O, T)>, + dump_metadata: bool, + last_map: Option>, } impl Feedback for DumpMapFeedback @@ -401,9 +420,34 @@ where fs::write(s,ron::to_string(&observer.edgemap).expect("Error serializing hashmap")).expect("Can not dump to file"); self.dumpfile = None }, - None => println!("{:?}",observer.edgemap), + None => if !self.dump_metadata {println!("{:?}",observer.edgemap);} }; - Ok(true) + if self.dump_metadata {self.last_map=Some(observer.edgemap.clone());} + Ok(!self.dump_metadata) + } + /// Append to the testcase the generated metadata in case of a new corpus item + #[inline] + fn append_metadata(&mut self, _state: &mut S, testcase: &mut Testcase) -> Result<(), Error> { + if !self.dump_metadata {return Ok(());} + let a = self.last_map.take(); + match a { + Some(s) => { + let mut tmp : HashMap<(u64,u64),usize> = HashMap::new(); + for (k, v) in s.iter() { + tmp.insert(*k, T::to_usize(v).unwrap()); + } + testcase.metadata_mut().insert(DumpEdgesMapMetadata::new(tmp)); + } + None => (), + } + Ok(()) + } + + /// Discard the stored metadata in case that the testcase is not added to the corpus + #[inline] + fn discard_metadata(&mut self, _state: &mut S, _input: &I) -> Result<(), Error> { + self.last_map = None; + Ok(()) } } @@ -426,11 +470,15 @@ where /// Creates a new [`HitFeedback`] #[must_use] pub fn new(_map_observer: &QemuHashMapObserver) -> Self { - Self {dumpfile: None, phantom: PhantomData} + Self {dumpfile: None, phantom: PhantomData, dump_metadata: false, last_map: None} } pub fn with_dump(dumpfile: Option,_map_observer: &QemuHashMapObserver) -> Self { - Self {dumpfile: dumpfile, phantom: PhantomData} + Self {dumpfile: dumpfile, phantom: PhantomData, dump_metadata: false, last_map: None} } + pub fn metadata_only(_map_observer: &QemuHashMapObserver) -> Self { + Self {dumpfile: None, phantom: PhantomData, dump_metadata: true, last_map: None} + } + } //=========================== Debugging Feedback diff --git a/libafl/src/feedbacks/map.rs b/libafl/src/feedbacks/map.rs index 8abf2dd24d..9fef754200 100644 --- a/libafl/src/feedbacks/map.rs +++ b/libafl/src/feedbacks/map.rs @@ -294,7 +294,7 @@ where impl MapFeedbackState where - T: PrimInt + Default + Copy + 'static + Serialize + serde::de::DeserializeOwned, + T: Debug + PrimInt + Default + Copy + 'static + Serialize + serde::de::DeserializeOwned, { /// Create new `MapFeedbackState` #[must_use] @@ -309,7 +309,6 @@ where pub fn with_observer(map_observer: &O) -> Self where O: MapObserver, - T: Debug, { Self { history_map: vec![T::min_value(); map_observer.len()], diff --git a/libafl_targets/src/coverage.rs b/libafl_targets/src/coverage.rs index feb2fb5b91..280ae47dd5 100644 --- a/libafl_targets/src/coverage.rs +++ b/libafl_targets/src/coverage.rs @@ -4,7 +4,7 @@ use crate::EDGES_MAP_SIZE; /// The map for edges. #[no_mangle] -pub static mut __afl_area_ptr_local: [u8; EDGES_MAP_SIZE] = [0; EDGES_MAP_SIZE]; +pub static mut __afl_area_ptr_local: [u16; EDGES_MAP_SIZE] = [0u16; EDGES_MAP_SIZE]; pub use __afl_area_ptr_local as EDGES_MAP; /// The max count of edges tracked. @@ -12,7 +12,7 @@ pub static mut MAX_EDGES_NUM: usize = 0; extern "C" { /// The area pointer points to the edges map. - pub static mut __afl_area_ptr: *mut u8; + pub static mut __afl_area_ptr: *mut u16; } pub use __afl_area_ptr as EDGES_MAP_PTR; @@ -29,7 +29,7 @@ use libafl::bolts::ownedref::OwnedSliceMut; /// This function will crash if `EDGES_MAP_PTR` is not a valid pointer. /// The `EDGES_MAP_PTR_SIZE` needs to be smaller than, or equal to the size of the map. #[must_use] -pub unsafe fn edges_map_from_ptr<'a>() -> OwnedSliceMut<'a, u8> { +pub unsafe fn edges_map_from_ptr<'a>() -> OwnedSliceMut<'a, u16> { debug_assert!(!EDGES_MAP_PTR.is_null()); OwnedSliceMut::from_raw_parts_mut(EDGES_MAP_PTR, EDGES_MAP_PTR_SIZE) }