1use vrf_pbft::{Config, ConsensusEngine, Node};
2
3fn main() {
4 let config = Config::new(2);
6 let mut engine = ConsensusEngine::new(config);
7
8 for i in 1..=7 {
9 let mut node = Node::new(i, 1000).expect("failed to create node");
10 if i <= 2 {
12 node.set_byzantine(true);
13 }
14 engine.add_node(node);
15 }
16
17 println!("Byzantine fault tolerance demo");
18 println!(" Nodes: 7 (5 honest, 2 byzantine)");
19 println!(" f=2: system tolerates up to 2 faults");
20 println!(" Threshold: 2f+1 = {}\n", 2 * 2 + 1);
21
22 let total_rounds = 100;
23 let blocks = engine.run(total_rounds).expect("simulation failed");
24
25 println!("After {} round attempts:", engine.round());
26 println!(" Blocks committed: {}", blocks.len());
27
28 if !blocks.is_empty() {
29 println!("\n Byzantine nodes voted AGAINST every block,");
30 println!(" but consensus still passed because 5 honest");
31 println!(" nodes exceed the threshold of 5 (2f+1).\n");
32
33 let first_len = engine.nodes()[0].ledger().len();
35 let consistent = engine.nodes().iter().all(|n| n.ledger().len() == first_len);
36 println!(
37 " Ledger consistency: {} ({} blocks per node)",
38 if consistent { "PASS" } else { "FAIL" },
39 first_len
40 );
41 } else {
42 println!("\n No blocks committed (VRF didn't elect enough validators).");
43 println!(" Try running again -- VRF selection is probabilistic.");
44 }
45}