diff --git a/hw/usb/hcd-ehci.c b/hw/usb/hcd-ehci.c index 159f58d5a080f7f693db3ccaeea5a5d2330591dd..d5c0e1c60dfd3b15043f324a0a51ee29b1e6f7fc 100644 --- a/hw/usb/hcd-ehci.c +++ b/hw/usb/hcd-ehci.c @@ -2011,6 +2011,7 @@ static int ehci_state_writeback(EHCIQueue *q) static void ehci_advance_state(EHCIState *ehci, int async) { EHCIQueue *q = NULL; + int itd_count = 0; int again; do { @@ -2035,10 +2036,12 @@ static void ehci_advance_state(EHCIState *ehci, int async) case EST_FETCHITD: again = ehci_state_fetchitd(ehci, async); + itd_count++; break; case EST_FETCHSITD: again = ehci_state_fetchsitd(ehci, async); + itd_count++; break; case EST_ADVANCEQUEUE: @@ -2087,7 +2090,8 @@ static void ehci_advance_state(EHCIState *ehci, int async) break; } - if (again < 0) { + if (again < 0 || itd_count > 16) { + /* TODO: notify guest (raise HSE irq?) */ fprintf(stderr, "processing error - resetting ehci HC\n"); ehci_reset(ehci); again = 0;