/u011728480/article/details/78588827
#PS:要转载请注明出处,本人版权所有
#PS:这个只是 《 我自己 》理解,如果和你的
#原则相冲突,请谅解,勿喷
EC20简介
EC20是一个全网通的4G模块,并提供了详细的驱动移植资料(源码+文档),我也仅仅是照着文档,一点点的改,并建立起来一个可用的环境。
EC20驱动移植准备
1 首先你会从厂家拿到一个资料文件,并解压(类似Quectel_GobiNetSR01A02V16.zip)
2 你会找到一个用户手册的PDF打开(类似Quectel_WCDMA<E_Linux_USB_Driver_User_Guide_V1.6.pdf)
3 这里还有一个Readme.txt告诉你需要阅读上文pdf的哪些内容。可能如下:
About GobiNet driver, please refer to the chapter 3.2、3.4、5.4、6About ConnectManager,please refer to the chapter 5.4
4 按照pdf指示如下。
EC20 Linux驱动移植
1 增加PID&VID(对着两个不了解的,建议去找找资料来看看,这个的意思可以简单理解为这个设备的唯一标识)
[KERNEL]/drivers/usb/serial/option.c
static const struct usb_device_id option_ids[] = {#if 1 //Added by Sky { USB_DEVICE(0x05C6, 0x9090) }, /* Quectel UC15 */ { USB_DEVICE(0x05C6, 0x9003) }, /* Quectel UC20 */ { USB_DEVICE(0x05C6, 0x9215) }, /* Quectel EC20 */ { USB_DEVICE(0x2C7C, 0x0125) }, /* Quectel EC25/EC20 R2.0 */ { USB_DEVICE(0x2C7C, 0x0121) }, /* Quectel EC21 */ #endif
这里其实只需要{ USB_DEVICE(0x05C6, 0x9215) }, /* Quectel EC20 */ 这一项,其他是无关紧要的,可以不放进去。option_ids[]就是一usb serial的设备pid,vid表。
2 注释掉冲突的vid以及pid设备(我猜存在相同的vid和pid是历史的原因)
[KERNEL]/drivers/usb/serial/qcserial.c
//Comment by Sky,//{USB_DEVICE(0x05c6, 0x9215)}, /* Acer Gobi 2000 Modem device (VP413) */
[KERNEL]/drivers/net/usb/qmi_wwan.c
//comment by Sky//{QMI_GOBI_DEVICE(0x05c6, 0x9215)}, /* Acer Gobi 2000 Modem device (VP413) */
注意这里貌似只有EC20的冲突了。
3 添加零包处理(这个和usb 协议中的批量传输有关)
For Linux Kernel Version newer than 2.6.34:
File: [KERNEL]/drivers/usb/serial/usb_wwan.c
usb_fill_bulk_urb(urb, serial->dev,usb_sndbulkpipe(serial->dev, endpoint) | dir,buf, len, callback, ctx);#if 1 //Added by Sky for Zero Packetif (dir == USB_DIR_OUT){struct usb_device_descriptor *desc = &serial->dev->descriptor;if (desc->idVendor == cpu_to_le16(0x05C6) && desc->idProduct == cpu_to_le16(0x9090))urb->transfer_flags |= URB_ZERO_PACKET;if (desc->idVendor == cpu_to_le16(0x05C6) && desc->idProduct == cpu_to_le16(0x9003))urb->transfer_flags |= URB_ZERO_PACKET;if (desc->idVendor == cpu_to_le16(0x05C6) && desc->idProduct == cpu_to_le16(0x9215))urb->transfer_flags |= URB_ZERO_PACKET;if (desc->idVendor == cpu_to_le16(0x2C7C))urb->transfer_flags |= URB_ZERO_PACKET;}#endif
注意,pdf上还有For Linux Kernel Version older than 2.6.35的内容,请自行根据内核版本查看。
4 增加休眠后唤醒接口
For Linux Kernel Version newer than 3.4:
File: [KERNEL]/drivers/usb/serial/option.c
static struct usb_serial_driver option_1port_device = {.driver = {.owner = THIS_MODULE,.name ="option1",},.description = "GSM modem (1-port)",.id_table= option_ids,.num_ports = 1,.probe = option_probe,.open = usb_wwan_open,.close = usb_wwan_close,.dtr_rts = usb_wwan_dtr_rts,.write = usb_wwan_write,.write_room = usb_wwan_write_room,.chars_in_buffer = usb_wwan_chars_in_buffer,.set_termios = usb_wwan_set_termios,.tiocmget= usb_wwan_tiocmget,.tiocmset= usb_wwan_tiocmset,.ioctl = usb_wwan_ioctl,.attach = option_attach,.release = option_release,.port_probe = usb_wwan_port_probe,.port_remove = usb_wwan_port_remove,.read_int_callback = option_instat_callback,#ifdef CONFIG_PM.suspend = usb_wwan_suspend,.resume = usb_wwan_resume,#if 1 //Added by Sky .reset_resume = usb_wwan_resume, #endif #endif};
5 如果要使用 GobiNet or QMI WWAN,需要阻止第四个接口注册为串口。
For Linux Kernel Version newer than 2.6.30:
File: [KERNEL]/drivers/usb/serial/option.c
static int option_probe(struct usb_serial *serial,const struct usb_device_id *id){struct usb_interface_descriptor *iface_desc =&serial->interface->cur_altsetting->desc;struct usb_device_descriptor *dev_desc = &serial->dev->descriptor;
<span class="hljs-comment"><span class="hljs-comment">/* Never bind to the CD-Rom emulation interface */</span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (iface_desc->bInterfaceClass == <span class="hljs-number"><span class="hljs-number">0x08</span></span>)<span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV;<span class="hljs-comment"><span class="hljs-comment">/* * Don't bind reserved interfaces (like network ones) which often have * the same class/subclass/protocol as the serial interfaces. Look at * the Windows driver .INF files for reserved interface numbers. */</span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (is_blacklisted(iface_desc->bInterfaceNumber,OPTION_BLACKLIST_RESERVED_IF,(<span class="hljs-keyword"><span class="hljs-keyword">const</span></span> <span class="hljs-keyword">struct</span> option_blacklist_info *) id->driver_info))<span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV;<span class="hljs-comment"><span class="hljs-comment">/* * Don't bind network interface on Samsung GT-B3730, it is handled by * a separate module. */</span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (dev_desc->idVendor == cpu_to_le16(SAMSUNG_VENDOR_ID) &&dev_desc->idProduct == cpu_to_le16(SAMSUNG_PRODUCT_GT_B3730) &&iface_desc->bInterfaceClass != USB_CLASS_CDC_DATA)<span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV;<span class="hljs-preprocessor"><span class="hljs-comment">#if 1 </span><span class="hljs-comment"><span class="hljs-comment">//Added by Sky </span></span></span><span class="hljs-comment"><span class="hljs-comment">//Quectel UC20's interface 4 can be used as USB Network device </span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (serial->dev->descriptor.idVendor == cpu_to_le16(<span class="hljs-number"><span class="hljs-number">0x05C6</span></span>) && serial->dev->descriptor.idProduct == cpu_to_le16(<span class="hljs-number"><span class="hljs-number">0x9003</span></span>) \&& serial->interface->cur_altsetting->desc.bInterfaceNumber >= <span class="hljs-number"><span class="hljs-number">4</span></span>) <span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV; <span class="hljs-comment"><span class="hljs-comment">//Quectel EC20's interface 4 can be used as USB Network device </span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (serial->dev->descriptor.idVendor == cpu_to_le16(<span class="hljs-number"><span class="hljs-number">0x05C6</span></span>) && serial->dev->descriptor.idProduct == cpu_to_le16(<span class="hljs-number"><span class="hljs-number">0x9215</span></span>) \&& serial->interface->cur_altsetting->desc.bInterfaceNumber >= <span class="hljs-number"><span class="hljs-number">4</span></span>) <span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV; <span class="hljs-comment"><span class="hljs-comment">//Quectel EC21&EC25&EC20 R2.0's interface 4 can be used as USB Network device </span></span><span class="hljs-keyword"><span class="hljs-keyword">if</span></span> (serial->dev->descriptor.idVendor == cpu_to_le16(<span class="hljs-number"><span class="hljs-number">0x2C7C</span></span>) \&& serial->interface->cur_altsetting->desc.bInterfaceNumber >= <span class="hljs-number"><span class="hljs-number">4</span></span>) <span class="hljs-keyword"><span class="hljs-keyword">return</span></span> -ENODEV; <span class="hljs-preprocessor"><span class="hljs-comment">#endif </span></span><span class="hljs-comment"><span class="hljs-comment">/* Store device id so we can use it during attach. */</span></span>usb_set_serial_data(serial, (<span class="hljs-keyword">void</span> *)id);<span class="hljs-keyword"><span class="hljs-keyword">return</span></span> <span class="hljs-number"><span class="hljs-number">0</span></span>;
}
6 修改内核配置,并编译内核,刷入新内核
添加USB 串口 GSM 和 CDMA 驱动选项
启用USB网络支持
添加驱动代码
//Step 5: Please add the following statements to file "[KERNEL]/drivers/net/usb/Makefile" ([KERNEL]/drivers/usb/net/Makefile if the kernel version is older than 2.6.22). obj-y += GobiNet.o GobiNet-objs := GobiUSBNet.o QMIDevice.o QMI.o
7 quectel-CM 测试
//交叉编译quectel-CM /*quectel-CM will call busybox udhpc to obtain IP and NDS, and busybox udhpc will call script file /usr/share/udhcpc/default.script to set IP/DNS/Routing table for Linux board. You can download this tool’s source code from /. You should enable CONFIG_UDHCPC in busybox menuconfig,and copy the script file [BUSYBOX]/examples/udhcp/simple.script to your Linux board (renamed as /usr/share/udhcpc/default.script). */quectel-CM –s ctnet & [01-01_00:26:45:355] Quectel_ConnectManager_SR01A01V10 [01-01_00:26:45:356] ./quectel-CM profile = ctnet///, pincode = [01-01_00:26:45:357] Find qmichannel = /dev/qcqmi2 [01-01_00:26:45:358] Find usbnet_adapter = eth2 [01-01_00:26:45:368] Get clientWDS = 7 [01-01_00:26:45:400] Get clientDMS = 8 [01-01_00:26:45:432] Get clientNAS = 9 [01-01_00:26:45:464] Get clientWDA = 10 [01-01_00:26:45:496] requestBaseBandVersion EC20CQAR02A03E2G_BETA0914 1 [Sep 14 13:51:27] [01-01_00:26:45:560] requestGetSIMStatus SIMStatus: SIM_READY [01-01_00:26:45:624] requestGetProfile ctnet///0 [01-01_00:26:45:656] requestRegistrationState MCC: 460, MNC: 11, PS: Attached, DataCap: LTE [01-01_00:26:45:688] requestQueryDataCall ConnectionStatus: DISCONNECTED [01-01_00:26:45:720] requestRegistrationState MCC: 460, MNC: 11, PS: Attached, DataCap: LTE [01-01_00:26:45:752] requestQueryDataCall ConnectionStatus: DISCONNECTED [01-01_00:26:45:816] requestSetupDataCall WdsConnectionIPv4Handle: 0x43cc4478 [01-01_00:26:45:912] requestQueryDataCall ConnectionStatus: CONNECTED [01-01_00:26:45:937] udhcpc (v1.20.2) started [01-01_00:26:45:956] Sending discover... [01-01_00:26:45:960] Sending select for 10.172.27.151... [01-01_00:26:45:964] Lease of 10.172.27.151 obtained, lease time 7200 [01-01_00:26:45:984] deleting routers route: SIOCDELRT: No such process [01-01_00:26:46:003] adding dns 61.132.163.68 [01-01_00:26:46:003] adding dns 202.102.213.68
注意,这里需要UDHCPC ,检测你的busybox是否有这个东西,如果不存在,你需要重新移植busybox,启用CONFIG_UDHCPC选项。还需要配置一个配置文件,注意检查。
特别提示,其中很多关于内核源码修改,以及内核配置修改,不同的版本有不同的写法,文档里面都有详细说明,请使用时,特别注意。
#PS:请尊重原创,不喜勿喷
#PS:要转载请注明出处,本人版权所有.
有问题请留言,看到后我会第一时间回复