STM32 零基础系列第 6 篇:完成模拟采集、传感器通信和高效率数据搬运。
第 9 章:ADC 模数转换
章节介绍
ADC 把连续电压转换成数字量。它像一把刻度尺:把 0~3.3V 分成 4096 个格子,读取电压落在哪一格。
专业名词
- ADC:Analog-to-Digital Converter,模数转换器。
- 分辨率:例如 12 位表示 0~4095。
- 采样时间:ADC 观察输入电压的时间。
- 参考电压 Vref:数字满量程对应的电压。
- 触发源:软件、定时器或外部事件。
- 校准:减少偏移和增益误差。
HAL 读取示例
c
uint32_t adc_value;
float voltage;
HAL_ADC_Start(&hadc1);
HAL_ADC_PollForConversion(&hadc1, 10);
adc_value = HAL_ADC_GetValue(&hadc1);
HAL_ADC_Stop(&hadc1);
voltage = 3.3f * adc_value / 4095.0f;
不要把 ADC 数值直接当成物理量。光照、温度、电流等都需要结合传感器电路和标定公式转换。
本章掌握标准
- 能根据分辨率和参考电压换算输入电压。
- 能配置单次转换、连续转换和多通道扫描。
- 能解释采样时间、噪声、平均滤波和校准。
未来使用场景
电池电压、温度、光照、电流、电位器、麦克风和模拟传感器。
第 10 章:I2C 与 SPI
I2C
I2C 像一条公交线路:SCL 是统一时钟,SDA 是共享数据线,每个设备有地址。它只需要两根线,适合多个低速传感器。
专业名词:
- 主机/从机:谁产生时钟,谁就是主机。
- 设备地址:总线上区分不同设备的编号。
- ACK:应答信号。
- 重复起始:不释放总线,直接切换读写方向。
- 上拉电阻:I2C 开漏总线恢复高电平所必需。
c
uint8_t data;
HAL_I2C_Mem_Read(&hi2c1,
0x48 << 1,
0x00,
I2C_MEMADD_SIZE_8BIT,
&data,
1,
100);
STM32 HAL 的设备地址通常需要左移一位,因为最低位用于读写方向。
SPI
SPI 像一条专用高速传送带:
text
SCK 时钟
MOSI 主机发送
MISO 主机接收
NSS/CS 片选
SPI 没有统一的设备地址,每个设备通常单独占用一个 CS 引脚,速度比 I2C 高。
c
uint8_t tx = 0x9F;
uint8_t rx[3];
HAL_GPIO_WritePin(FLASH_CS_GPIO_Port, FLASH_CS_Pin, GPIO_PIN_RESET);
HAL_SPI_TransmitReceive(&hspi1, &tx, rx, 1, 100);
HAL_SPI_Receive(&hspi1, rx, 3, 100);
HAL_GPIO_WritePin(FLASH_CS_GPIO_Port, FLASH_CS_Pin, GPIO_PIN_SET);
本章掌握标准
- 能区分 I2C 的地址和 SPI 的片选。
- 能使用逻辑分析仪观察 SCL/SDA 或 SCK/MOSI/MISO。
- 能处理 ACK、超时、总线忙和设备无响应。
未来使用场景
OLED、EEPROM、RTC、IMU、温度传感器、Flash、屏幕和无线芯片。
第 11 章:DMA
章节介绍
DMA 是 Direct Memory Access,直接存储器访问。它像仓库搬运机器人:CPU 只下达"把这批数据从 UART 搬到 RAM"的命令,搬运期间 CPU 可以做其他工作。
适合 DMA 的数据
- UART 连续接收。
- ADC 多通道采样。
- SPI 屏幕刷新。
- 定时器波形输出。
UART DMA 示例
c
uint8_t rx_buffer[128];
HAL_UART_Receive_DMA(&huart2, rx_buffer, sizeof(rx_buffer));
DMA 完成或半传输时可以产生回调。实际协议应结合空闲线检测、环形缓冲区和帧解析。
本章掌握标准
- 能解释 DMA 源地址、目标地址、数据宽度和传输长度。
- 能区分普通模式、循环模式和双缓冲。
- 能处理 DMA 缓冲区与 CPU 同时访问造成的数据一致性问题。
未来使用场景
高采样率数据采集、音频、摄像头、网络数据、串口高吞吐和屏幕刷新。