> ## Documentation Index
> Fetch the complete documentation index at: https://codspeed.io/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# Writing Benchmarks in Rust

> Learn how to write benchmarks and measure the performance of your Rust code.

## Supported Benchmarking Crates

CodSpeed offers compatibility layers for several popular benchmarking crates:

<Card horizontal title="divan (recommended)" href="/benchmarks/rust/divan" icon="star">
  The most convenient way to run your Rust benchmarks
</Card>

<Columns cols={2}>
  <Card title="criterion.rs" href="/benchmarks/rust/criterion">
    A benchmarking crate inspired by the criterion haskell library
  </Card>

  <Card title="libtest (bencher)" href="/benchmarks/rust/bencher">
    The libtest (unstable) benchmark runner
  </Card>
</Columns>

You should use the [`divan` benchmarking framework](/benchmarks/rust/divan) due
to its [extensive features](/benchmarks/rust/divan#advanced-usage), such as
running type-generic benchmarks. Its popularity is growing rapidly within the
Rust ecosystem.

If you're already using [`criterion.rs`](/benchmarks/rust/criterion) or
[`bencher`](/benchmarks/rust/bencher), consider their respective plugins, as
they require minimal adjustments to work with CodSpeed.

## How does CodSpeed work with Rust benchmarks?

Rust, being a compiled language, has CodSpeed integrations that differ from
those for interpreted languages. The CodSpeed benchmarking process for Rust
occurs at both build time and runtime.

To facilitate this, CodSpeed provides:

1. A [`cargo-codspeed` cargo subcommand](./#cargo-codspeed): used regardless of
   the benchmarking crate.
2. [Compatibility layers](./#benchmarking-crates) for popular benchmarking
   crates: chose the appropriate one based on your project's needs.

## `cargo-codspeed`

To integrate CodSpeed with your Rust codebase, use the `cargo` subcommand:
[cargo-codspeed](https://crates.io/crates/cargo-codspeed). This tool allows you
to run CodSpeed benchmarks without modifying the behavior of the standard
`cargo bench` command.

<Tip>
  Creating benchmarks with `cargo-codspeed` is the same as with the supported
  APIs. So if you already have benchmarks written with one of these, only a
  minor import change is required.
</Tip>

<Danger>
  Due to a [limitation of cargo](https://github.com/rust-lang/cargo/issues/5376), we currently do not support `build.rustflags` in `.cargo/config.toml` file
  when using `cargo-codspeed`.

  However, you can use `[target.'cfg(all())']` instead of `[build]` as a
  workaround which does the same and is compatible.

  ```toml theme={null}
  [build]                                       // [!code --]
  [target.'cfg(all())']                         // [!code ++]
  rustflags = ["--cfg", "your_feature_flag"]
  ```
</Danger>

### Installation

To check your benchmarks with CodSpeed, you first need to install the
`cargo-codspeed` CLI tool:

```sh theme={null}
cargo install cargo-codspeed --locked
```

This tool can then be used directly within cargo:

```shellsession title=terminal icon="square-terminal" theme={null}
$ cargo codspeed
Cargo extension to build & run your codspeed benchmarks

Usage: cargo codspeed <COMMAND>

Commands:
  build  Build the benchmarks
  run    Run the previously built benchmarks

Options:
  -h, --help     Print help information
  -V, --version  Print version information
```

### Usage

No matter which benchmarking crate you're using, the `cargo-codspeed` command is
used to help you build and run the benchmark in a CodSpeed environment.

```shellsession title=terminal icon="square-terminal" theme={null}
$ cargo codspeed build
    Finished release [optimized] target(s) in 0.12s
    Finished built 1 benchmark suite(s)
$ cargo codspeed run
   Collected 1 benchmark suite(s) to run
     Running example
Using codspeed-bencher-compat v1.0.0 compatibility layer
NOTICE: codspeed is enabled, but no performance measurement will be made since it's running in an unknown environment.
Checked: benches/example.rs::a (group: benches)
Checked: benches/example.rs::b (group: benches)
        Done running bencher_example
    Finished running 1 benchmark suite(s)
```

<Info>
  Use `--measurement-mode` / `-m` to select the CodSpeed instrument:

  * **`simulation`** (default): Runs benchmarks once on a
    [simulated CPU](/instruments/cpu) for consistent measurements.
  * **`walltime`**: Measures [wall-clock time](/instruments/walltime) for
    real-world scenarios.
  * **`memory`**: Benchmarks are run once using
    [memory profiling](/instruments/memory) to track heap allocations and memory
    usage.

  See the
  [`cargo-codspeed` reference](/reference/codspeed-rust/cargo-codspeed#the-measurement-mode-flag)
  for more information.
</Info>

#### Advanced build options

By default, `cargo codspeed build` will build all the benchmark executables of
your workspace. But you can also be more specific with the following options:

<Tip>
  **Cargo Workspaces**

  If you're using CodSpeed within a workspace you can use the `-p` flag to specify
  the crate to run the build command on:

  ```sh theme={null}
  cargo codspeed build -p my_package
  ```
</Tip>

<Tip>
  **Build only specific benchmark executables**

  With the following folder structure:

  ```plaintext theme={null}
  benches/
    ├── bench1.rs
    └── bench2.rs
  ```

  To build only `bench1`, you can pass its name as the `--bench` flag:

  ```sh theme={null}
  cargo codspeed build --bench bench1
  # Repeat this argument to build multiple benchmark executables
  cargo codspeed build --bench bench1 --bench bench2
  ```
</Tip>

<Tip>
  **Feature flags**

  If you're using feature flags in your benchmark suite, you can use the
  `--features` flag to specify the features to enable:

  ```sh theme={null}
  cargo codspeed build --features my_feature
  ```
</Tip>

#### Advanced run options

By default, `cargo codspeed run` will run all the **built** benchmarks (of the
latest `cargo codspeed build ...` command you ran).

To run only a subset of the built benchmarks, you can do the following:

```sh theme={null}
# Run all the benchmark executables of the `my_package` crate
cargo codspeed run -p my_package
# Run only the `bench1` benchmark executable
cargo codspeed run --bench bench1
# Run only benches containing `foo` in their name
cargo codspeed run foo
# Run only benches matching the `foo.*bar` regex
cargo codspeed run "foo.*bar"
# You can combine these options
cargo codspeed run -p my_package --bench bench1 foo
```

#### Building multiple instruments

When using multiple measurement modes, you need to build your benchmarks with
all the required instruments. Use the `-m` flag to specify each mode:

```sh theme={null}
# Build with both simulation and memory instruments
cargo codspeed build -m memory -m simulation
```

The resulting binaries are compatible across these modes, so you only need to
build once. At runtime, `cargo codspeed run` will execute the benchmarks for
each mode specified in your CI workflow.

<Info>
  To combine measurement modes like simulation and memory, check out the
  documentation on [running multiple instruments
  serially](/integrations/ci/github-actions/configuration#running-multiple-instruments-serially).
</Info>

## Continue by choosing a benchmarking crate

<Card horizontal title="divan (recommended)" href="/benchmarks/rust/divan" icon="star">
  The most convenient way to run your Rust benchmarks
</Card>

<Columns cols={2}>
  <Card title="criterion.rs" href="/benchmarks/rust/criterion">
    A benchmarking crate inspired by the criterion haskell library
  </Card>

  <Card title="libtest (bencher)" href="/benchmarks/rust/bencher">
    The libtest (unstable) benchmark runner
  </Card>
</Columns>
