2019-05-17 11:09:42 -07:00
|
|
|
#![feature(test)]
|
2022-01-17 09:37:05 -08:00
|
|
|
#![allow(clippy::integer_arithmetic)]
|
2019-05-17 11:09:42 -07:00
|
|
|
|
2019-08-21 10:23:33 -07:00
|
|
|
extern crate solana_core;
|
2019-05-17 11:09:42 -07:00
|
|
|
extern crate test;
|
|
|
|
|
2021-12-03 09:00:31 -08:00
|
|
|
use {
|
|
|
|
crossbeam_channel::unbounded,
|
|
|
|
log::*,
|
2022-06-02 07:19:01 -07:00
|
|
|
rand::{
|
|
|
|
distributions::{Distribution, Uniform},
|
|
|
|
thread_rng, Rng,
|
|
|
|
},
|
|
|
|
solana_core::{
|
|
|
|
sigverify::TransactionSigVerifier,
|
|
|
|
sigverify_stage::{SigVerifier, SigVerifyStage},
|
|
|
|
},
|
|
|
|
solana_measure::measure::Measure,
|
2022-02-18 21:32:29 -08:00
|
|
|
solana_perf::{
|
|
|
|
packet::{to_packet_batches, PacketBatch},
|
|
|
|
test_tx::test_tx,
|
|
|
|
},
|
2021-12-03 09:00:31 -08:00
|
|
|
solana_sdk::{
|
|
|
|
hash::Hash,
|
|
|
|
signature::{Keypair, Signer},
|
|
|
|
system_transaction,
|
|
|
|
timing::duration_as_ms,
|
|
|
|
},
|
2022-01-11 02:44:46 -08:00
|
|
|
std::time::{Duration, Instant},
|
2021-12-03 09:00:31 -08:00
|
|
|
test::Bencher,
|
|
|
|
};
|
2019-05-17 11:09:42 -07:00
|
|
|
|
2022-01-17 09:37:05 -08:00
|
|
|
fn run_bench_packet_discard(num_ips: usize, bencher: &mut Bencher) {
|
2021-09-29 20:41:05 -07:00
|
|
|
solana_logger::setup();
|
|
|
|
let len = 30 * 1000;
|
|
|
|
let chunk_size = 1024;
|
|
|
|
let tx = test_tx();
|
2021-12-11 06:44:15 -08:00
|
|
|
let mut batches = to_packet_batches(&vec![tx; len], chunk_size);
|
2021-09-29 20:41:05 -07:00
|
|
|
|
|
|
|
let mut total = 0;
|
|
|
|
|
2022-01-17 09:37:05 -08:00
|
|
|
let ips: Vec<_> = (0..num_ips)
|
2021-09-29 20:41:05 -07:00
|
|
|
.map(|_| {
|
|
|
|
let mut addr = [0u16; 8];
|
|
|
|
thread_rng().fill(&mut addr);
|
2022-01-02 08:13:57 -08:00
|
|
|
std::net::IpAddr::from(addr)
|
2021-09-29 20:41:05 -07:00
|
|
|
})
|
|
|
|
.collect();
|
|
|
|
|
|
|
|
for batch in batches.iter_mut() {
|
2022-05-23 13:30:15 -07:00
|
|
|
total += batch.len();
|
|
|
|
for p in batch.iter_mut() {
|
2021-09-29 20:41:05 -07:00
|
|
|
let ip_index = thread_rng().gen_range(0, ips.len());
|
2022-12-06 03:54:49 -08:00
|
|
|
p.meta_mut().addr = ips[ip_index];
|
2021-09-29 20:41:05 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
info!("total packets: {}", total);
|
|
|
|
|
|
|
|
bencher.iter(move || {
|
2022-05-24 14:01:41 -07:00
|
|
|
SigVerifyStage::discard_excess_packets(&mut batches, 10_000, |_| ());
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
let mut num_packets = 0;
|
2021-09-29 20:41:05 -07:00
|
|
|
for batch in batches.iter_mut() {
|
2022-05-23 13:30:15 -07:00
|
|
|
for p in batch.iter_mut() {
|
2022-12-06 03:54:49 -08:00
|
|
|
if !p.meta().discard() {
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
num_packets += 1;
|
|
|
|
}
|
2022-12-06 03:54:49 -08:00
|
|
|
p.meta_mut().set_discard(false);
|
2021-09-29 20:41:05 -07:00
|
|
|
}
|
|
|
|
}
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
assert_eq!(num_packets, 10_000);
|
2021-09-29 20:41:05 -07:00
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2022-01-17 09:37:05 -08:00
|
|
|
#[bench]
|
|
|
|
fn bench_packet_discard_many_senders(bencher: &mut Bencher) {
|
|
|
|
run_bench_packet_discard(1000, bencher);
|
|
|
|
}
|
|
|
|
|
|
|
|
#[bench]
|
|
|
|
fn bench_packet_discard_single_sender(bencher: &mut Bencher) {
|
|
|
|
run_bench_packet_discard(1, bencher);
|
|
|
|
}
|
|
|
|
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
#[bench]
|
|
|
|
fn bench_packet_discard_mixed_senders(bencher: &mut Bencher) {
|
|
|
|
const SIZE: usize = 30 * 1000;
|
|
|
|
const CHUNK_SIZE: usize = 1024;
|
|
|
|
fn new_rand_addr<R: Rng>(rng: &mut R) -> std::net::IpAddr {
|
|
|
|
let mut addr = [0u16; 8];
|
|
|
|
rng.fill(&mut addr);
|
|
|
|
std::net::IpAddr::from(addr)
|
|
|
|
}
|
|
|
|
let mut rng = thread_rng();
|
|
|
|
let mut batches = to_packet_batches(&vec![test_tx(); SIZE], CHUNK_SIZE);
|
|
|
|
let spam_addr = new_rand_addr(&mut rng);
|
|
|
|
for batch in batches.iter_mut() {
|
2022-05-23 13:30:15 -07:00
|
|
|
for packet in batch.iter_mut() {
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
// One spam address, ~1000 unique addresses.
|
2022-12-06 03:54:49 -08:00
|
|
|
packet.meta_mut().addr = if rng.gen_ratio(1, 30) {
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
new_rand_addr(&mut rng)
|
|
|
|
} else {
|
|
|
|
spam_addr
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
bencher.iter(move || {
|
2022-05-24 14:01:41 -07:00
|
|
|
SigVerifyStage::discard_excess_packets(&mut batches, 10_000, |_| ());
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
let mut num_packets = 0;
|
|
|
|
for batch in batches.iter_mut() {
|
2022-05-23 13:30:15 -07:00
|
|
|
for packet in batch.iter_mut() {
|
2022-12-06 03:54:49 -08:00
|
|
|
if !packet.meta().discard() {
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
num_packets += 1;
|
|
|
|
}
|
2022-12-06 03:54:49 -08:00
|
|
|
packet.meta_mut().set_discard(false);
|
improves sigverify discard_excess_packets performance (#22577)
As shown by the added benchmark, current code does worse if there is a
spam address plus a lot of unique addresses.
on current master:
test bench_packet_discard_many_senders ... bench: 1,997,960 ns/iter (+/- 103,715)
test bench_packet_discard_mixed_senders ... bench: 14,256,116 ns/iter (+/- 534,865)
test bench_packet_discard_single_sender ... bench: 1,306,809 ns/iter (+/- 61,992)
with this commit:
test bench_packet_discard_many_senders ... bench: 1,644,025 ns/iter (+/- 83,715)
test bench_packet_discard_mixed_senders ... bench: 1,089,789 ns/iter (+/- 86,324)
test bench_packet_discard_single_sender ... bench: 955,234 ns/iter (+/- 55,953)
2022-01-19 10:10:02 -08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
assert_eq!(num_packets, 10_000);
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
2022-02-16 08:18:17 -08:00
|
|
|
fn gen_batches(use_same_tx: bool) -> Vec<PacketBatch> {
|
2019-05-17 11:09:42 -07:00
|
|
|
let len = 4096;
|
|
|
|
let chunk_size = 1024;
|
2022-02-16 08:18:17 -08:00
|
|
|
if use_same_tx {
|
2019-05-17 11:09:42 -07:00
|
|
|
let tx = test_tx();
|
2021-12-11 06:44:15 -08:00
|
|
|
to_packet_batches(&vec![tx; len], chunk_size)
|
2019-05-17 11:09:42 -07:00
|
|
|
} else {
|
|
|
|
let from_keypair = Keypair::new();
|
|
|
|
let to_keypair = Keypair::new();
|
|
|
|
let txs: Vec<_> = (0..len)
|
|
|
|
.map(|_| {
|
|
|
|
let amount = thread_rng().gen();
|
2020-06-08 17:38:14 -07:00
|
|
|
system_transaction::transfer(
|
2019-05-17 11:09:42 -07:00
|
|
|
&from_keypair,
|
|
|
|
&to_keypair.pubkey(),
|
|
|
|
amount,
|
|
|
|
Hash::default(),
|
2020-06-08 17:38:14 -07:00
|
|
|
)
|
2019-05-17 11:09:42 -07:00
|
|
|
})
|
|
|
|
.collect();
|
2021-12-11 06:44:15 -08:00
|
|
|
to_packet_batches(&txs, chunk_size)
|
2022-02-16 08:18:17 -08:00
|
|
|
}
|
|
|
|
}
|
2019-05-17 11:09:42 -07:00
|
|
|
|
2022-02-16 08:18:17 -08:00
|
|
|
#[bench]
|
|
|
|
fn bench_sigverify_stage(bencher: &mut Bencher) {
|
|
|
|
solana_logger::setup();
|
|
|
|
trace!("start");
|
|
|
|
let (packet_s, packet_r) = unbounded();
|
|
|
|
let (verified_s, verified_r) = unbounded();
|
2022-05-24 14:01:41 -07:00
|
|
|
let verifier = TransactionSigVerifier::new(verified_s);
|
|
|
|
let stage = SigVerifyStage::new(packet_r, verifier, "bench");
|
2022-02-16 08:18:17 -08:00
|
|
|
|
|
|
|
let use_same_tx = true;
|
2019-05-17 11:09:42 -07:00
|
|
|
bencher.iter(move || {
|
2022-02-16 08:18:17 -08:00
|
|
|
let now = Instant::now();
|
|
|
|
let mut batches = gen_batches(use_same_tx);
|
|
|
|
trace!(
|
|
|
|
"starting... generation took: {} ms batches: {}",
|
|
|
|
duration_as_ms(&now.elapsed()),
|
|
|
|
batches.len()
|
|
|
|
);
|
|
|
|
|
2019-05-17 11:09:42 -07:00
|
|
|
let mut sent_len = 0;
|
|
|
|
for _ in 0..batches.len() {
|
|
|
|
if let Some(batch) = batches.pop() {
|
2022-05-23 13:30:15 -07:00
|
|
|
sent_len += batch.len();
|
2021-12-16 06:47:55 -08:00
|
|
|
packet_s.send(vec![batch]).unwrap();
|
2019-05-17 11:09:42 -07:00
|
|
|
}
|
|
|
|
}
|
|
|
|
let mut received = 0;
|
2019-05-22 13:00:03 -07:00
|
|
|
trace!("sent: {}", sent_len);
|
2019-05-17 11:09:42 -07:00
|
|
|
loop {
|
2022-05-24 14:01:41 -07:00
|
|
|
if let Ok((mut verifieds, _)) = verified_r.recv_timeout(Duration::from_millis(10)) {
|
2019-05-17 11:09:42 -07:00
|
|
|
while let Some(v) = verifieds.pop() {
|
2022-05-23 13:30:15 -07:00
|
|
|
received += v.len();
|
2019-11-01 14:23:03 -07:00
|
|
|
batches.push(v);
|
2019-05-17 11:09:42 -07:00
|
|
|
}
|
2022-02-16 08:18:17 -08:00
|
|
|
if use_same_tx || received >= sent_len {
|
2019-05-17 11:09:42 -07:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2019-05-22 13:00:03 -07:00
|
|
|
trace!("received: {}", received);
|
2019-05-17 11:09:42 -07:00
|
|
|
});
|
|
|
|
stage.join().unwrap();
|
|
|
|
}
|
2022-06-02 07:19:01 -07:00
|
|
|
|
|
|
|
fn prepare_batches(discard_factor: i32) -> (Vec<PacketBatch>, usize) {
|
|
|
|
let len = 10_000; // max batch size
|
|
|
|
let chunk_size = 1024;
|
|
|
|
|
|
|
|
let from_keypair = Keypair::new();
|
|
|
|
let to_keypair = Keypair::new();
|
|
|
|
|
|
|
|
let txs: Vec<_> = (0..len)
|
|
|
|
.map(|_| {
|
|
|
|
let amount = thread_rng().gen();
|
|
|
|
system_transaction::transfer(
|
|
|
|
&from_keypair,
|
|
|
|
&to_keypair.pubkey(),
|
|
|
|
amount,
|
|
|
|
Hash::default(),
|
|
|
|
)
|
|
|
|
})
|
|
|
|
.collect();
|
|
|
|
let mut batches = to_packet_batches(&txs, chunk_size);
|
|
|
|
|
|
|
|
let mut rng = rand::thread_rng();
|
|
|
|
let die = Uniform::<i32>::from(1..100);
|
|
|
|
|
|
|
|
let mut c = 0;
|
|
|
|
batches.iter_mut().for_each(|batch| {
|
|
|
|
batch.iter_mut().for_each(|p| {
|
|
|
|
let throw = die.sample(&mut rng);
|
|
|
|
if throw < discard_factor {
|
2022-12-06 03:54:49 -08:00
|
|
|
p.meta_mut().set_discard(true);
|
2022-06-02 07:19:01 -07:00
|
|
|
c += 1;
|
|
|
|
}
|
|
|
|
})
|
|
|
|
});
|
|
|
|
(batches, len - c)
|
|
|
|
}
|
|
|
|
|
|
|
|
fn bench_shrink_sigverify_stage_core(bencher: &mut Bencher, discard_factor: i32) {
|
|
|
|
let (batches0, num_valid_packets) = prepare_batches(discard_factor);
|
|
|
|
let (_verified_s, _verified_r) = unbounded();
|
|
|
|
let verifier = TransactionSigVerifier::new(_verified_s);
|
|
|
|
|
|
|
|
let mut c = 0;
|
|
|
|
let mut total_shrink_time = 0;
|
|
|
|
let mut total_verify_time = 0;
|
|
|
|
|
|
|
|
bencher.iter(|| {
|
|
|
|
let mut batches = batches0.clone();
|
|
|
|
let (pre_shrink_time_us, _pre_shrink_total) =
|
|
|
|
SigVerifyStage::maybe_shrink_batches(&mut batches);
|
|
|
|
|
|
|
|
let mut verify_time = Measure::start("sigverify_batch_time");
|
|
|
|
let _batches = verifier.verify_batches(batches, num_valid_packets);
|
|
|
|
verify_time.stop();
|
|
|
|
|
|
|
|
c += 1;
|
|
|
|
total_shrink_time += pre_shrink_time_us;
|
|
|
|
total_verify_time += verify_time.as_us();
|
|
|
|
});
|
|
|
|
|
|
|
|
error!(
|
|
|
|
"bsv, {}, {}, {}",
|
|
|
|
discard_factor,
|
|
|
|
(total_shrink_time as f64) / (c as f64),
|
|
|
|
(total_verify_time as f64) / (c as f64),
|
|
|
|
);
|
|
|
|
}
|
|
|
|
|
|
|
|
macro_rules! GEN_SHRINK_SIGVERIFY_BENCH {
|
|
|
|
($i:ident, $n:literal) => {
|
|
|
|
#[bench]
|
|
|
|
fn $i(bencher: &mut Bencher) {
|
|
|
|
bench_shrink_sigverify_stage_core(bencher, $n);
|
|
|
|
}
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_0, 0);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_10, 10);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_20, 20);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_30, 30);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_40, 40);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_50, 50);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_60, 60);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_70, 70);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_80, 80);
|
|
|
|
GEN_SHRINK_SIGVERIFY_BENCH!(bsv_90, 90);
|