mirror of
https://github.com/sigp/lighthouse.git
synced 2026-05-30 12:47:05 +00:00
resolve merge conflicts
This commit is contained in:
@@ -5,8 +5,12 @@ use crate::common::spec_with_all_forks_enabled;
|
||||
use crate::common::{Protocol, build_tracing_subscriber};
|
||||
use bls::Signature;
|
||||
use fixed_bytes::FixedBytesExtended;
|
||||
use libp2p::PeerId;
|
||||
use lighthouse_network::rpc::{RequestType, methods::*};
|
||||
use lighthouse_network::service::api_types::AppRequestId;
|
||||
use lighthouse_network::service::api_types::{
|
||||
AppRequestId, BlobsByRangeRequestId, BlocksByRangeRequestId, ComponentsByRangeRequestId,
|
||||
DataColumnsByRangeRequestId, DataColumnsByRangeRequester, RangeRequestId, SyncRequestId,
|
||||
};
|
||||
use lighthouse_network::{NetworkEvent, ReportSource, Response};
|
||||
use ssz::Encode;
|
||||
use ssz_types::{RuntimeVariableList, VariableList};
|
||||
@@ -14,12 +18,12 @@ use std::sync::Arc;
|
||||
use std::time::{Duration, Instant};
|
||||
use tokio::runtime::Runtime;
|
||||
use tokio::time::sleep;
|
||||
use tracing::{Instrument, debug, error, info_span, warn};
|
||||
use tracing::{Instrument, debug, error, info, info_span, warn};
|
||||
use types::{
|
||||
BeaconBlock, BeaconBlockAltair, BeaconBlockBase, BeaconBlockBellatrix, BeaconBlockHeader,
|
||||
BlobSidecar, ChainSpec, DataColumnSidecar, DataColumnsByRootIdentifier, EmptyBlock, Epoch,
|
||||
EthSpec, ForkName, Hash256, KzgCommitment, KzgProof, MinimalEthSpec, SignedBeaconBlock,
|
||||
SignedBeaconBlockHeader, Slot,
|
||||
BlobSidecar, ChainSpec, DataColumnSidecar, DataColumnSidecarFulu, DataColumnSidecarGloas,
|
||||
DataColumnsByRootIdentifier, EmptyBlock, Epoch, EthSpec, ForkName, Hash256, KzgCommitment,
|
||||
KzgProof, MinimalEthSpec, SignedBeaconBlock, SignedBeaconBlockHeader, Slot,
|
||||
};
|
||||
|
||||
type E = MinimalEthSpec;
|
||||
@@ -42,8 +46,10 @@ fn bellatrix_block_small(spec: &ChainSpec) -> BeaconBlock<E> {
|
||||
/// Hence, we generate a bellatrix block just greater than `MAX_RPC_SIZE` to test rejection on the rpc layer.
|
||||
fn bellatrix_block_large(spec: &ChainSpec) -> BeaconBlock<E> {
|
||||
let mut block = BeaconBlockBellatrix::<E>::empty(spec);
|
||||
// 11,000 × 1KB ≈ 11MB, just above the 10MB max_payload_size.
|
||||
// Previously used 100,000 txs (~100MB) which caused hangs and timeouts.
|
||||
let tx = VariableList::try_from(vec![0; 1024]).unwrap();
|
||||
let txs = VariableList::try_from(std::iter::repeat_n(tx, 100000).collect::<Vec<_>>()).unwrap();
|
||||
let txs = VariableList::try_from(std::iter::repeat_n(tx, 11000).collect::<Vec<_>>()).unwrap();
|
||||
|
||||
block.body.execution_payload.execution_payload.transactions = txs;
|
||||
|
||||
@@ -133,16 +139,10 @@ fn test_tcp_status_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
debug!("Receiver Received");
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
debug!("Receiver Received");
|
||||
receiver.send_response(peer_id, inbound_request_id, rpc_response.clone());
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
@@ -263,34 +263,33 @@ fn test_tcp_blocks_by_range_chunked_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for i in 0..messages_to_send {
|
||||
// Send first third of responses as base blocks,
|
||||
// second as altair and third as bellatrix.
|
||||
let rpc_response = if i < 2 {
|
||||
rpc_response_base.clone()
|
||||
} else if i < 4 {
|
||||
rpc_response_altair.clone()
|
||||
} else {
|
||||
rpc_response_bellatrix_small.clone()
|
||||
};
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for i in 0..messages_to_send {
|
||||
// Send first third of responses as base blocks,
|
||||
// second as altair and third as bellatrix.
|
||||
let rpc_response = if i < 2 {
|
||||
rpc_response_base.clone()
|
||||
} else if i < 4 {
|
||||
rpc_response_altair.clone()
|
||||
} else {
|
||||
rpc_response_bellatrix_small.clone()
|
||||
};
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
);
|
||||
}
|
||||
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
}
|
||||
@@ -398,26 +397,24 @@ fn test_blobs_by_range_chunked_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for _ in 0..messages_to_send {
|
||||
// Send first third of responses as base blocks,
|
||||
// second as altair and third as bellatrix.
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for _ in 0..messages_to_send {
|
||||
// Send first third of responses as base blocks,
|
||||
// second as altair and third as bellatrix.
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlobsByRange(None),
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlobsByRange(None),
|
||||
);
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
@@ -506,25 +503,23 @@ fn test_tcp_blocks_by_range_over_limit() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for _ in 0..messages_to_send {
|
||||
let rpc_response = rpc_response_bellatrix_large.clone();
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
for _ in 0..messages_to_send {
|
||||
let rpc_response = rpc_response_bellatrix_large.clone();
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
);
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
@@ -644,12 +639,10 @@ fn test_tcp_blocks_by_range_chunked_rpc_terminates_correctly() {
|
||||
request_type,
|
||||
},
|
||||
_,
|
||||
)) => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
message_info = Some((peer_id, inbound_request_id));
|
||||
}
|
||||
)) if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
message_info = Some((peer_id, inbound_request_id));
|
||||
}
|
||||
futures::future::Either::Right((_, _)) => {} // The timeout hit, send messages if required
|
||||
_ => continue,
|
||||
@@ -764,25 +757,23 @@ fn test_tcp_blocks_by_range_single_empty_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
|
||||
for _ in 1..=messages_to_send {
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
for _ in 1..=messages_to_send {
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
rpc_response.clone(),
|
||||
);
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
);
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
@@ -911,31 +902,29 @@ fn test_tcp_blocks_by_root_chunked_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
debug!("Receiver got request");
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
debug!("Receiver got request");
|
||||
|
||||
for i in 0..messages_to_send {
|
||||
// Send equal base, altair and bellatrix blocks
|
||||
let rpc_response = if i < 2 {
|
||||
rpc_response_base.clone()
|
||||
} else if i < 4 {
|
||||
rpc_response_altair.clone()
|
||||
} else {
|
||||
rpc_response_bellatrix_small.clone()
|
||||
};
|
||||
receiver.send_response(peer_id, inbound_request_id, rpc_response);
|
||||
debug!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
);
|
||||
debug!("Send stream term");
|
||||
for i in 0..messages_to_send {
|
||||
// Send equal base, altair and bellatrix blocks
|
||||
let rpc_response = if i < 2 {
|
||||
rpc_response_base.clone()
|
||||
} else if i < 4 {
|
||||
rpc_response_altair.clone()
|
||||
} else {
|
||||
rpc_response_bellatrix_small.clone()
|
||||
};
|
||||
receiver.send_response(peer_id, inbound_request_id, rpc_response);
|
||||
debug!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::BlocksByRange(None),
|
||||
);
|
||||
debug!("Send stream term");
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
}
|
||||
@@ -952,9 +941,7 @@ fn test_tcp_blocks_by_root_chunked_rpc() {
|
||||
})
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[allow(clippy::single_match)]
|
||||
fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
fn test_tcp_columns_by_root_chunked_rpc_for_fork(fork_name: ForkName) {
|
||||
// Set up the logging.
|
||||
let log_level = "debug";
|
||||
let enable_logging = true;
|
||||
@@ -963,14 +950,17 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
let messages_to_send = 32 * num_of_columns;
|
||||
|
||||
let spec = Arc::new(spec_with_all_forks_enabled());
|
||||
let current_fork_name = ForkName::Fulu;
|
||||
let slot = spec
|
||||
.fork_epoch(fork_name)
|
||||
.expect("fork must be scheduled")
|
||||
.start_slot(E::slots_per_epoch());
|
||||
|
||||
let rt = Arc::new(Runtime::new().unwrap());
|
||||
// get sender/receiver
|
||||
rt.block_on(async {
|
||||
let (mut sender, mut receiver) = common::build_node_pair(
|
||||
Arc::downgrade(&rt),
|
||||
current_fork_name,
|
||||
fork_name,
|
||||
spec.clone(),
|
||||
Protocol::Tcp,
|
||||
false,
|
||||
@@ -980,7 +970,7 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
|
||||
// DataColumnsByRootRequest Request
|
||||
|
||||
let max_request_blocks = spec.max_request_blocks(current_fork_name);
|
||||
let max_request_blocks = spec.max_request_blocks(fork_name);
|
||||
let req = DataColumnsByRootRequest::new(
|
||||
vec![
|
||||
DataColumnsByRootIdentifier {
|
||||
@@ -999,7 +989,7 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
let req_decoded = DataColumnsByRootRequest {
|
||||
data_column_ids: <RuntimeVariableList<DataColumnsByRootIdentifier<E>>>::from_ssz_bytes(
|
||||
&req_bytes,
|
||||
spec.max_request_blocks(current_fork_name),
|
||||
spec.max_request_blocks(fork_name),
|
||||
)
|
||||
.unwrap(),
|
||||
};
|
||||
@@ -1007,30 +997,43 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
let rpc_request = RequestType::DataColumnsByRoot(req);
|
||||
|
||||
// DataColumnsByRoot Response
|
||||
let data_column = Arc::new(DataColumnSidecar {
|
||||
index: 1,
|
||||
signed_block_header: SignedBeaconBlockHeader {
|
||||
message: BeaconBlockHeader {
|
||||
slot: 320u64.into(),
|
||||
proposer_index: 1,
|
||||
parent_root: Hash256::zero(),
|
||||
state_root: Hash256::zero(),
|
||||
body_root: Hash256::zero(),
|
||||
let data_column = if fork_name.gloas_enabled() {
|
||||
Arc::new(DataColumnSidecar::Gloas(DataColumnSidecarGloas {
|
||||
index: 1,
|
||||
slot,
|
||||
beacon_block_root: Hash256::zero(),
|
||||
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
}))
|
||||
} else {
|
||||
Arc::new(DataColumnSidecar::Fulu(DataColumnSidecarFulu {
|
||||
index: 1,
|
||||
signed_block_header: SignedBeaconBlockHeader {
|
||||
message: BeaconBlockHeader {
|
||||
slot,
|
||||
proposer_index: 1,
|
||||
parent_root: Hash256::zero(),
|
||||
state_root: Hash256::zero(),
|
||||
body_root: Hash256::zero(),
|
||||
},
|
||||
signature: Signature::empty(),
|
||||
},
|
||||
signature: Signature::empty(),
|
||||
},
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_commitments: vec![KzgCommitment::empty_for_testing()].try_into().unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
kzg_commitments_inclusion_proof: vec![
|
||||
Hash256::zero();
|
||||
E::kzg_commitments_inclusion_proof_depth()
|
||||
]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_commitments: vec![KzgCommitment::empty_for_testing()].try_into().unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
kzg_commitments_inclusion_proof: vec![
|
||||
Hash256::zero();
|
||||
E::kzg_commitments_inclusion_proof_depth()
|
||||
]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
});
|
||||
}))
|
||||
};
|
||||
|
||||
let rpc_response = Response::DataColumnsByRoot(Some(data_column.clone()));
|
||||
|
||||
@@ -1041,7 +1044,7 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
loop {
|
||||
match sender.next_event().await {
|
||||
NetworkEvent::PeerConnectedOutgoing(peer_id) => {
|
||||
tracing::info!("Sending RPC");
|
||||
info!("Sending RPC");
|
||||
tokio::time::sleep(Duration::from_secs(1)).await;
|
||||
sender
|
||||
.send_request(peer_id, AppRequestId::Router, rpc_request.clone())
|
||||
@@ -1055,7 +1058,7 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
Response::DataColumnsByRoot(Some(sidecar)) => {
|
||||
assert_eq!(sidecar, data_column.clone());
|
||||
messages_received += 1;
|
||||
tracing::info!("Chunk received");
|
||||
info!("Chunk received");
|
||||
}
|
||||
Response::DataColumnsByRoot(None) => {
|
||||
// should be exactly messages_to_send
|
||||
@@ -1079,30 +1082,28 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
tracing::info!("Receiver got request");
|
||||
} if request_type == rpc_request => {
|
||||
// send the response
|
||||
info!("Receiver got request");
|
||||
|
||||
for _ in 0..messages_to_send {
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
tracing::info!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
for _ in 0..messages_to_send {
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::DataColumnsByRoot(None),
|
||||
rpc_response.clone(),
|
||||
);
|
||||
tracing::info!("Send stream term");
|
||||
info!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::DataColumnsByRoot(None),
|
||||
);
|
||||
info!("Send stream term");
|
||||
}
|
||||
e => {
|
||||
tracing::info!(?e, "Got event");
|
||||
info!(?e, "Got event");
|
||||
} // Ignore other events
|
||||
}
|
||||
}
|
||||
@@ -1120,7 +1121,17 @@ fn test_tcp_columns_by_root_chunked_rpc() {
|
||||
|
||||
#[test]
|
||||
#[allow(clippy::single_match)]
|
||||
fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
fn test_tcp_columns_by_root_chunked_rpc_fulu() {
|
||||
test_tcp_columns_by_root_chunked_rpc_for_fork(ForkName::Fulu);
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[allow(clippy::single_match)]
|
||||
fn test_tcp_columns_by_root_chunked_rpc_gloas() {
|
||||
test_tcp_columns_by_root_chunked_rpc_for_fork(ForkName::Gloas);
|
||||
}
|
||||
|
||||
fn test_tcp_columns_by_range_chunked_rpc_for_fork(fork_name: ForkName) {
|
||||
// Set up the logging.
|
||||
let log_level = "debug";
|
||||
let enable_logging = true;
|
||||
@@ -1129,14 +1140,17 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
let messages_to_send = 32;
|
||||
|
||||
let spec = Arc::new(spec_with_all_forks_enabled());
|
||||
let current_fork_name = ForkName::Fulu;
|
||||
let slot = spec
|
||||
.fork_epoch(fork_name)
|
||||
.expect("fork must be scheduled")
|
||||
.start_slot(E::slots_per_epoch());
|
||||
|
||||
let rt = Arc::new(Runtime::new().unwrap());
|
||||
// get sender/receiver
|
||||
rt.block_on(async {
|
||||
let (mut sender, mut receiver) = common::build_node_pair(
|
||||
Arc::downgrade(&rt),
|
||||
current_fork_name,
|
||||
fork_name,
|
||||
spec.clone(),
|
||||
Protocol::Tcp,
|
||||
false,
|
||||
@@ -1146,36 +1160,48 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
|
||||
// DataColumnsByRange Request
|
||||
let rpc_request = RequestType::DataColumnsByRange(DataColumnsByRangeRequest {
|
||||
start_slot: 320,
|
||||
start_slot: slot.as_u64(),
|
||||
count: 32,
|
||||
columns: (0..E::number_of_columns() as u64).collect(),
|
||||
});
|
||||
|
||||
// DataColumnsByRange Response
|
||||
let data_column = Arc::new(DataColumnSidecar {
|
||||
index: 1,
|
||||
signed_block_header: SignedBeaconBlockHeader {
|
||||
message: BeaconBlockHeader {
|
||||
slot: 320u64.into(),
|
||||
proposer_index: 1,
|
||||
parent_root: Hash256::zero(),
|
||||
state_root: Hash256::zero(),
|
||||
body_root: Hash256::zero(),
|
||||
let data_column = if fork_name.gloas_enabled() {
|
||||
Arc::new(DataColumnSidecar::Gloas(DataColumnSidecarGloas {
|
||||
index: 1,
|
||||
slot,
|
||||
beacon_block_root: Hash256::zero(),
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
}))
|
||||
} else {
|
||||
Arc::new(DataColumnSidecar::Fulu(DataColumnSidecarFulu {
|
||||
index: 1,
|
||||
signed_block_header: SignedBeaconBlockHeader {
|
||||
message: BeaconBlockHeader {
|
||||
slot,
|
||||
proposer_index: 1,
|
||||
parent_root: Hash256::zero(),
|
||||
state_root: Hash256::zero(),
|
||||
body_root: Hash256::zero(),
|
||||
},
|
||||
signature: Signature::empty(),
|
||||
},
|
||||
signature: Signature::empty(),
|
||||
},
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
column: vec![vec![0; E::bytes_per_cell()].try_into().unwrap()]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_commitments: vec![KzgCommitment::empty_for_testing()].try_into().unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
kzg_commitments_inclusion_proof: vec![
|
||||
Hash256::zero();
|
||||
E::kzg_commitments_inclusion_proof_depth()
|
||||
]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
kzg_commitments: vec![KzgCommitment::empty_for_testing()].try_into().unwrap(),
|
||||
kzg_proofs: vec![KzgProof::empty()].try_into().unwrap(),
|
||||
kzg_commitments_inclusion_proof: vec![
|
||||
Hash256::zero();
|
||||
E::kzg_commitments_inclusion_proof_depth()
|
||||
]
|
||||
.try_into()
|
||||
.unwrap(),
|
||||
});
|
||||
}))
|
||||
};
|
||||
|
||||
let rpc_response = Response::DataColumnsByRange(Some(data_column.clone()));
|
||||
|
||||
@@ -1186,7 +1212,7 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
loop {
|
||||
match sender.next_event().await {
|
||||
NetworkEvent::PeerConnectedOutgoing(peer_id) => {
|
||||
tracing::info!("Sending RPC");
|
||||
info!("Sending RPC");
|
||||
sender
|
||||
.send_request(peer_id, AppRequestId::Router, rpc_request.clone())
|
||||
.unwrap();
|
||||
@@ -1199,7 +1225,7 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
Response::DataColumnsByRange(Some(sidecar)) => {
|
||||
assert_eq!(sidecar, data_column.clone());
|
||||
messages_received += 1;
|
||||
tracing::info!("Chunk received");
|
||||
info!("Chunk received");
|
||||
}
|
||||
Response::DataColumnsByRange(None) => {
|
||||
// should be exactly messages_to_send
|
||||
@@ -1218,34 +1244,27 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
// build the receiver future
|
||||
let receiver_future = async {
|
||||
loop {
|
||||
match receiver.next_event().await {
|
||||
NetworkEvent::RequestReceived {
|
||||
if let NetworkEvent::RequestReceived {
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} = receiver.next_event().await
|
||||
&& request_type == rpc_request
|
||||
{
|
||||
// send the response
|
||||
info!("Receiver got request");
|
||||
|
||||
for _ in 0..messages_to_send {
|
||||
receiver.send_response(peer_id, inbound_request_id, rpc_response.clone());
|
||||
info!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
request_type,
|
||||
} => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
tracing::info!("Receiver got request");
|
||||
|
||||
for _ in 0..messages_to_send {
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
rpc_response.clone(),
|
||||
);
|
||||
tracing::info!("Sending message");
|
||||
}
|
||||
// send the stream termination
|
||||
receiver.send_response(
|
||||
peer_id,
|
||||
inbound_request_id,
|
||||
Response::DataColumnsByRange(None),
|
||||
);
|
||||
tracing::info!("Send stream term");
|
||||
}
|
||||
}
|
||||
_ => {} // Ignore other events
|
||||
Response::DataColumnsByRange(None),
|
||||
);
|
||||
info!("Send stream term");
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1260,6 +1279,18 @@ fn test_tcp_columns_by_range_chunked_rpc() {
|
||||
})
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[allow(clippy::single_match)]
|
||||
fn test_tcp_columns_by_range_chunked_rpc_fulu() {
|
||||
test_tcp_columns_by_range_chunked_rpc_for_fork(ForkName::Fulu);
|
||||
}
|
||||
|
||||
#[test]
|
||||
#[allow(clippy::single_match)]
|
||||
fn test_tcp_columns_by_range_chunked_rpc_gloas() {
|
||||
test_tcp_columns_by_range_chunked_rpc_for_fork(ForkName::Gloas);
|
||||
}
|
||||
|
||||
// Tests a streamed, chunked BlocksByRoot RPC Message terminates when all expected reponses have been received
|
||||
#[test]
|
||||
fn test_tcp_blocks_by_root_chunked_rpc_terminates_correctly() {
|
||||
@@ -1375,12 +1406,10 @@ fn test_tcp_blocks_by_root_chunked_rpc_terminates_correctly() {
|
||||
request_type,
|
||||
},
|
||||
_,
|
||||
)) => {
|
||||
if request_type == rpc_request {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
message_info = Some((peer_id, inbound_request_id));
|
||||
}
|
||||
)) if request_type == rpc_request => {
|
||||
// send the response
|
||||
warn!("Receiver got request");
|
||||
message_info = Some((peer_id, inbound_request_id));
|
||||
}
|
||||
futures::future::Either::Right((_, _)) => {} // The timeout hit, send messages if required
|
||||
_ => continue,
|
||||
@@ -1739,3 +1768,157 @@ fn test_active_requests() {
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
// Test that when a node receives an invalid BlocksByRange request exceeding the maximum count,
|
||||
// it bans the sender.
|
||||
#[test]
|
||||
fn test_request_too_large_blocks_by_range() {
|
||||
let spec = Arc::new(spec_with_all_forks_enabled());
|
||||
|
||||
test_request_too_large(
|
||||
AppRequestId::Sync(SyncRequestId::BlocksByRange(BlocksByRangeRequestId {
|
||||
id: 1,
|
||||
parent_request_id: ComponentsByRangeRequestId {
|
||||
id: 1,
|
||||
requester: RangeRequestId::RangeSync {
|
||||
chain_id: 1,
|
||||
batch_id: Epoch::new(1),
|
||||
},
|
||||
},
|
||||
})),
|
||||
RequestType::BlocksByRange(OldBlocksByRangeRequest::new(
|
||||
0,
|
||||
spec.max_request_blocks(ForkName::Base) as u64 + 1, // exceeds the max request defined in the spec.
|
||||
1,
|
||||
)),
|
||||
);
|
||||
}
|
||||
|
||||
// Test that when a node receives an invalid BlobsByRange request exceeding the maximum count,
|
||||
// it bans the sender.
|
||||
#[test]
|
||||
fn test_request_too_large_blobs_by_range() {
|
||||
let spec = Arc::new(spec_with_all_forks_enabled());
|
||||
|
||||
let max_request_blobs_count = spec.max_request_blob_sidecars(ForkName::Base) as u64
|
||||
/ spec.max_blobs_per_block_within_fork(ForkName::Base);
|
||||
test_request_too_large(
|
||||
AppRequestId::Sync(SyncRequestId::BlobsByRange(BlobsByRangeRequestId {
|
||||
id: 1,
|
||||
parent_request_id: ComponentsByRangeRequestId {
|
||||
id: 1,
|
||||
requester: RangeRequestId::RangeSync {
|
||||
chain_id: 1,
|
||||
batch_id: Epoch::new(1),
|
||||
},
|
||||
},
|
||||
})),
|
||||
RequestType::BlobsByRange(BlobsByRangeRequest {
|
||||
start_slot: 0,
|
||||
count: max_request_blobs_count + 1, // exceeds the max request defined in the spec.
|
||||
}),
|
||||
);
|
||||
}
|
||||
|
||||
// Test that when a node receives an invalid DataColumnsByRange request exceeding the columns count,
|
||||
// it bans the sender.
|
||||
#[test]
|
||||
fn test_request_too_large_data_columns_by_range() {
|
||||
test_request_too_large(
|
||||
AppRequestId::Sync(SyncRequestId::DataColumnsByRange(
|
||||
DataColumnsByRangeRequestId {
|
||||
id: 1,
|
||||
parent_request_id: DataColumnsByRangeRequester::ComponentsByRange(
|
||||
ComponentsByRangeRequestId {
|
||||
id: 1,
|
||||
requester: RangeRequestId::RangeSync {
|
||||
chain_id: 1,
|
||||
batch_id: Epoch::new(1),
|
||||
},
|
||||
},
|
||||
),
|
||||
peer: PeerId::random(),
|
||||
},
|
||||
)),
|
||||
RequestType::DataColumnsByRange(DataColumnsByRangeRequest {
|
||||
start_slot: 0,
|
||||
count: 0,
|
||||
// exceeds the max request defined in the spec.
|
||||
columns: vec![0; E::number_of_columns() + 1],
|
||||
}),
|
||||
);
|
||||
}
|
||||
|
||||
fn test_request_too_large(app_request_id: AppRequestId, request: RequestType<E>) {
|
||||
// Set up the logging.
|
||||
let log_level = "debug";
|
||||
let enable_logging = true;
|
||||
let _subscriber = build_tracing_subscriber(log_level, enable_logging);
|
||||
let rt = Arc::new(Runtime::new().unwrap());
|
||||
let spec = Arc::new(spec_with_all_forks_enabled());
|
||||
|
||||
rt.block_on(async {
|
||||
let (mut sender, mut receiver) = common::build_node_pair(
|
||||
Arc::downgrade(&rt),
|
||||
ForkName::Base,
|
||||
spec,
|
||||
Protocol::Tcp,
|
||||
false,
|
||||
None,
|
||||
)
|
||||
.await;
|
||||
|
||||
// Build the sender future
|
||||
let sender_future = async {
|
||||
loop {
|
||||
match sender.next_event().await {
|
||||
NetworkEvent::PeerConnectedOutgoing(peer_id) => {
|
||||
debug!(?request, %peer_id, "Sending RPC request");
|
||||
sender
|
||||
.send_request(peer_id, app_request_id, request.clone())
|
||||
.unwrap();
|
||||
}
|
||||
NetworkEvent::ResponseReceived {
|
||||
app_request_id,
|
||||
response,
|
||||
..
|
||||
} => {
|
||||
debug!(?app_request_id, ?response, "Received response");
|
||||
}
|
||||
NetworkEvent::RPCFailed { error, .. } => {
|
||||
// This variant should be unreachable, as the receiver doesn't respond with an error when a request exceeds the limit.
|
||||
debug!(?error, "RPC failed");
|
||||
unreachable!();
|
||||
}
|
||||
NetworkEvent::PeerDisconnected(peer_id) => {
|
||||
// The receiver should disconnect as a result of the invalid request.
|
||||
debug!(%peer_id, "Peer disconnected");
|
||||
// End the test.
|
||||
return;
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
.instrument(info_span!("Sender"));
|
||||
|
||||
// Build the receiver future
|
||||
let receiver_future = async {
|
||||
loop {
|
||||
if let NetworkEvent::RequestReceived { .. } = receiver.next_event().await {
|
||||
// This event should be unreachable, as the handler drops the invalid request.
|
||||
unreachable!();
|
||||
}
|
||||
}
|
||||
}
|
||||
.instrument(info_span!("Receiver"));
|
||||
|
||||
tokio::select! {
|
||||
_ = sender_future => {}
|
||||
_ = receiver_future => {}
|
||||
_ = sleep(Duration::from_secs(30)) => {
|
||||
panic!("Future timed out");
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user