USB 驅動相關基礎知識記錄
在usb_20.pdf中解釋了USB(Universal Serial Bus,通用序列匯流排)的最初目的:
○ Connection of the PC to the telephone ——> 廉價的方案實現計算機領域和通訊領域的連線
○ Ease-of-use ——> 支援即插即用
○ Port expansion ——> 介面統一
a. usb理論傳輸速度:
USB 1.0的傳輸速度是1.5Mbps=192KB/s,稱為低速USB,如USB鍵盤滑鼠等
USB 1.1的傳輸速度是12Mbps=1.5MB/s,稱為全速USB
USB 2.0的傳輸速度是480Mbps=60MB/s,稱為高速USB,如USB儲存器等
USB 3.0的傳輸速度是5Gbps=600MB/s,稱為超高速USB,如USB行動硬碟等
USB 3.2···
b. usb介面型別及引腳定義
USB的介面型別,根據介面形狀不同,主要可以分為三大類:
i. 普通的硬體直接叫做Type
ii. 小型版本的叫Mini迷你的
iii. 更加小的,叫做Micro微小的
其中每一種大類中,又都可以分為兩類
i. A類(Type A)
ii. B類(Type B)
下面詳細對比USB的各種介面,包括對應的插頭和插座:
引腳定義:
USB 2.0 USB 3.0
USB2.0向下相容USB1.0和1.1,host和裝置之間的速度識別,依靠D+和D-線的電平高低及列舉時雙方通訊確定的。
c. USB主機控制器分類:
i. UHCI(Universal Host Controller Interface,通用主機控制器介面):該標準有Intel提出,常用在基於Intel的PC機上
ii. OHCI(Open Host Controller Interface,開放主機控制器介面):由Compaq,Microsoft等公司提出.
共同點:都是基於USB 1.1的標準的,完全符合USB協議標準。
不同點:
OHCI更多地把要做的事情,用硬體來實現,因此實現OHCI的USB控制器(HCD->Host Controller Drivers)的軟體驅動的開發工作,相對要容易些,軟體要做的事情相對較少。對應地,OHCI更多地應用在擴充套件卡,尤其是嵌入式領域中,常見的很多開發板中的USB的控制器,很多都是OHCI的。而UHCI把更多的功能,留給了軟體,相對來說軟體做的事情,即負擔要重些。但是實現對應的UHCI的硬體的USB控制器,價格上,就相對便宜些。對應地,UHCI更多地應用在PC機中的主機板上的USB控制器。
iii. EHCI(Enhanced Host Controller Interface,增強型主機控制器介面),基於USB2.0協議標準,但是相容UHCI和OHCI控制器用於支援低速USB裝置
iv. xHCI(Extensible Host Controller Interface,擴充套件主機控制器介面),基於USB3.0協議標準。
v. USB OTG(On-The-Go)控制器:常用於嵌入式微控制器領域,該技術使每個通訊終端都能充當DRD(Dual-Role Device,雙重角色裝置),即可以利用主機溝通協議根據功能需要在主機模式和裝置模式之間任意切換。
2. USB子系統在核心中的位置
如下圖所示,USB 驅動位於不同的核心子系統(塊裝置, 網路裝置, 字元裝置等等)和USB硬體控制器之間. USB 核心為 USB 驅動提供了一個介面用於訪問和控制 USB 硬體, 而不必考慮出現在系統中的不同的 USB 硬體控制器.
USB Device Driver 向下利用 USB Core 提供的介面訪問和控制硬體(Hardware),向上表現為將 USB 裝置抽象成塊裝置,網路裝置或字元裝置同 User 使用。
3. usb裝置連線星形拓撲圖
一個 USB host 最多支援128個地址,地址0作為預設地址,只在裝置列舉時臨時使用,而不能分配給任何一個裝置,因此一個host最多同時支援127個地址。若一個裝置佔用一個地址,USB hub也是需要佔用地址的,所以一個USB host實際可支援的裝置一定少於127個。
USB 體系採用分層的星形拓撲連線所有USB裝置,以HOST-ROOT Hub為起點,最多支援7層,也就是說一個USB系統中最多允許使用5個USB Hub級聯。
usb_20.pdf->ch4 4.1.1 Bus Topology
4. USB裝置組織及端點定址
在USB裝置的邏輯組織中,包含裝置,配置,介面和端點4個層次,一個裝置通常有一個或多個配置,一個配置有一個或多個介面,一個介面有零個或多個端點。同一裝置的不同配置使裝置對外表現出不同的功能組合(在探測/連線時選擇一個配置)。在USB協議中,介面由多個端點組成,代表一個基本的功能,是USB裝置驅動程式控制的物件。
舉例:
一個USB播放器帶有音訊、視訊、旋鈕和按鈕。
配置1:音訊(介面)+ 旋鈕(介面)
配置2:音訊(介面)+ 旋鈕(介面)+ 視訊(介面)
配置3:音訊(介面)+ 視訊(介面)
而音訊介面,視訊介面,按鈕介面,旋鈕介面均需要一個驅動程式。
USB裝置中唯一可定址的部分是端點,可以抽象成USB裝置上的一個數據緩衝區,用來存放和傳送USB的各種資料。主機和裝置的通訊最終作用於省的各個端點,它是主機和裝置間通訊的一個邏輯終端。
每個USB裝置在USB總線上都有一個唯一的地址,在連線主機時由主機分配,而USB裝置中的每個端點在裝置內部有唯一的端點號,是在設計裝置是指定的。所以在USB裝置被列舉時,必須向主機報告自己所有端點的特性,包括端點號,通訊方向,端點支援的最大包大小等(詳見usb_endpoint_descriptor結構體)。每個裝置必須有端點0,用於裝置列舉時對裝置進行基本的控制功能,除了端點0其餘端點在裝置配置之前不能與主機通訊,只有向主機報告這些端點的特性並確認後才能被啟用。
5. USB描述符
標準USB裝置5種USB描述符,包括:
裝置描述符(usb_device_descriptor)->usb_20.pdf->ch9 Table 9-8
配置描述符(usb_config_descriptor)->usb_20.pdf->ch9 Table 9-10
介面描述符(usb_interface_descriptor)->usb_20.pdf->ch9 Table 9-12
端點描述符(usb_endpoint_descriptor)->usb_20.pdf->ch9 Table 9-13
字串描述符(usb_string_descriptor)->usb_20.pdf->ch9 Table 9-16
各描述符關係:
與USB裝置組織類似,一個USB裝置只有一個USB描述符,而一個USB描述符可以包含多個配置描述符,一個配置描述符可以包含多個介面描述符,一個介面使用了幾個端點就有幾個端點描述符,字串描述符是可選的,包含一些裝置的描述資訊。
各種描述符在原始碼中的聯絡:
例如在裝置上插入U盤,使用lsusb命令:
# lsusb -d 1976:1307 -v
檢視到U盤資訊->HYUNDAI.lsusb
Bus 001 Device 003: ID 1976:1307 Chipsbrand Microelectronics (HK) Co., Ltd.
Device Descriptor:
bLength 18
bDescriptorType 1
bcdUSB 2.00
bDeviceClass 0 (Defined at Interface level)
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 64
idVendor 0x1976 Chipsbrand Microelectronics (HK) Co., Ltd.
idProduct 0x1307
bcdDevice 1.00
iManufacturer 1 ChipsBnk
iProduct 2 USB Reader
iSerial 3 110074973765
bNumConfigurations 1
Configuration Descriptor:
bLength 9
bDescriptorType 2
wTotalLength 32
bNumInterfaces 1
bConfigurationValue 1
iConfiguration 0
bmAttributes 0x80
(Bus Powered)
MaxPower 100mA
Interface Descriptor:
bLength 9
bDescriptorType 4
bInterfaceNumber 0
bAlternateSetting 0
bNumEndpoints 2
bInterfaceClass 8 Mass Storage
bInterfaceSubClass 6 SCSI
bInterfaceProtocol 80 Bulk-Only
iInterface 0
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x01 EP 1 OUT
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0200 1x 512 bytes
bInterval 0
Endpoint Descriptor:
bLength 7
bDescriptorType 5
bEndpointAddress 0x81 EP 1 IN
bmAttributes 2
Transfer Type Bulk
Synch Type None
Usage Type Data
wMaxPacketSize 0x0200 1x 512 bytes
bInterval 0
Device Qualifier (for other device speed):
bLength 10
bDescriptorType 6
bcdUSB 2.00
bDeviceClass 0 (Defined at Interface level)
bDeviceSubClass 0
bDeviceProtocol 0
bMaxPacketSize0 64
bNumConfigurations 1
Device Status: 0x0000
(Bus Powered)
6. USB資料傳輸四種傳輸模式:
控制傳輸(control)->傳送主機和外設之間的設定、控制、狀態等資訊
等時傳輸(isochronous)->傳輸實時資料,傳輸速率預先可知。可容忍偶爾錯誤,一般用於麥克風,音響,usb視訊裝置等
批量傳輸(bulk)->傳輸大量時延要求不高的資料,但是要求不能出錯,適用於印表機,儲存裝置等
中斷傳輸(interrupt)->傳輸資料量小,但是對傳輸時延敏感,要求馬上響應,如鍵盤滑鼠等。
USB通訊最基本的形式是通過端點(endpoint),USB端點只能往一個方向傳輸資料,從host到device(稱為輸出端點)或從device到host(稱為輸入端點)。對應時鐘傳輸模式,端點也分成4種:
控制端點:
用來允許對 USB 裝置的不同部分存取. 通常用作配置裝置, 獲取關於裝置的資訊, 傳送命令到裝置, 或者獲取關於裝置的狀態報告. 每個 USB 裝置有一個控制端點稱為"端點 0", 被 USB 核用來在插入時配置裝置(列舉). 這些傳送由 USB 協議保證來總有足夠的頻寬使它到達裝置.
等時端點:
可以傳送大量資料, 但是這個資料常常不能保證傳輸完全正確. 這些端點用在可以處理資料丟失的裝置中, 並且更多依賴於保持持續的資料流. 實時資料收集, 例如音訊和視訊裝置, 一直都使用這些端點.
批量端點:
用來傳送大量的資料. 對於需要傳送不能有任何資料丟失的資料. 這些傳送不被 USB 協議保證來一直使它在特定時間範圍內完成. 如果總線上沒有足夠的空間來發送整個 BULK 報文, 它被分為多次傳送到或者從裝置. 這些端點普遍在印表機, 儲存器, 和網路裝置上
中斷端點:
傳送小量的資料, 以固定的速率在每次 USB 主請求裝置資料時. 這些端點對 USB 鍵盤和滑鼠來說是主要的傳送方法. 它們還用來傳送資料到 USB 裝置來控制裝置, 但通常不用來傳送大量資料. 這些傳送由 USB 協議保證來總有足夠的頻寬使它到達裝置.
注意:
a. 所有傳輸都是有USB主機發起的,不能由USB裝置發起傳輸。
b. 注意此處的中斷區別於硬體中斷,而是CPU一直在輪詢裝置狀態,有資料則發起中斷取走資料。
c. 一個裝置也可能會使用多種傳輸模式,如USB儲存裝置使用控制傳輸模式完成磁碟訪問命令,使用批量傳輸模式和主機交換資料。
7. USB資料組織
USB的資料傳遞首先是基於傳輸(Transfer)的,四種傳輸:控制傳輸,等時傳輸,批量傳輸,中斷傳輸;
一次傳輸由一個或多個事務(transaction)構成,三種事務:IN事務,OUT事務,SETUP事務;
一個事務有一個或多個包(Packet)構成,四種包:令牌包(SETUP),資料包(DATA),握手包(ACK),特殊包(PRE);
一個包由多個域(欄位)構成,多種域:同步域(SYNC),標識域(PID),地址域(ADDR),端點域(ENDP),幀號域(FRAM),資料域(DATA),校驗域(CRC)等
8. USB裝置列舉
USB裝置列舉8個步驟:
a. 獲取裝置描述符
b. 裝置復位
c. 設定裝置地址
d. 再次獲取裝置描述符
e. 獲取配置描述符
f. 獲取介面描述符、端點描述符
g. 獲取字串描述符
h. 選擇裝置配置
9. usb基本函式及資料結構->usb-DS+FUNC
Data Structures:
資料結構 路徑 說明
urb include/linux/usb.h USB資料傳輸機制的核心結構
pipe include/linux/usb.h 存放URB的地址資訊等 Line 1796
usb_device_descriptor include/linux/usb/ch9.h usb裝置描述符
usb_config_descriptor usb配置描述符
usb_interface_descriptor usb介面描述符
usb_endpoint_descriptor usb端點描述符
usb_device include/linux/usb.h USB裝置在核心裡的抽象
usb_interface include/linux/usb.h USB裝置介面
usb_device_id include/linux/mod_devicetable.h 標識一個USB裝置,用於.id_table
usb_driver include/linux/usb.h USB客戶驅動程式
usb_gadget_driver include/linux/usb_gadget.h USB gadget驅動程式
Kernel Function:
核心介面 路徑 說明
usb_register() include/linux/usb.h 向USB核心註冊usb_driver結構體
drivers/usb/core/driver.c
usb_deregister() driver/usb/core/driver.c 從USB核心登出usb_driver結構體
usb_set_intfdata() include/linux/usb.h 把裝置相關的資料附著到usb_interface
usb_get_intfdata() include/linux/usb.h 從usb_interface中獲得相關資料
usb_register_dev() drivers/usb/core/file.c 把字元裝置介面和USB客戶驅動程式關聯起來
usb_deregister_dev() drivers/usb/core/file.c 解除關聯
usb_alloc_urb() drivers/usb/core/urb.c 建立並置零、初始化URB->kerf等
usb_fill_[control
|int|bulk|_urb() include/linux/usb.h 初始化URB
usb_[control|interrupt
|bulk]_msg() drivers/usb/core/message.c URB同步提交函式
usb_submit_urb() drivers/usb/core/urb.c URB非同步提交函式
usb_free_urb() drivers/usb/core/urb.c 釋放URB
usb_unlink_urb() drivers/usb/core/urb.c 取消URB的提交
usb_[rcv|snd][ctrl
|int|bulk|isoc]pipe() include/linux/usb.h 建立URB管道 Line 1820
usb_find_interface() drivers/usb/core/usb.c 獲得與USB客戶驅動程式相關的usb_interface變數
usb_buffer_alloc() drivers/usb/core/usb.c 分配一致性DMA傳輸緩衝區
usb_buffer_free() drivers/usb/core/usb.c 釋放usb_buffer_alloc函式分配的緩衝區
usb_serial_register() drivers/usb/serial/usb_serial.c 向USB-Serial核心註冊驅動程式
usb_serial_deregister() drivers/usb/serial/usb_serial.c 從USB-Serial核心登出驅動程式
10. USB驅動基本框架 usb-skeleton.c 簡析