USB device drivers

Source: Internet
Author: User
Document directory
  • A quick tour of the hardware
  • The various modules and their interrelations
  • How URBS keep it all together
  • Input Handling

Even though UNIX traditionally considers a device as either a "char device" or a "Block device" (as outlined by the 'C' or 'B' in their/DevEntry points), new classes of device are being introduced as technology advances. One of such classes is that of ''usb devices ''.

An USB device is still, at its lowest levels, a ''char devic'' or a ''block devic'' (this only if it is a mass-storage device ), but the programming interface offered to device driver writers has been simplified and ''factorized' in order to take advantage of the common hardware features offered by those devices and to offer arbitration of the bus and coordination in its use by the various drivers.

This discussion is based on version 2.3.99-pre3 of the Linux kernel, the one current at time of writing. I have CT little of no differences between this version and the 2.4 kernel that sits in front of you as you read. I chose to compile the USB subsystem as modules and discuss the role of individual modules as the modularized form helps understanding the overall design, as compared to a kernel with the whole USB subsystem linked in.

A quick tour of the hardware

While the ''usb ''acronym means ''universal serial bus'', its physical structure is not a bus. the physical layout is rather a tree, where each transmission link can only connect two nodes: one of them is called the "upstream" node and the other is called the "downstream" node. to make the distinction clearer and avoiding endless cabling problems like those we experience daily with serial interfaces, the USB specification requires different connectors at the upstream and the downstream end of the cables. what you see lurking from the back of your computer is not ''the USB ctor ''but rather ''the upstream USB connector'', also called type ''a ''.

Each non-leaf node in the tree is an USB hub. the host controller (the hardware installed in the computer set) implements an USB hub, as this is the only way to spit out several communication channels towards USB devices. to preserve the tree structure, it is not possible for a device to have two upstream connections -- while there exist USB devices that can interconnect two computers by connecting to two different USB busses, those devices are conceptually two separate USB peripherals, each connected to its own bus. figure 1 and figure 2 depict two typical USB environments and their physical structure represented as a tree.


Figure 1:A pc with usb kbd and mouse, and associated USB tree.

The image is available as postscript here


Figure 2:Overly-complex USB tree with hubs etc

The image is available as postscript here

As far as the host controller is concerned, all the implementations currently fall under one of two classes: ''open host controller interface'' (OHCI) and ''universal host controller interface'' (uhci ). in Linux You can thus choose between two device drivers for your USB subsystem:Usb-ohci.oAndUsb-uhci.o; Whatever hardware you have, the moduleUsbcore. oIs required in order to load the hardware driver.

When a device is plugged in the bus, it identifies itself as one of several classes of peripherals; in order to use the device you'll need to load a driver that reclaims ownership of that device and handles the associated communication protocol.

The USB Protocol allows for a variety of device types and bandwidth usage. to keep the discussion simple, I'll only stick to simple input devices, like mice and keyboards. those devices don't need a sustained data rate or strict timing, so are the easiest to discuss as well as the most renown to the general public.

The various modules and their interrelations

When you compile the USB Linux subsystem as modules, you'll end up with several kernel modules. while the internal communication among them is somehow complex, the dependencies of the modules are quite straightforward, as depicted in table 1 and figure 3.

Table 1 lists the main entry points exported and used by each module


Module Symbols exported by the module Symbols used at load and run time
Usbcore. o Usb_register (); Usb_deregister (); Register_chrdev ();
Usb_connect (); Usb_disconnect (); Register_filesystem ();
Usb_alloc_bus (); Usb_free_bus (); Kernel_thread ();
Usb_alloc_dev (); Usb_free_dev ();  
USB = OHCI. o     Pci_find_class ();
    Request_irq ();
    Usb_alloc_bus ();
    Usb_alloc_dev ();
Input. o Input_register_device (); Input_unregister_device ();  
Input_open_device (); Input_close_device ();  
Input_event ();    
Keybdev. o     Input_register_handler ();
Mousedev. o     Input_register_handler ();
Usbmouse. o     Usb_register ();
    Usb_submit_urb ()
    Input_register_device ();
    Input_event ();
Usbkbd. o     Usb_register ();
    Usb_submit_urb ()
    Input_register_device ();
    Input_event ();

