当前位置: 首页 > news >正文

嵌入式学习笔记——SysTick(系统滴答)

系统滴答

  • 前言
  • SysTick概述
    • SysTick是个啥
    • SysTick结构框图
      • 1. 时钟选择
      • 2.计数器部分
      • 3.中断部分
      • 工作一个计数周期(从重装载值减到0)的最大延时时间
      • 工作流程
    • SysTick寄存器
      • 1.控制和状态寄存器SysTick->CTRL
      • 2.重装载值寄存器SysTick->LOAD
      • 3.当前值寄存器SysTick->VAL
      • 4.校准值寄存器
    • 配置流程
  • 代码
  • 总结

前言

上一篇中,介绍了关于STM32F407的时钟系统,在了解了系统的时钟后,最重要的内容就是搞定定时器的操作,本文从最基本的定时器,也是内核里面自带的一个定时器——SysTick(系统滴答)来进行介绍。旨在搞清楚什么是系统滴答,系统滴答有什么用,系统滴答怎么用。

SysTick概述

SysTick这个词其实之前出现过,在介绍中断的时候,就是下面这个图,SysTick就出现了,看他的位置,在图中阴影部分内,也就是说,SysTick是内核里面的属于NVIC的一部分;不是类似USART、GPIO的片上外设,而是一个内核内的外设;看图中有个箭头指向了NVIC,说明它是可以像前面用过的EXTI、USART来产生中断的。
在这里插入图片描述

SysTick是个啥

关于是个啥这种问题,实在是不好表述,咱还是让官方来作答吧。
在这里插入图片描述
看了上面的描述,会有一个大致的概念,首先,它是一个可编程的系统定时器,其次,它被用来做延时和计时的操作,然后还可以触发中断。有一点需要纠正,上面说它是一个32位的自动递减计数器,这点有误,在STM32F407中,它是一个24位的自动递减计数器。
这里一直在说系统滴答是个定时器,那么定时器是个啥,直白点说,定时器就是一个按照时间规律递增或者递减的计数器,在STM32中这个时间规律就是时钟,例如,我们假设系统滴答的时钟是168MHZ;那么系统滴答这个定时器就会在一秒钟内,从0自增到168 000 000;同样的换个方向来理解,就是说计数器计满168000 000就是1s钟的时间。至于递减和递增,递减就是说计数器的初始有我们给定,然后计数器就从这个值开始做自减;而自增则是,我们给定值,然后计数器从0开始自增,一直增加到这个数。

好了,在有了一个大致的映像后,下面就来具体分析它的结构和功能。

SysTick结构框图

由于系统滴答是内部定时器,所以在ST公司的中文参考手册是找不到的,只有在ARM的权威指南中才可以找到相关描述,具体位置在M3和M4权威指南的第九章第五节。
在这里插入图片描述
下拉就可以看见系统框图:
还是按照老套路,把能够省略部分先噶了,这里可以很明显的看见最下面红框与上面的东西都没有联系,所以它是可以噶了的,他的作用就是校准SysTick的,一般来说,SysTick就是使用的系统时钟,如果这个不准了,那么多半这个单片机也命不久矣,所以这个东西可以直接不看。
在这里插入图片描述
去掉不需要看的,接下来就分模块一个部分一个部分的来介绍。

1. 时钟选择

如下图,左侧的红框代表的就是系统滴答的时钟输入选部分;绿色框内是一个二选一数据选择器,两个输入分别是处理器时钟以及经过上升沿检测的参考时钟;执行选择的是下方的“控制和状态寄存器的第2位”,具体的选择流程在寄存器部分会详细介绍。然后时钟就给到了计数器。
在这里插入图片描述
既然有两个输入的时钟,那么这两个时钟具体是指什么呢?
其一是处理器时钟,也就是我们说的主频,对于STM32F407来说对应168MHZ;那么另外一个参考时钟是什么呢?其实这个时钟在昨天的时钟树介绍中也出现了。如下图所示,橙色框中的到Cortex系统定时器的就是这里的参考时钟,可以发现,它经过了一个8分频的分频器,也就是说这个时钟的频率应该是168/8=21Mhz。

