Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
33 commits
Select commit Hold shift + click to select a range
c23a13c
introduce candidatedescriptor type
rphmeier Jul 2, 2020
7a2be24
add PoVDistribution message type
rphmeier Jul 2, 2020
55e1b5a
loosen bound on PoV Distribution to account for equivocations
rphmeier Jul 2, 2020
1db4f3c
re-export some types from the messages module
rphmeier Jul 2, 2020
f6641c4
begin PoV Distribution subsystem
rphmeier Jul 2, 2020
fe005b7
remove redundant index from PoV distribution
rphmeier Jul 3, 2020
27da7ef
define state machine for pov distribution
rphmeier Jul 3, 2020
2cdcefd
handle overseer signals
rphmeier Jul 3, 2020
e66e063
set up control flow
rphmeier Jul 3, 2020
6197058
remove `ValidatorStatement` section
rphmeier Jul 3, 2020
623db00
implement PoV fetching
rphmeier Jul 3, 2020
86d1cf0
implement distribution logic
rphmeier Jul 3, 2020
8557778
add missing `
rphmeier Jul 3, 2020
fa86b24
implement some network bridge event handlers
rphmeier Jul 3, 2020
8b4a7b0
stub for message processing, handle our view change
rphmeier Jul 3, 2020
0b82a0c
control flow for handling messages
rphmeier Jul 3, 2020
a45e58e
handle `awaiting` message
rphmeier Jul 3, 2020
a768179
handle any incoming PoVs and redistribute
rphmeier Jul 3, 2020
d47905d
actually provide a subsystem implementation
rphmeier Jul 3, 2020
bb31777
remove set-builder notation
rphmeier Jul 6, 2020
24d6278
begin testing PoV distribution
rphmeier Jul 7, 2020
5202b3d
test that we send awaiting messages only to peers with same view
rphmeier Jul 7, 2020
3d9d000
ensure we distribute awaited PoVs to peers on view changes
rphmeier Jul 7, 2020
df4a1f1
test that peers can complete fetch and are rewarded
rphmeier Jul 7, 2020
f2c9bfb
test some reporting logic
rphmeier Jul 7, 2020
7923146
ensure peer is reported for flooding
rphmeier Jul 7, 2020
43d610d
test punishing peers diverging from awaited protocol
rphmeier Jul 7, 2020
57f133f
test that we eagerly complete peers' awaited PoVs based on what we re…
rphmeier Jul 7, 2020
7d26c53
test that we prune the awaited set after receiving
rphmeier Jul 7, 2020
6406423
Merge branch 'master' into rh-pov-distribution
rphmeier Jul 7, 2020
0ff3988
expand pov-distribution in guide to match a change I made
rphmeier Jul 7, 2020
8cc66a7
Merge branch 'master' into rh-pov-distribution
rphmeier Jul 7, 2020
f506a91
remove unneeded import
rphmeier Jul 7, 2020
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
handle any incoming PoVs and redistribute
  • Loading branch information
rphmeier committed Jul 3, 2020
commit a768179e7924159264505bea2db59cf55f316c4e
61 changes: 59 additions & 2 deletions node/network/pov-distribution/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -267,6 +267,7 @@ async fn report_peer(
ctx.send_message(AllMessages::NetworkBridge(NetworkBridgeMessage::ReportPeer(peer, rep))).await
}

/// Handle a notification from a peer that they are awaiting some PoVs.
async fn handle_awaiting(
state: &mut State,
ctx: &mut impl SubsystemContext<Message = PoVDistributionMessage>,
Expand Down Expand Up @@ -319,6 +320,9 @@ async fn handle_awaiting(
Ok(())
}

/// Handle an incoming PoV from our peer. Reports them if unexpected, rewards them if not.
///
/// Completes any requests awaiting that PoV.
async fn handle_incoming_pov(
state: &mut State,
ctx: &mut impl SubsystemContext<Message = PoVDistributionMessage>,
Expand All @@ -327,8 +331,61 @@ async fn handle_incoming_pov(
pov_hash: Hash,
pov: PoV,
) -> SubsystemResult<()> {
// TODO [now]
Ok(())
let relay_parent_state = match state.relay_parent_state.get_mut(&relay_parent) {
None => {
report_peer(ctx, peer, COST_UNEXPECTED_POV).await?;
return Ok(());
},
Some(r) => r,
};

let pov = {
// Do validity checks and complete all senders awaiting this PoV.
let fetching = match relay_parent_state.fetching.get_mut(&pov_hash) {
None => {
report_peer(ctx, peer, COST_UNEXPECTED_POV).await?;
return Ok(());
}
Some(f) => f,
};

let hash = pov.hash();
if hash != pov_hash {
report_peer(ctx, peer, COST_UNEXPECTED_POV).await?;
return Ok(());
}

let pov = Arc::new(pov);

if fetching.is_empty() {
// fetching is empty whenever we were awaiting something and
// it was completed afterwards.
report_peer(ctx, peer.clone(), BENEFIT_LATE_POV).await?;
} else {
// fetching is non-empty when the peer just provided us with data we needed.
report_peer(ctx, peer.clone(), BENEFIT_FRESH_POV).await?;
}

for response_sender in fetching.drain(..) {
let _ = response_sender.send(pov.clone());
}

pov
};

// make sure we don't consider this peer as awaiting that PoV anymore.
if let Some(peer_state) = state.peer_state.get_mut(&peer) {
peer_state.awaited.remove(&pov_hash);
}

// distribute the PoV to all other peers who are awaiting it.
distribute_to_awaiting(
&mut state.peer_state,
ctx,
relay_parent,
pov_hash,
&*pov,
).await
}

/// Handles a network bridge update.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -105,10 +105,11 @@ Here is the logic of the state machine:
- For each new `pov_hash` in `pov_hashes`, if there is a `pov` under `pov_hash` in the `known` map, send the peer a `NetworkMessage::SendPoV(relay_parent, pov_hash, pov)`.
- Otherwise, add the `pov_hash` to the `awaited` map
- If this is `NetworkMessage::SendPoV(relay_parent, pov_hash, pov)`:
- If there is no entry under `relay_parent` in `relay_parent_state` or no entry under `pov_hash` in our `awaited` map for that `relay_parent`, report and ignore.
- If there is no entry under `relay_parent` in `relay_parent_state` or no entry under `pov_hash` in our `fetching` map for that `relay_parent`, report and ignore.
- If the blake2-256 hash of the pov doesn't equal `pov_hash`, report and ignore.
- Complete and remove any listeners in the `fetching` map under `pov_hash`. However, leave an empty set of listeners in the `fetching` map to denote that this was something we once awaited. This will allow us to recognize peers who have sent us something we were expecting, but just a little late.
- Add to `known` map.
- Remove the `pov_hash` from the `peer.awaited` map, if any.
- Send `NetworkMessage::SendPoV(relay_parent, descriptor.pov_hash, PoV)` to all peers who have the `descriptor.pov_hash` in the set under `relay_parent` in the `peer.awaited` map and remove the entry from `peer.awaited`.
- On `PeerViewChange(peer_id, view)`
- If Peer is unknown, ignore.
Expand Down