DMA 详解

目录

  • 一、简介
  • 二、STM32 中的 DMA
    • 1、DMA 框图
      • 1.1 传输方式
      • 1.2 仲裁器
      • 1.3 数据流
      • 1.4 指针递增模式
      • 1.5 存储器到存储器模式
      • 1.6 DMA 中断
    • 2、DMA 配置


一、简介

DMADirect Memory Access,直接存储器访问)顾名思义,就是绕开 CPU 直接访问 Memory。在计算机中,相比 CPU,Memory 和外设的速度是非常慢的,因而在 Memory 和 Memory (或者 Memory 和外设)之间搬运数据,非常浪费 CPU 的时间,造成 CPU 无法及时处理一些实时事件。因此,工程师们就设计出来一种专门用来搬运数据的器件——DMA 控制器(DMA ControllerDMAC),协助 CPU 进行数据搬运。


由上图可知,DMA 无需 CPU 直接控制传输,也没有中断处理方式那样保留现场和恢复现场的过程,通过硬件为 RAM 与 I/O 设备开辟一条直接传送数据的通路,能使 CPU 的效率大为提高。

  • 使用 DMA,对于高速设备而言,如硬盘,它不只是降低 CPU 的使用率,而且还能大大提高硬件设备的吞吐量。
  • 因为对于这种设备,CPU 直接供应数据的速度太低。 CPU 一个总线周期最多只能存取一次总线,而且对于 ARM 设备,它不能把内存中 A 地址的值直接搬到 B 地址。它只能先把 A 地址的值搬到一个寄存器,然后再从这个寄存器搬到 B 地址。也就是说,对于 ARM,要花费两个总线周期才能将 A 地址的值送到 B 地址。
  • 而 DMA 就不同了,一般系统中的 DMA 都有突发(Burst)传输的能力,在这种模式下,DMA 能一次传输几个甚至几十个字节的数据,所以使用 DMA 能使设备的吞吐能力大为增强。

使用 DMA 时我们必须要注意如下几点:

  • DMA 使用物理地址,程序是使用虚拟地址的,所以配置 DMA 时必须将虚拟地址转化成物理地址
    因为程序使用虚拟地址,而且一般使用 Cache 地址,所以 Cache 中的内容与其物理地址(内存)的内容不一定一致,所以在启动 DMA 传输前一定要将该地址的 Cache 刷新,即写入内存
  • OS 并不能保证每次分配到的内存空间在物理上是连续的。尤其是在系统使用过一段时间而又分配了一块比较大的内存时。所以每次都需要判断地址是不是连续的,如果不连续就需要把这段内存分成几段让 DMA 完成传输

二、STM32 中的 DMA

刚才简单介绍了一下,什么是 DMA,下面结合实例,看一下 DMA 是怎么在 STM32 中使用的。

1、DMA 框图

这是 STM32F4xx 设备的 DMA 框图:

每个通道都直接连接专用的硬件 DMA 请求,每个通道都同样支持软件触发。这些功能通过软件来配置:

  1. 在同一个 DMA 模块上,多个请求间的优先权可以通过软件编程设置(共有四级:很高、高、中等和低),优先权设置相等时由硬件决定(请求 0 优先于请求 1,依此类推);
  2. 独立数据源和目标数据区的传输宽度(字节、半字、全字),模拟打包和拆包的过程。源和目标地址必须按数据传输宽度对齐;
  3. 支持循环的缓冲器管理;
  4. 每个通道都有 3 个事件标志(DMA 半传输、DMA 传输完成和 DMA 传输出错),这 3 个事件标志逻辑或成为一个单独的中断请求;
  5. 存储器和存储器间的传输、外设和存储器、存储器和外设之间的传输;
  6. FLASH、SRAM、外设的 SRAM、APB1、APB2 和 AHB 外 设均可作为访问的源和目标;
  7. 可编程的数据传输数目:最大为 65535。

中间的 FIFO 区,每个数据流(总共 8 个数据流)都有一个独立的 FIFO,可以实现存储器接口到外设接口之间的数据长度非对齐传输

