凌
凌未风
Unregistered / Unconfirmed
GUEST, unregistred user!
我在编写hid类器件的编程中遇见一个奇怪的问题,程序在和设备设备建立连接,识别后经检查<br>无误,取得的厂商(vendor id)和产品(product id)的id号和厂家提供的id完全符合.缓冲区的指针<br>和设备的能力也取得了,并且也不是按键型hid类设备。 而且设备里的确是有数据的,但<br>在用readfile函数取数据时取得的数据全是0,我检查了数据类型和前期的连接相信没错。<br>各位高手那位能给我讲讲这是为什么???还有各位能否留下QQ号,我在编程时还有些没解决的<br>问题想请教大家,此外我这里还有WINDOWS下编程的资料(400M)也可以和大家共享的!!!<br>我的QQ:121144437(微尘)!!!我先谢谢大家了!!!<br>下面是我的程序,主要使用的API函数这些函数在DDK中可以找到,此外我的HID设备有两个管道<br>一个是写,一个是读。程序有点乱,大家包含一下吧!!!<br><br><br>unit TranThreadUnit;<br><br>interface<br> Uses Classes,Windows,StdCtrls,SysUtils,SyncObjs,<br> Messages, Variants, Graphics, Controls, Forms,<br> Dialogs, ExtCtrls, Math;<br> var<br> hiddata:array[0..1000000]of byte;//usb数据缓冲区<br>Type<br> TUSBTranThread = Class(TThread) //(TThread):初始化一个多线程的程序<br> private<br> devicehandle,InfoOutPipe,InfoInPipe,MainInPipe:THandle;<br> TotalTimes,NowTime,LastLength:Word;<br> MyOverLapData:OverLapped; // The OVERLAPPED 构造一个信息使用在异步输入或是输入<br> DeviceName:String;<br> FileName:String;<br><br> protected<br> procedure Execute;Override;<br> public<br> Constructor Create(UsbDeviceName, SaveFileName: String);<br><br> end;<br><br>Var<br> BytesTransfered,<br> PackageNum:Cardinal;<br> StartATrans:Boolean;<br>implementation<br><br>uses SetupAPI;<br><br>Constructor TUSBTranThread.Create(UsbDeviceName, SaveFileName: String);<br>begin<br> Inherited Create(False);<br> FreeOnTerminate:=True;<br><br> DeviceName := UsbDeviceName; //主线程传回设备的路径<br> FileName := SaveFileName;//主线程传回存盘文件名<br>end;<br><br>procedure TUSBTranThread.Execute; // 线程开始工作<br>label SkipReadLoop;<br>Const<br> EachBulkSize=1024; //数据缓冲区长度<br>var<br> a:word;<br> l,c:integer;<br> shuzi,getcaps:cardinal;//作为hidp_getcaps函数的返回值<br> ifatt: THIDD_ATTRIBUTES;<br> ifcaps: THIDP_CAPS;<br> ifphidointer;<br> Data:array[0..EachBulkSize-1] of byte; //数据缓冲区<br> DataFile:File;<br> EndEvent:TEvent; //结束事件<br> InfoIn:Array[1..2] of Word;<br> MyCommand:Word;<br>// Len,TranLen,<br> TransLength,i,T:Cardinal; //Cardinal类型 0..4294967295 unsigned(无符号) 32-bit<br> Tr:Boolean;<br> begin<br><br> devicehandle := CreateFile(PChar(DeviceName),Generic_Write,File_Share_Write,Nil,Open_Existing,0,0); //取得设备的代号<br><br> ifatt.size := sizeof(ifatt);<br> HidD_GetAttributes (devicehandle,@ifatt); //取厂商与产品的id<br><br> HidD_GetPreparsedData(devicehandle,@ifphid); //取得包含设备能力的缓冲区指针<br><br> // ifcaps.size := sizeof(ifcaps);<br> getcaps:=HidP_GetCaps(ifphid,@ifcaps); //判断是否取得设备的能力<br><br>{ if (getcaps=hidp_status_invalid_preparsed_data) then //如果上一个函数返回的是错误的信息给出出错提示<br> begin<br> with Application do<br> begin<br> NormalizeTopMosts;<br> MessageBox('无法取得USB设备的能力!!!', '提示!!!', MB_OK);<br> RestoreTopMosts;<br> end;<br> end;<br> }<br>// if (ifcaps.NumberInputValueCaps=0) then // 上一个函数返回的结构中说明接口内无数据<br>// begin<br>// with Application do<br>// begin<br>// NormalizeTopMosts;<br>// MessageBox('USB设备内无数据!!!', '提示!!!', MB_OK);<br>// RestoreTopMosts;<br>// application.Terminate;<br>// end;<br>// end<br>// else<br>// begin<br> l:=round(ifcaps.NumberInputValueCaps div ifcaps.InputReportByteLength); //要取多少次数据,并确保除数部为零<br> a:=ifcaps.NumberInputValueCaps mod ifcaps.InputReportByteLength ; //最后一次要取多少数据<br>// end;<br>//我觉得以上的程序没有问题的<br> try<br> AssignFile(DataFile,FileName); // (连接的外部文件类型 / 文件名)<br> rewrite(datafile,1);<br> filemode:=2;//datafile类型是可读/写<br> for c:=0 to l-1 do<br> begin<br> ReadFile(devicehandle,hiddata,ifcaps.InputReportByteLength,i,Nil); //读文件<br> //ReadFile读回来的数据全时0,问题就在这里<br>// While(WaitForSingleObject(EndEvent.Handle,100)=Wait_TimeOut) do //判定数据是否读完 (或者是度文件完毕/下在文件超时 毫秒)<br>// begin<br> //append(datafile);<br> //write(datafile,ifcaps.InputReportByteLength ); //??????????????????<br> blockwrite(datafile,hiddata,ifcaps.InputReportByteLength);//应该是i还是ifcaps.InputReportByteLength<br>// end; //??????????????????<br> end;<br> ReadFile(devicehandle,hiddata,a,i,Nil); //读文件<br> //ReadFile读回来的数据全时0,问题就在这里<br> blockwrite(datafile,hiddata,ifcaps.InputReportByteLength);<br><br> closefile(datafile);<br> except<br> // MessageBox(handle,'文件打开失败','错误',MB_OK);<br> begin<br> with Application do<br> begin<br> NormalizeTopMosts;<br> MessageBox('文件下载失败!!!', '提示!!!', MB_OK);<br> RestoreTopMosts;<br> end;<br> end<br> end;<br>end;<br>end.