Bluetooth: Controller: Kconfig Tx buffer size

Add Kconfig configuration to select Tx buffer size, this
value will be returned in the HCI LE Read Buffer Size
command response.
This configuration will allow lower Tx RAM usage when
larger PDU sizes are desired in Rx direction only.

Change-Id: I5106a448d78a0754c4b0f6fa61fd5dcacd87a67c
Signed-off-by: Vinayak Chettimada <vinayak.kariappa.chettimada@nordicsemi.no>
This commit is contained in:
Vinayak Chettimada 2016-12-30 06:24:42 +01:00 committed by Johan Hedberg
commit 404e7662e0
6 changed files with 44 additions and 20 deletions

View file

@ -21,6 +21,19 @@ config BLUETOOTH_CONTROLLER_TX_BUFFERS
Set the number of Tx PDUs to be queued for transmission Set the number of Tx PDUs to be queued for transmission
in the controller. in the controller.
config BLUETOOTH_CONTROLLER_TX_BUFFER_SIZE
prompt "Tx buffer size"
int
range 27 16384
default 27
help
Size of the Tx buffers and the value returned in HCI LE Read Buffer
Size command response. If this size if greater than effective PDU size
then controller will perform fragmentation before transmitting on the
the packet on air.
Maximum is set to 16384 due to implementation limitations (use of
uint16_t for size/length variables).
config BLUETOOTH_CONTROLLER_RX_STACK_SIZE config BLUETOOTH_CONTROLLER_RX_STACK_SIZE
int "Size of the receiving thread stack" int "Size of the receiving thread stack"
default 512 default 512

View file

@ -300,7 +300,7 @@ static void le_read_buffer_size(struct net_buf *buf, struct net_buf *evt)
rp->status = 0x00; rp->status = 0x00;
rp->le_max_len = sys_cpu_to_le16(RADIO_LL_LENGTH_OCTETS_RX_MAX); rp->le_max_len = sys_cpu_to_le16(RADIO_PACKET_TX_DATA_SIZE);
rp->le_max_num = RADIO_PACKET_COUNT_TX_MAX; rp->le_max_num = RADIO_PACKET_COUNT_TX_MAX;
} }

View file

