diff --git a/src/co2.rs b/src/co2.rs index 9190dce..0766312 100644 --- a/src/co2.rs +++ b/src/co2.rs @@ -9,6 +9,7 @@ const CCS811_I2C_ADDRESS: u16 = 0x5A; const CCS811_REGISTER_STATUS: u8 = 0x00; const CCS811_REGISTER_MEAS_MODE: u8 = 0x01; const CCS811_REGISTER_ALG_RESULT_DATA: u8 = 0x02; +const CCS811_REGISTER_ENV_DATA: u8 = 0x05; /// Bootloader I2C Register addresses of the co2 sensor const CCS811_REGISTER_BOOTLOADER_APP_START: u8 = 0xF4; @@ -69,3 +70,45 @@ pub async fn set_measurement_mode( ) -> Result<(), embassy_rp::i2c::Error> { write_register(i2c, CCS811_REGISTER_MEAS_MODE, [mode]).await } + +/// Set the ambient temperature and humidity of the measurement environment to +/// calibrate the sensor output +/// +/// The function panics for humidity values > 100% or temperatures < -25 +/// degrees Celsius. +/// +/// * `temperature` - Current temperature in milidegrees celsius +/// * `humidity` - Current humidity in per mille +pub async fn set_environment_values( + i2c: &mut I2c<'_, I2C1, Async>, + temperature: i32, + humidity: u32, +) -> Result<(), embassy_rp::i2c::Error> { + assert!(temperature >= -25000, "`temperature` was lower than -25000"); + assert!(humidity <= 1000, "`humidity` was higher than 100%"); + + // A register value of 0 maps to -25 degrees + let temperature: i32 = temperature + 25000; + // A single increment in the register maps to 1/512 degrees. + // Order of operations is relevant due to integer division + let temperature: i32 = (temperature * 512) / 1000; + + assert!( + temperature <= (u16::MAX as i32), + "temperature register value was higher than u16::MAX" + ); + let temperature: u16 = temperature + .try_into() + .expect("We checked the value in an assert already"); + + // A single increment in the register maps to 1/512%RH + let humidity: u16 = ((humidity * 512) / 1000) + .try_into() + .expect("We checked the value in an assert already"); + + let bytes = humidity + .to_be_bytes() + .into_iter() + .chain(temperature.to_ne_bytes().into_iter()); + write_register(i2c, CCS811_REGISTER_STATUS, bytes).await +} diff --git a/src/main.rs b/src/main.rs index ea58c25..dbcee04 100644 --- a/src/main.rs +++ b/src/main.rs @@ -92,6 +92,9 @@ async fn main(spawner: Spawner) { // 16 is measurement mode 1 => 1 measurement per second co2::set_measurement_mode(&mut i2c, 16).await.unwrap(); + co2::set_environment_values(&mut i2c, 25000, 660) + .await + .unwrap(); loop { let status = co2::get_status(&mut i2c).await.unwrap();