【转载】WinCE中串口驱动及接口函数介绍

转载自:http://blog.csdn.net/nanjianhui/article/details/2627755

 

WinCE中,串口驱动实际上就是一个流设备驱动,具体架构如图

 

       串口驱动本身分为MDD层和PDD层。MDD层对上层的Device Manager提供了标准的流设备驱动接口(COM_xxx)PDD层实现了HWOBJ结构及结构中若干针对于串口硬件操作的函数指针,这些函数指针将指向PDD层中的串口操作函数。DDSI是指MDD层与PDD层的接口,在串口驱动中实际上就是指HWOBJPDD层会传给MDD层一个HWOBJ结构的指针,这样MDD层就可以调用PDD层的函数来操作串口。

       微软针对于串口驱动提供了参考源代码,可以在下面的目录下找到:”/WINCE600/PUBLIC/COMMON/OAK/DRIVERS/SERIAL”

   串口驱动的结构也就是这样了,下面介绍相关的驱动中的接口。

1. HWOBJ结构 

    在串口驱动中,HWOBJ结构中的函数实现了对串口硬件的操作,并在MDD层被调用。可以说,该结构描述了串口设备的所有特性,先来介绍一下该结构,具体定义如下:
typedef struct __HWOBJ
{  
    ULONG BindFlags;  
    DWORD dwIntID;  
    PHW_VTBL pFuncTbl;
} HWOBJ, *PHWOBJ;

BindFlags:用于控制MDD层如何来处理IST,具体值如下:           

                       THREAD_IN_PDD:MDD层不处理,中断在PDD层处理。           

                       THREAD_AT_INIT:在驱动初始化的时候,MDD层启动IST。           

                       THREAD_AT_OPEN:在驱动被Open的时候,MDD层启动IST。

dwInitID: 系统的中断号 pFuncTbl: 指向一个PHW_VTBL结构,该结构中包含一个函数指针列表,这些函数指针指向串口硬件操作函数,用于操作串口。

 

  1. typedef struct __HW_VTBL   
  2.   
  3.     {  
  4.   
  5.     PVOID (*HWInit)(ULONG Identifier, PVOID pMDDContext);  
  6.   
  7.     ULONG (*HWDeinit)(PVOID pHead);  
  8.   
  9.     BOOL (*HWOpen)(PVOID pHead);  
  10.   
  11.     ULONG (*HWClose)(PVOID pHead);  
  12.   
  13.     ULONG (*HWGetBytes)(PVOID pHead, PUCHAR pTarget, PULONG pBytes);  
  14.   
  15.     PVOID (*HWGetRxStart)(PVOID pHead);  
  16.   
  17.     INTERRUPT_TYPE (*HWGetIntrType)(PVOID pHead);  
  18.   
  19.     VOID (*HWOtherIntrHandler)(PVOID pHead);  
  20.   
  21.     VOID (*HWLineIntrHandler)(PVOID pHead);  
  22.   
  23.     ULONG (*HWGetRxBufferSize)(PVOID pHead);  
  24.   
  25.     VOID (*HWTxIntrHandler)(PVOID pHead);  
  26.   
  27.     ULONG (*HWPutBytes)(PVOID pHead, PUCHAR pSrc, ULONG NumBytes, PULONG pBytesSent);  
  28.   
  29.     BOOL (*HWPowerOff)(PVOID pHead);  
  30.   
  31.     BOOL (*HWPowerOn)(PVOID pHead);  
  32.   
  33.     VOID (*HWClearDTR)(PVOID pHead);  
  34.   
  35.     VOID (*HWSetDTR)(PVOID pHead);  
  36.   
  37.     VOID (*HWClearRTS)(PVOID pHead);  
  38.   
  39.     VOID (*HWSetRTS)(PVOID pHead);  
  40.   
  41.     BOOL (*HWEnableIR)(PVOID pHead, ULONG BaudRate);  
  42.   
  43.     BOOL (*HWDisableIR)(PVOID pHead);  
  44.   
  45.     VOID (*HWClearBreak)(PVOID pHead);  
  46.   
  47.     VOID (*HWSetBreak)(PVOID pHead);  
  48.   
  49.     BOOL (*HWXmitComChar)(PVOID pHead, UCHAR ComChar);  
  50.   
  51.     ULONG (*HWGetStatus)(PVOID pHead, LPCOMSTAT lpStat);  
  52.   
  53.     VOID (*HWReset)(PVOID pHead);  
  54.   
  55.     VOID (*HWGetModemStatus)(PVOID pHead, PULONG pModemStatus);  
  56.   
  57.     VOID (*HWGetCommProperties)(PVOID pHead, LPCOMMPROP pCommProp);  
  58.   
  59.     VOID (*HWPurgeComm)(PVOID pHead, DWORD fdwAction);  
  60.   
  61.     BOOL (*HWSetDCB)(PVOID pHead, LPDCB pDCB);  
  62.   
  63.     BOOL (*HWSetCommTimeouts)(PVOID pHead, LPCOMMTIMEOUTS lpCommTO);  
  64.   
  65.     BOOL (*HWIoctl)(PVOID pHead, DWORD dwCode,PBYTE pBufIn, DWORD dwLenIn, PBYTE pBufOut,DWORD dwLenOut,PDWORD pdwActualOut);  
  66.   
  67. } HW_VTBL, *PHW_VTBL;  

 这些函数将在PDD层实现,用于实际的串口硬件操作。

 

2. MDD层API

MDD层向上提供了流设备接口,这部分代码微软已经实现,用于管理串口。虽然我们不需要实现这部分,但是还是对相应的接口做个简单介绍。

 

2.1HANDLE COM_Init(ULONG Identifier)

       初始化串口设备,该函数通过读取注册表获得串口设备号,并获得相应的HWOBJ的结构指针,通过该指针调用PDD层的硬件初始化函数初始化串口。

Identifier如果驱动被设备管理器加载,那么这个参数将包含一个注册表键值在” HKEY_LOCAL_MACHINE/Drivers/Active”路径下。如果驱动是通过调用RegisterDevice函数来加载的,那么这个值等于dwInfo的值。在COM_Init中,会先打开该键值,用返回的句柄来查询DeviceArrayIndex值,并根据该值获得PDD层的HWOBJ结构指针。

 

2.2 BOOL COM_Deinit(void)

       卸载串口设备,该函数中主要做了一些释放资源的操作。也可以被DeregisterDevice函数调用。

 

2.3 HANDLE COM_Open(HANDLE pContext, DWORD AccessCode, DWORD ShareMode)

       打开串口设备。应用程序调用CreateFile函数打开串口时,该函数会被调用。

       pContextCOM_Init函数返回的Handle

       AccessCode设置访问模式,比如共享读或者是读写模式。

       ShareMode在参数从应用程序中的CreateFile函数中传来,表示是否支持独自占有。

 

2.4 BOOL COM_Close(DWORD pContext)

       关闭串口设备。应用程序调用CloseHandle函数关闭串口时,该函数会被调用。

       pContext该参数为COM_Open函数返回的Handle

 

2.5 ULONG COM_Read(HANDLE pContext, PUCHAR pTargetBuffer, ULONG BufferLength, PULONG pBytesRead)

       读串口数据。应用程序调用ReadFile函数读串口的时候,该函数被调用。

       pContextCOM_Open函数返回的Handle

       pTargetBuffer指向一个用于存放读到数据的Buffer

       BufferLengthpTargetBuffer指向的Buffer的大小。

       pBytesRead实际读到的数据的大小。

 

2.6 ULONG COM_Write(HANDLE pContext, PUCHAR pSourceBytes, ULONG NumberOfBytes)

       写串口数据。应用程序调用WriteFile函数写串口的时候,该函数被调用。

       pContextCOM_Open函数返回的Handle

       pSourceBytes指向一个Buffer,该Buffer包含要写入串口的数据。

       NumberOfBytes要写入串口的数据的大小。

 

