From Friday, April 19th (11:00 PM CDT) through Saturday, April 20th (2:00 PM CDT), 2024, ni.com will undergo system upgrades that may result in temporary service interruption.

We appreciate your patience as we improve our online experience.

NI LabVIEW,CVI,数据采集等产品讨论区

取消
显示结果 
搜索替代 
您的意思是: 

DMA收发数据时的内存分配问题

问题描述:

RapidIO卡在收发数据时,均使用了DMA方式。发送方式为先malloc一段memory空间,然后把该段空间的首地址写入到DMA的基地址寄存器中,以后在发送数据时,就将数据复制到该memory空间中,然后启动DMA发送即可,接收也是相同的方法。

目前的问题是发送和接收均不正确,原因是:设备驱动使用DMA工作方式对所申请的memory空间有一定要求,首先需要memory空间在物理上连续,另外malloc出来的memory空间的地址因为是虚拟地址,所以需要先将该地址转换成物理地址,再把该物理地址写入到DMA的基地址寄存器中去,这样DMA才能正确的在正确的物理地址空间上去发送数据,接收也是同样的道理。所以我们如果malloc一段memory空间,但malloc不能保证这段memory空间在物理上连续,另外malloc在上层分配的memory空间也是虚拟地址空间,所以还需要将该虚拟地址先调用转换函数将其转换成物理地址之后才能使用,但目前VISA并没有找到提供分配连续空间的函数,也没有提供将虚拟地址转换成物理地址的函数,所以现在DMA收发存在问题。

 

 

 

 

其他平台对驱动中的DMA方式的支持:

Windows平台:

申请连续的memory空间有专门的函数,如下:

VirtualAddress = MmAllocateContiguousMemory(Len, PhyAddress);

上面的函数就申请到了在物理上连续的memory空间,但申请到的memory依然是虚拟地址,所以有另外一个专门的函数将该虚拟地址转换成物理地址,如下:

PhyAddress = MmGetPhysicalAddress(VirtualAddress);

然后就可以将转换后得到的物理地址PhyAddress写入到DMA相关的基地址中去,这样DMA就能正确的工作。

 

 

 

VxWorks平台:

vxworks平台因为用于嵌入式实时系统,所以vxworks和其他一般的操作系统有所不同,最大的不同就是vxworks一般使用的flat地址空间,就是不分用户空间和内核空间,所以程序和操作系统都是位于同一个地址空间范围内,没有换页的功能,所以应用程序能访问到整个内存地址,也可以破坏操作系统的代码,因为这样,所以在vxworks平台malloc一段memory空间的话,其必然在物理上连续,同时也就是物理地址,所以可以直接将该首地址写入到DMA的基地址中去,DMA也能正常工作。

 

 

综上,每个平台都有自己的DMA实现方式,但目前NI的VISA驱动模型却没有找到相关DMA支持方式???

 

 

0 项奖励
1 条消息(共 3 条)
6,303 次查看

目前的情况是在CVI环境,Windows系统下使用标准C的malloc得到的是windows分配的虚拟地址,导致在写数据时DMA将虚拟地址当作物理地址来使用,导致我们无法定位数据,我们不确定到时候移植到NI -RT上面时 malloc能否正常

0 项奖励
2 条消息(共 3 条)
6,289 次查看

请问您的DMA搞定了吗?vxworks下的。目前我在调试6221卡的数据采集卡的驱动,AO数据写入不到FIFO中,有三个地址空间,一个是内存地址,一个是基地址,还有一个是设备地址,这几个地址都怎么配置啊?还有就是fifo请求标志怎么用啊?

0 项奖励
3 条消息(共 3 条)
3,992 次查看