Nareshkumar Rao 7 months ago
parent
commit
6804acd6e2
  1. 8
      Cargo.lock
  2. 3
      Cargo.toml
  3. 30
      src/dht11.rs
  4. 39
      src/main.rs

8
Cargo.lock

@ -36,6 +36,13 @@ version = "0.2.153"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9c198f91728a82281a64e1f4f9eeb25d82cb32a5de251c6bd1b5154d63a8e7bd"
[[package]]
name = "linux_realtime"
version = "0.1.0"
dependencies = [
"libc",
]
[[package]]
name = "nix"
version = "0.28.0"
@ -54,6 +61,7 @@ version = "0.1.0"
dependencies = [
"interrupts",
"libc",
"linux_realtime",
"rppal",
]

3
Cargo.toml

@ -10,3 +10,6 @@ rppal = "0.17.1"
#rumqttc = "0.24.0"
interrupts = "0.1.5"
libc = "0.2.153"
[dependencies.linux_realtime]
path = "../linux_realtime"

30
src/dht11.rs

@ -1,8 +1,4 @@
use std::{
error::Error,
thread,
time::{Duration, Instant},
};
use std::{error::Error, time::Duration};
use rppal::gpio::Gpio;
@ -19,45 +15,47 @@ impl Dht11Sensor {
Ok(Dht11Sensor { pin })
}
fn expect_pulse(&mut self, expected_level: bool) -> Result<Duration, Box<dyn Error>> {
let started = Instant::now();
fn expect_pulse(&mut self, expected_level: bool) -> Result<u32, Box<dyn Error>> {
let _guard = interrupts::disable();
let mut count: u32 = 0;
let mut rtclock = linux_realtime::Clock::new()?;
loop {
if self.pin.is_high() != expected_level {
break;
}
if started.elapsed() >= Duration::from_micros(1000) {
if count >= 1000 {
return Err(std::io::Error::new(
std::io::ErrorKind::InvalidData,
"Timeout while reading pulse",
)
.into());
}
thread::sleep(Duration::from_micros(1));
count += 1;
rtclock.sleep(Duration::from_micros(1))?;
}
Ok(started.elapsed())
Ok(count)
}
pub fn read(&mut self) -> Result<Dht11Data, Box<dyn Error>> {
use rppal::gpio::{Bias, Mode};
let mut data = [0; 5];
let mut cycles: [Duration; 80] = [Duration::from_micros(0); 80];
let mut cycles: [u32; 80] = [0; 80];
let guard = interrupts::disable();
let mut rtclock = linux_realtime::Clock::new()?;
self.pin.set_mode(Mode::Input);
self.pin.set_bias(Bias::PullUp);
thread::sleep(Duration::from_millis(1));
rtclock.sleep(Duration::from_millis(1))?;
self.pin.set_mode(Mode::Output);
self.pin.set_low();
thread::sleep(Duration::from_millis(20));
rtclock.sleep(Duration::from_millis(20))?;
// Timing Critical Code
self.pin.set_mode(Mode::Input);
self.pin.set_bias(Bias::PullUp);
thread::sleep(Duration::from_micros(55));
rtclock.sleep(Duration::from_micros(55))?;
self.expect_pulse(false)?;
self.expect_pulse(true)?;

39
src/main.rs

@ -1,24 +1,35 @@
use std::{error::Error, thread, time::Duration};
use std::{error::Error, time::Duration};
use dht11::Dht11Sensor;
use linux_realtime::ThreadAttributes;
mod dht11;
fn main() -> Result<(), Box<dyn Error>> {
unsafe {
libc::setpriority(libc::PRIO_PROCESS, 0, -20);
}
let mut sensor = Dht11Sensor::new(2)?;
loop {
match sensor.read() {
Ok(data) => println!(
"Humidity: {}; Temperature: {}",
data.humidity, data.temperature
),
Err(msg) => println!("Error: {}", msg),
}
thread::sleep(Duration::from_millis(2000));
}
let t = linux_realtime::JoinHandle::spawn(
ThreadAttributes {
stack_size: libc::PTHREAD_STACK_MIN,
scheduler_policy: linux_realtime::SchedulerPolicy::Fifo,
thread_priority: 99,
},
move || -> Result<(), Box<dyn Error>> {
loop {
let mut rtclock = linux_realtime::Clock::new()?;
match sensor.read() {
Ok(data) => println!(
"Humidity: {}; Temperature: {}",
data.humidity, data.temperature
),
Err(msg) => println!("Error: {}", msg),
}
for n in 1..10 {
rtclock.sleep(Duration::from_millis(500))?;
}
}
},
)?;
_ = t.join();
Ok(())
}

Loading…
Cancel
Save