Interrupt handling, Support for usb testing – Comtrol eCos User Manual
Page 714
Writing a USB Device Driver
Interrupt Handling
A typical USB device driver will need to service interrupts for all of the endpoints and possibly for additional USB
events such as entering or leaving suspended mode. Usually these interrupts need not be serviced directly by the
ISR. Instead, they can be left to a DSR. If the peripheral is not able to accept or send another packet just yet, the
hardware will generate a NAK and the host will just retry a little bit later. If high throughput is required then it may
be desirable to handle the bulk transfer protocol largely at ISR level, that is take care of each packet in the ISR and
only activate the DSR once the whole transfer has completed.
Control messages may involve invoking arbitrary callback functions in higher-level code. This should normally
happen at DSR level. Doing it at ISR level could seriously affect the system’s interrupt latency and impose unac-
ceptable constraints on what operations can be performed by those callbacks. If the device driver requires a thread
anyway then it may be appropriate to use this thread for invoking the callbacks, but usually it is not worthwhile to
add a new thread to the system just for this; higher-level code is expected to write callbacks that function sensibly
at DSR level. Much the same applies to the completion functions associated with data transfers. These should also
be invoked at DSR or thread level.
Support for USB Testing
Optionally a USB device driver can provide support for the
. This requires defining a number
of additional data structures, allowing the generic test code to work out just what the hardware is capable of and
hence what testing can be performed.
The key data structure is usbs_testing_endpoint, defined in
cyg/io/usb/usbs.h
. In addition some commonly
required constants are provided by the common USB package in
cyg/io/usb/usb.h
. One usbs_testing_endpoint
structure should be defined for each supported endpoint. The following fields need to be filled in:
endpoint_type
This specifies the type of endpoint and should be one of
USB_ENDPOINT_DESCRIPTOR_ATTR_CONTROL
,
BULK
,
ISOCHRONOUS
or
INTERRUPT
.
endpoint_number
This identifies the number that should be used by the host to address this endpoint. For a control endpoint it
should be 0. For other types of endpoints it should be between 1 and 15.
endpoint_direction
For control endpoints this field is irrelevant. For other types of endpoint it should be either
USB_ENDPOINT_DESCRIPTOR_ENDPOINT_IN
or
USB_ENDPOINT_DESCRIPTOR_ENDPOINT_OUT
. If a given
endpoint number can be used for traffic in both directions then there should be two entries in the array, one
for each direction.
endpoint
This should be a pointer to the appropriate usbs_control_endpoint, usbs_rx_endpoint or usbs_tx_endpoint
structure, allowing the generic testing code to perform low-level I/O.
devtab_entry
If the endpoint also has an entry in the system’s device table then this field should give the corresponding
string, for example
"/dev/usbs1r"
. This allows the generic testing code to access the device via higher-level
610