Remove executor hooks (#124)
* remove HasExecHooks from Executor * adapt the frida executor * adapt frida and avoid recursive type infearence * fix win build
This commit is contained in:
parent
7493b59ba8
commit
46716e8090
@ -20,7 +20,7 @@ use libafl::{
|
|||||||
QueueCorpusScheduler,
|
QueueCorpusScheduler,
|
||||||
},
|
},
|
||||||
executors::{
|
executors::{
|
||||||
inprocess::InProcessExecutor, timeout::TimeoutExecutor, Executor, ExitKind, HasExecHooks,
|
inprocess::InProcessExecutor, timeout::TimeoutExecutor, Executor, ExitKind,
|
||||||
HasExecHooksTuple, HasObservers, HasObserversHooks,
|
HasExecHooksTuple, HasObservers, HasObserversHooks,
|
||||||
},
|
},
|
||||||
feedback_or,
|
feedback_or,
|
||||||
@ -65,7 +65,7 @@ where
|
|||||||
I: Input + HasTargetBytes,
|
I: Input + HasTargetBytes,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
{
|
{
|
||||||
base: TimeoutExecutor<InProcessExecutor<'a, H, I, OT, S>, I>,
|
base: TimeoutExecutor<InProcessExecutor<'a, H, I, OT, S>>,
|
||||||
/// Frida's dynamic rewriting engine
|
/// Frida's dynamic rewriting engine
|
||||||
stalker: Stalker<'a>,
|
stalker: Stalker<'a>,
|
||||||
/// User provided callback for instrumentation
|
/// User provided callback for instrumentation
|
||||||
@ -74,7 +74,7 @@ where
|
|||||||
_phantom: PhantomData<&'b u8>,
|
_phantom: PhantomData<&'b u8>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, 'b, 'c, FH, H, I, OT, S> Executor<I>
|
impl<'a, 'b, 'c, EM, FH, H, I, OT, S, Z> Executor<EM, I, S, Z>
|
||||||
for FridaInProcessExecutor<'a, 'b, 'c, FH, H, I, OT, S>
|
for FridaInProcessExecutor<'a, 'b, 'c, FH, H, I, OT, S>
|
||||||
where
|
where
|
||||||
FH: FridaHelper<'b>,
|
FH: FridaHelper<'b>,
|
||||||
@ -84,7 +84,14 @@ where
|
|||||||
{
|
{
|
||||||
/// Instruct the target about the input and run
|
/// Instruct the target about the input and run
|
||||||
#[inline]
|
#[inline]
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
|
&mut self,
|
||||||
|
fuzzer: &mut Z,
|
||||||
|
state: &mut S,
|
||||||
|
mgr: &mut EM,
|
||||||
|
input: &I,
|
||||||
|
) -> Result<ExitKind, Error> {
|
||||||
|
self.helper.pre_exec(input);
|
||||||
if self.helper.stalker_enabled() {
|
if self.helper.stalker_enabled() {
|
||||||
if self.followed {
|
if self.followed {
|
||||||
self.stalker.activate(NativePointer(
|
self.stalker.activate(NativePointer(
|
||||||
@ -96,7 +103,7 @@ where
|
|||||||
.follow_me::<NoneEventSink>(self.helper.transformer(), None);
|
.follow_me::<NoneEventSink>(self.helper.transformer(), None);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
let res = self.base.run_target(input);
|
let res = self.base.run_target(fuzzer, state, mgr, input);
|
||||||
if self.helper.stalker_enabled() {
|
if self.helper.stalker_enabled() {
|
||||||
self.stalker.deactivate();
|
self.stalker.deactivate();
|
||||||
}
|
}
|
||||||
@ -109,42 +116,8 @@ where
|
|||||||
if self.helper.stalker_enabled() {
|
if self.helper.stalker_enabled() {
|
||||||
self.stalker.deactivate();
|
self.stalker.deactivate();
|
||||||
}
|
}
|
||||||
res
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a, 'b, 'c, EM, FH, H, I, OT, S, Z> HasExecHooks<EM, I, S, Z>
|
|
||||||
for FridaInProcessExecutor<'a, 'b, 'c, FH, H, I, OT, S>
|
|
||||||
where
|
|
||||||
FH: FridaHelper<'b>,
|
|
||||||
H: FnMut(&I) -> ExitKind,
|
|
||||||
I: Input + HasTargetBytes,
|
|
||||||
OT: ObserversTuple,
|
|
||||||
{
|
|
||||||
/// Called right before exexution starts
|
|
||||||
#[inline]
|
|
||||||
fn pre_exec(
|
|
||||||
&mut self,
|
|
||||||
fuzzer: &mut Z,
|
|
||||||
state: &mut S,
|
|
||||||
event_mgr: &mut EM,
|
|
||||||
input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
self.helper.pre_exec(input);
|
|
||||||
self.base.pre_exec(fuzzer, state, event_mgr, input)
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Called right after execution finished.
|
|
||||||
#[inline]
|
|
||||||
fn post_exec(
|
|
||||||
&mut self,
|
|
||||||
fuzzer: &mut Z,
|
|
||||||
state: &mut S,
|
|
||||||
event_mgr: &mut EM,
|
|
||||||
input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
self.helper.post_exec(input);
|
self.helper.post_exec(input);
|
||||||
self.base.post_exec(fuzzer, state, event_mgr, input)
|
res
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -328,6 +328,7 @@ where
|
|||||||
event: Event<I>,
|
event: Event<I>,
|
||||||
) -> Result<(), Error>
|
) -> Result<(), Error>
|
||||||
where
|
where
|
||||||
|
E: Executor<Self, I, S, Z>,
|
||||||
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
||||||
{
|
{
|
||||||
match event {
|
match event {
|
||||||
@ -346,6 +347,7 @@ where
|
|||||||
|
|
||||||
let observers: OT = postcard::from_bytes(&observers_buf)?;
|
let observers: OT = postcard::from_bytes(&observers_buf)?;
|
||||||
// TODO include ExitKind in NewTestcase
|
// TODO include ExitKind in NewTestcase
|
||||||
|
// TODO check for objective too
|
||||||
let is_interesting =
|
let is_interesting =
|
||||||
fuzzer.is_interesting(state, self, &input, &observers, &ExitKind::Ok)?;
|
fuzzer.is_interesting(state, self, &input, &observers, &ExitKind::Ok)?;
|
||||||
if fuzzer
|
if fuzzer
|
||||||
@ -423,7 +425,7 @@ impl<E, I, OT, S, SP, ST, Z> EventProcessor<E, S, Z> for LlmpEventManager<I, OT,
|
|||||||
where
|
where
|
||||||
SP: ShMemProvider,
|
SP: ShMemProvider,
|
||||||
ST: Stats,
|
ST: Stats,
|
||||||
E: Executor<I>,
|
E: Executor<Self, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>, //CE: CustomEvent<I>,
|
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>, //CE: CustomEvent<I>,
|
||||||
@ -469,7 +471,7 @@ impl<E, I, OT, S, SP, ST, Z> EventManager<E, I, S, Z> for LlmpEventManager<I, OT
|
|||||||
where
|
where
|
||||||
SP: ShMemProvider,
|
SP: ShMemProvider,
|
||||||
ST: Stats,
|
ST: Stats,
|
||||||
E: Executor<I>,
|
E: Executor<Self, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>, //CE: CustomEvent<I>,
|
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>, //CE: CustomEvent<I>,
|
||||||
@ -573,7 +575,7 @@ where
|
|||||||
impl<E, I, OT, S, SP, ST, Z> EventProcessor<E, S, Z>
|
impl<E, I, OT, S, SP, ST, Z> EventProcessor<E, S, Z>
|
||||||
for LlmpRestartingEventManager<I, OT, S, SP, ST>
|
for LlmpRestartingEventManager<I, OT, S, SP, ST>
|
||||||
where
|
where
|
||||||
E: Executor<I>,
|
E: Executor<LlmpEventManager<I, OT, S, SP, ST>, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
@ -589,7 +591,7 @@ where
|
|||||||
impl<E, I, OT, S, SP, ST, Z> EventManager<E, I, S, Z>
|
impl<E, I, OT, S, SP, ST, Z> EventManager<E, I, S, Z>
|
||||||
for LlmpRestartingEventManager<I, OT, S, SP, ST>
|
for LlmpRestartingEventManager<I, OT, S, SP, ST>
|
||||||
where
|
where
|
||||||
E: Executor<I>,
|
E: Executor<LlmpEventManager<I, OT, S, SP, ST>, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
S: Serialize,
|
S: Serialize,
|
||||||
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
Z: IfInteresting<I, S> + IsInteresting<I, OT, S>,
|
||||||
|
@ -1,41 +1,22 @@
|
|||||||
//! A `CombinedExecutor` wraps a primary executor and a secondary one
|
//! A `CombinedExecutor` wraps a primary executor and a secondary one
|
||||||
|
|
||||||
use core::marker::PhantomData;
|
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
executors::{
|
executors::{Executor, ExitKind, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
Executor, ExitKind, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks,
|
|
||||||
},
|
|
||||||
inputs::Input,
|
inputs::Input,
|
||||||
observers::ObserversTuple,
|
observers::ObserversTuple,
|
||||||
Error,
|
Error,
|
||||||
};
|
};
|
||||||
|
|
||||||
/// A [`CombinedExecutor`] wraps a primary executor, forwarding its methods, and a secondary one
|
/// A [`CombinedExecutor`] wraps a primary executor, forwarding its methods, and a secondary one
|
||||||
pub struct CombinedExecutor<A, B, I>
|
pub struct CombinedExecutor<A, B> {
|
||||||
where
|
|
||||||
A: Executor<I>,
|
|
||||||
B: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
primary: A,
|
primary: A,
|
||||||
secondary: B,
|
secondary: B,
|
||||||
phantom: PhantomData<I>,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<A, B, I> CombinedExecutor<A, B, I>
|
impl<A, B> CombinedExecutor<A, B> {
|
||||||
where
|
|
||||||
A: Executor<I>,
|
|
||||||
B: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
/// Create a new `CombinedExecutor`, wrapping the given `executor`s.
|
/// Create a new `CombinedExecutor`, wrapping the given `executor`s.
|
||||||
pub fn new(primary: A, secondary: B) -> Self {
|
pub fn new<EM, I, S, Z>(primary: A, secondary: B) -> Self {
|
||||||
Self {
|
Self { primary, secondary }
|
||||||
primary,
|
|
||||||
secondary,
|
|
||||||
phantom: PhantomData,
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Retrieve the primary `Executor` that is wrapped by this `CombinedExecutor`.
|
/// Retrieve the primary `Executor` that is wrapped by this `CombinedExecutor`.
|
||||||
@ -49,22 +30,26 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<A, B, I> Executor<I> for CombinedExecutor<A, B, I>
|
impl<A, B, EM, I, S, Z> Executor<EM, I, S, Z> for CombinedExecutor<A, B>
|
||||||
where
|
where
|
||||||
A: Executor<I>,
|
A: Executor<EM, I, S, Z>,
|
||||||
B: Executor<I>,
|
B: Executor<EM, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
{
|
{
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
self.primary.run_target(input)
|
&mut self,
|
||||||
|
fuzzer: &mut Z,
|
||||||
|
state: &mut S,
|
||||||
|
mgr: &mut EM,
|
||||||
|
input: &I,
|
||||||
|
) -> Result<ExitKind, Error> {
|
||||||
|
self.primary.run_target(fuzzer, state, mgr, input)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<A, B, I, OT> HasObservers<OT> for CombinedExecutor<A, B, I>
|
impl<A, B, OT> HasObservers<OT> for CombinedExecutor<A, B>
|
||||||
where
|
where
|
||||||
A: Executor<I> + HasObservers<OT>,
|
A: HasObservers<OT>,
|
||||||
B: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
{
|
{
|
||||||
#[inline]
|
#[inline]
|
||||||
@ -78,40 +63,10 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<A, B, EM, I, OT, S, Z> HasObserversHooks<EM, I, OT, S, Z> for CombinedExecutor<A, B, I>
|
impl<A, B, EM, I, OT, S, Z> HasObserversHooks<EM, I, OT, S, Z> for CombinedExecutor<A, B>
|
||||||
where
|
where
|
||||||
A: Executor<I> + HasObservers<OT>,
|
A: HasObservers<OT>,
|
||||||
B: Executor<I>,
|
|
||||||
I: Input,
|
I: Input,
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<A, B, EM, I, S, Z> HasExecHooks<EM, I, S, Z> for CombinedExecutor<A, B, I>
|
|
||||||
where
|
|
||||||
A: Executor<I> + HasExecHooks<EM, I, S, Z>,
|
|
||||||
B: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
#[inline]
|
|
||||||
fn pre_exec(
|
|
||||||
&mut self,
|
|
||||||
fuzzer: &mut Z,
|
|
||||||
state: &mut S,
|
|
||||||
mgr: &mut EM,
|
|
||||||
input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
self.primary.pre_exec(fuzzer, state, mgr, input)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn post_exec(
|
|
||||||
&mut self,
|
|
||||||
fuzzer: &mut Z,
|
|
||||||
state: &mut S,
|
|
||||||
mgr: &mut EM,
|
|
||||||
input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
self.primary.post_exec(fuzzer, state, mgr, input)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
@ -13,9 +13,7 @@ use std::{
|
|||||||
|
|
||||||
use crate::bolts::os::{dup2, pipes::Pipe};
|
use crate::bolts::os::{dup2, pipes::Pipe};
|
||||||
use crate::{
|
use crate::{
|
||||||
executors::{
|
executors::{Executor, ExitKind, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
Executor, ExitKind, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks,
|
|
||||||
},
|
|
||||||
inputs::{HasTargetBytes, Input},
|
inputs::{HasTargetBytes, Input},
|
||||||
observers::ObserversTuple,
|
observers::ObserversTuple,
|
||||||
Error,
|
Error,
|
||||||
@ -328,13 +326,19 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<I, OT> Executor<I> for ForkserverExecutor<I, OT>
|
impl<EM, I, OT, S, Z> Executor<EM, I, S, Z> for ForkserverExecutor<I, OT>
|
||||||
where
|
where
|
||||||
I: Input + HasTargetBytes,
|
I: Input + HasTargetBytes,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
{
|
{
|
||||||
#[inline]
|
#[inline]
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
|
&mut self,
|
||||||
|
_fuzzer: &mut Z,
|
||||||
|
_state: &mut S,
|
||||||
|
_mgr: &mut EM,
|
||||||
|
input: &I,
|
||||||
|
) -> Result<ExitKind, Error> {
|
||||||
let mut exit_kind = ExitKind::Ok;
|
let mut exit_kind = ExitKind::Ok;
|
||||||
|
|
||||||
// Write to testcase
|
// Write to testcase
|
||||||
@ -377,13 +381,6 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<EM, I, OT, S, Z> HasExecHooks<EM, I, S, Z> for ForkserverExecutor<I, OT>
|
|
||||||
where
|
|
||||||
I: Input + HasTargetBytes,
|
|
||||||
OT: ObserversTuple,
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<I, OT> HasObservers<OT> for ForkserverExecutor<I, OT>
|
impl<I, OT> HasObservers<OT> for ForkserverExecutor<I, OT>
|
||||||
where
|
where
|
||||||
I: Input + HasTargetBytes,
|
I: Input + HasTargetBytes,
|
||||||
|
@ -18,9 +18,7 @@ use crate::bolts::os::windows_exceptions::setup_exception_handler;
|
|||||||
use crate::{
|
use crate::{
|
||||||
corpus::Corpus,
|
corpus::Corpus,
|
||||||
events::{EventFirer, EventRestarter},
|
events::{EventFirer, EventRestarter},
|
||||||
executors::{
|
executors::{Executor, ExitKind, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
Executor, ExitKind, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks,
|
|
||||||
},
|
|
||||||
feedbacks::Feedback,
|
feedbacks::Feedback,
|
||||||
fuzzer::HasObjective,
|
fuzzer::HasObjective,
|
||||||
inputs::Input,
|
inputs::Input,
|
||||||
@ -43,39 +41,26 @@ where
|
|||||||
phantom: PhantomData<(I, S)>,
|
phantom: PhantomData<(I, S)>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, H, I, OT, S> Executor<I> for InProcessExecutor<'a, H, I, OT, S>
|
impl<'a, EM, H, I, OT, S, Z> Executor<EM, I, S, Z> for InProcessExecutor<'a, H, I, OT, S>
|
||||||
where
|
where
|
||||||
H: FnMut(&I) -> ExitKind,
|
H: FnMut(&I) -> ExitKind,
|
||||||
I: Input,
|
I: Input,
|
||||||
OT: ObserversTuple,
|
OT: ObserversTuple,
|
||||||
{
|
{
|
||||||
#[inline]
|
#[inline]
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
let ret = (self.harness_fn)(input);
|
|
||||||
Ok(ret)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<'a, EM, H, I, OT, S, Z> HasExecHooks<EM, I, S, Z> for InProcessExecutor<'a, H, I, OT, S>
|
|
||||||
where
|
|
||||||
H: FnMut(&I) -> ExitKind,
|
|
||||||
I: Input,
|
|
||||||
OT: ObserversTuple,
|
|
||||||
{
|
|
||||||
#[inline]
|
|
||||||
fn pre_exec(
|
|
||||||
&mut self,
|
&mut self,
|
||||||
_fuzzer: &mut Z,
|
fuzzer: &mut Z,
|
||||||
_state: &mut S,
|
state: &mut S,
|
||||||
_event_mgr: &mut EM,
|
mgr: &mut EM,
|
||||||
_input: &I,
|
input: &I,
|
||||||
) -> Result<(), Error> {
|
) -> Result<ExitKind, Error> {
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
unsafe {
|
unsafe {
|
||||||
let data = &mut unix_signal_handler::GLOBAL_STATE;
|
let data = &mut unix_signal_handler::GLOBAL_STATE;
|
||||||
write_volatile(
|
write_volatile(
|
||||||
&mut data.current_input_ptr,
|
&mut data.current_input_ptr,
|
||||||
_input as *const _ as *const c_void,
|
input as *const _ as *const c_void,
|
||||||
);
|
);
|
||||||
write_volatile(
|
write_volatile(
|
||||||
&mut data.observers_ptr,
|
&mut data.observers_ptr,
|
||||||
@ -83,9 +68,9 @@ where
|
|||||||
);
|
);
|
||||||
// Direct raw pointers access /aliasing is pretty undefined behavior.
|
// Direct raw pointers access /aliasing is pretty undefined behavior.
|
||||||
// Since the state and event may have moved in memory, refresh them right before the signal may happen
|
// Since the state and event may have moved in memory, refresh them right before the signal may happen
|
||||||
write_volatile(&mut data.state_ptr, _state as *mut _ as *mut c_void);
|
write_volatile(&mut data.state_ptr, state as *mut _ as *mut c_void);
|
||||||
write_volatile(&mut data.event_mgr_ptr, _event_mgr as *mut _ as *mut c_void);
|
write_volatile(&mut data.event_mgr_ptr, mgr as *mut _ as *mut c_void);
|
||||||
write_volatile(&mut data.fuzzer_ptr, _fuzzer as *mut _ as *mut c_void);
|
write_volatile(&mut data.fuzzer_ptr, fuzzer as *mut _ as *mut c_void);
|
||||||
compiler_fence(Ordering::SeqCst);
|
compiler_fence(Ordering::SeqCst);
|
||||||
}
|
}
|
||||||
#[cfg(all(windows, feature = "std"))]
|
#[cfg(all(windows, feature = "std"))]
|
||||||
@ -93,7 +78,7 @@ where
|
|||||||
let data = &mut windows_exception_handler::GLOBAL_STATE;
|
let data = &mut windows_exception_handler::GLOBAL_STATE;
|
||||||
write_volatile(
|
write_volatile(
|
||||||
&mut data.current_input_ptr,
|
&mut data.current_input_ptr,
|
||||||
_input as *const _ as *const c_void,
|
input as *const _ as *const c_void,
|
||||||
);
|
);
|
||||||
write_volatile(
|
write_volatile(
|
||||||
&mut data.observers_ptr,
|
&mut data.observers_ptr,
|
||||||
@ -101,22 +86,14 @@ where
|
|||||||
);
|
);
|
||||||
// Direct raw pointers access /aliasing is pretty undefined behavior.
|
// Direct raw pointers access /aliasing is pretty undefined behavior.
|
||||||
// Since the state and event may have moved in memory, refresh them right before the signal may happen
|
// Since the state and event may have moved in memory, refresh them right before the signal may happen
|
||||||
write_volatile(&mut data.state_ptr, _state as *mut _ as *mut c_void);
|
write_volatile(&mut data.state_ptr, state as *mut _ as *mut c_void);
|
||||||
write_volatile(&mut data.event_mgr_ptr, _event_mgr as *mut _ as *mut c_void);
|
write_volatile(&mut data.event_mgr_ptr, mgr as *mut _ as *mut c_void);
|
||||||
write_volatile(&mut data.fuzzer_ptr, _fuzzer as *mut _ as *mut c_void);
|
write_volatile(&mut data.fuzzer_ptr, fuzzer as *mut _ as *mut c_void);
|
||||||
compiler_fence(Ordering::SeqCst);
|
compiler_fence(Ordering::SeqCst);
|
||||||
}
|
}
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
let ret = (self.harness_fn)(input);
|
||||||
fn post_exec(
|
|
||||||
&mut self,
|
|
||||||
_fuzzer: &mut Z,
|
|
||||||
_state: &mut S,
|
|
||||||
_event_mgr: &mut EM,
|
|
||||||
_input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
unsafe {
|
unsafe {
|
||||||
write_volatile(
|
write_volatile(
|
||||||
@ -133,7 +110,8 @@ where
|
|||||||
);
|
);
|
||||||
compiler_fence(Ordering::SeqCst);
|
compiler_fence(Ordering::SeqCst);
|
||||||
}
|
}
|
||||||
Ok(())
|
|
||||||
|
Ok(ret)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -742,6 +720,8 @@ mod tests {
|
|||||||
phantom: PhantomData,
|
phantom: PhantomData,
|
||||||
};
|
};
|
||||||
let input = NopInput {};
|
let input = NopInput {};
|
||||||
assert!(in_process_executor.run_target(&input).is_ok());
|
assert!(in_process_executor
|
||||||
|
.run_target(&mut (), &mut (), &mut (), &input)
|
||||||
|
.is_ok());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -13,8 +13,6 @@ pub use forkserver::{Forkserver, ForkserverExecutor, OutFile};
|
|||||||
pub mod combined;
|
pub mod combined;
|
||||||
pub use combined::CombinedExecutor;
|
pub use combined::CombinedExecutor;
|
||||||
|
|
||||||
use core::marker::PhantomData;
|
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
bolts::serdeany::SerdeAny,
|
bolts::serdeany::SerdeAny,
|
||||||
inputs::{HasTargetBytes, Input},
|
inputs::{HasTargetBytes, Input},
|
||||||
@ -184,25 +182,35 @@ where
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// An executor takes the given inputs, and runs the harness/target.
|
/// An executor takes the given inputs, and runs the harness/target.
|
||||||
pub trait Executor<I>
|
pub trait Executor<EM, I, S, Z>
|
||||||
where
|
where
|
||||||
I: Input,
|
I: Input,
|
||||||
{
|
{
|
||||||
/// Instruct the target about the input and run
|
/// Instruct the target about the input and run
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error>;
|
fn run_target(
|
||||||
|
&mut self,
|
||||||
|
fuzzer: &mut Z,
|
||||||
|
state: &mut S,
|
||||||
|
mgr: &mut EM,
|
||||||
|
input: &I,
|
||||||
|
) -> Result<ExitKind, Error>;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A simple executor that does nothing.
|
/// A simple executor that does nothing.
|
||||||
/// If intput len is 0, `run_target` will return Err
|
/// If intput len is 0, `run_target` will return Err
|
||||||
struct NopExecutor<EM, I, S> {
|
struct NopExecutor {}
|
||||||
phantom: PhantomData<(EM, I, S)>,
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<EM, I, S> Executor<I> for NopExecutor<EM, I, S>
|
impl<EM, I, S, Z> Executor<EM, I, S, Z> for NopExecutor
|
||||||
where
|
where
|
||||||
I: Input + HasTargetBytes,
|
I: Input + HasTargetBytes,
|
||||||
{
|
{
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
|
&mut self,
|
||||||
|
_fuzzer: &mut Z,
|
||||||
|
_state: &mut S,
|
||||||
|
_mgr: &mut EM,
|
||||||
|
input: &I,
|
||||||
|
) -> Result<ExitKind, Error> {
|
||||||
if input.target_bytes().as_slice().is_empty() {
|
if input.target_bytes().as_slice().is_empty() {
|
||||||
Err(Error::Empty("Input Empty".into()))
|
Err(Error::Empty("Input Empty".into()))
|
||||||
} else {
|
} else {
|
||||||
@ -211,13 +219,8 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<EM, I, S, Z> HasExecHooks<EM, I, S, Z> for NopExecutor<EM, I, S> where I: Input + HasTargetBytes
|
|
||||||
{}
|
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod test {
|
mod test {
|
||||||
use core::marker::PhantomData;
|
|
||||||
|
|
||||||
use super::{Executor, NopExecutor};
|
use super::{Executor, NopExecutor};
|
||||||
use crate::inputs::BytesInput;
|
use crate::inputs::BytesInput;
|
||||||
|
|
||||||
@ -225,10 +228,12 @@ mod test {
|
|||||||
fn nop_executor() {
|
fn nop_executor() {
|
||||||
let empty_input = BytesInput::new(vec![]);
|
let empty_input = BytesInput::new(vec![]);
|
||||||
let nonempty_input = BytesInput::new(vec![1u8]);
|
let nonempty_input = BytesInput::new(vec![1u8]);
|
||||||
let mut executor = NopExecutor::<(), _, ()> {
|
let mut executor = NopExecutor {};
|
||||||
phantom: PhantomData,
|
assert!(executor
|
||||||
};
|
.run_target(&mut (), &mut (), &mut (), &empty_input)
|
||||||
assert!(executor.run_target(&empty_input).is_err());
|
.is_err());
|
||||||
assert!(executor.run_target(&nonempty_input).is_ok());
|
assert!(executor
|
||||||
|
.run_target(&mut (), &mut (), &mut (), &nonempty_input)
|
||||||
|
.is_ok());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,11 +1,9 @@
|
|||||||
//! A `TimeoutExecutor` sets a timeout before each target run
|
//! A `TimeoutExecutor` sets a timeout before each target run
|
||||||
|
|
||||||
use core::{marker::PhantomData, time::Duration};
|
use core::time::Duration;
|
||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
executors::{
|
executors::{Executor, ExitKind, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
Executor, ExitKind, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks,
|
|
||||||
},
|
|
||||||
inputs::Input,
|
inputs::Input,
|
||||||
observers::ObserversTuple,
|
observers::ObserversTuple,
|
||||||
Error,
|
Error,
|
||||||
@ -39,28 +37,18 @@ extern "C" {
|
|||||||
const ITIMER_REAL: c_int = 0;
|
const ITIMER_REAL: c_int = 0;
|
||||||
|
|
||||||
/// The timeout excutor is a wrapper that set a timeout before each run
|
/// The timeout excutor is a wrapper that set a timeout before each run
|
||||||
pub struct TimeoutExecutor<E, I>
|
pub struct TimeoutExecutor<E> {
|
||||||
where
|
|
||||||
E: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
executor: E,
|
executor: E,
|
||||||
exec_tmout: Duration,
|
exec_tmout: Duration,
|
||||||
phantom: PhantomData<I>,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<E, I> TimeoutExecutor<E, I>
|
impl<E> TimeoutExecutor<E> {
|
||||||
where
|
|
||||||
E: Executor<I>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
/// Create a new `TimeoutExecutor`, wrapping the given `executor` and checking for timeouts.
|
/// Create a new `TimeoutExecutor`, wrapping the given `executor` and checking for timeouts.
|
||||||
/// This should usually be used for `InProcess` fuzzing.
|
/// This should usually be used for `InProcess` fuzzing.
|
||||||
pub fn new(executor: E, exec_tmout: Duration) -> Self {
|
pub fn new(executor: E, exec_tmout: Duration) -> Self {
|
||||||
Self {
|
Self {
|
||||||
executor,
|
executor,
|
||||||
exec_tmout,
|
exec_tmout,
|
||||||
phantom: PhantomData,
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -70,54 +58,18 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<E, I> Executor<I> for TimeoutExecutor<E, I>
|
impl<E, EM, I, S, Z> Executor<EM, I, S, Z> for TimeoutExecutor<E>
|
||||||
where
|
where
|
||||||
E: Executor<I>,
|
E: Executor<EM, I, S, Z>,
|
||||||
I: Input,
|
I: Input,
|
||||||
{
|
{
|
||||||
fn run_target(&mut self, input: &I) -> Result<ExitKind, Error> {
|
fn run_target(
|
||||||
self.executor.run_target(input)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<E, I, OT> HasObservers<OT> for TimeoutExecutor<E, I>
|
|
||||||
where
|
|
||||||
E: Executor<I> + HasObservers<OT>,
|
|
||||||
I: Input,
|
|
||||||
OT: ObserversTuple,
|
|
||||||
{
|
|
||||||
#[inline]
|
|
||||||
fn observers(&self) -> &OT {
|
|
||||||
self.executor.observers()
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
|
||||||
fn observers_mut(&mut self) -> &mut OT {
|
|
||||||
self.executor.observers_mut()
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<E, EM, I, OT, S, Z> HasObserversHooks<EM, I, OT, S, Z> for TimeoutExecutor<E, I>
|
|
||||||
where
|
|
||||||
E: Executor<I> + HasObservers<OT>,
|
|
||||||
I: Input,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<E, EM, I, S, Z> HasExecHooks<EM, I, S, Z> for TimeoutExecutor<E, I>
|
|
||||||
where
|
|
||||||
E: Executor<I> + HasExecHooks<EM, I, S, Z>,
|
|
||||||
I: Input,
|
|
||||||
{
|
|
||||||
#[inline]
|
|
||||||
fn pre_exec(
|
|
||||||
&mut self,
|
&mut self,
|
||||||
fuzzer: &mut Z,
|
fuzzer: &mut Z,
|
||||||
state: &mut S,
|
state: &mut S,
|
||||||
mgr: &mut EM,
|
mgr: &mut EM,
|
||||||
input: &I,
|
input: &I,
|
||||||
) -> Result<(), Error> {
|
) -> Result<ExitKind, Error> {
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
unsafe {
|
unsafe {
|
||||||
let milli_sec = self.exec_tmout.as_millis();
|
let milli_sec = self.exec_tmout.as_millis();
|
||||||
@ -143,17 +95,9 @@ where
|
|||||||
// TODO
|
// TODO
|
||||||
let _ = self.exec_tmout.as_millis();
|
let _ = self.exec_tmout.as_millis();
|
||||||
}
|
}
|
||||||
self.executor.pre_exec(fuzzer, state, mgr, input)
|
|
||||||
}
|
|
||||||
|
|
||||||
#[inline]
|
let ret = self.executor.run_target(fuzzer, state, mgr, input);
|
||||||
fn post_exec(
|
|
||||||
&mut self,
|
|
||||||
fuzzer: &mut Z,
|
|
||||||
state: &mut S,
|
|
||||||
mgr: &mut EM,
|
|
||||||
input: &I,
|
|
||||||
) -> Result<(), Error> {
|
|
||||||
#[cfg(unix)]
|
#[cfg(unix)]
|
||||||
unsafe {
|
unsafe {
|
||||||
let it_value = Timeval {
|
let it_value = Timeval {
|
||||||
@ -177,6 +121,31 @@ where
|
|||||||
{
|
{
|
||||||
// TODO
|
// TODO
|
||||||
}
|
}
|
||||||
self.executor.post_exec(fuzzer, state, mgr, input)
|
|
||||||
|
ret
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl<E, OT> HasObservers<OT> for TimeoutExecutor<E>
|
||||||
|
where
|
||||||
|
E: HasObservers<OT>,
|
||||||
|
OT: ObserversTuple,
|
||||||
|
{
|
||||||
|
#[inline]
|
||||||
|
fn observers(&self) -> &OT {
|
||||||
|
self.executor.observers()
|
||||||
|
}
|
||||||
|
|
||||||
|
#[inline]
|
||||||
|
fn observers_mut(&mut self) -> &mut OT {
|
||||||
|
self.executor.observers_mut()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl<E, EM, I, OT, S, Z> HasObserversHooks<EM, I, OT, S, Z> for TimeoutExecutor<E>
|
||||||
|
where
|
||||||
|
E: HasObservers<OT>,
|
||||||
|
I: Input,
|
||||||
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
||||||
|
{
|
||||||
|
}
|
||||||
|
@ -265,61 +265,6 @@ where
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*if self.indexes.is_none() && self.novelties.is_none() {
|
|
||||||
for i in 0..size {
|
|
||||||
let history = map_state.history_map[i];
|
|
||||||
let item = observer.map()[i];
|
|
||||||
|
|
||||||
let reduced = R::reduce(history, item);
|
|
||||||
if history != reduced {
|
|
||||||
map_state.history_map[i] = reduced;
|
|
||||||
interesting = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if self.indexes.is_some() && self.novelties.is_none() {
|
|
||||||
for i in 0..size {
|
|
||||||
let history = map_state.history_map[i];
|
|
||||||
let item = observer.map()[i];
|
|
||||||
// TODO maybe walk again the histroy map only when it is interesting is more efficient
|
|
||||||
if item != initial {
|
|
||||||
self.indexes.as_mut().unwrap().push(i);
|
|
||||||
}
|
|
||||||
|
|
||||||
let reduced = R::reduce(history, item);
|
|
||||||
if history != reduced {
|
|
||||||
map_state.history_map[i] = reduced;
|
|
||||||
interesting = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if self.indexes.is_none() && self.novelties.is_some() {
|
|
||||||
for i in 0..size {
|
|
||||||
let history = map_state.history_map[i];
|
|
||||||
let item = observer.map()[i];
|
|
||||||
|
|
||||||
let reduced = R::reduce(history, item);
|
|
||||||
if history != reduced {
|
|
||||||
map_state.history_map[i] = reduced;
|
|
||||||
interesting = true;
|
|
||||||
self.novelties.as_mut().unwrap().push(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
for i in 0..size {
|
|
||||||
let history = map_state.history_map[i];
|
|
||||||
let item = observer.map()[i];
|
|
||||||
if item != initial {
|
|
||||||
self.indexes.as_mut().unwrap().push(i);
|
|
||||||
}
|
|
||||||
|
|
||||||
let reduced = R::reduce(history, item);
|
|
||||||
if history != reduced {
|
|
||||||
map_state.history_map[i] = reduced;
|
|
||||||
interesting = true;
|
|
||||||
self.novelties.as_mut().unwrap().push(i);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}*/
|
|
||||||
|
|
||||||
if interesting {
|
if interesting {
|
||||||
let mut filled = 0;
|
let mut filled = 0;
|
||||||
for i in 0..size {
|
for i in 0..size {
|
||||||
|
@ -4,9 +4,7 @@ use crate::{
|
|||||||
bolts::current_time,
|
bolts::current_time,
|
||||||
corpus::{Corpus, CorpusScheduler, Testcase},
|
corpus::{Corpus, CorpusScheduler, Testcase},
|
||||||
events::{Event, EventFirer, EventManager},
|
events::{Event, EventFirer, EventManager},
|
||||||
executors::{
|
executors::{Executor, ExitKind, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
Executor, ExitKind, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks,
|
|
||||||
},
|
|
||||||
feedbacks::Feedback,
|
feedbacks::Feedback,
|
||||||
inputs::Input,
|
inputs::Input,
|
||||||
mark_feature_time,
|
mark_feature_time,
|
||||||
@ -321,10 +319,7 @@ impl<C, CS, E, EM, F, I, OF, OT, S, SC> Evaluator<E, EM, I, S>
|
|||||||
where
|
where
|
||||||
C: Corpus<I>,
|
C: Corpus<I>,
|
||||||
CS: CorpusScheduler<I, S>,
|
CS: CorpusScheduler<I, S>,
|
||||||
E: Executor<I>
|
E: Executor<EM, I, S, Self> + HasObservers<OT> + HasObserversHooks<EM, I, OT, S, Self>,
|
||||||
+ HasObservers<OT>
|
|
||||||
+ HasExecHooks<EM, I, S, Self>
|
|
||||||
+ HasObserversHooks<EM, I, OT, S, Self>,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Self>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Self>,
|
||||||
EM: EventManager<E, I, S, Self>,
|
EM: EventManager<E, I, S, Self>,
|
||||||
F: Feedback<I, S>,
|
F: Feedback<I, S>,
|
||||||
@ -521,10 +516,7 @@ where
|
|||||||
input: &I,
|
input: &I,
|
||||||
) -> Result<ExecuteInputResult, Error>
|
) -> Result<ExecuteInputResult, Error>
|
||||||
where
|
where
|
||||||
E: Executor<I>
|
E: Executor<EM, I, S, Self> + HasObservers<OT> + HasObserversHooks<EM, I, OT, S, Self>,
|
||||||
+ HasObservers<OT>
|
|
||||||
+ HasExecHooks<EM, I, S, Self>
|
|
||||||
+ HasObserversHooks<EM, I, OT, S, Self>,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Self>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Self>,
|
||||||
EM: EventManager<E, I, S, Self>,
|
EM: EventManager<E, I, S, Self>,
|
||||||
{
|
{
|
||||||
@ -533,17 +525,9 @@ where
|
|||||||
mark_feature_time!(state, PerfFeature::PreExecObservers);
|
mark_feature_time!(state, PerfFeature::PreExecObservers);
|
||||||
|
|
||||||
start_timer!(state);
|
start_timer!(state);
|
||||||
executor.pre_exec(self, state, event_mgr, input)?;
|
let exit_kind = executor.run_target(self, state, event_mgr, input)?;
|
||||||
mark_feature_time!(state, PerfFeature::PreExec);
|
|
||||||
|
|
||||||
start_timer!(state);
|
|
||||||
let exit_kind = executor.run_target(input)?;
|
|
||||||
mark_feature_time!(state, PerfFeature::TargetExecution);
|
mark_feature_time!(state, PerfFeature::TargetExecution);
|
||||||
|
|
||||||
start_timer!(state);
|
|
||||||
executor.post_exec(self, state, event_mgr, input)?;
|
|
||||||
mark_feature_time!(state, PerfFeature::PostExec);
|
|
||||||
|
|
||||||
*state.executions_mut() += 1;
|
*state.executions_mut() += 1;
|
||||||
|
|
||||||
start_timer!(state);
|
start_timer!(state);
|
||||||
|
@ -2,7 +2,7 @@ use core::{marker::PhantomData, mem::drop};
|
|||||||
|
|
||||||
use crate::{
|
use crate::{
|
||||||
corpus::Corpus,
|
corpus::Corpus,
|
||||||
executors::{Executor, HasExecHooks, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
executors::{Executor, HasExecHooksTuple, HasObservers, HasObserversHooks},
|
||||||
inputs::Input,
|
inputs::Input,
|
||||||
mark_feature_time,
|
mark_feature_time,
|
||||||
observers::ObserversTuple,
|
observers::ObserversTuple,
|
||||||
@ -21,10 +21,7 @@ pub struct TracingStage<C, EM, I, OT, S, TE, Z>
|
|||||||
where
|
where
|
||||||
I: Input,
|
I: Input,
|
||||||
C: Corpus<I>,
|
C: Corpus<I>,
|
||||||
TE: Executor<I>
|
TE: Executor<EM, I, S, Z> + HasObservers<OT> + HasObserversHooks<EM, I, OT, S, Z>,
|
||||||
+ HasObservers<OT>
|
|
||||||
+ HasExecHooks<EM, I, S, Z>
|
|
||||||
+ HasObserversHooks<EM, I, OT, S, Z>,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
||||||
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
||||||
{
|
{
|
||||||
@ -37,10 +34,7 @@ impl<E, C, EM, I, OT, S, TE, Z> Stage<E, EM, S, Z> for TracingStage<C, EM, I, OT
|
|||||||
where
|
where
|
||||||
I: Input,
|
I: Input,
|
||||||
C: Corpus<I>,
|
C: Corpus<I>,
|
||||||
TE: Executor<I>
|
TE: Executor<EM, I, S, Z> + HasObservers<OT> + HasObserversHooks<EM, I, OT, S, Z>,
|
||||||
+ HasObservers<OT>
|
|
||||||
+ HasExecHooks<EM, I, S, Z>
|
|
||||||
+ HasObserversHooks<EM, I, OT, S, Z>,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
||||||
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
||||||
{
|
{
|
||||||
@ -68,19 +62,12 @@ where
|
|||||||
mark_feature_time!(state, PerfFeature::PreExecObservers);
|
mark_feature_time!(state, PerfFeature::PreExecObservers);
|
||||||
|
|
||||||
start_timer!(state);
|
start_timer!(state);
|
||||||
self.tracer_executor
|
drop(
|
||||||
.pre_exec(fuzzer, state, manager, &input)?;
|
self.tracer_executor
|
||||||
mark_feature_time!(state, PerfFeature::PreExec);
|
.run_target(fuzzer, state, manager, &input)?,
|
||||||
|
);
|
||||||
start_timer!(state);
|
|
||||||
drop(self.tracer_executor.run_target(&input)?);
|
|
||||||
mark_feature_time!(state, PerfFeature::TargetExecution);
|
mark_feature_time!(state, PerfFeature::TargetExecution);
|
||||||
|
|
||||||
start_timer!(state);
|
|
||||||
self.tracer_executor
|
|
||||||
.post_exec(fuzzer, state, manager, &input)?;
|
|
||||||
mark_feature_time!(state, PerfFeature::PostExec);
|
|
||||||
|
|
||||||
*state.executions_mut() += 1;
|
*state.executions_mut() += 1;
|
||||||
|
|
||||||
start_timer!(state);
|
start_timer!(state);
|
||||||
@ -96,10 +83,7 @@ impl<C, EM, I, OT, S, TE, Z> TracingStage<C, EM, I, OT, S, TE, Z>
|
|||||||
where
|
where
|
||||||
I: Input,
|
I: Input,
|
||||||
C: Corpus<I>,
|
C: Corpus<I>,
|
||||||
TE: Executor<I>
|
TE: Executor<EM, I, S, Z> + HasObservers<OT> + HasObserversHooks<EM, I, OT, S, Z>,
|
||||||
+ HasObservers<OT>
|
|
||||||
+ HasExecHooks<EM, I, S, Z>
|
|
||||||
+ HasObserversHooks<EM, I, OT, S, Z>,
|
|
||||||
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
OT: ObserversTuple + HasExecHooksTuple<EM, I, S, Z>,
|
||||||
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
S: HasClientPerfStats + HasExecutions + HasCorpus<C, I>,
|
||||||
{
|
{
|
||||||
|
Loading…
x
Reference in New Issue
Block a user