Initial node implementation (#4)
Reviewed-on: #4 Co-authored-by: Zack <zack@bfpower.io> Co-committed-by: Zack <zack@bfpower.io>
This commit is contained in:
9
examples/ads1256/.cargo/config.toml
Normal file
9
examples/ads1256/.cargo/config.toml
Normal file
@ -0,0 +1,9 @@
|
||||
[target.'cfg(all(target_arch = "arm", target_os = "none"))']
|
||||
# replace STM32F429ZITx with your chip as listed in `probe-run --list-chips`
|
||||
runner = "probe-rs-cli run --chip STM32F429ZITx"
|
||||
|
||||
[build]
|
||||
target = "thumbv7em-none-eabi"
|
||||
|
||||
[env]
|
||||
DEFMT_LOG = "trace"
|
45
examples/ads1256/Cargo.toml
Normal file
45
examples/ads1256/Cargo.toml
Normal file
@ -0,0 +1,45 @@
|
||||
[package]
|
||||
name = "ads1256-examples"
|
||||
description = "Examples using the ads1256."
|
||||
version.workspace = true
|
||||
edition.workspace = true
|
||||
repository.workspace = true
|
||||
readme.workspace = true
|
||||
license.workspace = true
|
||||
|
||||
[dependencies.physical]
|
||||
path = "../.."
|
||||
features = ["thermocouple_k", "lm35"]
|
||||
[dependencies.physical-node]
|
||||
path = "../../node"
|
||||
features = ["embassy-sync"]
|
||||
[dependencies.physical-ads1256]
|
||||
path = "../../peripheral-components/ads1256/node"
|
||||
features = ["poll"]
|
||||
[dependencies.ads1256]
|
||||
workspace = true
|
||||
[dependencies.uom]
|
||||
workspace = true
|
||||
[dependencies.defmt]
|
||||
workspace = true
|
||||
[dependencies.defmt-rtt]
|
||||
workspace = true
|
||||
[dependencies.cortex-m]
|
||||
workspace = true
|
||||
features = ["critical-section-single-core"]
|
||||
[dependencies.cortex-m-rt]
|
||||
workspace = true
|
||||
[dependencies.embassy-stm32]
|
||||
workspace = true
|
||||
features = ["stm32f429zi", "memory-x", "time", "exti", "time-driver-any"]
|
||||
[dependencies.embassy-executor]
|
||||
workspace = true
|
||||
[dependencies.embassy-futures]
|
||||
workspace = true
|
||||
[dependencies.embassy-time]
|
||||
workspace = true
|
||||
features = ["tick-hz-16_000_000"]
|
||||
[dependencies.embassy-sync]
|
||||
workspace = true
|
||||
[dependencies.panic-probe]
|
||||
workspace = true
|
5
examples/ads1256/build.rs
Normal file
5
examples/ads1256/build.rs
Normal file
@ -0,0 +1,5 @@
|
||||
fn main() {
|
||||
println!("cargo:rustc-link-arg-bins=--nmagic");
|
||||
println!("cargo:rustc-link-arg-bins=-Tlink.x");
|
||||
println!("cargo:rustc-link-arg-bins=-Tdefmt.x");
|
||||
}
|
181
examples/ads1256/src/bin/multiplex.rs
Normal file
181
examples/ads1256/src/bin/multiplex.rs
Normal file
@ -0,0 +1,181 @@
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
#![feature(type_alias_impl_trait, async_fn_in_trait)]
|
||||
|
||||
use core::cell::Cell;
|
||||
use cortex_m::prelude::{
|
||||
_embedded_hal_blocking_delay_DelayMs, _embedded_hal_blocking_delay_DelayUs,
|
||||
};
|
||||
use {defmt_rtt as _, panic_probe as _};
|
||||
|
||||
use {embassy_executor as executor, embassy_stm32 as stm32};
|
||||
|
||||
use ads1256::standard::input::SingleEnded;
|
||||
use ads1256::{
|
||||
AdControl, Ads1256, AutoCal, BitOrder, BlockingDelay, Buffer, ClockOut, Config, DState,
|
||||
DataRate, DigitalIo, DigitalIoDirection, DigitalIoState, DioDirection, Gain, Multiplexer,
|
||||
MuxInput, OutputPin, Sdcs, SpiBus, Status, Wait,
|
||||
};
|
||||
use embassy_time::{Delay, Duration, Timer};
|
||||
use executor::Spawner;
|
||||
use stm32::dma::NoDma;
|
||||
use stm32::exti::ExtiInput;
|
||||
use stm32::gpio::{Input, Level, Output, Pull, Speed};
|
||||
use stm32::spi::Spi;
|
||||
use stm32::time::Hertz;
|
||||
use stm32::{pac, spi};
|
||||
|
||||
use uom::si::electric_potential::volt;
|
||||
use uom::si::f32;
|
||||
|
||||
use defmt::{debug, error, info, trace, unwrap};
|
||||
use embassy_executor::_export::StaticCell;
|
||||
use embassy_stm32::peripherals::{EXTI6, PF6, PF7, SPI3};
|
||||
use embassy_sync::blocking_mutex::raw::NoopRawMutex;
|
||||
use embassy_sync::pubsub::PubSubChannel;
|
||||
use physical_node::transducer::{Publish, StatefulPublisher};
|
||||
|
||||
const AUTOCAL_CONF: Config = Config {
|
||||
status: Status::setting(Buffer::Enabled, AutoCal::Enabled, BitOrder::MostSigFirst),
|
||||
multiplexer: Multiplexer::setting(MuxInput::AIn0, MuxInput::Common),
|
||||
ad_control: AdControl::setting(Gain::X2, Sdcs::Off, ClockOut::Off),
|
||||
data_rate: DataRate::Sps2_5,
|
||||
digital_io: DigitalIo::setting(DigitalIoState::default(), DigitalIoDirection::default()),
|
||||
};
|
||||
|
||||
struct Ads1256Delay;
|
||||
|
||||
impl ads1256::BlockingDelay for Ads1256Delay {
|
||||
#[inline]
|
||||
fn t6_delay(&mut self) {
|
||||
Delay.delay_us(1u32);
|
||||
}
|
||||
|
||||
fn t11_1_delay(&mut self) {}
|
||||
|
||||
fn t11_2_delay(&mut self) {}
|
||||
}
|
||||
|
||||
struct Inputs {
|
||||
ai0: StatefulPublisher<f32::ElectricPotential, NoopRawMutex, 10, 1>,
|
||||
ai1: StatefulPublisher<f32::ElectricPotential, NoopRawMutex, 10, 1>,
|
||||
ai2: StatefulPublisher<f32::ElectricPotential, NoopRawMutex, 10, 1>,
|
||||
}
|
||||
|
||||
// Inputs
|
||||
static ANALOG_INPUTS: StaticCell<Inputs> = StaticCell::new();
|
||||
static ADS_1256: StaticCell<Ads1256<Ads1256Delay, Output<PF7>, ExtiInput<PF6>>> = StaticCell::new();
|
||||
static SPI: StaticCell<Spi<SPI3, NoDma, NoDma>> = StaticCell::new();
|
||||
|
||||
#[embassy_executor::main]
|
||||
async fn main(spawner: Spawner) {
|
||||
unsafe {
|
||||
pac::FLASH.acr().modify(|v| {
|
||||
v.set_prften(true);
|
||||
v.set_icen(true);
|
||||
v.set_dcen(true);
|
||||
});
|
||||
}
|
||||
|
||||
let p = embassy_stm32::init(Default::default());
|
||||
|
||||
let mut spi_conf = spi::Config::default();
|
||||
spi_conf.mode = spi::MODE_1;
|
||||
spi_conf.bit_order = spi::BitOrder::MsbFirst;
|
||||
|
||||
let ads1256_data_ready = ExtiInput::new(Input::new(p.PF6, Pull::Up), p.EXTI6);
|
||||
let select_ads1256 = Output::new(p.PF7, Level::High, Speed::VeryHigh);
|
||||
|
||||
let spi = SPI.init(Spi::new(
|
||||
p.SPI3,
|
||||
p.PC10,
|
||||
p.PC12,
|
||||
p.PC11,
|
||||
NoDma,
|
||||
NoDma,
|
||||
Hertz(ads1256::defaults::SPI_CLK_HZ),
|
||||
spi_conf,
|
||||
));
|
||||
|
||||
let ads_1256 = ADS_1256.init(Ads1256::new(Ads1256Delay, select_ads1256, ads1256_data_ready));
|
||||
ads_1256.write_config(spi, AUTOCAL_CONF).unwrap();
|
||||
|
||||
let inputs = &*ANALOG_INPUTS.init(Inputs {
|
||||
ai0: StatefulPublisher::new(
|
||||
Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
PubSubChannel::new().into(),
|
||||
),
|
||||
ai1: StatefulPublisher::new(
|
||||
Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
PubSubChannel::new().into(),
|
||||
),
|
||||
ai2: StatefulPublisher::new(
|
||||
Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
PubSubChannel::new().into(),
|
||||
),
|
||||
});
|
||||
|
||||
spawner.spawn(log_task(inputs)).unwrap();
|
||||
spawner
|
||||
.spawn(drive_inputs_task(ads_1256, spi, inputs))
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
#[embassy_executor::task]
|
||||
async fn drive_inputs_task(
|
||||
ads_1256: &'static mut Ads1256<Ads1256Delay, Output<'static, PF7>, ExtiInput<'static, PF6>>,
|
||||
spi: &'static mut Spi<'static, SPI3, NoDma, NoDma>,
|
||||
inputs: &'static Inputs,
|
||||
) {
|
||||
let Inputs { ai0, ai1, ai2 } = inputs;
|
||||
|
||||
loop {
|
||||
let mut accumulator = f32::ElectricPotential::new::<volt>(0.0);
|
||||
|
||||
let voltage = ads_1256
|
||||
.autocal_convert(spi, SingleEnded::AIn0.into(), None, None, None, false)
|
||||
.await
|
||||
.unwrap()
|
||||
.to_voltage(AUTOCAL_CONF.ad_control.gain());
|
||||
ai0.update(voltage);
|
||||
accumulator += voltage;
|
||||
|
||||
let voltage = ads_1256
|
||||
.autocal_convert(spi, SingleEnded::AIn1.into(), None, None, None, false)
|
||||
.await
|
||||
.unwrap()
|
||||
.to_voltage(AUTOCAL_CONF.ad_control.gain());
|
||||
ai1.update(voltage);
|
||||
accumulator += voltage;
|
||||
|
||||
let voltage = ads_1256
|
||||
.autocal_convert(spi, SingleEnded::AIn2.into(), None, None, None, false)
|
||||
.await
|
||||
.unwrap()
|
||||
.to_voltage(AUTOCAL_CONF.ad_control.gain());
|
||||
ai2.update(voltage);
|
||||
accumulator += voltage;
|
||||
|
||||
let accum_volts = accumulator.get::<volt>();
|
||||
info!("Immediate loop iteration result, combined volts: {}", accum_volts);
|
||||
}
|
||||
}
|
||||
|
||||
#[embassy_executor::task]
|
||||
async fn log_task(inputs: &'static Inputs) {
|
||||
let Inputs { ai0, ai1, ai2 } = inputs;
|
||||
let mut ai0_sub = ai0.subscribe().unwrap();
|
||||
let mut ai1_sub = ai1.subscribe().unwrap();
|
||||
let mut ai2_sub = ai2.subscribe().unwrap();
|
||||
|
||||
loop {
|
||||
let msg = ai0_sub.next_message_pure().await.get::<volt>();
|
||||
info!("Log task ai0: {}", msg);
|
||||
|
||||
let msg = ai1_sub.next_message_pure().await.get::<volt>();
|
||||
info!("Log task ai1: {}", msg);
|
||||
|
||||
let msg = ai2_sub.next_message_pure().await.get::<volt>();
|
||||
info!("Log task ai2: {}", msg);
|
||||
}
|
||||
}
|
197
examples/ads1256/src/bin/poll.rs
Normal file
197
examples/ads1256/src/bin/poll.rs
Normal file
@ -0,0 +1,197 @@
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
#![feature(type_alias_impl_trait, async_fn_in_trait)]
|
||||
|
||||
use core::cell::Cell;
|
||||
use core::ops::DerefMut;
|
||||
use cortex_m::prelude::{
|
||||
_embedded_hal_blocking_delay_DelayMs, _embedded_hal_blocking_delay_DelayUs,
|
||||
};
|
||||
use {defmt_rtt as _, panic_probe as _};
|
||||
|
||||
use {embassy_executor as executor, embassy_stm32 as stm32};
|
||||
|
||||
use ads1256::standard::input::SingleEnded;
|
||||
use ads1256::{
|
||||
AdControl, Ads1256, AutoCal, BitOrder, BlockingDelay, Buffer, ClockOut, Config, DState,
|
||||
DataRate, DigitalIo, DigitalIoDirection, DigitalIoState, DioDirection, Gain, Multiplexer,
|
||||
MuxInput, OutputPin, Sdcs, SpiBus, Status, Wait,
|
||||
};
|
||||
use embassy_time::{Delay, Duration, Timer};
|
||||
use executor::Spawner;
|
||||
use stm32::dma::NoDma;
|
||||
use stm32::exti::ExtiInput;
|
||||
use stm32::gpio::{Input, Level, Output, Pull, Speed};
|
||||
use stm32::spi::Spi;
|
||||
use stm32::time::Hertz;
|
||||
use stm32::{pac, spi};
|
||||
|
||||
use uom::si::electric_potential::volt;
|
||||
use uom::si::f32;
|
||||
|
||||
use defmt::{debug, error, info, trace, unwrap};
|
||||
use embassy_executor::_export::StaticCell;
|
||||
use embassy_stm32::peripherals::{EXTI6, PF6, PF7, SPI3};
|
||||
use embassy_sync::blocking_mutex::raw::NoopRawMutex;
|
||||
use embassy_sync::mutex::Mutex;
|
||||
use embassy_sync::pubsub::PubSubChannel;
|
||||
use physical_ads1256::standard::multiplexer::poll::{
|
||||
AutocalPoll, AutocalPollStatePub, ModInputOnly,
|
||||
};
|
||||
use physical_node::transducer::input::Poll;
|
||||
use physical_node::transducer::{Publish, Publisher, StatefulPublisher};
|
||||
|
||||
const AUTOCAL_CONF: Config = Config {
|
||||
status: Status::setting(Buffer::Enabled, AutoCal::Enabled, BitOrder::MostSigFirst),
|
||||
multiplexer: Multiplexer::setting(MuxInput::AIn0, MuxInput::Common),
|
||||
ad_control: AdControl::setting(Gain::X2, Sdcs::Off, ClockOut::Off),
|
||||
data_rate: DataRate::Sps2_5,
|
||||
digital_io: DigitalIo::setting(DigitalIoState::default(), DigitalIoDirection::default()),
|
||||
};
|
||||
|
||||
struct Ads1256Delay;
|
||||
|
||||
impl ads1256::BlockingDelay for Ads1256Delay {
|
||||
#[inline]
|
||||
fn t6_delay(&mut self) {
|
||||
Delay.delay_us(1u32);
|
||||
}
|
||||
|
||||
fn t11_1_delay(&mut self) {}
|
||||
|
||||
fn t11_2_delay(&mut self) {}
|
||||
}
|
||||
|
||||
type ExampleInput = AutocalPollStatePub<
|
||||
'static,
|
||||
NoopRawMutex,
|
||||
NoopRawMutex,
|
||||
ModInputOnly,
|
||||
Ads1256Delay,
|
||||
Output<'static, PF7>,
|
||||
ExtiInput<'static, PF6>,
|
||||
Spi<'static, SPI3, NoDma, NoDma>,
|
||||
10,
|
||||
1,
|
||||
>;
|
||||
|
||||
struct Inputs {
|
||||
ai1: ExampleInput,
|
||||
ai2: ExampleInput,
|
||||
ai3: ExampleInput,
|
||||
}
|
||||
|
||||
// Inputs
|
||||
static ANALOG_INPUTS: StaticCell<Inputs> = StaticCell::new();
|
||||
static ADS_1256: StaticCell<
|
||||
Mutex<NoopRawMutex, Ads1256<Ads1256Delay, Output<PF7>, ExtiInput<PF6>>>,
|
||||
> = StaticCell::new();
|
||||
static SPI: StaticCell<Mutex<NoopRawMutex, Spi<SPI3, NoDma, NoDma>>> = StaticCell::new();
|
||||
|
||||
#[embassy_executor::main]
|
||||
async fn main(spawner: Spawner) {
|
||||
unsafe {
|
||||
pac::FLASH.acr().modify(|v| {
|
||||
v.set_prften(true);
|
||||
v.set_icen(true);
|
||||
v.set_dcen(true);
|
||||
});
|
||||
}
|
||||
|
||||
let p = embassy_stm32::init(Default::default());
|
||||
|
||||
let mut spi_conf = spi::Config::default();
|
||||
spi_conf.mode = spi::MODE_1;
|
||||
spi_conf.bit_order = spi::BitOrder::MsbFirst;
|
||||
|
||||
let ads1256_data_ready = ExtiInput::new(Input::new(p.PF6, Pull::Up), p.EXTI6);
|
||||
let select_ads1256 = Output::new(p.PF7, Level::High, Speed::VeryHigh);
|
||||
|
||||
let spi = SPI.init(Mutex::new(Spi::new(
|
||||
p.SPI3,
|
||||
p.PC10,
|
||||
p.PC12,
|
||||
p.PC11,
|
||||
NoDma,
|
||||
NoDma,
|
||||
Hertz(ads1256::defaults::SPI_CLK_HZ),
|
||||
spi_conf,
|
||||
)));
|
||||
|
||||
let ads_1256 =
|
||||
ADS_1256.init(Mutex::new(Ads1256::new(Ads1256Delay, select_ads1256, ads1256_data_ready)));
|
||||
|
||||
ads_1256
|
||||
.get_mut()
|
||||
.write_config(spi.get_mut(), AUTOCAL_CONF)
|
||||
.unwrap();
|
||||
|
||||
let inputs = &*ANALOG_INPUTS.init(Inputs {
|
||||
ai1: AutocalPollStatePub {
|
||||
poll: AutocalPoll::new(
|
||||
ModInputOnly {
|
||||
gain: Gain::X2,
|
||||
multiplexer: SingleEnded::AIn1.into(),
|
||||
},
|
||||
ads_1256,
|
||||
spi,
|
||||
),
|
||||
publisher: PubSubChannel::new().into(),
|
||||
state: Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
},
|
||||
ai2: AutocalPollStatePub {
|
||||
poll: AutocalPoll::new(
|
||||
ModInputOnly {
|
||||
gain: Gain::X2,
|
||||
multiplexer: SingleEnded::AIn2.into(),
|
||||
},
|
||||
ads_1256,
|
||||
spi,
|
||||
),
|
||||
publisher: PubSubChannel::new().into(),
|
||||
state: Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
},
|
||||
ai3: AutocalPollStatePub {
|
||||
poll: AutocalPoll::new(
|
||||
ModInputOnly {
|
||||
gain: Gain::X2,
|
||||
multiplexer: SingleEnded::AIn3.into(),
|
||||
},
|
||||
ads_1256,
|
||||
spi,
|
||||
),
|
||||
publisher: PubSubChannel::new().into(),
|
||||
state: Cell::new(f32::ElectricPotential::new::<volt>(f32::NAN)).into(),
|
||||
},
|
||||
});
|
||||
spawner.spawn(log_task(&inputs.ai1, 1)).unwrap();
|
||||
spawner.spawn(log_task(&inputs.ai2, 2)).unwrap();
|
||||
spawner.spawn(log_task(&inputs.ai3, 3)).unwrap();
|
||||
spawner
|
||||
.spawn(poll_task(&inputs.ai1, 1, Duration::from_secs(5)))
|
||||
.unwrap();
|
||||
spawner
|
||||
.spawn(poll_task(&inputs.ai2, 2, Duration::from_secs(10)))
|
||||
.unwrap();
|
||||
spawner
|
||||
.spawn(poll_task(&inputs.ai3, 3, Duration::from_secs(20)))
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
#[embassy_executor::task(pool_size = 3)]
|
||||
async fn poll_task(input: &'static ExampleInput, input_num: u8, every: Duration) {
|
||||
loop {
|
||||
Timer::after(every).await;
|
||||
let result = input.poll().await.unwrap().get::<volt>();
|
||||
info!("ai{} poll result: {} volts", input_num, result);
|
||||
}
|
||||
}
|
||||
|
||||
#[embassy_executor::task(pool_size = 3)]
|
||||
async fn log_task(input: &'static ExampleInput, input_num: u8) {
|
||||
let mut subscriber = input.subscribe().unwrap();
|
||||
loop {
|
||||
let msg = subscriber.next_message_pure().await.get::<volt>();
|
||||
info!("Log task ai{}: {}", input_num, msg);
|
||||
}
|
||||
}
|
126
examples/ads1256/src/bin/thermocouple.rs
Normal file
126
examples/ads1256/src/bin/thermocouple.rs
Normal file
@ -0,0 +1,126 @@
|
||||
#![no_std]
|
||||
#![no_main]
|
||||
#![feature(type_alias_impl_trait, async_fn_in_trait)]
|
||||
|
||||
use core::cell::Cell;
|
||||
use cortex_m::prelude::{
|
||||
_embedded_hal_blocking_delay_DelayMs, _embedded_hal_blocking_delay_DelayUs,
|
||||
};
|
||||
use {defmt_rtt as _, panic_probe as _};
|
||||
|
||||
use {embassy_executor as executor, embassy_stm32 as stm32};
|
||||
|
||||
use ads1256::standard::input::{Differential, SingleEnded};
|
||||
use ads1256::{
|
||||
AdControl, Ads1256, AutoCal, BitOrder, BlockingDelay, Buffer, ClockOut, Config, DState,
|
||||
DataRate, DigitalIo, DigitalIoDirection, DigitalIoState, DioDirection, Gain, Multiplexer,
|
||||
MuxInput, OutputPin, Sdcs, SpiBus, Status, Wait,
|
||||
};
|
||||
use embassy_time::{Delay, Duration, Timer};
|
||||
use executor::Spawner;
|
||||
use stm32::dma::NoDma;
|
||||
use stm32::exti::ExtiInput;
|
||||
use stm32::gpio::{Input, Level, Output, Pull, Speed};
|
||||
use stm32::spi::Spi;
|
||||
use stm32::time::Hertz;
|
||||
use stm32::{pac, spi};
|
||||
|
||||
use uom::si::electric_potential::{millivolt, volt};
|
||||
use uom::si::f32;
|
||||
|
||||
use defmt::{debug, error, info, trace, unwrap};
|
||||
use physical::transducer::{lm35, thermocouple_k};
|
||||
use uom::si::thermodynamic_temperature::degree_celsius;
|
||||
|
||||
const AUTOCAL_CONF: Config = Config {
|
||||
status: Status::setting(Buffer::Enabled, AutoCal::Enabled, BitOrder::MostSigFirst),
|
||||
multiplexer: Multiplexer::setting(MuxInput::AIn0, MuxInput::AIn1),
|
||||
ad_control: AdControl::setting(Gain::X64, Sdcs::Off, ClockOut::Off),
|
||||
data_rate: DataRate::Sps2_5,
|
||||
digital_io: DigitalIo::setting(DigitalIoState::default(), DigitalIoDirection::default()),
|
||||
};
|
||||
|
||||
struct Ads1256Delay;
|
||||
|
||||
impl ads1256::BlockingDelay for Ads1256Delay {
|
||||
#[inline]
|
||||
fn t6_delay(&mut self) {
|
||||
Delay.delay_us(1u32);
|
||||
}
|
||||
|
||||
fn t11_1_delay(&mut self) {}
|
||||
|
||||
fn t11_2_delay(&mut self) {}
|
||||
}
|
||||
|
||||
#[embassy_executor::main]
|
||||
async fn main(spawner: Spawner) {
|
||||
unsafe {
|
||||
pac::FLASH.acr().modify(|v| {
|
||||
v.set_prften(true);
|
||||
v.set_icen(true);
|
||||
v.set_dcen(true);
|
||||
});
|
||||
}
|
||||
|
||||
let p = embassy_stm32::init(Default::default());
|
||||
|
||||
let mut spi_conf = spi::Config::default();
|
||||
spi_conf.mode = spi::MODE_1;
|
||||
spi_conf.bit_order = spi::BitOrder::MsbFirst;
|
||||
|
||||
let ads1256_data_ready = ExtiInput::new(Input::new(p.PF6, Pull::Up), p.EXTI6);
|
||||
let select_ads1256 = Output::new(p.PF7, Level::High, Speed::VeryHigh);
|
||||
|
||||
let mut spi = Spi::new(
|
||||
p.SPI3,
|
||||
p.PC10,
|
||||
p.PC12,
|
||||
p.PC11,
|
||||
NoDma,
|
||||
NoDma,
|
||||
Hertz(ads1256::defaults::SPI_CLK_HZ),
|
||||
spi_conf,
|
||||
);
|
||||
|
||||
let mut ads_1256 = Ads1256::new(Ads1256Delay, select_ads1256, ads1256_data_ready);
|
||||
ads_1256.write_config(&mut spi, AUTOCAL_CONF).unwrap();
|
||||
ads_1256.self_calibrate(&mut spi).await.unwrap();
|
||||
|
||||
loop {
|
||||
let gain = Gain::X4;
|
||||
let reference = ads_1256
|
||||
.autocal_convert(
|
||||
&mut spi,
|
||||
SingleEnded::AIn2.into(),
|
||||
None,
|
||||
Some(AUTOCAL_CONF.ad_control.with_gain(gain)),
|
||||
None,
|
||||
false,
|
||||
)
|
||||
.await
|
||||
.unwrap()
|
||||
.to_voltage(gain);
|
||||
let reference = lm35::convert(reference).unwrap();
|
||||
let reference_celsius = reference.get::<degree_celsius>();
|
||||
info!("Reference junction temperature: {}°C", reference_celsius);
|
||||
|
||||
let gain = Gain::X64;
|
||||
let voltage = ads_1256
|
||||
.autocal_convert(
|
||||
&mut spi,
|
||||
Differential::AIn0.into(),
|
||||
None,
|
||||
Some(AUTOCAL_CONF.ad_control.with_gain(gain)),
|
||||
None,
|
||||
false,
|
||||
)
|
||||
.await
|
||||
.unwrap()
|
||||
.to_voltage(AUTOCAL_CONF.ad_control.gain());
|
||||
let mv = voltage.get::<millivolt>();
|
||||
let temperature = thermocouple_k::convert_direct(voltage, reference).unwrap();
|
||||
let celsius = temperature.get::<degree_celsius>();
|
||||
info!("Thermocouple temperature: {}°C, millivolts: {}", celsius, mv);
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user