1.1 传输方式

DMA 的作用就是实现数据的直接传输,而去掉了传统数据传输需要 CPU 寄存器参与的环节,主要涉及三种情况的数据传输,但本质上是一样的,都是从内存的某一区域传输到内存的另一区域(外设的数据寄存器本质上就是内存的一个存储单元)。三种情况的数据传输如下:

  • 外设到内存)
  • 内存到外设
  • 内存到内存

DMA1 控制器 AHB 外设端口与 DMA2 控制器的情况不同,不连接到总线矩阵,因此,仅 DMA2 数据流能够执行内存到内存的传输

在发生一个事件后,外设向 DMA 控制器发送一个请求信号。DMA 控制器根据通道的优先权处理请求。当 DMA 控制器开始访问发出请求的外设时,DMA 控制器立即发送给它一个应答信号。当从 DMA 控制器得到应答信号时,外设立即释放它的请求。一旦外设释放了这个请求,DMA 控制器同时撤销应答信号。DMA 传输结束,如果有更多的请求时,外设可以启动下一个周期。

总之,每次 DMA 传送由 3 个操作组成:

  1. 从外设数据寄存器或者从当前外设/存储器地址寄存器指示的存储器地址取数据,第一次传输时的开始地址是 DMA_CPARxDMA_CMARx 寄存器指定的外设基地址或存储器单元;
  2. 存数据到外设数据寄存器或者当前外设/存储器地址寄存器指示的存储器地址,第一次传输时的开始地址是 DMA_CPARxDMA_CMARx 寄存器指定的外设基地址或存储器单元;
  3. 执行一次 DMA_CNDTRx 寄存器的递减操作,该寄存器包含未完成的操作数目。

DMA 有以下两种传输方式:

  1. DMA_Mode_Normal(正常模式):当一次 DMA 数据传输完后,停止 DMA 传送 ,也就是只传输一次
  2. DMA_Mode_Circular(循环传输模式):当传输结束时,硬件自动会将传输数据量寄存器进行重装,进行下一轮的数据传输。 也就是多次传输模式

1.2 仲裁器

仲裁器用于仲裁数据流 0~7 的请求优先级,保证数据有序传输。

仲裁器根据通道请求的优先级来启动外设/存储器的访问。优先权管理分2个阶段:

  1. 软件:每个通道的优先权可以在 DMA_CCRx 寄存器中设置,有 4 个等级:
    • 最高优先级
    • 高优先级
    • 中等优先级
    • 低优先级;
  2. 硬件:如果 2 个请求有相同的软件优先级,则较低编号的通道比较高编号的通道有较高的优先权。比如:如果软件优先级相同,通道 2 优先于通道 4。

注意: 在大容量产品和互联型产品中,DMA1 控制器拥有高于 DMA2 控制器的优先级。

1.3 数据流

仅限于 Cortex-M4 内核上有数据流

8 个 DMA 控制器数据流都能够提供源和目标之间的单向传输链路。每个数据流配置后都可以执行:

  • 常规类型事务:存储器到外设、外设到存储器或存储器到存储器的传输。
  • 双缓冲区类型事务:使用存储器的两个存储器指针的双缓冲区传输(当 DMA 正在进行自/至缓冲区的读/写操作时,应用程序可以进行至/自其它缓冲区的写/读操作)。要传输的数据量(多达 65535)可以编程,并与连接到外设 AHB 端口的外设(请求 DMA 传输)的源宽度相关。每个事务完成后,包含要传输的数据项总量的寄存器都会递减。

STM32F4xx 有两个 DMA:DMA1、DMA2,其请求映射如下表:

1.4 指针递增模式

根据 DMA_SxCR 寄存器中 PINCMINC 位的状态,外设和存储器指针在每次传输后可以自动向后递增或保持常量。当设置为增量模式时,下一个要传输的地址将是前一个地址加上增量值。

通过单个寄存器访问外设源或目标数据时,禁止递增模式十分有用。

如果使能了递增模式,则根据在 DMA_SxCR 寄存器 PSIZEMSIZE 位中编程的数据宽度,下一次传输的地址将是前一次传输的地址递增 1个数据宽度、2个数据宽度或 4个数据宽度。

1.5 存储器到存储器模式

DMA 通道的操作可以在没有外设请求的情况下进行,这种操作就是存储器到存储器模式。

当设置了 DMA_CCRx 寄存器中的 MEM2MEM 位之后,在软件设置了 DMA_CCRx 寄存器中的 EN 位启动 DMA 通道时,DMA 传输将马上开始。当 DMA_CNDTRx 寄存器变为 0 时,DMA 传输结束。存储器到存储器模式不能与循环模式同时使用。

这里要注意仅 DMA2 的外设接口可以访问存储器,所以仅 DMA2 控制器支持存储器到存储器的传输,DMA1 不支持。

1.6 DMA 中断

每个 DMA 通道都可以在 DMA 传输过半、传输完成和传输错误时产生中断。为应用的灵活性考虑,通过设置寄存器的不同位来打开这些中断。

2、DMA 配置

经过刚才的介绍可以知道,要配置 DMA,大致要实现如下内容:

  1. 源地址(Source Address):源地址表示数据传输的起始地址,即外设设备中数据缓冲区的地址。DMA 将从这个地址开始读取数据。
  2. 目标地址(Destination Address):目标地址表示数据传输的目的地址,即系统内存中的指定地址。DMA 将数据传输到这个地址。
  3. 数据长度(Data Length):数据长度表示需要传输的数据大小。它可以以字节、字或者其他单位进行表示。
  4. 控制信息(Control Information):控制信息包括传输模式、中断使能等参数。在传输过程中,DMA 根据这些参数来控制数据的传输行为。
  5. DMA 通道选择(DMA Channel Selection):在具有多个 DMA 通道的系统中,选择要使用的 DMA 通道。
  6. DMA 传输模式(DMA Transfer Mode):指定DMA传输的模式,如单次传输模式、循环传输模式等。
  7. DMA 中断使能(DMA Interrupt Enable):用于控制 DMA 传输完成时是否产生中断。

下面的代码实现了 USART1 发送接口的 DMA 配置:

DMA_InitTypeDef DMA_InitStructure;DMA_InitStructure.DMA_BufferSize           =   0;                               // 缓冲区大小   
DMA_InitStructure.DMA_Channel              =   DMA_Channel_4;                   // DMA通道4
DMA_InitStructure.DMA_DIR                  =   DMA_DIR_MemoryToPeripheral;      // 内存到外设
DMA_InitStructure.DMA_FIFOMode             =   DMA_FIFOMode_Disable;            // 禁用FIFO模式
DMA_InitStructure.DMA_FIFOThreshold        =   DMA_FIFOThreshold_1QuarterFull;  // FIFO阈值:1/4满
DMA_InitStructure.DMA_Mode                 =   DMA_Mode_Normal;                 // 正常模式
DMA_InitStructure.DMA_Memory0BaseAddr      =   0;                               // 内存源地址
DMA_InitStructure.DMA_MemoryDataSize       =   DMA_MemoryDataSize_Byte;         // 内存数据长度
DMA_InitStructure.DMA_MemoryBurst          =   DMA_MemoryBurst_Single;          // 单次传输
DMA_InitStructure.DMA_MemoryInc            =   DMA_MemoryInc_Enable;            // 内存地址自增
DMA_InitStructure.DMA_PeripheralBaseAddr   =   (uint32_t)&(USART1->DR);         // 外设地址
DMA_InitStructure.DMA_PeripheralDataSize   =   DMA_PeripheralDataSize_Byte;     // 外设数据长度
DMA_InitStructure.DMA_PeripheralBurst      =   DMA_PeripheralBurst_Single;      // 单次传输
DMA_InitStructure.DMA_PeripheralInc        =   DMA_PeripheralInc_Disable;       // 外设地址不自增
DMA_InitStructure.DMA_Priority             =   DMA_Priority_Medium;             // 中等优先级DMA_Init(DMA2_Stream7, &DMA_InitStructure);
DMA_ITConfig(DMA2_Stream7, DMA_IT_TC, ENABLE);
DMA_Cmd(DMA2_Stream7, DISABLE);

中断函数如下:

void DMA2_Stream7_IRQHandler(void)
{if (DMA_GetFlagStatus(DMA2_Stream7, DMA_FLAG_TCIF7) != RESET){DMA_ClearFlag(DMA2_Stream7, DMA_FLAG_TCIF7);...}
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1560023.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

美国1米DEM地形瓦片数据免费分享(4)-新泽西州

一、简要介绍 新泽西州(英语:State of New Jersey)位于美国中大西洋地区,其命名源自位于英吉利海峡中的泽西岛,昵称为“花园州”。新泽西州亦为美国东部的一个州,北接纽约州,东面大西洋,南向特拉华州,西临…

OpenEBS 实现 PV 动态持久化存储安装

什么是 OpenEBS OpenEBS 将 Kubernetes 工作节点可用的任何存储转换为本地或复制的 Kubernetes 持久卷。OpenEBS 可帮助应用程序和平台团队轻松部署需要快速、高持久性、可靠且可扩展的容器原生存储的Kubernetes 有状态工作负载。 安装OpenEBS 1.所有节点安装iSCSI启动器 yu…

生成式专题的第二节课--DCGAN

一、DCGAN基础概念 DCGAN(Deep Convolutional Generative Adversarial Network,即深度卷积生成对抗网络),于2016年提出,是一种深度学习模型,是生成对抗网络(GAN)的一种变体&#xf…

HarmonyOS NEXT应用元服务开发按钮标注场景

对于用户可点击等操作的任何按钮,如果不是文本类控件,则须通过给出标注信息,包括用户自定义的控件中的虚拟按钮区域,否则可能会导致屏幕朗读用户无法完成对应的功能。 此类控件在进行标注时,标注文本不要包含控件类型、…

干部管理系统:全面提升干部管理效能

数字化浪潮下,干部管理系统作为管理利器,日益凸显其核心价值。该系统全面实现干部信息的数据化,涵盖从基础档案到教育、工作、培训及考核等全方位细节,信息详尽且条理清晰。这不仅极大提升了干部信息查询与更新的效率,…

商标恶意维权形式及应对策略

在商业领域,商标恶意维权的现象时有出现,给正常的市场秩序和企业经营带来了不良影响。以下将介绍其常见形式及应对方法。 一、商标恶意维权的形式1、囤积商标后恶意诉讼。一些人或企业大量注册与知名品牌相似或具有一定通用性的商标,并非用于…

【STL】二叉搜索树模拟实现

BinarySearchTree模拟实现 1 什么是二叉搜索树2 二叉搜索树的插入2.1 插入的流程2.2 插入的代码 3 二叉搜索树的查找3.1 查找的流程3.2 查找的代码 4 二叉搜索树的中序遍历4.1 中序遍历流程4.2 中序遍历代码 5 二叉搜索树的删除5.1 没有孩子 | 有右孩子5.2 没有右孩子5.3 有两个…

广州自闭症寄宿学校有哪些?选择最适合孩子的学校

在广州这座繁华而充满人文关怀的城市里,有一群特殊的孩子,他们被称为“星星的孩子”——自闭症儿童。他们生活在自己的世界里,对外界的刺激反应迟钝或过度敏感,社交互动困难,语言表达受限。然而,在广州&…

医学图像处理入门:VS2019+DCMTK3.6.8编译及环境配置

1. 下载DCMTK的源文件包和支持库 首先下载dcmtk软件包,此处我们下载源码和支持库来进行自己编译。下载网址: https://dicom.offis.de/en/dcmtk/dcmtk-software-development/ 如图所示,选择合适的版本进行下载,此处采用VS2019进行…

5款人声分离免费软件分享,从入门到精通,伴奏提取分分钟拿捏!

人声分离通常是音乐制作、混音和卡拉OK中常用的重要技术之一。它的核心是将乐器伴奏从原始音轨中分离出来,使得用户可以单独处理或重混音频,创造出清晰干净的伴奏轨道。若缺乏强大的音频剪辑软件或专业人声分离工具,这一过程往往会比较困难。…

Xinstall品牌揭秘:如何成为App拉新的行业翘楚?

在移动互联网时代,App作为连接用户与服务的桥梁,其重要性不言而喻。然而,随着市场竞争的加剧,App拉新(即吸引新用户下载并使用App)的难度也在逐渐增大。传统的营销方式往往面临着成本高、效率低、用户留存差…

前端开发攻略---分块加载大数据

一、问题 解决当遇到较大的数据请求,当用户网络较差的时候,需要等很久很久才能拿到服务器的响应结果,如果这个响应结果需要再页面上展示的话,会导致页面长时间白屏的问题 二、实现原理 当发送一个请求时,需要等服务器把…

照片相册SDK解决方案,模板化包装,简化视频制作流程

专业的视频制作往往门槛较高,让许多用户望而却步,美摄科技推出了全新的照片相册SDK解决方案,旨在通过模板化包装方式,让用户轻松上传照片,快速生成一个充满创意和个性化的照片视频,让每个人都能成为自己生活…

Java的TCP通信

Java的TCP通信 TCP发送数据 Java中的TCP通信 Java对基于TCP协议的的网络提供了良好的封装,使用Socket对象来代表两端的通信端口,并通过Socket产生IO流来进行网络通信。Java为客户端提供了Socket类,为服务器端提供了ServerSocket类 构造方法…

使用 Go 语言与 Elasticsearch 实现高效搜索服务

使用 Go 语言与 Elasticsearch 实现高效搜索服务 什么是 Elasticsearch Elasticsearch 是一个基于 Apache Lucene 构建的分布式搜索引擎,能够存储、搜索和分析大量数据。它具有高可扩展性、快速的搜索速度,支持全文检索、多字段查询和近实时数据分析。…

mysql/doris 计算两个时间相差n天n时n分示范

mysql/doris 计算两个时间相差n天n时n分示范 两个时间:so.create_time,so.update_time CONCAT(FLOOR(DATEDIFF(HOUR ,so.create_time,so.update_time)/24),天,DATEDIFF(HOUR ,so.create_time,so.update_time)%24,时,DATEDIFF(MINUTE ,so.create_time,so…

自动猫砂盆“智商税”还是“真香”?2024自动猫砂盆保姆级干货

平时忙着上班,或者一遇到出差就要离家四五天,没办法给毛孩子的猫砂盆铲屎,导致粪便堆积太久。很多铲屎官也了解到有自动猫砂盆这种东西,但是生怕是智商税,总觉得忍忍手铲也可以,要知道,猫咪的便…

如何在阿里云一键部署FlowiseAI

什么是FlowiseAI FlowiseAI 是一个开源的低代码开发工具,专为开发者构建定制的语言学习模型(LLM)应用而设计。 通过其拖放式界面,用户可以轻松创建和管理AI驱动的交互式应用,如聊天机器人和数据分析工具。 它基于Lang…

网络安全-Morpheus

NVIDIA Morpheus 文章目录 前言一、简介1. NVIDIA Morpheus 是什么?二、优势1. 深入了解 NVIDIA Morpheus 的优势高管借助全面的数据可见性,实时检测威胁利用生成式 AI 提高效率提升性能,降低成本开发者轻松开发和部署功能丰富,灵活性强实时遥测三、用例Morpheus 用例四、A…

通过观测云 DataKit Extension 接入 AWS Lambda 最佳实践

前言 AWS Lambda 是一项计算服务,使用时无需预配置或管理服务器即可运行代码。AWS Lambda 只在需要时执行代码并自动缩放。借助 AWS Lambda,几乎可以为任何类型的应用程序或后端服务运行代码,而且无需执行任何管理。 Lambda Layer 是一个包…