From 71bc00568dae42de149d495a202c834bc8d90ba3 Mon Sep 17 00:00:00 2001 From: zwl Date: Wed, 11 Jun 2025 11:27:24 +0800 Subject: [PATCH] feat(ble): add dtm test code to cert test example on ESP32-C6 --- examples/phy/cert_test/README.md | 4 +- examples/phy/cert_test/main/CMakeLists.txt | 9 +- examples/phy/cert_test/main/Kconfig.projbuild | 7 + examples/phy/cert_test/main/cert_test.c | 10 +- examples/phy/cert_test/main/cmd_ble_dtm.c | 189 ++++++++++++++++++ examples/phy/cert_test/main/cmd_ble_dtm.h | 13 ++ .../phy/cert_test/sdkconfig.defaults.esp32c6 | 10 + .../phy/cert_test/sdkconfig.defaults.esp32h2 | 9 + 8 files changed, 245 insertions(+), 6 deletions(-) create mode 100644 examples/phy/cert_test/main/cmd_ble_dtm.c create mode 100644 examples/phy/cert_test/main/cmd_ble_dtm.h create mode 100644 examples/phy/cert_test/sdkconfig.defaults.esp32c6 create mode 100644 examples/phy/cert_test/sdkconfig.defaults.esp32h2 diff --git a/examples/phy/cert_test/README.md b/examples/phy/cert_test/README.md index 748bbba0f0..42c3dc000e 100644 --- a/examples/phy/cert_test/README.md +++ b/examples/phy/cert_test/README.md @@ -6,7 +6,6 @@ (See the README.md file in the upper level 'examples' directory for more information about examples.) This example shows how to use the Certification test APIS. - ## How to use example Before project configuration and build, be sure to set the correct chip target using `idf.py set-target `. @@ -114,6 +113,9 @@ phy> For BLE test, if you want to use `fcc_le_tx` and `rw_le_rx_per` legacy commands for tx/rx test, you need to enable `ESP_PHY_LEGACY_COMMANDS` in menuconfig, otherwise, the new format commands `esp_ble_tx` and `esp_ble_rx` are supported. +## BLE DTM Test Function + +The BLE DTM test function in this example currently supports only the ESP32-H2 and ESP32-C6 chips. ## Troubleshooting For any technical queries, please open an [issue](https://github.com/espressif/esp-idf/issues) on GitHub. We will get back to you soon. diff --git a/examples/phy/cert_test/main/CMakeLists.txt b/examples/phy/cert_test/main/CMakeLists.txt index 34ce19d25e..7bb4e0d24f 100644 --- a/examples/phy/cert_test/main/CMakeLists.txt +++ b/examples/phy/cert_test/main/CMakeLists.txt @@ -1,4 +1,9 @@ -idf_component_register(SRCS "cert_test.c" - "cmd_phy.c" +set(srcs "cert_test.c" + "cmd_phy.c") +if(CONFIG_COMMANDS_ENABLE_BLE_DTM_TEST) +list(APPEND srcs "cmd_ble_dtm.c") +endif() + +idf_component_register(SRCS "${srcs}" PRIV_REQUIRES bt INCLUDE_DIRS ".") diff --git a/examples/phy/cert_test/main/Kconfig.projbuild b/examples/phy/cert_test/main/Kconfig.projbuild index ce75aded8f..c751f1a68a 100644 --- a/examples/phy/cert_test/main/Kconfig.projbuild +++ b/examples/phy/cert_test/main/Kconfig.projbuild @@ -11,4 +11,11 @@ menu "Example Configuration" endchoice + config COMMANDS_ENABLE_BLE_DTM_TEST + bool "Enable BLE DTM Test Mode" + depends on IDF_TARGET_ESP32C6 || IDF_TARGET_ESP32H2 + default n + help + Enable this option to support BLE Direct Test Mode (DTM) for RF testing and validation. + endmenu diff --git a/examples/phy/cert_test/main/cert_test.c b/examples/phy/cert_test/main/cert_test.c index cd8ac2afac..0c23d7850e 100644 --- a/examples/phy/cert_test/main/cert_test.c +++ b/examples/phy/cert_test/main/cert_test.c @@ -1,5 +1,5 @@ /* - * SPDX-FileCopyrightText: 2023-2024 Espressif Systems (Shanghai) CO LTD + * SPDX-FileCopyrightText: 2023-2025 Espressif Systems (Shanghai) CO LTD * * SPDX-License-Identifier: Apache-2.0 */ @@ -12,6 +12,9 @@ #include "cmd_phy.h" #include "esp_phy_cert_test.h" +#if CONFIG_COMMANDS_ENABLE_BLE_DTM_TEST +#include "cmd_ble_dtm.h" +#endif void app_main(void) { @@ -20,7 +23,6 @@ void app_main(void) esp_console_repl_t *repl = NULL; esp_console_repl_config_t repl_config = ESP_CONSOLE_REPL_CONFIG_DEFAULT(); repl_config.prompt = "phy>"; - #if CONFIG_ESP_CONSOLE_UART esp_console_dev_uart_config_t uart_config = ESP_CONSOLE_DEV_UART_CONFIG_DEFAULT(); ESP_ERROR_CHECK(esp_console_new_repl_uart(&uart_config, &repl_config, &repl)); @@ -46,7 +48,9 @@ void app_main(void) esp_phy_rftest_config(1); esp_phy_rftest_init(); #endif - +#if CONFIG_COMMANDS_ENABLE_BLE_DTM_TEST + dtm_configuration_command_register(); +#endif int help_index = 1; printf("\n ==================================================\n"); printf(" | RF certification test |\n"); diff --git a/examples/phy/cert_test/main/cmd_ble_dtm.c b/examples/phy/cert_test/main/cmd_ble_dtm.c new file mode 100644 index 0000000000..90e9d8daf7 --- /dev/null +++ b/examples/phy/cert_test/main/cmd_ble_dtm.c @@ -0,0 +1,189 @@ +/* + * SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ +#include "esp_log.h" +#include "esp_bt.h" + +#include "esp_console.h" +#include "argtable3/argtable3.h" +#include "esp_hci_driver.h" + +#define PROMPT_STR CONFIG_IDF_TARGET +static struct { + struct arg_int *cmd_params; + struct arg_end *end; +} dtm_set_tx_power_cmd_args; + +static struct { + struct arg_int *tx_pin; + struct arg_int *rx_pin; + struct arg_end *end; +} dtm_reconfig_uart_cmd_args; + +static struct { + struct arg_int *cmd_params; + struct arg_end *end; +} dtm_enable_cmd_args; + +static int dtm_set_ble_tx_power_command(int argc, char **argv) +{ + esp_err_t ret = ESP_OK; + int nerrors = arg_parse(argc, argv, (void **) &dtm_set_tx_power_cmd_args); + if (nerrors != 0) { + arg_print_errors(stderr, dtm_set_tx_power_cmd_args.end, argv[0]); + return 1; + } + + if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_ENABLED) { + esp_rom_printf("\nPlease enable BLE DTM mode first by using the command enable_ble_dtm -e 1 before sending this command.\n"); + return 2; + } + + ESP_LOGI(__func__, "Set tx power level '%d'", dtm_set_tx_power_cmd_args.cmd_params->ival[0]); + if (dtm_set_tx_power_cmd_args.cmd_params->ival[0] > 15) { + return 3; + } + + ret = esp_ble_tx_power_set_enhanced(ESP_BLE_ENHANCED_PWR_TYPE_DEFAULT, 0, dtm_set_tx_power_cmd_args.cmd_params->ival[0]); + if (ret != ESP_OK) { + return 4; + } + + return 0; +} + +static int dtm_get_ble_tx_power_command(int argc, char **argv) +{ + esp_power_level_t power_level = 0xFF; + if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_ENABLED) { + esp_rom_printf("\nPlease enable BLE DTM mode first by using the command enable_ble_dtm -e 1 before sending this command.\n"); + return 2; + } + + power_level = esp_ble_tx_power_get_enhanced(ESP_BLE_ENHANCED_PWR_TYPE_DEFAULT, 0); + esp_rom_printf("\nCurrent BLE TX power is %d level\n", power_level); + return 0; +} + +static int dtm_reconfig_uart_pins_command(int argc, char **argv) +{ + int nerrors = arg_parse(argc, argv, (void **) &dtm_reconfig_uart_cmd_args); + if (nerrors != 0) { + arg_print_errors(stderr, dtm_reconfig_uart_cmd_args.end, argv[0]); + return 1; + } + + if (esp_bt_controller_get_status() != ESP_BT_CONTROLLER_STATUS_ENABLED) { + esp_rom_printf("\nPlease enable BLE DTM mode first by using the command enable_ble_dtm -e 1 before sending this command.\n"); + return 2; + } + + ESP_LOGI(__func__, "reconfig tx:'%d', rx: '%d'", + dtm_reconfig_uart_cmd_args.tx_pin->ival[0], dtm_reconfig_uart_cmd_args.rx_pin->ival[0]); + hci_uart_reconfig_pin(dtm_reconfig_uart_cmd_args.tx_pin->ival[0], + dtm_reconfig_uart_cmd_args.rx_pin->ival[0], -1, -1); + return 0; +} + +static int dtm_test_enable_command(int argc, char **argv) +{ + int dtm_enable = 0; + esp_bt_controller_config_t config_opts = BT_CONTROLLER_INIT_CONFIG_DEFAULT(); + int nerrors = arg_parse(argc, argv, (void **) &dtm_enable_cmd_args); + if (nerrors != 0) { + arg_print_errors(stderr, dtm_enable_cmd_args.end, argv[0]); + return 1; + } + + dtm_enable = dtm_enable_cmd_args.cmd_params->ival[0]; + ESP_LOGI(__func__, "Enable DTM Test '%d'", dtm_enable); + if (dtm_enable > 2) { + return 2; + } + + if (dtm_enable) { + if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_IDLE) { + /* Initialize Bluetooth Controller parameters. */ + ESP_ERROR_CHECK(esp_bt_controller_init(&config_opts)); + + /* Enable the task stack of the Bluetooth Controller. */ + ESP_ERROR_CHECK(esp_bt_controller_enable(ESP_BT_MODE_BLE)); + } + } else { + if (esp_bt_controller_get_status() == ESP_BT_CONTROLLER_STATUS_ENABLED) { + ESP_ERROR_CHECK(esp_bt_controller_disable()); + ESP_ERROR_CHECK(esp_bt_controller_deinit()); + } + } + + return 0; +} + +esp_err_t esp_console_register_set_ble_tx_power_command(void) +{ + dtm_set_tx_power_cmd_args.cmd_params = arg_int1("i", "index", "","tx power level index"); + dtm_set_tx_power_cmd_args.end = arg_end(1); + + esp_console_cmd_t command = { + .command = "set_ble_tx_power", + .help = "Set ble tx power during DTM", + .func = &dtm_set_ble_tx_power_command, + .argtable = &dtm_set_tx_power_cmd_args + }; + + return esp_console_cmd_register(&command); +} + +esp_err_t esp_console_register_get_ble_tx_power_command(void) +{ + esp_console_cmd_t command = { + .command = "get_ble_tx_power", + .help = "Get ble tx power during DTM", + .func = &dtm_get_ble_tx_power_command, + }; + + return esp_console_cmd_register(&command); +} + + +esp_err_t esp_console_register_reconfig_dtm_pins_command(void) +{ + dtm_reconfig_uart_cmd_args.tx_pin = arg_int1("t", "tx", "","tx pin index"); + dtm_reconfig_uart_cmd_args.rx_pin = arg_int1("r", "rx", "","rx pin index"); + dtm_reconfig_uart_cmd_args.end = arg_end(2); + + esp_console_cmd_t command = { + .command = "reconfig_dtm_uart_pin", + .help = "Reconfig dtm uart pins during DTM", + .func = &dtm_reconfig_uart_pins_command, + .argtable = &dtm_reconfig_uart_cmd_args + }; + + return esp_console_cmd_register(&command); +} + +esp_err_t esp_console_register_enable_ble_dtm_command(void) +{ + dtm_enable_cmd_args.cmd_params = arg_int1("e", "enable", "","enable/disable ble dtm test"); + dtm_enable_cmd_args.end = arg_end(1); + + esp_console_cmd_t command = { + .command = "enable_ble_dtm", + .help = "Enable BLE DTM Test", + .func = &dtm_test_enable_command, + .argtable = &dtm_enable_cmd_args + }; + + return esp_console_cmd_register(&command); +} + +esp_err_t dtm_configuration_command_register(void) +{ + esp_console_register_set_ble_tx_power_command(); + esp_console_register_get_ble_tx_power_command(); + esp_console_register_reconfig_dtm_pins_command(); + esp_console_register_enable_ble_dtm_command(); + return ESP_OK; +} diff --git a/examples/phy/cert_test/main/cmd_ble_dtm.h b/examples/phy/cert_test/main/cmd_ble_dtm.h new file mode 100644 index 0000000000..b6dc400c15 --- /dev/null +++ b/examples/phy/cert_test/main/cmd_ble_dtm.h @@ -0,0 +1,13 @@ +/* + * SPDX-FileCopyrightText: 2024-2025 Espressif Systems (Shanghai) CO LTD + * + * SPDX-License-Identifier: Unlicense OR CC0-1.0 + */ +#ifndef __CMD_BLE_DTM_H__ +#define __CMD_BLE_DTM_H__ +#include +#include +#include "esp_err.h" + +esp_err_t dtm_configuration_command_register(void); +#endif diff --git a/examples/phy/cert_test/sdkconfig.defaults.esp32c6 b/examples/phy/cert_test/sdkconfig.defaults.esp32c6 new file mode 100644 index 0000000000..8ae9f0ef3b --- /dev/null +++ b/examples/phy/cert_test/sdkconfig.defaults.esp32c6 @@ -0,0 +1,10 @@ +# +# ESP32C6-specific +# + +CONFIG_COMMANDS_ENABLE_BLE_DTM_TEST=y +CONFIG_BT_CONTROLLER_ONLY=y +CONFIG_BT_LE_HCI_INTERFACE_USE_UART=y +CONFIG_BT_LE_HCI_UART_TX_PIN=8 +CONFIG_BT_LE_HCI_UART_RX_PIN=9 +CONFIG_BT_LE_HCI_UART_BAUD=115200 diff --git a/examples/phy/cert_test/sdkconfig.defaults.esp32h2 b/examples/phy/cert_test/sdkconfig.defaults.esp32h2 new file mode 100644 index 0000000000..6cc9f6cd96 --- /dev/null +++ b/examples/phy/cert_test/sdkconfig.defaults.esp32h2 @@ -0,0 +1,9 @@ +# +# ESP32C6-specific +# +CONFIG_COMMANDS_ENABLE_BLE_DTM_TEST=y +CONFIG_BT_CONTROLLER_ONLY=y +CONFIG_BT_LE_HCI_INTERFACE_USE_UART=y +CONFIG_BT_LE_HCI_UART_TX_PIN=8 +CONFIG_BT_LE_HCI_UART_RX_PIN=9 +CONFIG_BT_LE_HCI_UART_BAUD=115200