hotmint_consensus/
network.rs1use std::collections::HashMap;
2
3use hotmint_types::epoch::EpochNumber;
4use hotmint_types::evidence::EquivocationProof;
5use hotmint_types::{ConsensusMessage, ValidatorId, ValidatorSet};
6
7pub type MsgSender = tokio::sync::mpsc::Sender<(Option<ValidatorId>, ConsensusMessage)>;
9pub type MsgReceiver = tokio::sync::mpsc::Receiver<(Option<ValidatorId>, ConsensusMessage)>;
10
11pub trait NetworkSink: Send + Sync {
12 fn broadcast(&self, msg: ConsensusMessage);
13 fn send_to(&self, target: ValidatorId, msg: ConsensusMessage);
14 fn on_epoch_change(&self, _epoch: EpochNumber, _new_validator_set: &ValidatorSet) {}
17
18 fn broadcast_evidence(&self, _proof: &EquivocationProof) {}
21}
22
23pub struct ChannelNetwork {
25 pub self_id: ValidatorId,
26 pub senders: Vec<(ValidatorId, MsgSender)>,
27}
28
29impl ChannelNetwork {
30 pub fn new(self_id: ValidatorId, senders: Vec<(ValidatorId, MsgSender)>) -> Self {
31 Self { self_id, senders }
32 }
33
34 pub fn create_mesh(n: u64) -> Vec<(ChannelNetwork, MsgReceiver)> {
40 let mut senders: HashMap<ValidatorId, MsgSender> = HashMap::new();
41 let mut receivers: HashMap<ValidatorId, MsgReceiver> = HashMap::new();
42
43 for i in 0..n {
44 let (tx, rx) = tokio::sync::mpsc::channel(8192);
45 senders.insert(ValidatorId(i), tx);
46 receivers.insert(ValidatorId(i), rx);
47 }
48
49 let all_senders: Vec<(ValidatorId, MsgSender)> =
50 senders.iter().map(|(&id, tx)| (id, tx.clone())).collect();
51
52 (0..n)
53 .map(|i| {
54 let vid = ValidatorId(i);
55 let rx = receivers.remove(&vid).unwrap();
56 let network = ChannelNetwork::new(vid, all_senders.clone());
57 (network, rx)
58 })
59 .collect()
60 }
61}
62
63impl NetworkSink for ChannelNetwork {
64 fn broadcast(&self, msg: ConsensusMessage) {
65 for (id, sender) in &self.senders {
66 if *id != self.self_id {
67 let _ = sender.try_send((Some(self.self_id), msg.clone()));
68 }
69 }
70 }
71
72 fn send_to(&self, target: ValidatorId, msg: ConsensusMessage) {
73 for (id, sender) in &self.senders {
74 if *id == target {
75 let _ = sender.try_send((Some(self.self_id), msg));
76 return;
77 }
78 }
79 }
80}