diff options
Diffstat (limited to 'usbh/src/pipe.rs')
-rw-r--r-- | usbh/src/pipe.rs | 45 |
1 files changed, 21 insertions, 24 deletions
diff --git a/usbh/src/pipe.rs b/usbh/src/pipe.rs index beac863..56acc00 100644 --- a/usbh/src/pipe.rs +++ b/usbh/src/pipe.rs @@ -96,23 +96,23 @@ pub(crate) struct Pipe<'a, 'b> { pub(crate) desc: &'a mut PipeDesc, } impl Pipe<'_, '_> { - pub(crate) fn control_req( + pub(crate) fn control_req<T>( &mut self, bm_request_type: RequestType, b_request: RequestCode, w_value: WValue, w_index: u16, - buf: Option<DataBuf>, + buf: Option<&mut T>, millis: &dyn Fn() -> usize, ) -> Result<(), PipeErr> { - if let Some(ref b) = buf { - assert!(b.ptr as usize & 0x3 == 0); - assert!(b.len <= 65_535); - } - // Pipe data toggles for control pipes defined in SAMD21 data // sheet §32.6.3.9 + let len = match buf { + None => 0, + _ => core::mem::size_of::<T>(), + }; + /* * Setup stage. */ @@ -121,10 +121,7 @@ impl Pipe<'_, '_> { b_request: b_request, w_value: w_value, w_index: w_index, - w_length: match buf { - None => 0, - Some(ref b) => b.len as u16, - }, + w_length: len as u16, }; self.dtgl_clear(); self.send( @@ -143,13 +140,11 @@ impl Pipe<'_, '_> { // per-packet chunks) to complete. cf §9.2.6.4 of USB 2.0. match bm_request_type.direction()? { RequestDirection::DeviceToHost => { - trace!("buf0: {:?}", &b); - self.in_transfer(&b, NAK_LIMIT, millis)?; - trace!("buf1: {:?}", &b); + self.in_transfer(b, NAK_LIMIT, millis)?; } RequestDirection::HostToDevice => { - debug!("Should OUT for {}b", b.len); + debug!("Should OUT for {}b", len); } } } @@ -204,18 +199,20 @@ impl Pipe<'_, '_> { self.dispatch_retries(token, nak_limit, millis) } - pub(crate) fn in_transfer( + pub(crate) fn in_transfer<T>( &mut self, - buf: &DataBuf, + buf: &mut T, nak_limit: usize, millis: &dyn Fn() -> usize, ) -> Result<(usize), PipeErr> { // TODO: pull this from pipe descriptor for this addr/ep. let packet_size = 8; - trace!("p{}: Should IN for {}b.", self.num, buf.len); + let db: DataBuf = buf.into(); + + trace!("p{}: Should IN for {}b.", self.num, db.len); self.desc.bank0.pcksize.write(|w| { - unsafe { w.byte_count().bits(buf.len as u16) }; + unsafe { w.byte_count().bits(db.len as u16) }; unsafe { w.multi_packet_size().bits(0) } }); @@ -223,18 +220,18 @@ impl Pipe<'_, '_> { // nothing left for us in this transaction) or the buffer is // full. let mut bytes_received = 0; - while bytes_received < buf.len { + while bytes_received < db.len { // Move the buffer pointer forward as we get data. self.desc .bank0 .addr - .write(|w| unsafe { w.addr().bits(buf.ptr as u32 + bytes_received as u32) }); + .write(|w| unsafe { w.addr().bits(db.ptr as u32 + bytes_received as u32) }); self.regs.statusclr.write(|w| w.bk0rdy().set_bit()); self.dispatch_retries(USBToken::In, nak_limit, millis)?; let recvd = self.desc.bank0.pcksize.read().byte_count().bits() as usize; bytes_received += recvd; - trace!("!! read {} of {}", bytes_received, buf.len); + trace!("!! read {} of {}", bytes_received, db.len); if recvd < packet_size { // If we receive a short packet, we should be done // here. It /may/ be possible to get a short packet @@ -245,12 +242,12 @@ impl Pipe<'_, '_> { } // Don't allow writing past the buffer. - assert!(bytes_received <= buf.len); + assert!(bytes_received <= db.len); } //self.dtgl(); self.regs.statusset.write(|w| w.pfreeze().set_bit()); - if bytes_received < buf.len { + if bytes_received < db.len { self.log_regs(); // TODO: honestly, this is probably a panic condition, // since whatever's in DataBuf.ptr is totally |