- 這裏介紹一下USB Serial。USB Serial就是指基於USB的虛擬串口,實際上是將USB作爲一個串口設備來進行操作。
對於應用程序來說,通訊起來比較簡單,就是打開串口,然後接收發送數據就可以了。下面介紹一下具體步驟:
1. 選擇USB Client Serial組件
在定製WinCE
的時候,在Catalog Items View中選擇”Device Drivers”->”USB Function”->”USB Function Clients”->”RNDIS Clients”,如圖:
2. 更改USB Client的註冊表配置
選擇默認驅動爲Serial_class類,如下:
[HKEY_LOCAL_MACHINEDriversUSBFunctionDrivers]
"DefaultClientDriver"="Serial_class"
[HKEY_LOCAL_MACHINEDriversUSBFunctionDriversSerial_Class]
"Dll"="serialusbfn.dll"
"DeviceName"="USBFNS1:"
"Prefix"="COM"
"IClass"=""
"idVendor"=dword:0547
"Manufacturer"=”Honeywell”
"idProduct"=dword:2720
"Product"=”Honeywell Product”
"bcdDevice"=dword:0
"DeviceType"=dword:0
具體這些配置不多說了,以前已經介紹過Mass Storage和RNDIS,這個應該很好理解。
http://blog.zdnet.com.cn/html/98/427598-2886454.html
3. 重新編譯WinCE
完成了上面的配置以後,重新編譯WinCE,然後下載
到板子上面運行。
4. PC端USB Serial驅動更新
如
果想讓PC識別出目標板的USB設備,這裏必須安裝相應的驅動。驅動包含在微軟提供的ActiveSync軟件中,從微軟的網站上面下載就可以了,然後在
PC端進行安裝。安裝好後,進入安裝目錄找到”Drivers”目錄,在該目錄下有個文件叫”
wceusbsh.inf”,打開這個文件,添加相應的驅動信息,VID和PID要和前面的註冊表配置保持一致。具體改動如下:
(1) 找到第一個<VENDOR SECTION>並添加如下信息:
%Honeywell% = Honeywell
(2) 搜索到第二個<VENDOR SECTION>並添加如下信息:
[Honeywell]
%USBVid_0547&Pid_2720.DeviceDesc% = Host_Inst, USBVid_0547&Pid_2720
(3) 搜索到第三個<VENDOR SECTION>並添加如下信息:
Honeywell = "Honeywell"
USBVid_0547&Pid_2720.DeviceDesc = "Honeywell USB Serial"
5. 安裝USB Serial驅動
具有USB Serial功能的WinCE在目標板上運行之後,將USB插到PC上面,這時會彈出安裝驅動的對話框,根據嚮導將驅動程序的位置指向”Microsoft ActivesyncDrivers”目錄,然後就可以成功安裝了。
6. 基於USB Serial的串口通訊
對於WinCE目標板來說,直接打開串口就可以,在我的系統裏面支持多個串口,USB Serial是”COM5:”,通過CreateFile打開就可以,然後通過WriteFile和ReadFile函數來發送和接收數據,和一般的串口通訊是一樣的。
對於PC來說,需要打開” wceusbsh001”設備,同樣用CreateFile,這一點和普通的串口通訊略有區別,發送和接收數據同樣用WriteFile和ReadFile,這裏還是給個例子吧,搞清楚例子是PC端的串口通訊,如下:
#define WRITE_COM 1
#define USBSERIAL_NAME "[url=]/.wceusbsh001[/url]"
int _tmain(int argc, _TCHAR* argv[])
{
HANDLE hSerial;
DCB PortDCB;
COMMTIMEOUTS CommTimeouts;
unsigned char buf[64];
DWORD i, num;
BOOL SerialFlag;
hSerial = CreateFile(_T(USBSERIAL_NAME), (GENERIC_READ | GENERIC_WRITE), 0, NULL, OPEN_EXISTING, 0, NULL);
if (hSerial == NULL)
{
printf("Open Error.rn");
return 1;
}
PortDCB.DCBlength = sizeof(DCB);
GetCommState(hSerial, &PortDCB);
PortDCB.BaudRate = 115200;
PortDCB.ByteSize = 8;
PortDCB.Parity = NOPARITY;
PortDCB.StopBits = ONESTOPBIT;
if (! SetCommState(hSerial, &PortDCB))
{
printf("Set COM Parameter Error.rn");
CloseHandle(hSerial);
return 1;
}
GetCommTimeouts(hSerial, &CommTimeouts);
CommTimeouts.ReadIntervalTimeout = MAXDWORD;
CommTimeouts.ReadTotalTimeoutMultiplier = 10;
CommTimeouts.ReadTotalTimeoutConstant = 10;
CommTimeouts.WriteTotalTimeoutMultiplier = 50;
CommTimeouts.WriteTotalTimeoutConstant = 100;
if (!SetCommTimeouts(hSerial, &CommTimeouts))
{
printf("Set COM timeout parameter error.rn");
CloseHandle(hSerial);
return 1;
}
#if WRITE_COM
for (i = 0; i < 10; i ++)
{
memset(buf, i, sizeof(buf));
SerialFlag = WriteFile(hSerial, buf, sizeof(buf), &num, NULL);
if (SerialFlag)
{
printf("Write %d bytes to COM.rn", num);
}
else
{
printf("Write COM Error.rn");
}
Sleep(1000);
}
#else
while(1)
{
memset(buf, 0, sizeof(buf));
SerialFlag = ReadFile(hSerial, buf, 16, &num, 0);
if (SerialFlag)
{
if (num == 0)
{
printf("Read Successfully, but didn't read any data.rn");
}
else
{
printf("Read data: ");
for (i = 0; i < 16; i ++)
{
printf("0x%x, ", buf);
}
printf("rn");
}
}
else
{
printf("Read COM Error.rn");
}
Sleep(1000);
}
#endif
CloseHandle(hSerial);
return 0;
}