@@ -199,9 +199,9 @@ bool hcd_init(uint8_t rhport, const tusb_rhport_init_t* rh_init) {
199199 ohci_data .hcca .interrupt_table [i ] = (uint32_t ) _phys_addr (& ohci_data .period_head_ed );
200200 }
201201
202- ohci_data .control [0 ].ed .skip = 1 ;
203- ohci_data .bulk_head_ed .skip = 1 ;
204- ohci_data .period_head_ed .skip = 1 ;
202+ ohci_data .control [0 ].ed .w0 . skip = 1 ;
203+ ohci_data .bulk_head_ed .w0 . skip = 1 ;
204+ ohci_data .period_head_ed .w0 . skip = 1 ;
205205
206206 //If OHCI hardware is in SMM mode, gain ownership (Ref OHCI spec 5.1.1.3.3)
207207 if (OHCI_REG -> control_bit .interrupt_routing == 1 )
@@ -300,7 +300,7 @@ void hcd_device_close(uint8_t rhport, uint8_t dev_addr)
300300 // addr0 serves as static head --> only set skip bit
301301 if ( dev_addr == 0 )
302302 {
303- ohci_data .control [0 ].ed .skip = 1 ;
303+ hcd_dcache_uncached ( ohci_data .control [0 ].ed . w0 ) .skip = 1 ;
304304 }else
305305 {
306306 // remove control
@@ -323,11 +323,11 @@ void hcd_device_close(uint8_t rhport, uint8_t dev_addr)
323323//--------------------------------------------------------------------+
324324// List Helper
325325//--------------------------------------------------------------------+
326- static inline tusb_xfer_type_t ed_get_xfer_type (ohci_ed_t const * const p_ed )
326+ static inline tusb_xfer_type_t ed_get_xfer_type (ohci_ed_word0 w0 )
327327{
328- return (p_ed -> ep_number == 0 ) ? TUSB_XFER_CONTROL :
329- (p_ed -> is_iso ) ? TUSB_XFER_ISOCHRONOUS :
330- (p_ed -> is_interrupt_xfer ) ? TUSB_XFER_INTERRUPT : TUSB_XFER_BULK ;
328+ return (w0 . ep_number == 0 ) ? TUSB_XFER_CONTROL :
329+ (w0 . is_iso ) ? TUSB_XFER_ISOCHRONOUS :
330+ (w0 . is_interrupt_xfer ) ? TUSB_XFER_INTERRUPT : TUSB_XFER_BULK ;
331331}
332332
333333static void ed_init (ohci_ed_t * p_ed , uint8_t dev_addr , uint16_t ep_size , uint8_t ep_addr , uint8_t xfer_type , uint8_t interval )
@@ -337,21 +337,25 @@ static void ed_init(ohci_ed_t *p_ed, uint8_t dev_addr, uint16_t ep_size, uint8_t
337337 // address 0 is used as async head, which always on the list --> cannot be cleared
338338 if (dev_addr != 0 )
339339 {
340- tu_memclr (p_ed , sizeof (ohci_ed_t ));
340+ hcd_dcache_uncached (p_ed -> td_tail ) = 0 ;
341+ hcd_dcache_uncached (p_ed -> td_head ).address = 0 ;
342+ hcd_dcache_uncached (p_ed -> next ) = 0 ;
341343 }
342344
343345 tuh_bus_info_t bus_info ;
344346 tuh_bus_info_get (dev_addr , & bus_info );
345347
346- p_ed -> dev_addr = dev_addr ;
347- p_ed -> ep_number = ep_addr & 0x0F ;
348- p_ed -> pid = (xfer_type == TUSB_XFER_CONTROL ) ? PID_FROM_TD : (tu_edpt_dir (ep_addr ) ? PID_IN : PID_OUT );
349- p_ed -> speed = bus_info .speed ;
350- p_ed -> is_iso = (xfer_type == TUSB_XFER_ISOCHRONOUS ) ? 1 : 0 ;
351- p_ed -> max_packet_size = ep_size ;
352-
353- p_ed -> used = 1 ;
354- p_ed -> is_interrupt_xfer = (xfer_type == TUSB_XFER_INTERRUPT ? 1 : 0 );
348+ ohci_ed_word0 w0 = {.u = 0 };
349+ w0 .dev_addr = dev_addr ;
350+ w0 .ep_number = ep_addr & 0x0F ;
351+ w0 .pid = (xfer_type == TUSB_XFER_CONTROL ) ? PID_FROM_TD : (tu_edpt_dir (ep_addr ) ? PID_IN : PID_OUT );
352+ w0 .speed = bus_info .speed ;
353+ w0 .is_iso = (xfer_type == TUSB_XFER_ISOCHRONOUS ) ? 1 : 0 ;
354+ w0 .max_packet_size = ep_size ;
355+
356+ w0 .used = 1 ;
357+ w0 .is_interrupt_xfer = (xfer_type == TUSB_XFER_INTERRUPT ? 1 : 0 );
358+ hcd_dcache_uncached (p_ed -> w0 ) = w0 ;
355359}
356360
357361static void gtd_init (ohci_gtd_t * p_td , uint8_t * data_ptr , uint16_t total_bytes ) {
@@ -381,8 +385,9 @@ static ohci_ed_t * ed_from_addr(uint8_t dev_addr, uint8_t ep_addr)
381385
382386 for (uint32_t i = 0 ; i < ED_MAX ; i ++ )
383387 {
384- if ( (ed_pool [i ].dev_addr == dev_addr ) &&
385- ep_addr == tu_edpt_addr (ed_pool [i ].ep_number , ed_pool [i ].pid == PID_IN ) )
388+ ohci_ed_word0 w0 = hcd_dcache_uncached (ed_pool [i ].w0 );
389+ if ( (w0 .dev_addr == dev_addr ) &&
390+ ep_addr == tu_edpt_addr (w0 .ep_number , w0 .pid == PID_IN ) )
386391 {
387392 return & ed_pool [i ];
388393 }
@@ -397,41 +402,44 @@ static ohci_ed_t * ed_find_free(void)
397402
398403 for (uint8_t i = 0 ; i < ED_MAX ; i ++ )
399404 {
400- if ( !ed_pool [i ].used ) return & ed_pool [i ];
405+ if ( !hcd_dcache_uncached ( ed_pool [i ]. w0 ) .used ) return & ed_pool [i ];
401406 }
402407
403408 return NULL ;
404409}
405410
406411static void ed_list_insert (ohci_ed_t * p_pre , ohci_ed_t * p_ed )
407412{
408- p_ed -> next = p_pre -> next ;
409- p_pre -> next = (uint32_t ) _phys_addr (p_ed );
413+ hcd_dcache_uncached ( p_ed -> next ) = hcd_dcache_uncached ( p_pre -> next ) ;
414+ hcd_dcache_uncached ( p_pre -> next ) = (uint32_t ) _phys_addr (p_ed );
410415}
411416
412417static void ed_list_remove_by_addr (ohci_ed_t * p_head , uint8_t dev_addr )
413418{
414419 ohci_ed_t * p_prev = p_head ;
415420
416- while ( p_prev -> next )
421+ uint32_t ed_pa ;
422+ while ( (ed_pa = hcd_dcache_uncached (p_prev -> next )) )
417423 {
418- ohci_ed_t * ed = (ohci_ed_t * ) _virt_addr ((void * )p_prev -> next );
424+ ohci_ed_t * ed = (ohci_ed_t * ) _virt_addr ((void * )ed_pa );
419425
420- if (ed -> dev_addr == dev_addr )
426+ if (hcd_dcache_uncached ( ed -> w0 ). dev_addr == dev_addr )
421427 {
422428 // Prevent Host Controller from processing this ED while we remove it
423- ed -> skip = 1 ;
429+ hcd_dcache_uncached ( ed -> w0 ). skip = 1 ;
424430
425431 // unlink ed, will also move up p_prev
426- p_prev -> next = ed -> next ;
432+ hcd_dcache_uncached ( p_prev -> next ) = hcd_dcache_uncached ( ed -> next ) ;
427433
428434 // point the removed ED's next pointer to list head to make sure HC can always safely move away from this ED
429- ed -> next = (uint32_t ) _phys_addr (p_head );
430- ed -> used = 0 ;
431- ed -> skip = 0 ;
435+ hcd_dcache_uncached (ed -> next ) = (uint32_t ) _phys_addr (p_head );
436+ ohci_ed_word0 w0 = hcd_dcache_uncached (ed -> w0 );
437+ w0 .used = 0 ;
438+ w0 .skip = 0 ;
439+ hcd_dcache_uncached (ed -> w0 ) = w0 ;
432440 }else
433441 {
434- p_prev = (ohci_ed_t * ) _virt_addr ((void * )p_prev -> next );
442+ p_prev = (ohci_ed_t * ) _virt_addr ((void * )ed_pa );
435443 }
436444 }
437445}
@@ -477,7 +485,7 @@ bool hcd_edpt_open(uint8_t rhport, uint8_t dev_addr, tusb_desc_endpoint_t const
477485 // control of dev0 is used as static async head
478486 if ( dev_addr == 0 )
479487 {
480- p_ed -> skip = 0 ; // only need to clear skip bit
488+ hcd_dcache_uncached ( p_ed -> w0 ). skip = 0 ; // only need to clear skip bit
481489 return true;
482490 }
483491
@@ -519,7 +527,7 @@ bool hcd_setup_send(uint8_t rhport, uint8_t dev_addr, uint8_t const setup_packet
519527 hcd_dcache_clean (qtd , sizeof (ohci_gtd_t ));
520528
521529 //------------- Attach TDs list to Control Endpoint -------------//
522- ed -> td_head .address = (uint32_t ) _phys_addr (qtd );
530+ hcd_dcache_uncached ( ed -> td_head .address ) = (uint32_t ) _phys_addr (qtd );
523531
524532 OHCI_REG -> command_status_bit .control_list_filled = 1 ;
525533
@@ -554,12 +562,13 @@ bool hcd_edpt_xfer(uint8_t rhport, uint8_t dev_addr, uint8_t ep_addr, uint8_t *
554562 gtd -> delay_interrupt = OHCI_INT_ON_COMPLETE_YES ;
555563 hcd_dcache_clean (gtd , sizeof (ohci_gtd_t ));
556564
557- ed -> td_head .address = (uint32_t ) _phys_addr (gtd );
565+ hcd_dcache_uncached ( ed -> td_head ) .address = (uint32_t ) _phys_addr (gtd );
558566
559567 OHCI_REG -> command_status_bit .control_list_filled = 1 ;
560568 }else
561569 {
562570 ohci_ed_t * ed = ed_from_addr (dev_addr , ep_addr );
571+ tusb_xfer_type_t xfer_type = ed_get_xfer_type ( hcd_dcache_uncached (ed -> w0 ) );
563572 ohci_gtd_t * gtd = (ohci_gtd_t * )_virt_addr ((void * )hcd_dcache_uncached (ed -> td_tail ));
564573
565574 gtd_init (gtd , buffer , buflen );
@@ -576,7 +585,6 @@ bool hcd_edpt_xfer(uint8_t rhport, uint8_t dev_addr, uint8_t ep_addr, uint8_t *
576585
577586 hcd_dcache_uncached (ed -> td_tail ) = (uint32_t )_phys_addr (new_gtd );
578587
579- tusb_xfer_type_t xfer_type = ed_get_xfer_type ( ed_from_addr (dev_addr , ep_addr ) );
580588 if (TUSB_XFER_BULK == xfer_type ) OHCI_REG -> command_status_bit .bulk_list_filled = 1 ;
581589 }
582590
@@ -595,13 +603,12 @@ bool hcd_edpt_clear_stall(uint8_t rhport, uint8_t dev_addr, uint8_t ep_addr) {
595603 (void ) rhport ;
596604 ohci_ed_t * const p_ed = ed_from_addr (dev_addr , ep_addr );
597605
598- p_ed -> is_stalled = 0 ;
599- p_ed -> td_tail &= 0x0Ful ; // set tail pointer back to NULL
600-
601- p_ed -> td_head .toggle = 0 ; // reset data toggle
602- p_ed -> td_head .halted = 0 ;
606+ ohci_ed_td_head td_head = hcd_dcache_uncached (p_ed -> td_head );
607+ td_head .toggle = 0 ; // reset data toggle
608+ td_head .halted = 0 ;
609+ hcd_dcache_uncached (p_ed -> td_head ) = td_head ;
603610
604- if ( TUSB_XFER_BULK == ed_get_xfer_type (p_ed ) ) OHCI_REG -> command_status_bit .bulk_list_filled = 1 ;
611+ if ( TUSB_XFER_BULK == ed_get_xfer_type (hcd_dcache_uncached ( p_ed -> w0 ) ) ) OHCI_REG -> command_status_bit .bulk_list_filled = 1 ;
605612
606613 return true;
607614}
@@ -665,7 +672,7 @@ static void done_queue_isr(uint8_t hostid)
665672 (void ) hostid ;
666673
667674 // done head is written in reversed order of completion --> need to reverse the done queue first
668- ohci_td_item_t * td_head = list_reverse ( (ohci_td_item_t * ) tu_align16 (ohci_data .hcca .done_head ) );
675+ ohci_td_item_t * td_head = list_reverse ( (ohci_td_item_t * ) tu_align16 (hcd_dcache_uncached ( ohci_data .hcca ) .done_head ) );
669676 ohci_data .hcca .done_head = 0 ;
670677
671678 while ( td_head != NULL )
0 commit comments