1use core::cell::Cell;
8use cortexm4f::support::atomic;
9use kernel::hil;
10use kernel::hil::usb::TransferType;
11use kernel::utilities::cells::{OptionalCell, VolatileCell};
12use kernel::utilities::registers::interfaces::{ReadWriteable, Readable, Writeable};
13use kernel::utilities::registers::{
14 register_bitfields, register_structs, Field, InMemoryRegister, LocalRegisterCopy, ReadOnly,
15 ReadWrite, WriteOnly,
16};
17use kernel::utilities::StaticRef;
18
19use crate::power;
20
21macro_rules! debug_events {
25 [ $( $arg:expr ),+ ] => {
26 {} };
28}
29
30macro_rules! debug_tasks {
31 [ $( $arg:expr ),+ ] => {
32 {} };
34}
35
36macro_rules! debug_packets {
37 [ $( $arg:expr ),+ ] => {
38 {} };
40}
41
42macro_rules! debug_info {
43 [ $( $arg:expr ),+ ] => {
44 {} };
46}
47
48macro_rules! internal_warn {
49 [ $( $arg:expr ),+ ] => {
50 {} };
52}
53
54macro_rules! internal_err {
55 [ $( $arg:expr ),+ ] => {
56 panic!($( $arg ),+)
57 };
58}
59
60const CHIPINFO_BASE: StaticRef<ChipInfoRegisters> =
61 unsafe { StaticRef::new(0x10000130 as *const ChipInfoRegisters) };
62
63const USBD_BASE: StaticRef<UsbdRegisters<'static>> =
64 unsafe { StaticRef::new(0x40027000 as *const UsbdRegisters<'static>) };
65
66const USBERRATA_BASE: StaticRef<UsbErrataRegisters> =
67 unsafe { StaticRef::new(0x4006E000 as *const UsbErrataRegisters) };
68
69const NUM_ENDPOINTS: usize = 8;
70
71register_structs! {
72 ChipInfoRegisters {
73 (0x000 => chip_model: ReadOnly<u32, ChipModel::Register>),
75 (0x004 => chip_revision: ReadOnly<u32, ChipRevision::Register>),
78 (0x008 => @END),
79 },
80
81 UsbErrataRegisters {
82 (0x000 => _reserved0),
83 (0xC00 => reg_c00: ReadWrite<u32>),
85 (0xC04 => _reserved1),
86 (0xC14 => reg_c14: WriteOnly<u32>),
88 (0xC18 => _reserved2),
89 (0xD14 => reg_d14: WriteOnly<u32>),
91 (0xD18 => @END),
92 }
93}
94
95#[repr(C)]
96struct UsbdRegisters<'a> {
97 _reserved1: [u32; 1],
98 task_startepin: [WriteOnly<u32, Task::Register>; NUM_ENDPOINTS],
103 task_startisoin: WriteOnly<u32, Task::Register>,
107 task_startepout: [WriteOnly<u32, Task::Register>; NUM_ENDPOINTS],
112 task_startisoout: WriteOnly<u32, Task::Register>,
116 task_ep0rcvout: WriteOnly<u32, Task::Register>,
119 task_ep0status: WriteOnly<u32, Task::Register>,
122 task_ep0stall: WriteOnly<u32, Task::Register>,
125 task_dpdmdrive: WriteOnly<u32, Task::Register>,
128 task_dpdmnodrive: WriteOnly<u32, Task::Register>,
131 _reserved2: [u32; 40],
132 event_usbreset: ReadWrite<u32, Event::Register>,
135 event_started: ReadWrite<u32, Event::Register>,
141 event_endepin: [ReadWrite<u32, Event::Register>; NUM_ENDPOINTS],
145 event_ep0datadone: ReadWrite<u32, Event::Register>,
148 event_endisoin: ReadWrite<u32, Event::Register>,
152 event_endepout: [ReadWrite<u32, Event::Register>; NUM_ENDPOINTS],
156 event_endisoout: ReadWrite<u32, Event::Register>,
160 event_sof: ReadWrite<u32, Event::Register>,
164 event_usbevent: ReadWrite<u32, Event::Register>,
168 event_ep0setup: ReadWrite<u32, Event::Register>,
172 event_epdata: ReadWrite<u32, Event::Register>,
176 _reserved3: [u32; 39],
177 shorts: ReadWrite<u32, Shorts::Register>,
180 _reserved4: [u32; 63],
181 inten: ReadWrite<u32, Interrupt::Register>,
184 intenset: ReadWrite<u32, Interrupt::Register>,
187 intenclr: ReadWrite<u32, Interrupt::Register>,
190 _reserved5: [u32; 61],
191 eventcause: ReadWrite<u32, EventCause::Register>,
194 _reserved6: [u32; 7],
195 halted_epin: [ReadOnly<u32, Halted::Register>; NUM_ENDPOINTS],
199 _reserved7: [u32; 1],
200 halted_epout: [ReadOnly<u32, Halted::Register>; NUM_ENDPOINTS],
204 _reserved8: [u32; 1],
205 epstatus: ReadWrite<u32, EndpointStatus::Register>,
209 epdatastatus: ReadWrite<u32, EndpointStatus::Register>,
213 usbaddr: ReadOnly<u32, UsbAddress::Register>,
216 _reserved9: [u32; 3],
217 bmrequesttype: ReadOnly<u32, RequestType::Register>,
220 brequest: ReadOnly<u32, Request::Register>,
223 wvaluel: ReadOnly<u32, Byte::Register>,
226 wvalueh: ReadOnly<u32, Byte::Register>,
229 windexl: ReadOnly<u32, Byte::Register>,
232 windexh: ReadOnly<u32, Byte::Register>,
235 wlengthl: ReadOnly<u32, Byte::Register>,
238 wlengthh: ReadOnly<u32, Byte::Register>,
241 size_epout: [ReadWrite<u32, EndpointSize::Register>; NUM_ENDPOINTS],
245 size_iosout: ReadOnly<u32, IsoEndpointSize::Register>,
248 _reserved10: [u32; 15],
249 enable: ReadWrite<u32, Usb::Register>,
252 usbpullup: ReadWrite<u32, UsbPullup::Register>,
255 dpdmvalue: ReadWrite<u32, DpDmValue::Register>,
260 dtoggle: ReadWrite<u32, Toggle::Register>,
263 epinen: ReadWrite<u32, EndpointEnable::Register>,
266 epouten: ReadWrite<u32, EndpointEnable::Register>,
269 epstall: WriteOnly<u32, EndpointStall::Register>,
272 isosplit: ReadWrite<u32, IsoSplit::Register>,
275 framecntr: ReadOnly<u32, FrameCounter::Register>,
278 _reserved11: [u32; 2],
279 lowpower: ReadWrite<u32, LowPower::Register>,
282 isoinconfig: ReadWrite<u32, IsoInConfig::Register>,
286 _reserved12: [u32; 51],
287 epin: [detail::EndpointRegisters<'a>; NUM_ENDPOINTS],
289 isoin: detail::EndpointRegisters<'a>,
291 _reserved13: [u32; 19],
292 epout: [detail::EndpointRegisters<'a>; NUM_ENDPOINTS],
294 isoout: detail::EndpointRegisters<'a>,
296 _reserved14: [u32; 19],
297 errata166_1: WriteOnly<u32>,
300 errata166_2: WriteOnly<u32>,
303 _reserved15: [u32; 261],
304 errata199: WriteOnly<u32>,
307}
308
309mod detail {
310 use super::{Amount, Count};
311 use core::marker::PhantomData;
312 use kernel::utilities::cells::VolatileCell;
313 use kernel::utilities::registers::interfaces::Writeable;
314 use kernel::utilities::registers::{ReadOnly, ReadWrite};
315
316 #[repr(C)]
317 pub struct EndpointRegisters<'a> {
318 ptr: VolatileCell<*const u8>,
319 maxcnt: ReadWrite<u32, Count::Register>,
320 amount: ReadOnly<u32, Amount::Register>,
321 _reserved: [u32; 2],
323 _phantom: PhantomData<&'a [u8]>,
325 }
326
327 impl<'a> EndpointRegisters<'a> {
328 pub fn set_buffer(&self, slice: &'a [VolatileCell<u8>]) {
329 self.ptr.set(slice.as_ptr().cast::<u8>());
330 self.maxcnt.write(Count::MAXCNT.val(slice.len() as u32));
331 }
332 }
333}
334
335register_bitfields! [u32,
336 Task [
338 ENABLE OFFSET(0) NUMBITS(1)
339 ],
340
341 Event [
343 READY OFFSET(0) NUMBITS(1)
344 ],
345
346 Shorts [
348 EP0DATADONE_STARTEPIN0 OFFSET(0) NUMBITS(1),
350 EP0DATADONE_STARTEPOUT0 OFFSET(1) NUMBITS(1),
352 EP0DATADONE_EP0STATUS OFFSET(2) NUMBITS(1),
354 ENDEPOUT0_EP0STATUS OFFSET(3) NUMBITS(1),
356 ENDEPOUT0_EP0RCVOUT OFFSET(4) NUMBITS(1)
358 ],
359
360 Interrupt [
362 USBRESET OFFSET(0) NUMBITS(1),
363 STARTED OFFSET(1) NUMBITS(1),
364 ENDEPIN0 OFFSET(2) NUMBITS(1),
365 ENDEPIN1 OFFSET(3) NUMBITS(1),
366 ENDEPIN2 OFFSET(4) NUMBITS(1),
367 ENDEPIN3 OFFSET(5) NUMBITS(1),
368 ENDEPIN4 OFFSET(6) NUMBITS(1),
369 ENDEPIN5 OFFSET(7) NUMBITS(1),
370 ENDEPIN6 OFFSET(8) NUMBITS(1),
371 ENDEPIN7 OFFSET(9) NUMBITS(1),
372 EP0DATADONE OFFSET(10) NUMBITS(1),
373 ENDISOIN OFFSET(11) NUMBITS(1),
374 ENDEPOUT0 OFFSET(12) NUMBITS(1),
375 ENDEPOUT1 OFFSET(13) NUMBITS(1),
376 ENDEPOUT2 OFFSET(14) NUMBITS(1),
377 ENDEPOUT3 OFFSET(15) NUMBITS(1),
378 ENDEPOUT4 OFFSET(16) NUMBITS(1),
379 ENDEPOUT5 OFFSET(17) NUMBITS(1),
380 ENDEPOUT6 OFFSET(18) NUMBITS(1),
381 ENDEPOUT7 OFFSET(19) NUMBITS(1),
382 ENDISOOUT OFFSET(20) NUMBITS(1),
383 SOF OFFSET(21) NUMBITS(1),
384 USBEVENT OFFSET(22) NUMBITS(1),
385 EP0SETUP OFFSET(23) NUMBITS(1),
386 EPDATA OFFSET(24) NUMBITS(1)
387 ],
388
389 EventCause [
391 ISOOUTCRC OFFSET(0) NUMBITS(1),
392 SUSPEND OFFSET(8) NUMBITS(1),
393 RESUME OFFSET(9) NUMBITS(1),
394 USBWUALLOWED OFFSET(10) NUMBITS(1),
395 READY OFFSET(11) NUMBITS(1)
396 ],
397
398 Halted [
399 GETSTATUS OFFSET(0) NUMBITS(16) [
400 NotHalted = 0,
401 Halted = 1
402 ]
403 ],
404
405 EndpointStatus [
406 EPIN0 OFFSET(0) NUMBITS(1),
407 EPIN1 OFFSET(1) NUMBITS(1),
408 EPIN2 OFFSET(2) NUMBITS(1),
409 EPIN3 OFFSET(3) NUMBITS(1),
410 EPIN4 OFFSET(4) NUMBITS(1),
411 EPIN5 OFFSET(5) NUMBITS(1),
412 EPIN6 OFFSET(6) NUMBITS(1),
413 EPIN7 OFFSET(7) NUMBITS(1),
414 EPIN8 OFFSET(8) NUMBITS(1),
415 EPOUT0 OFFSET(16) NUMBITS(1),
416 EPOUT1 OFFSET(17) NUMBITS(1),
417 EPOUT2 OFFSET(18) NUMBITS(1),
418 EPOUT3 OFFSET(19) NUMBITS(1),
419 EPOUT4 OFFSET(20) NUMBITS(1),
420 EPOUT5 OFFSET(21) NUMBITS(1),
421 EPOUT6 OFFSET(22) NUMBITS(1),
422 EPOUT7 OFFSET(23) NUMBITS(1),
423 EPOUT8 OFFSET(24) NUMBITS(1)
424 ],
425
426 UsbAddress [
427 ADDR OFFSET(0) NUMBITS(7)
428 ],
429
430 RequestType [
431 RECIPIENT OFFSET(0) NUMBITS(5) [
432 Device = 0,
433 Interface = 1,
434 Endpoint = 2,
435 Other = 3
436 ],
437 TYPE OFFSET(5) NUMBITS(2) [
438 Standard = 0,
439 Class = 1,
440 Vendor = 2
441 ],
442 DIRECTION OFFSET(7) NUMBITS(1) [
443 HostToDevice = 0,
444 DeviceToHost = 1
445 ]
446 ],
447
448 Request [
449 BREQUEST OFFSET(0) NUMBITS(8) [
450 STD_GET_STATUS = 0,
451 STD_CLEAR_FEATURE = 1,
452 STD_SET_FEATURE = 3,
453 STD_SET_ADDRESS = 5,
454 STD_GET_DESCRIPTOR = 6,
455 STD_SET_DESCRIPTOR = 7,
456 STD_GET_CONFIGURATION = 8,
457 STD_SET_CONFIGURATION = 9,
458 STD_GET_INTERFACE = 10,
459 STD_SET_INTERFACE = 11,
460 STD_SYNCH_FRAME = 12
461 ]
462 ],
463
464 Byte [
465 VALUE OFFSET(0) NUMBITS(8)
466 ],
467
468 EndpointSize [
469 SIZE OFFSET(0) NUMBITS(7)
470 ],
471
472 IsoEndpointSize [
473 SIZE OFFSET(0) NUMBITS(10),
474 ZERO OFFSET(16) NUMBITS(1)
475 ],
476
477 Usb [
479 ENABLE OFFSET(0) NUMBITS(1) [
480 OFF = 0,
481 ON = 1
482 ]
483 ],
484
485 UsbPullup [
486 CONNECT OFFSET(0) NUMBITS(1) [
487 Disabled = 0,
488 Enabled = 1
489 ]
490 ],
491
492 DpDmValue [
493 STATE OFFSET(0) NUMBITS(5) [
494 Resume = 1,
495 J = 2,
496 K = 4
497 ]
498 ],
499
500 Toggle [
501 EP OFFSET(0) NUMBITS(3) [],
502 IO OFFSET(7) NUMBITS(1) [
503 Out = 0,
504 In = 1
505 ],
506 VALUE OFFSET(8) NUMBITS(2) [
507 Nop = 0,
508 Data0 = 1,
509 Data1 = 2
510 ]
511 ],
512
513 EndpointEnable [
514 EP0 OFFSET(0) NUMBITS(1) [
515 Disable = 0,
516 Enable = 1
517 ],
518 EP1 OFFSET(1) NUMBITS(1) [
519 Disable = 0,
520 Enable = 1
521 ],
522 EP2 OFFSET(2) NUMBITS(1) [
523 Disable = 0,
524 Enable = 1
525 ],
526 EP3 OFFSET(3) NUMBITS(1) [
527 Disable = 0,
528 Enable = 1
529 ],
530 EP4 OFFSET(4) NUMBITS(1) [
531 Disable = 0,
532 Enable = 1
533 ],
534 EP5 OFFSET(5) NUMBITS(1) [
535 Disable = 0,
536 Enable = 1
537 ],
538 EP6 OFFSET(6) NUMBITS(1) [
539 Disable = 0,
540 Enable = 1
541 ],
542 EP7 OFFSET(7) NUMBITS(1) [
543 Disable = 0,
544 Enable = 1
545 ],
546 ISO OFFSET(8) NUMBITS(1) [
547 Disable = 0,
548 Enable = 1
549 ]
550 ],
551
552 EndpointStall [
553 EP OFFSET(0) NUMBITS(3) [],
554 IO OFFSET(7) NUMBITS(1) [
555 Out = 0,
556 In = 1
557 ],
558 STALL OFFSET(8) NUMBITS(1) [
559 UnStall = 0,
560 Stall = 1
561 ]
562 ],
563
564 IsoSplit [
565 SPLIT OFFSET(0) NUMBITS(16) [
566 OneDir = 0x0000,
567 HalfIN = 0x0080
568 ]
569 ],
570
571 FrameCounter [
572 FRAMECNTR OFFSET(0) NUMBITS(11)
573 ],
574
575 LowPower [
576 LOWPOWER OFFSET(0) NUMBITS(1) [
577 ForceNormal = 0,
578 LowPower = 1
579 ]
580 ],
581
582 IsoInConfig [
583 RESPONSE OFFSET(0) NUMBITS(1) [
584 NoResp = 0,
585 ZeroData = 1
586 ]
587 ],
588
589 Count [
590 MAXCNT OFFSET(0) NUMBITS(10)
592 ],
593
594 Amount [
595 AMOUNT OFFSET(0) NUMBITS(10)
597 ],
598
599 ChipModel [
600 MODEL OFFSET(0) NUMBITS(32) [
601 NRF52840 = 8
602 ]
603 ],
604
605 ChipRevision [
606 REV OFFSET(0) NUMBITS(32) [
607 REVA = 0,
608 REVB = 1,
609 REVC = 2,
610 REVD = 3,
611 REVE = 4,
612 REVF = 5,
613 ]
614 ]
615];
616
617#[derive(Copy, Clone, Debug, PartialEq)]
618pub enum UsbState {
619 Disabled,
620 Started,
621 Initialized,
622 PoweredOn,
623 Attached,
624 Configured,
625}
626
627#[derive(Copy, Clone, Debug)]
628pub enum EndpointState {
629 Disabled,
630 Ctrl(CtrlState),
631 Bulk(TransferType, Option<BulkInState>, Option<BulkOutState>),
632}
633
634impl EndpointState {
635 fn ctrl_state(self) -> CtrlState {
636 match self {
637 EndpointState::Ctrl(state) => state,
638 _ => panic!("Expected EndpointState::Ctrl"),
639 }
640 }
641
642 fn bulk_state(self) -> (TransferType, Option<BulkInState>, Option<BulkOutState>) {
643 match self {
644 EndpointState::Bulk(transfer_type, in_state, out_state) => {
645 (transfer_type, in_state, out_state)
646 }
647 _ => panic!("Expected EndpointState::Bulk"),
648 }
649 }
650}
651
652#[derive(Copy, Clone, PartialEq, Debug)]
654pub enum CtrlState {
655 Init,
657 ReadIn,
659 ReadStatus,
661 WriteOut,
663}
664
665#[derive(Copy, Clone, PartialEq, Debug)]
666pub enum BulkInState {
667 Init,
669 InDma,
671 InData,
673}
674
675#[derive(Copy, Clone, PartialEq, Debug)]
676pub enum BulkOutState {
677 Init,
679 OutDelay,
682 OutData { size: u32 },
685 OutDma { size: u32 },
688}
689
690pub struct Endpoint<'a> {
691 slice_in: OptionalCell<&'a [VolatileCell<u8>]>,
692 slice_out: OptionalCell<&'a [VolatileCell<u8>]>,
693 state: Cell<EndpointState>,
694 request_transmit_in: Cell<bool>,
698 request_transmit_out: Cell<bool>,
700}
701
702impl Endpoint<'_> {
703 const fn new() -> Self {
704 Endpoint {
705 slice_in: OptionalCell::empty(),
706 slice_out: OptionalCell::empty(),
707 state: Cell::new(EndpointState::Disabled),
708 request_transmit_in: Cell::new(false),
709 request_transmit_out: Cell::new(false),
710 }
711 }
712}
713
714pub struct Usbd<'a> {
715 registers: StaticRef<UsbdRegisters<'a>>,
716 state: OptionalCell<UsbState>,
717 dma_pending: Cell<bool>,
718 client: OptionalCell<&'a dyn hil::usb::Client<'a>>,
719 descriptors: [Endpoint<'a>; NUM_ENDPOINTS],
720 power: OptionalCell<&'a power::Power<'a>>,
721}
722
723impl<'a> Usbd<'a> {
724 pub const fn new() -> Self {
725 Usbd {
726 registers: USBD_BASE,
727 client: OptionalCell::empty(),
728 state: OptionalCell::new(UsbState::Disabled),
729 dma_pending: Cell::new(false),
730 descriptors: [
731 Endpoint::new(),
732 Endpoint::new(),
733 Endpoint::new(),
734 Endpoint::new(),
735 Endpoint::new(),
736 Endpoint::new(),
737 Endpoint::new(),
738 Endpoint::new(),
739 ],
740 power: OptionalCell::empty(),
741 }
742 }
743
744 pub fn set_power_ref(&self, power: &'a power::Power<'a>) {
745 self.power.set(power);
746 }
747
748 fn has_errata_166(&self) -> bool {
758 true
759 }
760
761 fn has_errata_171(&self) -> bool {
762 true
763 }
764
765 fn has_errata_187(&self) -> bool {
766 CHIPINFO_BASE
767 .chip_model
768 .matches_all(ChipModel::MODEL::NRF52840)
769 && match CHIPINFO_BASE.chip_revision.read_as_enum(ChipRevision::REV) {
770 Some(ChipRevision::REV::Value::REVB)
771 | Some(ChipRevision::REV::Value::REVC)
772 | Some(ChipRevision::REV::Value::REVD)
773 | Some(ChipRevision::REV::Value::REVE)
774 | Some(ChipRevision::REV::Value::REVF) => true,
775 Some(ChipRevision::REV::Value::REVA) | None => false,
776 }
777 }
778
779 fn has_errata_199(&self) -> bool {
780 true
781 }
782
783 fn apply_errata_166(&self) {
785 if self.has_errata_166() {
786 self.registers.errata166_1.set(0x7e3);
787 self.registers.errata166_2.set(0x40);
788 }
789 }
790
791 fn apply_errata_171(&self, val: u32) {
793 if self.has_errata_171() {
794 unsafe {
795 atomic(|| {
796 if USBERRATA_BASE.reg_c00.get() == 0 {
797 USBERRATA_BASE.reg_c00.set(0x9375);
798 USBERRATA_BASE.reg_c14.set(val);
799 USBERRATA_BASE.reg_c00.set(0x9375);
800 } else {
801 USBERRATA_BASE.reg_c14.set(val);
802 }
803 });
804 }
805 }
806 }
807
808 fn apply_errata_187(&self, val: u32) {
810 if self.has_errata_187() {
811 unsafe {
812 atomic(|| {
813 if USBERRATA_BASE.reg_c00.get() == 0 {
814 USBERRATA_BASE.reg_c00.set(0x9375);
815 USBERRATA_BASE.reg_d14.set(val);
816 USBERRATA_BASE.reg_c00.set(0x9375);
817 } else {
818 USBERRATA_BASE.reg_d14.set(val);
819 }
820 });
821 }
822 }
823 }
824
825 fn apply_errata_199(&self, val: u32) {
826 if self.has_errata_199() {
827 self.registers.errata199.set(val);
828 }
829 }
830
831 pub fn get_state(&self) -> UsbState {
832 self.state.unwrap_or_panic() }
834
835 fn enable(&self) {
837 if self.get_state() != UsbState::Disabled {
838 internal_warn!("USBC is already enabled");
839 return;
840 }
841 self.registers.eventcause.modify(EventCause::READY::CLEAR);
842 self.apply_errata_187(3);
843 self.apply_errata_171(0xc0);
844 self.registers.enable.write(Usb::ENABLE::ON);
845 while !self.registers.eventcause.is_set(EventCause::READY) {}
846 self.registers.eventcause.modify(EventCause::READY::CLEAR);
847 self.apply_errata_171(0);
848 self.apply_errata_166();
849 self.clear_pending_dma();
850 self.state.set(UsbState::Initialized);
851 self.apply_errata_187(0);
852 }
853
854 fn _suspend(&self) {
856 debug_info!("usbc::suspend()");
857 self.ep_abort_all();
858 if self.registers.eventcause.is_set(EventCause::RESUME) {
859 return;
860 }
861 self.enable_lowpower();
862 if self.registers.eventcause.is_set(EventCause::RESUME) {
863 self.disable_lowpower();
864 } else {
865 self.apply_errata_171(0);
866 }
867 internal_warn!("suspend() not fully implemented");
868 }
869
870 fn disable_all_interrupts(&self) {
871 self.registers.intenclr.set(0xffffffff);
872 }
873
874 fn enable_interrupts(&self, inter: u32) {
875 self.registers.inten.set(inter);
876 }
877
878 fn power_ready(&self) {
879 match self.get_state() {
880 UsbState::Disabled => {
881 self.enable();
882 self.state.set(UsbState::PoweredOn);
883 }
884 UsbState::Initialized => self.state.set(UsbState::PoweredOn),
885 _ => (),
886 }
887 }
888
889 fn enable_pullup(&self) {
890 debug_info!("enable_pullup() - State={:?}", self.get_state());
891 if self.get_state() == UsbState::Started {
892 debug_info!("Enabling USB pullups");
893 self.registers.usbpullup.write(UsbPullup::CONNECT::Enabled);
894 }
895 self.state.set(UsbState::Attached);
896 debug_info!("New state is {:?}", self.get_state());
897 }
898
899 fn disable_pullup(&self) {
900 debug_info!("Disabling USB pullup - State={:?}", self.get_state());
901 self.registers.usbpullup.write(UsbPullup::CONNECT::Disabled);
902 self.state.set(UsbState::Started);
903 debug_info!("New state is {:?}", self.get_state());
904 }
905
906 fn start(&self) {
908 debug_info!("usbc::start() - State={:?}", self.get_state());
909
910 let chip_model = CHIPINFO_BASE.chip_model.get();
918 if chip_model != u32::from(ChipModel::MODEL::NRF52840) {
919 panic!(
920 "USB was only tested on NRF52840. Your chip model is {}.",
921 chip_model
922 );
923 }
924 let chip_revision = CHIPINFO_BASE.chip_revision.extract();
925 match chip_revision.read_as_enum(ChipRevision::REV) {
926 Some(ChipRevision::REV::Value::REVA) | Some(ChipRevision::REV::Value::REVB) => {
927 panic!(
928 "Errata for USB on NRF52840 chips revisions A and B are not implemented. Your chip revision is {}.",
929 chip_revision.get()
930 );
931 }
932 Some(ChipRevision::REV::Value::REVC)
933 | Some(ChipRevision::REV::Value::REVD)
934 | Some(ChipRevision::REV::Value::REVE)
935 | Some(ChipRevision::REV::Value::REVF) => {
936 debug_info!(
937 "Your chip is NRF52840 revision {}. The USB stack was tested on your chip :)",
938 chip_revision.get()
939 );
940 }
941 None => {
942 internal_warn!(
943 "Your chip is NRF52840 revision {} (unknown revision). Although this USB implementation should be compatible, your chip hasn't been tested.",
944 chip_revision.get()
945 );
946 }
947 }
948 let power = self.power.unwrap_or_panic(); if !power.is_vbus_present() {
950 debug_info!("[!] VBUS power is not detected.");
951 return;
952 }
953 if self.get_state() == UsbState::Disabled {
954 self.enable();
955 }
956 if self.get_state() != UsbState::PoweredOn {
957 debug_info!("Waiting for power regulators...");
958 while power.is_vbus_present() && power.is_usb_power_ready() {}
959 }
960 debug_info!("usbc::start() - subscribing to interrupts.");
961 self.registers.intenset.write(
962 Interrupt::USBRESET::SET
963 + Interrupt::STARTED::SET
964 + Interrupt::ENDEPIN0::SET
965 + Interrupt::EP0DATADONE::SET
966 + Interrupt::ENDEPOUT0::SET
967 + Interrupt::USBEVENT::SET
968 + Interrupt::EP0SETUP::SET
969 + Interrupt::EPDATA::SET,
970 );
971 self.state.set(UsbState::Started);
972 }
973
974 fn stop(&self) {
975 debug_info!("usbc::stop() - State={:?}", self.get_state());
976 if self.get_state() != UsbState::Started {
977 return;
978 }
979 self.ep_abort_all();
980 self.disable_all_interrupts();
981 self.registers.usbpullup.write(UsbPullup::CONNECT::Disabled);
982 self.state.set(UsbState::PoweredOn);
983 }
984
985 fn disable(&self) {
986 debug_info!("usbc::disable() - State={:?}", self.get_state());
987 self.stop();
988 self.registers.enable.write(Usb::ENABLE::OFF);
989 self.state.set(UsbState::Initialized);
990 self.clear_pending_dma();
991 }
992
993 fn clear_pending_dma(&self) {
994 debug_packets!("clear_pending_dma()");
995 self.apply_errata_199(0);
996 self.dma_pending.set(false);
997 }
998
999 fn set_pending_dma(&self) {
1000 debug_packets!("set_pending_dma()");
1001 if self.dma_pending.get() {
1002 internal_err!("Pending DMA already in flight");
1003 }
1004 self.apply_errata_199(0x82);
1005 self.dma_pending.set(true);
1006 }
1007
1008 fn enable_in_endpoint_(&self, transfer_type: TransferType, endpoint: usize) {
1009 debug_info!(
1010 "enable_in_endpoint_({}), State={:?}",
1011 endpoint,
1012 self.get_state()
1013 );
1014 self.registers.intenset.write(match endpoint {
1015 0 => Interrupt::ENDEPIN0::SET,
1016 1 => Interrupt::ENDEPIN1::SET,
1017 2 => Interrupt::ENDEPIN2::SET,
1018 3 => Interrupt::ENDEPIN3::SET,
1019 4 => Interrupt::ENDEPIN4::SET,
1020 5 => Interrupt::ENDEPIN5::SET,
1021 6 => Interrupt::ENDEPIN6::SET,
1022 7 => Interrupt::ENDEPIN7::SET,
1023 8 => Interrupt::ENDISOIN::SET,
1024 _ => unreachable!("unexisting endpoint"),
1025 });
1026 self.registers.epinen.modify(match endpoint {
1027 0 => EndpointEnable::EP0::Enable,
1028 1 => EndpointEnable::EP1::Enable,
1029 2 => EndpointEnable::EP2::Enable,
1030 3 => EndpointEnable::EP3::Enable,
1031 4 => EndpointEnable::EP4::Enable,
1032 5 => EndpointEnable::EP5::Enable,
1033 6 => EndpointEnable::EP6::Enable,
1034 7 => EndpointEnable::EP7::Enable,
1035 8 => EndpointEnable::ISO::Enable,
1036 _ => unreachable!("unexisting endpoint"),
1037 });
1038 self.descriptors[endpoint].state.set(match endpoint {
1039 0 => EndpointState::Ctrl(CtrlState::Init),
1040 1..=7 => EndpointState::Bulk(transfer_type, Some(BulkInState::Init), None),
1041 8 => unimplemented!("isochronous endpoint"),
1042 _ => unreachable!("unexisting endpoint"),
1043 });
1044 }
1045
1046 fn enable_out_endpoint_(&self, transfer_type: TransferType, endpoint: usize) {
1047 debug_info!(
1048 "enable_out_endpoint_({}) - State={:?}",
1049 endpoint,
1050 self.get_state()
1051 );
1052 self.registers.intenset.write(match endpoint {
1053 0 => Interrupt::ENDEPOUT0::SET,
1054 1 => Interrupt::ENDEPOUT1::SET,
1055 2 => Interrupt::ENDEPOUT2::SET,
1056 3 => Interrupt::ENDEPOUT3::SET,
1057 4 => Interrupt::ENDEPOUT4::SET,
1058 5 => Interrupt::ENDEPOUT5::SET,
1059 6 => Interrupt::ENDEPOUT6::SET,
1060 7 => Interrupt::ENDEPOUT7::SET,
1061 8 => Interrupt::ENDISOOUT::SET,
1062 _ => unreachable!("unexisting endpoint"),
1063 });
1064 self.registers.epouten.modify(match endpoint {
1065 0 => EndpointEnable::EP0::Enable,
1066 1 => EndpointEnable::EP1::Enable,
1067 2 => EndpointEnable::EP2::Enable,
1068 3 => EndpointEnable::EP3::Enable,
1069 4 => EndpointEnable::EP4::Enable,
1070 5 => EndpointEnable::EP5::Enable,
1071 6 => EndpointEnable::EP6::Enable,
1072 7 => EndpointEnable::EP7::Enable,
1073 8 => EndpointEnable::ISO::Enable,
1074 _ => unreachable!("unexisting endpoint"),
1075 });
1076 self.descriptors[endpoint].state.set(match endpoint {
1077 0 => EndpointState::Ctrl(CtrlState::Init),
1078 1..=7 => EndpointState::Bulk(transfer_type, None, Some(BulkOutState::Init)),
1079 8 => unimplemented!("isochronous endpoint"),
1080 _ => unreachable!("unexisting endpoint"),
1081 });
1082 }
1083
1084 fn enable_in_out_endpoint_(&self, transfer_type: TransferType, endpoint: usize) {
1085 debug_info!(
1086 "enable_in_out_endpoint_({}) - State={:?}",
1087 endpoint,
1088 self.get_state()
1089 );
1090 self.registers.intenset.write(match endpoint {
1091 0 => Interrupt::ENDEPIN0::SET + Interrupt::ENDEPOUT0::SET,
1092 1 => Interrupt::ENDEPIN1::SET + Interrupt::ENDEPOUT1::SET,
1093 2 => Interrupt::ENDEPIN2::SET + Interrupt::ENDEPOUT2::SET,
1094 3 => Interrupt::ENDEPIN3::SET + Interrupt::ENDEPOUT3::SET,
1095 4 => Interrupt::ENDEPIN4::SET + Interrupt::ENDEPOUT4::SET,
1096 5 => Interrupt::ENDEPIN5::SET + Interrupt::ENDEPOUT5::SET,
1097 6 => Interrupt::ENDEPIN6::SET + Interrupt::ENDEPOUT6::SET,
1098 7 => Interrupt::ENDEPIN7::SET + Interrupt::ENDEPOUT7::SET,
1099 8 => Interrupt::ENDISOIN::SET + Interrupt::ENDISOOUT::SET,
1100 _ => unreachable!("unexisting endpoint"),
1101 });
1102 self.registers.epinen.modify(match endpoint {
1103 0 => EndpointEnable::EP0::Enable,
1104 1 => EndpointEnable::EP1::Enable,
1105 2 => EndpointEnable::EP2::Enable,
1106 3 => EndpointEnable::EP3::Enable,
1107 4 => EndpointEnable::EP4::Enable,
1108 5 => EndpointEnable::EP5::Enable,
1109 6 => EndpointEnable::EP6::Enable,
1110 7 => EndpointEnable::EP7::Enable,
1111 8 => EndpointEnable::ISO::Enable,
1112 _ => unreachable!("unexisting endpoint"),
1113 });
1114 self.registers.epouten.modify(match endpoint {
1115 0 => EndpointEnable::EP0::Enable,
1116 1 => EndpointEnable::EP1::Enable,
1117 2 => EndpointEnable::EP2::Enable,
1118 3 => EndpointEnable::EP3::Enable,
1119 4 => EndpointEnable::EP4::Enable,
1120 5 => EndpointEnable::EP5::Enable,
1121 6 => EndpointEnable::EP6::Enable,
1122 7 => EndpointEnable::EP7::Enable,
1123 8 => EndpointEnable::ISO::Enable,
1124 _ => unreachable!("unexisting endpoint"),
1125 });
1126 self.descriptors[endpoint].state.set(match endpoint {
1127 0 => EndpointState::Ctrl(CtrlState::Init),
1128 1..=7 => EndpointState::Bulk(
1129 transfer_type,
1130 Some(BulkInState::Init),
1131 Some(BulkOutState::Init),
1132 ),
1133 8 => unimplemented!("isochronous endpoint"),
1134 _ => unreachable!("unexisting endpoint"),
1135 });
1136 }
1137
1138 fn ep_abort_all(&self) {
1139 internal_warn!("ep_abort_all() not implemented");
1140 }
1141
1142 pub fn enable_lowpower(&self) {
1143 internal_warn!("enable_lowpower() not implemented");
1144 }
1145
1146 pub fn disable_lowpower(&self) {
1147 internal_warn!("disable_lowpower() not implemented");
1148 }
1149
1150 pub fn handle_interrupt(&self) {
1151 let saved_inter = self.registers.intenset.extract();
1153 self.disable_all_interrupts();
1154
1155 let active_events = self.active_events(&saved_inter);
1156 let events_to_process = saved_inter.bitand(active_events.get());
1157
1158 if events_to_process.is_set(Interrupt::USBRESET) {
1161 self.handle_usbreset();
1162 }
1163 if events_to_process.is_set(Interrupt::STARTED) {
1164 self.handle_started();
1165 }
1166 for ep in 0..NUM_ENDPOINTS {
1168 if events_to_process.is_set(inter_endepin(ep)) {
1169 self.handle_endepin(ep);
1170 }
1171 }
1172 if events_to_process.is_set(Interrupt::EP0DATADONE) {
1173 self.handle_ep0datadone();
1174 }
1175 if events_to_process.is_set(Interrupt::ENDISOIN) {
1176 self.handle_endisoin();
1177 }
1178 for ep in 0..NUM_ENDPOINTS {
1180 if events_to_process.is_set(inter_endepout(ep)) {
1181 self.handle_endepout(ep);
1182 }
1183 }
1184 if events_to_process.is_set(Interrupt::ENDISOOUT) {
1185 self.handle_endisoout();
1186 }
1187 if events_to_process.is_set(Interrupt::SOF) {
1188 self.handle_sof();
1189 }
1190 if events_to_process.is_set(Interrupt::USBEVENT) {
1191 self.handle_usbevent();
1192 }
1193 if events_to_process.is_set(Interrupt::EPDATA) {
1194 self.handle_epdata();
1195 }
1196
1197 self.process_dma_requests();
1198
1199 if events_to_process.is_set(Interrupt::EP0SETUP) {
1202 self.handle_ep0setup();
1203 }
1204
1205 self.enable_interrupts(saved_inter.get());
1207 }
1208
1209 fn active_events(
1210 &self,
1211 _saved_inter: &LocalRegisterCopy<u32, Interrupt::Register>,
1212 ) -> InMemoryRegister<u32, Interrupt::Register> {
1213 let result = InMemoryRegister::new(0);
1214 if Usbd::take_event(&self.registers.event_usbreset) {
1215 debug_events!(
1216 "- event: usbreset{}",
1217 ignored_str(_saved_inter, Interrupt::USBRESET)
1218 );
1219 result.modify(Interrupt::USBRESET::SET);
1220 }
1221 if Usbd::take_event(&self.registers.event_started) {
1222 debug_events!(
1223 "- event: started{}",
1224 ignored_str(_saved_inter, Interrupt::STARTED)
1225 );
1226 result.modify(Interrupt::STARTED::SET);
1227 }
1228 for ep in 0..8 {
1229 if Usbd::take_event(&self.registers.event_endepin[ep]) {
1230 debug_events!(
1231 "- event: endepin[{}]{}",
1232 ep,
1233 ignored_str(_saved_inter, inter_endepin(ep))
1234 );
1235 result.modify(inter_endepin(ep).val(1));
1236 }
1237 }
1238 if Usbd::take_event(&self.registers.event_ep0datadone) {
1239 debug_events!(
1240 "- event: ep0datadone{}",
1241 ignored_str(_saved_inter, Interrupt::EP0DATADONE)
1242 );
1243 result.modify(Interrupt::EP0DATADONE::SET);
1244 }
1245 if Usbd::take_event(&self.registers.event_endisoin) {
1246 debug_events!(
1247 "- event: endisoin{}",
1248 ignored_str(_saved_inter, Interrupt::ENDISOIN)
1249 );
1250 result.modify(Interrupt::ENDISOIN::SET);
1251 }
1252 for ep in 0..8 {
1253 if Usbd::take_event(&self.registers.event_endepout[ep]) {
1254 debug_events!(
1255 "- event: endepout[{}]{}",
1256 ep,
1257 ignored_str(_saved_inter, inter_endepout(ep))
1258 );
1259 result.modify(inter_endepout(ep).val(1));
1260 }
1261 }
1262 if Usbd::take_event(&self.registers.event_endisoout) {
1263 debug_events!(
1264 "- event: endisoout{}",
1265 ignored_str(_saved_inter, Interrupt::ENDISOOUT)
1266 );
1267 result.modify(Interrupt::ENDISOOUT::SET);
1268 }
1269 if Usbd::take_event(&self.registers.event_sof) {
1270 debug_events!("- event: sof{}", ignored_str(_saved_inter, Interrupt::SOF));
1271 result.modify(Interrupt::SOF::SET);
1272 }
1273 if Usbd::take_event(&self.registers.event_usbevent) {
1274 debug_events!(
1275 "- event: usbevent{}",
1276 ignored_str(_saved_inter, Interrupt::USBEVENT)
1277 );
1278 result.modify(Interrupt::USBEVENT::SET);
1279 }
1280 if Usbd::take_event(&self.registers.event_ep0setup) {
1281 debug_events!(
1282 "- event: ep0setup{}",
1283 ignored_str(_saved_inter, Interrupt::EP0SETUP)
1284 );
1285 result.modify(Interrupt::EP0SETUP::SET);
1286 }
1287 if Usbd::take_event(&self.registers.event_epdata) {
1288 debug_events!(
1289 "- event: epdata{}",
1290 ignored_str(_saved_inter, Interrupt::EPDATA)
1291 );
1292 result.modify(Interrupt::EPDATA::SET);
1293 }
1294 result
1295 }
1296
1297 fn take_event(event: &ReadWrite<u32, Event::Register>) -> bool {
1300 let result = event.is_set(Event::READY);
1301 if result {
1302 event.write(Event::READY::CLEAR);
1303 }
1304 result
1305 }
1306
1307 fn handle_usbreset(&self) {
1308 for (ep, desc) in self.descriptors.iter().enumerate() {
1309 match desc.state.get() {
1310 EndpointState::Disabled => {}
1311 EndpointState::Ctrl(_) => desc.state.set(EndpointState::Ctrl(CtrlState::Init)),
1312 EndpointState::Bulk(transfer_type, in_state, out_state) => {
1313 desc.state.set(EndpointState::Bulk(
1314 transfer_type,
1315 in_state.map(|_| BulkInState::Init),
1316 out_state.map(|_| BulkOutState::Init),
1317 ));
1318 if out_state.is_some() {
1319 self.registers.size_epout[ep].set(0);
1321 }
1322 }
1323 }
1324 desc.request_transmit_in.set(false);
1326 desc.request_transmit_out.set(false);
1327 }
1328
1329 self.dma_pending.set(false);
1330
1331 for _ in 0..800000 {
1338 cortexm4f::support::nop();
1339 }
1340
1341 self.client.map(|client| {
1343 client.bus_reset();
1344 });
1345 }
1346
1347 fn handle_started(&self) {
1348 let epstatus = self.registers.epstatus.extract();
1349 self.registers.epstatus.set(epstatus.get());
1351 debug_events!("epstatus: {:08X}", epstatus.get());
1352
1353 }
1355
1356 fn handle_endepin(&self, endpoint: usize) {
1357 self.clear_pending_dma();
1359
1360 match endpoint {
1361 0 => {}
1362 1..=7 => {
1363 let (transfer_type, in_state, out_state) =
1364 self.descriptors[endpoint].state.get().bulk_state();
1365 assert_eq!(in_state, Some(BulkInState::InDma));
1366 self.descriptors[endpoint].state.set(EndpointState::Bulk(
1367 transfer_type,
1368 Some(BulkInState::InData),
1369 out_state,
1370 ));
1371 }
1372 8 => unimplemented!("isochronous endpoint"),
1373 _ => unreachable!("unexisting endpoint"),
1374 }
1375
1376 }
1378
1379 fn handle_ep0datadone(&self) {
1382 let endpoint = 0;
1383 let state = self.descriptors[endpoint].state.get().ctrl_state();
1384 match state {
1385 CtrlState::ReadIn => {
1386 if self.dma_pending.get() {
1387 self.descriptors[endpoint].request_transmit_in.set(true);
1388 } else {
1389 self.transmit_in_ep0();
1390 }
1391 }
1392
1393 CtrlState::ReadStatus => {
1394 self.complete_ctrl_status();
1395 }
1396
1397 CtrlState::WriteOut => {
1398 if self.dma_pending.get() {
1402 self.descriptors[endpoint].request_transmit_out.set(true);
1403 } else {
1404 self.transmit_out_ep0();
1405 }
1406 }
1407
1408 CtrlState::Init => {
1409 debug_tasks!("- task: ep0stall");
1411 self.registers.task_ep0stall.write(Task::ENABLE::SET);
1412 }
1413 }
1414 }
1415
1416 fn handle_endisoin(&self) {
1417 unimplemented!("handle_endisoin");
1418 }
1419
1420 fn handle_endepout(&self, endpoint: usize) {
1421 self.clear_pending_dma();
1423
1424 match endpoint {
1425 0 => {
1426 self.client.map(|client| {
1433 match client.ctrl_out(endpoint, self.registers.size_epout[endpoint].get()) {
1434 hil::usb::CtrlOutResult::Ok => {
1435 self.complete_ctrl_status();
1442 }
1443 hil::usb::CtrlOutResult::Delay => {}
1444 _ => {
1445 debug_tasks!("- task: ep0stall");
1448 self.registers.task_ep0stall.write(Task::ENABLE::SET);
1449 self.descriptors[endpoint]
1450 .state
1451 .set(EndpointState::Ctrl(CtrlState::Init));
1452 }
1453 }
1454 });
1455 }
1456 1..=7 => {
1457 let (transfer_type, in_state, out_state) =
1459 self.descriptors[endpoint].state.get().bulk_state();
1460 assert!(matches!(out_state, Some(BulkOutState::OutDma { .. })));
1461
1462 let packet_bytes = if let Some(BulkOutState::OutDma { size }) = out_state {
1463 size
1464 } else {
1465 0
1466 };
1467
1468 self.debug_out_packet(packet_bytes as usize, endpoint);
1469
1470 self.client.map(|client| {
1471 let result = client.packet_out(transfer_type, endpoint, packet_bytes);
1472 debug_packets!("packet_out => {:?}", result);
1473 let new_out_state = match result {
1474 hil::usb::OutResult::Ok => {
1475 BulkOutState::Init
1480 }
1481
1482 hil::usb::OutResult::Delay => {
1483 BulkOutState::OutDelay
1485 }
1486
1487 hil::usb::OutResult::Error => {
1488 self.registers.epstall.write(
1489 EndpointStall::EP.val(endpoint as u32)
1490 + EndpointStall::IO::Out
1491 + EndpointStall::STALL::Stall,
1492 );
1493 BulkOutState::Init
1494 }
1495 };
1496 self.descriptors[endpoint].state.set(EndpointState::Bulk(
1497 transfer_type,
1498 in_state,
1499 Some(new_out_state),
1500 ));
1501 });
1502 }
1503 8 => unimplemented!("isochronous endpoint"),
1504 _ => unreachable!("unexisting endpoint"),
1505 }
1506 }
1507
1508 fn handle_endisoout(&self) {
1509 unimplemented!("handle_endisoout");
1510 }
1511
1512 fn handle_sof(&self) {
1513 unimplemented!("handle_sof");
1514 }
1515
1516 fn handle_usbevent(&self) {
1517 let eventcause = self.registers.eventcause.extract();
1518 self.registers.eventcause.set(eventcause.get());
1520
1521 debug_events!("eventcause: {:08x}", eventcause.get());
1522 if eventcause.is_set(EventCause::ISOOUTCRC) {
1523 debug_events!("- usbevent: isooutcrc");
1524 internal_warn!("usbc::isooutcrc not implemented");
1525 }
1526 if eventcause.is_set(EventCause::SUSPEND) {
1527 debug_events!("- usbevent: suspend");
1528 internal_warn!("usbc::suspend not implemented");
1529 }
1530 if eventcause.is_set(EventCause::RESUME) {
1531 debug_events!("- usbevent: resume");
1532 internal_warn!("usbc::resume not implemented");
1533 }
1534 if eventcause.is_set(EventCause::USBWUALLOWED) {
1535 debug_events!("- usbevent: usbwuallowed");
1536 internal_warn!("usbc::usbwuallowed not implemented");
1537 }
1538 if eventcause.is_set(EventCause::READY) {
1539 debug_events!("- usbevent: ready");
1540 internal_warn!("usbc::ready not implemented");
1541 }
1542 }
1543
1544 fn handle_epdata(&self) {
1545 let epdatastatus = self.registers.epdatastatus.extract();
1546 self.registers.epdatastatus.set(epdatastatus.get());
1548 debug_events!("epdatastatus: {:08X}", epdatastatus.get());
1549
1550 for endpoint in 1..NUM_ENDPOINTS {
1553 if epdatastatus.is_set(status_epin(endpoint)) {
1554 let (transfer_type, in_state, out_state) =
1555 self.descriptors[endpoint].state.get().bulk_state();
1556 assert!(in_state.is_some());
1557 match in_state.unwrap() {
1558 BulkInState::InData => {
1559 }
1561 BulkInState::Init => {
1562 internal_warn!(
1563 "Received a stale epdata IN in an unexpected state: {:?}",
1564 in_state
1565 );
1566 }
1567 BulkInState::InDma => {
1568 internal_err!("Unexpected state: {:?}", in_state);
1569 }
1570 }
1571 self.descriptors[endpoint].state.set(EndpointState::Bulk(
1572 transfer_type,
1573 Some(BulkInState::Init),
1574 out_state,
1575 ));
1576 self.client
1577 .map(|client| client.packet_transmitted(endpoint));
1578 }
1579 }
1580
1581 for ep in 1..NUM_ENDPOINTS {
1584 if epdatastatus.is_set(status_epout(ep)) {
1585 let (transfer_type, in_state, out_state) =
1586 self.descriptors[ep].state.get().bulk_state();
1587 assert!(out_state.is_some());
1588
1589 let ep_size = self.registers.size_epout[ep].get();
1596
1597 match out_state.unwrap() {
1598 BulkOutState::Init => {
1599 self.descriptors[ep].request_transmit_out.set(true);
1601 }
1602 BulkOutState::OutDelay => {
1603 }
1605 BulkOutState::OutData { size: _ } | BulkOutState::OutDma { size: _ } => {
1606 internal_err!("Unexpected state: {:?}", out_state);
1607 }
1608 }
1609 self.descriptors[ep].state.set(EndpointState::Bulk(
1611 transfer_type,
1612 in_state,
1613 Some(BulkOutState::OutData { size: ep_size }),
1614 ));
1615 }
1616 }
1617 }
1618
1619 fn handle_ep0setup(&self) {
1621 let endpoint = 0;
1622 let state = self.descriptors[endpoint].state.get().ctrl_state();
1623 match state {
1624 CtrlState::Init => {
1625 let ep_buf = &self.descriptors[endpoint].slice_out;
1628 let ep_buf = ep_buf.unwrap_or_panic(); if ep_buf.len() < 8 {
1630 panic!("EP0 DMA buffer length < 8");
1631 }
1632
1633 ep_buf[0].set((self.registers.bmrequesttype.get() & 0xff) as u8);
1637 ep_buf[1].set((self.registers.brequest.get() & 0xff) as u8);
1638 ep_buf[2].set(self.registers.wvaluel.read(Byte::VALUE) as u8);
1639 ep_buf[3].set(self.registers.wvalueh.read(Byte::VALUE) as u8);
1640 ep_buf[4].set(self.registers.windexl.read(Byte::VALUE) as u8);
1641 ep_buf[5].set(self.registers.windexh.read(Byte::VALUE) as u8);
1642 ep_buf[6].set(self.registers.wlengthl.read(Byte::VALUE) as u8);
1643 ep_buf[7].set(self.registers.wlengthh.read(Byte::VALUE) as u8);
1644 let size = self.registers.wlengthl.read(Byte::VALUE)
1645 + (self.registers.wlengthh.read(Byte::VALUE) << 8);
1646
1647 self.client.map(|client| {
1648 match client.ctrl_setup(endpoint) {
1651 hil::usb::CtrlSetupResult::OkSetAddress => {}
1652 hil::usb::CtrlSetupResult::Ok => {
1653 if size == 0 {
1655 self.complete_ctrl_status();
1657 } else {
1658 match self
1659 .registers
1660 .bmrequesttype
1661 .read_as_enum(RequestType::DIRECTION)
1662 {
1663 Some(RequestType::DIRECTION::Value::HostToDevice) => {
1664 self.descriptors[endpoint]
1667 .state
1668 .set(EndpointState::Ctrl(CtrlState::WriteOut));
1669
1670 debug_tasks!("- task: ep0rcvout");
1691 self.registers.task_ep0rcvout.write(Task::ENABLE::SET);
1692 }
1693 Some(RequestType::DIRECTION::Value::DeviceToHost) => {
1694 self.descriptors[endpoint]
1695 .state
1696 .set(EndpointState::Ctrl(CtrlState::ReadIn));
1697 if self.dma_pending.get() {
1700 self.descriptors[endpoint]
1701 .request_transmit_in
1702 .set(true);
1703 } else {
1704 self.transmit_in_ep0();
1705 }
1706 }
1707 None => unreachable!(),
1708 }
1709 }
1710 }
1711 _err => {
1712 debug_tasks!("- task: ep0stall");
1714 self.registers.task_ep0stall.write(Task::ENABLE::SET);
1715 }
1716 }
1717 });
1718 }
1719
1720 CtrlState::ReadIn | CtrlState::ReadStatus | CtrlState::WriteOut => {
1721 internal_warn!("handle_ep0setup - unexpected state = {:?}", state);
1723 debug_tasks!("- task: ep0stall");
1724 self.registers.task_ep0stall.write(Task::ENABLE::SET);
1725 }
1726 }
1727 }
1728
1729 fn complete_ctrl_status(&self) {
1730 let endpoint = 0;
1731
1732 self.client.map(|client| {
1733 client.ctrl_status(endpoint);
1734 debug_tasks!("- task: ep0status");
1735 self.registers.task_ep0status.write(Task::ENABLE::SET);
1736 client.ctrl_status_complete(endpoint);
1737 self.descriptors[endpoint]
1738 .state
1739 .set(EndpointState::Ctrl(CtrlState::Init));
1740 });
1741 }
1742
1743 fn process_dma_requests(&self) {
1744 if self.dma_pending.get() {
1745 return;
1746 }
1747
1748 for (endpoint, desc) in self.descriptors.iter().enumerate() {
1749 if desc.request_transmit_in.take() {
1750 if endpoint == 0 {
1751 self.transmit_in_ep0();
1752 } else {
1753 self.transmit_in(endpoint);
1754 }
1755 if self.dma_pending.get() {
1756 break;
1757 }
1758 }
1759 if desc.request_transmit_out.take() {
1760 if endpoint == 0 {
1761 self.transmit_out_ep0();
1762 } else {
1763 self.transmit_out(endpoint);
1764 }
1765 if self.dma_pending.get() {
1766 break;
1767 }
1768 }
1769 }
1770 }
1771
1772 fn transmit_in_ep0(&self) {
1773 let endpoint = 0;
1774
1775 self.client.map(|client| {
1776 match client.ctrl_in(endpoint) {
1777 hil::usb::CtrlInResult::Packet(size, last) => {
1778 if size == 0 {
1779 internal_err!("Empty ctrl packet?");
1780 }
1781 self.start_dma_in(endpoint, size);
1782 if last {
1783 self.descriptors[endpoint]
1784 .state
1785 .set(EndpointState::Ctrl(CtrlState::ReadStatus));
1786 }
1787 }
1788
1789 hil::usb::CtrlInResult::Delay => {
1790 internal_err!("Unexpected CtrlInResult::Delay");
1791 }
1793
1794 hil::usb::CtrlInResult::Error => {
1795 debug_tasks!("- task: ep0stall");
1797 self.registers.task_ep0stall.write(Task::ENABLE::SET);
1798 }
1799 }
1800 });
1801 }
1802
1803 fn transmit_out_ep0(&self) {
1809 let endpoint = 0;
1810 self.start_dma_out(endpoint);
1811 }
1812
1813 fn transmit_in(&self, endpoint: usize) {
1814 debug_events!("transmit_in({})", endpoint);
1815
1816 self.client.map(|client| {
1817 let (transfer_type, in_state, out_state) =
1818 self.descriptors[endpoint].state.get().bulk_state();
1819 assert_eq!(in_state, Some(BulkInState::Init));
1820
1821 let result = client.packet_in(transfer_type, endpoint);
1822 debug_packets!("packet_in => {:?}", result);
1823 let new_in_state = match result {
1824 hil::usb::InResult::Packet(size) => {
1825 self.start_dma_in(endpoint, size);
1826 BulkInState::InDma
1827 }
1828
1829 hil::usb::InResult::Delay => {
1830 BulkInState::Init
1832 }
1833
1834 hil::usb::InResult::Error => {
1835 self.registers.epstall.write(
1836 EndpointStall::EP.val(endpoint as u32)
1837 + EndpointStall::IO::In
1838 + EndpointStall::STALL::Stall,
1839 );
1840 BulkInState::Init
1841 }
1842 };
1843
1844 self.descriptors[endpoint].state.set(EndpointState::Bulk(
1845 transfer_type,
1846 Some(new_in_state),
1847 out_state,
1848 ));
1849 });
1850 }
1851
1852 fn transmit_out(&self, endpoint: usize) {
1853 debug_events!("transmit_out({})", endpoint);
1854
1855 let (transfer_type, in_state, out_state) =
1856 self.descriptors[endpoint].state.get().bulk_state();
1857 assert!(matches!(out_state, Some(BulkOutState::OutData { .. })));
1859 self.start_dma_out(endpoint);
1860
1861 let size = if let Some(BulkOutState::OutData { size }) = out_state {
1862 size
1863 } else {
1864 0
1865 };
1866
1867 self.descriptors[endpoint].state.set(EndpointState::Bulk(
1868 transfer_type,
1869 in_state,
1870 Some(BulkOutState::OutDma { size }),
1871 ));
1872 }
1873
1874 fn start_dma_in(&self, endpoint: usize, size: usize) {
1875 let slice = self.descriptors[endpoint].slice_in.unwrap_or_panic(); self.debug_in_packet(size, endpoint);
1877
1878 self.set_pending_dma();
1880 self.registers.epin[endpoint].set_buffer(&slice[..size]);
1881 debug_tasks!("- task: startepin[{}]", endpoint);
1882 self.registers.task_startepin[endpoint].write(Task::ENABLE::SET);
1883 }
1884
1885 fn start_dma_out(&self, endpoint: usize) {
1886 let slice = self.descriptors[endpoint].slice_out.unwrap_or_panic(); self.set_pending_dma();
1890 self.registers.epout[endpoint].set_buffer(slice);
1891 debug_tasks!("- task: startepout[{}]", endpoint);
1892 self.registers.task_startepout[endpoint].write(Task::ENABLE::SET);
1893 }
1894
1895 fn debug_in_packet(&self, size: usize, endpoint: usize) {
1897 let slice = self.descriptors[endpoint].slice_in.unwrap_or_panic(); if size > slice.len() {
1899 panic!("Packet is too large: {}", size);
1900 }
1901
1902 let mut packet_hex = [0; 128];
1903 packet_to_hex(slice, &mut packet_hex);
1904 debug_packets!(
1905 "in={}",
1906 core::str::from_utf8(&packet_hex[..(2 * size)]).unwrap()
1907 );
1908 }
1909
1910 fn debug_out_packet(&self, size: usize, endpoint: usize) {
1912 let slice = self.descriptors[endpoint].slice_out.unwrap_or_panic(); if size > slice.len() {
1914 panic!("Packet is too large: {}", size);
1915 }
1916
1917 let mut packet_hex = [0; 128];
1918 packet_to_hex(slice, &mut packet_hex);
1919 debug_packets!(
1920 "out={}",
1921 core::str::from_utf8(&packet_hex[..(2 * size)]).unwrap()
1922 );
1923 }
1924}
1925
1926impl power::PowerClient for Usbd<'_> {
1927 fn handle_power_event(&self, event: power::PowerEvent) {
1928 match event {
1929 power::PowerEvent::UsbPluggedIn => self.enable(),
1930 power::PowerEvent::UsbPluggedOut => self.disable(),
1931 power::PowerEvent::UsbPowerReady => self.power_ready(),
1932 _ => internal_warn!("usbc::handle_power_event: unknown power event"),
1933 }
1934 }
1935}
1936
1937impl<'a> hil::usb::UsbController<'a> for Usbd<'a> {
1938 fn set_client(&self, client: &'a dyn hil::usb::Client<'a>) {
1939 self.client.set(client);
1940 }
1941
1942 fn endpoint_set_ctrl_buffer(&self, buf: &'a [VolatileCell<u8>]) {
1943 if buf.len() < 8 {
1944 panic!("Endpoint buffer must be at least 8 bytes");
1945 }
1946 if !buf.len().is_power_of_two() {
1947 panic!("Buffer size must be a power of 2");
1948 }
1949 self.descriptors[0].slice_in.set(buf);
1950 self.descriptors[0].slice_out.set(buf);
1951 }
1952
1953 fn endpoint_set_in_buffer(&self, endpoint: usize, buf: &'a [VolatileCell<u8>]) {
1954 if buf.len() < 8 {
1955 panic!("Endpoint buffer must be at least 8 bytes");
1956 }
1957 if !buf.len().is_power_of_two() {
1958 panic!("Buffer size must be a power of 2");
1959 }
1960 if endpoint == 0 || endpoint >= NUM_ENDPOINTS {
1961 panic!("Endpoint number is invalid");
1962 }
1963 self.descriptors[endpoint].slice_in.set(buf);
1964 }
1965
1966 fn endpoint_set_out_buffer(&self, endpoint: usize, buf: &'a [VolatileCell<u8>]) {
1967 if buf.len() < 8 {
1968 panic!("Endpoint buffer must be at least 8 bytes");
1969 }
1970 if !buf.len().is_power_of_two() {
1971 panic!("Buffer size must be a power of 2");
1972 }
1973 if endpoint == 0 || endpoint >= NUM_ENDPOINTS {
1974 panic!("Endpoint number is invalid");
1975 }
1976 self.descriptors[endpoint].slice_out.set(buf);
1977 }
1978
1979 fn enable_as_device(&self, speed: hil::usb::DeviceSpeed) {
1980 match speed {
1981 hil::usb::DeviceSpeed::Low => internal_err!("Low speed is not supported"),
1982 hil::usb::DeviceSpeed::Full => {}
1983 }
1984 self.start();
1985 }
1986
1987 fn attach(&self) {
1988 debug_info!("attach() - State={:?}", self.get_state());
1989 self.enable_pullup();
1990 }
1991
1992 fn detach(&self) {
1993 debug_info!("detach() - Disabling pull-ups");
1994 self.disable_pullup();
1995 }
1996
1997 fn set_address(&self, _addr: u16) {
1998 debug_info!("Set Address = {}", _addr);
2000 }
2001
2002 fn enable_address(&self) {
2003 let _regs = &*self.registers;
2004 debug_info!("Enable Address = {}", _regs.usbaddr.read(UsbAddress::ADDR));
2005 }
2007
2008 fn endpoint_in_enable(&self, transfer_type: TransferType, endpoint: usize) {
2009 match transfer_type {
2010 TransferType::Control => {
2011 panic!("There is no IN control endpoint");
2012 }
2013 TransferType::Bulk | TransferType::Interrupt => {
2014 if endpoint == 0 || endpoint >= NUM_ENDPOINTS {
2015 panic!("Bulk/Interrupt endpoints are endpoints 1 to 7");
2016 }
2017 self.enable_in_endpoint_(transfer_type, endpoint);
2018 }
2019 TransferType::Isochronous => unimplemented!("isochronous endpoint"),
2020 }
2021 }
2022
2023 fn endpoint_out_enable(&self, transfer_type: TransferType, endpoint: usize) {
2024 match transfer_type {
2025 TransferType::Control => {
2026 if endpoint != 0 {
2027 panic!("Only endpoint 0 can be a control endpoint");
2028 }
2029 self.enable_out_endpoint_(transfer_type, endpoint);
2030 }
2031 TransferType::Bulk | TransferType::Interrupt => {
2032 if endpoint == 0 || endpoint >= NUM_ENDPOINTS {
2033 panic!("Bulk/Interrupt endpoints are endpoints 1 to 7");
2034 }
2035 self.enable_out_endpoint_(transfer_type, endpoint);
2036 }
2037 TransferType::Isochronous => unimplemented!("isochronous endpoint"),
2038 }
2039 }
2040
2041 fn endpoint_in_out_enable(&self, transfer_type: TransferType, endpoint: usize) {
2042 match transfer_type {
2043 TransferType::Control => {
2044 panic!("There is no IN control endpoint");
2045 }
2046 TransferType::Bulk | TransferType::Interrupt => {
2047 if endpoint == 0 || endpoint >= NUM_ENDPOINTS {
2048 panic!("Bulk/Interrupt endpoints are endpoints 1 to 7");
2049 }
2050 self.enable_in_out_endpoint_(transfer_type, endpoint);
2051 }
2052 TransferType::Isochronous => unimplemented!("isochronous endpoint"),
2053 }
2054 }
2055
2056 fn endpoint_resume_in(&self, endpoint: usize) {
2057 debug_events!("endpoint_resume_in({})", endpoint);
2058
2059 let (_, in_state, _) = self.descriptors[endpoint].state.get().bulk_state();
2062 assert!(in_state.is_some());
2065
2066 if self.dma_pending.get() || in_state != Some(BulkInState::Init) {
2070 debug_events!("requesting resume_in[{}]", endpoint);
2071 self.descriptors[endpoint].request_transmit_in.set(true);
2073 } else {
2074 self.transmit_in(endpoint);
2083 }
2084 }
2085
2086 fn endpoint_resume_out(&self, endpoint: usize) {
2087 debug_events!("endpoint_resume_out({})", endpoint);
2088
2089 let (transfer_type, in_state, out_state) =
2090 self.descriptors[endpoint].state.get().bulk_state();
2091 assert!(out_state.is_some());
2092
2093 match out_state.unwrap() {
2094 BulkOutState::OutDelay => {
2095 self.descriptors[endpoint].state.set(EndpointState::Bulk(
2098 transfer_type,
2099 in_state,
2100 Some(BulkOutState::Init),
2101 ));
2102 }
2103 BulkOutState::OutData { size: _ } => {
2104 if self.dma_pending.get() {
2108 debug_events!("requesting resume_out[{}]", endpoint);
2109 self.descriptors[endpoint].request_transmit_out.set(true);
2111 } else {
2112 self.transmit_out(endpoint);
2114 }
2115 }
2116 BulkOutState::Init | BulkOutState::OutDma { size: _ } => {
2117 internal_err!("Unexpected state: {:?}", out_state);
2118 }
2119 }
2120 }
2121}
2122
2123fn status_epin(ep: usize) -> Field<u32, EndpointStatus::Register> {
2124 match ep {
2125 0 => EndpointStatus::EPIN0,
2126 1 => EndpointStatus::EPIN1,
2127 2 => EndpointStatus::EPIN2,
2128 3 => EndpointStatus::EPIN3,
2129 4 => EndpointStatus::EPIN4,
2130 5 => EndpointStatus::EPIN5,
2131 6 => EndpointStatus::EPIN6,
2132 7 => EndpointStatus::EPIN7,
2133 8 => EndpointStatus::EPIN8,
2134 _ => unreachable!(),
2135 }
2136}
2137
2138fn status_epout(ep: usize) -> Field<u32, EndpointStatus::Register> {
2139 match ep {
2140 0 => EndpointStatus::EPOUT0,
2141 1 => EndpointStatus::EPOUT1,
2142 2 => EndpointStatus::EPOUT2,
2143 3 => EndpointStatus::EPOUT3,
2144 4 => EndpointStatus::EPOUT4,
2145 5 => EndpointStatus::EPOUT5,
2146 6 => EndpointStatus::EPOUT6,
2147 7 => EndpointStatus::EPOUT7,
2148 8 => EndpointStatus::EPOUT8,
2149 _ => unreachable!(),
2150 }
2151}
2152
2153fn inter_endepin(ep: usize) -> Field<u32, Interrupt::Register> {
2154 match ep {
2155 0 => Interrupt::ENDEPIN0,
2156 1 => Interrupt::ENDEPIN1,
2157 2 => Interrupt::ENDEPIN2,
2158 3 => Interrupt::ENDEPIN3,
2159 4 => Interrupt::ENDEPIN4,
2160 5 => Interrupt::ENDEPIN5,
2161 6 => Interrupt::ENDEPIN6,
2162 7 => Interrupt::ENDEPIN7,
2163 _ => unreachable!(),
2164 }
2165}
2166
2167fn inter_endepout(ep: usize) -> Field<u32, Interrupt::Register> {
2168 match ep {
2169 0 => Interrupt::ENDEPOUT0,
2170 1 => Interrupt::ENDEPOUT1,
2171 2 => Interrupt::ENDEPOUT2,
2172 3 => Interrupt::ENDEPOUT3,
2173 4 => Interrupt::ENDEPOUT4,
2174 5 => Interrupt::ENDEPOUT5,
2175 6 => Interrupt::ENDEPOUT6,
2176 7 => Interrupt::ENDEPOUT7,
2177 _ => unreachable!(),
2178 }
2179}
2180
2181fn packet_to_hex(packet: &[VolatileCell<u8>], packet_hex: &mut [u8]) {
2183 let hex_char = |x: u8| {
2184 if x < 10 {
2185 b'0' + x
2186 } else {
2187 b'a' + x - 10
2188 }
2189 };
2190
2191 for (i, x) in packet.iter().enumerate() {
2192 let x = x.get();
2193 packet_hex[2 * i] = hex_char(x >> 4);
2194 packet_hex[2 * i + 1] = hex_char(x & 0x0f);
2195 }
2196}
2197
2198#[allow(dead_code)]
2199fn ignored_str(
2200 saved_inter: &LocalRegisterCopy<u32, Interrupt::Register>,
2201 field: Field<u32, Interrupt::Register>,
2202) -> &'static str {
2203 if saved_inter.is_set(field) {
2204 ""
2205 } else {
2206 " (ignored)"
2207 }
2208}