How to set BLE PHY

BLE PHY setting defaults to 1M. They can be set to 2M or CODED_S2 or CODED_S8 by using Zephyr supported APIs as explained below.

To set PHY rate, applications need to do the following:

Set these in Application’s prj.conf file:

CONFIG_BT_USER_PHY_UPDATE=y
CONFIG_BT_PHY_UPDATE=y
CONFIG_BT_AUTO_PHY_UPDATE=n

BLE PHY can be configured using Zephyr API bt_conn_le_phy_update() to the desired PHY value.

Here is a sample code reference:

/*
 * PHY Update: Configure the physical layer based on Kconfig selection
 * - 1M PHY: Standard BLE PHY with 1 Mbps data rate
 * - 2M PHY: Enhanced PHY with 2 Mbps data rate (better throughput)
 * - Coded PHY S2/S8: Long-range PHY with error correction (better range)
 */
#if defined(CONFIG_ATM_BT_PHY_CODED_S2) || defined(CONFIG_ATM_BT_PHY_CODED_S8)
        static struct bt_conn_le_phy_param update_phy;
#endif

#if defined(CONFIG_ATM_BT_PHY_1M)
        err = bt_conn_le_phy_update(default_conn, BT_CONN_LE_PHY_PARAM_1M);
#elif defined(CONFIG_ATM_BT_PHY_2M)
        err = bt_conn_le_phy_update(default_conn, BT_CONN_LE_PHY_PARAM_2M);
#elif defined(CONFIG_ATM_BT_PHY_CODED_S2)
        update_phy.options = BT_CONN_LE_PHY_OPT_CODED_S2;
        update_phy.pref_rx_phy = BT_GAP_LE_PHY_CODED;
        update_phy.pref_tx_phy = BT_GAP_LE_PHY_CODED;
        err = bt_conn_le_phy_update(default_conn, &update_phy);
#elif defined(CONFIG_ATM_BT_PHY_CODED_S8)
        update_phy.options = BT_CONN_LE_PHY_OPT_CODED_S8;
        update_phy.pref_rx_phy = BT_GAP_LE_PHY_CODED;
        update_phy.pref_tx_phy = BT_GAP_LE_PHY_CODED;
        err = bt_conn_le_phy_update(default_conn, &update_phy);
#else
        LOG_INF("PHY mode not set in Kconfig");
        return;
#endif

To get a Connection PHY update callback defined using the Zephyr facilities, insert code as below:

BT_CONN_CB_DEFINE(conn_callbacks) = {
        .connected = connected,
        .disconnected = disconnected,
        .le_phy_updated = le_phy_updated,
 };

/**
 * @brief Callback for BLE PHY update completion
 *
 * @param conn Connection handle for the BLE connection
 * @param param PHY information containing new RX and TX PHY values
 */
static void le_phy_updated(struct bt_conn *conn, struct bt_conn_le_phy_info *param)
{
        LOG_INF("PHY UPDATED RX PHY %d, TX PHY %d", param->rx_phy, param->tx_phy);
}

And Application’s Kconfig can specify the configuration choice for PHY setting as follows:

choice
    prompt "Select BLE PHY mode"
    default ATM_BT_PHY_1M

config ATM_BT_PHY_1M
    bool "1M PHY"

config ATM_BT_PHY_2M
    bool "2M PHY"

config ATM_BT_PHY_CODED_S2
    bool "Coded PHY (S2)"

config ATM_BT_PHY_CODED_S8
    bool "Coded PHY (S8)"

endchoice