diff --git a/libafl/src/corpus/mod.rs b/libafl/src/corpus/mod.rs index 32069c5f46..1bea657106 100644 --- a/libafl/src/corpus/mod.rs +++ b/libafl/src/corpus/mod.rs @@ -41,21 +41,21 @@ where I: Input, { /// Add an entry to the corpus and return its index - fn on_add(&self, state: &mut S, idx: usize, testcase: &Testcase) -> Result<(), Error> { + fn on_add(&self, _state: &mut S, _idx: usize, _testcase: &Testcase) -> Result<(), Error> { Ok(()) } /// Replaces the testcase at the given idx - fn on_replace(&self, state: &mut S, idx: usize, testcase: &Testcase) -> Result<(), Error> { + fn on_replace(&self, _state: &mut S, _idx: usize, _testcase: &Testcase) -> Result<(), Error> { Ok(()) } /// Removes an entry from the corpus, returning it if it was present. fn on_remove( &self, - state: &mut S, - idx: usize, - testcase: &Option>, + _state: &mut S, + _idx: usize, + _testcase: &Option>, ) -> Result<(), Error> { Ok(()) } diff --git a/libafl/src/events/logger.rs b/libafl/src/events/logger.rs index 4262d847a3..ba3761ac32 100644 --- a/libafl/src/events/logger.rs +++ b/libafl/src/events/logger.rs @@ -31,7 +31,7 @@ where I: Input, ST: Stats, //CE: CustomEvent, { - fn process(&mut self, state: &mut S, executor: &mut E) -> Result + fn process(&mut self, state: &mut S, _executor: &mut E) -> Result where E: Executor + HasObservers, OT: ObserversTuple, diff --git a/libafl/src/events/mod.rs b/libafl/src/events/mod.rs index 40e0fe05c6..d801f46aaa 100644 --- a/libafl/src/events/mod.rs +++ b/libafl/src/events/mod.rs @@ -202,7 +202,7 @@ impl EventManager for NopEventManager where I: Input, { - fn process(&mut self, state: &mut S, executor: &mut E) -> Result + fn process(&mut self, _state: &mut S, _executor: &mut E) -> Result where E: Executor + HasObservers, OT: ObserversTuple, diff --git a/libafl/src/executors/inprocess.rs b/libafl/src/executors/inprocess.rs index 36972050c5..825e52ca73 100644 --- a/libafl/src/executors/inprocess.rs +++ b/libafl/src/executors/inprocess.rs @@ -249,7 +249,7 @@ pub mod unix_signals { .is_interesting_all(&input, observers, ExitKind::Crash) .expect("In crash handler objectives failure.".into()); if obj_fitness > 0 { - state.solutions_mut().add(Testcase::new(*input)); + state.solutions_mut().add(Testcase::new(input.clone())).expect("In crash handler solutions failure.".into()); mgr.fire( state, Event::Objective { @@ -270,7 +270,7 @@ pub mod unix_signals { unsafe fn inmem_handle_timeout( _sig: c_int, - info: siginfo_t, + _info: siginfo_t, _void: c_void, ) where EM: EventManager, @@ -302,7 +302,7 @@ pub mod unix_signals { .is_interesting_all(&input, observers, ExitKind::Crash) .expect("In timeout handler objectives failure.".into()); if obj_fitness > 0 { - state.solutions_mut().add(Testcase::new(*input)); + state.solutions_mut().add(Testcase::new(input.clone())).expect("In timeout handler solutions failure.".into()); mgr.fire( state, Event::Objective { diff --git a/libafl/src/mutators/mutations.rs b/libafl/src/mutators/mutations.rs index c2af06a1c2..ef45a83085 100644 --- a/libafl/src/mutators/mutations.rs +++ b/libafl/src/mutators/mutations.rs @@ -125,7 +125,7 @@ const INTERESTING_32: [i32; 27] = [ /// Bitflip mutation for inputs with a bytes vector pub fn mutation_bitflip( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -148,7 +148,7 @@ where pub fn mutation_byteflip( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -171,7 +171,7 @@ where pub fn mutation_byteinc( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -195,7 +195,7 @@ where pub fn mutation_bytedec( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -219,7 +219,7 @@ where pub fn mutation_byteneg( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -242,7 +242,7 @@ where pub fn mutation_byterand( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -265,7 +265,7 @@ where pub fn mutation_byteadd( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -293,7 +293,7 @@ where pub fn mutation_wordadd( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -323,7 +323,7 @@ where pub fn mutation_dwordadd( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -353,7 +353,7 @@ where pub fn mutation_qwordadd( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -383,7 +383,7 @@ where pub fn mutation_byteinteresting( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -407,7 +407,7 @@ where pub fn mutation_wordinteresting( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -437,7 +437,7 @@ where pub fn mutation_dwordinteresting( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -467,7 +467,7 @@ where pub fn mutation_bytesdelete( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -490,7 +490,7 @@ where pub fn mutation_bytesexpand( mutator: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -520,7 +520,7 @@ where pub fn mutation_bytesinsert( mutator: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -553,7 +553,7 @@ where pub fn mutation_bytesrandinsert( mutator: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -586,7 +586,7 @@ where pub fn mutation_bytesset( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -611,7 +611,7 @@ where pub fn mutation_bytesrandset( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -636,7 +636,7 @@ where pub fn mutation_bytescopy( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -661,7 +661,7 @@ where pub fn mutation_bytesswap( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -689,7 +689,7 @@ where /// Crossover insert mutation pub fn mutation_crossover_insert( mutator: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -703,18 +703,15 @@ where let size = input.bytes().len(); // We don't want to use the testcase we're already using for splicing - let idx = state.rand_mut().below(state.corpus().count() as u64) as usize; + let count = state.corpus().count(); + let idx = state.rand_mut().below(count as u64) as usize; if let Some(cur) = state.corpus().current() { if idx == *cur { return Ok(MutationResult::Skipped); } } - let other_testcase = state.corpus().get(idx)?; - let mut other_ref = other_testcase.borrow_mut(); - let other = other_ref.load_input()?; - - let other_size = other.bytes().len(); + let other_size = state.corpus().get(idx)?.borrow_mut().load_input()?.bytes().len(); if other_size < 2 { return Ok(MutationResult::Skipped); } @@ -723,6 +720,9 @@ where let to = state.rand_mut().below(size as u64) as usize; let mut len = state.rand_mut().below((other_size - from) as u64) as usize; + let mut other_testcase = state.corpus().get(idx)?.borrow_mut(); + let other = other_testcase.load_input()?; + if size + len > mutator.max_size() { if mutator.max_size() > size { len = mutator.max_size() - size; @@ -741,7 +741,7 @@ where /// Crossover replace mutation pub fn mutation_crossover_replace( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -754,18 +754,15 @@ where let size = input.bytes().len(); // We don't want to use the testcase we're already using for splicing - let idx = state.rand_mut().below(state.corpus().count() as u64) as usize; + let count = state.corpus().count(); + let idx = state.rand_mut().below(count as u64) as usize; if let Some(cur) = state.corpus().current() { if idx == *cur { return Ok(MutationResult::Skipped); } } - let other_testcase = state.corpus().get(idx)?; - - let mut other_ref = other_testcase.borrow_mut(); - let other = other_ref.load_input()?; - - let other_size = other.bytes().len(); + + let other_size = state.corpus().get(idx)?.borrow_mut().load_input()?.bytes().len(); if other_size < 2 { return Ok(MutationResult::Skipped); } @@ -774,6 +771,9 @@ where let len = state.rand_mut().below(min(other_size - from, size) as u64) as usize; let to = state.rand_mut().below((size - len) as u64) as usize; + let mut other_testcase = state.corpus().get(idx)?.borrow_mut(); + let other = other_testcase.load_input()?; + buffer_copy(input.bytes_mut(), other.bytes(), from, to, len); Ok(MutationResult::Mutated) @@ -798,7 +798,7 @@ fn locate_diffs(this: &[u8], other: &[u8]) -> (i64, i64) { /// Splicing mutation from AFL pub fn mutation_splice( _: &M, - fuzzer: &F, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -809,33 +809,38 @@ where S: HasRand + HasCorpus, { // We don't want to use the testcase we're already using for splicing - let idx = state.rand_mut().below(state.corpus().count() as u64) as usize; + let count = state.corpus().count(); + let idx = state.rand_mut().below(count as u64) as usize; if let Some(cur) = state.corpus().current() { if idx == *cur { return Ok(MutationResult::Skipped); } } - let other_testcase = state.corpus().get(idx)?; - let mut other_ref = other_testcase.borrow_mut(); - let other = other_ref.load_input()?; + let (first_diff, last_diff) = { + let mut other_testcase = state.corpus().get(idx)?.borrow_mut(); + let other = other_testcase.load_input()?; - let mut counter = 0; - let (first_diff, last_diff) = loop { - let (f, l) = locate_diffs(input.bytes(), other.bytes()); + let mut counter = 0; + loop { + let (f, l) = locate_diffs(input.bytes(), other.bytes()); - if f != l && f >= 0 && l >= 2 { - break (f, l); + if f != l && f >= 0 && l >= 2 { + break (f, l); + } + if counter == 3 { + return Ok(MutationResult::Skipped); + } + counter += 1; } - if counter == 3 { - return Ok(MutationResult::Skipped); - } - counter += 1; }; let split_at = state .rand_mut() .between(first_diff as u64, last_diff as u64) as usize; + + let mut other_testcase = state.corpus().get(idx)?.borrow_mut(); + let other = other_testcase.load_input()?; input .bytes_mut() .splice(split_at.., other.bytes()[split_at..].iter().cloned()); diff --git a/libafl/src/mutators/scheduled.rs b/libafl/src/mutators/scheduled.rs index e8b880e3d9..2a3feeb1f7 100644 --- a/libafl/src/mutators/scheduled.rs +++ b/libafl/src/mutators/scheduled.rs @@ -117,12 +117,12 @@ where R: Rand, { /// Compute the number of iterations used to apply stacked mutations - fn iterations(&self, state: &mut S, input: &I) -> u64 { + fn iterations(&self, state: &mut S, _: &I) -> u64 { 1 << (1 + state.rand_mut().below(6)) } /// Get the next mutation to apply - fn schedule(&self, mutations_count: usize, state: &mut S, input: &I) -> usize { + fn schedule(&self, mutations_count: usize, state: &mut S, _: &I) -> usize { debug_assert!(mutations_count > 0); state.rand_mut().below(mutations_count as u64) as usize } @@ -301,8 +301,8 @@ where scheduled.add_mutation(mutation_bytescopy); scheduled.add_mutation(mutation_bytesswap); - //scheduled.add_mutation(mutation_tokeninsert); - //scheduled.add_mutation(mutation_tokenreplace); + scheduled.add_mutation(mutation_tokeninsert); + scheduled.add_mutation(mutation_tokenreplace); scheduled.add_mutation(mutation_crossover_insert); scheduled.add_mutation(mutation_crossover_replace); diff --git a/libafl/src/mutators/token_mutations.rs b/libafl/src/mutators/token_mutations.rs index b86937b45f..505dc9d54b 100644 --- a/libafl/src/mutators/token_mutations.rs +++ b/libafl/src/mutators/token_mutations.rs @@ -30,8 +30,9 @@ impl TokensMetadata { } /// Insert a dictionary token -pub fn mutation_tokeninsert( - mutator: &mut M, +pub fn mutation_tokeninsert( + mutator: &M, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -41,22 +42,23 @@ where S: HasMetadata + HasRand, R: Rand, { - let meta; - match state.metadata().get::() { - Some(t) => { - meta = t; - } - None => { + let tokens_len = { + let meta = state.metadata().get::(); + if meta.is_none() { return Ok(MutationResult::Skipped); } + if meta.unwrap().tokens.len() == 0 { + return Ok(MutationResult::Skipped); + } + meta.unwrap().tokens.len() }; - if meta.tokens.len() == 0 { - return Ok(MutationResult::Skipped); - } - let token = &meta.tokens[state.rand_mut().below(meta.tokens.len() as u64) as usize]; - + let token_idx = state.rand_mut().below(tokens_len as u64) as usize; + let size = input.bytes().len(); let off = state.rand_mut().below((size + 1) as u64) as usize; + + let meta = state.metadata().get::().unwrap(); + let token = &meta.tokens[token_idx]; let mut len = token.len(); if size + len > mutator.max_size() { @@ -75,8 +77,9 @@ where } /// Overwrite with a dictionary token -pub fn mutation_tokenreplace( - _: &mut M, +pub fn mutation_tokenreplace( + _: &M, + _: &F, state: &mut S, input: &mut I, ) -> Result @@ -91,22 +94,22 @@ where return Ok(MutationResult::Skipped); } - let meta; - match state.metadata().get::() { - Some(t) => { - meta = t; - } - None => { + let tokens_len = { + let meta = state.metadata().get::(); + if meta.is_none() { return Ok(MutationResult::Skipped); } + if meta.unwrap().tokens.len() == 0 { + return Ok(MutationResult::Skipped); + } + meta.unwrap().tokens.len() }; - if meta.tokens.len() == 0 { - return Ok(MutationResult::Skipped); - } - let token = &meta.tokens[state.rand_mut().below(meta.tokens.len() as u64) as usize]; + let token_idx = state.rand_mut().below(tokens_len as u64) as usize; let off = state.rand_mut().below(size as u64) as usize; + let meta = state.metadata().get::().unwrap(); + let token = &meta.tokens[token_idx]; let mut len = token.len(); if off + len > size { len = size - off; diff --git a/libafl/src/stages/mod.rs b/libafl/src/stages/mod.rs index 45c4db9b8d..27f88c1bfb 100644 --- a/libafl/src/stages/mod.rs +++ b/libafl/src/stages/mod.rs @@ -1,7 +1,7 @@ pub mod mutational; pub use mutational::StdMutationalStage; -use crate::{bolts::tuples::TupleList, corpus::Corpus, Error}; +use crate::{bolts::tuples::TupleList, Error}; /// A stage is one step in the fuzzing process. /// Multiple stages will be scheduled one by one for each input. @@ -31,11 +31,11 @@ pub trait StagesTuple { impl StagesTuple for () { fn perform_all( &self, - fuzzer: &F, - state: &mut S, - executor: &mut E, - manager: &mut EM, - corpus_idx: usize, + _: &F, + _: &mut S, + _: &mut E, + _: &mut EM, + _: usize, ) -> Result<(), Error> { Ok(()) } diff --git a/libafl/src/stages/mutational.rs b/libafl/src/stages/mutational.rs index add170ba89..a77aaeb6e5 100644 --- a/libafl/src/stages/mutational.rs +++ b/libafl/src/stages/mutational.rs @@ -35,7 +35,7 @@ where fn mutator_mut(&mut self) -> &mut M; /// Gets the number of iterations this mutator should run for. - fn iterations(&mut self, state: &mut S) -> usize; + fn iterations(&self, state: &mut S) -> usize; /// Runs this (mutational) stage for the given testcase fn perform_mutational( @@ -54,12 +54,12 @@ where .borrow_mut() .load_input()? .clone(); - self.mutator_mut() + self.mutator() .mutate(fuzzer, state, &mut input_mut, i as i32)?; let fitness = state.evaluate_input(input_mut, executor, manager)?; - self.mutator_mut() + self.mutator() .post_exec(fuzzer, state, fitness, i as i32)?; } Ok(()) @@ -110,7 +110,7 @@ where } /// Gets the number of iterations as a random number - fn iterations(&mut self, state: &mut S) -> usize { + fn iterations(&self, state: &mut S) -> usize { 1 + state.rand_mut().below(DEFAULT_MUTATIONAL_MAX_ITERATIONS) as usize } } diff --git a/libafl/src/state/mod.rs b/libafl/src/state/mod.rs index eddab4e503..38eb7b0c86 100644 --- a/libafl/src/state/mod.rs +++ b/libafl/src/state/mod.rs @@ -453,7 +453,7 @@ where self.solutions_mut().add(Testcase::new(input.clone()))?; } - if let idx = Some(self.add_if_interesting(&input, fitness)?) { + if !self.add_if_interesting(&input, fitness)?.is_none() { let observers_buf = manager.serialize_observers(observers)?; manager.fire( self, @@ -577,7 +577,7 @@ where executor.pre_exec(self, event_mgr, input)?; let exit_kind = executor.run_target(input)?; - executor.post_exec(&self, event_mgr, input)?; + //executor.post_exec(&self, event_mgr, input)?; *self.executions_mut() += 1; executor.post_exec_observers()?; @@ -585,18 +585,17 @@ where let observers = executor.observers(); let fitness = self .feedbacks_mut() - .is_interesting_all(&input, observers, exit_kind)?; + .is_interesting_all(&input, observers, exit_kind.clone())?; let is_solution = self.objectives_mut() - .is_interesting_all(&input, observers, exit_kind.clone())? + .is_interesting_all(&input, observers, exit_kind)? > 0; Ok((fitness, is_solution)) } pub fn generate_initial_inputs( &mut self, - rand: &mut R, executor: &mut E, generator: &mut G, manager: &mut EM,