farorlee
驱动牛犊
驱动牛犊
  • 注册日期2004-11-05
  • 最后登录2006-01-12
  • 粉丝0
  • 关注0
  • 积分0分
  • 威望0点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
阅读:1762回复:2

BULK传输块与块数据错位的问题,各位大侠帮忙给看看啊!急

楼主#
更多 发布于:2005-03-09 17:58
    各位大侠,小弟做USB2.0数据采集卡的开发,最近被一个问题卡住了,都快两个星期了,急得不得了,哪位大侠不吝赐教,小弟必会散尽所有回报。

    我用的是CY7C68013做主控芯片,ADS7862做AD并同时采集两通道信号,每通道500K,12位,也就是总的数据量是2MBytes/s。68013与AD之间用了两个IDT7202(每个1K,分别存放AD转换结果的高字节和低字节)做为FIFO,一旦7202发出半满信号,68013就启动一次GPIF波形,TranstionCount我设为512(因为我的端点配置是EP2,IN,4×1024,BULK,AUTOINLEN = 1024),因为数据是16位的,512次GPIF传输恰好填满一个EP2的1024。数据在FIFO中 存放的格式是:1通道,2通道,1通道,2通道…………1通道,2通道。我在主机应用程序中开辟一个1024Bytes的数组来存放一次用DeviceIOControl读回来的数据。

    现在的问题是我将每次读回来的数据组合起来画图,发现每个1024缓冲块中的数据都是连续的,但偶尔块与块的数据会出现错位,也就是1通道和2通道的数据存放位置错位了。也即本来应该是1通道,2通道,1通道,2通道…………1通道,2通道(数组的偶数索引放1通道,奇数索引放2通道);而现在会有1通道,2通道,1通道,2通道…………2通道,1通道,2通道,1通道的情况出现(变成数组的偶数索引放2通道,奇数索引放1通道),这样的数据我后续无法区分并处理啊。

    哪位大侠知道问题会出在哪里啊?教教小弟吧,小弟快急死了。谢谢!谢谢!
    下面我贴出来一些我用来调试程序的源代码,请大侠们帮我看看:
/////////////////////////////////////////////////////////////////////////////////////
//                            gpif波形                           ////////////////////
/////////////////////////////////////////////////////////////////////////////////////
// GPIF Waveform 2: FIFO Rea                                                                
//                                                                                        
// Interval     0         1         2         3         4         5         6     Idle (7)
//          _________ _________ _________ _________ _________ _________ _________ _________
//                                                                                        
// AddrMode Same Val  Same Val  Same Val  Same Val  Same Val  Same Val  Same Val          
// DataMode NO Data   NO Data   Activate  Activate  Activate  Activate  Activate          
// NextData SameData  SameData  SameData  SameData  SameData  SameData  SameData          
// Int Trig No Int    No Int    No Int    No Int    No Int    No Int    No Int            
// IF/Wait  IF        Wait 1    IF        Wait 1    Wait 1    Wait 1    Wait 1            
//   Term A FIFOFlag            TCXpire                                                    
//   LFunc  AND                 AND                                                        
//   Term B FIFOFlag            TCXpire                                                    
// Branch1  Then 0              ThenIdle                                                  
// Branch0  Else 1              Else 0                                                    
// Re-Exec  No                  Yes                                                        
// Sngl/CRC Default   Default   Default   Default   Default   Default   Default            
// RD           1         0         0         0         0         0         0         1    
// CTL1         0         0         0         0         0         0         0         0    
// CTL2         0         0         0         0         0         0         0         0    
// CTL3         0         0         0         0         0         0         0         0    
// CTL4         0         0         0         0         0         0         0         0    
// CTL5         0         0         0         0         0         0         0         0    
//
//GPIF FIFO READ大概思路是S0(DP)检测EP2FIFO是否满,是则转S0,否则转S1,S1是FIFO读信号为低,但不读数据,S2(DP)检测TCExpire,是则转IDLE,否则转S0。总共就三个态。


/////////////////////////////////////////////////////////////////////////////////////
//                            FIFO READ函数                           ///////////////
/////////////////////////////////////////////////////////////////////////////////////
// read byte(s)/word(s) from PERIPHERAL, using GPIF and EPxFIFO
// if EPx WORDWIDE=0 then read byte(s)
// if EPx WORDWIDE=1 then read word(s)

