diff --git a/drivers/bluetooth/hci/h4.c b/drivers/bluetooth/hci/h4.c index 0f6935c99b..0a7293b62b 100644 --- a/drivers/bluetooth/hci/h4.c +++ b/drivers/bluetooth/hci/h4.c @@ -251,8 +251,8 @@ static inline void read_payload(void) rx.have_hdr = false; if (prio) { - BT_DBG("Calling bt_recv(%p)", buf); - bt_recv(buf); + BT_DBG("Calling bt_recv_prio(%p)", buf); + bt_recv_prio(buf); } else { BT_DBG("Putting buf %p to rx fifo", buf); net_buf_put(&rx.fifo, buf); diff --git a/include/drivers/bluetooth/hci_driver.h b/include/drivers/bluetooth/hci_driver.h index 61b6eca9bf..b6e9a8df1a 100644 --- a/include/drivers/bluetooth/hci_driver.h +++ b/include/drivers/bluetooth/hci_driver.h @@ -35,7 +35,6 @@ extern "C" { #endif -#if defined(CONFIG_BLUETOOTH_RECV_IS_RX_THREAD) /** Helper for the HCI driver to know which events are ok to be passed * through the RX thread and which must be given to bt_recv() from another * context. If this function returns true it's safe to pass the event @@ -60,11 +59,13 @@ static inline bool bt_hci_evt_is_prio(uint8_t evt) return false; } } -#endif /* Receive data from the controller/HCI driver */ int bt_recv(struct net_buf *buf); +/* Receive priority event from the controller/HCI driver */ +int bt_recv_prio(struct net_buf *buf); + enum bt_hci_driver_bus { BT_HCI_DRIVER_BUS_VIRTUAL = 0, BT_HCI_DRIVER_BUS_USB = 1, diff --git a/subsys/bluetooth/controller/hci/hci_driver.c b/subsys/bluetooth/controller/hci/hci_driver.c index e64212ff41..1e27d65302 100644 --- a/subsys/bluetooth/controller/hci/hci_driver.c +++ b/subsys/bluetooth/controller/hci/hci_driver.c @@ -222,7 +222,7 @@ static void recv_thread(void *p1, void *p2, void *p3) bt_buf_set_type(buf, BT_BUF_EVT); hci_num_cmplt_encode(buf, handle, num_cmplt); BT_DBG("Num Complete: 0x%04x:%u", handle, num_cmplt); - bt_recv(buf); + bt_recv_prio(buf); k_yield(); } @@ -294,7 +294,7 @@ static int cmd_handle(struct net_buf *buf) err = hci_cmd_handle(buf, evt); if (!err && evt->len) { BT_DBG("Replying with event of %u bytes", evt->len); - bt_recv(evt); + bt_recv_prio(evt); } else { net_buf_unref(evt); } diff --git a/subsys/bluetooth/host/hci_core.c b/subsys/bluetooth/host/hci_core.c index 3e8cd39003..29c4f23e7d 100644 --- a/subsys/bluetooth/host/hci_core.c +++ b/subsys/bluetooth/host/hci_core.c @@ -2605,6 +2605,8 @@ static void hci_event(struct net_buf *buf) BT_DBG("event 0x%02x", hdr->evt); + BT_ASSERT(!bt_hci_evt_is_prio(hdr->evt)); + net_buf_pull(buf, sizeof(*hdr)); switch (hdr->evt) { @@ -3412,37 +3414,6 @@ int bt_send(struct net_buf *buf) return bt_dev.drv->send(buf); } -static inline void handle_event(struct net_buf *buf) -{ - struct bt_hci_evt_hdr *hdr = (void *)buf->data; - - switch (hdr->evt) { - case BT_HCI_EVT_CMD_COMPLETE: - net_buf_pull(buf, sizeof(*hdr)); - hci_cmd_complete(buf); - break; - case BT_HCI_EVT_CMD_STATUS: - net_buf_pull(buf, sizeof(*hdr)); - hci_cmd_status(buf); - break; -#if defined(CONFIG_BLUETOOTH_CONN) - case BT_HCI_EVT_NUM_COMPLETED_PACKETS: - net_buf_pull(buf, sizeof(*hdr)); - hci_num_completed_packets(buf); - break; -#endif /* CONFIG_BLUETOOTH_CONN */ - default: -#if defined(CONFIG_BLUETOOTH_RECV_IS_RX_THREAD) - hci_event(net_buf_ref(buf)); -#else - net_buf_put(&bt_dev.rx_queue, net_buf_ref(buf)); -#endif - break; - } - - net_buf_unref(buf); -} - int bt_recv(struct net_buf *buf) { bt_monitor_send(bt_monitor_opcode(buf), buf->data, buf->len); @@ -3466,7 +3437,11 @@ int bt_recv(struct net_buf *buf) return 0; #endif /* BLUETOOTH_CONN */ case BT_BUF_EVT: - handle_event(buf); +#if defined(CONFIG_BLUETOOTH_RECV_IS_RX_THREAD) + hci_event(buf); +#else + net_buf_put(&bt_dev.rx_queue, buf); +#endif return 0; default: BT_ERR("Invalid buf type %u", bt_buf_get_type(buf)); @@ -3475,6 +3450,41 @@ int bt_recv(struct net_buf *buf) } } +int bt_recv_prio(struct net_buf *buf) +{ + struct bt_hci_evt_hdr *hdr = (void *)buf->data; + + bt_monitor_send(bt_monitor_opcode(buf), buf->data, buf->len); + + BT_ASSERT(bt_buf_get_type(buf) == BT_BUF_EVT); + BT_ASSERT(buf->len >= sizeof(*hdr)); + BT_ASSERT(bt_hci_evt_is_prio(hdr->evt)); + + net_buf_pull(buf, sizeof(*hdr)); + + switch (hdr->evt) { + case BT_HCI_EVT_CMD_COMPLETE: + hci_cmd_complete(buf); + break; + case BT_HCI_EVT_CMD_STATUS: + hci_cmd_status(buf); + break; +#if defined(CONFIG_BLUETOOTH_CONN) + case BT_HCI_EVT_NUM_COMPLETED_PACKETS: + hci_num_completed_packets(buf); + break; +#endif /* CONFIG_BLUETOOTH_CONN */ + default: + net_buf_unref(buf); + BT_ASSERT(0); + return -EINVAL; + } + + net_buf_unref(buf); + + return 0; +} + int bt_hci_driver_register(struct bt_hci_driver *drv) { if (bt_dev.drv) { diff --git a/subsys/bluetooth/host/hci_ecc.c b/subsys/bluetooth/host/hci_ecc.c index 0e0096fab1..b06391fd03 100644 --- a/subsys/bluetooth/host/hci_ecc.c +++ b/subsys/bluetooth/host/hci_ecc.c @@ -87,7 +87,7 @@ static void send_cmd_status(uint16_t opcode, uint8_t status) evt->opcode = sys_cpu_to_le16(opcode); evt->status = status; - bt_recv(buf); + bt_recv_prio(buf); } static uint8_t generate_keys(EccPoint *pkey, uint32_t private_key[8]) diff --git a/subsys/bluetooth/host/hci_raw.c b/subsys/bluetooth/host/hci_raw.c index a68d3a133e..28bc85a250 100644 --- a/subsys/bluetooth/host/hci_raw.c +++ b/subsys/bluetooth/host/hci_raw.c @@ -100,6 +100,11 @@ int bt_recv(struct net_buf *buf) return 0; } +int bt_recv_prio(struct net_buf *buf) +{ + return bt_recv(buf); +} + int bt_send(struct net_buf *buf) { BT_DBG("buf %p len %u", buf, buf->len);