81 lines
2.3 KiB
Rust
81 lines
2.3 KiB
Rust
//! Simple DAC-ADC example.
|
|
#![no_main]
|
|
#![no_std]
|
|
|
|
// Import panic provider.
|
|
use panic_probe as _;
|
|
// Import logger.
|
|
use defmt_rtt as _;
|
|
|
|
use cortex_m_rt::entry;
|
|
use embedded_hal::delay::DelayNs;
|
|
use simple_examples::peb1;
|
|
use va416xx_hal::{adc::Adc, dac::Dac, pac, prelude::*, timer::CountdownTimer};
|
|
|
|
const DAC_INCREMENT: u16 = 256;
|
|
|
|
#[derive(Debug, PartialEq, Eq)]
|
|
pub enum AppMode {
|
|
// Measurements on AIN0.
|
|
AdcOnly,
|
|
// AOUT0. You can use a multi-meter to measure the changing voltage on the pin.
|
|
DacOnly,
|
|
/// AOUT0 needs to be wired to AIN0.
|
|
DacAndAdc,
|
|
}
|
|
|
|
const APP_MODE: AppMode = AppMode::DacAndAdc;
|
|
|
|
#[entry]
|
|
fn main() -> ! {
|
|
defmt::println!("VA416xx DAC/ADC example");
|
|
|
|
let mut dp = pac::Peripherals::take().unwrap();
|
|
// Use the external clock connected to XTAL_N.
|
|
let clocks = dp
|
|
.clkgen
|
|
.constrain()
|
|
.xtal_n_clk_with_src_freq(peb1::EXTCLK_FREQ)
|
|
.freeze(&mut dp.sysconfig)
|
|
.unwrap();
|
|
let mut dac = None;
|
|
if APP_MODE == AppMode::DacOnly || APP_MODE == AppMode::DacAndAdc {
|
|
dac = Some(Dac::new(
|
|
&mut dp.sysconfig,
|
|
dp.dac0,
|
|
va416xx_hal::dac::DacSettling::Apb2Times100,
|
|
&clocks,
|
|
));
|
|
}
|
|
let mut adc = None;
|
|
if APP_MODE == AppMode::AdcOnly || APP_MODE == AppMode::DacAndAdc {
|
|
adc = Some(Adc::new(&mut dp.sysconfig, dp.adc, &clocks));
|
|
}
|
|
let mut delay_provider = CountdownTimer::new(&mut dp.sysconfig, dp.tim0, &clocks);
|
|
let mut current_val = 0;
|
|
loop {
|
|
if let Some(dac) = &dac {
|
|
defmt::info!("loading DAC with value {}", current_val);
|
|
dac.load_and_trigger_manually(current_val)
|
|
.expect("loading DAC value failed");
|
|
if current_val + DAC_INCREMENT >= 4096 {
|
|
current_val = 0;
|
|
} else {
|
|
current_val += DAC_INCREMENT;
|
|
}
|
|
}
|
|
if let Some(dac) = &dac {
|
|
// This should never block.
|
|
nb::block!(dac.is_settled()).unwrap();
|
|
}
|
|
if let Some(adc) = &adc {
|
|
let ch_value = adc
|
|
.trigger_and_read_single_channel(va416xx_hal::adc::ChannelSelect::AnIn0)
|
|
.expect("reading ADC channel 0 failed");
|
|
defmt::info!("Received channel value {:?}", ch_value);
|
|
}
|
|
|
|
delay_provider.delay_ms(500);
|
|
}
|
|
}
|