components/
sht3x.rs

1// Licensed under the Apache License, Version 2.0 or the MIT License.
2// SPDX-License-Identifier: Apache-2.0 OR MIT
3// Copyright Tock Contributors 2022.
4
5//! Component for the SHT3x sensor.
6//!
7//! I2C Interface
8//!
9//! Usage
10//! -----
11//!
12//! ```rust
13//! let sht3x = components::sht3x::SHT3xComponent::new(sensors_i2c_bus, capsules_extra::sht3x::BASE_ADDR, mux_alarm).finalize(
14//!         components::sht3x_component_static!(nrf52::rtc::Rtc<'static>),
15//!     );
16//! sht3x.reset();
17//! ```
18
19use capsules_core::virtualizers::virtual_alarm::{MuxAlarm, VirtualMuxAlarm};
20use capsules_core::virtualizers::virtual_i2c::{I2CDevice, MuxI2C};
21use capsules_extra::sht3x::SHT3x;
22use core::mem::MaybeUninit;
23use kernel::component::Component;
24use kernel::hil::i2c;
25use kernel::hil::time::Alarm;
26
27// Setup static space for the objects.
28#[macro_export]
29macro_rules! sht3x_component_static {
30    ($A:ty, $I:ty $(,)?) => {{
31        let buffer = kernel::static_buf!([u8; 6]);
32        let i2c_device =
33            kernel::static_buf!(capsules_core::virtualizers::virtual_i2c::I2CDevice<'static, $I>);
34        let sht3x_alarm = kernel::static_buf!(
35            capsules_core::virtualizers::virtual_alarm::VirtualMuxAlarm<'static, $A>
36        );
37        let sht3x = kernel::static_buf!(
38            capsules_extra::sht3x::SHT3x<
39                'static,
40                capsules_core::virtualizers::virtual_alarm::VirtualMuxAlarm<'static, $A>,
41                capsules_core::virtualizers::virtual_i2c::I2CDevice<'static, $I>,
42            >
43        );
44
45        (sht3x_alarm, i2c_device, sht3x, buffer)
46    };};
47}
48
49pub type SHT3xComponentType<A, I> = capsules_extra::sht3x::SHT3x<'static, A, I>;
50
51pub struct SHT3xComponent<A: 'static + Alarm<'static>, I: 'static + i2c::I2CMaster<'static>> {
52    i2c_mux: &'static MuxI2C<'static, I>,
53    i2c_address: u8,
54    alarm_mux: &'static MuxAlarm<'static, A>,
55}
56
57impl<A: 'static + Alarm<'static>, I: 'static + i2c::I2CMaster<'static>> SHT3xComponent<A, I> {
58    pub fn new(
59        i2c_mux: &'static MuxI2C<'static, I>,
60        i2c_address: u8,
61        alarm_mux: &'static MuxAlarm<'static, A>,
62    ) -> SHT3xComponent<A, I> {
63        SHT3xComponent {
64            i2c_mux,
65            i2c_address,
66            alarm_mux,
67        }
68    }
69}
70
71impl<A: 'static + Alarm<'static>, I: 'static + i2c::I2CMaster<'static>> Component
72    for SHT3xComponent<A, I>
73{
74    type StaticInput = (
75        &'static mut MaybeUninit<VirtualMuxAlarm<'static, A>>,
76        &'static mut MaybeUninit<I2CDevice<'static, I>>,
77        &'static mut MaybeUninit<
78            SHT3x<'static, VirtualMuxAlarm<'static, A>, I2CDevice<'static, I>>,
79        >,
80        &'static mut MaybeUninit<[u8; 6]>,
81    );
82    type Output = &'static SHT3x<'static, VirtualMuxAlarm<'static, A>, I2CDevice<'static, I>>;
83
84    fn finalize(self, static_buffer: Self::StaticInput) -> Self::Output {
85        let sht3x_i2c = static_buffer
86            .1
87            .write(I2CDevice::new(self.i2c_mux, self.i2c_address));
88
89        let buffer = static_buffer.3.write([0; 6]);
90
91        let sht3x_alarm = static_buffer.0.write(VirtualMuxAlarm::new(self.alarm_mux));
92        sht3x_alarm.setup();
93
94        let sht3x = static_buffer
95            .2
96            .write(SHT3x::new(sht3x_i2c, buffer, sht3x_alarm));
97        sht3x_i2c.set_client(sht3x);
98        sht3x_alarm.set_alarm_client(sht3x);
99
100        sht3x
101    }
102}