-
Notifications
You must be signed in to change notification settings - Fork 37
Reworked blocking i2c slave interface #389
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
base: main
Are you sure you want to change the base?
Reworked blocking i2c slave interface #389
Conversation
|
This is only the rewrite of the blocking interface. If this design is considered reasonable I can extend it to the async side and actually do the support around automatic address ack/nack. The choice for separate types for the blocking and async slave interfaces is that both will need different code to run on drop, which cannot be done another way because of restrictions on Drop implementations. |
b99d4a3 to
f60674d
Compare
tdittr
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
A few thoughts for now, going to finish the review next week.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In general I think we should improve the granularity of the returned errors to make debugging easier.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
All these errors are essentially identical (bus is in a strange state), so there isn't really anything to separate them.
tdittr
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like the new API, however it does feel a bit rough around the edges.
Should we maybe implement the async version and improve the documentation before merging?
| i2c.stat().write(|w| w.slvdesel().deselected()); | ||
| return Ok(Response::Complete(xfer_count)); | ||
| // inhibit drop | ||
| core::mem::forget(self); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nit-pick: I would replace with a destructuring assignment.
| core::mem::forget(self); | |
| let BlockingI2cSlaveWrite{..} = self; |
Or alternatively have a Self::defuse method.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I like this example for showing a real-world use-case 👍
jerrysxie
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@davidv1992 Still going through the review, just one question about the overall goals and next steps:
- For all the ODP I2C slave HALs, the plan is to have a HW agnostic traits interface to be implemented by both
embassy-imxrtandembassy-npcx, is this a step toward that direction? The I2C traits are eventually to be upstreamed to embedded-hal, but meanwhile we should probably have it as a independent crate in ODP until the upstreaming can happen. - We do have some clients that relies on this i2c slave interface already. Merging this will require a bit coordination.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Copilot reviewed 5 out of 5 changed files in this pull request and generated no comments.
|
@jerrysxie Yes, this is aimed to be a step in that direction. The exact shape of a hardware agnostic trait is still in the design phase, but something along these lines is what we are trending towards. The main pain points right now (though those are less relevant for the two crates you mention) is that some hardware has quite limited i2c slave support. As for this requiring some coordination to merge, that is not entirely unexpected. My main goal at this stage is to gather feedback on the overall shape of the design in preparation for doing the same reworking of the interface in the async case. So far, reactions seem positive, but if on your end you feel different about it it would be nice to catch that before I have sunk a bunch of work into the async version, as it's likely going to be somewhat more complicated to implement. |
98f39fd to
32cfbe2
Compare
2f7a2e6 to
77854a9
Compare
Hi, @davidv1992! One more question regarding the plan to |
67618e8 to
d240c12
Compare
@jerrysxie Sorry for the late response, missed this before my vacation. Yes there is some mess here, and there is a lot of complications due to potential race conditions between the software and the hardware, but the way I manage it currently is by having the rest of the code more streamlined so that the expectation doesn't match scenario becomes less of an alternate path. I am still in the process of cleaning up the code, but everything is implemented right now. |
044a9e0 to
c351e90
Compare
f08aef0 to
e84bb4f
Compare
Cargo Vet Audit Passed
|
|
@jerrysxie the CI fails, but this seems to be an issue with the setup of the pipeline, not the code. Would it be possible for you to look into this? |
f404fa7 to
bc756a7
Compare
|
@JamesHuard , @felipebalbi , @RobertZ2011 can you guys please review and provide feedback? Thanks. |
Main motivators are: - More consistent interface that is better misuse resistant. - Easier to extend with support for Automatic Ack/Nack of addresses in async variant. - Better support for cancelation and capable of better surfacing what the hardware can actually do. The code changes also fixes some issues in 10-bit addressing. It should now match the behaviour specified in UM10204
This is done through the expect_read and expect_write interfaces, as automatic acknowledgement requires the dma to be in place beforehand.
This register contains both write-to-trigger bits and bits that represent semi-permanent state. This commit ensures we don't accidentaly write 1s to the write-to-trigger bits, as the hardware doesn't clear these automatically.
bc756a7 to
8cfc384
Compare
|
@jeffglaum You have assigned this one back to me, but it is unclear what is required from me at this point. Could you clarify that? |
felipebalbi
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I didn't attempt to run the examples yet, but the code looks easy enough to read. Since you're using auto-ack, did you manage to quantify any changes to bus utilization?
| } | ||
| } | ||
|
|
||
| impl<'a> I2cSlave<'a, Blocking> { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just curious: why remove the Mode type parameter here?
Just assigning to you, to complete the PR (looks like there are still open discussion points which are blocking the merge). Thanks. |
|
@davidv1992 are you intending to complete this PR (looks like it had approvals) or to abandon? Thanks. |


Main motivators are:
The code changes also fixes some issues in 10-bit addressing. It should now match the behaviour specified in UM10204