Skip to content

Commit

Permalink
random testing for multiple cycles
Browse files Browse the repository at this point in the history
  • Loading branch information
ekiwi committed Aug 27, 2024
1 parent 4ecebf7 commit 774839a
Show file tree
Hide file tree
Showing 2 changed files with 46 additions and 12 deletions.
5 changes: 3 additions & 2 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,8 @@ struct Args {

static RANDOM_OPTS: RandomOptions = RandomOptions {
small_k: 50,
large_k: 10_000,
large_k: 1_000,
large_k_prob: 0.01,
};

fn main() {
Expand All @@ -38,7 +39,7 @@ fn main() {
simplify_expressions(&mut ctx, &mut sys);

// try random testing
match random_testing(&mut ctx, sys, RANDOM_OPTS) {
match random_testing(ctx, sys, RANDOM_OPTS) {
RandomResult::None => {
println!("None")
}
Expand Down
53 changes: 43 additions & 10 deletions src/random.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,8 @@ pub struct RandomOptions {
pub small_k: u64,
/// maximum length to try
pub large_k: u64,
/// probability of sampling a large instead of a small k
pub large_k_prob: f64,
}

#[derive(Debug)]
Expand All @@ -27,12 +29,12 @@ pub enum RandomResult {
}

pub fn random_testing(
ctx: &mut Context,
mut ctx: Context,
sys: TransitionSystem,
opts: RandomOptions,
) -> RandomResult {
// collect constraints for input randomization
let constraints = analyze_constraints(ctx, &sys, false);
let constraints = analyze_constraints(&mut ctx, &sys, false);

// find out which inputs are unconstrained
let constrained_inputs = constraints
Expand Down Expand Up @@ -61,21 +63,52 @@ pub fn random_testing(
// we initialize all states to zero, since most bugs are not reset initialization bugs
sim.init(InitKind::Zero);

// take a snapshot so that we can go back to the initial state
let start_state = sim.take_snapshot();

// create random number generator
let mut rng = rand_xoshiro::Xoshiro256PlusPlus::seed_from_u64(1);

// randomize inputs to the system
randomize_inputs(ctx, &mut rng, &constraints, &unconstrained_inputs, &mut sim);
sim.update(); // FIXME: support partial re-evaluation!
// main loop
loop {
let k_max = sample_k_max(&mut rng, &opts);

// restore starting state
sim.restore_snapshot(start_state);

for k in 0..=k_max {
// randomize inputs to the system
randomize_inputs(
&mut ctx,
&mut rng,
&constraints,
&unconstrained_inputs,
&mut sim,
);
sim.update(); // FIXME: support partial re-evaluation!

// check if we are in a bad state
let bads = check_for_bad_states(ctx, &bad_states, &mut sim);
if !bads.is_empty() {
return RandomResult::Sat(bads);
}
// check if we are in a bad state
let bads = check_for_bad_states(&mut ctx, &bad_states, &mut sim);
if !bads.is_empty() {
return RandomResult::Sat(bads);
}

// advance the system
sim.step();
}
}
RandomResult::None
}

fn sample_k_max(rng: &mut impl Rng, opts: &RandomOptions) -> u64 {
let pick_large_k = rng.gen_bool(opts.large_k_prob);
if pick_large_k {
rng.gen_range(opts.small_k..(opts.large_k + 1))
} else {
rng.gen_range(1..(opts.small_k + 1))
}
}

fn check_for_bad_states(
ctx: &Context,
bad_states: &[ExprRef],
Expand Down

0 comments on commit 774839a

Please sign in to comment.