在这里插入图片描述

2.计数器部分

计数器简化后如下图所示,这是一个计数器的最基本结构,首先有三部分输入:
1.时钟基准:这个时钟直接决定了这个计数器多少时间执行一次计数;
2.重装载值:上方的重装载值直接决定了计数器的最大计数值;
3.控制部分:控制部分直接决定了计数器什么时刻开始计数,什么时候关闭计数,这里的第0位就是用来控制计数器是否计数的。
在这里插入图片描述
然后是输出部分,输出只有一个方向,就是4的位置,注意描述:当计数器从1减到0的时候会触发,而且这个触发是指向了“控制和状态寄存器”的,这就说明,当计数完成的时候,在“控制和状态寄存器”中会有对应的位,让我么来判断计时是否完成。
最后,最主要的部分,就是橙色框的24位向下计数器,它的作用就是隔一段时间将数值减一。当然,这里的明子就叫向下计数器,那么肯定还有对应的向上计数器,以及中心对齐的计数器,这个在后面基本通用和高级定时器中会碰到,遇到了再说。

3.中断部分

然后这个图还剩最后一部分,就是有关中断的了,这里有一个与门,与门的输入一个来自计数器技术完成后的标志,另一个来自“控制与状态寄存器”的第1位,也就是中断使能,说明在需要使用到中断的过程中,需要使能这个位才能开启中断。

在这里插入图片描述

工作一个计数周期(从重装载值减到0)的最大延时时间

弄清楚了上面的结构后,就可以计算出两个频率下,计数器工作一个周期,最长所需要花费的时间。
最大的重装载值:2^24=16777216
系统滴答具备两个时钟源:
内核时钟:主频提供时钟 168MHZ
最大的延时时长:1S16777216/168 000 000=0.09986S
0.09986s---->99.8ms
外部时钟:由AHB线提供 21MHZ
最大的延时时长:1S
16777216/21 000 000=0.7989 S
0.7989s-----》798.9ms

工作流程

根据框图的分析,可以大致总结出系统滴答的初始化流程:

{①选择时钟;②根据自己所需时间计算出重装载值;③使能计数器;④判断对应的标志位是否到了,到了说明计时到了,没到说明计时还没到
}

SysTick寄存器

其实根据框图,寄存器也已经猜的七七八八了,还是具体的看一眼,关于系统滴答一共有四个寄存器。
在这里插入图片描述

1.控制和状态寄存器SysTick->CTRL

在这里插入图片描述
写法:SysTick->CTRL
功能:对系统滴答定时器做控制,以及读取对应的状态
第0位:ENALEB
置1:使能计数器 一直重复工作
置0:失能计数器

第1位:中断使能位 计数标志一定会置1/中断标志
置1:使能中断
置0:失能中断

第2位:选择时钟源 默认1
置1:选择内核时钟 168MHZ
置0:外部参考时钟 21MHZ

第16位:标志位 只读
为1:计数器到0则返回1
为0:读取时清零
读取时的具体写法:

while(! (SysTick->CTRL & (1<<16)) );

2.重装载值寄存器SysTick->LOAD

在这里插入图片描述
写法: SysTick->LOAD
功能:提供计数器的最大值
用法:直接写入需要写入的最大计数值
不能超过最大的重装载值范围(0-1667216)
SysTick->LOAD=arr-1;
这个值具体写入多少,要结合需求,计算出大小

3.当前值寄存器SysTick->VAL

写法:SysTick->VAL
功能:存储计数器的当前值
读取这个寄存器:能够获取到计数器的当前值
写入这个寄存器:任意值都能清除计数标志位

4.校准值寄存器

在分析框图的时候提到过,这个一般不用。

配置流程

这里的配置流程分为两类:
其一是实现一个延时功能,延时功能只需要定时器工作一个周期,也就是从重装载值减到一的一个过程,执行一次后需要关闭定时器,不让他还会不停的从重装载值减到0然后又从重装载值减到0无限循环。
伪代码:

