前置介绍
TRGO 信号 (Trigger Output 触发输出)
是微控制器(如 STM32)中定时器模块产生的一种内部硬件信号。
核心作用是,在不占用 CPU 资源的情况下,精确地触发和同步其他外设的工作
例如启动 ADC(模数转换器)进行采样、更新 DAC(数模转换器)的输出,或者同步其他定时器的启动。
TRGO 典型应用场景 - 定时器周期性触发 ADC 采样
- 定时器 被配置为以固定频率(例如每秒1000次)计数。
- 每当定时器计数到一个特定值(例如周期结束),它就会自动产生一个 TRGO 信号。
- ADC 模块 被配置为监听这个 TRGO 信号。
- 一旦 ADC 检测到 TRGO 信号,就立即启动一次数据转换。
通过这种方式,系统可以实现非常稳定、精确且周期性的数据采集,这对于电机控制、音频处理、电源管理等对时序要求极高的应用至关重要。
TIM 触发 ADC 采集内部温度

项目配置
USART1
配置 Mode 为 Asynchronous
TIM3

- 勾选 Internal Clock
- 设置 Prescaler 为 7200 - 1 , 最终每秒计数一万次
- 设置 Counter Period 为 5000 - 1, 即每半秒触发一次 TRGO 信号输出
- 设置 Trigger Event Selection 为 Update Event.
ADC1

- 勾选 Temperature Sensor Channel 温度传感器通道
- Extenal Trigger Conversion Source (外部触发转换源) 设置为 Timer 3 Trigger Out event. (定时器 3 触发外部事件)
- Sampling Time (采样时间), 设置为 55.5 Cycles (采样时间长, 数据更稳定准确)
代码部分
因为用到了串口, 记得勾选 Use MicroLIB
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include <stdio.h> // 使用 printf 函数
#include <string.h> // 使用 strncmp
/* USER CODE END Includes */
/* Private typedef -----------------------------------------------------------*/
/* USER CODE BEGIN PTD */
/* USER CODE END PTD */
/* Private define ------------------------------------------------------------*/
/* USER CODE BEGIN PD */
/* USER CODE END PD */
/* Private macro -------------------------------------------------------------*/
/* USER CODE BEGIN PM */
/* USER CODE END PM */
/* Private variables ---------------------------------------------------------*/
/* USER CODE BEGIN PV */
uint32_t adc_val = 0; // 存储原始值
float voltage = 0.0f; // 存储电压值
float temperature = 0.0f; // 存储温度
/* USER CODE END PV */
/* Private function prototypes -----------------------------------------------*/
void SystemClock_Config(void);
/* USER CODE BEGIN PFP */
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
/* USER CODE BEGIN 0 */
/* USER CODE END 0 */
/**
* @brief The application entry point.
* @retval int
*/
int main(void)
{
/* USER CODE BEGIN 1 */
/* USER CODE END 1 */
/* MCU Configuration--------------------------------------------------------*/
/* Reset of all peripherals, Initializes the Flash interface and the Systick. */
HAL_Init();
/* USER CODE BEGIN Init */
/* USER CODE END Init */
/* Configure the system clock */
SystemClock_Config();
/* USER CODE BEGIN SysInit */
/* USER CODE END SysInit */
/* Initialize all configured peripherals */
MX_GPIO_Init();
MX_TIM3_Init();
MX_ADC1_Init();
MX_USART1_UART_Init();
/* USER CODE BEGIN 2 */
// 启动 ADC1 校准
HAL_ADCEx_Calibration_Start(&hadc1);
// 启动 ADC1 转换
HAL_ADC_Start(&hadc1);
// 启动 TIM3 基础定时
HAL_TIM_Base_Start(&htim3);
// 等待芯片传感器稳定
HAL_Delay(3000);
/* USER CODE END 2 */
/* Infinite loop */
/* USER CODE BEGIN WHILE */
while (1)
{
if (HAL_ADC_PollForConversion(&hadc1, HAL_MAX_DELAY) == HAL_OK) // 等待 ADC 转换完成
{
adc_val = HAL_ADC_GetValue(&hadc1); // 读取原始值
voltage = (float)adc_val / 4095 * 3.3f; // 将原始值转换为电压值 (单位 V)
temperature = (1.43f - voltage) / 0.0043f + 25; // 将电压转换为芯片内部温度 (单位 C)
printf("当前芯片内部温度: %.3f C \r\n", temperature);
// 这里不需要去写延迟, 因为这里是通过 HAL_ADC_PollForConversion 等待定时器每 500ms 触发一次转换,
// 如果没有触发完成, 是不会通过的.
}
/* USER CODE END WHILE */
/* USER CODE BEGIN 3 */
}
/* USER CODE BEGIN 4 */
/**
* @brief 重定向 printf 的输出到串口
* @param ch: 要发送的字符
* @param f: 文件指针 (标准库要求的参数, 一般不使用)
* @retval 返回发送的字符
*/
int fputc(int ch, FILE *f)
{
HAL_UART_Transmit(&huart1, (uint8_t *)&ch, 1, HAL_MAX_DELAY);
return ch;
}
/* USER CODE END 4 */
程序现象

程序运行后, 会先有一段时间的空白期 (进行校准和等待温度传感器稳定)
空白期结束之后, TIM3 每隔 500ms 触发一次 TRGO 信号, 触发 ADC1 采集芯片温度
然后在主程序中等待 ADC1 转换完成后, 将 ADC 原始值转换为电压值, 再转换为温度, 然后通过串口进行输出.
可以将手指放在芯片上, 可以看到温度会有小的变动.