void Peripheral_FIFORead( BYTE FIFO_EpNum, WORD TC )
{
       //如果GPIF波形正在执行,则等待
while( !( GPIFTRIG & 0x80 ) ) // poll GPIFTRIG.7 GPIF Done bit
   {
   ;
   }

//设置TC
Peripheral_SetEP2GPIFTC(TC);

   // trigger FIFO read transaction(s), using SFR
   GPIFTRIG = GPIFTRIGRD | FIFO_EpNum; // R/W=1, EP[1:0]=FIFO_EpNum for EPx read(s)  

}

// Set EP2GPIF Decision Point FIFO Flag Select (PF, EF, FF)
void SetEP2GPIFFLGSEL( WORD DP_FIFOFlag )
{
EP2GPIFFLGSEL = DP_FIFOFlag;
}

//在这个函数中不断检测IDT7202的半满标志,为低则读,TransitionCount=0x0200
void TD_Poll(void)             // Called repeatedly while the device is idle
{
if ( !IDT_HALF )
{
if(EP2468STAT & 0x02)
{
                 //如果EP2满
}
else
{
       SetEP2GPIFFLGSEL( GPIF_FLGSELFF );
Peripheral_FIFORead(GPIF_EP2, TransitionCount);
}
}  
}


/////////////////////////////////////////////////////////////////////////////////////
//                           主机的WIN32程序                           //////////////
/////////////////////////////////////////////////////////////////////////////////////
BOOL ReceiveData(FILE* pfile)
{
BOOL ReadSuccess;
BULK_TRANSFER_CONTROL bulkControl;
ULONG nBytes = 0;
ULONG count = 0;
SHORT tempdata0 = 0, tempdata1 = 0;
int block = 0;

UCHAR usbBuffer[1024];               //分配一个512 BYTES的USB接收缓冲区
//初始化缓冲区
for(int i=0;i<1024;i++)
usbBuffer = 0;

cout<<\"1024字节的缓冲区已经分配并且初始化!\\n\"<<endl;


if(!BeginCommand())             //发送开始采样命令
{
return FALSE;
}

bulkControl.pipeNum = 1;

cout<<\"\\n已经开始采样,请等待...\\n\"<<endl;

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
while(count<10000)              //测试时采样数据的总字节数,可改,我怀疑这有问题!!
{
ReadSuccess = DeviceIoControl(devhandle,
IOCTL_EZUSB_BULK_READ,
&bulkControl,
sizeof(BULK_TRANSFER_CONTROL),
usbBuffer,
sizeof(usbBuffer),
&nBytes,
NULL);

if(!ReadSuccess)
{
return FALSE;
}

//将数据写入文件中,这是将两通道12位采样数据区分并且整理成10进制数的程序
for(ULONG i=0;i<nBytes;i=i+4)
{
tempdata0 = (SHORT)(CombineData(usbBuffer[i+1],usbBuffer)<<4);
tempdata0 /= 16;
tempdata1 = (SHORT)(CombineData(usbBuffer[i+3],usbBuffer[i+2])<<4);
tempdata1 /= 16;
fprintf(pfile,\"%d,%d\\n\",tempdata0,tempdata1);
}

cout<<++block<<\": \"<<nBytes<<\"  \";
if(block%5 == 0)
cout<<\"\\n\";

count += nBytes;    //对接收到的数据点进行计数
}
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////

cout<<\"\\n\"<<\"采样已经结束!\\n\"<<endl;
cout<<\"count = \"<<count<<endl<<endl;

if(!EndCommand())     //发送采样结束命令
{
return FALSE;
}

return TRUE;
}

下面有一个附件,是用EXCEL画的错位的数据。














[编辑 -  3/9/05 by  farorlee]

[编辑 -  3/9/05 by  farorlee]

[编辑 -  3/9/05 by  farorlee]

最新喜欢:

murongyumurong...
farorlee
驱动牛犊
驱动牛犊
  • 注册日期2004-11-05
  • 最后登录2006-01-12
  • 粉丝0
  • 关注0
  • 积分0分
  • 威望0点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
沙发#
发布于:2005-03-09 19:46
没有大哥顶一下啊?是小弟说的不清楚吗?
flyto
驱动牛犊
驱动牛犊
  • 注册日期2001-10-26
  • 最后登录2005-05-27
  • 粉丝0
  • 关注0
  • 积分5分
  • 威望1点
  • 贡献值0点
  • 好评度0点
  • 原创分0分
  • 专家分0分
板凳#
发布于:2005-04-13 17:27
你的设置能发过来看看吗?
flyto@flyto.cn


[编辑 -  4/13/05 by  flyto]
flyto
游客

返回顶部