use criterion::{Criterion, criterion_group, criterion_main};
#[cfg(feature = "parallel")]
use srcmap_codec::encode_parallel;
use srcmap_codec::{Segment, decode, encode};
use std::hint::black_box;
fn make_synthetic_mappings() -> String {
let line = std::iter::repeat_n("AAAA", 50).collect::<Vec<_>>().join(",");
std::iter::repeat_n(line.as_str(), 1000).collect::<Vec<_>>().join(";")
}
fn make_realistic_mappings() -> String {
let mut mappings = Vec::with_capacity(500);
let mut src: i64 = 0;
let mut src_line: i64 = 0;
let mut src_col: i64 = 0;
let mut name: i64 = 0;
for line_idx in 0..500_i64 {
let segments_per_line = 10 + (line_idx % 40) as usize;
let mut line = Vec::with_capacity(segments_per_line);
let mut gen_col: i64 = 0;
for seg in 0..segments_per_line {
let seg = seg as i64;
gen_col += 2 + (seg * 3) % 28;
if seg % 15 == 0 {
src += 1;
}
src_line += if seg % 7 == 0 { -3 } else { 1 };
src_line = src_line.max(0);
src_col += (seg * 7 + 3) % 50 - 10;
src_col = src_col.max(0);
if seg % 5 == 0 {
name += 1;
line.push(Segment::five(gen_col, src, src_line, src_col, name));
} else {
line.push(Segment::four(gen_col, src, src_line, src_col));
}
}
mappings.push(line);
}
encode(&mappings)
}
fn bench_decode(c: &mut Criterion) {
let small = "AAAA;AACA,GAAG;AACA,IAAI,EAAE";
let synthetic = make_synthetic_mappings();
let realistic = make_realistic_mappings();
c.bench_function("decode small", |b| {
b.iter(|| decode(black_box(small)).unwrap());
});
c.bench_function("decode synthetic (50K segments)", |b| {
b.iter(|| decode(black_box(&synthetic)).unwrap());
});
c.bench_function("decode realistic (500 lines)", |b| {
b.iter(|| decode(black_box(&realistic)).unwrap());
});
}
#[cfg(feature = "parallel")]
fn make_large_realistic_mappings() -> srcmap_codec::SourceMapMappings {
let mut mappings = Vec::with_capacity(5000);
let mut src: i64 = 0;
let mut src_line: i64 = 0;
let mut src_col: i64 = 0;
let mut name: i64 = 0;
for line_idx in 0..5000_i64 {
let segments_per_line = 10 + (line_idx % 40) as usize;
let mut line = Vec::with_capacity(segments_per_line);
let mut gen_col: i64 = 0;
for seg in 0..segments_per_line {
let seg = seg as i64;
gen_col += 2 + (seg * 3) % 28;
if seg % 15 == 0 {
src += 1;
}
src_line += if seg % 7 == 0 { -3 } else { 1 };
src_line = src_line.max(0);
src_col += (seg * 7 + 3) % 50 - 10;
src_col = src_col.max(0);
if seg % 5 == 0 {
name += 1;
line.push(Segment::five(gen_col, src, src_line, src_col, name));
} else {
line.push(Segment::four(gen_col, src, src_line, src_col));
}
}
mappings.push(line);
}
mappings
}
fn bench_encode(c: &mut Criterion) {
let synthetic = make_synthetic_mappings();
let decoded_synthetic = decode(&synthetic).unwrap();
let realistic = make_realistic_mappings();
let decoded_realistic = decode(&realistic).unwrap();
c.bench_function("encode synthetic (50K segments)", |b| {
b.iter(|| encode(black_box(&decoded_synthetic)));
});
c.bench_function("encode realistic (500 lines)", |b| {
b.iter(|| encode(black_box(&decoded_realistic)));
});
#[cfg(feature = "parallel")]
{
let large = make_large_realistic_mappings();
c.bench_function("encode sequential (5K lines)", |b| {
b.iter(|| encode(black_box(&large)));
});
c.bench_function("encode parallel (5K lines)", |b| {
b.iter(|| encode_parallel(black_box(&large)));
});
let very_large = {
let mut mappings = Vec::with_capacity(50000);
let mut src: i64 = 0;
let mut src_line: i64 = 0;
let mut src_col: i64 = 0;
let mut name: i64 = 0;
for line_idx in 0..50000_i64 {
let segments_per_line = 5 + (line_idx % 20) as usize;
let mut line = Vec::with_capacity(segments_per_line);
let mut gen_col: i64 = 0;
for seg in 0..segments_per_line {
let seg = seg as i64;
gen_col += 2 + (seg * 3) % 28;
if seg % 15 == 0 {
src += 1;
}
src_line += if seg % 7 == 0 { -3 } else { 1 };
src_line = src_line.max(0);
src_col += (seg * 7 + 3) % 50 - 10;
src_col = src_col.max(0);
if seg % 5 == 0 {
name += 1;
line.push(Segment::five(gen_col, src, src_line, src_col, name));
} else {
line.push(Segment::four(gen_col, src, src_line, src_col));
}
}
mappings.push(line);
}
mappings
};
c.bench_function("encode sequential (50K lines)", |b| {
b.iter(|| encode(black_box(&very_large)));
});
c.bench_function("encode parallel (50K lines)", |b| {
b.iter(|| encode_parallel(black_box(&very_large)));
});
}
}
fn bench_roundtrip(c: &mut Criterion) {
let realistic = make_realistic_mappings();
c.bench_function("roundtrip realistic (500 lines)", |b| {
b.iter(|| {
let decoded = decode(black_box(&realistic)).unwrap();
encode(black_box(&decoded))
});
});
}
criterion_group!(benches, bench_decode, bench_encode, bench_roundtrip);
criterion_main!(benches);