aboutsummaryrefslogtreecommitdiff
path: root/embassy-usb
diff options
context:
space:
mode:
authorDario Nieuwenhuis <[email protected]>2022-04-06 03:02:13 +0200
committerDario Nieuwenhuis <[email protected]>2022-04-06 05:38:11 +0200
commitf6d11dfba56b2b04868e87a14d10395e1916306d (patch)
tree74d437fdc17b3e221df52a00029bd247ff77431c /embassy-usb
parentb2e517bb2860b1ec35bb744b8a28efae50cb2d59 (diff)
usb: fix slow enumeration with EP0 max_packet_size of 8 or 16.
Diffstat (limited to 'embassy-usb')
-rw-r--r--embassy-usb/src/control.rs2
-rw-r--r--embassy-usb/src/lib.rs15
2 files changed, 15 insertions, 2 deletions
diff --git a/embassy-usb/src/control.rs b/embassy-usb/src/control.rs
index da48dccaf..b15ba4463 100644
--- a/embassy-usb/src/control.rs
+++ b/embassy-usb/src/control.rs
@@ -198,7 +198,7 @@ pub trait ControlHandler {
198#[derive(Debug)] 198#[derive(Debug)]
199#[cfg_attr(feature = "defmt", derive(defmt::Format))] 199#[cfg_attr(feature = "defmt", derive(defmt::Format))]
200pub(crate) struct DataInStage { 200pub(crate) struct DataInStage {
201 length: usize, 201 pub(crate) length: usize,
202} 202}
203 203
204/// Typestate representing a ControlPipe in the DATA OUT stage 204/// Typestate representing a ControlPipe in the DATA OUT stage
diff --git a/embassy-usb/src/lib.rs b/embassy-usb/src/lib.rs
index cf8d12539..f833a86d8 100644
--- a/embassy-usb/src/lib.rs
+++ b/embassy-usb/src/lib.rs
@@ -222,7 +222,20 @@ impl<'d, D: Driver<'d>> UsbDevice<'d, D> {
222 } 222 }
223 } 223 }
224 224
225 async fn handle_control_in(&mut self, req: Request, stage: DataInStage) { 225 async fn handle_control_in(&mut self, req: Request, mut stage: DataInStage) {
226 // If we don't have an address yet, respond with max 1 packet.
227 // The host doesn't know our EP0 max packet size yet, and might assume
228 // a full-length packet is a short packet, thinking we're done sending data.
229 // See https://github.com/hathach/tinyusb/issues/184
230 const DEVICE_DESCRIPTOR_LEN: u8 = 18;
231 if self.pending_address == 0
232 && self.config.max_packet_size_0 < DEVICE_DESCRIPTOR_LEN
233 && (self.config.max_packet_size_0 as usize) < stage.length
234 {
235 trace!("received control req while not addressed: capping response to 1 packet.");
236 stage.length = self.config.max_packet_size_0 as _;
237 }
238
226 match (req.request_type, req.recipient) { 239 match (req.request_type, req.recipient) {
227 (RequestType::Standard, Recipient::Device) => match req.request { 240 (RequestType::Standard, Recipient::Device) => match req.request {
228 Request::GET_STATUS => { 241 Request::GET_STATUS => {