1use capsules_core::virtualizers::virtual_spi::{MuxSpiMaster, VirtualSpiMasterDevice};
17use capsules_extra::l3gd20::L3gd20Spi;
18use core::mem::MaybeUninit;
19use kernel::capabilities;
20use kernel::component::Component;
21use kernel::create_capability;
22use kernel::hil::spi;
23use kernel::hil::spi::SpiMasterDevice;
24
25#[macro_export]
27macro_rules! l3gd20_component_static {
28 ($S:ty $(,)?) => {{
29 let txbuffer = kernel::static_buf!([u8; capsules_extra::l3gd20::TX_BUF_LEN]);
30 let rxbuffer = kernel::static_buf!([u8; capsules_extra::l3gd20::RX_BUF_LEN]);
31
32 let spi = kernel::static_buf!(
33 capsules_core::virtualizers::virtual_spi::VirtualSpiMasterDevice<'static, $S>
34 );
35 let l3gd20spi = kernel::static_buf!(
36 capsules_extra::l3gd20::L3gd20Spi<
37 'static,
38 capsules_core::virtualizers::virtual_spi::VirtualSpiMasterDevice<'static, $S>,
39 >
40 );
41
42 (spi, l3gd20spi, txbuffer, rxbuffer)
43 };};
44}
45
46pub type L3gd20ComponentType<S> = capsules_extra::l3gd20::L3gd20Spi<'static, S>;
47
48pub struct L3gd20Component<
49 S: 'static + spi::SpiMaster<'static>,
50 CS: spi::cs::IntoChipSelect<S::ChipSelect, spi::cs::ActiveLow>,
51> {
52 spi_mux: &'static MuxSpiMaster<'static, S>,
53 chip_select: CS,
54 board_kernel: &'static kernel::Kernel,
55 driver_num: usize,
56}
57
58impl<
59 S: 'static + spi::SpiMaster<'static>,
60 CS: spi::cs::IntoChipSelect<S::ChipSelect, spi::cs::ActiveLow>,
61 > L3gd20Component<S, CS>
62{
63 pub fn new(
64 spi_mux: &'static MuxSpiMaster<'static, S>,
65 chip_select: CS,
66 board_kernel: &'static kernel::Kernel,
67 driver_num: usize,
68 ) -> Self {
69 Self {
70 spi_mux,
71 chip_select,
72 board_kernel,
73 driver_num,
74 }
75 }
76}
77
78impl<
79 S: 'static + spi::SpiMaster<'static>,
80 CS: spi::cs::IntoChipSelect<S::ChipSelect, spi::cs::ActiveLow>,
81 > Component for L3gd20Component<S, CS>
82{
83 type StaticInput = (
84 &'static mut MaybeUninit<VirtualSpiMasterDevice<'static, S>>,
85 &'static mut MaybeUninit<L3gd20Spi<'static, VirtualSpiMasterDevice<'static, S>>>,
86 &'static mut MaybeUninit<[u8; capsules_extra::l3gd20::TX_BUF_LEN]>,
87 &'static mut MaybeUninit<[u8; capsules_extra::l3gd20::RX_BUF_LEN]>,
88 );
89 type Output = &'static L3gd20Spi<'static, VirtualSpiMasterDevice<'static, S>>;
90
91 fn finalize(self, static_buffer: Self::StaticInput) -> Self::Output {
92 let grant_cap = create_capability!(capabilities::MemoryAllocationCapability);
93 let grant = self.board_kernel.create_grant(self.driver_num, &grant_cap);
94
95 let spi_device = static_buffer.0.write(VirtualSpiMasterDevice::new(
96 self.spi_mux,
97 self.chip_select.into_cs(),
98 ));
99 spi_device.setup();
100
101 let txbuffer = static_buffer
102 .2
103 .write([0; capsules_extra::l3gd20::TX_BUF_LEN]);
104 let rxbuffer = static_buffer
105 .3
106 .write([0; capsules_extra::l3gd20::RX_BUF_LEN]);
107
108 let l3gd20 = static_buffer
109 .1
110 .write(L3gd20Spi::new(spi_device, txbuffer, rxbuffer, grant));
111 spi_device.set_client(l3gd20);
112
113 let _ = l3gd20.configure();
115
116 l3gd20
117 }
118}