-
Notifications
You must be signed in to change notification settings - Fork 1
Fixes response and data block for CMD17 and CMD18 #2
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: bisync
Are you sure you want to change the base?
Conversation
src/inner/sdcard/mod.rs
Outdated
// http://elm-chan.org/docs/mmc/mmc_e.html | ||
const MAX_WAIT_BYTES: usize = 8; | ||
const TRANSFER_BYTES: usize = COMMAND_BYTES + MAX_WAIT_BYTES + COMMAND_RESPONSE_BYTES; | ||
|
||
let mut buf = [0xFF; TRANSFER_BYTES]; | ||
let mut buf: [u8; 19] = [0xFF; TRANSFER_BYTES]; |
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.
Magic number
(Some(res), _) => Ok(res), | ||
(None, CMD17 | CMD18) => { | ||
for _retry in 0..8 - 2 { | ||
let ret = self.read_byte().await?; |
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.
Would it be possible to do another multi-byte read here instead of reading one at a time?
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.
According to the specification, the timing of a read operation is
| cmd | Ncr | resp | Nac | data blk |
where (unless otherwise specified, the unit is 8 clock cycles)
- Ncr = 1..8
- Nac = 1..100ms (see 4.6.2.1)
In the case of a fast response, we therefore have
| cmd | 0xFF | R1 | 0xFF | Start |
For the slow case
| cmd | 8 * 0xFF | R1 | n * 0xFF | Start | // where n is the equivalent of 100ms
If we read more bytes, the start
may be included. We could optimize by reading two bytes at a time because Nac is at least one.
In my tests, the SDHC responded quickly, so it's not a problem.
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.
The problem is that the single byte reads can reintroduce the problem I fixed in #1. If the task gets stalled between sending the command and reading the respons then the card can run into some sort of timeout and the whole command can fail. I'm a little shirt on time right now so I don't know if that's a problem with this specific command but it would be a good edge case to check.
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 ran some timeout tests (see here: https://github.com/marcfir/sd_timout_test/blob/b3a18608a5a11f2832cabde6d4463c661d276789/src/bin/main.rs#L68-L86), and everything looks fine.
I used an ESP32S3 and two different SDHC microSD cards.
I could not reproduce your problem with CMD13 in the write function, too.
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 previously created this reproducer for the write error problem. The key is that there are multiple tasks that compete for bus access.
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 tested your reproducer and was able to reproduce the errors.
Using your commit, 835b2e4, removed the errors.
I extended your example to read a large file in the same loop. I did not encounter any errors.
So, where is the ReadError that I encountered previously?
I experimented with the SPI frequency, and at 400 kHz, I received a DeviceError(ReadError) for open_volume.
At this point, I switched to my PR, and the DeviceError(ReadError) disappeared for 400 kHz as well as 25 MHz.
Using a logic analyzer, I analyzed the CMD17 with SPI at 10 MHz, and I saw only one 0xFF between CMD17 and R1, which indicates that the R1 comes within https://github.com/marcfir/embedded-sdmmc-rs/blob/1add59b16a9af841794cdfedfc98333cf1f8174e/src/inner/sdcard/mod.rs#L548. I added a log to https://github.com/marcfir/embedded-sdmmc-rs/blob/1add59b16a9af841794cdfedfc98333cf1f8174e/src/inner/sdcard/mod.rs#L569, but it never fired, even when I used 25 MHz.
Without the fix, I get a
DeviceError(ReadError)
because CMD17 does not detect a start block