Driver Implementation of USB devices in Embedded linux

Source: Internet
Author: User


The embedded linux system environment is widely used in the embedded field because of its ease of transplantation and cutting, small kernel, high efficiency, integrity, open source code, and excellent performance. Linux USB device source code mainly includes the massive storage devices of USB device, serial devices, network devices, and other device drivers and drivers of various USB device controller chips. There are many types of USB device controller chips on the market. Most users need to develop related USB device controller drivers for specific applications to make the devices work normally in linux.

1 USB driver

The Linux Gadget subsystem is divided into three layers: the first layer is the chip driver layer, which abstracts various USB device controllers into unified function interfaces for upper-layer drivers to call; the second layer is a simple encapsulation of operation functions. The third layer is the device driver layer, which can implement the corresponding functions according to system requirements. Figure 1 shows the driver hierarchy of the Linux Gadget subsystem. The device driver layer of the Linux Gadget subsystem is used to implement drivers for various devices according to various specifications and protocols. In this design, an embedded device must have the mobile hard disk function, this function can be implemented based on the specifications and protocols of the massive storage class.

1.1 Basic architecture of UDC driver

Figure 2 shows the basic architecture of the UDC driver. In the controller driver, register the platform driver, call its probe function to search for devices, initialize structures such as usb_ep and usb_gadget in the probe function, register the devices, and apply for interruptions, then, wait for the interruption to enter the interrupt service subroutine, and finally declare and implement the function registration function of usb_gadget_register_driver and output it to the upper-layer driver. In this process, the link connecting them is some global struct variables.

1.2 Gadget API

The Gadget API defines a unified data structure and interface functions for the Gadget system. It is similar to the USB Core of the host, but its function is limited to providing programming interfaces, for example, use the structures usb_gadget_ops and usb_ep_ops to re-encapsulate the device controller driver operation function and Endpoint operation function. Specifically, the register function usb_gadget_register_driver of the Gadget driver is provided directly by the device controller (UDC) driver to bind the UDC to the gadget driver. This increases the dependency between the Gadget Driver and UDC.

On the device side, although the Gadget system is similar to the host driver system in a three-tier structure, the Gadget API only defines some data structures, macros, and function functions, and the UDC driver is simply packaged, without driver management and other functions.

1.3 device application drivers

The device application (Gadget Driver) is used to control the implementation of USB device functions, so that the device shows "network connection", "Printer" or "Large Storage Device" and other features. This article uses a large-capacity mobile storage device as an example to implement the mobile hard disk function.

BULK-ONLY transmission refers to a data transmission mode between a host and a large-capacity storage device.

2 device-side driver scheduling

In the embedded Linux operating system, the Gadget driver and the Gadget API can complete some USB protocol processing, bulk only, and other transmission protocols and instructions parsing, you only need to connect some USB protocol processing and the Gadget API in the device controller driver.

The flowchart shown in Figure 3 shows the basic scheduling idea of the driver on the USB device. The main idea of this solution is to passively accept the transmission commands of the host (any type of communication is initiated by the USB host, and the USB devices cannot communicate directly ), the host data transmission is completed through the interrupt trigger. When a device is interrupted, the device controller driver first determines the interrupt type. When it is an IN interrupt of the batch transmission endpoint, the driver will write the data IN the REQ linked to the EP into the memory zone of the device controller of the USB2.0 otg ip address IN sequence; when it is an OUT-of-batch transmission interrupt, the driver will read the data in the memory area of the device controller into the buffer in REQ; when it is a control transmission interrupt with the endpoint 0, the driver will read the data in the endpoint buffer and parse the current device request. If the request sent from the host to the device is usb reo sedress (set the device address), USB_REQ_GET_STATUS (get the device status), and USB_REQ_SET_FEATURE (set the device features ), the device controller driver automatically responds to the request. However, if it is a request from another device, such as GET_DESCRIPTOR (get device descriptor), the device controller Driver will submit the request to the Gadget Driver, then, the Gadget Driver queues and submits the device request to the endpoint, waiting for the next control endpoint to be interrupted.

