use interweave::{World, explore};
const TOTAL: i32 = 100;
fn bank(world: &mut World) {
let a = world.atomic("a", TOTAL);
let b = world.atomic("b", 0);
let (from, to) = (a.clone(), b.clone());
world.spawn("transfer", async move {
let av = from.load().await;
from.store(av - 10).await;
let bv = to.load().await;
to.store(bv + 10).await;
Ok(())
});
world.spawn("audit", async move {
let av = a.load().await;
let bv = b.load().await;
let total = av + bv;
if total != TOTAL {
return Err(
format!("invariant violated: a={av} + b={bv} = {total}, expected {TOTAL}").into(),
);
}
Ok(())
});
}
fn main() {
match explore(&bank, &mut ()) {
Ok(()) => println!("no interleaving violates the invariant (unexpected for this program)"),
Err(failed) => {
println!("found a schedule that breaks the a + b == {TOTAL} invariant:");
println!(" {failed}");
}
}
}