As shown,USB coreModule offers all the software infrastructure needed for hardware handling whileInputOffers a generic input management framework; all other modules stack on those two, registering as either producers or consumers of information.

As far as hardware is concerned, the Host Controller Device Driver (OHCIOrUhci) Registers its functionalityUSB core'S data structures, and the same do the device-specific drivers (for example,UsbmouseAndUsbkbd); Their role is however different, as the host controller produces information (collected from the wire) while the other drivers consume information (by decoding the data and pushing it to its final destination ).

Input management operates in a similar way: hardware drivers (UsbmouseAndUsbkbd) Produce data and the generic input handlers (MousedevAndKeybdev) Consume data. Both kinds of modules stack onInput. o, Registering their own entry points.

The question still unanswered is how can a module push information to another moduleOnlyRegistering a callback. if you are confident with generic kernel drivers, you'll remember that things are usually set up the other way round: the consumer module registers its callback to be invoked whenever there is new data to consume. the USB driver is laid out differently because it is designed as a message-passing environment, instead of being a data-flow system like most of the Linux kernel. the key data structure, the ''message', is called ''urb', short for ''usb request block ''.

How URBS keep it all together

When a USB hardware driver is loaded, it CILSusb_alloc_bus()To register its ownusb_operationsData StructureUsbcore. o(The data structure is defined in<linux/usb.h>Like every other header material relevant to this article). The operations thus registered includesubmit_urbAndunlink_urb, So the software layer can commit data transfer to the hardware driver.

With the software layer and the hardware drivers in place, a specific peripheral driver (likeUsbmouse. o) Can register its ownusb_driverData structure by callingusb_register(). The data structure between des pointers toprobeAnddisconnectFunction. The former is called by the USB framework whenever a new device is detected and the latter whenever the device is unplugged from the bus.

When the probe succeeds (I. e., the new USB device can be handled by this device driver), the function submits its urb structure to the USB engine (by callingusb_submit_urb()), Including in the urb a pointer to its ''completion handler', a callback that will be invoked at the end of each hardware transaction.

Withinusb_submit_urb, The urb is passed back to the host controller interface, so that the hardware driver can fill the urb buffers with relevant information and call the proper completion handler when a data transfer happens.

As of 2.3.99-pre3, the module usage count is behaving in a peculiar way. Even though the USB device driver (suchUsbmouse. o) Is notified when the peripheral device is connected to the bus, its usage count is never incremented, And You cocould remove the device driver module whenever you want.

While this description referred to mice and keyboards, the same design rules apply to other USB peripheral devices. the difference is mainly in how hardware handles the individual transactions: Not every device works like keyboards and mice, a digital camera for example needs to push a sustained data rate into the bus. the USB specification describes a few different transaction types, and all of them are handled by the USB Linux subsystem using URBS.

Input Handling

Although the issue is not directly related to USB hardware, I think it's interesting to see how USB input devices, like keyboards and mice, are designed as part of a more generic input mechanic, implemented in the source filedrivers/usb/input.c.

As already outlined (and shown in table 1), the USB modules for keyboards and mice stack onInputModule as ''producers' of data, while more generic modules (MousedevAndKeybdev) Stack onInputAs consumers of data.


Figure 3:Dependencies among USB modules

The image is available as postscript here

Whenever an USB input driver's completion handler is invoked, it pushes the data just passed ed to the input management engine, by callinginput_event().

A ''consumer' module registers its own callbacksInput. o, By callingInput_register_handler ()At load time.input_handlerData structure includes pointers to Three callbacks:connect,disconnectAndevent, All that's needed for proper device management. What actually consumes input data iseventHandler.

The roleinput_event(), As called by the completion function of the peripheral USB driver, is that of distributing the input data to all the registered handlers. each handler will just ignore data it is not interested in. thus, if you didn't loadKeybdev. o, Your USB keyboard will be ignored by the system, even though you loadedUsbkbdModule and key-presses are correctly decoded and passed to the input engine.

The input handling machinery is very interesting, in my opinion, as it allows insertion of custom kernel modules in the event chain, both as producers and consumers of input events. A new event producer cocould push keyboard or mouse events down the system's chain even though it is not physically a keyboard, while a new event consumer can associate special actions (any action) to input events. that's a flexible tool for people who play with non-standard devices or need to implement non-standard behaviors in their kernels.

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.