December 8, 2020

USB - SOF interrupts

I am doing this the hard way, so to speak. I want to learn by experience, because when push comes to shove, that is the only kind of learning that really matters. So I push as far as I can with actual hardware and writing software and then go read as needed to explain what is going on.

So here is where I am at. I have the chip initialized and various interrupts are enabled. What I expected to do was to plug the cable in and to have the host send me a message asking "who are you?". It doesn't seem to be working that way. I am getting endless SOF interrupts, and now that I pay attention it is not really a furious interrupt loop like what happens when I am not acknowledging an interrupt. When I unplug the device I get a suspend interrupt, but that is not the topic as yet.

It turns out that the host sends an SOF every millisecond. So I am doing everything right (sort of). I am acking the interrupt, the issue is that 1 millisecond later, another comes along. These serve as sort of "keep alive" signals. If we don't get these for some period, we are supposed to go into the suspend state and wait for a reset or resume.

The article mentions that USB has a lot of overhead. I have heard this in other places, but now I am seeing it first hand. They say that high speed (480 Mb/s) can be up to 15 percent overhead. High Speed has SOF every 125 us (8 per millisecond) - these are called "microframes".

Some code I have looked at waits for 40 of these SOF signals, then tries to send something. I expected the host to send me something, but maybe I am simply supposed to introduce myself as soon as these SOF signals start coming along. This is not yet clear to me, but we will see. The SOF token is supposed to contain an 11 bit "frame number" that can be used for various purposes.

I change the code so my output is not flooded with these SOF interrupts being reported and now I see new and interesting things that were lost in the flood.
I am getting RESET signals at various intervals. Apparently the host is getting upset and suspicious that I am not responding as a good device ought to.

Here is what I see now. The first value is the interrupt status register in hex, the second is a count of SOF packets since the game started. The SOF count isa handy millisecond count, so we can see the final Suspend happens after 75 seconds.

Int -- Suspend 04000820 0
Int -- Reset 04801020 0
Int -- Enumeration done 04002020 0
Int -- Reset 04001030 15795
Int -- Enumeration done 04002030 15795
Int -- Reset 04001030 31652
Int -- Enumeration done 04002030 31652
Int -- Reset 04001030 31805
Int -- Enumeration done 04002030 31805
Int -- Reset 04009030 47496
Int -- Enumeration done 04002030 47496
Int -- Reset 04009030 63353
Int -- Enumeration done 04002030 63353
Int -- Suspend 04008C30 63506
Int -- Reset 04801030 63506
Int -- Enumeration done 04002030 63506
Int -- Enumeration done 04002030 63506
Int -- Reset 04001030 69560
Int -- Enumeration done 04002030 69560
Int -- Suspend 04008C30 75179

Messages on the linux side corresponding to this look like:

Dec  8 18:45:13 trona kernel: usb 3-1.2.3: new full-speed USB device number 69 using xhci_hcd
Dec  8 18:45:28 trona kernel: usb 3-1.2.3: device descriptor read/64, error -110
Dec  8 18:45:44 trona kernel: usb 3-1.2.3: device descriptor read/64, error -110
Dec  8 18:45:44 trona kernel: usb 3-1.2.3: new full-speed USB device number 70 using xhci_hcd
Dec  8 18:46:00 trona kernel: usb 3-1.2.3: device descriptor read/64, error -110
Dec  8 18:46:16 trona kernel: usb 3-1.2.3: device descriptor read/64, error -110
Dec  8 18:46:16 trona kernel: usb 3-1.2-port3: attempt power cycle
Dec  8 18:46:17 trona kernel: usb 3-1.2.3: new full-speed USB device number 71 using xhci_hcd
Dec  8 18:46:22 trona kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device command
Dec  8 18:46:22 trona kernel: usb 3-1.2.3: Device not responding to setup address.
Dec  8 18:46:23 trona kernel: usb 3-1.2.3: device not accepting address 71, error -71
Dec  8 18:46:23 trona kernel: usb 3-1.2.3: new full-speed USB device number 72 using xhci_hcd
Dec  8 18:46:28 trona kernel: xhci_hcd 0000:00:14.0: Timeout while waiting for setup device command
Dec  8 18:46:28 trona kernel: usb 3-1.2.3: Device not responding to setup address.
Dec  8 18:46:28 trona kernel: usb 3-1.2.3: device not accepting address 72, error -71
Dec  8 18:46:28 trona kernel: usb 3-1.2-port3: unable to enumerate USB device

Feedback? Questions? Drop me a line!

Tom's Computer Info / tom@mmto.org