RandomCorpus struct
This commit is contained in:
parent
ca1be853e1
commit
d4dd8117fd
@ -30,23 +30,14 @@ pub trait Corpus: Debug {
|
|||||||
fn get(&mut self) -> Result<&Box<dyn Testcase>, Error>;
|
fn get(&mut self) -> Result<&Box<dyn Testcase>, Error>;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A queue-like corpus
|
|
||||||
pub trait Queue: Corpus {
|
|
||||||
fn get_cycles(&self) -> u64;
|
|
||||||
|
|
||||||
fn get_pos(&self) -> usize;
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct DefaultQueue<'a> {
|
pub struct RandomCorpus<'a> {
|
||||||
rand: &'a mut dyn Rand,
|
rand: &'a mut dyn Rand,
|
||||||
pos: usize,
|
|
||||||
cycles: u64,
|
|
||||||
entries: Vec<Box<dyn Testcase>>,
|
entries: Vec<Box<dyn Testcase>>,
|
||||||
dir_path: String,
|
dir_path: String,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Corpus for DefaultQueue<'_> {
|
impl Corpus for RandomCorpus<'_> {
|
||||||
/// Returns the number of elements
|
/// Returns the number of elements
|
||||||
fn count(&self) -> usize {
|
fn count(&self) -> usize {
|
||||||
self.entries.len()
|
self.entries.len()
|
||||||
@ -62,7 +53,7 @@ impl Corpus for DefaultQueue<'_> {
|
|||||||
let mut found = false;
|
let mut found = false;
|
||||||
for x in &self.entries {
|
for x in &self.entries {
|
||||||
i = i + 1;
|
i = i + 1;
|
||||||
if x.as_ref().get_filename() == entry.get_filename() {
|
if x.as_ref() as *const _ == entry as *const _ {
|
||||||
found = true;
|
found = true;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -81,40 +72,80 @@ impl Corpus for DefaultQueue<'_> {
|
|||||||
|
|
||||||
/// Gets the next entry
|
/// Gets the next entry
|
||||||
fn get(&mut self) -> Result<&Box<dyn Testcase>, Error> {
|
fn get(&mut self) -> Result<&Box<dyn Testcase>, Error> {
|
||||||
if self.entries.len() == 0 {
|
self.random_entry()
|
||||||
return Err(Error::Unknown);
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl RandomCorpus<'_> {
|
||||||
|
pub fn new<'a>(rand: &'a mut dyn Rand, dir_path: &str) -> RandomCorpus<'a> {
|
||||||
|
RandomCorpus {
|
||||||
|
dir_path: dir_path.to_owned(),
|
||||||
|
entries: vec![],
|
||||||
|
rand: rand,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// A queue-like corpus
|
||||||
|
#[derive(Debug)]
|
||||||
|
pub struct QueueCorpus<'a> {
|
||||||
|
random_corpus: RandomCorpus<'a>,
|
||||||
|
pos: usize,
|
||||||
|
cycles: u64,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Corpus for QueueCorpus<'_> {
|
||||||
|
/// Returns the number of elements
|
||||||
|
fn count(&self) -> usize {
|
||||||
|
self.random_corpus.count()
|
||||||
|
}
|
||||||
|
|
||||||
|
fn add(&mut self, entry: Box<dyn Testcase>) {
|
||||||
|
self.random_corpus.add(entry);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Removes an entry from the corpus, returning it if it was present.
|
||||||
|
fn remove(&mut self, entry: &dyn Testcase) -> Option<Box<dyn Testcase>> {
|
||||||
|
self.random_corpus.remove(entry)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Gets a random entry
|
||||||
|
fn random_entry(&mut self) -> Result<&Box<dyn Testcase>, Error> {
|
||||||
|
self.random_corpus.random_entry()
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Gets the next entry
|
||||||
|
fn get(&mut self) -> Result<&Box<dyn Testcase>, Error> {
|
||||||
|
if self.count() == 0 {
|
||||||
|
return Err(Error::Unknown); // TODO(andrea) why unknown? use EmptyContainerError or similar
|
||||||
}
|
}
|
||||||
self.pos = self.pos + 1;
|
self.pos = self.pos + 1;
|
||||||
if self.pos >= self.entries.len() {
|
if self.pos >= self.count() {
|
||||||
self.cycles = self.cycles + 1;
|
self.cycles = self.cycles + 1;
|
||||||
self.pos = 0;
|
self.pos = 0;
|
||||||
}
|
}
|
||||||
Ok(self.entries.get_mut(self.pos).unwrap())
|
Ok(self.random_corpus.entries.get_mut(self.pos).unwrap())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Queue for DefaultQueue<'_> {
|
impl QueueCorpus<'_> {
|
||||||
fn get_cycles(&self) -> u64 {
|
pub fn new<'a>(rand: &'a mut dyn Rand, dir_path: &str) -> QueueCorpus<'a> {
|
||||||
|
QueueCorpus {
|
||||||
|
random_corpus: RandomCorpus::new(rand, dir_path),
|
||||||
|
cycles: 0,
|
||||||
|
pos: 0,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn get_cycles(&self) -> u64 {
|
||||||
self.cycles
|
self.cycles
|
||||||
}
|
}
|
||||||
|
|
||||||
fn get_pos(&self) -> usize {
|
pub fn get_pos(&self) -> usize {
|
||||||
self.pos
|
self.pos
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl DefaultQueue<'_> {
|
|
||||||
pub fn new<'a>(rand: &'a mut dyn Rand, dir_path: &str) -> DefaultQueue<'a> {
|
|
||||||
DefaultQueue {
|
|
||||||
cycles: 0,
|
|
||||||
dir_path: dir_path.to_owned(),
|
|
||||||
entries: vec![],
|
|
||||||
pos: 0,
|
|
||||||
rand: rand,
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
#[derive(Debug, Default)]
|
#[derive(Debug, Default)]
|
||||||
struct SimpleTestcase {
|
struct SimpleTestcase {
|
||||||
is_on_disk: bool,
|
is_on_disk: bool,
|
||||||
@ -154,14 +185,14 @@ impl SimpleTestcase {
|
|||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
use crate::corpus::Corpus;
|
use crate::corpus::Corpus;
|
||||||
use crate::corpus::DefaultQueue;
|
use crate::corpus::QueueCorpus;
|
||||||
use crate::corpus::SimpleTestcase;
|
use crate::corpus::SimpleTestcase;
|
||||||
use crate::utils::Xoshiro256StarRand;
|
use crate::utils::Xoshiro256StarRand;
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
fn test_defaultqueue() {
|
fn test_queuecorpus() {
|
||||||
let mut rand = Xoshiro256StarRand::new();
|
let mut rand = Xoshiro256StarRand::new();
|
||||||
let mut q = DefaultQueue::new(&mut rand, "fancy/path");
|
let mut q = QueueCorpus::new(&mut rand, "fancy/path");
|
||||||
q.add(Box::new(SimpleTestcase::new("fancyfile")));
|
q.add(Box::new(SimpleTestcase::new("fancyfile")));
|
||||||
let filename = q.get().unwrap().get_filename().to_owned();
|
let filename = q.get().unwrap().get_filename().to_owned();
|
||||||
assert_eq!(filename, q.get().unwrap().get_filename());
|
assert_eq!(filename, q.get().unwrap().get_filename());
|
||||||
|
Loading…
x
Reference in New Issue
Block a user