extern crate capstone_git as capstone;
#[macro_use]
extern crate criterion;
use capstone::prelude::*;
use capstone::{Arch, Endian, ExtraMode, Mode, NO_EXTRA_MODE};
use criterion::{black_box, Criterion};
const X86_CODE: &[u8] = include_bytes!("../test-inputs/x86_64.bin_ls.bin");
fn arch_bench<T: Iterator<Item = ExtraMode>>(
code: &[u8],
arch: Arch,
mode: Mode,
extra_mode: T,
endian: Option<Endian>,
detail: bool,
iter: bool,
) {
let mut cs =
Capstone::new_raw(arch, mode, extra_mode, endian).expect("failed to make capstone");
cs.set_detail(detail).expect("failed to set detail");
if iter {
let mut iter = cs.disasm_iter(code, 0x1000).expect("failed to disassemble");
while let Some(i) = iter.next() {
black_box(i);
}
} else {
let insns = cs.disasm_all(code, 0x1000).expect("failed to disassemble");
for i in insns.iter() {
black_box(i);
}
}
}
fn criterion_benchmark(c: &mut Criterion) {
macro_rules! bench {
($name:expr; $( $args:expr ),+ ) => {
c.bench_function($name, |b| {
b.iter(|| arch_bench($( $args, )+ false, false))
});
c.bench_function(concat!($name, "_iter"), |b| {
b.iter(|| arch_bench($( $args, )+ false, true))
});
c.bench_function(concat!($name, "_detail"), move |b| {
b.iter(|| arch_bench($( $args, )+ true, false))
});
c.bench_function(concat!($name, "_detail_iter"), |b| {
b.iter(|| arch_bench($( $args, )+ true, true))
});
}
}
bench!("disasm_x86"; X86_CODE, Arch::X86, Mode::Mode64, NO_EXTRA_MODE, None);
}
criterion_group!(benches, criterion_benchmark);
criterion_main!(benches);