2.7 BOOL COM_PowerUp(HANDLE pContext)

       该函数主要用于串口设备从suspend模式恢复到正常模式。

       pContext串口设备的Handle

 

2.8 BOOL COM_PowerDown(HANDLE pContext)

       该函数主要用于串口设备从正常模式进入suspend状态。

       pContext串口设备的Handle

 

2.9 BOOL COM_IOControl(DWORD dwOpenData, DWORD dwCode, PBYTE pBufIn, DOWRD dwLenIn, PBYTE pBufOut, DWORD dwLenOut, PDWORD pdwActualOut)

       该函数主要实现了一些串口的IO控制,他会被应用层的一些串口函数调用来获得或者设置串口的状态。

       dwOpenDataCOM_Open函数返回的Handle

       dwCodeI/O控制操作码。

       pBufIn传入的Buffer

       dwLenIn传入的Buffer的大小。

       pBufOut传出的Buffer

       dwLenOut传出的Buffer的大小。

       pdwActualOut:实际传出的数据的大小。

    对于串口驱动来说,COM_IOControl函数非常有用,应用程序通过调用COM_IOControl函数并传入不同的操作码,实现了控制串口的功能。这里列举一些操作码如下:

操作码

解释

IOCTL_SERIAL_CLR_DTR

设置串口的DTR管脚为低

IOCTL_SERIAL_CLR_RTS

设置串口的RTS管脚为低

IOCTL_SERIAL_DISABLE_IR

禁用串口的红外模式

IOCTL_SERIAL_ENABLE_IR

启用串口的红外模式

IOCTL_SERIAL_GET_COMMSTATUS

清除串口设备的异常标记并返回当前状态

IOCTL_SERIAL_GET_DCB

获得串口的DCB结构

IOCTL_SERIAL_GET_MODEMSTATUS

获得当前Modem的控制寄存器值

IOCTL_SERIAL_GET_PROPERTIES

重新获得当前串口设备的硬件属性

IOCTL_SERIAL_GET_TIMEOUTS

获得串口设备的读写超时

IOCTL_SERIAL_GET_WAIT_MASK

获得等待事件标记掩码

IOCTL_SERIAL_IMMEDIATE_CHAR

在发送数据前,先发送一个特定的字符

IOCTL_SERIAL_PURGE

清除串口中的输入输出Buffer,也可以中止未进行的读写操作

IOCTL_SERIAL_SET_BREAK_OFF

串口通讯从中断状态恢复

IOCTL_SERIAL_SET_BREAK_ON

设置串口为中断状态,停止发送接收数据

IOCTL_SERIAL_SET_DCB

设置串口的DCB结构

IOCTL_SERIAL_SET_DTR

设置串口的DTR管脚为高

IOCTL_SERIAL_SET_QUEUE_SIZE

目前,在微软的MDD层代码中没有支持

IOCTL_SERIAL_SET_RTS

设置串口的RTS管脚为高

IOCTL_SERIAL_SET_TIMEOUTS

设置串口的读写操作超时

IOCTL_SERIAL_SET_WAIT_MASK

设置等待事件标记掩码

IOCTL_SERIAL_SET_XOFF

软件流控模式下,终止数据传输

IOCTL_SERIAL_SET_XON

软件流控模式下,启动数据传输

IOCTL_SERIAL_WAIT_ON_MASK

等待一个与事件掩码中匹配的事件

       上述的操作码,很多都会被应用程序调用,看看MDD层中的实现,其中一些也是调用了PDD层下的函数来完成对串口硬件的设置。

3. PDD层API

       PDD层的函数主要是实现了对串口硬件的操作,函数比较多,不过还是都说一下吧:

3.1 PHWOBJ GetSerialObject(DWORD DeviceArrayIndex)

       该函数返回一个指向HWOBJ结构的指针,该结构包含了相关硬件接口函数的函数指针。

       DeviceArrayIndex串口索引号

 

