使用STM32的ADC以及DMA获取红外传感器的数据,并通过串口打印(本文硬件环境基于板载STM32F303RE的Nucleo开发板,程序使用HAL库进行开发)
原理
ADC
关于ADC,摘自Wikipedia的定义如下
模拟数字转换器(英语:Analog-to-digital converter, ADC, A/D 或 A to D)是用于将模拟形式的连续信号转换为数字形式的离散信号的一类设备。一个模拟数字转换器可以提供信号用于测量。与之相对的设备成为数字模拟转换器。
典型的模拟数字转换器将模拟信号转换为表示一定比例电压值的数字信号。然而,有一些模拟数字转换器并非纯的电子设备,例如旋转编码器,也可以被视为模拟数字转换器。
对于本文所使用的STM32F303RE芯片,其内置的ADC拥有将模拟信号最高转化为16位数据的能力,不同的STM32芯片其内置的ADC可能会存在差异,具体的参数请参见该芯片所对应的数据手册。
DMA
对于DMA,数据手册对其介绍如下:
直接存储器存取 (DMA) 用来提供在外设和存储器之间或者存储器和存储器之间的高速数据传 输。无须 CPU 干预,数据都可以通过 DMA 进行快速地传输。这就为其他操作保留了 CPU 资源。
在Wikipedia中如下:
直接内存访问(Direct Memory Access,DMA)是计算机科学中的一种内存访问技术。它允许某些电脑内部的硬件子系统(电脑外设),可以独立地直接读写系统内存,而不需中央处理器(CPU)介入处理 。在同等程度的处理器负担下,DMA是一种快速的数据传送方式。很多硬件的系统会使用DMA,包含硬盘控制器、绘图显卡、网卡和声卡。
对于本文所使用的STM32F303RE芯片,其内置的DMA有着多个通道可供配置,每个通道都直接连接专用的硬件 DMA 请求,每个通道也同样支持软件触发。同样的,对于不同的芯片,具体的参数请参见该芯片所对应的数据手册。
红外传感器
本文使用的红外传感器为红外测距传感器,该传感器由一个红外发射管和一个红外接收管组成。红外发射管向前方发射红外线,遇到障碍物时将发生反射,由红外接收管接收红外线,红外线越强其电流越大、电压越小。
环境
硬件环境
- 板载STM32F303RE的Nucleo开发板
- PC13引脚接红外距离传感器的VCC
- PC2引脚接红外距离传感器的OUT
软件环境
- 使用STM32CubeMX完成外设的配置以及工程代码的初始化
- 开发环境为VScode + PlatformIO
- 使用STM32Cube框架开发
前置知识
ADC与DMA
- ADC参考来源>>STM32—ADC详解<<
- DMA参考来源>>STM32DMA实验<<
在本文中,将通过ADC来将红外距离传感器的OUT引脚输出的模拟信号,即电压转换成占用12位的数值(0~4096),然后通过DMA将该值保存至一个变量。
输出重定向
通过输出重定向C语言标准库的printf函数将数据通过串口打印在PC上,对于本文所使用的arm-gcc编译器,需要重写_write()
函数如下:
int _write(int fd, char *ptr, int len)
{
HAL_UART_Transmit(&huart2, (uint8_t *)ptr, len, HAL_MAX_DELAY);
return len;
}
其中HAL_UART_Transmit
函数的参数根据硬件的连接而异,对于Nucleo开发板应该配置USART2为数据打印的端口。
-u_printf_float
来启用编译器对浮点数的支持
代码部分
使能红外传感器
直接将该引脚电平拉高
/* USER CODE BEGIN 2 */
HAL_GPIO_WritePin(RS_VCC_GPIO_Port,RS_VCC_Pin,GPIO_PIN_SET);
/* USER CODE END 2 */
读取并打印传感器的值
uint32_t dat = 0;
HAL_ADC_Start_DMA(&hadc1,&dat,1);
HAL_ADC_Stop_DMA(&hadc1);
printf("ADC : %lu\n", dat);
HAL_Delay(1000);
此时在串口监视器上,将可以观察到字符串输出:
将白纸正对红外传感器,并逐渐增大它们之间的距离: