當前位置:首頁 > IT技術(shù) > Web編程 > 正文

USB NCM usbnet 枚舉流程代碼分析
2021-10-20 10:31:48


USB NCM usbnet 枚舉流程代碼分析

一、cdc_ncm.c

在linux 驅(qū)動中,CDC NCM的驅(qū)動位于: ??kerneldrivers etusbcdc_ncm.c??

static struct usb_driver cdc_ncm_driver = {
.name = "cdc_ncm",
.id_table = cdc_devs,
.probe = usbnet_probe,
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
.reset_resume = usbnet_resume,
.supports_autosuspend = 1,
.disable_hub_initiated_lpm = 1,
};

module_usb_driver(cdc_ncm_driver);

在結(jié)構(gòu)體??cdc_ncm_driver??中,比較重要的是??id_table??,??probe??這兩個,

在??id_table?? 中定義了所有符合??cdc_ncm??設(shè)備的 ??idVendor??號,當??linux?? 枚舉時檢測到USB設(shè)備的??idVendor??在這個??id_table??中時,就會調(diào)用??usbnet_probe??進行起網(wǎng)操作。


1.1 struct usb_device_id結(jié)構(gòu)體

在分析??cdc_ncm??的??id_table??之前,我們先來看下??usb_device_id?? 結(jié)構(gòu)體是如何定義的:

# kernelincludelinuxmod_devicetable.h
struct usb_device_id {
/* which fields to match against? */
__u16 match_flags; //說明使用哪種匹配方式

/* Used for product specific matches; range is inclusive */
__u16 idVendor; //供應(yīng)商ID
__u16 idProduct; //產(chǎn)品ID
__u16 bcdDevice_lo;
__u16 bcdDevice_hi;

/* Used for device class matches */
__u8 bDeviceClass; //設(shè)備類型
__u8 bDeviceSubClass; //設(shè)備子類型
__u8 bDeviceProtocol; //協(xié)議

/* Used for interface class matches */
__u8 bInterfaceClass; //接口類
__u8 bInterfaceSubClass; //接口子類
__u8 bInterfaceProtocol; //接口協(xié)議

/* Used for vendor-specific interface matches */
__u8 bInterfaceNumber;

/* not matched against */
kernel_ulong_t driver_info
__attribute__((aligned(sizeof(kernel_ulong_t)))); // NCM 驅(qū)動結(jié)構(gòu)體,其中包含了收發(fā)包的函數(shù)等
};

結(jié)合結(jié)構(gòu)體定義,我們來看下??cdc_ncm??的??id_table??:

static const struct usb_device_id cdc_devs[] = {
// 愛立信 F5521gw USB網(wǎng)卡
/* Ericsson MBM devices like F5521gw */
{ .match_flags = USB_DEVICE_ID_MATCH_INT_INFO | USB_DEVICE_ID_MATCH_VENDOR,
//匹配方式:CLASS(設(shè)備類)、SUBCLASS(子類)、PROTOCOL(設(shè)備協(xié)議)
.idVendor = 0x0bdb, //供應(yīng)商ID: 0x0bdb
.bInterfaceClass = USB_CLASS_COMM, //設(shè)備類型: 網(wǎng)卡類
.bInterfaceSubClass = USB_CDC_SUBCLASS_NCM, //設(shè)備子類型:NCM
.bInterfaceProtocol = USB_CDC_PROTO_NONE, //設(shè)備協(xié)議: 無
.driver_info = (unsigned long) &wwan_info, // NCM 驅(qū)動結(jié)構(gòu)體,其中包含了收發(fā)包的函數(shù)等
},

/* DW5812 LTE Verizon Mobile Broadband Card Unlike DW5550 this device requires FLAG_NOARP */
{ USB_DEVICE_AND_INTERFACE_INFO(0x413c, 0x81bb,
USB_CLASS_COMM,
USB_CDC_SUBCLASS_NCM, USB_CDC_PROTO_NONE),
.driver_info = (unsigned long)&wwan_noarp_info,
},

/* DW5813 LTE AT&T Mobile Broadband Card Unlike DW5550 this device requires FLAG_NOARP */
{ USB_DEVICE_AND_INTERFACE_INFO(0x413c, 0x81bc,
USB_CLASS_COMM,
USB_CDC_SUBCLASS_NCM, USB_CDC_PROTO_NONE),
.driver_info = (unsigned long)&wwan_noarp_info,
},

/* Dell branded MBM devices like DW5550 */
{ .match_flags = USB_DEVICE_ID_MATCH_INT_INFO | USB_DEVICE_ID_MATCH_VENDOR,
.idVendor = 0x413c,
.bInterfaceClass = USB_CLASS_COMM,
.bInterfaceSubClass = USB_CDC_SUBCLASS_NCM,
.bInterfaceProtocol = USB_CDC_PROTO_NONE,
.driver_info = (unsigned long) &wwan_info,
},

/* Toshiba branded MBM devices */
{ .match_flags = USB_DEVICE_ID_MATCH_INT_INFO | USB_DEVICE_ID_MATCH_VENDOR,
.idVendor = 0x0930,
.bInterfaceClass = USB_CLASS_COMM,
.bInterfaceSubClass = USB_CDC_SUBCLASS_NCM,
.bInterfaceProtocol = USB_CDC_PROTO_NONE,
.driver_info = (unsigned long) &wwan_info,
},

/* tag Huawei devices as wwan */
{ USB_VENDOR_AND_INTERFACE_INFO(0x12d1,
USB_CLASS_COMM,
USB_CDC_SUBCLASS_NCM,
USB_CDC_PROTO_NONE),
.driver_info = (unsigned long)&wwan_info,
},

/* Infineon(now Intel) HSPA Modem platform */
{ USB_DEVICE_AND_INTERFACE_INFO(0x1519, 0x0443,
USB_CLASS_COMM,
USB_CDC_SUBCLASS_NCM, USB_CDC_PROTO_NONE),
.driver_info = (unsigned long)&wwan_noarp_info,
},

/* Generic CDC-NCM devices */
{ USB_INTERFACE_INFO(USB_CLASS_COMM,
USB_CDC_SUBCLASS_NCM, USB_CDC_PROTO_NONE),
.driver_info = (unsigned long)&cdc_ncm_info,
}
};
MODULE_DEVICE_TABLE(usb, cdc_devs);

1.1.1 match_flags 設(shè)備類型

所有的??match_flags??定義在??mod_devicetable.h?? 中:

# kernelincludelinuxmod_devicetable.h
/* Some useful macros to use to create struct usb_device_id */
#define USB_DEVICE_ID_MATCH_VENDOR 0x0001
#define USB_DEVICE_ID_MATCH_PRODUCT 0x0002
#define USB_DEVICE_ID_MATCH_DEV_LO 0x0004
#define USB_DEVICE_ID_MATCH_DEV_HI 0x0008
#define USB_DEVICE_ID_MATCH_DEV_CLASS 0x0010
#define USB_DEVICE_ID_MATCH_DEV_SUBCLASS 0x0020
#define USB_DEVICE_ID_MATCH_DEV_PROTOCOL 0x0040
#define USB_DEVICE_ID_MATCH_INT_CLASS 0x0080
#define USB_DEVICE_ID_MATCH_INT_SUBCLASS 0x0100
#define USB_DEVICE_ID_MATCH_INT_PROTOCOL 0x0200
#define USB_DEVICE_ID_MATCH_INT_NUMBER 0x0400

1.1.2 bInterfaceClass 接口類

# kernelincludeuapilinuxusbch9.h

/* Device and/or Interface Class codes
* as found in bDeviceClass or bInterfaceClass
* and defined by www.usb.org documents */
#define USB_CLASS_PER_INTERFACE 0 /* for DeviceClass */
#define USB_CLASS_AUDIO 1 //聲音設(shè)備
#define USB_CLASS_COMM 2 //調(diào)制解調(diào)器,網(wǎng)卡,ISDN連接
#define USB_CLASS_HID 3 //HID設(shè)備,如鼠標,鍵盤
#define USB_CLASS_PHYSICAL 5 //物理設(shè)備
#define USB_CLASS_STILL_IMAGE 6 //靜止圖像捕捉設(shè)備
#define USB_CLASS_PRINTER 7 //打印機
#define USB_CLASS_MASS_STORAGE 8 //批量存儲設(shè)備
#define USB_CLASS_HUB 9 //USB HUBS
#define USB_CLASS_CDC_DATA 0x0a
#define USB_CLASS_CSCID 0x0b /* chip+ smart card */ //智能卡
#define USB_CLASS_CONTENT_SEC 0x0d /* content security */
#define USB_CLASS_VIDEO 0x0e //視頻設(shè)備,如網(wǎng)絡(luò)攝像頭
#define USB_CLASS_WIRELESS_CONTROLLER 0xe0 //網(wǎng)絡(luò)控制設(shè)備
#define USB_CLASS_MISC 0xef //雜項設(shè)備
#define USB_CLASS_APP_SPEC 0xfe
#define USB_CLASS_VENDOR_SPEC 0xff //廠商自定義的設(shè)備

#define USB_SUBCLASS_VENDOR_SPEC 0xff

wait…

本文摘自 :https://blog.51cto.com/c

開通會員,享受整站包年服務(wù)立即開通 >