Skip to main content

I2cBus

Struct I2cBus 

Source
pub struct I2cBus { /* private fields */ }
Expand description

One I2C bus, reached by every clone of this handle.

§Examples

use pamoja_hal::bus::{BusKind, I2cBus};
use pamoja_hal::i2c::I2c;
use pamoja_hal::script::{I2cScript, I2cStep};

// A script of one register read, a BME280 answering its chip id, and a driver that
// makes it.
const BME280: u8 = 0x76;
const CHIP_ID_REGISTER: u8 = 0xD0;
const BME280_CHIP_ID: u8 = 0x60;
let bus = I2cBus::scripted(I2cScript::new([I2cStep::write_read(
    BME280,
    [CHIP_ID_REGISTER],
    [BME280_CHIP_ID],
)]));
let mut driver = bus.clone();
let mut id = [0u8; 1];
driver.write_read(BME280, &[CHIP_ID_REGISTER], &mut id)?;

assert_eq!(bus.kind(), BusKind::Scripted);
assert_eq!(bus.remaining(), Some(0), "the script has been played through");

Implementations§

Source§

impl I2cBus

Source

pub fn open(path: impl AsRef<Path>) -> Result<I2cBus, OpenError>

Opens the kernel’s I2C adapter, such as /dev/i2c-1 on a Raspberry Pi.

§Arguments
  • path - the adapter’s device file.
§Returns

The bus, with the real parts wired to it on the other end.

§Errors

OpenError::Unsupported anywhere but Linux, or in a build without the linux feature, and OpenError::Adapter when the file cannot be opened as an adapter: the interface is not turned on, or the process may not use it.

§Examples
use pamoja_hal::bus::I2cBus;

let bus = I2cBus::open("/dev/i2c-1")?;
Source

pub fn simulated<P: Into<Part>>(parts: impl IntoIterator<Item = P>) -> I2cBus

A bus of simulated parts, each answering at its own address.

§Arguments
  • parts - the parts on the bus, of any of the three kinds, put on in order as I2cBus::attach puts them, so a part at an address an earlier one holds takes its place.
§Returns

The bus. A transfer to an address no part holds fails with BusError::NoAcknowledge.

Source

pub fn attach( &self, part: impl Into<Part>, ) -> Result<Option<Part>, NotSimulated>

Puts a simulated part on the bus, in place of any part already at its address.

A driver keeps working across the change, which is how a test moves a reading on: a part built to report different values takes the old one’s place.

§Arguments
  • part - the part, of any of the three kinds.
§Returns

The part it replaced, or None when the address was free.

§Errors

NotSimulated when the bus is the kernel’s adapter or a script.

Source

pub fn scripted(script: I2cScript) -> I2cBus

A bus that plays one conversation and refuses any other.

§Arguments
  • script - the transfers a driver is expected to make, in order, and the replies.
§Returns

The bus. A transfer that does not match the next step fails with BusError::Script and consumes nothing.

Source

pub fn kind(&self) -> BusKind

What answers on the bus.

§Returns

The kind of bus.

Source

pub fn part<P: FromPart>(&self, address: u8) -> Option<P>

What a simulated part holds now, as the kind of part the caller names.

§Arguments
  • address - the part’s address.
§Returns

A copy of the part, with whatever drivers have written to it, or None when the bus is not simulated, no part holds the address, or the part there is another kind. Ask for a Part to take any kind.

§Examples
use pamoja_hal::bus::I2cBus;
use pamoja_hal::i2c::I2c;
use pamoja_hal::sim::{I2cPart, WordPart};

// A driver asks a BME280 for one forced measurement: ctrl_meas takes one temperature
// sample, one pressure sample, and forced mode, in its three fields.
const BME280: u8 = 0x76;
const CTRL_MEAS: u8 = 0xF4;
const FORCED_ONCE: u8 = 0b001_001_01;
let mut bus = I2cBus::simulated([I2cPart::new(BME280)]);
bus.write(BME280, &[CTRL_MEAS, FORCED_ONCE])?;

// The program looks at what the driver left in the part.
let part: I2cPart = bus.part(BME280).expect("a byte-wide part");
assert_eq!(part.register(CTRL_MEAS), FORCED_ONCE);
assert!(bus.part::<WordPart>(BME280).is_none(), "it is not a word-wide one");
Source

pub fn transfers(&self) -> usize

How many transfers have been made on the bus, by every clone, including any that failed.

§Returns

The count, one per transaction however many operations it held.

Source

pub fn remaining(&self) -> Option<usize>

How many steps a script has left.

§Returns

The steps not yet reached, Some(0) once a driver has made every transfer the script expected, or None when the bus is not scripted.

Source

pub fn waited_micros(&self) -> u64

How long the drivers on the bus have asked to wait, through I2cBus::delay.

§Returns

The total in microseconds, counted whether or not the process slept through it.

Source

pub fn delay(&self) -> BusDelay

The delay a driver on this bus waits with.

§Returns

A delay that sleeps the process when the bus is the kernel’s adapter, returns at once when it is simulated or scripted, and adds every wait to I2cBus::waited_micros.

Trait Implementations§

Source§

impl Clone for I2cBus

Source§

fn clone(&self) -> I2cBus

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl Debug for I2cBus

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl ErrorType for I2cBus

Source§

type Error = BusError

Error type
Source§

impl I2c for I2cBus

Source§

fn transaction( &mut self, address: SevenBitAddress, operations: &mut [Operation<'_>], ) -> Result<(), BusError>

Execute the provided operations on the I2C bus. Read more
§

fn read(&mut self, address: A, read: &mut [u8]) -> Result<(), Self::Error>

Reads enough bytes from slave with address to fill read. Read more
§

fn write(&mut self, address: A, write: &[u8]) -> Result<(), Self::Error>

Writes bytes to slave with address address. Read more
§

fn write_read( &mut self, address: A, write: &[u8], read: &mut [u8], ) -> Result<(), Self::Error>

Writes bytes to slave with address address and then reads enough bytes to fill read in a single transaction. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.