Skip to content

i2c: Add target implementation #45

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 7 commits into
base: master
Choose a base branch
from
Open

i2c: Add target implementation #45

wants to merge 7 commits into from

Conversation

astapleton
Copy link
Contributor

This extends the I2C driver to support target operation. It adds an I2cTarget type to represent the I2C operation as the target.

Target operation can be operated in automatic ACKing mode, letting the hardware manage clock stretching and ACKing automatically, or it can be operated in manual ACK control mode, which lets the user of the driver determine when to ACK the end of a transaction. Manual ACK control allows for clock stretching while data is being processed or retrieved before ACK'ing the final byte of a transfer and initiating either the end of a transfer or a repeat start to read the processed/retrieved data. This implementation does not currently allow for ACKing individual or a subset of bytes manually, but extending the interface to do so can build upon what is implemented so far.

This also adds role switching to the driver, enabling both controller and target implementation through choosing the appropriate initialization functions.

The example is currently only tested on  NUCLEO-STM32H503, and uses
pins that are not available on other H5 processors. This can be
enabled on other processors by choosing different pins for the
various evaluation boards.
src/i2c.rs Outdated
Comment on lines 227 to 234
/// This encapsulates a transaction event that occurs when listening in Target
/// operation. A TargetWrite event indicates that the Controller wants to read
/// data from the Target (I2C read operation). A TargetRead event indicates
/// that the Controller wants to write data to the Target (I2C write
/// operation). A Stop event indicates that a Stop condition was received and
/// the transaction has been completed.
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum TargetEvent {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These definitions are pretty confusing. Wouldn't a TargetRead indicates that the controller wants to read data from the target?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ha. I actually had these the other way round, simply called TargetEvent::Read (controller wants to read, target must execute a write) and TargetEvent::Write (controller wants to write, target must execute a read), but I thought that was confusing, so I tried to disambiguate it by indicating that a TargetRead event is in response to controller write. Guess they're both a bit confusing, so I'll go back to the old iteration.

- Deduplicate functions shared between AutoAck and ManualAck implementations for I2cTarget
- Rename TargetEvent variants
- Fix writing buffer larger than 255 bytes in ManualAck operation
- Improved documentation
length <= u8::MAX as usize,
"I2C max transfer size per reload = {}",
u8::MAX
);
Copy link
Contributor Author

@astapleton astapleton Mar 3, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I added these bounds checks in the controller start logic because I realized that the controller implementation does not use NBYTES reloads to write buffers longer than 255 bytes, but also doesn't bounds check on repeat starts or reloads, leading to wrap around bugs on the value written to the NBYTES field and transactions that were unexpectedly short.

Created this issue to track: #46

@astapleton
Copy link
Contributor Author

@ryan-summers mind taking another look at this? I believe I've addressed everything

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants