一、了解几个地址概念
1、虚拟地址:内核通常使用的地址是虚拟地址。我们调用kmalloc()、vmalloc()或者类似的接口返回的地址都是虚拟地址,保存在 void * 的变量中。
2、物理地址:对于嵌入式开发,物理地址是必须明白的,物理地址是指处理器芯片发出,来进行地址空间寻址的地址,它与处理器地址引脚上发出的电信号相对应。物理地址一般与CPU有关系,是给CPU指令使用的。
3、总线地址:总线地址主要是给设备使用的,是设备中的一些内存资源。如果要CPU的物理地址连接上设备上的总线地址就需要使用mmapi映射,这样就能将物理地址与总线地址链接在一起。
二、为什么有两种类型的DMA映射
1、为什么需要映射?
DMA操作是需要物理地址的,但是linux内核中使用的都是虚拟地址。如果想要用DMA对一段内存进行操作,可以用dma映射的api得到一段内存的物理地址和虚拟地址的映射。
2、为什么需要两种映射?
要从cache和内存中内容不一致说起。。。
cpu写内存有两种方式:
(1) write through:同步写到cache和内存。
(2) write back:CPU只写到cache中。cache的硬件使用LRU算法将cache里面的内容替换到内存。
DMA想要完成的是从内存到外设直接进行数据搬移。并且DMA不能访问CPU的cache。而CPU与内存、cache的关系如下:CPU在读内存的时候,如果cache命中则只是在cache去读,而不是从内存读