|
3 | 3 | #[cfg(not(feature = "std"))] |
4 | 4 | use alloc::{boxed::Box, vec}; |
5 | 5 | use core::convert::TryFrom; |
| 6 | +use core::fmt; |
6 | 7 |
|
7 | 8 | use crate::{Access, Error, Spi, SpiTarget}; |
8 | 9 |
|
@@ -31,6 +32,8 @@ enum Cmd { |
31 | 32 | SetNoInput = 19, |
32 | 33 | SecurityGet = 20, |
33 | 34 | SecuritySet = 21, |
| 35 | + FanGetMode = 22, |
| 36 | + FanSetMode = 23, |
34 | 37 | } |
35 | 38 |
|
36 | 39 | const CMD_SPI_FLAG_READ: u8 = 1 << 0; |
@@ -65,6 +68,42 @@ impl TryFrom<u8> for SecurityState { |
65 | 68 | } |
66 | 69 | } |
67 | 70 |
|
| 71 | +#[derive(Clone, Copy, Default, Debug, Eq, PartialEq)] |
| 72 | +#[cfg_attr(feature = "std", derive(clap::ValueEnum))] |
| 73 | +#[repr(u8)] |
| 74 | +pub enum FanMode { |
| 75 | + /// EC control |
| 76 | + #[default] |
| 77 | + Auto = 0, |
| 78 | + /// Host control via target PWM |
| 79 | + Pwm = 1, |
| 80 | + /// Host control via target RPM |
| 81 | + Rpm = 2, |
| 82 | +} |
| 83 | + |
| 84 | +impl fmt::Display for FanMode { |
| 85 | + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { |
| 86 | + match self { |
| 87 | + Self::Auto => write!(f, "auto"), |
| 88 | + Self::Pwm => write!(f, "pwm"), |
| 89 | + Self::Rpm => write!(f, "rpm"), |
| 90 | + } |
| 91 | + } |
| 92 | +} |
| 93 | + |
| 94 | +impl TryFrom<u8> for FanMode { |
| 95 | + type Error = Error; |
| 96 | + |
| 97 | + fn try_from(value: u8) -> Result<Self, Self::Error> { |
| 98 | + match value { |
| 99 | + 0 => Ok(Self::Auto), |
| 100 | + 1 => Ok(Self::Pwm), |
| 101 | + 2 => Ok(Self::Rpm), |
| 102 | + _ => Err(Error::Verify), |
| 103 | + } |
| 104 | + } |
| 105 | +} |
| 106 | + |
68 | 107 | /// Run EC commands using a provided access method |
69 | 108 | pub struct Ec<A: Access> { |
70 | 109 | access: A, |
@@ -275,6 +314,19 @@ impl<A: Access> Ec<A> { |
275 | 314 | self.command(Cmd::SecuritySet, &mut data) |
276 | 315 | } |
277 | 316 |
|
| 317 | + /// Get fan control mode. |
| 318 | + pub unsafe fn fan_get_mode(&mut self) -> Result<FanMode, Error> { |
| 319 | + let mut data = [0]; |
| 320 | + self.command(Cmd::FanGetMode, &mut data)?; |
| 321 | + FanMode::try_from(data[0]) |
| 322 | + } |
| 323 | + |
| 324 | + /// Set fan control mode. |
| 325 | + pub unsafe fn fan_set_mode(&mut self, mode: FanMode) -> Result<(), Error> { |
| 326 | + let mut data = [mode as u8]; |
| 327 | + self.command(Cmd::FanSetMode, &mut data) |
| 328 | + } |
| 329 | + |
278 | 330 | pub fn into_dyn(self) -> Ec<Box<dyn Access>> |
279 | 331 | where |
280 | 332 | A: 'static, |
|
0 commit comments