1 //! Hci shim
2
3 use crate::bridge::ffi;
4 use bt_facade_helpers::U8SliceRunnable;
5 use bt_hci::facade::HciFacadeService;
6 use bt_packets::hci::{AclPacket, CommandPacket, Packet};
7 use std::sync::Arc;
8 use tokio::runtime::Runtime;
9
10 // we take ownership when we get the callbacks
11 unsafe impl Send for ffi::u8SliceCallback {}
12 unsafe impl Send for ffi::u8SliceOnceCallback {}
13
14 struct CallbackWrapper {
15 cb: cxx::UniquePtr<ffi::u8SliceCallback>,
16 }
17
18 impl U8SliceRunnable for CallbackWrapper {
run(&self, data: &[u8])19 fn run(&self, data: &[u8]) {
20 self.cb.Run(data);
21 }
22 }
23
24 pub struct Hci {
25 internal: HciFacadeService,
26 rt: Arc<Runtime>,
27 }
28
29 impl Hci {
new(rt: Arc<Runtime>, internal: HciFacadeService) -> Self30 pub fn new(rt: Arc<Runtime>, internal: HciFacadeService) -> Self {
31 Self { rt, internal }
32 }
33 }
34
hci_send_command( hci: &mut Hci, data: &[u8], callback: cxx::UniquePtr<ffi::u8SliceOnceCallback>, )35 pub fn hci_send_command(
36 hci: &mut Hci,
37 data: &[u8],
38 callback: cxx::UniquePtr<ffi::u8SliceOnceCallback>,
39 ) {
40 log::error!("sending command: {:02x?}", data);
41 match CommandPacket::parse(data) {
42 Ok(packet) => {
43 let mut commands = hci.internal.commands.clone();
44 hci.rt.spawn(async move {
45 let resp = commands.send(packet).await.unwrap();
46 callback.Run(&resp.to_bytes());
47 });
48 }
49 Err(e) => panic!("could not parse command: {:?} {:02x?}", e, data),
50 }
51 }
52
hci_send_acl(hci: &mut Hci, data: &[u8])53 pub fn hci_send_acl(hci: &mut Hci, data: &[u8]) {
54 match AclPacket::parse(data) {
55 Ok(packet) => {
56 let tx = hci.internal.acl_tx.clone();
57 hci.rt.spawn(async move {
58 tx.send(packet).await.unwrap();
59 });
60 }
61 Err(e) => panic!("could not parse acl: {:?} {:02x?}", e, data),
62 }
63 }
64
hci_register_event(hci: &mut Hci, event: u8)65 pub fn hci_register_event(hci: &mut Hci, event: u8) {
66 let mut hci_facade = hci.internal.clone();
67 hci.rt.spawn(async move {
68 hci_facade.register_event(event.into()).await;
69 });
70 }
71
hci_register_le_event(hci: &mut Hci, subevent: u8)72 pub fn hci_register_le_event(hci: &mut Hci, subevent: u8) {
73 let mut hci_facade = hci.internal.clone();
74 hci.rt.spawn(async move {
75 hci_facade.register_le_event(subevent.into()).await;
76 });
77 }
78
hci_set_acl_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>)79 pub fn hci_set_acl_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
80 hci.internal.acl_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
81 }
82
hci_set_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>)83 pub fn hci_set_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
84 hci.internal.evt_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
85 }
86
hci_set_le_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>)87 pub fn hci_set_le_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
88 hci.internal.le_evt_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
89 }
90