实现系统的us延时(参数)
{//选择时钟 建议选择外部时钟//写入重装载值  21*参数//当前值清零//打开计数器//等待标志位置1//关闭计数器
}

其二就是利用中断,一定时间进一次中断,以此来实现一个时间片轮询的操作方式。这时候,就需要定时器一直计数了,所以不能计数完成后就关闭计数器了。伪代码如下:

系统滴答的初始化代码
{//选择系统滴答的时钟//配置系统抵达的重装载值//当前值清零//打开中断使能//NVIC控制器//开启定时器   
}
中断服务函数
{判断标志;清楚标志;执行操作。
}

代码

#include "SysTick.h"
u16 SysTick_us;
u16 SysTick_ms;/*******************************
函数名:SysTick_Init
函数功能:初始化系统滴答,选择外部时钟
函数形参:u32 sysclk 系统时钟168(MHZ)
函数返回值:void
备注:开启1ms中断********************************/
void SysTick_Init(u32 sysclk) //168MHZ
{u32 pri;//存储优先级合成函数返回的优先级SysTick->CTRL &=~(1<<2); //选择外部时钟,必须清零默认是1内核时钟SysTick_us=sysclk/8;           //21     1us//外部时钟8分频SysTick_ms=SysTick_us*1000;            //21 000  1msSysTick->LOAD = SysTick_ms-1;//重装载值21000-1SysTick->VAL=0;    //清空计数器,清标志位SysTick->CTRL |=1<<1;   //使能中断 /*-----------------------配置NVIC---------------------------------------------*/	pri=NVIC_EncodePriority(7-2,1,2);NVIC_SetPriority(SysTick_IRQn,pri);NVIC_EnableIRQ(SysTick_IRQn);SysTick->CTRL |=1<<0;   //使能计数器  
}/*******************************
函数名:SysTick_Delay_us
函数功能:系统滴答实现us延时
函数形参:u32 nus
函数返回值:void
备注:
//因为LOAD为24位,所以最大重装载值16,777,216
最长时间:形参最大值,798,915us********************************/
void SysTick_Delay_us(u32 nus)//1us
{SysTick->LOAD =nus*SysTick_us;//传进来的参数*21  nus 传多少就是多少微秒SysTick->VAL=0;    //清空计数器,清标志位SysTick->CTRL |=1<<0;   //使能  while(!(SysTick->CTRL & 1<<16));//等待计数完成SysTick->CTRL &=~(1<<0);  //关闭计数器SysTick->VAL=0;     //清空计数器,清标志位
}/*******************************
函数名:SysTick_Delay_ms
函数功能:系统滴答实现ms延时
函数形参:u32 nms
函数返回值:void
备注:
形参最大值798ms
********************************/
void SysTick_Delay_ms(u32 nms)
{SysTick->LOAD =nms*SysTick_ms;//传进来的参数*21  nms 传多少就是多少毫秒SysTick->VAL=0;    //清空计数器,清标志位SysTick->CTRL |=1<<0;   //使能  while(!(SysTick->CTRL & 1<<16));//等待标志位到SysTick->CTRL &=~(1<<0);  //关闭计数器SysTick->VAL=0;     //清空计数器,清标志位
}//.h
#ifndef _SYSTICK_H
#define _SYSTICK_H
#include "stm32f4xx.h"
#include "Nvic.h"
void SysTick_Init(u32 sysclk); //168MHZ
void SysTick_Delay_us(u32 nus);//1us
void SysTick_Delay_ms(u32 nms);//1ms
#endif//中断服务函数:/*******************************
函数名:SysTick_Handler
函数功能:系统滴答的中断服务函数函数
函数形参:无
函数返回值:void
备注:1ms进一次中断
********************************/
void SysTick_Handler(void)
{static u8 i=100;while(SysTick->CTRL &(1<<16))//检测中断标志,同时也是清除标志位mtime--;Led_cnt++;_TIMER_1MS++;i--;if(i==0){i = 100;_TIMER_100MS ++;}
}

总结

系统滴答就是一个系统内的定时器,其主要作用就是提供精确延时以及计时的功能,可以借此实现时间片轮询的代码框架。

相关文章:

嵌入式学习笔记——SysTick(系统滴答)

系统滴答前言SysTick概述SysTick是个啥SysTick结构框图1. 时钟选择2.计数器部分3.中断部分工作一个计数周期&#xff08;从重装载值减到0&#xff09;的最大延时时间工作流程SysTick寄存器1.控制和状态寄存器SysTick->CTRL2.重装载值寄存器SysTick->LOAD3.当前值寄存器Sy…...

Linux实操之服务管理

文章目录一、服务(service)管理介绍:service管理指令查看服务名服务的运行级别(runlevel):CentOS7后运行级别说明chkconfig指令介绍一、服务(service)管理介绍: 服务(service)本质就是进程&#xff0c;但是是运行在后台的&#xff0c;通常都会监听某个端口&#xff0c;等待其它…...

基于Java+SpringBoot+vue的毕业生信息招聘平台设计和实现【源码+论文+演示视频+包运行成功】

博主介绍&#xff1a;专注于Java技术领域和毕业项目实战 &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精彩专栏推荐订阅&#x1f447;&#x1f3fb; 不然下次找不到哟 Java项目精品实战案例&#xff08;200套&#xff09; 目录 一、效果演示 二、…...

智能生活垃圾检测与分类系统(UI界面+YOLOv5+训练数据集)

摘要&#xff1a;智能生活垃圾检测与分类系统用于日常生活垃圾的智能监测与分类&#xff0c;通过图片、视频和摄像头识别生活垃圾&#xff0c;对常见的可降解、纸板、玻璃、金属、纸质和塑料等类别垃圾进行检测和计数&#xff0c;以协助垃圾环保分类处理。本文详细介绍基于YOLO…...

建立农村污水处理设施已经成为了当务之急!

在现代社会中&#xff0c;随着城市化进程的加速和人口的增长&#xff0c;选择农村污水处理设备进行污水处理已经成为了一个非常重要的问题。虽然城市中的污水处理设施得到了很好的发展&#xff0c;但是农村地区的污水处理还存在很多问题。 在农村地区&#xff0c;由于缺乏污水…...

【Matlab算法】粒子群算法求解一维线性函数问题(附MATLAB代码)

MATLAB求解一维线性函数问题前言正文函数实现可视化处理可视化结果前言 一维线性函数&#xff0c;也称为一次函数&#xff0c;是指只有一个自变量xxx的函数&#xff0c;且函数表达式可以写成yaxbyaxbyaxb的形式&#xff0c;其中aaa和bbb是常数。具体来说&#xff0c;aaa称为斜…...

【JavaEE】Thread 类及常用方法

一、Thread 类Thread 类我们可以理解为是 java 用于管理线程的一个类&#xff0c;里面封装了操作系统提供的线程管理这一方面的 API &#xff08;Thread 是优化后的结果&#xff09;, Java 代码创建的每一个线程&#xff0c;可以理解为为 Thread 实例化的对象&#xff0c;Threa…...

C语言数据结构初阶(7)----队列

CSDN的uu们&#xff0c;大家好。这里是C语言数据结构的第七讲。 目标&#xff1a;前路坎坷&#xff0c;披荆斩棘&#xff0c;扶摇直上。 博客主页&#xff1a;姬如祎队列的基础知识队列&#xff08;queue&#xff09;是只允许在一端进行插入操作&#xff0c;而在另一端进行删除…...

代码随想录二刷 day01 | 704. 二分查找 27. 移除元素 977. 有序数组的平方

代码随想录二刷day01704. 二分查找27. 移除元素977. 有序数组的平方704. 二分查找 题目链接 做这种题最好现在纸上写一写&#xff0c;如果在大脑中想&#xff0c;可能一会就晕了。 二刷的时候发现了一个新的知识点 即&#xff1a; >>的作用 二分法第二种写法&#xff1a…...

Linux 终端、进程组、会话、守护进程

文章目录一、终端概念终端概念控制终端二、进程组概念进程组概述进程组相关 API会话会话概念会话相关 API创建会话注意事项守护进程守护进程介绍守护进程模型守护进程参考代码守护进程相关 API参考文章一、终端概念 终端概念 1、终端&#xff08;Terminal&#xff09; 终端是…...

你是否有潜质成为谷歌开发者专家?加入 GDE 成长计划,释放潜力!

谷歌开发者专家 (Google Developer Experts&#xff0c;GDE)&#xff0c;又称谷歌开发者专家项目&#xff0c;是由一群经验丰富的技术专家、具有社交影响力的开发者和思想领袖组成的全球性社区。通过在各项活动演讲以及各个平台上发布优质内容来积极助力开发者、企业和技术社区…...

安全防御之防火墙篇(二)

目录 1.防火墙如何处理双通道协议&#xff1f; 2.防火墙如何处理NAT&#xff1f; 3.防火墙支持哪些NAT技术&#xff0c;主要应用的场景是什么&#xff1f; 4.当内网PC通过公网域名解析访问内网服务器的时候&#xff0c;会存在什么问题&#xff0c;如何解决&#xff1f;请详细…...

设计必备,5个png免抠素材网站,建议收藏

做设计、PPT都需要用到大量的免抠素材&#xff0c;职场中熟练使用Photoshop的人毕竟是少数&#xff0c;也很少有人愿意花费时间去精细抠图。那这5个免抠素材网站一定要收藏好&#xff0c;可以有效帮你节省时间&#xff0c;提高工作效率。 1、菜鸟图库 https://www.sucai999.co…...

shell 脚本expect

expect 是什么 expect - programmed dialogue with interactive programs&#xff08;与互动程序进行程序对话&#xff09; 定义脚本执行的 shell #!/usr/bin/expect -f 定义的是执行 expect 可执行文件的链接路径&#xff08;或真实路径&#xff09;&#xff0c;功能类似于bas…...

第十九天 Maven总结

目录 Maven 1. 前言 2. 概述 2.1 介绍 2.2 安装 3. IDEA集成Maven 3.1 集成Maven环境 3.2 创建Maven项目 3.3 Maven坐标详解 3.4 导入maven项目 4. 依赖管理 4.1 依赖配置 4.2 依赖传递 4.3 依赖范围 4.4 生命周期 4.5 插件 Maven 1. 前言 1). 什么是Maven? …...

ESP8266-NodeMCU开发板-------开发板介绍(1)

目录 认识ESP8266-NodeMCU开发板​编辑 GPIO编号与NodeMCU开发板引脚名的区别&#xff1a; ESP8266 GPIO编号与NodeMCU开发板引脚名的对应关系 可用引脚 电压电流限制 特殊引脚情况说明 上拉电阻/下拉电阻 模拟输入 通讯 认识ESP8266-NodeMCU开发板 初识NodeMCU开发板 (第1章-第…...

【测试开发篇3】软件测试的常用概念

目录 一、软件测试的生命周期(5个步骤) ①需求分析(两个角度) 用户角度&#xff1a; 开发人员的角度&#xff1a; ②测试计划 ③测试设计、测试开发 ④执行测试 ⑤测试评估 二、软件测试贯穿项目的整个生命周期的体现 需求分析阶段 计划阶段 设计阶段 编码阶段 …...

javaEE初阶 — JavaScript WebAPI

文章目录什么是 DOMDOM 树获取元素1. querySelector2. querySelectorAll事件1. 事件三要素2. 代码案例获取 / 修改元素内容1. innerHTML获取 / 修改元素属性获取 / 修改表单元素属性获取 / 修改样式属性1. 修改内联样式&#xff08;修改 style 属性的值&#xff09;2. 修改元素…...

UE实现地面动态交互效果

文章目录 1.实现目标2.实现过程2.1 SphereMask2.2 材质实现2.3 位置更新3.参考资料1.实现目标 基于SphereMask材质节点实现人物在地面一定范围内的颜色高亮效果。 2.实现过程 实现原理是首先通过,SphereMask材质节点更具计算输出Mask值,其中在球体半径内的输入1,在外部的则…...

如何用自己的数据训练YOLOv5

