components/
adc_microphone.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 ADC Microphone
6//!
7//! Usage
8//! -----
9//!
10//!
11//! ```rust
12//! let adc_microphone = components::adc_microphone::AdcMicrophoneComponent::new(
13//!     adc_mux,
14//!     nrf52833::adc::AdcChannelSetup::setup(
15//!         nrf52833::adc::AdcChannel::AnalogInput3,
16//!         nrf52833::adc::AdcChannelGain::Gain4,
17//!         nrf52833::adc::AdcChannelResistor::Bypass,
18//!         nrf52833::adc::AdcChannelResistor::Pulldown,
19//!         nrf52833::adc::AdcChannelSamplingTime::us3,
20//!     ),
21//!     Some(&nrf52833_peripherals.gpio_port[LED_MICROPHONE_PIN]),
22//! )
23//! .finalize(components::adc_microphone_component_static!(
24//!     // adc
25//!     nrf52833::adc::Adc,
26//!     // buffer size
27//!     50,
28//!     // gpio
29//!     nrf52833::gpio::GPIOPin
30//! ));
31//! ```
32
33use capsules_core::virtualizers::virtual_adc::AdcDevice;
34use capsules_extra::adc_microphone::AdcMicrophone;
35use core::mem::MaybeUninit;
36use kernel::component::Component;
37use kernel::hil::adc::{self, AdcChannel};
38use kernel::hil::gpio;
39
40#[macro_export]
41macro_rules! adc_microphone_component_static {
42    ($A:ty, $LEN:literal, $P: ty $(,)?) => {{
43        let adc_device = components::adc_component_static!($A);
44        let buffer = kernel::static_buf!([u16; $LEN]);
45        let adc_microphone =
46            kernel::static_buf!(capsules_extra::adc_microphone::AdcMicrophone<'static, $P>);
47
48        (adc_device, buffer, adc_microphone)
49    };};
50}
51
52pub struct AdcMicrophoneComponent<
53    A: 'static + adc::Adc<'static>,
54    P: 'static + gpio::Pin,
55    const BUF_LEN: usize,
56> {
57    adc_mux: &'static capsules_core::virtualizers::virtual_adc::MuxAdc<'static, A>,
58    adc_channel: A::Channel,
59    pin: Option<&'static P>,
60}
61
62impl<A: 'static + adc::Adc<'static>, P: 'static + gpio::Pin, const BUF_LEN: usize>
63    AdcMicrophoneComponent<A, P, BUF_LEN>
64{
65    pub fn new(
66        adc_mux: &'static capsules_core::virtualizers::virtual_adc::MuxAdc<'static, A>,
67        adc_channel: A::Channel,
68        pin: Option<&'static P>,
69    ) -> AdcMicrophoneComponent<A, P, BUF_LEN> {
70        AdcMicrophoneComponent {
71            adc_mux,
72            adc_channel,
73            pin,
74        }
75    }
76}
77
78impl<A: 'static + adc::Adc<'static>, P: 'static + gpio::Pin, const BUF_LEN: usize> Component
79    for AdcMicrophoneComponent<A, P, BUF_LEN>
80{
81    type StaticInput = (
82        &'static mut MaybeUninit<AdcDevice<'static, A>>,
83        &'static mut MaybeUninit<[u16; BUF_LEN]>,
84        &'static mut MaybeUninit<AdcMicrophone<'static, P>>,
85    );
86    type Output = &'static AdcMicrophone<'static, P>;
87
88    fn finalize(self, s: Self::StaticInput) -> Self::Output {
89        let adc_device =
90            crate::adc::AdcComponent::new(self.adc_mux, self.adc_channel).finalize(s.0);
91
92        let buffer = s.1.write([0; BUF_LEN]);
93
94        let adc_microphone = s.2.write(AdcMicrophone::new(adc_device, self.pin, buffer));
95
96        adc_device.set_client(adc_microphone);
97
98        adc_microphone
99    }
100}