1
完善资料让更多小伙伴认识你,还能领取20积分哦, 立即完善>
概述
直接存储器访问(DMA)用于在外设与存储器之间以及存储器与存储器之间提供高速数据传输。可以在无需任何CPU操作的情况下通过DMA快速传输传输。这样节省的CPU资源可供其它操作使用。 DMA允许在后台执行数据传输,无需Cortex-MO处理器干预。在此操作过程中,主处理器可以执行其它任务,仅当整个数据块需要处理时,才会中断主处理器。这样即使传输大量数据也不会对系统性能造成太大影响。 DMA主要用于为不同的外设模块实现集中数据缓冲存储(通常在系统SRAM中)。与分布式解决方案(其中每个外设都需要实现自己的本地数据存储)相比,DMA解决方案在硅片成本和功耗方面的成本较低。 根据使用的产品型号的不同,有一个或两个DMA模块。 STM32F0XX DMA控制器总共有5个通道用于DMA1,每个通道都专门管理来自一个或多个外设的存储器访问请求。它具有一个仲裁器,用于处理不同的DMA请求的优先级。 本篇文章主要介绍如何使用STM32CubeMX实现ADC在DMA下快速采集,并且打印出去。 硬件准备 首先需要准备一个开发板,这里我准备的是NUCLEO-F030R8的开发板: 选择芯片型号 使用STM32CUBEMX选择芯片stm32f030r8,如下所示: 配置时钟源 HSE与LSE分别为外部高速时钟和低速时钟,在本文中使用内置的时钟源,故都选择Disable选项,如下所示: 配置时钟树 STM32F0的最高主频到48M,所以配置48即可: 串口配置 本次实验使用的串口1进行串口通信,波特率配置为115200。 ADC配置 STM32f030中,有一个ADC(模拟/数字转换器),每个 ADC 有 12 位、 10 位、 8 位和 6 位可选,每个ADC有16个外部通道、2个内部通道和一个VBAT 通道的信号。 本文将开ADC的IN0、IN1、IN4一共三个通道,来分别读取ADC,由于串口2和IN2,IN3复用,故不使用IN2、IN3。配置如下: 开启DMA: 打开中断: 生成工程设置 最后设置生成独立的初始化文件: 生成代码 配置keil 代码 在main.c中,添加头文件,若不添加会出现 identifier “FILE” is undefined报错。 /* USER CODE BEGIN Includes */ #include "stdio.h" /* USER CODE END Includes */ 函数声明和串口重定向: /* USER CODE BEGIN PFP */ #ifdef __GNUC__ #define PUTCHAR_PROTOTYPE int __io_putchar(int ch) #else #define PUTCHAR_PROTOTYPE int fputc(int ch, FILE *f) #endif /* __GNUC__ */ /* USER CODE END PFP */ /* USER CODE BEGIN 0 */ PUTCHAR_PROTOTYPE { HAL_UART_Transmit(&huart1 , (uint8_t *)&ch, 1, 0xFFFF); return ch; } /* USER CODE END 0 */ 变量定义: /* USER CODE BEGIN 1 */ uint32_t ADC_1, ADC_2,ADC_3; //各采样30次,故30*3为90 uint32_t ADC_Value[90]; uint8_t i; /* USER CODE END 1 */ 使用DMA传输: /* USER CODE BEGIN 2 */ HAL_ADC_Start_DMA(&hadc,(uint32_t*)&ADC_Value,90); //使用DMA传输 /* USER CODE END 2 */ 主循环: /* USER CODE BEGIN WHILE */ while (1) { //放个延迟,防止程序运行第一次读出数据有误 HAL_Delay(100); ADC_1=0; ADC_2=0; ADC_3=0; for(i=0,ADC_1=0,ADC_2=0;i<90;) { ADC_1+=ADC_Value[i++]; ADC_2+=ADC_Value[i++]; ADC_3+=ADC_Value[i++]; } printf("ADC数据如下n"); //除以30为求30次平均ADC值,乘以3.3为以3.3电压为基准,除以4096为ADC配置为12位 printf("ADC_IN0=%1.4frn",ADC_1/30*3.3f/4096); printf("ADC_IN1=%1.4frn",ADC_2/30*3.3f/4096); printf("ADC_IN2=%1.4frn",ADC_3/30*3.3f/4096); /* USER CODE END WHILE */ /* USER CODE BEGIN 3 */ HAL_Delay(900); } /* USER CODE END 3 */ 演示效果 设定adc1口接3.3V,adc2口接GND,adc口接1.5V,输出如下。 |
|
|
|
只有小组成员才能发言,加入小组>>
3324 浏览 9 评论
3003 浏览 16 评论
3498 浏览 1 评论
9077 浏览 16 评论
4094 浏览 18 评论
1198浏览 3评论
615浏览 2评论
const uint16_t Tab[10]={0}; const uint16_t *p; p = Tab;//报错是怎么回事?
603浏览 2评论
用NUC131单片机UART3作为打印口,但printf没有输出东西是什么原因?
2343浏览 2评论
NUC980DK61YC启动随机性出现Err-DDR是为什么?
1902浏览 2评论
小黑屋| 手机版| Archiver| 德赢Vwin官网 ( 湘ICP备2023018690号 )
GMT+8, 2024-12-31 03:10 , Processed in 1.201809 second(s), Total 80, Slave 61 queries .
Powered by 德赢Vwin官网 网
© 2015 bbs.elecfans.com
关注我们的微信
下载发烧友APP
德赢Vwin官网 观察
版权所有 © 湖南华秋数字科技有限公司
德赢Vwin官网 (电路图) 湘公网安备 43011202000918 号 电信与信息服务业务经营许可证:合字B2-20210191 工商网监 湘ICP备2023018690号