# How to Configure BBRv2 Congestion Control in XQUIC: Build and Runtime Guide

> Learn how to configure BBRv2 congestion control in XQUIC. Compile with -DXQC_ENABLE_BBR2=ON and use --conn_options B2ON at runtime for optimal performance.

- Repository: [Alibaba/xquic](https://github.com/alibaba/xquic)
- Tags: how-to-guide
- Published: 2026-02-24

---

**Enable BBRv2 in XQUIC by compiling with `-DXQC_ENABLE_BBR2=ON` and passing the `--conn_options B2ON` flag at runtime to activate the algorithm via the internal option tag system.**

XQUIC is Alibaba's open-source QUIC protocol implementation that provides a pluggable congestion control framework supporting multiple algorithms including BBRv2. To configure BBRv2 congestion control in XQUIC, you must enable the algorithm at compile time using CMake flags and then activate it through connection option strings or command-line arguments when initializing connections.

## Build-Time Configuration: Enabling BBRv2 in CMake

BBRv2 support is conditionally compiled via the `XQC_ENABLE_BBR2` macro. The implementation resides in [`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c) and [`src/congestion_control/xqc_bbr2.h`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.h), which are only included in the build when the CMake flag is set.

To compile XQUIC with BBRv2 support, add `-DXQC_ENABLE_BBR2=ON` to your CMake configuration:

```bash
cd xquic
mkdir -p build && cd build
cmake -DXQC_ENABLE_BBR2=ON \
      -DXQC_ENABLE_RENO=ON \
      -DSSL_TYPE=boringssl \
      -DSSL_PATH=/path/to/boringssl \
      -DCMAKE_BUILD_TYPE=Release ..
make -j

```

The `XQC_ENABLE_BBR2` flag activates the BBRv2 state machine, bandwidth probing, and pacing logic implemented in [`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c). As documented in the repository's [`README.md`](https://github.com/alibaba/xquic/blob/main/README.md) (lines 95-99), this is the required first step before any runtime configuration can take effect.

## Runtime Configuration: Activating BBRv2 with Connection Options

XQUIC uses a four-character option tag system to enable specific connection features at runtime. The BBRv2 algorithm is controlled by the `XQC_CO_B2ON` tag, defined in [`include/xquic/xquic_typedef.h`](https://github.com/alibaba/xquic/blob/main/include/xquic/xquic_typedef.h) (line 278) as:

```c
#define XQC_CO_B2ON  XQC_CO_TAG('B','2','O','N')   // Enable BBRv2

```

### Command-Line Activation

Both the test client ([`tests/test_client.c`](https://github.com/alibaba/xquic/blob/main/tests/test_client.c)) and test server ([`tests/test_server.c`](https://github.com/alibaba/xquic/blob/main/tests/test_server.c)) accept the `--conn_options` argument. The parsing logic in [`src/transport/xqc_conn.c`](https://github.com/alibaba/xquic/blob/main/src/transport/xqc_conn.c) (around line 545) processes this string and stores the corresponding tags in the connection's `conn_options[]` array.

To enable BBRv2 via command line:

```bash

# Client side

./xquic_client -c bbr2 --conn_options B2ON -s 1024 -l d -t 1 -E

# Server side (optional, for server-initiated congestion control)

./xquic_server --conn_options B2ON -s 1024 -l d -t 1

```

The `-c bbr2` switch selects the congestion control algorithm, while `--conn_options B2ON` passes the specific option tag that activates the BBRv2 variant within the connection structure defined in [`src/transport/xqc_conn.h`](https://github.com/alibaba/xquic/blob/main/src/transport/xqc_conn.h).

## Advanced Configuration: Enabling BBRv2+ Mode

XQUIC ships with an experimental "BBRv2+" mode that modifies the pacing-gain cycle for specific performance characteristics. This feature requires additional compile-time and runtime configuration.

### Compile-Time Setup

Enable the plus variant by setting `XQC_BBR2_PLUS_ENABLED` to 1 in your CMake command:

```bash
cmake -DXQC_ENABLE_BBR2=ON -DXQC_BBR2_PLUS_ENABLED=1 ..

```

This macro is defined in [`include/xquic/xquic_typedef.h`](https://github.com/alibaba/xquic/blob/main/include/xquic/xquic_typedef.h) (line 164) and guards the extended pacing logic within the BBRv2 implementation.

### Runtime Selection

When running the test client, use the `bbr2+` or `bbr+` algorithm identifier with the `-c` switch. The parsing logic in [`tests/test_client.c`](https://github.com/alibaba/xquic/blob/main/tests/test_client.c) (lines 13-22) automatically sets the internal `c_cong_plus` flag when these strings are detected:

```bash
./xquic_client -c bbr2+ --conn_options B2ON -s 1024 -l d -t 1 -E

```

This activates the enhanced BBRv2 variant with modified probe bandwidth behavior while maintaining compatibility with the standard BBRv2 state machine in [`xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/xqc_bbr2.c).

## Programmatic Configuration via C API

For applications integrating XQUIC as a library, configure BBRv2 through the `xqc_conn_settings_t` structure before creating a connection.

### Basic BBRv2 Activation

```c
#include <xquic/xquic.h>

int main() {
    xqc_engine_t *engine = xqc_engine_create(&engine_config, NULL);
    if (!engine) return -1;

    xqc_conn_settings_t settings = XQC_DEFAULT_CONN_SETTINGS;
    
    /* Enable BBRv2 via the connection option string */
    strncpy(settings.conn_option_str, "B2ON", XQC_CO_STR_MAX_LEN);

    xqc_connection_t *conn = xqc_conn_create(engine, &dcid, &scid,
                                             &settings, NULL,
                                             XQC_CONN_TYPE_CLIENT);
    if (!conn) return -1;

    xqc_engine_connect(engine, conn, server_addr, server_port);
    /* ... run event loop ... */
    return 0;
}

```

The `conn_option_str` field mirrors the command-line `--conn_options B2ON` behavior, causing the connection logic in [`src/transport/xqc_conn.c`](https://github.com/alibaba/xquic/blob/main/src/transport/xqc_conn.c) to populate the `conn_options[]` array with the `XQC_CO_B2ON` tag.

### BBRv2+ via API

When the library is compiled with `XQC_BBR2_PLUS_ENABLED=1`, you can activate the plus mode by combining the option string with algorithm selection flags:

```c
strncpy(settings.conn_option_str, "B2ON", XQC_CO_STR_MAX_LEN);
settings.cong_ctl_flags |= XQC_CO_B2ON;   // Explicit tag setting
settings.c_cong_plus = 1;                // Enable plus mode

```

Note that `c_cong_plus` is typically managed internally by the algorithm selection logic when using `-c bbr2+` in the test harness.

## Summary

- **Compile with `-DXQC_ENABLE_BBR2=ON`** to include the BBRv2 implementation files ([`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c)) in the build.
- **Pass the `B2ON` option tag** via `--conn_options B2ON` at runtime or set `conn_option_str` to `"B2ON"` in the C API to activate the algorithm.
- **Use `-DXQC_BBR2_PLUS_ENABLED=1`** and the `bbr2+` algorithm identifier to enable experimental BBRv2+ features.
- **Reference implementation** resides in [`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c) with parsing logic in [`src/transport/xqc_conn.c`](https://github.com/alibaba/xquic/blob/main/src/transport/xqc_conn.c) and option definitions in [`include/xquic/xquic_typedef.h`](https://github.com/alibaba/xquic/blob/main/include/xquic/xquic_typedef.h).

## Frequently Asked Questions

### What is the difference between BBRv2 and BBRv2+ in XQUIC?

**BBRv2+ is an experimental variant** that modifies the pacing-gain cycle within the standard BBRv2 state machine. While standard BBRv2 uses the default probe bandwidth behavior defined in the IETF draft, BBRv2+ (enabled via `-DXQC_BBR2_PLUS_ENABLED=1` and `-c bbr2+`) applies custom pacing parameters for specific high-throughput scenarios. Both implementations share the core state machine in [`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c) but diverge in the gain cycle calculations.

### Can I use BBRv2 on both client and server sides simultaneously?

**Yes, BBRv2 operates independently on each peer.** Pass `--conn_options B2ON` to both the client ([`tests/test_client.c`](https://github.com/alibaba/xquic/blob/main/tests/test_client.c)) and server ([`tests/test_server.c`](https://github.com/alibaba/xquic/blob/main/tests/test_server.c)) binaries, or set the option string in both connection settings when using the C API. Each endpoint maintains its own congestion control state in [`xqc_send_ctl.c`](https://github.com/alibaba/xquic/blob/main/xqc_send_ctl.c), allowing asymmetric configurations where one peer uses BBRv2 and the other uses a different algorithm like Reno or Cubic.

### Why does XQUIC require both `-c bbr2` and `--conn_options B2ON`?

**The `-c` switch selects the algorithm module**, while `--conn_options` passes specific feature flags to that module. The `-c bbr2` argument loads the callbacks defined in [`xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/xqc_bbr2.c) (such as `xqc_cong_ctl_get_cwnd` and `xqc_cong_ctl_on_ack`), whereas the `B2ON` tag in `conn_options[]` triggers internal initialization paths specific to BBRv2's startup behavior. Omitting the option tag may result in the connection defaulting to basic congestion control behavior even when the BBRv2 module is loaded.

### Does enabling BBRv2 affect connection performance compared to Reno?

**BBRv2 generally provides higher throughput and lower latency** on high-BDP (bandwidth-delay product) networks by using a model-based approach rather than loss-based signals. According to the implementation in [`src/congestion_control/xqc_bbr2.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_bbr2.c), BBRv2 maintains separate pacing and bandwidth estimation loops compared to the loss-based Reno algorithm in [`src/congestion_control/xqc_reno.c`](https://github.com/alibaba/xquic/blob/main/src/congestion_control/xqc_reno.c). However, BBRv2 may exhibit different behavior during the startup phase and under extreme packet loss conditions, making the `B2ON` option tag essential for proper initialization tuning.