Micro Framework USB Driver开发
2009-01-21 16:28
393 查看
为Micro Framework开发USB驱动也有一段时间了,随着开发的深入,对USB理解也渐渐清晰起来。
从系统架构上来说为Micro Framework开发USB驱动有三个层面的工作。一是针对USB芯片的驱动移植(很多ARM CPU都集成了USB功能),实现MF的HAL层要求的USB接口;二是开发PC平台上针对MF设备的USB驱动;三是编写应用程序(非Micro Framework应用程序),通过USB接口直接和MF设备通信(这个工作是我加的,其实完成前两步工作,就已经使MFDeploy和VS2008和设备正常通信了)。
下面我针对这三个层面,详细说一下我的开发工作。
一、USB驱动移植
这一步是最难的,特别是对USB没有任何了解的人来说。Micro Farmework的USB开发接口如下(含HAL层和PAL层的接口,其中PAL层的代码已经提供,不需要任何编程)。
1、CPU_USB_GetInterruptState Function
Determines whether there are currently interrupts pending for the USB port.
2、CPU_USB_Initialize Function
Initializes the client module at the driver layer.
3、CPU_USB_ProtectPins Function
Puts USB pins into a known state to prevent spurious inputs.
4、CPU_USB_RxEnable Function
Enables a specified USB port to receive data.
5、CPU_USB_StartOutput Function
Begins sending output to a specified USB port.
6、CPU_USB_Uninitialize Function
Uninitializes (shuts down) USB communications at the driver layer.
7、USB_ClearEvent Function
Clears one or more USB events.
8、USB_Flush Function
Flushes the buffers associated with USB ports.
9、USB_GetEvent Function
Gets the state of a USB event.
10、USB_Initialize Function
Initializes the USB subsystem.
11、USB_Read Function
Reads a block of data from a USB port.
12、USB_SetEvent Function
Sets the state of a USB event.
13、USB_Uninitialize Function
Initializes the USB subsystem.
14、USB_Write Function
Writes a block of data to a USB port.
其实接口什么样都无所谓,关键是首先你要让USB设备能work,让PC机能识别你的设备,USB开发的里程碑有三个,一是让PC机发现未知设备,二是让PC机识别USB设备,三是正确安装USB驱动(当然要能正常工作)。
1、第一步让USB识别你的设备,这一步可以说是最难,也可以说是最容易的一步,说它最难是因为这一步和硬件的正常工作非常相关,如果硬件工作不正常或USB接口有物理故障,这一步都很难通过,所以在开发USB驱动之前,一定确保硬件设备的USB能正常工作(比如在linux或Wince环境下能正常工作)。说它容易是因为仅需要正确配置一两个寄存器,不需要什么编程就能实现这一步。这个过程不需要了解太多的USB相关知识,只需要精读该芯片的英文技术文档即可。
2、第二步让PC机识别你的USB设备,这一步是最关键的一步,也是需要大量USB知识的一步。这一步仅需要实现USB的端点0(称控制端点或默认端点)相关的功能即可。
如果没有USB基础的人,这一步必须要充电,必须要知道USB相关协议规范,否则你就会寸步难行。我这里推荐一下两个人的blog,一个是大名鼎鼎的USB研究专家圈圈,写的关于USB的文章都非常透彻,相关链接(http://group.ednchina.com/93/240.aspx );另一个是蔡军生的关于USB的文章,写的也非常好,对开发很有帮助(http://blog.csdn.net/caimouse/archive/2007/03/24/1539835.aspx )。其次我推荐,如果大家有条件就要购买一本周立功编著的《USB 2.0与OTG规范及开发指南》,这可以说是一本USB2.0英文协议文档的翻译版,不过翻译的还不错(网上也流传了不少USB2.0中文协议文档,不过有些差强人意),可以相对比较准确地理解USB术语。对我来说,还是比较习惯读书的,在电脑上看大篇大篇的技术文档很容易看了后面忘了前面的。
这一步其实就是PC机对USB设备的盘查工作,有点类似公安局审犯人,如你是谁?什么背景?有什么能力等等。其中最关键的要问到USB设备的PID和VID,问到这一个才能安装相对应的驱动程序,当然获得相关的接口和端点配置也是非常重要的。详细的信息交互,这一步我就不多说了,协议上都说的非常清楚。这一步要说一点,就是设置地址这个环节最容易出错,PC机分配的地址收到后,一定要等返回相关ACK响应后,再修改设备的USB设备地址,否则很容易出问题。
这里推荐一下北航frank的文章《USB项目技术报告》,这个环节写的很清楚。
此外如果你手边有USB协议分析仪,那么你真是一个非常幸福的人,这一步就需要这个东东(我不太幸运,我是在调通USB驱动之后,才有的USB协议分析仪),Bus Hound工具虽然好用,但是在这一步却帮不上忙,它是要识别USB设备后才能正常监控USB数据流的,这对第三步的工作非常有帮助。
(USB通信过程一目了然,你会发现USB协议分析仪原来这么强大)。
注:Micro Framework的PAL层已实现相关通信交互的指令,你仅需要把USB通道打通即可,此外不要拘泥于MF porting kit中的USB驱动示例,要根据需要大胆一些调整相关逻辑。具体的要求请参见我以前的文章《MF Porting之USB驱动开发》http://yfsoft.blog.51cto.com/1635641/321265
第三步,安装驱动,如果第二步正确完成,PC机就会要求你安装USB驱动了。
二、PC USB驱动开发
Micro Framework的Porting kit开发包中已经提供了MF 设备的USB驱动源码(MFUSB_PortingKitSample),你仅需要修改一下Inf文件(主要修改相关的PID和VID,记住PID和VID仅是设备和相关驱动关联用的,除此之外没有其它任何用处),此外需要安装Windows DDK开发包,用来编译该驱动程序。相关说明如下:
To compile the USB drivers you must
1) install the DDK
2) open a command window for building (build environment must be initialized for that cmd window by calling setenv.cmd on the appropriate client directory)
3) build with the script build_usb_drivers in %SPOCLIENT%\Tools\scripts directory
usage: build_usb_drivers.cmd DDK_INSTALLDIR
example: build_usb_drivers.cmd c:\WINDDK\6001.18001
Output directories are under the drivers' source tree. Please move the sys files in the corresponding sub-directories in the inf folder before installing.
NOTE: the build_usb_drivers script will only build the MFUSB_PortingKitSample driver. The MFUSB_DualInterface_PortingKitSample driver is the same
as the previous one but can handle 4 endpoints instead of two and allows debugging over USB the first pair of endpoints while reading/writing
on the other pair.
由于MF设备仅支持3个端点(0,1,2),所以要扩展功能或增加端点,就需要你修改此程序的相关源码了(当然MF设备的USB驱动你也要相应地修改)。
三、USB应用程序开发
很多网上的此类程序大部分都是基于VC的,几乎找不到C#相关的源代码,即使有也发现文不对题,根本实现不了和设备的直接通信,网上有一个ICSharpCode.USBlib的库可以在C#中引用,据说功能还很强大,不过我在Vista和XP上好像没有测试成功,枚举USB设备时老出现异常。
幸好MFDeploy程序(MF SDK中的部署工具)是用C#开发的,所以深入研究该程序后,终于从中提取出一个USB读写类(MFDeploy程序太复杂了,我研究了好长时间才粗略理清相关逻辑脉络),终于很方便的用C#操作USB设备了。
相关接口:
应用代码:
现在很多USB设备都是免驱的了,就是实现了HID封装,借助该通道和USB设备通信。我对该技术非常感兴趣,有时间可以深入研究一下。有此类经验的朋友也希望能分享一下。
还有一个值得高兴的事,Micro Framework美国微软研发团队终于向我们开放了TinyCLR源码,这是一个非常值得纪念的开始,意味着我们中国的MF团队又向美国的MF开发团队走近了一步,期待我们能在MF上走的更远。正如Lorenzo所说:We are very excited about this opportunity and we are confident that it will have a huge impact on our business. This could be the beginning of a great collaboration.
从系统架构上来说为Micro Framework开发USB驱动有三个层面的工作。一是针对USB芯片的驱动移植(很多ARM CPU都集成了USB功能),实现MF的HAL层要求的USB接口;二是开发PC平台上针对MF设备的USB驱动;三是编写应用程序(非Micro Framework应用程序),通过USB接口直接和MF设备通信(这个工作是我加的,其实完成前两步工作,就已经使MFDeploy和VS2008和设备正常通信了)。
下面我针对这三个层面,详细说一下我的开发工作。
一、USB驱动移植
这一步是最难的,特别是对USB没有任何了解的人来说。Micro Farmework的USB开发接口如下(含HAL层和PAL层的接口,其中PAL层的代码已经提供,不需要任何编程)。
1、CPU_USB_GetInterruptState Function
Determines whether there are currently interrupts pending for the USB port.
2、CPU_USB_Initialize Function
Initializes the client module at the driver layer.
3、CPU_USB_ProtectPins Function
Puts USB pins into a known state to prevent spurious inputs.
4、CPU_USB_RxEnable Function
Enables a specified USB port to receive data.
5、CPU_USB_StartOutput Function
Begins sending output to a specified USB port.
6、CPU_USB_Uninitialize Function
Uninitializes (shuts down) USB communications at the driver layer.
7、USB_ClearEvent Function
Clears one or more USB events.
8、USB_Flush Function
Flushes the buffers associated with USB ports.
9、USB_GetEvent Function
Gets the state of a USB event.
10、USB_Initialize Function
Initializes the USB subsystem.
11、USB_Read Function
Reads a block of data from a USB port.
12、USB_SetEvent Function
Sets the state of a USB event.
13、USB_Uninitialize Function
Initializes the USB subsystem.
14、USB_Write Function
Writes a block of data to a USB port.
其实接口什么样都无所谓,关键是首先你要让USB设备能work,让PC机能识别你的设备,USB开发的里程碑有三个,一是让PC机发现未知设备,二是让PC机识别USB设备,三是正确安装USB驱动(当然要能正常工作)。
1、第一步让USB识别你的设备,这一步可以说是最难,也可以说是最容易的一步,说它最难是因为这一步和硬件的正常工作非常相关,如果硬件工作不正常或USB接口有物理故障,这一步都很难通过,所以在开发USB驱动之前,一定确保硬件设备的USB能正常工作(比如在linux或Wince环境下能正常工作)。说它容易是因为仅需要正确配置一两个寄存器,不需要什么编程就能实现这一步。这个过程不需要了解太多的USB相关知识,只需要精读该芯片的英文技术文档即可。
2、第二步让PC机识别你的USB设备,这一步是最关键的一步,也是需要大量USB知识的一步。这一步仅需要实现USB的端点0(称控制端点或默认端点)相关的功能即可。
如果没有USB基础的人,这一步必须要充电,必须要知道USB相关协议规范,否则你就会寸步难行。我这里推荐一下两个人的blog,一个是大名鼎鼎的USB研究专家圈圈,写的关于USB的文章都非常透彻,相关链接(http://group.ednchina.com/93/240.aspx );另一个是蔡军生的关于USB的文章,写的也非常好,对开发很有帮助(http://blog.csdn.net/caimouse/archive/2007/03/24/1539835.aspx )。其次我推荐,如果大家有条件就要购买一本周立功编著的《USB 2.0与OTG规范及开发指南》,这可以说是一本USB2.0英文协议文档的翻译版,不过翻译的还不错(网上也流传了不少USB2.0中文协议文档,不过有些差强人意),可以相对比较准确地理解USB术语。对我来说,还是比较习惯读书的,在电脑上看大篇大篇的技术文档很容易看了后面忘了前面的。
这一步其实就是PC机对USB设备的盘查工作,有点类似公安局审犯人,如你是谁?什么背景?有什么能力等等。其中最关键的要问到USB设备的PID和VID,问到这一个才能安装相对应的驱动程序,当然获得相关的接口和端点配置也是非常重要的。详细的信息交互,这一步我就不多说了,协议上都说的非常清楚。这一步要说一点,就是设置地址这个环节最容易出错,PC机分配的地址收到后,一定要等返回相关ACK响应后,再修改设备的USB设备地址,否则很容易出问题。
这里推荐一下北航frank的文章《USB项目技术报告》,这个环节写的很清楚。
此外如果你手边有USB协议分析仪,那么你真是一个非常幸福的人,这一步就需要这个东东(我不太幸运,我是在调通USB驱动之后,才有的USB协议分析仪),Bus Hound工具虽然好用,但是在这一步却帮不上忙,它是要识别USB设备后才能正常监控USB数据流的,这对第三步的工作非常有帮助。
(USB通信过程一目了然,你会发现USB协议分析仪原来这么强大)。
注:Micro Framework的PAL层已实现相关通信交互的指令,你仅需要把USB通道打通即可,此外不要拘泥于MF porting kit中的USB驱动示例,要根据需要大胆一些调整相关逻辑。具体的要求请参见我以前的文章《MF Porting之USB驱动开发》http://yfsoft.blog.51cto.com/1635641/321265
第三步,安装驱动,如果第二步正确完成,PC机就会要求你安装USB驱动了。
二、PC USB驱动开发
Micro Framework的Porting kit开发包中已经提供了MF 设备的USB驱动源码(MFUSB_PortingKitSample),你仅需要修改一下Inf文件(主要修改相关的PID和VID,记住PID和VID仅是设备和相关驱动关联用的,除此之外没有其它任何用处),此外需要安装Windows DDK开发包,用来编译该驱动程序。相关说明如下:
To compile the USB drivers you must
1) install the DDK
2) open a command window for building (build environment must be initialized for that cmd window by calling setenv.cmd on the appropriate client directory)
3) build with the script build_usb_drivers in %SPOCLIENT%\Tools\scripts directory
usage: build_usb_drivers.cmd DDK_INSTALLDIR
example: build_usb_drivers.cmd c:\WINDDK\6001.18001
Output directories are under the drivers' source tree. Please move the sys files in the corresponding sub-directories in the inf folder before installing.
NOTE: the build_usb_drivers script will only build the MFUSB_PortingKitSample driver. The MFUSB_DualInterface_PortingKitSample driver is the same
as the previous one but can handle 4 endpoints instead of two and allows debugging over USB the first pair of endpoints while reading/writing
on the other pair.
由于MF设备仅支持3个端点(0,1,2),所以要扩展功能或增加端点,就需要你修改此程序的相关源码了(当然MF设备的USB驱动你也要相应地修改)。
三、USB应用程序开发
很多网上的此类程序大部分都是基于VC的,几乎找不到C#相关的源代码,即使有也发现文不对题,根本实现不了和设备的直接通信,网上有一个ICSharpCode.USBlib的库可以在C#中引用,据说功能还很强大,不过我在Vista和XP上好像没有测试成功,枚举USB设备时老出现异常。
幸好MFDeploy程序(MF SDK中的部署工具)是用C#开发的,所以深入研究该程序后,终于从中提取出一个USB读写类(MFDeploy程序太复杂了,我研究了好长时间才粗略理清相关逻辑脉络),终于很方便的用C#操作USB设备了。
相关接口:
public interface IControllerLocal : IController { Stream OpenPort(); } public interface IController { void ClosePort(); bool SendData(byte[] buf); int Available { get; } int ReadData(byte[] buf, int offset, int count); void Start(); void Stop(); bool IsPortConnected { get; } DateTime LastActivity { get; } } public interface IControllerHostLocal { Stream OpenConnection(); }
应用代码:
using System; using System.Drawing; using System.Windows.Forms; using System.Collections; using System.Threading; using Microsoft.SPOT.Debugger; namespace USBTest { public partial class frmMain : Form { UsbEngine usb =null; ArrayList pds=null; private Thread m_ReadThread; public frmMain() { InitializeComponent(); btnSend.Enabled = false; btnUpdata_Click(null, null); } private void btnUpdata_Click(object sender, EventArgs e) { pds = UsbEngine.Enumerate(); cmbUSBList.Items.Clear(); foreach (PortDefinition pd in pds) { cmbUSBList.Items.Add(pd.DisplayName); } if (cmbUSBList.Items.Count > 0 )cmbUSBList.SelectedIndex = 0; else btnSend.Enabled = false; } private void cmbUSBList_SelectedIndexChanged(object sender, EventArgs e) { if (usb != null) { btnSend.Enabled = false; usb.Dispose(); } btnSend.Enabled = true; usb = new UsbEngine((PortDefinition)pds[cmbUSBList.SelectedIndex]); usb.Start(); m_ReadThread = new Thread(new ThreadStart(this.ReadDataThread)); m_ReadThread.IsBackground = true; m_ReadThread.Start(); } private void ReadDataThread() { byte[] bytData = new byte[1024]; while (btnSend.Enabled) { try { if (usb.Available> 0) { int intRet = usb.ReadData(bytData, 0, usb.Available); MethodInvoker method = delegate { string strData = ""; for (int i = 0; i < intRet; i++) { strData += bytData[i].ToString("X2") + " "; } txtRead.Text += strData; }; this.txtRead.Invoke(method); } Thread.Sleep(100); } catch { } } } private void btnSend_Click(object sender, EventArgs e) { if (usb == null || txtSend.Text.Length == 0 ) return; try { string[] strData = txtSend.Text.Split(new char[] { ' ' }); byte[] bytData = new byte[strData.Length]; for (int i = 0; i < bytData.Length; i++) { bytData[i] = (byte)Convert.ToInt32(strData[i], 16); } usb.SendData(bytData); } catch(Exception ex) { txtRead.Text = "Send Error:" + ex.Message.ToString(); } } private void frmMain_FormClosing(object sender, FormClosingEventArgs e) { if (usb == null) return; btnSend.Enabled = false; usb.Stop(); } } }
现在很多USB设备都是免驱的了,就是实现了HID封装,借助该通道和USB设备通信。我对该技术非常感兴趣,有时间可以深入研究一下。有此类经验的朋友也希望能分享一下。
还有一个值得高兴的事,Micro Framework美国微软研发团队终于向我们开放了TinyCLR源码,这是一个非常值得纪念的开始,意味着我们中国的MF团队又向美国的MF开发团队走近了一步,期待我们能在MF上走的更远。正如Lorenzo所说:We are very excited about this opportunity and we are confident that it will have a huge impact on our business. This could be the beginning of a great collaboration.
相关文章推荐
- Micro Framework USB Driver开发
- Micro Framework USB Driver开发
- 【.Net Micro Framework PortingKit(补) – 1】USB驱动开发 推荐
- 【.Net Micro Framework PortingKit(补) – 1】USB驱动开发
- [待解决问题] 支持 net micro framework开发的开发板?
- .Net Micro framework在开发过程中的bugs/problems及解决方案。
- 【.NET MF】.NET Micro Framework USB移植
- 开源System.Windows.Forms库,让.Net Micro Framework界面开发和上位机一样简单
- 使用Net Micro Framework加速无线传感器网络开发
- g_ncm Linux USB network gadget driver framework
- 【.Net Micro Framework PortingKit – 12】SysTick驱动开发
- 用VB.net开发.NET Micro Framework
- 【.Net Micro Framework PortingKit – 11】NandFlash驱动开发
- 开源System.Windows.Forms库,让.Net Micro Framework界面开发和上位机一样简单
- Microsoft .NET Micro Framework移植开发笔记1
- .Net Micro Framework - USB Mass Storage功能实现
- 用VB.net开发.NET Micro Framework
- 【.Net Micro Framework PortingKit – 11】NandFlash驱动开发
- USB设备驱动开发-USB Gadget Driver(一)
- USB设备驱动开发-USB Gadget Driver(一)