criterion/
macros.rs

1//! Contains macros which together define a benchmark harness that can be used
2//! in place of the standard benchmark harness. This allows the user to run
3//! Criterion.rs benchmarks with `cargo bench`.
4
5/// Macro used to define a function group for the benchmark harness; see the
6/// `criterion_main!` macro for more details.
7///
8/// This is used to define a function group; a collection of functions to call with a common
9/// Criterion configuration. Accepts two forms which can be seen below.
10///
11/// Note that the group name given here is not important, it must simply
12/// be unique. Note also that this macro is not related to the `Criterion::benchmark_group` function
13/// or the `BenchmarkGroup` type.
14///
15/// # Examples:
16///
17/// Complete form:
18///
19/// ```
20/// # use criterion::{Criterion, criterion_group};
21/// # fn bench_method1(c: &mut Criterion) {
22/// # }
23/// #
24/// # fn bench_method2(c: &mut Criterion) {
25/// # }
26/// #
27/// criterion_group!{
28///     name = benches;
29///     config = Criterion::default();
30///     targets = bench_method1, bench_method2
31/// }
32/// #
33/// # fn main() {}
34/// ```
35///
36/// In this form, all of the options are clearly spelled out. This expands to
37/// a function named benches, which uses the given config expression to create
38/// an instance of the Criterion struct. This is then passed by mutable
39/// reference to the targets.
40///
41/// Compact Form:
42///
43/// ```
44/// # use criterion::{Criterion, criterion_group};
45/// # fn bench_method1(c: &mut Criterion) {
46/// # }
47/// #
48/// # fn bench_method2(c: &mut Criterion) {
49/// # }
50/// #
51/// criterion_group!(benches, bench_method1, bench_method2);
52/// #
53/// # fn main() {}
54/// ```
55/// In this form, the first parameter is the name of the group and subsequent
56/// parameters are the target methods. The Criterion struct will be created using
57/// the `Criterion::default()` function. If you wish to customize the
58/// configuration, use the complete form and provide your own configuration
59/// function.
60#[macro_export]
61macro_rules! criterion_group {
62    (name = $name:ident; config = $config:expr_2021; targets = $( $target:path ),+ $(,)*) => {
63        pub fn $name() {
64            let mut criterion: $crate::Criterion<_> = $config
65                .configure_from_args();
66            $(
67                $target(&mut criterion);
68            )+
69        }
70    };
71    ($name:ident, $( $target:path ),+ $(,)*) => {
72        $crate::criterion_group!{
73            name = $name;
74            config = $crate::Criterion::default();
75            targets = $( $target ),+
76        }
77    }
78}
79
80/// Macro which expands to a benchmark harness.
81///
82/// Currently, using Criterion.rs requires disabling the benchmark harness
83/// generated automatically by rustc. This can be done like so:
84///
85/// ```toml
86/// [[bench]]
87/// name = "my_bench"
88/// harness = false
89/// ```
90///
91/// In this case, `my_bench` must be a rust file inside the 'benches' directory,
92/// like so:
93///
94/// `benches/my_bench.rs`
95///
96/// Since we've disabled the default benchmark harness, we need to add our own:
97///
98/// ```ignore
99/// use criterion::Criterion;
100/// fn bench_method1(c: &mut Criterion) {
101/// }
102///
103/// fn bench_method2(c: &mut Criterion) {
104/// }
105///
106/// criterion_group!(benches, bench_method1, bench_method2);
107/// criterion_main!(benches);
108/// ```
109///
110/// The `criterion_main` macro expands to a `main` function which runs all of the
111/// benchmarks in the given groups.
112///
113#[macro_export]
114macro_rules! criterion_main {
115    ( $( $group:path ),+ $(,)* ) => {
116        fn main() {
117            $(
118                $group();
119            )+
120
121            $crate::Criterion::default()
122                .configure_from_args()
123                .final_summary();
124        }
125    }
126}