3.2 VOID HWClearBreak(PVOID pContext)

       清除串口中断状态,用于串口从中断状态恢复。

       pConText指向HWInit函数返回的指针。

 

3.3 VOID HWClearDTR(PVOID pContext)

       设置串口的DTR管脚为低

       pConText指向HWInit函数返回的指针。

 

3.4 VOID HWClearRTS(PVOID pContext)

       设置串口的RTS管脚为低

       pConText指向HWInit函数返回的指针。

 

3.5 VOID HWClose(PVOID pContext)

       关闭由HWInit函数初始化的设备

       pConText指向HWInit函数返回的指针。

 

3.6 VOID HWDeinit(PVOID pContext)

       当设备驱动被卸载的时候,该函数被调用。

       pConText指向HWInit函数返回的指针。

 

3.7 VOID HWDisableIR(PVOID pContext)

       禁用串口的红外模式

       pConText指向HWInit函数返回的指针。

 

3.8 VOID HWEnableIR(PVOID pContext)

       启用串口的红外模式

       pConText指向HWInit函数返回的指针。

 

3.9 VOID HWGetCommProperties(PVOID pContext, LPCOMMPROP pCommProp)

       重新获得当前串口设备的硬件属性。

       pConText指向HWInit函数返回的指针。

       pCommProp指向一个COMMPROP结构,该结构描述硬件设备的属性,比如最大波特率,停止位以及流控模式等。

 

3.10 INTERRUPT_TYPE HWGetIntrType(PVOID pContext)

       获得当前的中断类型。返回值可以是INTR_NONEINTR_LINEINTR_RXINTR_TXINTR_MODEM,这些值在Serhw.h中定义。

       pConText指向HWInit函数返回的指针。

 

3.11 VOID HWGetModemStatus(PVOID pContext, PULONG pModemStatus)

       获得Modem的状态。

       pConText指向HWInit函数返回的指针。

       pModemStatusModem的状态。

 

3.12 ULONG HWGetRxBufferSize(PVOID pContext)

       获得串口硬件接收Buffer的大小。

       pConText指向HWInit函数返回的指针。

 

3.13 PVOID HWGetRxStart(PVOID pContext)

       返回硬件接收Buffer的起始位置。

       pConText没有被使用。

 

3.14 ULONG HWGetStatus(PVOID pContext, LPCOMSTAT lpStat)

       获得硬件状态信息。

       pConText指向HWInit函数返回的指针。

       lpStat指向COMSTAT结构,该结构描述硬件状态。

 

3.15 PVOID HWInit(ULONG Identifier, PVOID pMDDContext, PHWOBJ pHWObj)

       初始化串口硬件设备。

       Identifier该驱动的键值,从MDD层传到PDD层。

       pMDDContext指向MDD层串口相关信息,从MDD层传给PDD层。

       pHWObj指向HWOBJ结构。

 

3.16 BOOL HWIoctl(DWORD dwOpenData, DWORD dwCode, PBYTE pBufIn, DWORD dwLenIn, PBYTE pBufOut, DWORD dwLenOut, PDWORD pdwActualOut)

       执行I/O控制

       dwOpenDataCOM_Open函数返回的Handle

       dwCodeI/O控制操作码。

       pBufIn传入的Buffer

       dwLenIn传入的Buffer的大小。

       pBufOut传出的Buffer

       dwLenOut传出的Buffer的大小。

       pdwActualOut:实际传出的数据的大小。

 

3.17 VOID HWLineIntrHandler(PVOID pContext)

       线路状态信息中断处理函数

       pContext指向HWInit函数返回的指针。

 

3.18 VOID HWModemIntrHandler(PVOID pContext)

       该函数检测Modem状态,并对相关中断进行处理。

       pContext指向HWInit函数返回的指针。

 

3.19 BOOL HWOpen(PVOID pContext)

       打开串口设备,可以在该函数中打开串口硬件供电。

       pContext指向HWInit函数返回的指针。

 

