STM32delay函数delay延时函数讲解如何计算

stm32中delay(0x1affff)延迟500ms是怎么算的?_百度知道
stm32中delay(0x1affff)延迟500ms是怎么算的?
speed50mhz
我有更好的答案
通过系统时钟时间估算出来的,可用示波器查看是否符合要求。stm32有丰富的定时器,可以用定时器做延时,时间容易算,并且以后移植方便,不用纠结0x1affff到底是执行了多久
采纳率:39%
来自团队:
为您推荐:
其他类似问题
stm32的相关知识
换一换
回答问题,赢新手礼包
个人、企业类
违法有害信息,请在下方选择后提交
色情、暴力
我们会通过消息、邮箱等方式尽快将举报结果通知您。单片机、电路板
连接器、接插件
其他元器件
STM32 延时函数封装程序
STM32 延时函数封装程序
& & /*---------------------------------
& & 延时模块函数
& & 说明:只需在工程中加入delay.c和delay.h
& & 文件,即可用 Delayms(__IO uint32_t nTime);
& & Delayus(__IO uint32_t n
& & /*---------------------------------
& & 延时模块函数
& & 说明:只需在工程中加入delay.c和delay.h
& & 文件,即可用 Delayms(__IO uint32_t nTime);
& & Delayus(__IO uint32_t nTime)
& & -----------------------------------*/
& & #ifndef __DELAY_H
& & #define __DELAY_H
& & #include "stm32f10x.h"
& & /*---------------------------------
& & 描 述:参数1即为1ms,1000即为1s;只有几
& & us的误差;
& & -----------------------------------*/
& & extern void Delayms(__IO uint32_t nTime);
& & /*---------------------------------
& & 描 述:参数1即为1us,1000即为1只有几
& & us的误差;
& & -----------------------------------*/
& & extern void Delayus(__IO uint32_t nTime);
& & /*---------------------------------
& & 函数名:延时调整形式的delaynus函数,
& & 描 述:参数1即为1us,1000即为1
& & -----------------------------------*/
& & extern void delay_nus(unsigned long n);
& & /*---------------------------------
& & 函数名:延时调整形式的delaynms函数,
& & 描 述:参数1即为1ms,1000即为1s;
& & -----------------------------------*/
& & extern void delay_nms(unsigned long n);
& & #endif
& & C 函数
& & /*---------------------------------
& & 延时模块函数
& & 说明:只需在工程中加入delay.c和delay.h
& & 文件,即可用 Delayms(__IO uint32_t nTime);
& & Delayus(__IO uint32_t nTime)
& & -----------------------------------*/
& & #include"delay.h"
& & statIC __IO uint32_t TimingD
& & /* Private function prototypes -----------------------------------------------*/
& & /*---------------------------------
& & 函数名:ms延时函数
& & 描 述:参数1即为1ms,1000即为1s;只有几
& & us的误差;
& & -----------------------------------*/
& & void Delayms(__IO uint32_t nTime)
& & while(SysTick_Config(SystEMCoreCLOCk/1000));
& & TimingDelay = nT
& & while(TimingDelay != 0);
& & SysTick-&CTRL=0x00; //关闭计数器
& & SysTick-&VAL =0X00; //清空计数器
& & /*---------------------------------
& & 函数名:us延时函数
& & 描 述:参数1即为1us,1000即为1只有几
& & us的误差;
& & -----------------------------------*/
& & void Delayus(__IO uint32_t nTime)
& & while(SysTick_Config(SystEMCoreClock/1000000));
& & TimingDelay = nT
& & while(TimingDelay != 0);
& & SysTick-&CTRL=0x00; //关闭计数器
& & SysTick-&VAL =0X00; //清空计数器
& & /*---------------------------------
& & 函数名:延时辅助函数
& & 描 述:
& & -----------------------------------*/
& & void TimingDelay_Decrement(void)
& & if (TimingDelay != 0x00)
& & TimingDelay--;
& & /*---------------------------------
& & 函数名:systick的中断函数
& & 描 述:参数1即为1us,1000即为1只有几
& & us的误差;
& & -----------------------------------*/
& & void SysTick_Handler(void)
& & TimingDelay_Decrement();
& & /*---------------------------------
& & 函数名:延时调整形式的delaynus函数,
& & 描 述:参数1即为1us,1000即为1
& & -----------------------------------*/
& & void delay_nus(unsigned long n)
& & while(n--)
& & while(j--);
& & /*---------------------------------
& & 函数名:延时调整形式的delaynms函数,
& & 描 述:参数1即为1ms,1000即为1s;
& & -----------------------------------*/
& & void delay_nms(unsigned long n)
& & while(n--)
& & delay_nus(1030);
型号/产品名
深圳优耐检测技术有限公司
深圳优耐检测技术有限公司
深圳优耐检测技术有限公司
深圳优耐检测技术有限公司
深圳优耐检测技术有限公司我想每个单片机爱好者及工程开发设计人员都有过点灯的经历。流水灯是个好东西,尤其是在调试资源有限的环境中,有时会帮上大忙。
然在最初入门时,如何让这些小灯们按照我们的想法欢快地跑起来呢,绝大多数小朋友的做法是:在一个while循环里加上延时程序,让小灯在每个状态下停留一段时间,再进入下一个状态,这样小灯们就会在不同的状态中切换,就可以根据我们设计的程序闪烁了。
这样这里就会涉及到一个延时程序的编写的问题,而一般的做法是一个for循环里去减一个很大的数,直到为0,则延时完成,那个数的值则是根据时钟频率和指令运行周期,估算出来的,还记得较久以前看过一篇帖子介绍51单片机精确延时的几种方法,有一种方法是在keil中设定好时钟频率,然后通过软件仿真试来算延时时间,以达到较精确定时。
但这些方法一般都不够方便,延时也不够精确,更高阶一点的方法便是开一个定时器,在定时中断里面计数达到精确延时的目的。
在STM32的应用中,可考虑利用SysTick系统嘀嗒定时器来实现。但在STM32开发手册中对它的介绍却很少,几乎到没有的程度。因为它是Cortex内核的部分,CM3为它专门开出一个异常类型,并且在中断向量表中占有一席之地(异常号15),这样它可以很方便的移植到不同厂商出CM3内核的芯片上,并且对于有实时操作系统的软件,它一般会作为整个系统的时基,这个对操作系统非常重要。有关SysTick的详细介绍可参考《Cortex-M3 权威指南》第133 页第八章及第179页第十三章。
SysTick总共有四个寄存器:
对应于软件中 SysTick-&CTRL;
对应于软件中&SysTick-& LOAD;
对应于软件中&SysTick-& VAL;
对应于软件中 SysTick-& CALIB& (如上图),没有用过,也不常用,暂不作介绍。
这几个寄存器的偏移量如下图所示:
?寄存器结构体的定义在 \CMSIS\CM3\CoreSupport& core_cm3.h中,如下?
/**&@addtogroup&CMSIS_CM3_SysTick&CMSIS&CM3&SysTick
&&memory&mapped&structure&for&SysTick
typedef&struct
&&__IO&uint32_t&CTRL;&&&&&&&&&&&/*!&&Offset:&0x00&&SysTick&Control&and&Status&Register&*/
&&__IO&uint32_t&LOAD;&&&&&&&&&&&/*!&&Offset:&0x04&&SysTick&Reload&Value&Register&&&&&&&*/
&&__IO&uint32_t&VAL;&&&&&&&&&&&&/*!&&Offset:&0x08&&SysTick&Current&Value&Register&&&&&&*/
&&__I&&uint32_t&CALIB;&&&&&&&&&&/*!&&Offset:&0x0C&&SysTick&Calibration&Register&&&&&&&&*/
}&SysTick_T
?SysTick? 是一个24 位的定时器,即一次最多可以计数 224个时钟脉冲,这个脉冲计数值被保存到SysTick-&VAL 当前计数值寄存器中,它只能向下计数,每接收到一个时钟脉冲SysTick-&VAL 的值就向下减 1,直至0,然后由硬件自动把重载寄存器SysTick-&LOAD 中的值到SysTick-&VAL重新计数,并且当SysTick-&VAL值计数到0时,触发异常,调用void SysTick_Handler(void)函数,可以在此中断服务函数中处理定时中断事件了,一般是对设定值进行递减计数操作。只要不把它在SysTick控制及状态寄存器SysTick-&CTRL中的第0位使能位清除,就永不停息。
SysTick 中断优先级问题这里需要强调下。
&它属于系统异常,是内核级中断,并且优先级是可以设置的,具体设置也是在& core_cm3.h中
&*&@brief&&Initialize&and&start&the&SysTick&counter&and&its&interrupt.
&*&@param&&&ticks&&&number&of&ticks&between&two&interrupts
&*&@return&&1&=&failed,&0&=&successful
&*&Initialise&the&system&tick&timer&and&its&interrupt&and&start&the
&*&system&tick&timer&/&counter&in&free&running&mode&to&generate&
&*&periodical&interrupts.
static&__INLINE&uint32_t&SysTick_Config(uint32_t&ticks)
&&&&if&(ticks&&&SysTick_LOAD_RELOAD_Msk)&&return&(1);&&&&&&&&&/*&Reload&value&impossible&*/
&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
&&&&SysTick-&LOAD&&=&(ticks&&&SysTick_LOAD_RELOAD_Msk)&-&1;&&&/*&set&reload&register&*/
&&&&NVIC_SetPriority&(SysTick_IRQn,&(1&&__NVIC_PRIO_BITS)&-&1);&&
&&&&SysTick-&VAL&&&=&0;&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&
&&&&SysTick-&CTRL&&=&SysTick_CTRL_CLKSOURCE_Msk&|&
&&&&&&&&&&&&&&&&&&&SysTick_CTRL_TICKINT_Msk&&&|&
&&&&&&&&&&&&&&&&&&&SysTick_CTRL_ENABLE_M&&&&&&&&&&&&&&&&&&&&
&&&&return&(0);&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&/*&Function&successful&*/
其中如下这句就是设置优先级的函数,此函数对内核中断优先级和外部中断优先级设置通吃,比较强大,但需要手动算出来抢占和从优先级,不太方便,当跳进此函数,我们可以算出Systick默认优先是最低的(效果相当于SCB-&SHP[11] = 0xF0;)
NVIC_SetPriority&(SysTick_IRQn,&(1&&__NVIC_PRIO_BITS)&-&1);
此时若其它外部中断优先级设置比它高时,可以剥夺它进而转向外部中断。
可以做如下实验验证:
先设置一事件中断,把优先级设置高一些,
void&Exti_Config(void)
&&&&EXTI_InitTypeDef&EXTI_InitS
&&&&NVIC_InitTypeDef&NVIC_InitS
&&&&EXTI_InitStructure.EXTI_Line&=&EXTI_Line1;
&&&&EXTI_InitStructure.EXTI_Mode&=&EXTI_Mode_E
&&&&EXTI_InitStructure.EXTI_LineCmd&=&ENABLE;
&&&&EXTI_Init(&EXTI_InitStructure);
&&&&NVIC_InitStructure.NVIC_IRQChannel&=&EXTI1_IRQn;
&&&&NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority&=&1;&&&&
&&&&NVIC_InitStructure.NVIC_IRQChannelSubPriority&=&1;&&&&&&&&&&&&&&&&
&&&&NVIC_InitStructure.NVIC_IRQChannelCmd&=&ENABLE;
&&&&NVIC_Init(&NVIC_InitStructure);
注:中断分组我在实验中,最初初始化设置为如下:
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);
设为第二组。
void&SysTick_Handler(void)
&&&&EXTI_GenerateSWInterrupt(EXTI_SWIER_SWIER1);&
&&&&LED_1&=&ON;
&&&&Delay();
系统滴答中断里触发外部中断事件,并点亮LED1 。
外部中断处理函数如下
void&EXTI1_IRQHandler(void)
&&&&if&(EXTI_GetITStatus(EXTI_Line1)&!=&RESET)&
&&&&&&&&EXTI_ClearITPendingBit(EXTI_Line1);&&&&&
&&&&&&&&LED_0&=&ON;
&&&&&&&&Delay();
此延时函数为阻塞延时如下:
void&Delay(void)
&&&&u32&i;
&&&&for(i=0&&;&i&&&0xFFFFF;&i++){}
加入延时是为了看出来哪个灯先亮。
当外部中断优先级比较高时,它可以抢占Systick中断先执行,以上代码实验结果为,LED0先点亮后,再回到LED1再点亮。
当把外部中断设置为与systick相同的优先级时,则systick优先级就会相对较高,例如把上面的优先级改为
NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority&=&3;&&&&
NVIC_InitStructure.NVIC_IRQChannelSubPriority&=&3;
则会LED1先亮,执行完SysTick_Handle函数后才轮到EXTI1_IRQHandler执行。
个人认为,若要实现systick精确延时,最好把systick优先级设置高一些,例如
NVIC_SetPriority&(SysTick_IRQn,&0);
即把SCB-&SHP[11] = 0x00;则可达到systick优先级高于任合外部中断的效果,此时延时会比较精准。
另外对于SysTick的时钟源的选择,要注意它的时钟源可选择内部时钟(FCLK,CM3上的自由运行时钟,STM32中对应是AHB),或者是外部时钟(& CM3处理器上的STCLK信号,STM32中对应是AHB/8)
可参考如下图
它是在SysTick-&CTRL第二位CLKSOURCE时钟源选择中设置。
有关systick延时函数的编写可参考野火《零死角玩转stm32-初级篇》。
至此我们可以简单的实现一流水灯程序
&&&&LED_0&=OFF;
&&&&LED_1&=&ON;
&&&&Delay_ms(500);
&&&&LED_0&=OFF;
&&&&LED_1&=&ON;
&&&&Delay_ms(500);
然而这样做真的好吗 ?这里用的是 阻塞延时哦,CPU的效率很大一部分就耗在了空转上了,太浪费资源。
?假设系统时钟频率为72MHZ或者几十上百MHZ时,当完成一个循环只需要几十或十几纳秒级或者更短,而在这个循环之中阻塞延时个几十至几百毫秒的话,就像是在高速公路上突然横出一条坑坑洼洼的泥泞路,那可想整条路都会因此而慢下来,甚至会出现灾难性的后果,个人认为,一般在系统初始化过程中,各芯片的时序对时间有要求,可以用下阻塞延时,只需要系统启动时运行一下,当系统跑起来之后,最好就别再傻呼呼的这么做了。?
这时主要采用的是在定时器里计数,在外部循环中对变量查询,达到某个值时再执行某个动作,达到延时的效果,而在时间未到时,系统还可以不停的跑圈圈,做别的事情去。
?&gticks在定时中断里每毫秒计数一次
&&&&if(500&==&gticks)
&&&&&&&&LED_0&=OFF;
&&&&&&&&LED_1&=&ON;
&&&&if(1000&==&gticks)
&&&&&&&&LED_0&=OFF;
&&&&&&&&LED_1&=&ON;
&&&&&&&&gticks&=&0
&&&&Do_others();&
??以上需要在事件处理过程中对gticks进行处理,增加了代码的耦合度,更容易出错,如果在一个事件处理中对gticks清除了,而下个事件中又需要查询它,这样就可能导致处理时序的错乱,相互干扰。??
能否在事件处理中只提供查询功能,而定时的事情就交给定时自己去做?
下节高手将登场了,为大家介绍个我曾在一项目中学到的,非阻塞延时的精妙设计。
& 著作权归作者所有
人打赏支持
码字总数 14052
下面为大家介绍一个曾见过的在裸机系统中,非阻塞延时的巧妙设计,当时它是被用在一导航影音娱乐系统的MCU驱动软件中,在此我对其作了一定的改动。 此章节涉及到STM32内容不多,以软件为主。...
SysTick-------操作系统的心跳 SysTick是系统滴答定时器,可以说是操作系统的的“心跳”,它被绑在NVIC中,用于产生SysTick异常(异常号:15)。一旦产生SysTick异常,就会产生滴答中断,这个...
SysTick系统嘀嗒定时器并非STM32独有的,它是Cortex内核的部分,CM3为它专门开出一个异常类型,并且在中断向量表中占有一席之地(异常号15)。这样它可以很方便的移植到不同厂商出CM3内核...
OceanStack
因为网上关于STM32读取6050的例程并不少但是总会有古怪的问题存在,在尝试读取的过程中在网上逛论坛发现很多问题到最后没结果不了了之,不知那些前辈们是否已经自己查出了问题,我想尽自己微...
一、Linux时钟系统 1.时钟硬件 绝大多数的PC都有两个时钟源,RTC(实时时钟)和OS(系统时钟)。RTC也叫做CMOS时钟,它是PC主机板上的一块芯片。OS时钟产生于PC主板上的定时/计数芯片,由操作...
8yi少女的夢
1、stm32中断向量表配置 在STM32使用中由于中断优先级的设置采用的是库函数,因此要请保证所有的优先级设置为可抢占优先级,具体实现方式是在RTOS启动前调用函数:NVICPriorityGroupConfig(N...
让自己别忘了大学里学的东西,那么就把它记录下下来,效率会比忘记然后重新再去找资料再重头学高的多 先讲讲定时器的基础定时功能: 1.先做一个形象的比喻: 它们俩基本相同,不同的是,对...
最近一直在忙STM32的学习,在学习中遇到了不少问题,也经过各种尝试解决问题,在这里我通过博文的形式写出来,也希望能够帮到遇见同样问题的人们。对于STM32系列的芯片,有一个好处就是官方给...
jerry2012cn
cube基本配置,外设开启编码器,串口2 -------------------------------------------------------------------------------------------------------------------------- 错误:error: #20:......
这一部分描述异常模型。 每一个异常都存在一个状态: 闲置 这个异常没有活跃,没有暂停 待进行 异常等待被处理器服务。一个外设或软件中断请求可以改变相应中断的状态到即将发生状态。 ·活跃...
没有更多内容
加载失败,请刷新页面
快速入门 本章主要目标完成Spring Boot基础项目的构建,并且实现一个简单的Http请求处理,通过这个例子对Spring Boot有一个初步的了解,并体验其结构简单、开发快速的特性。 系统要求: Java...
$("input[type='file']#uploadRes").click(function(){$("#progress").show();$('#progress .bar').css(
shimmerkaiye
这种算法的主要思想就是将内存 划分为不同的几块 然后根据各个年到的特点采用最适当的收集算法。 在新生代 每次垃圾回收时 都有大批量的对象死去,只有少量存活那就采用--复制算法。 而老年代...
html代码: &volist name="sblx.shebei" id="sb"&&tr&&td&
&input level='1' name="shebei[]" type="checkbox" value="&{$sb.sbid}&"&&{$sb.sbname}&&/td&&td&
&volist ......
1.配置渠道相关信息 在App 目录下新建一个channel(txt)文件 Qh360 #360Yyb #应用宝Wdj #豌豆荚Lenovo #联想Xiaomi #小米Huawei #华为Meizhu #魅族 2.在位于项目的根目录 build....
遇见sunshine
应领导要求 小弟今天也对RabbitMQ的业务逻辑流程简单的了解了一下。从win环境搭建RabbitMQ服务,到代码测试(单机部署、单生产者、单消费者),一套流程下来,感觉都挺正常。但想着好记性不如...
Error Domain=NSURLErrorDomain Code=-1022 "The resource could not be loaded because the App Transport Security policy requires the use of a secure connection." 这是因为Xcode 7以后......
资源整理 1 Coding: 1.Python工程,使用networkx,geopandas,mplleaflet在地图上可视化网络流。 map-network 2.R语言包rsample, 用于创建和汇总不同类型的重采样对象的类和函数。 rsample ...
最近研究多数据源问题,使用的是druid连接池,多数据源通过注解自动配置,使用这三个注解 @Retention @Documented @Inherited 自定义一个注解配置数据源 Retention注解:- Retention(保留)注...
gitk 是一个强悍的git图形化工具。它可不仅仅是命令行的一个替代产品,实际上它能实现很多命令行并不能提供的git功能。所以不要认为它和命令行是git操作的两种实现工具。 然而gitk相关的文档...
WeiXiaodong
没有更多内容
加载失败,请刷新页面
文章删除后无法恢复,确定取消删除此文章吗?
亲,自荐的博客将通过私信方式通知管理员,优秀的博客文章审核通过后将在博客推荐列表中显示
确定推荐此文章吗?
确定推荐此博主吗?
聚合全网技术文章,根据你的阅读喜好进行个性推荐
指定官方社区
深圳市奥思网络科技有限公司版权所有STM32中3个延时函数使用方法
第一个延时函数:
void delay(u16 num)
for(i=0;i第二个延时函数:static u8
fac_us=0;//us延时倍乘数
static u16 fac_ms=0;//ms延时倍乘数
//初始化延迟函数
//SYSTICK的时钟固定为HCLK时钟的1/8
//SYSCLK:时钟
void delay_init(u8 SYSCLK)
SysTick-&CTRL&=0//bit2清空,选择外部时钟
fac_us=SYSCLK/8;
fac_ms=(u16)fac_us*1000;
//注意nms的范围
//SysTick-&LOAD为24位寄存器,所以,最大延时为:
//nms&=0xffffff*8*1000/SYSCLK
//SYSCLK单位为Hz,nms单位为ms
//对72M条件下,nms&=1864
void delay_ms(u16 nms)
SysTick-&LOAD=(u32)nms*fac_//时间加载(SysTick-&LOAD为24bit)
SysTick-&VAL =0x00;
//清空计数器
SysTick-&CTRL=0x01 ; //开始倒数
temp=SysTick-&CTRL;
while(temp&0x01&&!(temp&(1&&16)));//等待时间到达
SysTick-&CTRL=0x00; //关闭计数器
SysTick-&VAL =0X00; //清空计数器
//nus为要延时的us数.
void delay_us(u32 nus)
SysTick-&LOAD=nus*fac_ //时间加载
SysTick-&VAL=0x00;
//清空计数器
SysTick-&CTRL=0x01 ;//开始倒数
temp=SysTick-&CTRL;
while(temp&0x01&&!(temp&(1&&16)));//等待时间到达
SysTick-&CTRL=0x00; //关闭计数器
SysTick-&VAL =0X00; //清空计数器STM32延时函数_百度文库
您的浏览器Javascript被禁用,需开启后体验完整功能,
享专业文档下载特权
&赠共享文档下载特权
&10W篇文档免费专享
&每天抽奖多种福利
两大类热门资源免费畅读
续费一年阅读会员,立省24元!
STM32延时函数
&&STM32延时函数。
阅读已结束,下载本文需要
想免费下载更多文档?
定制HR最喜欢的简历
你可能喜欢

我要回帖

更多关于 C51延时函数delay的编写 的文章

 

随机推荐