///|
pub(all) struct SimSnapshot {
name : String
time : Int
next_id : Int
rng_state : UInt64
digest : UInt64
events : Array[ScheduledEvent]
counters : Array[CounterSample]
gauges : Array[CounterSample]
samples : Array[CounterSample]
}
///|
pub(all) struct ForkComparison {
left_name : String
right_name : String
left_digest : UInt64
right_digest : UInt64
same_digest : Bool
left_events : Int
right_events : Int
}
///|
pub fn Sim::snapshot(self : Sim, name? : String = "snapshot") -> SimSnapshot {
self.record(0, "snapshot", name)
{
name,
time: self.now,
next_id: self.next_id,
rng_state: self.rng.state(),
digest: self.digest(),
events: self.events.copy(),
counters: self.metrics.snapshot(),
gauges: self.metrics.gauge_snapshot(),
samples: self.metrics.sample_snapshot(),
}
}
///|
pub fn Sim::restore(snapshot : SimSnapshot) -> Sim {
let sim = Sim::new(seed=snapshot.rng_state)
sim.now = snapshot.time
sim.next_id = snapshot.next_id
sim.events = snapshot.events.copy()
for counter in snapshot.counters {
sim.metrics.inc(counter.name, delta=counter.value)
}
for gauge in snapshot.gauges {
sim.metrics.set_gauge(gauge.name, gauge.value)
}
for sample in snapshot.samples {
sim.metrics.sample(sample.name, sample.value)
}
sim.record(0, "restore", snapshot.name)
sim
}
///|
pub fn SimSnapshot::fork(self : SimSnapshot, name : String) -> Sim {
let sim = Sim::restore(self)
sim.record(0, "fork", name)
sim
}
///|
pub fn compare_forks(
left_name : String,
left : Sim,
right_name : String,
right : Sim,
) -> ForkComparison {
{
left_name,
right_name,
left_digest: left.digest(),
right_digest: right.digest(),
same_digest: left.digest() == right.digest(),
left_events: left.metrics().counter("events_executed"),
right_events: right.metrics().counter("events_executed"),
}
}
///|
pub fn ForkComparison::summary(self : ForkComparison) -> String {
let status = if self.same_digest { "same" } else { "different" }
"forks " +
status +
" left=" +
self.left_name +
" right=" +
self.right_name +
" left_events=" +
self.left_events.to_string() +
" right_events=" +
self.right_events.to_string()
}