bluetooth: hci: SPI backend boot timeout

Add a timeout to the SPI boot process to ensure that `bt_enable` does
not block forever but instead returns an error after an appropriately
large delay. While 1 second would be sufficient under normal operation,
we also want to give the controller time to perform any application
upgrades via a bootloader.

Signed-off-by: Jordan Yates <jordan@embeint.com>
This commit is contained in:
Jordan Yates 2024-08-16 21:55:34 +10:00 committed by Benjamin Cabé
commit c3139c59d0
3 changed files with 19 additions and 3 deletions

View file

@ -81,6 +81,16 @@ config BT_SPI_INIT_PRIORITY
depends on BT_SPI depends on BT_SPI
default 75 default 75
config BT_SPI_BOOT_TIMEOUT_SEC
int "Seconds to wait for SPI device to report ready"
depends on BT_SPI_ZEPHYR || BT_SPI_BLUENRG
default 30
help
Maximum duration for a HCI SPI Controller to report ready through the
Zephyr Project defined `EVT_BLUE_INITIALIZED` HCI vendor event.
Default is 30 seconds to support a bootloader image swap on the
Controller.
config BT_SPI_ZEPHYR config BT_SPI_ZEPHYR
bool bool
default y default y

View file

@ -631,7 +631,9 @@ static int bt_spi_send(const struct device *dev, struct net_buf *buf)
* EVT_BLUE_INITIALIZED as an indication that it is safe to proceed. * EVT_BLUE_INITIALIZED as an indication that it is safe to proceed.
*/ */
if (bt_spi_get_cmd(buf->data) == BT_HCI_OP_RESET) { if (bt_spi_get_cmd(buf->data) == BT_HCI_OP_RESET) {
k_sem_take(&sem_initialised, K_FOREVER); if (k_sem_take(&sem_initialised, K_SECONDS(CONFIG_BT_SPI_BOOT_TIMEOUT_SEC)) < 0) {
ret = -EIO;
}
} }
#endif /* DT_HAS_COMPAT_STATUS_OKAY(st_hci_spi_v1) */ #endif /* DT_HAS_COMPAT_STATUS_OKAY(st_hci_spi_v1) */
net_buf_unref(buf); net_buf_unref(buf);
@ -682,7 +684,9 @@ static int bt_spi_open(const struct device *dev, bt_hci_recv_t recv)
0, K_NO_WAIT); 0, K_NO_WAIT);
/* Device will let us know when it's ready */ /* Device will let us know when it's ready */
k_sem_take(&sem_initialised, K_FOREVER); if (k_sem_take(&sem_initialised, K_SECONDS(CONFIG_BT_SPI_BOOT_TIMEOUT_SEC)) < 0) {
return -EIO;
}
#if defined(CONFIG_BT_HCI_RAW) && defined(CONFIG_BT_BLUENRG_ACI) #if defined(CONFIG_BT_HCI_RAW) && defined(CONFIG_BT_BLUENRG_ACI)
/* force BlueNRG to be on controller mode */ /* force BlueNRG to be on controller mode */

View file

@ -416,7 +416,9 @@ static int bt_spi_open(const struct device *dev, bt_hci_recv_t recv)
k_thread_name_set(&spi_rx_thread_data, "bt_spi_rx_thread"); k_thread_name_set(&spi_rx_thread_data, "bt_spi_rx_thread");
/* Device will let us know when it's ready */ /* Device will let us know when it's ready */
k_sem_take(&sem_initialised, K_FOREVER); if (k_sem_take(&sem_initialised, K_SECONDS(CONFIG_BT_SPI_BOOT_TIMEOUT_SEC)) < 0) {
return -EIO;
}
return 0; return 0;
} }