Subject: Re: USB control endpoint stalled
To: None <tech-kern@NetBSD.org>
From: Edgar =?iso-8859-1?B?RnXf?= <Edgar.Fuss@bn2.maus.net>
List: tech-kern
Date: 03/15/2007 11:27:18
Thanks very much for your detailed reply.

I'm trying to talk to a Masterguard UPS via USB.
The problem is that the most helpful people at Masterguard didn't build
the USB interface themselves, but outsourced that and only got a M$ Win
driver. However, they, helpful as they are, supplied me with a trace of
the driver talking to the UPS. The interesting part of it reads as follows:

Vendor-Specific Request (DOWN)
Destination: Endpoint, Index 0
Reserved Bits: 9
Request: 0xd
Value: 0x0
Send 0x3 bytes to the device

I deduced from this that I had to send a vendor-specific request #0x0d
to the control endpoint. I can't make sense of the "reserved bits".

> The device can return a STALL handshake to indicate an error.
Do I read this correctly as that the device actively generates this
"STALL" condition and it's not something like a timeout or protocol
violation?

> Because the type is 0x42, this is a 
> "host-to-device, vendor-specific request directed 
> at an endpoint", where the endpoint is specified 
> by the low 8 bits of wIndex.  The request code is 0x0D.
Good. That looks exactly like what I intended to do.

> This request fails.
Where "fails" means that the UPS actively answers that it cannot
handle the request?

> Since this is a vendor request, it's seems likely that you're running 
> software that doesn't actually know how to talk to your device.
As mentioned, the software is of my own making.
However, most of the time, it works. But sometimes something (where I
can't tell being that the USB stack, the UPS or whatever) seems to get
stuck and the only known ways to get it work again is either to wait
something in he order of ten minutes or re-plug the USB cable.
I've also no idea what leads to the "stuck" state.

> this sends the setup.
Where "setup" is USB speak meaning aproximately what "CDB" would be
in SCSI?

> >TD(0xffff80004dc4d6c0) at 082b46c0: 
> >f3ec0000<R,OUT,TOG1,SETTOGGLE> delay=7 ec=0 cc=15
> >cbp=0x07b9dec0 nexttd=0x082b4710 be=0x07b9dec2
> 
> this sends the two bytes of data
TWO bytes? That would exactly explain the problem as I have to send
THREE bytes. Where do you read from that I'm erroneously sending only two?

> This usually means that your device doesn't understand the request.
Hm. Now I have to find out why it sometimes does and sometimes does not
understand the same request?

Can there be anny issue with timing? Like the NetBSD USB stack overrunning
the "well, it works with Window$"-type device. Any knobs to turn?

> Your driver, or the stack issues this.
Must be the stack.

> It also seems to complete without errors, which 
> means the device is NOT stuck in the STALL state.
OK, that's a most valuable thing for me to know.

If your analysis that I'm only sending two instead of three bytes
is correct I'll have to find out what makes that happen.
Could you be so kind as to double-check that?
And instruct me how I can extract that information from the trace?

> Then the app gives up and closes ugen:
OK.

> Then the app reopens.
Well, that's actually the operator (e.g. me) re-starting gdb.
Seems like I sent to large an excerpt of the syslog trace.

> The app does the same thing over and over?
No. It won't close and re-open ugen. It either retries sending the
command after a delay or gives up, closes ugen and returns an error.

> Seems like the app is the problem, not the device.
Maybe yes. If it would only either work all the time or fail all the time.
Indeed, yesterday, I was happy that it consistently failed while I was
trying to produce the trace.


Two remaining questions:

1. Can anyone make any sense of the "reserved bits" mentioned in the trace
they provided me? From the relevant parts of the USB spec I read, I could
not find any field of at least five bits that could hold a value of 9
and be called "reserved"

2. With the NetBSD stack, is there any way to do something like a USB reset,
e.g. something in software close to walk down to the server room and
phyically re-plug the cable?

Thanks again a lot for your most detailed reply.