extern crate alloc;
use alloc::vec;
use alloc::vec::Vec;
use core::num::NonZeroUsize;
use crate::metis::{Cut, EpochPreparation, EpochPreparationMiss, Epochs, Stability, VersionVector};
use super::super::{Moves, Text, d, rank, vector};
use super::{Fleet, MEMBERS, Message, Op, Payload, base_ops};
use crate::metis::dot::RawDot;
#[test]
fn the_model_fence_detects_and_falls_back_on_a_skewed_advertisement() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Grow {
member: 2,
station: 2,
});
ops.push(Op::Declare { member: 2 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Advertise { member: 2 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Replay {
to: 1,
from: 2,
index: 1,
});
fleet.run(&ops).expect("the ordered prefix is lawful");
assert_eq!(fleet.detections, 0);
let mut ops: Vec<Op> = Vec::new();
for member in 0..MEMBERS {
ops.push(Op::Grow { member, station: 0 });
}
ops.extend([
Op::Gossip { member: 1, of: 0 },
Op::Gossip { member: 1, of: 2 },
Op::Gossip { member: 2, of: 0 },
Op::Gossip { member: 2, of: 1 },
Op::Advertise { member: 1 },
Op::Advertise { member: 2 },
Op::Deliver { to: 1, from: 2 },
Op::Declare { member: 0 },
Op::Gossip { member: 0, of: 1 },
Op::Gossip { member: 0, of: 2 },
Op::Advertise { member: 0 },
Op::DeliverSkewed { to: 1, from: 0 },
Op::Deliver { to: 1, from: 0 },
]);
fleet
.run(&ops)
.expect("the skewed delivery is detected, never trusted");
assert_eq!(
fleet.detections, 1,
"the fence fired exactly once, on the outrun declaration"
);
}
#[test]
fn the_model_generation_discipline_survives_seals_and_replays() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
for member in 0..MEMBERS {
ops.push(Op::Grow { member, station: 0 });
}
for member in 0..MEMBERS {
for of in (0..MEMBERS).filter(|&of| of != member) {
ops.push(Op::Gossip { member, of });
}
}
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Declare { member: 0 });
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 2, from: 0 });
ops.push(Op::Deliver { to: 2, from: 0 });
ops.extend((0..MEMBERS).map(|member| Op::Seal { member }));
ops.extend((0..MEMBERS).map(|from| Op::Replay {
to: 1,
from,
index: 0,
}));
fleet.run(&ops).expect("seals and stale replays are lawful");
assert_eq!(fleet.generations, [1; MEMBERS]);
assert!(
fleet.held[1].iter().all(Option::is_none),
"the reborn oath table holds nothing: reset at seal, replays excluded"
);
let mut ops = base_ops();
ops.push(Op::Declare { member: 0 });
ops.push(Op::Deliver { to: 1, from: 0 });
fleet
.run(&ops)
.expect("the reborn declaration is never overshot");
assert_eq!(fleet.detections, 0);
}
#[test]
fn a_candidates_staging_seeds_at_its_own_delivery_not_later() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Declare { member: 0 });
ops.push(Op::Deliver { to: 1, from: 0 });
fleet.run(&ops).expect("the ordered prefix is lawful");
let snapshot = fleet.oath_meet(1).expect("the table is full");
let first_cut = vector(&[(0, 1), (1, 1), (2, 1)]);
assert_eq!(snapshot, first_cut);
let mut ops: Vec<Op> = Vec::new();
for member in 0..MEMBERS {
ops.push(Op::Grow { member, station: 0 });
}
for member in 0..MEMBERS {
for of in (0..MEMBERS).filter(|&of| of != member) {
ops.push(Op::Gossip { member, of });
}
}
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
fleet
.run(&ops)
.expect("post-declaration advertisements are lawful");
let risen = fleet.oath_meet(1).expect("the table stays full");
assert!(
first_cut.happens_before(&risen),
"the oath meet passed the delivered cut, as the schedule allows"
);
let ops = [Op::Declare { member: 2 }, Op::Deliver { to: 1, from: 2 }];
fleet
.run(&ops)
.expect("the second candidate's delivery is bounded");
assert_eq!(fleet.detections, 0);
let mut stability = Stability::new([0, 1, 2]);
let witnessed = Cut::from_witnessed(first_cut);
for member in [0, 1, 2] {
stability.report_cut(member, &witnessed).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let declaration = epochs
.declare(d(0, 2), rank(2), &stability, &Cut::bottom())
.unwrap();
let seeded_at_delivery = Text::from_context(Cut::from_witnessed(snapshot).to_have_set());
assert!(EpochPreparation::begin(&declaration, seeded_at_delivery, Moves::new()).is_ok());
let seeded_late = Text::from_context(Cut::from_witnessed(risen).to_have_set());
assert_eq!(
EpochPreparation::begin(&declaration, seeded_late, Moves::new()).unwrap_err(),
EpochPreparationMiss::UnpinnedBase {
dot: RawDot::new(0, 2)
}
);
}
#[test]
fn a_locally_declared_candidate_absorbs_its_own_redelivery() {
let mut fleet = Fleet::new();
let ops = [
Op::Advertise { member: 0 },
Op::Declare { member: 0 },
Op::Advertise { member: 0 },
Op::Replay {
to: 0,
from: 0,
index: 1,
},
];
fleet.run(&ops).expect("a self echo is lawful");
assert_eq!(
fleet.detections, 0,
"the echo is a duplicate, never a broken order"
);
}
#[test]
fn a_reconnect_replay_cannot_silently_overtake_an_undelivered_declaration() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.extend([
Op::Declare { member: 0 },
Op::Grow {
member: 0,
station: 0,
},
Op::Advertise { member: 0 },
]);
ops.push(Op::Replay {
to: 1,
from: 0,
index: 2,
});
ops.push(Op::Deliver { to: 1, from: 0 });
fleet
.run(&ops)
.expect("the overtaken declaration is detected, never silently folded");
assert_eq!(
fleet.detections, 1,
"every session was ordered, only the stamp saw the overtaking"
);
}
#[test]
fn the_oath_refuses_at_the_numeral_and_generation_ceilings() {
let mut fleet = Fleet::new();
fleet.emitted[0] = u64::MAX - 1;
fleet.floors[0].observe(0, u64::MAX - 1);
let ops = [
Op::Grow {
member: 0,
station: 0,
},
Op::Advertise { member: 0 },
Op::Declare { member: 0 },
];
fleet
.run(&ops)
.expect("the ceiling refusals are silent skips");
assert_eq!(fleet.emitted[0], u64::MAX, "the last mint landed");
assert_eq!(
fleet.history[0].len(),
1,
"the advertisement emitted; the saturating declaration refused"
);
assert!(!fleet.window[0], "no window opened at the ceiling");
assert_eq!(fleet.detections, 0);
let mut fleet = Fleet::new();
fleet.generations = [u64::MAX; MEMBERS];
fleet.window[1] = true;
fleet
.run(&[Op::Seal { member: 1 }])
.expect("the refusal is a skip");
assert_eq!(fleet.generations, [u64::MAX; MEMBERS], "no tag reuse");
assert!(fleet.window[1], "the window stays open: the seal refused");
}
#[test]
fn a_restarted_declarer_cannot_declare_below_its_advertised_oath() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Crash { member: 0 });
ops.push(Op::Declare { member: 0 });
fleet.run(&ops).expect("the refused declaration is a skip");
assert!(
!fleet.window[0],
"the post-crash declaration refused: the cut does not cover the oath"
);
assert_eq!(fleet.history[0].len(), 1, "only the advertisement emitted");
let mut ops: Vec<Op> = Vec::new();
for of in (0..MEMBERS).filter(|&of| of != 0) {
ops.push(Op::Gossip { member: 0, of });
}
ops.push(Op::Declare { member: 0 });
ops.push(Op::Deliver { to: 1, from: 0 });
fleet
.run(&ops)
.expect("the recovered declaration is bounded");
assert!(fleet.window[0], "the recovered declaration minted");
assert_eq!(fleet.detections, 0);
}
#[test]
fn a_receiver_crash_forfeits_the_fast_path_and_a_replay_cannot_regain_it() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Declare { member: 2 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.extend([
Op::Declare { member: 0 },
Op::Grow {
member: 0,
station: 0,
},
Op::Advertise { member: 0 },
Op::Replay {
to: 1,
from: 0,
index: 2,
},
Op::Deliver { to: 1, from: 0 },
]);
fleet.run(&ops).expect("the overtaking is detected");
assert_eq!(fleet.detections, 1);
let overtaken = *fleet.eligible[1][0].values().next().unwrap();
let clean = *fleet.eligible[1][2].values().next().unwrap();
assert!(!overtaken, "the overtaken candidate's fast path is refused");
assert!(clean, "the clean candidate's fast path was granted");
let mut ops: Vec<Op> = vec![Op::Crash { member: 1 }];
ops.extend([
Op::Replay {
to: 1,
from: 0,
index: 0,
},
Op::Replay {
to: 1,
from: 0,
index: 2,
},
Op::Replay {
to: 1,
from: 0,
index: 1,
},
]);
fleet
.run(&ops)
.expect("the duplicate absorbs without a fresh verdict");
assert_eq!(fleet.detections, 1, "no second verdict was ever taken");
assert!(
fleet.eligible[1]
.iter()
.all(|per_emitter| per_emitter.values().all(|&eligible| !eligible)),
"every pre-crash candidate's fast path stays forfeit; the replay regained nothing"
);
let local = *fleet.eligible[0][0].values().next().unwrap();
assert!(local, "the declarer's own candidate was fast-path eligible");
fleet
.run(&[
Op::Crash { member: 0 },
Op::Replay {
to: 0,
from: 0,
index: 1,
},
])
.expect("the self echo after the crash absorbs");
let local = *fleet.eligible[0][0].values().next().unwrap();
assert!(
!local,
"the declarer's own pre-crash candidate stays forfeit"
);
}
#[test]
fn a_sender_that_advertises_inside_its_declare_step_costs_a_spurious_rebuild() {
let mut fleet = Fleet::new();
fleet.channels[0][1].push_back(Message {
generation: 0,
counter: 1,
position: 0,
payload: Payload::Advertisement(vector(&[(0, 1)])),
});
fleet.channels[0][1].push_back(Message {
generation: 0,
counter: 1,
position: 1,
payload: Payload::Declaration(VersionVector::new()),
});
let outcome = fleet.run(&[
Op::Deliver { to: 1, from: 0 },
Op::Deliver { to: 1, from: 0 },
]);
assert_eq!(
fleet.detections, 1,
"the fence conservatively detects: a rebuild, never a wrong stratum"
);
assert!(
outcome.is_err(),
"the precision oracle flags the schedule as outside the linearization duty"
);
}
#[test]
fn a_scoped_oath_meet_serves_in_scope_declarers_past_a_silent_straggler() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
for member in 0..MEMBERS {
ops.push(Op::Grow { member, station: 0 });
}
for member in 0..2 {
for of in (0..MEMBERS).filter(|&of| of != member) {
ops.push(Op::Gossip { member, of });
}
}
ops.push(Op::Advertise { member: 0 });
ops.push(Op::Advertise { member: 1 });
ops.push(Op::Deliver { to: 1, from: 0 });
fleet.run(&ops).expect("the ordered prefix is lawful");
assert_eq!(fleet.oath_meet(1), None);
assert_eq!(fleet.scoped_oath_meet(1, &[0, 1, 2]), None);
let scoped = fleet
.scoped_oath_meet(1, &[0, 1])
.expect("every scope member has advertised");
assert_eq!(scoped, vector(&[(0, 2), (1, 1), (2, 1)]));
let ops = [Op::Declare { member: 0 }, Op::Deliver { to: 1, from: 0 }];
fleet.run(&ops).expect("the in-scope candidate is bounded");
assert_eq!(fleet.detections, 0);
let in_scope_cut = Cut::from_witnessed(vector(&[(0, 2), (1, 1), (2, 1)]));
let mut stability = Stability::new([0, 1, 2]);
for member in [0, 1, 2] {
stability.report_cut(member, &in_scope_cut).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let in_scope = epochs
.declare(d(0, 3), rank(3), &stability, &Cut::bottom())
.unwrap();
let trailing = Text::from_context(Cut::from_witnessed(scoped.clone()).to_have_set());
assert!(EpochPreparation::begin(&in_scope, trailing, Moves::new()).is_ok());
let straggler_cut = Cut::from_witnessed(vector(&[(0, 1), (1, 1), (2, 1)]));
let mut stability = Stability::new([0, 1, 2]);
for member in [0, 1, 2] {
stability.report_cut(member, &straggler_cut).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let straggler = epochs
.declare(d(2, 2), rank(2), &stability, &Cut::bottom())
.unwrap();
assert!(straggler.cut().as_vector().happens_before(&scoped));
let trailing = Text::from_context(Cut::from_witnessed(scoped).to_have_set());
assert_eq!(
EpochPreparation::begin(&straggler, trailing, Moves::new()).unwrap_err(),
EpochPreparationMiss::UnpinnedBase {
dot: RawDot::new(0, 2)
}
);
}
#[test]
fn a_seal_re_arms_the_scoped_gate_on_scope_advertisements_only() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
ops.extend((0..MEMBERS).map(|member| Op::Advertise { member }));
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 1, from: 2 });
ops.push(Op::Declare { member: 0 });
ops.push(Op::Deliver { to: 1, from: 0 });
ops.push(Op::Deliver { to: 2, from: 0 });
ops.push(Op::Deliver { to: 2, from: 0 });
ops.extend((0..MEMBERS).map(|member| Op::Seal { member }));
fleet.run(&ops).expect("the sealed generation is lawful");
assert_eq!(fleet.generations, [1; MEMBERS]);
let ops = [
Op::Advertise { member: 0 },
Op::Advertise { member: 1 },
Op::Deliver { to: 1, from: 0 },
];
fleet
.run(&ops)
.expect("the reborn advertisements are lawful");
assert_eq!(fleet.oath_meet(1), None);
assert_eq!(
fleet.scoped_oath_meet(1, &[0, 1]),
Some(VersionVector::new()),
"the scoped gate re-arms on its scope alone, at the reborn bottom"
);
fleet
.run(&[Op::Replay {
to: 1,
from: 2,
index: 0,
}])
.expect("the stale replay is excluded");
assert_eq!(fleet.scoped_oath_meet(1, &[0, 1, 2]), None);
assert_eq!(fleet.oath_meet(1), None);
}
#[test]
fn a_scope_change_protects_exactly_the_members_whose_oaths_cover_the_base() {
let mut fleet = Fleet::new();
let mut ops = base_ops();
for member in 0..MEMBERS {
ops.push(Op::Grow { member, station: 0 });
}
for member in 0..2 {
for of in (0..MEMBERS).filter(|&of| of != member) {
ops.push(Op::Gossip { member, of });
}
}
ops.push(Op::Advertise { member: 0 });
ops.push(Op::Advertise { member: 1 });
ops.push(Op::Deliver { to: 1, from: 0 });
fleet.run(&ops).expect("the ordered prefix is lawful");
let advanced = fleet
.scoped_oath_meet(1, &[0, 1])
.expect("the pair scope reads");
assert_eq!(advanced, vector(&[(0, 2), (1, 1), (2, 1)]));
fleet
.run(&[Op::Advertise { member: 2 }, Op::Deliver { to: 1, from: 2 }])
.expect("the late advertisement is lawful");
let widened = fleet
.scoped_oath_meet(1, &[0, 1, 2])
.expect("the widened scope reads once the straggler advertises");
assert!(widened.happens_before(&advanced));
let admitted_cut = Cut::from_witnessed(vector(&[(0, 1), (1, 1), (2, 1)]));
let mut stability = Stability::new([0, 1, 2]);
for member in [0, 1, 2] {
stability.report_cut(member, &admitted_cut).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let admitted = epochs
.declare(d(2, 2), rank(2), &stability, &Cut::bottom())
.unwrap();
let trailing = Text::from_context(Cut::from_witnessed(advanced.clone()).to_have_set());
assert_eq!(
EpochPreparation::begin(&admitted, trailing, Moves::new()).unwrap_err(),
EpochPreparationMiss::UnpinnedBase {
dot: RawDot::new(0, 2)
}
);
fleet
.run(&[
Op::Gossip { member: 2, of: 0 },
Op::Gossip { member: 2, of: 1 },
Op::Advertise { member: 2 },
Op::Deliver { to: 1, from: 2 },
])
.expect("the covering advertisement is lawful");
let covered = fleet
.scoped_oath_meet(1, &[0, 1, 2])
.expect("the widened scope still reads");
assert_eq!(covered, advanced, "the widened meet rose back to the base");
let covering_cut = Cut::from_witnessed(vector(&[(0, 2), (1, 1), (2, 1)]));
let mut stability = Stability::new([0, 1, 2]);
for member in [0, 1, 2] {
stability.report_cut(member, &covering_cut).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let covering = epochs
.declare(d(2, 2), rank(4), &stability, &Cut::bottom())
.unwrap();
let trailing = Text::from_context(Cut::from_witnessed(advanced.clone()).to_have_set());
assert!(EpochPreparation::begin(&covering, trailing, Moves::new()).is_ok());
let shrunken = fleet
.scoped_oath_meet(1, &[0])
.expect("the shrunken scope reads");
assert!(advanced <= shrunken);
let retained_cut = Cut::from_witnessed(vector(&[(0, 2), (1, 1), (2, 1)]));
let mut stability = Stability::new([0, 1, 2]);
for member in [0, 1, 2] {
stability.report_cut(member, &retained_cut).unwrap();
}
let mut epochs = Epochs::new([0, 1, 2], NonZeroUsize::new(1).unwrap());
let retained = epochs
.declare(d(0, 3), rank(3), &stability, &Cut::bottom())
.unwrap();
let trailing = Text::from_context(Cut::from_witnessed(advanced).to_have_set());
assert!(EpochPreparation::begin(&retained, trailing, Moves::new()).is_ok());
}