Control transmission is complex, and it needs to complete the establishment phase, data transmission phase, and status phase. The entire control endpoint interrupt processing can be achieved through four States, namely, the endpoint 0 idle (EP0_IDLE), the data IN transmission (EP0 IN DATA_PHASE), and the data OUT transmission (EP0 OUT DATA_PHASE) and EPO_STATUS ). The EP0_IDLE status mainly processes the setup token in the setup phase, processes the device requests that can be processed according to the obtained device requests, and processes the requests that cannot be processed (such as obtaining the device descriptor and configuring the descriptor) submitted to the upper-layer Gadget Driver; EP0_OUT_DATA_PHASE status mainly processes OUT transmission IN the data phase; EP0_OUT_DATA_PHASE status mainly processes IN transmission IN the data phase; EP0_STATUS status mainly controls the status phase during transmission.

In the flowchart shown in figure 3, EP0 is the control transmission endpoint, and EP1, EP2, and EP3 are the batch transmission endpoint. They mainly include the endpoint transmission type, endpoint buffer size, and other information. REQ is an endpoint request submitted by the Gadget Driver. It mainly includes the length and address of the transmitted data.

3 UDC Design and Implementation

Device controller drivers are mainly divided into the Gadget Driver interface module, Gadget API function module, interrupt processing module, data structure definition, initialization module, and hardware read/write module. Each module can be independently designed.

3.1 data structure definition

According to the data structure provided by the Gadget API, you can define your own data structure (such as the device data structure otg_udc and the endpoint data structure otg_udc_ep) to describe the USB device controller.

After defining the data structure driven by a specific device controller, perform the corresponding static ing (static struct otg_ip_udcmemory ), in this way, the specific device controller, device endpoint, and the abstract data structure of the Gadget are linked.

3.2 Gadget Driver Interface Module

The UDC Driver provides the usb_gadget_driver_register module, which can implement function binding functions such as usb_gadget_register_driver to bind UDC and Gadget Driver.

3.3 Gadget API function module

The Linux USB gadget driver API defines a general interface of the gadget driver, which can be used to communicate with the underlying USB controller driver through the API. This API shields the underlying hardware from being different, so you can make the gadget driver focus only on the implementation of functions, and try to be unrelated to the hardware. The Code is as follows:

This module mainly implements the functions defined by the Gadget API, such as the functions in the Structure usb_ep_ops and usb_gadget_ops, and the registration functions of usb_gadget_register_driver. These functions can be called by the Gadget Driver.

3.4 Interrupt Processing Module

Because the device is passively controlled by the host, all actions of the device are triggered Based on device interruption. Therefore, the function mainly handles Reset interruptions, Resume interruptions, Suspend interruptions, EP0 interruptions, and other port interruptions.

3.5 initialization module

Initialization mainly refers to opening interruption, opening and setting the endpoint, setting the maximum Bus Steering time (this is the maximum waiting time between packages), and setting the maximum buffer length.

3.6 hardware read/write module

Similar to the host controller driver, the read/write mode of the device controller is PIO read/write and DMA read/write. The read/write content is also divided into Register read/write and endpoint buffer read/write. During reading and writing, all read and write addresses must be in dual-byte alignment mode.

4. Driving Test Results

The HCD studied in this article has been applied to actual engineering, as shown in hardware environment 4 of driver testing.

The hardware platform of this system is Realview EB, which is a highly integrated development board. The hardware resources on its parent board include: a FPGA (Xilinx Virtex-II XC2V6000) static and dynamic memory, integrated peripheral device, and two tile connectors for Core Tiles connection. You can create a micro-processing system by adding an additional Core Tile (ARM926EJS CORE. Logic Tile (Xilinx XC2V6000) contains an otg_ip chip with host controller function. otg_ip can be mounted to the mother plate EB through the on-chip Bus AHB. When running a Linux system on the Development Board, you can use the cross-compilation debugging environment to connect the development report to a PC. In this way, the debugging information can be printed on the terminal of the host through the serial port. Otg_ip can connect to the PHY chip through the ULPI interface and connect to the USB device.

After the device controller driver modules otg_ip_udc.ko and g_filestorage.ko are loaded successfully, the driver can be identified by inserting them as a USB interface of the mobile USB drive into the computer host. Figure 5 shows the result of kernel printing.

5 conclusion

USB Universal Serial Bus has the advantages of high transmission rate, low power consumption, hot swapping, and rapid development, the Linus operating system has the features of ease of transplantation and reduction, small kernel, high efficiency, and open source code. This article combines the Linux environment with the USB driver method, the large-capacity storage function can be quickly implemented. The experiment shows that the data read/write speed of the system can reach 681 kB/s, and the effect is good.

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: 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.