PHY1M is slower than PHY2M while forwarding data.

Hello All,

I have a problem when I build my project from sample central_uart &  peripheral_uart.

I have two nrf5340 called A and BB scans the broadcast to A to establish a connection. Then my phone(C) connects B.

A sends data to B, and B forwards data to C.

Speed of retransmission  is 160kbps when B works on PHY1M. However, speed drops to 40kbps when B works on PHY2M

I wonder what cause this problem.

Is there any ways to increase forwarding data speed?

Thank you.

static uint8_t ble_data_received(struct bt_nus_client *nus,
						const uint8_t *data, uint16_t len)
{
	ARG_UNUSED(nus);
	int err;

	err = bt_nus_send(peripheral_conn, data, len);
		// printk("len:%d\n",len);
		if (err) {
			printk("Send Error(err %d)\n", err);
		}
	
	return BT_GATT_ITER_CONTINUE;
}

B is connected with A as the center and C as the periphery.

Parents
  • Hi,

    The theoretical maximum throughput is doubled when going from 1 Mbps to 2 Mbps PHY. However there are many factors that affect throughput. What are the connection parameters, what about the event length? Is the device (A) able to provide data quickly enough to fill the connection event with more packets? It could be interesting to know which parameters you use, and see a sniffer trace of both the cases (1 and 2 Mbps) to see what the differences are on air.

  • Hi,

    The parameters I use are below.

    CONFIG_BT_CTLR_DATA_LENGTH_MAX=251
    CONFIG_BT_BUF_ACL_TX_SIZE=256
    CONFIG_BT_BUF_ACL_RX_SIZE=512
    CONFIG_BT_CTLR_PHY_2M=y
    CONFIG_BT_CTLR_RX_BUFFERS=2
    CONFIG_BT_CTLR_SDC_MAX_CONN_EVENT_LEN_DEFAULT=50000

    I use the default parameters for the rest.

    Moreover, the speed of data could reach 1.2Mbps when A only connects B without advertising. 
    Thanks.
  • In 2Mbps PHY mode, I use this function of B.

    static void data_len_updated(struct bt_conn *conn, struct bt_conn_le_data_len_info *info)
    {
    	int err;
    
    	LOG_INF("Data length updated. RX length: %d, TX length: %d", info->rx_max_len,
    		info->tx_max_len);
    
    	err = bt_conn_le_phy_update(conn, BT_CONN_LE_PHY_PARAM_2M);
    	if (err) {
    		LOG_ERR("bt_conn_le_phy_update() returned %d", err);
    	}
    }
    
    static void 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);
    }
    
    static struct bt_conn_cb conn_callbacks = {
    	.connected = connected,
    	.disconnected = disconnected,
    #if CONFIG_BT_USER_DATA_LEN_UPDATE
    	.le_data_len_updated = data_len_updated,
    #endif
    	.le_phy_updated = phy_updated,
    };

    In 1Mbps PHY momde, I don't use data_len_updated().

Reply
  • In 2Mbps PHY mode, I use this function of B.

    static void data_len_updated(struct bt_conn *conn, struct bt_conn_le_data_len_info *info)
    {
    	int err;
    
    	LOG_INF("Data length updated. RX length: %d, TX length: %d", info->rx_max_len,
    		info->tx_max_len);
    
    	err = bt_conn_le_phy_update(conn, BT_CONN_LE_PHY_PARAM_2M);
    	if (err) {
    		LOG_ERR("bt_conn_le_phy_update() returned %d", err);
    	}
    }
    
    static void 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);
    }
    
    static struct bt_conn_cb conn_callbacks = {
    	.connected = connected,
    	.disconnected = disconnected,
    #if CONFIG_BT_USER_DATA_LEN_UPDATE
    	.le_data_len_updated = data_len_updated,
    #endif
    	.le_phy_updated = phy_updated,
    };

    In 1Mbps PHY momde, I don't use data_len_updated().

Children
Related