3.20 VOID HWOtherHandler(PVOID pContext)

       该函数已经被HWModemIntrHandler取代,实现与HWModemIntrHandler一样。

       pContext指向HWInit函数返回的指针。

 

3.21 BOOL HWPostInit(PVOID pContext)

       该函数在COM_Init中被调用,但是在串口数据,硬件以及IST初始化后备调用。

       pContext指向HWInit函数返回的指针。

 

3.22 BOOL HWPowerOff(PVOID pContext)

       串口硬件进入Suspend模式。

       pContext指向HWInit函数返回的指针。

 

3.23 BOOL HWPowerOn(PVOID pContext)

       串口硬件从Suspend模式恢复到工作模式。

       pContext指向HWInit函数返回的指针。

 

3.24 VOID HWPurgeComm(PVOID pContext, DWORD fdwAction)

       清除串口硬件buffer的信息。

       pContext指向HWInit函数返回的指针。

       fdwAction

                        PURGE_TXABORT:终止写操作立即返回。

                        PURGE_RXABORT:终止读操作立即返回。

                        PURGE_TXCLEAR:清空写Buffer

                        PURGE_RXCLEAR:清空读Buffer

 

3.25 ULONG HWPutBytes(PVOID pContext, PUCHAR pSrc, ULONG NumberOfBytes, PULONG pBytesSent)

       通过写数据到硬件中来直接发送数据。

       pContext指向HWInit函数返回的指针。

       pSrc指向要发送的数据Buffer

       NumberOfBytes要发送的数据长度。

       pBytesSent实际发送的数据长度。

 

3.26 VOID HWReset(PVOID pContext)

       复位串口硬件。

       pContext指向HWInit函数返回的指针。

 

3.27 ULONG HWRxIntrHandler(PVOID pContext, PUCHAR pTargetBuffer, PULONG pByteNumber)

       接收数据中断处理函数。

       pContext指向HWInit函数返回的指针。

       pTargetBuffer接收数据Buffer

       pByteNumber接收数据Buffer的大小。

 

3.28 VOID HWSetBreak(PVOID pContext)

       设置串口为中断状态,停止发送接收数据。

       pContext指向HWInit函数返回的指针。

 

3.29 BOOL HWSetCommTimeouts(PVOID pContext, LPCOMMTIMEOUT lpCommTO)

       设置串口操作超时时间。

       pContext指向HWInit函数返回的指针。

       lpComTO指向一个超时的结构,其中包括读写超时。

 

3.30 BOOL HWSetDCB(PVOID pContext, LPDCB pDCB)

       设置串口硬件设备信息。

       pContext指向HWInit函数返回的指针。

       pDCB指向DCB结构,该结构描述相关的串口硬件设置信息。

 

3.31 VOID HWSetDTR(PVOID pContext)

       设置串口的DTR管脚为高

       pContext指向HWInit函数返回的指针。

 

3.32 VOID HWSetRTS(PVOID pContext)

       设置串口的RTS管脚为高

       pContext指向HWInit函数返回的指针。

 

3.23 VOID HWTxIntrHandler(PVOID pContext, PUCHAR pSourceBuffer, PULONG pByteNumber)

       串口发送中断处理函数。

       pContext指向HWInit函数返回的指针。

       pSourceBuffer:发送数据Buffer

       pByteNumber:最大能够发送的数据的大小。函数返回时,指向实际发送的数据的大小。

 

3.24 VOID HWXmitComChar(PVOID pContext, UCHAR ComChar)

       发送一个字符

       pContext指向HWInit函数返回的指针。

       ComChar要被发送的字符。

 

 

 

    上述这些函数不一定串口驱动中都会被用到,根据具体要求来实现吧。在这里我还要给自己找条退路,由于本人并未实现上面的所有函数,一些是通过读文档和看源码分析得来,而且本人水平有限,如果有错误的地方,请谅解并欢迎指正。

posted @ 2011-10-13 10:20  风雨雪夜  阅读(249)  评论(0编辑  收藏  举报