Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[BUG] errors with other traffic on the bus #224

Open
nerdralph opened this issue Mar 9, 2021 · 4 comments
Open

[BUG] errors with other traffic on the bus #224

nerdralph opened this issue Mar 9, 2021 · 4 comments

Comments

@nerdralph
Copy link
Contributor

As mentioned in #223, the presence of other traffic on the bus can cause MN errors.

One possibility is because the bus idle detection time is too short.
https://github.com/micronucleus/micronucleus/blob/master/firmware/main.c#L554

If the hub sends a token packet for a different device on the bus, and the device sends a data packet in response, the AVR will not see the data packet. It will only see the token, then a delay of up to 80us while the other device sends the data packet, then the AVR will see the ACK packet from the host back to the device.

@nerdralph nerdralph added the bug label Mar 9, 2021
@nerdralph
Copy link
Contributor Author

I've been experimenting with the USBpoll collision bus idle detection loop. 80us makes things much worse. Although I didn't hook up my scope or logic analyzer, I'm confident what is happening is when MN misses the first IN packet after a SETUP transaction, the host waits for ~20us before re-transmitting the IN. An 80us idle means MN will miss all three IN packets, and enumeration will fail. I tried waiting for SEO (EOP), and that seems a bit worse than the 8.8uS wait.
I'm wondering where the 8.8us comes from?
https://github.com/micronucleus/micronucleus/blob/master/firmware/main.c#L549

6 1 bits would look like idle for 4us, so I wonder if 4.5 or 5us wouldn't be better.

Although I don't have a specific suggestion, I think there should be a better way of doing the polling loop.

@cpldcpu
Copy link
Member

cpldcpu commented Mar 11, 2021

The 8.8µs are basically the shortest time D- is idle between two packets. I am not 100% sure how I derived it back then, but I am quite certain that there is a reason for chosing that number. At least on my computer there are three identicaly transmissions right after another before timing out. There is no gap or wait time. If you increase this wait time, then the bus idle condition would only be recognized directly before SOF. This is something we want to avoid, since the host could timeout (3x resend) and the effective data transfer rate will suffer a lot.

Originally I used D+ for idle detection, which would have allowed a longer waiting time but that collided with some of Olimex device that had a lot of noise on USB pins when no USB was connected.

See here at the end:
https://cpldcpu.wordpress.com/2014/03/02/interrupt-free-v-usb/

@cpldcpu cpldcpu added enhancement and removed bug labels Aug 3, 2021
@cpldcpu
Copy link
Member

cpldcpu commented Aug 3, 2021

I relabeled this as an enhancement, as I am not sure if this is a persisting problem with the current codebase? Can this issue be reproduced?

Bus collision was an issue on osccal, but that has been fixed with @nerdralphs excellent new osccal code.

@nerdralph
Copy link
Contributor Author

nerdralph commented Aug 6, 2021 via email

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants