RT-Thread之STM32使用定时器实现输出比较

前言

基于RT-Thread的STM32开发,配置使用定时器实现输出比较。

例如设定一定的比较值,当定时器值等于设定比较值时会触发比较中断,在中断里打印输出,查看时间戳,计算验证是否和配置的定时器输出比较中断周期一致。

一、新建工程,我是用的是STM32F407ZGT6

二、工程配置及代码编写

1、打开CubeMX

2、时钟配置使用外部高速晶振

3、配置下载口

4、配置时钟树,频率直接拉满

5、打开串口一,调试打印用

6、打开定时器三通道二输出比较。

7、代码生成

8、编译一下,出现如下报错

9、右击工程,修改芯片支持包版本

10、再编译,无报错无警告

11、打开定时器设备驱动程序

12、board.h中打开定时器三注释

13、使能定时器模块

14、找到CubeMX自动生成的定时器三初始化函数

15、进入HAL_TIM_MspPostInit(&htim3)这个函数内部

16、在HAL_TIM_MspPostInit函数内部这个位置,补充上定时器三时钟初始化

17、在这个位置补充开启定时器三中断

18、在定时器三初始化的最后这个位置开启定时器三输出比较中断

19、回到主函数这,在函数开始进行定时器三初始化,编译一下发现报错

20、找到定时器三初始化代码,把这个static关键字去掉

21、函数声明这里的static也去掉

22、再编译,就能通过了

23、找到CubeMX生成的时钟配置函数,将其剪切

24、粘贴到drv_clk.c文件里

25、在时钟初始化这里,使用CubeMX生成的时钟配置函数,将原来的替换掉

26、再打开CubeMX,得知TIM3挂载在APB1总线上,时钟频率为84MHZ

27、回到定时器三初始化代码,时钟分频填83,则计算一下,分频后的时钟为1MHZ

28、比较值为0,自动重装载值为65535,则计算一下,得知0.065535S就会进一次中断

29、主函数中写入如下代码进行测试,在比较中断中进行打印输出,然后待会在串口助手查看打印输出的时间戳。

c 复制代码
/*
 * Copyright (c) 2006-2024, RT-Thread Development Team
 *
 * SPDX-License-Identifier: Apache-2.0
 *
 * Change Logs:
 * Date           Author       Notes
 * 2024-10-19     RT-Thread    first version
 */

#include <rtthread.h>
#include <rtdevice.h>
#include "board.h"

extern TIM_HandleTypeDef htim3;

#define SYS_LED             GET_PIN(A, 15)



static void SystemLedRun(void)
{
    static uint8_t l_ucmode = 0;
    if (l_ucmode == 0)
    {
        rt_pin_write(SYS_LED, PIN_HIGH);
        l_ucmode = 1;
    }
    else if (l_ucmode == 1)
    {
        rt_pin_write(SYS_LED, PIN_LOW);
        l_ucmode = 0;
    }
}




//输出比较中断函数
void HAL_TIM_OC_DelayElapsedCallback(TIM_HandleTypeDef *htim)
{

    if(htim->Instance == htim3.Instance)
    {
        switch(htim->Channel)
        {

            case HAL_TIM_ACTIVE_CHANNEL_2:
                rt_kprintf("TIM3_OC_TRICK!!!\r\n");
                break;

            default:
                break;
        }
    }

}


int main(void)
{
    MX_TIM3_Init();

    rt_pin_mode(SYS_LED, PIN_MODE_OUTPUT);
    rt_pin_write(SYS_LED, PIN_HIGH);

    while (1)
    {
        SystemLedRun();
        rt_thread_mdelay(500);
    }

    return RT_EOK;
}

30、每次进中断的间隔是0.065535s,则我们看打印输出时间戳的最后这两位,每两次输出的间隔基本都是65,拿上一次最后两位加65就得到下一次的最后两位,说明定时器输出比较功能配置成功,输出正常。

31、再来修改一下分频系数再验证一下,这次的分频系数为8300,计算一下则得到每两次中断的时间间隔为6.5535s

32、观察一下时间戳,发现也是对的,每两次打印的时间相差6.5535s

33、但其实仔细一计算发现是存在一点小误差的,这是因为串口打印输出也是需要一点时间的,故产生了一点影响,因此在实际使用中,不要在定时器中断内部进行串口打印输出,否则可能会存在精度上的影响,如果只是测试与验证,那问题不大。

相关推荐
启雀AI1 小时前
培训平台移动端离线学习方案设计与实现:视频缓存、断点续传与进度同步的工程实践
android·学习·缓存·音视频·企业lms
神经智研社1 小时前
ROS2-第十七章:网络通信,win11系统 通过镜像配置 打通 WSL 下的ros2与 同局域网(同IP段)的里其它设备上的ros2通信
机器人·机器人环境搭建·win11 ros2 开发环境
双星系统3 小时前
双臂机器人迎来广阔应用风口!既是工业柔性主力,也是人形机器人优质上肢配件
人工智能·机器人
Fa_Mian_Tuan3 小时前
图论基础|邻接矩阵超详细讲解(含无向/有向/带权图+完整可运行C语言代码)
c语言·数据结构·笔记·算法·图论
Bruce_Liuxiaowei3 小时前
从零到可运行:基于 Vue3 + FastAPI + DeepSeek-V3 的 AI 英语单词学习系统全栈实战
人工智能·python·学习·fastapi·全栈·智能体
恒锐丰-罗生3 小时前
SS8103 芯片解析:45V 同步整流降压半桥恒流驱动控制器 大功率光源国产优选 告别低灰闪烁!
驱动开发·嵌入式硬件·硬件工程
FakeOccupational4 小时前
【电路笔记 STM32】stm32f103 实现HAL_UART_Transmit_DMA + 普通模式/连续模式的 UART DMA 收发
笔记·stm32·嵌入式硬件
bkspiderx4 小时前
从零开始:VS Code搭建C/C++开发环境全指南(Windows/macOS/Linux)
c语言·c++·windows·vs code·c/c++开发环境
雪的季节4 小时前
OPENCV学习(补充1)
人工智能·opencv·学习
wuyk5554 小时前
第 6 章 FOC 完整系统整合:从算法到真机跑起来
c语言·开发语言·stm32·单片机·嵌入式硬件