Merge commit 'd803bfe2b1fe7f5e219e50ac20d6801a0a58ac75' as 'vendor/ruvector'
This commit is contained in:
703
vendor/ruvector/crates/ruQu/benches/throughput_bench.rs
vendored
Normal file
703
vendor/ruvector/crates/ruQu/benches/throughput_bench.rs
vendored
Normal file
@@ -0,0 +1,703 @@
|
||||
//! Throughput benchmarks for ruQu Coherence Gate.
|
||||
//!
|
||||
//! Performance Targets:
|
||||
//! - Syndrome ingestion rate: **1M rounds/sec**
|
||||
//! - Gate decisions per second: **250K decisions/sec**
|
||||
//! - Permit token generation rate: **100K tokens/sec**
|
||||
//!
|
||||
//! Run with: `cargo bench -p ruqu --bench throughput_bench`
|
||||
|
||||
use criterion::{black_box, criterion_group, criterion_main, BenchmarkId, Criterion, Throughput};
|
||||
|
||||
use ruqu::filters::{FilterConfig, FilterPipeline, SystemState};
|
||||
use ruqu::syndrome::{DetectorBitmap, SyndromeBuffer, SyndromeDelta, SyndromeRound};
|
||||
use ruqu::tile::{
|
||||
GateDecision, GateThresholds, PatchGraph, PermitToken, ReceiptLog,
|
||||
SyndromeDelta as TileSyndromeDelta, TileReport, TileZero, WorkerTile,
|
||||
};
|
||||
|
||||
// ============================================================================
|
||||
// HELPER FUNCTIONS
|
||||
// ============================================================================
|
||||
|
||||
/// Create a syndrome round with specified firing pattern
|
||||
fn create_syndrome_round(round_id: u64, detector_count: usize, firing_rate: f64) -> SyndromeRound {
|
||||
let mut detectors = DetectorBitmap::new(detector_count);
|
||||
let num_fired = ((detector_count as f64) * firing_rate) as usize;
|
||||
for i in 0..num_fired {
|
||||
detectors.set(i * (detector_count / num_fired.max(1)), true);
|
||||
}
|
||||
SyndromeRound::new(round_id, round_id, round_id * 1000, detectors, 0)
|
||||
}
|
||||
|
||||
/// Create a worker tile with pre-populated graph
|
||||
fn create_worker_tile(tile_id: u8, num_vertices: u16, num_edges: u16) -> WorkerTile {
|
||||
let mut tile = WorkerTile::new(tile_id);
|
||||
for i in 0..num_vertices.min(255) {
|
||||
tile.patch_graph.ensure_vertex(i);
|
||||
}
|
||||
let mut edges_added = 0u16;
|
||||
'outer: for i in 0..num_vertices.saturating_sub(1) {
|
||||
for j in (i + 1)..num_vertices.min(i + 4) {
|
||||
if edges_added >= num_edges {
|
||||
break 'outer;
|
||||
}
|
||||
if tile.patch_graph.add_edge(i, j, 1000).is_some() {
|
||||
edges_added += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
tile.patch_graph.recompute_components();
|
||||
tile
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// SYNDROME INGESTION THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark syndrome ingestion rate (target: 1M rounds/sec)
|
||||
fn bench_syndrome_ingestion(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("syndrome_ingestion");
|
||||
|
||||
// Single round ingestion
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_round", |b| {
|
||||
let mut buffer = SyndromeBuffer::new(4096);
|
||||
let mut round_id = 0u64;
|
||||
|
||||
b.iter(|| {
|
||||
let round = create_syndrome_round(round_id, 64, 0.1);
|
||||
buffer.push(round);
|
||||
round_id += 1;
|
||||
black_box(&buffer);
|
||||
});
|
||||
});
|
||||
|
||||
// Batch ingestion (1000 rounds)
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("batch_1000_rounds", |b| {
|
||||
let mut buffer = SyndromeBuffer::new(4096);
|
||||
let mut round_id = 0u64;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let round = create_syndrome_round(round_id, 64, 0.1);
|
||||
buffer.push(round);
|
||||
round_id += 1;
|
||||
}
|
||||
black_box(&buffer);
|
||||
});
|
||||
});
|
||||
|
||||
// Large batch ingestion (10000 rounds)
|
||||
group.throughput(Throughput::Elements(10_000));
|
||||
group.bench_function("batch_10000_rounds", |b| {
|
||||
let mut buffer = SyndromeBuffer::new(16384);
|
||||
let mut round_id = 0u64;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..10_000 {
|
||||
let round = create_syndrome_round(round_id, 64, 0.1);
|
||||
buffer.push(round);
|
||||
round_id += 1;
|
||||
}
|
||||
black_box(&buffer);
|
||||
});
|
||||
});
|
||||
|
||||
// Varying detector counts
|
||||
for detector_count in [64, 256, 512, 1024].iter() {
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_with_input(
|
||||
BenchmarkId::new("batch_1000_detectors", detector_count),
|
||||
detector_count,
|
||||
|b, &count| {
|
||||
let mut buffer = SyndromeBuffer::new(4096);
|
||||
let mut round_id = 0u64;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let round = create_syndrome_round(round_id, count, 0.1);
|
||||
buffer.push(round);
|
||||
round_id += 1;
|
||||
}
|
||||
black_box(&buffer);
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
// Varying firing rates
|
||||
for firing_rate in [0.01, 0.05, 0.1, 0.25].iter() {
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_with_input(
|
||||
BenchmarkId::new(
|
||||
"batch_1000_firing_rate",
|
||||
format!("{:.0}pct", firing_rate * 100.0),
|
||||
),
|
||||
firing_rate,
|
||||
|b, &rate| {
|
||||
let mut buffer = SyndromeBuffer::new(4096);
|
||||
let mut round_id = 0u64;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let round = create_syndrome_round(round_id, 256, rate);
|
||||
buffer.push(round);
|
||||
round_id += 1;
|
||||
}
|
||||
black_box(&buffer);
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// GATE DECISION THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark gate decisions per second
|
||||
fn bench_gate_decision_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("gate_decisions");
|
||||
|
||||
// Single decision
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_decision", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
let thresholds = GateThresholds::default();
|
||||
let mut tilezero = TileZero::new(thresholds);
|
||||
|
||||
b.iter(|| {
|
||||
let delta = TileSyndromeDelta::new(0, 1, 100);
|
||||
let report = tile.tick(&delta);
|
||||
let reports = vec![report; 10];
|
||||
let decision = tilezero.merge_reports(reports);
|
||||
black_box(decision)
|
||||
});
|
||||
});
|
||||
|
||||
// Batch decisions (100)
|
||||
group.throughput(Throughput::Elements(100));
|
||||
group.bench_function("batch_100_decisions", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
let thresholds = GateThresholds::default();
|
||||
let mut tilezero = TileZero::new(thresholds);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..100 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, i as u16);
|
||||
let report = tile.tick(&delta);
|
||||
let reports = vec![report; 10];
|
||||
let decision = tilezero.merge_reports(reports);
|
||||
black_box(decision);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Batch decisions (1000)
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("batch_1000_decisions", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
let thresholds = GateThresholds::default();
|
||||
let mut tilezero = TileZero::new(thresholds);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..1000 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, (i % 256) as u16);
|
||||
let report = tile.tick(&delta);
|
||||
let reports = vec![report; 10];
|
||||
let decision = tilezero.merge_reports(reports);
|
||||
black_box(decision);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Decisions with varying tile counts
|
||||
for tile_count in [10, 50, 100, 255].iter() {
|
||||
group.throughput(Throughput::Elements(100));
|
||||
group.bench_with_input(
|
||||
BenchmarkId::new("batch_100_tile_count", tile_count),
|
||||
tile_count,
|
||||
|b, &count| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
let thresholds = GateThresholds::default();
|
||||
let mut tilezero = TileZero::new(thresholds);
|
||||
|
||||
let base_reports: Vec<TileReport> = (1..=count)
|
||||
.map(|i| {
|
||||
let mut report = TileReport::new(i as u8);
|
||||
report.local_cut = 10.0;
|
||||
report.shift_score = 0.1;
|
||||
report.e_value = 200.0;
|
||||
report
|
||||
})
|
||||
.collect();
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..100 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, 100);
|
||||
let _ = tile.tick(&delta);
|
||||
let decision = tilezero.merge_reports(base_reports.clone());
|
||||
black_box(decision);
|
||||
}
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// PERMIT TOKEN GENERATION THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark permit token generation rate
|
||||
fn bench_permit_token_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("permit_tokens");
|
||||
|
||||
// Single token
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_token", |b| {
|
||||
let thresholds = GateThresholds::default();
|
||||
let tilezero = TileZero::new(thresholds);
|
||||
let decision = GateDecision::Permit;
|
||||
|
||||
b.iter(|| {
|
||||
let token = tilezero.issue_permit(&decision);
|
||||
black_box(token)
|
||||
});
|
||||
});
|
||||
|
||||
// Batch tokens (1000)
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("batch_1000_tokens", |b| {
|
||||
let thresholds = GateThresholds::default();
|
||||
let tilezero = TileZero::new(thresholds);
|
||||
let decision = GateDecision::Permit;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let token = tilezero.issue_permit(&decision);
|
||||
black_box(&token);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Token validation throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("validate_1000_tokens", |b| {
|
||||
let thresholds = GateThresholds::default();
|
||||
let tilezero = TileZero::new(thresholds);
|
||||
let token = tilezero.issue_permit(&GateDecision::Permit);
|
||||
let now_ns = token.timestamp + 1000;
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let valid = token.is_valid(now_ns);
|
||||
black_box(valid);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// RECEIPT LOG THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark receipt log operations
|
||||
fn bench_receipt_log_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("receipt_log");
|
||||
|
||||
// Append throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("append_1000", |b| {
|
||||
let mut log = ReceiptLog::new();
|
||||
let witness_hash = [0u8; 32];
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..1000 {
|
||||
log.append(GateDecision::Permit, i, i * 1000, witness_hash);
|
||||
}
|
||||
black_box(&log);
|
||||
});
|
||||
});
|
||||
|
||||
// Lookup throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("lookup_1000", |b| {
|
||||
let mut log = ReceiptLog::new();
|
||||
let witness_hash = [0u8; 32];
|
||||
for i in 0..10000 {
|
||||
log.append(GateDecision::Permit, i, i * 1000, witness_hash);
|
||||
}
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..1000 {
|
||||
let entry = log.get(i * 10);
|
||||
black_box(entry);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// WORKER TILE THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark worker tile tick throughput
|
||||
fn bench_worker_tile_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("worker_tile");
|
||||
|
||||
// Single tick
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_tick", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
|
||||
b.iter(|| {
|
||||
let delta = TileSyndromeDelta::new(0, 1, 100);
|
||||
let report = tile.tick(&delta);
|
||||
black_box(report)
|
||||
});
|
||||
});
|
||||
|
||||
// Batch ticks (1000)
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("batch_1000_ticks", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..1000 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, (i % 256) as u16);
|
||||
let report = tile.tick(&delta);
|
||||
black_box(&report);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Sustained throughput (10000 ticks)
|
||||
group.throughput(Throughput::Elements(10_000));
|
||||
group.bench_function("sustained_10000_ticks", |b| {
|
||||
let mut tile = create_worker_tile(1, 64, 128);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..10_000 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, (i % 256) as u16);
|
||||
let report = tile.tick(&delta);
|
||||
black_box(&report);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Varying graph sizes
|
||||
for (vertices, edges) in [(32, 64), (64, 128), (128, 256), (200, 400)].iter() {
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_with_input(
|
||||
BenchmarkId::new("batch_1000_graph", format!("v{}e{}", vertices, edges)),
|
||||
&(*vertices, *edges),
|
||||
|b, &(v, e)| {
|
||||
let mut tile = create_worker_tile(1, v, e);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..1000 {
|
||||
let delta = TileSyndromeDelta::new(0, 1, (i % 256) as u16);
|
||||
let report = tile.tick(&delta);
|
||||
black_box(&report);
|
||||
}
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// FILTER PIPELINE THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark filter pipeline throughput
|
||||
fn bench_filter_pipeline_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("filter_pipeline");
|
||||
|
||||
// Create a pre-warmed pipeline
|
||||
let create_pipeline = || {
|
||||
let config = FilterConfig::default();
|
||||
let mut pipeline = FilterPipeline::new(config);
|
||||
|
||||
for i in 0..50u64 {
|
||||
let _ = pipeline.structural_mut().insert_edge(i, i + 1, 1.0);
|
||||
}
|
||||
pipeline.structural_mut().build();
|
||||
|
||||
for region in 0..10 {
|
||||
for _ in 0..50 {
|
||||
pipeline.shift_mut().update(region, 0.5);
|
||||
}
|
||||
}
|
||||
|
||||
for _ in 0..20 {
|
||||
pipeline.evidence_mut().update(1.5);
|
||||
}
|
||||
|
||||
pipeline
|
||||
};
|
||||
|
||||
// Single evaluation
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_evaluation", |b| {
|
||||
let pipeline = create_pipeline();
|
||||
let state = SystemState::new(100);
|
||||
|
||||
b.iter(|| {
|
||||
let result = pipeline.evaluate(&state);
|
||||
black_box(result)
|
||||
});
|
||||
});
|
||||
|
||||
// Batch evaluations (1000)
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("batch_1000_evaluations", |b| {
|
||||
let pipeline = create_pipeline();
|
||||
let state = SystemState::new(100);
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let result = pipeline.evaluate(&state);
|
||||
black_box(&result);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// SYNDROME DELTA COMPUTATION THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark syndrome delta computation throughput
|
||||
fn bench_syndrome_delta_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("syndrome_delta");
|
||||
|
||||
// Create test rounds
|
||||
let create_rounds = |count: usize| -> Vec<SyndromeRound> {
|
||||
(0..count)
|
||||
.map(|i| create_syndrome_round(i as u64, 256, 0.1))
|
||||
.collect()
|
||||
};
|
||||
|
||||
// Single delta computation
|
||||
group.throughput(Throughput::Elements(1));
|
||||
group.bench_function("single_delta", |b| {
|
||||
let round1 = create_syndrome_round(0, 256, 0.1);
|
||||
let round2 = create_syndrome_round(1, 256, 0.1);
|
||||
|
||||
b.iter(|| {
|
||||
let delta = SyndromeDelta::compute(&round1, &round2);
|
||||
black_box(delta)
|
||||
});
|
||||
});
|
||||
|
||||
// Batch delta computation (1000)
|
||||
group.throughput(Throughput::Elements(999));
|
||||
group.bench_function("batch_1000_deltas", |b| {
|
||||
let rounds = create_rounds(1000);
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..999 {
|
||||
let delta = SyndromeDelta::compute(&rounds[i], &rounds[i + 1]);
|
||||
black_box(&delta);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Varying detector counts
|
||||
for detector_count in [64, 256, 512, 1024].iter() {
|
||||
group.throughput(Throughput::Elements(999));
|
||||
group.bench_with_input(
|
||||
BenchmarkId::new("batch_1000_detectors", detector_count),
|
||||
detector_count,
|
||||
|b, &count| {
|
||||
let rounds: Vec<SyndromeRound> = (0..1000)
|
||||
.map(|i| create_syndrome_round(i as u64, count, 0.1))
|
||||
.collect();
|
||||
|
||||
b.iter(|| {
|
||||
for i in 0..999 {
|
||||
let delta = SyndromeDelta::compute(&rounds[i], &rounds[i + 1]);
|
||||
black_box(&delta);
|
||||
}
|
||||
});
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// PATCH GRAPH THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark patch graph operation throughput
|
||||
fn bench_patch_graph_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("patch_graph_throughput");
|
||||
|
||||
// Edge insertion throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("insert_1000_edges", |b| {
|
||||
b.iter_batched(
|
||||
PatchGraph::new,
|
||||
|mut graph| {
|
||||
for i in 0..1000u16 {
|
||||
let v1 = i % 256;
|
||||
let v2 = (i + 1) % 256;
|
||||
if v1 != v2 {
|
||||
let _ = graph.add_edge(v1, v2, 1000);
|
||||
}
|
||||
}
|
||||
black_box(graph.num_edges)
|
||||
},
|
||||
criterion::BatchSize::SmallInput,
|
||||
);
|
||||
});
|
||||
|
||||
// Delta application throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("apply_1000_deltas", |b| {
|
||||
b.iter_batched(
|
||||
|| {
|
||||
let mut graph = PatchGraph::new();
|
||||
for i in 0..100u16 {
|
||||
let _ = graph.add_edge(i, (i + 1) % 100, 1000);
|
||||
}
|
||||
graph
|
||||
},
|
||||
|mut graph| {
|
||||
for i in 0..1000u16 {
|
||||
let delta = TileSyndromeDelta::new(i % 100, (i + 1) % 100, 100);
|
||||
graph.apply_delta(&delta);
|
||||
}
|
||||
black_box(graph.num_edges)
|
||||
},
|
||||
criterion::BatchSize::SmallInput,
|
||||
);
|
||||
});
|
||||
|
||||
// Component recomputation throughput
|
||||
group.throughput(Throughput::Elements(100));
|
||||
group.bench_function("recompute_100_times", |b| {
|
||||
b.iter_batched(
|
||||
|| {
|
||||
let mut graph = PatchGraph::new();
|
||||
for i in 0..200u16 {
|
||||
let _ = graph.add_edge(i, (i + 1) % 200, 1000);
|
||||
}
|
||||
graph
|
||||
},
|
||||
|mut graph| {
|
||||
let mut count = 0u16;
|
||||
for _ in 0..100 {
|
||||
graph.status |= PatchGraph::STATUS_DIRTY;
|
||||
count = graph.recompute_components();
|
||||
}
|
||||
black_box(count)
|
||||
},
|
||||
criterion::BatchSize::SmallInput,
|
||||
);
|
||||
});
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// DETECTOR BITMAP THROUGHPUT
|
||||
// ============================================================================
|
||||
|
||||
/// Benchmark detector bitmap throughput
|
||||
fn bench_bitmap_throughput(c: &mut Criterion) {
|
||||
let mut group = c.benchmark_group("bitmap_throughput");
|
||||
|
||||
// XOR throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("xor_1000", |b| {
|
||||
let mut a = DetectorBitmap::new(1024);
|
||||
let mut bb = DetectorBitmap::new(1024);
|
||||
for i in (0..512).step_by(2) {
|
||||
a.set(i, true);
|
||||
}
|
||||
for i in (256..768).step_by(2) {
|
||||
bb.set(i, true);
|
||||
}
|
||||
|
||||
b.iter(|| {
|
||||
for _ in 0..1000 {
|
||||
let result = a.xor(&bb);
|
||||
black_box(&result);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
// Popcount throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("popcount_1000", |b| {
|
||||
let mut bitmap = DetectorBitmap::new(1024);
|
||||
for i in (0..512).step_by(2) {
|
||||
bitmap.set(i, true);
|
||||
}
|
||||
|
||||
b.iter(|| {
|
||||
let mut total = 0usize;
|
||||
for _ in 0..1000 {
|
||||
total += bitmap.popcount();
|
||||
}
|
||||
black_box(total)
|
||||
});
|
||||
});
|
||||
|
||||
// Iterator throughput
|
||||
group.throughput(Throughput::Elements(1000));
|
||||
group.bench_function("iter_fired_1000", |b| {
|
||||
let mut bitmap = DetectorBitmap::new(1024);
|
||||
for i in 0..100 {
|
||||
bitmap.set(i * 10, true);
|
||||
}
|
||||
|
||||
b.iter(|| {
|
||||
let mut total = 0usize;
|
||||
for _ in 0..1000 {
|
||||
total += bitmap.iter_fired().count();
|
||||
}
|
||||
black_box(total)
|
||||
});
|
||||
});
|
||||
|
||||
group.finish();
|
||||
}
|
||||
|
||||
// ============================================================================
|
||||
// CRITERION GROUPS
|
||||
// ============================================================================
|
||||
|
||||
criterion_group!(
|
||||
throughput_benches,
|
||||
bench_syndrome_ingestion,
|
||||
bench_gate_decision_throughput,
|
||||
bench_permit_token_throughput,
|
||||
bench_receipt_log_throughput,
|
||||
bench_worker_tile_throughput,
|
||||
bench_filter_pipeline_throughput,
|
||||
bench_syndrome_delta_throughput,
|
||||
bench_patch_graph_throughput,
|
||||
bench_bitmap_throughput,
|
||||
);
|
||||
|
||||
criterion_main!(throughput_benches);
|
||||
Reference in New Issue
Block a user