如何训练YOLOv5 1. Clone the YOLOv5 repository and install dependencies: git clone https://github.com/ultralytics/yolov5.git cd yolov5 pip install -r requirements.txt2. 整理数据&#xff0c;使其适配YOLO训练 Step1&#xff1a;Organize your dataset in the fo…...

【基础算法】数组相关题目

系列综述&#xff1a; &#x1f49e;目的&#xff1a;本系列是个人整理为了秋招算法的&#xff0c;整理期间苛求每个知识点&#xff0c;平衡理解简易度与深入程度。 &#x1f970;来源&#xff1a;材料主要源于代码随想录进行的&#xff0c;每个算法代码参考leetcode高赞回答和…...

MatBox—基于PyQt快速入门matplotlib的教程库

MatBox—基于PyQt快速入门matplotlib的教程库 __ __ _ _ _ _ _ _ _______ _ _ _ | \/ | | | | | | | | |(_)| | |__ __| | | (_) | || \ / | __ _ |…...

go channel使用

go语言中有一句名言&#xff1a; 不要通过共享内存来通信&#xff0c;而应该通过通信来共享内存。 channel实现了协程间的互相通信。 目录 一、channel声明 二、向channel发送数据 三、从channel读取数据 1. i, ok : <-c 2. for i : range c&#xff08;常用&#xff09…...

5. QtDesignStudio中的3D场景

1. 说明&#xff1a; 三维渲染开发是Design Studio的重要功能&#xff0c;且操作方便&#xff0c;设计效率非常高&#xff0c;主要用到的控件是 View3D ,可以在3D窗口中用鼠标对模型直接进行旋转/移动/缩放等操作&#xff0c;也可以为模型设置各种动画&#xff0c;执行一系列的…...

人工智能的几个研究方向

人工智能主要研究内容是&#xff1a;分布式人工智能与多智能主体系统、人工思维模型、知识系统、知识发现与数据挖掘、遗传与演化计算、人工生命、人工智能应用等等。 其中热门研究有以下几种。 一、计算机视觉 就包括图像识别&#xff0c;视频识别&#xff0c;具体应用有人…...

软件测试 - 常见的开发模型和测试模型

1.瀑布模型优点强调开发的阶段性, 强调早期计划及需求调查, 强调产品测试;缺点1. 由于瀑布模型是一种线型结构的模型, 也就意味着前一个阶段结束, 后一个阶段才能开始, 这就导致了风险往往会迟至后期的测试阶段才显露, 因而失去了及早纠正的机会.2. 瀑布模型中测试被后置, 导致…...

从零开始的机械臂yolov5抓取gazebo仿真(四)

Moveit与Gazebo联合仿真 上一篇博客已经将moveit!配置完毕&#xff0c;然而想要让moveit!控制gazebo中的机械臂&#xff0c;还需要进行一些接口的配置。现在我们有的功能包为sunday_description、sunday_moveit_config这两个功能包。且已经配置好xacro文件&#xff0c;本篇内容…...

C++修炼之筑基期第一层——认识类与对象

文章目录&#x1f337;专栏导读&#x1f337;什么是面向对象&#xff1f;&#x1f337;类的引入&#x1f337;什么是类&#x1f337;类的定义方式&#x1f337;类的访问限定符与封装&#x1f33a;访问限定符&#x1f33a;封装&#x1f337;类的作用域&#x1f337;类的实例化&a…...

IT 运营监控工具

在技术复杂性日益增加、业务竞争激烈的挑战以及消费者对服务中断接受度降低的世界中&#xff0c;IT 运营效率已成为增长、利润和成功的关键。IT 宕机的影响在几十年前威胁较小&#xff0c;现在意味着价值数百万美元的损失&#xff0c;有时甚至会损失各种规模的组织的业务和声誉…...

java线程之Thread类的基本用法

Thread类的基本用法1. Thread类的构造方法2. Thread的几个常见属性常见属性线程中断等待一个线程小鱼在上一篇博客详细的讲解了如何创建线程,java使用Thread类来创建多线程,但是对于好多没有相关经验的人来说,比较不容易理解的地方在于操作系统调度的执行过程. 我们通过下面代码…...