feat(usb-otg): add support for ISO endpoints

This commit is contained in:
elagil 2024-09-05 21:29:11 +02:00
parent ccf68d7391
commit d37c482e21
2 changed files with 38 additions and 8 deletions

View File

@ -1071,6 +1071,21 @@ impl<'d> embassy_usb_driver::EndpointOut for Endpoint<'d, Out> {
w.set_pktcnt(1); w.set_pktcnt(1);
}); });
if self.info.ep_type == EndpointType::Isochronous {
// Isochronous endpoints must set the correct even/odd frame bit to
// correspond with the next frame's number.
let frame_number = self.regs.dsts().read().fnsof();
let frame_is_odd = frame_number & 0x01 == 1;
self.regs.doepctl(index).modify(|r| {
if frame_is_odd {
r.set_sd0pid_sevnfrm(true);
} else {
r.set_sd1pid_soddfrm(true);
}
});
}
// Clear NAK to indicate we are ready to receive more data // Clear NAK to indicate we are ready to receive more data
self.regs.doepctl(index).modify(|w| { self.regs.doepctl(index).modify(|w| {
w.set_cnak(true); w.set_cnak(true);
@ -1158,6 +1173,21 @@ impl<'d> embassy_usb_driver::EndpointIn for Endpoint<'d, In> {
w.set_xfrsiz(buf.len() as _); w.set_xfrsiz(buf.len() as _);
}); });
if self.info.ep_type == EndpointType::Isochronous {
// Isochronous endpoints must set the correct even/odd frame bit to
// correspond with the next frame's number.
let frame_number = self.regs.dsts().read().fnsof();
let frame_is_odd = frame_number & 0x01 == 1;
self.regs.diepctl(index).modify(|r| {
if frame_is_odd {
r.set_sd0pid_sevnfrm(true);
} else {
r.set_sd1pid_soddfrm(true);
}
});
}
// Enable endpoint // Enable endpoint
self.regs.diepctl(index).modify(|w| { self.regs.diepctl(index).modify(|w| {
w.set_cnak(true); w.set_cnak(true);

View File

@ -795,15 +795,15 @@ pub mod regs {
pub fn set_sd0pid_sevnfrm(&mut self, val: bool) { pub fn set_sd0pid_sevnfrm(&mut self, val: bool) {
self.0 = (self.0 & !(0x01 << 28usize)) | (((val as u32) & 0x01) << 28usize); self.0 = (self.0 & !(0x01 << 28usize)) | (((val as u32) & 0x01) << 28usize);
} }
#[doc = "SODDFRM/SD1PID"] #[doc = "SD1PID/SODDFRM"]
#[inline(always)] #[inline(always)]
pub const fn soddfrm_sd1pid(&self) -> bool { pub const fn sd1pid_soddfrm(&self) -> bool {
let val = (self.0 >> 29usize) & 0x01; let val = (self.0 >> 29usize) & 0x01;
val != 0 val != 0
} }
#[doc = "SODDFRM/SD1PID"] #[doc = "SD1PID/SODDFRM"]
#[inline(always)] #[inline(always)]
pub fn set_soddfrm_sd1pid(&mut self, val: bool) { pub fn set_sd1pid_soddfrm(&mut self, val: bool) {
self.0 = (self.0 & !(0x01 << 29usize)) | (((val as u32) & 0x01) << 29usize); self.0 = (self.0 & !(0x01 << 29usize)) | (((val as u32) & 0x01) << 29usize);
} }
#[doc = "EPDIS"] #[doc = "EPDIS"]
@ -1174,15 +1174,15 @@ pub mod regs {
pub fn set_sd0pid_sevnfrm(&mut self, val: bool) { pub fn set_sd0pid_sevnfrm(&mut self, val: bool) {
self.0 = (self.0 & !(0x01 << 28usize)) | (((val as u32) & 0x01) << 28usize); self.0 = (self.0 & !(0x01 << 28usize)) | (((val as u32) & 0x01) << 28usize);
} }
#[doc = "SODDFRM"] #[doc = "SD1PID/SODDFRM"]
#[inline(always)] #[inline(always)]
pub const fn soddfrm(&self) -> bool { pub const fn sd1pid_soddfrm(&self) -> bool {
let val = (self.0 >> 29usize) & 0x01; let val = (self.0 >> 29usize) & 0x01;
val != 0 val != 0
} }
#[doc = "SODDFRM"] #[doc = "SD1PID/SODDFRM"]
#[inline(always)] #[inline(always)]
pub fn set_soddfrm(&mut self, val: bool) { pub fn set_sd1pid_soddfrm(&mut self, val: bool) {
self.0 = (self.0 & !(0x01 << 29usize)) | (((val as u32) & 0x01) << 29usize); self.0 = (self.0 & !(0x01 << 29usize)) | (((val as u32) & 0x01) << 29usize);
} }
#[doc = "EPDIS"] #[doc = "EPDIS"]