Files
esp-idf/examples/bluetooth/nimble/throughput_app
Rahul Tank 24962cc3fe fix(nimble): Improve safety, fix bugs, and update docs across NimBLE examples
- Remove unused headers from examples
- Improve periodic adv/sync example functionality and readability
- Use ble_hs_id_infer_auto() instead of hardcoded BLE_OWN_ADDR_PUBLIC/RANDOM
- Add ble_hs_util_ensure_addr() calls in on_sync for proper address setup
- Use correct ext adv instance (0 instead of 1) in phy_prph, l2cap_coc, multi_conn
- Fix struct name: ble_gap_periodic_adv_enable_params -> ble_gap_periodic_adv_start_params
- Add CONFIG_BT_NIMBLE_GAP_SERVICE guards around ble_svc_gap_device_name_set
- Fix unsafe AD data parsing with bounds checks in central examples
- Fix UUID matching bugs (off-by-one loop condition and byte order) in
  phy_cent, htp_cent, and proximity_sensor_cent
- Fix ble_multi_conn_cent address type to use dynamic inference
- Remove contradictory sm_sc=0 after sm_sc=1 in ble_multi_adv
- Add CONFIG_BT_NIMBLE_EXT_ADV=y to ble_multi_adv sdkconfig defaults
- Check return values for ble_gap_set_host_feat, nimble_port_init
- Update tutorials and READMEs to match code changes
2026-02-25 13:04:23 +05:30
..

Throughput Demo Examples

There are two example folders inside this throughput_app: bleprph_throughput (peripheral) and blecent_throughput (central). These examples demonstrate BLE GATT throughput measurement using NimBLE on ESP32. Two ESP32 boards are needed to run this demo. The blecent_throughput example has CLI support to select GATT operation from READ/WRITE/NOTIFY and configure connection parameters at runtime. More details can be found in respective READMEs.

Using the Examples

Build and flash two ESP32 boards with bleprph_throughput and blecent_throughput examples. The central automatically scans and connects to the peripheral based on device name (nimble_prph). After connection, the user may optionally configure connection parameters (MTU, connection interval, latency, supervision timeout, connection event length). Then the user specifies the throughput test type (read, write or notify) and test duration in seconds.

Below are sample throughput numbers for a 60-second test run (MTU = 512, conn itvl = 7.5ms, DLE = 251 bytes, 1M PHY):

GATT Method Measurement Time Application Throughput
NOTIFY 60 seconds ~340 Kbps
READ 60 seconds ~200 Kbps
WRITE 60 seconds ~500 Kbps

The notify throughput output is displayed on the bleprph_throughput console, while read/write throughput results are shown on the blecent_throughput console.

Throughput Optimization

The following parameters have the most significant impact on throughput:

  1. Connection Interval: The default is 7.5ms (minimum allowed by BLE spec). Shorter intervals mean more connection events per second and higher throughput.

  2. Connection Event Length: Controls how long a single connection event can last. The default maximum CE length is 15ms, allowing the controller to extend events and transmit more PDUs per event when possible.

  3. Notification Pipelining: The peripheral queues multiple notifications simultaneously (pipeline depth of 15) rather than waiting for each one to complete before sending the next. This allows the controller to pack multiple PDUs into each connection event.

  4. Payload Size: Payload sizes are set to the maximum ATT capacity for each operation (509 bytes for notify/write, 510 bytes for read) to maximize data per PDU.

  5. Data Length Extension (DLE): LL packet length is set to 251 bytes to use the maximum Link Layer PDU size.

  6. MTU: Set to 512 bytes to allow large ATT payloads and reduce protocol overhead.

  7. MSYS Buffer Count: Both peripheral and central are configured with 50 MSYS blocks (CONFIG_BT_NIMBLE_MSYS_1_BLOCK_COUNT=50) to provide sufficient buffer space for high-throughput operations.

  8. PHY: On BLE 5.0 supported chipsets, 2M PHY can be selected to double the air data rate. Use Extended Advertising mode and specify PHY in the throughput CLI command.