-
Notifications
You must be signed in to change notification settings - Fork 746
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Generalize sync ActiveRequests #6398
Changes from all commits
043d52b
9446569
b9cd5ad
715ba8c
0d593b8
1270322
1910bf6
746612d
af35a27
a3c1ffe
a0844e1
fc67e59
b22278f
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change | ||||||||||||
---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
@@ -25,8 +25,8 @@ use beacon_chain::{ | |||||||||||||
use beacon_processor::WorkEvent; | ||||||||||||||
use lighthouse_network::rpc::{RPCError, RequestType, RpcErrorResponse}; | ||||||||||||||
use lighthouse_network::service::api_types::{ | ||||||||||||||
AppRequestId, DataColumnsByRootRequester, Id, SamplingRequester, SingleLookupReqId, | ||||||||||||||
SyncRequestId, | ||||||||||||||
AppRequestId, DataColumnsByRootRequestId, DataColumnsByRootRequester, Id, SamplingRequester, | ||||||||||||||
SingleLookupReqId, SyncRequestId, | ||||||||||||||
}; | ||||||||||||||
use lighthouse_network::types::SyncState; | ||||||||||||||
use lighthouse_network::NetworkConfig; | ||||||||||||||
|
@@ -745,10 +745,10 @@ impl TestRig { | |||||||||||||
let first_dc = data_columns.first().unwrap(); | ||||||||||||||
let block_root = first_dc.block_root(); | ||||||||||||||
let sampling_request_id = match id.0 { | ||||||||||||||
SyncRequestId::DataColumnsByRoot( | ||||||||||||||
_, | ||||||||||||||
_requester @ DataColumnsByRootRequester::Sampling(sampling_id), | ||||||||||||||
) => sampling_id.sampling_request_id, | ||||||||||||||
SyncRequestId::DataColumnsByRoot(DataColumnsByRootRequestId { | ||||||||||||||
requester: DataColumnsByRootRequester::Sampling(sampling_id), | ||||||||||||||
.. | ||||||||||||||
}) => sampling_id.sampling_request_id, | ||||||||||||||
_ => unreachable!(), | ||||||||||||||
}; | ||||||||||||||
self.complete_data_columns_by_root_request(id, data_columns); | ||||||||||||||
|
@@ -773,14 +773,15 @@ impl TestRig { | |||||||||||||
data_columns: Vec<Arc<DataColumnSidecar<E>>>, | ||||||||||||||
missing_components: bool, | ||||||||||||||
) { | ||||||||||||||
let lookup_id = | ||||||||||||||
if let SyncRequestId::DataColumnsByRoot(_, DataColumnsByRootRequester::Custody(id)) = | ||||||||||||||
ids.first().unwrap().0 | ||||||||||||||
{ | ||||||||||||||
id.requester.0.lookup_id | ||||||||||||||
} else { | ||||||||||||||
panic!("not a custody requester") | ||||||||||||||
}; | ||||||||||||||
let lookup_id = if let SyncRequestId::DataColumnsByRoot(DataColumnsByRootRequestId { | ||||||||||||||
requester: DataColumnsByRootRequester::Custody(id), | ||||||||||||||
.. | ||||||||||||||
}) = ids.first().unwrap().0 | ||||||||||||||
{ | ||||||||||||||
id.requester.0.lookup_id | ||||||||||||||
} else { | ||||||||||||||
panic!("not a custody requester") | ||||||||||||||
}; | ||||||||||||||
|
||||||||||||||
let first_column = data_columns.first().cloned().unwrap(); | ||||||||||||||
|
||||||||||||||
|
@@ -1189,6 +1190,7 @@ impl TestRig { | |||||||||||||
penalty_msg, expect_penalty_msg, | ||||||||||||||
"Unexpected penalty msg for {peer_id}" | ||||||||||||||
); | ||||||||||||||
self.log(&format!("Found expected penalty {penalty_msg}")); | ||||||||||||||
} | ||||||||||||||
|
||||||||||||||
pub fn expect_single_penalty(&mut self, peer_id: PeerId, expect_penalty_msg: &'static str) { | ||||||||||||||
|
@@ -1416,7 +1418,7 @@ fn test_single_block_lookup_empty_response() { | |||||||||||||
|
||||||||||||||
// The peer does not have the block. It should be penalized. | ||||||||||||||
r.single_lookup_block_response(id, peer_id, None); | ||||||||||||||
r.expect_penalty(peer_id, "NoResponseReturned"); | ||||||||||||||
r.expect_penalty(peer_id, "NotEnoughResponsesReturned"); | ||||||||||||||
// it should be retried | ||||||||||||||
let id = r.expect_block_lookup_request(block_root); | ||||||||||||||
// Send the right block this time. | ||||||||||||||
|
@@ -2160,7 +2162,7 @@ fn sampling_batch_requests_not_enough_responses_returned() { | |||||||||||||
r.assert_sampling_request_ongoing(block_root, &column_indexes); | ||||||||||||||
|
||||||||||||||
// Split the indexes to simulate the case where the supernode doesn't have the requested column. | ||||||||||||||
let (_column_indexes_supernode_does_not_have, column_indexes_to_complete) = | ||||||||||||||
let (column_indexes_supernode_does_not_have, column_indexes_to_complete) = | ||||||||||||||
column_indexes.split_at(1); | ||||||||||||||
|
||||||||||||||
// Complete the requests but only partially, so a NotEnoughResponsesReturned error occurs. | ||||||||||||||
|
@@ -2176,7 +2178,7 @@ fn sampling_batch_requests_not_enough_responses_returned() { | |||||||||||||
|
||||||||||||||
// The request status should be set to NoPeers since the supernode, the only peer, returned not enough responses. | ||||||||||||||
r.log_sampling_requests(block_root, &column_indexes); | ||||||||||||||
r.assert_sampling_request_nopeers(block_root, &column_indexes); | ||||||||||||||
r.assert_sampling_request_nopeers(block_root, column_indexes_supernode_does_not_have); | ||||||||||||||
|
||||||||||||||
// The sampling request stalls. | ||||||||||||||
r.expect_empty_network(); | ||||||||||||||
|
@@ -2721,11 +2723,6 @@ mod deneb_only { | |||||||||||||
self.blobs.pop().expect("blobs"); | ||||||||||||||
self | ||||||||||||||
} | ||||||||||||||
fn invalidate_blobs_too_many(mut self) -> Self { | ||||||||||||||
let first_blob = self.blobs.first().expect("blob").clone(); | ||||||||||||||
self.blobs.push(first_blob); | ||||||||||||||
self | ||||||||||||||
} | ||||||||||||||
fn expect_block_process(mut self) -> Self { | ||||||||||||||
self.rig.expect_block_process(ResponseType::Block); | ||||||||||||||
self | ||||||||||||||
|
@@ -2814,21 +2811,6 @@ mod deneb_only { | |||||||||||||
.expect_no_block_request(); | ||||||||||||||
} | ||||||||||||||
|
||||||||||||||
#[test] | ||||||||||||||
fn single_block_response_then_too_many_blobs_response_attestation() { | ||||||||||||||
let Some(tester) = DenebTester::new(RequestTrigger::AttestationUnknownBlock) else { | ||||||||||||||
return; | ||||||||||||||
}; | ||||||||||||||
tester | ||||||||||||||
.block_response_triggering_process() | ||||||||||||||
.invalidate_blobs_too_many() | ||||||||||||||
.blobs_response() | ||||||||||||||
.expect_penalty("TooManyResponses") | ||||||||||||||
// Network context returns "download success" because the request has enough blobs + it | ||||||||||||||
// downscores the peer for returning too many. | ||||||||||||||
.expect_no_block_request(); | ||||||||||||||
} | ||||||||||||||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This test needs a scenario where sync receives more blob chunks than originally requested. This can never happen in practice so I choose to not handle this scenario to reduce complexity lighthouse/beacon_node/network/src/sync/network_context/requests.rs Lines 114 to 119 in 9446569
|
||||||||||||||
|
||||||||||||||
// Test peer returning block that has unknown parent, and a new lookup is created | ||||||||||||||
#[test] | ||||||||||||||
fn parent_block_unknown_parent() { | ||||||||||||||
|
@@ -2869,7 +2851,7 @@ mod deneb_only { | |||||||||||||
}; | ||||||||||||||
tester | ||||||||||||||
.empty_block_response() | ||||||||||||||
.expect_penalty("NoResponseReturned") | ||||||||||||||
.expect_penalty("NotEnoughResponsesReturned") | ||||||||||||||
.expect_block_request() | ||||||||||||||
.expect_no_blobs_request() | ||||||||||||||
.block_response_and_expect_blob_request() | ||||||||||||||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Having the requester inside the ID just simplifies downstream code and makes it symmetrical with the other variants