Skip to content

Commit 0883a78

Browse files
authored
perf: skip trivial 1-raw-sig + 0-children case during aggregation (#1469)
skip trivial 1-raw-sig + 0-children case during aggregation
1 parent 2dc05c7 commit 0883a78

2 files changed

Lines changed: 79 additions & 41 deletions

File tree

Cargo.toml

Lines changed: 1 addition & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -57,14 +57,7 @@ exclude = ["book/cli"]
5757
[workspace.package]
5858
authors = ["https://github.com/ReamLabs/ream/graphs/contributors"]
5959
edition = "2024"
60-
keywords = [
61-
"ethereum",
62-
"beam-chain",
63-
"blockchain",
64-
"consensus",
65-
"protocol",
66-
"ream",
67-
]
60+
keywords = ["ethereum", "beam-chain", "blockchain", "consensus", "protocol", "ream"]
6861
license = "MIT"
6962
readme = "README.md"
7063
repository = "https://github.com/ReamLabs/ream"

crates/common/fork_choice/lean/src/store.rs

Lines changed: 78 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -655,6 +655,10 @@ impl Store {
655655
if raw_entries.is_empty() && child_proofs.len() < 2 {
656656
continue;
657657
}
658+
659+
if child_proofs.is_empty() && raw_entries.len() <= 1 {
660+
continue;
661+
}
658662
} else if raw_entries.is_empty() {
659663
continue;
660664
}
@@ -3994,10 +3998,57 @@ mod tests {
39943998
assert!(is_empty);
39953999
}
39964000

4001+
#[tokio::test]
4002+
pub async fn test_aggregate_skips_single_gossip_sig_with_no_children() {
4003+
let mut store: Store = sample_store_as_store(2).await;
4004+
let attesting_validators: Vec<u64> = vec![1];
4005+
let key_pairs = install_validator_keys(&store, &attesting_validators).await;
4006+
let slot = 1;
4007+
4008+
let attestation_data = store.produce_attestation_data(slot).await.unwrap();
4009+
let data_root = attestation_data.tree_hash_root();
4010+
let signature = key_pairs
4011+
.get(&1)
4012+
.unwrap()
4013+
.1
4014+
.sign(&data_root.0, slot as u32)
4015+
.unwrap();
4016+
4017+
{
4018+
let db = store.store.lock().await;
4019+
db.attestation_data_by_root_provider()
4020+
.insert(data_root, attestation_data)
4021+
.unwrap();
4022+
db.attestation_signatures_provider()
4023+
.insert(SignatureKey::from_parts(1, data_root), signature)
4024+
.unwrap();
4025+
}
4026+
4027+
store.aggregate().await.unwrap();
4028+
4029+
let db = store.store.lock().await;
4030+
4031+
// No aggregate was produced for the lone sig.
4032+
let no_proof = db
4033+
.latest_new_aggregated_payloads_provider()
4034+
.get(SignatureKey::from_parts(1, data_root))
4035+
.unwrap()
4036+
.is_none();
4037+
assert!(no_proof);
4038+
4039+
// The unconsumed gossip sig stays put for a later, non-trivial pass.
4040+
let sig_survives = db
4041+
.attestation_signatures_provider()
4042+
.get(SignatureKey::from_parts(1, data_root))
4043+
.unwrap()
4044+
.is_some();
4045+
assert!(sig_survives);
4046+
}
4047+
39974048
#[tokio::test]
39984049
pub async fn test_multiple_attestation_data_grouped_separately() {
39994050
let mut store: Store = sample_store_as_store(4).await;
4000-
let attesting_validators: Vec<u64> = vec![1, 2];
4051+
let attesting_validators: Vec<u64> = vec![0, 1, 2, 3];
40014052
let key_pairs = install_validator_keys(&store, &attesting_validators).await;
40024053
let slot = 1;
40034054

@@ -4014,18 +4065,14 @@ mod tests {
40144065
let data_root_1 = attestation_data_1.tree_hash_root();
40154066
let data_root_2 = attestation_data_2.tree_hash_root();
40164067

4017-
let sig_1 = key_pairs
4018-
.get(&1)
4019-
.unwrap()
4020-
.1
4021-
.sign(&data_root_1.0, attestation_data_1.slot as u32)
4022-
.unwrap();
4023-
let sig_2 = key_pairs
4024-
.get(&2)
4025-
.unwrap()
4026-
.1
4027-
.sign(&data_root_2.0, attestation_data_2.slot as u32)
4028-
.unwrap();
4068+
let sign = |validator_id: u64, data_root: &B256| {
4069+
key_pairs
4070+
.get(&validator_id)
4071+
.unwrap()
4072+
.1
4073+
.sign(&data_root.0, slot as u32)
4074+
.unwrap()
4075+
};
40294076

40304077
{
40314078
let db = store.store.lock().await;
@@ -4039,18 +4086,22 @@ mod tests {
40394086
.insert(data_root_2, attestation_data_2)
40404087
.unwrap();
40414088

4042-
gossip_signatures
4043-
.insert(
4044-
SignatureKey::from_parts(attesting_validators[0], data_root_1),
4045-
sig_1,
4046-
)
4047-
.unwrap();
4048-
gossip_signatures
4049-
.insert(
4050-
SignatureKey::from_parts(attesting_validators[1], data_root_2),
4051-
sig_2,
4052-
)
4053-
.unwrap();
4089+
for &validator_id in &[1u64, 3] {
4090+
gossip_signatures
4091+
.insert(
4092+
SignatureKey::from_parts(validator_id, data_root_1),
4093+
sign(validator_id, &data_root_1),
4094+
)
4095+
.unwrap();
4096+
}
4097+
for &validator_id in &[2u64, 0] {
4098+
gossip_signatures
4099+
.insert(
4100+
SignatureKey::from_parts(validator_id, data_root_2),
4101+
sign(validator_id, &data_root_2),
4102+
)
4103+
.unwrap();
4104+
}
40544105
}
40554106

40564107
store.aggregate().await.unwrap();
@@ -4063,19 +4114,13 @@ mod tests {
40634114

40644115
assert!(
40654116
latest_new
4066-
.get(SignatureKey::from_parts(
4067-
attesting_validators[0],
4068-
data_root_1
4069-
))
4117+
.get(SignatureKey::from_parts(1, data_root_1))
40704118
.unwrap()
40714119
.is_some()
40724120
);
40734121
assert!(
40744122
latest_new
4075-
.get(SignatureKey::from_parts(
4076-
attesting_validators[1],
4077-
data_root_2
4078-
))
4123+
.get(SignatureKey::from_parts(2, data_root_2))
40794124
.unwrap()
40804125
.is_some()
40814126
);

0 commit comments

Comments
 (0)