阅读:3401回复:13
ISP1581的DMA传输编程。
最近我购买了一块周立功公司的ISP1581开发板,
但直接连接上去速度不高。 所以我想使用DMA传输,希望可以获得更高的传输速度。 我选用的是GDMA从机模式。 按照时序外接了一块FPGA作为硬件电路。 但在软件编程上碰到了一些问题,不知如何解决, 希望各位大侠指点,不胜感激。 我的理解: 初始化时设置DMA, 当端口中断发生时,处理中断, 在数据处理循环中,发送DMA读写命令, 等待DMA传输完成。 具体代码如下: 在void Init_Main(void)里面增加调用DMA初始化函数DMA_Init(); void DMA_Init(void) { //issue DMA reset command to ISP1581 D14_Cntrl_Reg.D14_DMA_COMMAND = DMA_RESET; //初始化,这句没有写错吧。 D14_Cntrl_Reg.D14_GDMA_CONFIG.VALUE = 0x8000; //不要计数模式,不知需不需要计数器区别大不大? //initialize the config and hardware register to //set ISP1581 to generic DMA mode D14_Cntrl_Reg.D14_GDMA_CONFIG.BITS.CNTENA = 0; D14_Cntrl_Reg.D14_GDMA_CONFIG.BITS.WIDTH = 1; D14_Cntrl_Reg.D14_UDMA_CONFIG.BITS.IGNORE_IORDY = 0; D14_Cntrl_Reg.D14_UDMA_CONFIG.BITS.PIO_MODE = 0; D14_Cntrl_Reg.D14_UDMA_CONFIG.BITS.UDMA_MODE = 0; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.ENDIAN = 0; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.EOT_POL = 1; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.ACK_POL = 0; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.DREQ_POL = 1; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.WRITE_POL = 0; D14_Cntrl_Reg.D14_DMA_HARDWARE.BITS.READ_POL = 0; //set to DMA endpoint 1 //set to Endpoint Index to 2 //this is to prevent the endpoint index pointing to the same endpoint D14_Cntrl_Reg.D14_DMA_ENDPOINT = 4; //请教各位大侠,这个DMA端点应该怎么设置,它跟端点有什么对应关系,端点应该对应那个缓冲区呢,被设置为DMA的端点,在Init_Endpoint(void)里面应该怎么设置呢,DMA端点是否只能设置一个呢?设置以后还需要进行其他配置吗? D14_Cntrl_Reg.D14_ENDPT_INDEX = 2; //enable DMA interrupt D14_Cntrl_Reg.D14_DMA_INT_ENABLE.VALUE = 0x000D; //initialize internal variables Kernel_Flag.BITS.Out_Reset_Done = 0; Kernel_Flag.BITS.In_Reset_Done = 0; Kernel_Flag.BITS.MPIO_Out_Reset_Done = 0; Kernel_Flag.BITS.MPIO_In_Reset_Done = 0; } //以上这段代码改变自从P公司下载的代码。 不知DMA的初始化是否已经足够,还差什么,或者那些地方写错了? ----------------------------- DMA初始化后就进行传输处理了,我的理解是DMA端点对应普通的端点,在PC端对端口进行对写,就是对DMA端口进行读写了,不知这样的 理解对不对。所以我使用了D14_DMA_ENDPOINT = 4;PC程序不断想端点4 发送数据,我在中断处理程序void Int_Ext_0(void) interrupt 0 using 1里面增加代码: //DMA DMA_Int_Flag.VALUE |= D14_Cntrl_Reg.D14_DMA_INT.VALUE; D14_Cntrl_Reg.D14_DMA_INT.VALUE = DMA_Int_Flag.VALUE; //这样写对吗? 然后我在void DMA_Mode(Data)里面进行数据处理,我测试的代码只处理PC输出数据。 if(Data) { //read do { //Check for Out Token ACK interrupt while(!USB_Int_Flag.BITS.EP2RX) { if(USB_Int_Flag.BITS.SUSP || Kernel_Flag.BITS.Bus_Reset || USB_Int_Flag.BITS.EP0SETUP) break; } EA_DISABLE; USB_Int_Flag.BITS.EP2RX = 0; EA_ENABLE; 当检测到中断的时候,我的理解是这个端点写数据应该可以触发这个中断,而这个端点已经被设置成DMA端点。所以在这后面写处理代码: D14_Cntrl_Reg.D14_DMA_ENDPOINT = 4; //指向DMA端点 //Read in FIFO data if (bytecount > PIO_Count) { Datcount = PIO_Count; } else { Datcount = bytecount; } D14_Cntrl_Reg.D14_DMA_COMMAND = GDMA_Read_Command; //开始传输,不知是否可以发指令,是否是这个指令。 //等待DMA处理完成 while(!DMA_Int_Flag.BITS.DMA_DONE && !DMA_Int_Flag.BITS.INT_EOT) { //Exit function when bus reset or suspend detected if(USB_Int_Flag.BITS.SUSP || Kernel_Flag.BITS.Bus_Reset || USB_Int_Flag.BITS.EP0SETUP) { D14_Cntrl_Reg.D14_DMA_COMMAND = DMA_RESET; DMA_Init(); break; } } //完成 DMA_Int_Flag.BITS.DMA_DONE = 0; DMA_Int_Flag.BITS.INT_EOT = 0; //以下是其它代码 bytecount -= Datcount; }while(bytecount); } else { …… 但是在测试过程中,程序并没有运行起来,DREQ脚没有检测到高电平, 不知程序出错在那里,是初始化,还是中断处理,还是DMA控制处理。 还是DMA传输原理不是这样的。希望得到各位高手的指点。谢谢。 |
|
沙发#
发布于:2003-06-24 11:32
祝贺你购买了开发板
建议你用断开模式 |
|
板凳#
发布于:2003-06-24 11:38
周立功的那个ISP1581开发板是没有DMA功能的,USB2.0如果不能实现DMA传输的话其实是没有什么意义的。
|
|
地板#
发布于:2003-06-24 12:41
我用ISP1581的通用处理器模式最高的做到4.5M/s,不知道你能做到多高。我没用过dma,也没仔细深究过。
|
|
地下室#
发布于:2003-06-24 23:23
板子直接使用才用80K,
修改程序后可以达到400K, 不处理数据直接清空缓冲区可以达到4.5M,不过这样没有什么意义了。 板上单片机为PHILIPS P89C61x2 。 plasma:希望可以讲详细点,编程的关键点在哪里阿。 jinghuiren:你用什么单片机阿,可以达到这么高速度。 sod123:改板有输出脚,理论上可以外接DMA硬件线路的, 我外接了一块MAX7128,并且按照时序图编写了一个逻辑, 不知这样做行不行得通。 还请各位大侠指点赐教,不胜感激。^_^ |
|
5楼#
发布于:2003-06-25 10:36
我用的是40M的DSP,好像是ADSP21062,别名叫SHARC。
我用TMS3205402平均速度才能达到3M/s 用tms320f206平均速度能达到2M/s。 速度测试是,用dsp来填充端点缓冲区,由app读取数据,然后存储到文件中,整个过程的传输速度。 如果直接清空端点的话那当然会更快,可是这是无意义的,因此我根本就没有试过。 |
|
6楼#
发布于:2003-06-25 10:54
DMA的实现牵涉到两个地方,一是控制器对ISP1581的设置,包括DMA的模式选择,传输长度,BUFFER大小等;二是外部电路的配合,就是实现DMA读写的控制与时序。
DMA传输时,控制CPU是不参与的,所以这时的传输速率就取决于外部DMA控制电路的设计,以及PC机驱动程序的设计。PC机这边我们可以把缓存开的大一些,每次读写更多的数据,这样效率也就自然提高了;DMA控制电路的设计,主要是在满足ISP1581最小读写周期的前提下,使读写周期尽量小,这样也就提高了传输速率。 如果没有DMA传输,那么控制CPU就很可能成为一个瓶颈了。 其实DMA控制电路的设计并不麻烦,时序比较简单,我们的开发板上是用CPLD来实现的,几十行的代码就搞定了。 |
|
7楼#
发布于:2003-06-25 23:09
祝贺你购买了开发板 周立功的开发板就是断开总线模式的啊。 那还有什么好的方法。 |
|
8楼#
发布于:2003-06-25 23:12
我用的是40M的DSP,好像是ADSP21062,别名叫SHARC。 谢谢jinghuiren兄指点, 呵呵,没办法,我连DSP都还没有见过。 看来还需修炼多几年了,努力中。。。。 |
|
9楼#
发布于:2003-06-25 23:17
DMA的实现牵涉到两个地方,一是控制器对ISP1581的设置,包括DMA的模式选择,传输长度,BUFFER大小等;二是外部电路的配合,就是实现DMA读写的控制与时序。 XXG兄啊,多谢指点。 你提到的问题我基本都留意了,但还是无法成功, 我已经对DMA的相关寄存器进行了初始化, 不知哪里设置得不对,还希望给予指点。 另外,你提到你们的开发板, 我想问一下你们的开发板的实际速度达到多少, 是通过什么方法测量出来的速度。谢谢。 |
|
10楼#
发布于:2004-06-14 18:03
我的MDMA也动不了。 :(
我是这样启动dma的: 1)Set DMA Endpoint 04 2)Set DMA Transfer Counter 3)Set MDMA Read Command 然后理论上就应该开始了。 可是没有看到数据呀? |
|
11楼#
发布于:2004-06-14 20:23
hi
me too |
|
12楼#
发布于:2004-06-15 10:37
可以启动了。
数据是从设备上传到主机的,所以应该用endpt 05 |
|
13楼#
发布于:2005-01-29 09:16
lily311还在吗?有问题要请教……
你启动DMA的步骤里面不用设置LBA地址的吗? 还有,如果DMA成功启动把数据传到enpt 5,我能读出来吗? |
|