@ -325,13 +325,12 @@ static int hci_driver_open(void)
return -ENODEV; return -ENODEV;
} }
err = radio_init(clk_m16, err = radio_init(clk_m16, CLOCK_CONTROL_NRF5_K32SRC_ACCURACY,
CLOCK_CONTROL_NRF5_K32SRC_ACCURACY,
RADIO_CONNECTION_CONTEXT_MAX, RADIO_CONNECTION_CONTEXT_MAX,
RADIO_PACKET_COUNT_RX_MAX, RADIO_PACKET_COUNT_RX_MAX,
RADIO_PACKET_COUNT_TX_MAX, RADIO_PACKET_COUNT_TX_MAX,
RADIO_LL_LENGTH_OCTETS_RX_MAX, &_radio[0], RADIO_LL_LENGTH_OCTETS_RX_MAX,
sizeof(_radio)); RADIO_PACKET_TX_DATA_SIZE, &_radio[0], sizeof(_radio));
if (err) { if (err) {
BT_ERR("Required RAM size: %d, supplied: %u.", err, BT_ERR("Required RAM size: %d, supplied: %u.", err,
sizeof(_radio)); sizeof(_radio));

View file

@ -195,7 +195,6 @@ static struct {
void *pkt_tx_ctrl_free; void *pkt_tx_ctrl_free;
void *pkt_tx_data_pool; void *pkt_tx_data_pool;
void *pkt_tx_data_free; void *pkt_tx_data_free;
uint16_t packet_tx_data_pool_size;
uint16_t packet_tx_data_size; uint16_t packet_tx_data_size;
/* Host to Controller Tx, and Controller to Host Num complete queue */ /* Host to Controller Tx, and Controller to Host Num complete queue */
@ -299,7 +298,8 @@ static void rx_fc_lock(uint16_t handle);
****************************************************************************/ ****************************************************************************/
uint32_t radio_init(void *hf_clock, uint8_t sca, uint8_t connection_count_max, uint32_t radio_init(void *hf_clock, uint8_t sca, uint8_t connection_count_max,
uint8_t rx_count_max, uint8_t tx_count_max, uint8_t rx_count_max, uint8_t tx_count_max,
uint16_t packet_data_octets_max, uint8_t *mem_radio, uint16_t packet_data_octets_max,
uint16_t packet_tx_data_size, uint8_t *mem_radio,
uint16_t mem_size) uint16_t mem_size)
{ {
uint32_t retcode; uint32_t retcode;
@ -379,13 +379,11 @@ uint32_t radio_init(void *hf_clock, uint8_t sca, uint8_t connection_count_max,
_radio.packet_tx_data_size = _radio.packet_tx_data_size =
ALIGN4(offsetof(struct radio_pdu_node_tx, pdu_data) + ALIGN4(offsetof(struct radio_pdu_node_tx, pdu_data) +
offsetof(struct pdu_data, payload) + offsetof(struct pdu_data, payload) +
_radio.packet_data_octets_max); packet_tx_data_size);
_radio.packet_tx_data_pool_size =
(_radio.packet_tx_data_size * tx_count_max);
/* initialise tx data pool memory */ /* initialise tx data pool memory */
_radio.pkt_tx_data_pool = mem_radio; _radio.pkt_tx_data_pool = mem_radio;
mem_radio += _radio.packet_tx_data_pool_size; mem_radio += (_radio.packet_tx_data_size * tx_count_max);
/* check for sufficient memory allocation for stack /* check for sufficient memory allocation for stack
* configuration. * configuration.
@ -7602,6 +7600,8 @@ uint32_t radio_length_req_send(uint16_t handle, uint16_t tx_octets)
return 1; return 1;
} }
/* TODO: parameter check tx_octets */
conn->llcp_length.state = LLCP_LENGTH_STATE_REQ; conn->llcp_length.state = LLCP_LENGTH_STATE_REQ;
conn->llcp_length.tx_octets = tx_octets; conn->llcp_length.tx_octets = tx_octets;
conn->llcp_length.req++; conn->llcp_length.req++;
@ -7617,11 +7617,7 @@ void radio_length_default_get(uint16_t *max_tx_octets, uint16_t *max_tx_time)
uint32_t radio_length_default_set(uint16_t max_tx_octets, uint16_t max_tx_time) uint32_t radio_length_default_set(uint16_t max_tx_octets, uint16_t max_tx_time)
{ {
if (max_tx_octets > RADIO_LL_LENGTH_OCTETS_RX_MAX || /* TODO: parameter check (for BT 5.0 compliance) */
max_tx_time > RADIO_LL_LENGTH_TIME_RX_MAX) {
return 1;
}
_radio.default_tx_octets = max_tx_octets; _radio.default_tx_octets = max_tx_octets;
_radio.default_tx_time = max_tx_time; _radio.default_tx_time = max_tx_time;
@ -7957,11 +7953,15 @@ uint32_t radio_tx_mem_enqueue(uint16_t handle,
pdu_data = (struct pdu_data *)node_tx->pdu_data; pdu_data = (struct pdu_data *)node_tx->pdu_data;
conn = connection_get(handle); conn = connection_get(handle);
if ((last == _radio.packet_tx_first) || (conn == 0) || if (!conn || (last == _radio.packet_tx_first)) {
(pdu_data->len > _radio.packet_data_octets_max)) {
return 1; return 1;
} }
LL_ASSERT(pdu_data->len <= (_radio.packet_tx_data_size -
offsetof(struct radio_pdu_node_tx,
pdu_data) -
offsetof(struct pdu_data, payload)));
_radio.pkt_tx[_radio.packet_tx_last].handle = handle; _radio.pkt_tx[_radio.packet_tx_last].handle = handle;
_radio.pkt_tx[_radio.packet_tx_last]. node_tx = node_tx; _radio.pkt_tx[_radio.packet_tx_last]. node_tx = node_tx;
_radio.packet_tx_last = last; _radio.packet_tx_last = last;

View file

@ -39,6 +39,11 @@
CONFIG_BLUETOOTH_CONTROLLER_TX_BUFFERS CONFIG_BLUETOOTH_CONTROLLER_TX_BUFFERS
#endif #endif
#ifdef CONFIG_BLUETOOTH_CONTROLLER_TX_BUFFER_SIZE
#define RADIO_PACKET_TX_DATA_SIZE \
CONFIG_BLUETOOTH_CONTROLLER_TX_BUFFER_SIZE
#endif
#if defined(CONFIG_BLUETOOTH_CONTROLLER_LE_PING) #if defined(CONFIG_BLUETOOTH_CONTROLLER_LE_PING)
#define RADIO_BLE_FEATURES_BIT_PING BIT(BT_LE_FEAT_BIT_PING) #define RADIO_BLE_FEATURES_BIT_PING BIT(BT_LE_FEAT_BIT_PING)
#else /* !CONFIG_BLUETOOTH_CONTROLLER_LE_PING */ #else /* !CONFIG_BLUETOOTH_CONTROLLER_LE_PING */
@ -152,6 +157,12 @@
#define RADIO_PACKET_COUNT_APP_TX_MAX (RADIO_PACKET_COUNT_TX_MAX) #define RADIO_PACKET_COUNT_APP_TX_MAX (RADIO_PACKET_COUNT_TX_MAX)
#endif #endif
/* Tx Data Size */
#if !defined(RADIO_PACKET_TX_DATA_SIZE) || \
(RADIO_PACKET_TX_DATA_SIZE < RADIO_LL_LENGTH_OCTETS_RX_MIN)
#define RADIO_PACKET_TX_DATA_SIZE RADIO_LL_LENGTH_OCTETS_RX_MIN
#endif
/***************************************************************************** /*****************************************************************************
* Controller Interface Structures * Controller Interface Structures
****************************************************************************/ ****************************************************************************/
@ -229,7 +240,8 @@ struct radio_pdu_node_rx {
****************************************************************************/ ****************************************************************************/
uint32_t radio_init(void *hf_clock, uint8_t sca, uint8_t connection_count_max, uint32_t radio_init(void *hf_clock, uint8_t sca, uint8_t connection_count_max,
uint8_t rx_count_max, uint8_t tx_count_max, uint8_t rx_count_max, uint8_t tx_count_max,
uint16_t data_octets_max, uint8_t *mem_radio, uint16_t packet_data_octets_max,
uint16_t packet_tx_data_size, uint8_t *mem_radio,
uint16_t mem_size); uint16_t mem_size);
void ctrl_reset(void); void ctrl_reset(void);
void radio_ticks_active_to_start_set(uint32_t ticks_active_to_start); void radio_ticks_active_to_start_set(uint32_t ticks_active_to_start);

View file

@ -250,7 +250,7 @@ struct pdu_data_q_tx {
#define LL_MEM_TX_DATA_POOL ((ALIGN4(offsetof( \ #define LL_MEM_TX_DATA_POOL ((ALIGN4(offsetof( \
struct radio_pdu_node_tx, pdu_data) + \ struct radio_pdu_node_tx, pdu_data) + \
offsetof(struct pdu_data, payload) + \ offsetof(struct pdu_data, payload) + \
RADIO_LL_LENGTH_OCTETS_RX_MAX)) \ RADIO_PACKET_TX_DATA_SIZE)) \
* (RADIO_PACKET_COUNT_TX_MAX + 1)) * (RADIO_PACKET_COUNT_TX_MAX + 1))
#define LL_MEM_TOTAL (LL_MEM_CONN + LL_MEM_RXQ + (LL_MEM_TXQ * 2) + \ #define LL_MEM_TOTAL (LL_MEM_CONN + LL_MEM_RXQ + (LL_MEM_TXQ * 2) + \