Skip to content
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

[QUESTION] How to deal with RP2040-E4 #381

Open
shreeve opened this issue Feb 22, 2024 · 2 comments
Open

[QUESTION] How to deal with RP2040-E4 #381

shreeve opened this issue Feb 22, 2024 · 2 comments
Labels
question Further information is requested rp2040 Concerning the RP2040 chip

Comments

@shreeve
Copy link

shreeve commented Feb 22, 2024

When double-buffering isn't needed for USB Host support, then the RP2040-E4 errata issue arises where:

The USB host controller has a bug (RP2040-E4) that means the status written back to the buffer control register can appear in the wrong half of the register. Bits 0-15 are for buffer 0, and bits 16-31 are for buffer 1. The host controller has a buffer selector that is flipped after each transfer is complete. This buffer selector is incorrectly used when writing status information back to the buffer control register even in single buffered mode. The buffer selector is not used when reading the buffer control register. The implication of this is that host software needs to keep track of the buffer selector and shift the buffer control register to the right by 16 bits if the buffer selector is 1.

Another description in the datasheet says:

The USB host maintains a buffer selector which switches between BUF0 and BUF1. This should only be toggled in double buffered mode but is toggled in single buffered mode too. For a transaction lasting multiple packets (i.e. length more than 8 bytes in low speed mode, and length more than 64 bytes in full speed mode), the buffer status can be written back to the BUF1 half of the status register when the buffer select is incorrectly set to BUF1. Note this does not affect reading new buffer information from the buffer control register, as the controller ignores the buffer selector in single buffered mode when reading the buffer control register.

And, the workaround is stated as:

Shift endpoint control register to the right by 16 bits if the buffer selector is BUF1. You can use BUFF_CPU_SHOULD_HANDLE find the value of the buffer selector when the buffer was marked as done.

Even with the above, which I'm sure was not easy to discover nor document, I'm still not 100% certain on the problem or the workaround. Is this basically saying:

The USB controller can incorrectly write to the upper half (bits 16-31) of the buffer control register, even in single-buffered mode. To work around this issue, suppose bit 3 of BUFF_STATUS has been set, indicating that the buffer for the EP1_OUT endpoint needs attention. When reading the buffer control register for this endpoint, you would shift its value 16 bits to the right if bit 3 of BUFF_CPU_SHOULD_HANDLE is set.

Is this description correct?

@shreeve
Copy link
Author

shreeve commented Feb 29, 2024

Here's a simple workaround in code:

// Fix RP2040-E4 by shifting buffer control register for affected buffers (only EPX)
uint32_t bcr  = usbh_dpram->epx_buf_ctrl;           // Buffer control register (might be corrupt)
uint32_t ecr  = usbh_dpram->epx_ctrl;               // Endpoint control register
bool     dbl  = ecr & EP_CTRL_DOUBLE_BUFFERED_BITS; // EPX double buffered
if (!dbl && (usb_hw->buf_cpu_should_handle & 1u)) { // Fix EPX (int EPs are only single buffered)
    bcr >>= 16;
}

@aallan aallan added question Further information is requested rp2040 Concerning the RP2040 chip labels Feb 29, 2024
@lessSleep
Copy link

code in
static struct hw_endpoint *_hw_endpoint_allocate(uint8_t transfer_type) ?
I am full of gratitude for what you did.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
question Further information is requested rp2040 Concerning the RP2040 chip
Projects
None yet
Development

No branches or pull requests

3 participants