当前位置:文档之家› 16位定时器

16位定时器

16位定时器
16位定时器

16位定时计数器

1. 16位定时、计数器(定时计数器1、定时计数器3)

16位定时计数器可以用于精确事件定时,波形发生,信号时序测量的方面。它的主要特性是:

l 真16位设计(也就是可以16PWM)

l 三个独立的输出比较单元

l 双缓冲的输出比较寄存器

l 一个输入捕捉单元

l 输入捕捉具有噪声滤除功能

l 自动重装入功能

l PWM功能

l 可变的PWM周期

l 频率发生器

l 外部事件计数器

l 10个独立中断源

(TOV1,OCF1A,OCF1B,OCF1C,ICF1,TOV3,OCF3A,OCF3B,OCF3C,ICF3)

1.1在ATMEGA103兼容模式中的约束

注意在ATMEGA103兼容模式中只有一个16位定时计数器有效(Timer1/Counter1)。另外还要

注意,在这个模式中Timer1/Counter1只有两个比较寄存器(A、B)

2.简介

在这章中所提及的寄存器绝大部分拥有相同的结构。通过改变后面的字母n可以选择不同的定时计数器,通过改变字母x可以改变不同的输出比较单元通道。在程序中必须指明具体的寄存器或位。例如,TCNT1就是访问定时计数器的内容,依次类推。

图46给出一个16位定时计数器的简单框图,具体IO位置见图2,

2. 1寄存器

定时计数器(TCNTn),输出比较寄存器(OCRnA/B/C)和输入捕捉寄存器(ICRn)都是16位寄存器,访问16位寄存器必须采用一些特殊的步骤。这些过程将在“访问16位寄存器”一节介绍。对于控制寄存器(TCCRnA//B/C)这些8位寄存器,没有CPU访问限制。所有的中

断请求都在定时中断标志寄存器(TIFR)和扩展定时中断标志寄存器(ETIFR)中标出。每个

中断也都可以通过定时中断屏蔽寄存器(TIMSK)和扩展定时中断屏蔽寄存器(ETIMSK)分别予以屏蔽。由于TIMSK和ETIMSK通其他的定时器单元共享,所有没有列出它的具体性能。

定时/计数器可以使用经由分频器的内部时钟,也可以使用由Tn引进的外部时钟。时钟选择逻辑单元决定那一种时钟和那种边沿用于定时/计数器。如果没有时钟源选定,定时/计数

器处于停止状态。时钟选择逻辑的输出指定为定时器时钟(CLKTn)。

具有双缓冲的输出比较寄存器(OCRnA/B/C/)在所有时间里一直与定时/计数器的内容比较。比较内容可以用波形发生器在比较输出引脚(OcnA/B/C)上产生PWM或可变频率输出。

具体参见“输出比较单元”一节。输出比较相同事件还可以使比较相同标志(OCFnA/B/C)

置位,它可以生成输出比较中断请求。

通过外部输入捕捉引脚(ICPn)和模拟比较器所触发(边沿触发)的事件,输入捕捉寄

存器可以捕捉定时/计数器的内容。输入捕捉单元含有数字滤波器可以减小捕捉到噪声尖峰

的机会。

定时/计数器的最大值可以有许多方法设定,如通过OCRnA寄存器和ICRnA寄存器,也可以

设定成一个固定值。如果在PWM模式中使用OCRnA作为最大值,OCRnA就不能用在生成PWM输出

中。由于这种双缓冲的方式,可让最大值在运行中随时改变。如果只要固定的最大值,可以使用ICRnA代替。以使OCRnA可以用于PWM输出。

2. 2 常用定义

下面的定义广泛地应用于整个文档中

底定时/计数器为0000H称之为底

最大定时/计数器为0xfff(65535)是称之为最大

顶定时/计数器设定最大值为顶,它可以是固定值如0x00ff,0x001f,0x003f,也可

以由寄存器OCRnA、ICRnA设定。具体以使用模式而定。

2.3 兼容性

此16定时/计数器对于以前的AVR1的16定时/计数器,进行了改进和提高。它完全兼容以前的

特性:

l 所有16定时/计数器包括的寄存器和中断,包括定时中断寄存器

l 所有16定时/计数器中寄存器中的位地址,包括定时中断寄存器

l 中断向量

下面的位发生了名称改变,但功能还是一样的。

PWMn0改为WGMn0

PWMn1改为WGMn1

CTCn 改为WGMn2

下面是增加的寄存器

定时/计数控制寄存器C(RCCRnC)

输出比较寄存器C(OCRnCH、OCRnCL合成OCRnC)

下面是增加的位

COM1C1:0 位添加至TCCRnA

FOCnA ,FOCnB和FOCnC添加到新的寄存器C

增加了有关C的输出比较中断标志和屏蔽单元。

16位定时/计数器的性能提高,在一些特别的应用可能影响兼容性。

3. 1 16位寄存器的访问

AVRCPU可以通过8位数据总线访问象TCNTn、OCRnA/B/BC和ICRn这样的16位寄存器。这些寄存

器必须以两次字节访问来读写操作。每个16位寄存器都有一个8位暂寄存器,它用于高位地址的访问。同样,暂存寄存器由定时单元中的所有16定时器共享。对寄存器低8位访问会触发整个16位寄存器的读写操作。当CPU写16位寄存器的低位时,暂存寄存器中内容和要写到

低位的数据在同一时钟写如16位寄存器。CPU读16位寄存器的低位时,16位寄存器的高位内

容会与低位数据同一时钟复制到暂存寄存器中。

不是所有的16位寄存器访问都要借助暂存寄存器,16位寄存器OCRnA/B/C。

对于16位写操作,高字节必须在低字节前写入;对于16位读操作,低字节必须在高字节前读出。

下面的例子说明如何访问16位寄存器,假设期间没有中断修改暂存寄存器,同样的原则也可用于OCRnA/B/C、ICRn等16位寄存器的访问。注意使用“C”语言时的访问方法。Assembly Code Examples(1)

...

; Set TCNTn to 0x01FF

ldi r17,0x01

ldi r16,0xFF

out TCNTnH,r17

out TCNTnL,r16

; Read TCNTn into r17:r16

in r16,TCNTnL

in r17,TCNTnH

...

C Code Examples(1)

unsigned int i;

...

/* Set TCNTn to 0x01FF */

TCNTn = 0x1FF;

/* Read TCNTn into i */

i = TCNTn;

在汇编的例子中TCNTn的返回值在r16:r17中,要特别注意的是,访问16位寄存器是一个自

动连续的操作。在两条指令间有中断发生,并且这个中断也要访问16位寄存器导致暂存寄存器内容改变的话。那这次访问的结果就可能时错误的。所在进行16位地址访问的时候,要关闭中断。

下面的例子指出如何自动读取TCNTn,同样的方法也适用于OCRnA//B/C、ICRn。Assembly Code Example(1)

TIM16_ReadTCNTn:

; Save GLOBAL interrupt flag

in r18,SREG

; Disable interrupts

cli

; Read TCNTn into r17:r16

in r16,TCNTnL

in r17,TCNTnH

; Restore GLOBAL interrupt flag

out SREG,r18

ret

C Code Example(1)

unsigned int TIM16_ReadTCNTn( void )

{

unsigned CHAR sreg;

unsigned int i;

/* Save GLOBAL interrupt flag */

sreg = SREG;

/* Disable interrupts */

_CLI();

/* Read TCNTn into i */

i = TCNTn;

/* Restore GLOBAL interrupt flag */

SREG = sreg;

return i;

}

下面例子说明如何自动写TCNTn寄存器,方法也适用于OCRnA/B/C、ICRn

Assembly Code Example(1)

TIM16_WriteTCNTn:

; Save GLOBAL interrupt flag

in r18,SREG

; Disable interrupts

cli

; Set TCNTn to r17:r16

out TCNTnH,r17

out TCNTnL,r16

; Restore GLOBAL interrupt flag

out SREG,r18

ret

C Code Example(1)

void TIM16_WriteTCNTn( unsigned int i )

{

unsigned CHAR sreg;

unsigned int i;

/* Save GLOBAL interrupt flag */

sreg = SREG;

/* Disable interrupts */

_CLI();

/* Set TCNTn to i */

TCNTn = i;

/* Restore GLOBAL interrupt flag */

SREG = sreg;

3.2 高字节暂存寄存器的重复使用

如果写多于一个的16位寄存器,它们的高位内容相同。那么高位只需要写一次。

4. 定时/计数器的时钟源

定时/计数器可以被内部或外部的时钟源驱动,时钟控制逻辑可以选择时钟源的类型,它由

定时/计数器控制寄存器B中的时钟选择位(CSn2:0)决定。关于时钟源和分频器可参看“定时/计数器1,定时/计数器3的时钟源与预分频器”一节。

5. 计数器单元

16位定时/计数器的主要部分是一个可编程16位加/减计数器单元。图47给出此计数器的框图和周围的控制环境。

两个定时器蜂鸣器,一个控制频率,另一个控制时间

//同时利用两个定时器控制蜂鸣器发声,定时器0控制频率,定时器1控制同一个频率持续的时间,间隔300ms依次输出 1、"1 0、" // 50、" 100、" 200、" 400、"800HZ的方波 #include//52单片机头文件 #include //包含有左右循环移位子函数的库 #define uint unsigned int//宏定义 #define uchar unsigned char sbit Waveout=P1^0; uchar tt; uint fre,flag; uint Freq[]={1,10,50,100,200,400,800,1000} void main()//主函数{fre=500; TMOD=0x11;//设置定时器0,定时器1为工作方式1 TH0=(65536-fre)/256;

TL0=(65536-fre)%256; TH1=(65536-500)/256; TL1=(65536-500)%256; EA=1;//开总中断 ET0=1;//开定时器0中断 ET1=1; TR1=1; TR0=1;//启动定时器0 while (1) //等待中断产生{if(tt=a){tt=0; Waveout=~Waveout;}}}void timer0() interrupt 1//定时器0中断{TR0=0;//进中断后先把定时器0中断关闭,防止内部程序过多而造成中断丢失TH0=(65536-fre)/256; TL0=(65536-fre)%256; tt++;}void timer1() interrupt 3//定时器1中断用来产生300微秒时间定时{TH1=(65536-500)/256; TL1=(65536-500)%256; flag++; if(flag==6){flag=0; freq=Freq[i];}}

AVR定时器中断初值计算方法

AVR定时器中断初值计算方法 使用芯片ATMega16外部晶振 定时器1(16位定时器)寄存器TCCR1B=0x04设定256预分频要利用定时器定时1秒 1,4000000/256=15625说明定时器每当1/15625秒就会触发一次中断 2,65535-15625=49910计算出要累加多少次才能在1秒后出发定时器1的溢出中断 3,49910<==>C2F6将计算后的值换算成16进制 4,TCNT1H=0xC2;对寄存器赋值 TCNT1L=0xF6; ================================================= 例如用16位定时器TIMER1,4MHZ晶振,256分频,100ms定时,如何求得初值赋给TCNT1 65536-(4M/256)*= 其中,4M是晶体频率,是定时时长单位秒。 对于8位的定时器 T=(2^8-计数初值)*晶振周期*分频数=(2^8-计数初值)/晶振频率*分频数计数初值=2^8-T/晶振周期/分频数=2^8-T*晶振频率/分频数

因为AVR一指令一周期 IARForAVR精确延时 C语言中,想使用精确的延时程序并不容易。IAR中有这样的一个函数__delay_cycles(),该函数在头文件中定义,函数的作用就是延时N个指令周期。根据这个函数就可以实现精确的延时函数了(但不能做到100%精确度)。 实现的方法: 建立一个的头文件: #ifndef__IAR_DELAY_H #define__IAR_DELAY_H #include<> #defineXTAL8//可定义为你所用的晶振频率(单位Mhz) #definedelay_us(x)__delay_cycles((unsignedlong)(x*XTAL)) #definedelay_ms(x)__delay_cycles((unsignedlong)(x*XTAL*1000)) #definedelay_s(x)__delay_cycles((unsignedlong)(x*XTAL*1000000 )) #endif

WinCC 中定时器使用方法介绍

1、定时器功能介绍 2、脚本中定时器介绍 3、使用脚本实现更多定时器功能 3.1 整点归档 3.2 WinCC 项目激活时避免脚本初次执行及延迟执行脚本1 定时器功能介绍 WinCC 中定时器的使用可以使 WinCC按照指定的周期或者时间点去执行任务,比如周期执行变量归档、在指定的时间点执行全局脚本或条件满足时打印报表。WinCC 已经提供了一些简单的定时器,可以满足大部分定时功能。但是在有些情况下,WinCC 提供的定时器不能满足我们需求,这时我们就可以通过 WinCC 提供的脚本接口通过编程的方式实现定时的功能,因为脚本本身既可以直接调用 WinCC其他功能,比如报表打印,也可以通过中间变量来控制其他功能的执行,比如通过置位/复位归档控制变量来触发变量记录的执行。WinCC 提供了 C 脚本和 VBS 脚本,本文主要以全局 C 脚本编程为例介绍定时功能的实现。 2 脚本中定时器介绍既然在全局脚本中可以编程控制其他功能的执行,那么首先看看全局脚本的触发: 图1 脚本触发器分类如图1所示:脚本触发器分为使用定

时器和使用变量,定时器又分为周期执行和非周期执行一次,比如每分钟执行一次脚本属于周期执行,指定2012年10月1日执行一次属于非周期执行。使用变量触发脚本,即在变量发生变化时,脚本就执行一次,而变量的采集可以根据指定周期循环采集,或者根据变化采集,根据变化实际是1秒钟采集变量一次。 3使用脚本实现更多定时器功能 利用脚本自身的定时器,可以通过在脚本中编程的方式实现更多其它定时功能。 3.1整点归档 WinCC提供了变量归档,变量归档分为周期归档和非周期归档,不管是周期归档或非周期的归档,都又可以通过一些变量或脚本返回值来控制归档,比如:整点归档。下面的设置结合WinCC脚本,实现了在整点开始归档,归档五分种后停止归档,即每个小时仅归档前五分钟的数据。 软件环境:Windows 7 Professional Service Pack1 , WinCC V7.0 SP3 归档名称:ProcessValueArchive 归档变量:NewTag 归档周期:1 分钟 归档控制变量 startarchive C脚本触发周期:10秒 脚本代码: #include"apdefap.h" int gscAction( void ) { #pragma option(mbcs) #pragma code ("kernel32.dll");

51单片机定时器初值的计算

51单片机定时器初值的计算 一。10MS定时器初值的计算: 1.晶振12M 12MHz除12为1MHz,也就是说一秒=1000000次机器周期。10ms=10000次机器周期。65536-10000=55536(d8f0) TH0=0xd8,TL0=0xf0 2.晶振11.0592M 11.0592MHz除12为921600Hz,就是一秒921600次机器周期,10ms=9216次机器周期。 65536-9216=56320(dc00) TH0=0xdc,TL0=0x00 二。50MS定时器初值的计算: 1.晶振12M 12MHz除12为1MHz,也就是说一秒=1000000次机器周期。50ms=50000次机器周期。65536-50000=15536(3cb0) TH0=0x3c,TL0=0xb0 2.晶振11.0592M 11.0592MHz除12为921600Hz,就是一秒921600次机器周期,50ms=46080次机器周期。 65536-46080=19456(4c00) TH0=0x4c,TL0=0x00 三。使用说明 以12M晶振为例:每秒钟可以执行1000000次机器周期个机器周期。而T 每次溢出 最多65536 个机器周期。我们尽量应该让溢出中断的次数最少(如50ms),这样对主程序的干扰也就最小。开发的时候可能会根据需要更换不同频率的晶振(比如c51单片机,用11.0592M的晶振,很适合产生串

口时钟,而12M晶振很方便计算定时器的时间),使用插接式比较方便。 51单片机12M和11.0592M晶振定时器初值计算 2011-01-04 22:25 at89s52,晶振频率12m 其程序如下: 引用代码:#include #include void timer0_init() { TMOD=0x01;//方式1 TL0=0xb0; TH0=0x3c; TR0=1; ET0=1; } void timer0_ISR(void) interrupt 1 { TL0=0xb0; TH0=0x3c;//50ms中断一次 single++; if(single==20) { kk++; single=0; } } void main() { int kk=0;//计数器 int single=0; timer0_init(); } TL0=0xb0; TH0=0x3c; 这两个是怎么算出来得

linux内核定时器详解及实例

Linux内核定时器详解 80X86体系结构上,常用的定时器电路 实时时钟(RTC) RTC内核通过IRQ8上发出周期性的中断,频率在2-8192HZ之间,掉电后依然工作,内核通过访问0x70和0x71 I/O端口访问RTC。 时间戳计时器(TSC) 利用CLK输入引线,接收外部振荡器的时钟信号,该计算器是利用64位的时间戳计时器寄存器来实现额,与可编程间隔定时器传递来的时间测量相比,更为精确。 可编程间隔定时器(PIT) PIT的作用类似于微波炉的闹钟,PIT永远以内核确定的固定频率发出中断,但频率不算高。 CPU本地定时器 利用PIC或者APIC总线的时钟计算。 高精度时间定时器(HPET) 功能比较强大,家机很少用,也不去记了。 ACPI电源管理定时器 它的时钟信号拥有大约为3.58MHZ的固定频率,该设备实际上是一个简单的计数器,为了读取计算器的值,内核需要访问某个I/O端口,需要初始化 定时器的数据结构 利用timer_opts描述定时器 Timer_opts的数据结构 Name :标志定时器员的一个字符串 Mark_offset :记录上一个节拍开始所经过的时间,由时钟中断处理程序调用 Get_offset 返回自上一个节拍开始所经过的时间

Monotonic_clock :返回自内核初始化开始所经过的纳秒数 Delay:等待制定数目的“循环” 定时插补 就好像我们要为1小时35分34秒进行定时,我们不可能用秒表去统计,肯定先使用计算时的表,再用计算分的,最后才用秒表,在80x86架构的定时器也会使用各种定时器去进行定时插补,我们可以通过cur_timer指针来实现。 单处理器系统上的计时体系结构 所有与定时有关的活动都是由IRQ线0上的可编程间隔定时器的中断触发。 初始化阶段 1. 初始化间,time_init()函数被调用来建立计时体系结构 2. 初始化xtime变量(xtime变量存放当前时间和日期,它是一个timespec 类型的数据结构) 3. 初始化wall_to_monotonic变量,它跟xtime是同一类型的,但它存放将加在xtime上的描述和纳秒数,这样即使突发改变xtime也不会受到影响。 4. 看是否支持高精度计时器HPET 5. 调用select_timer()挑选系统中可利用的最好的定时资源,并让 cur_timer变量指向该定时器 6. 调用setup_irq(0,&irq0)来创建与IRQ相应的中断门。 时钟中断处理程序 1. 在xtime_lock顺序锁产生一个write_seqlock()来保护与定时相关的内核变量,这样防止中断让该进程被阻止。 2. 执行cur_timer定时器对象的mark_offset方法(记录上一个节拍开始所经过的时间,由时钟中断处理程序调用) 3. 调用do_timer_interrupt函数,步骤为 a) 使jiffies_64值增1 b) 调用updata_times()函数来更新系统日期和时间。

定时器定时时间的计算(SystemCoreClock与OS_TICKS_PER_SEC的关系)

定时器定时时间的计算(SystemCoreClock与OS_TICKS_PER_SEC的关系) 定时器定时时间的计算 xcj 2015/06/03 09:23 假设定时器的时钟频率为f,f已知。那么定时器每计数一次所用时间为1/f。1/f代表了定时器的定时的时间精度(或最小计时单位)。 往计数器写的初值为Ticks,就是经过Ticks个周期后,定时器值变为0,定时时间到了。 如果我们要定时的时间为T,那么计算公式为: T = ticks * (1/f) (1) 整理后可得 ticks = f * T (2) 举个例子,假如定时器的时钟为SystemCoreClock,要定时1mS。 那么 ticks = SystemCoreClock * 1mS =SystemCoreClock * 1 * 10^(-3)=SystemCoreClock/1000 换个思路,如果已知定时器的时钟频率为f,要用定时器产生一个频率为f1的定时中断(T=1/f1)。根据公式(2)有 ticks = f /f1 (3) 上面的式子中 f1

定时器产品使用说明书

定时器产品使用说明书 定时设置: 1、先检查时钟是否与当前时间一致,如需重新校准,在按住“时钟”键的同时,分别按住“星期”、“小时”、“分钟”键,将时钟调到当前准确时间。 2、按一下“设定”键,显示屏左下方出现“1开”字样(表示第一次开启的时间)。然后按“星期”调整本次设定的星期组合模式,再按“小时”、“分钟”键,输入所需开启的时间。 3、再按一下“设定”键,显示屏左下方出现“1关”字样(表示第一次关闭时间),再按“星期”、“小时”、“分钟”键,输入所需关闭的日期和时间。 4、继续按动“设定”键,显示屏左下方将依次显示“2开、2关、3开、3关……16开、16关”,参考步骤2、3设置以后各次开关时间。设置完成后,按一下“时钟”键返回。 5、如果每天不需设置16组开关,则必须按“清除”键,将多余各组消除,使其显示屏上显示“—:—”图样(不是00:00)。 6、按“模式”键,可以变换工作模式。总共有四种工作模式:A、液晶显示开(代表进入常开模式);B、液晶显示关(代表进入常关模式);C、由开进入自动(表示目前状态为开,等到下一组时间到后开始自动运行);D、由关进入自动(表示目前状态为关,等到下一组定时时间到后开始自动运行)。 当出现以下情况时: 1、定时器没有根据设定的程序开启或关闭,请检查设置程序是否正确或重新调整。 2、定时器长时间不用,显示模糊时,请将定时器接通电源充足,10分钟后无显示,按“复位”键,2-3秒。 3、如以上步骤均不能排除问题,请与公司或经销商联系维修。 注意事项: 1、对于那些因定时开关出错而可能发生的生命相关事故或者对社会产生重大影响的设备(如医疗设备等),请不要使用定时开关。 2、对于那些因定时开关出错而发生重大财产损失的设备(大型加热器或冷库),在使用本定时开关时,请务必是特性和性能的数值有足够的余量,并采取二重电路等安全对策。 3、请勿自行修理、分解或改造。 4、接通电源后请勿接触端子部分。本开关工作在无潮湿、腐蚀及高金属含量气体环境中。请勿沾染油或水。

ATMEGA16定时器的使用

ATMEGA16定时器的使用 [日期:2012-01-07 ] [来源:本站编辑作者:佚名] [字体:大中小] (投递新闻) /* 本程序简单的示范了如何使用ATMEGA16的定时器 AVR定时器的要点介绍 T0工作于CTC模式,输出1KHz/2KHz 50%占空比的方波 T1工作于快速PWM模式兼输入捕捉 T2工作于相位修正PWM模式,输出490Hz的8bit PWM波 出于简化程序考虑,各种数据没有对外输出,学习时建议使用JTAG ICE硬件仿真器对于定时器,AVRstudio的软件仿真是不准确的。 */ #include #include #include //时钟定为8MHz,F_CPU=8000000 //管脚定义 #define ICPKEY 6 //ICP1 PD6 按键模拟ICP输入 #define PWM0 3 //OC0 PB3 #define PWM1A 5 //OC1A PD5 #define PWM1B 4 //OC1B PD4 #define PWM2 7 //OC2 PD7 //宏定义 #define PWM1A_ON() PORTD|= (1<

STM32定时时间的计算

STM32 定时器定时时间的计算 假设系统时钟是72Mhz,TIM1 是由PCLK2 (72MHz)得到,TIM2-7是由 PCLK1 得到关键是设定时钟预分频数,自动重装载寄存器周期的值/*每1秒发生一次更新事件(进入中断服务程序)。RCC_Configuration()的SystemInit()的 RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV2表明TIM3CLK为72MHz。因此,每次进入中断服务程序间隔时间为: ((1+TIM_Prescaler )/72M)*(1+TIM_Period )=((1+7199)/72M)*(1+9999)=1秒。定时器的基本设置如下: 1、TIM_TimeBaseStructure.TIM_Prescaler = 7199;//时钟预分频数例如:时钟频率=72/(时钟预分频+1)。 2、TIM_TimeBaseStructure.TIM_Period = 9999; // 自动重装载寄存器周期的值(定时时间)累计 0xFFFF个频率后产生个更新或者中断(也是说定时时间到)。 3、TIM_TimeBaseStructure.TIM_CounterMode=TIM1_CounterMode_Up; //定时器模式向上计数。 4、 TIM_TimeBaseStructure.TIM_ClockDivision = 0x0; //时间分割值。 5、 TIM_TimeBaseInit(TIM2, &TIM_TimeBaseStructure);//初始化定时器2。 6、 TIM_ITConfig(TIM2, TIM_IT_Update, ENABLE); //打开中断溢出中断。 7、 TIM_Cmd(TIM2, ENABLE);//打开定时器或者: TIM_TimeBaseStructure.TIM_Prescaler = 35999;//分频35999,72M/ (35999+1)/2=1Hz 1秒中断溢出一次。 8、 TIM_TimeBaseStructure.TIM_Period = 2000; //计数值2000 ((1+TIM_Prescaler )/72M)*(1+TIM_Period )=((1+35999)/72M)*(1+2000)=1秒。 9、注意使用不同定时器时,要注意对应的时钟频率。例如TIM2对应的是APB1,而TIM1对应的是APB2 通用定时器实现简单定时功能 以TIME3为例作为说明,简单定时器的配置如下: void TIM3_Config(void) { TIM_TimeBaseInitTypeDefTIM_TimeBaseStructure; TIM_DeInit(TIM3); //复位TIM2定时器 /* TIM2 clock enable [TIM2定时器允许]*/ RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3, ENABLE); /* TIM2 configuration */ TIM_TimeBaseStructure.TIM_Period = 49; // 0.05s定时 TIM_TimeBaseStructure.TIM_Prescaler = 35999; // 分频36000 TIM_TimeBaseStructure.TIM_ClockDivision = TIM_CKD_DIV1; // 时钟分割TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //计数方向向上计数 TIM_TimeBaseInit(TIM3, &TIM_TimeBaseStructure); /* Clear TIM2 update pending flag[清除TIM2溢出中断标志] */

51单片机定时器初值的计算

51单片机定时器初值的计算一。10MS定时器初值的计算: 1.晶振12M 12MHz除12为1MHz,也就是说一秒=1000000次机器周期。10ms=10000次机器周期。 65536-10000=55536(d8f0) TH0=0xd8,TL0=0xf0 2.晶振11.0592M 11.0592MHz除12为921600Hz,就是一秒921600次机器周期,10ms=9216次机器周期。 65536-9216=56320(dc00) TH0=0xdc,TL0=0x00 二。50MS定时器初值的计算: 1.晶振12M 12MHz除12为1MHz,也就是说一秒=1000000次机器周期。50ms=50000次机器周期。 65536-50000=15536(3cb0) TH0=0x3c,TL0=0xb0 2.晶振11.0592M 11.0592MHz除12为921600Hz,就是一秒921600次机器周期,50ms=46080次机器周期。 65536-46080=19456(4c00)

TH0=0x4c,TL0=0x00 三。使用说明 以12M晶振为例:每秒钟可以执行1000000次机器周期个机器周期。而T 每次溢出 最多65536 个机器周期。我们尽量应该让溢出中断的次数最少(如50ms),这样对主程序的干扰也就最小。 开发的时候可能会根据需要更换不同频率的晶振(比如c51单片机,用11.0592M的晶振,很适合产生串口时钟,而12M晶振很方便计算定时器的时间),使用插接式比较方便。 对12MHz 1个机器周期1us 12/fosc = 1us 方式0 13位定时器最大时间间隔 = 2^13 = 8.192ms 方式1 16位定时器最大时间间隔 = 2^16 = 65.536ms 方式2 8位定时器最大时间间隔 = 2^8 = 0.256ms =256 us 定时5ms,计算计时器初值 M = 2^K-X*Fosc/12 12MHz 方式0: K=13,X=5ms,Fosc=12MHz 则M = 2^13 - 5*10^(-3)*12*10^6/12= 3192 = 0x0C78 THx = 0CH,TLx = 78H, 方式1: K=16,X=5ms,Fosc=12MHz 则M = 2^16 - 5*10^(-3)*12*10^6/12= 60536 = 0xEC78 THx = ECH,TLx = 78H,

定时器-计数器

定时器 / 计数器 一、实验目的 ⒈学会8253芯片和微机接口的原理和方法。 ⒉. 掌握8253定时器/计数器的工作方式和编程原理。 二、实验内容 利用8253进行二次分频,控制LED灯亮10秒,灭10秒。 三、实验程序清单(在H8253.ASM的基础上修改) CODE SEGMENT ;H8253.ASM ASSUME CS: CODE ORG 1290H START: JMP TCONT TCONTRO EQU 0043H TCON0 EQU 0040H TCON1 EQU 0041H TCONT: MOV DX,TCONTRO MOV AL,36H ;0号通道控制字需要修改 OUT DX,AL MOV DX,TCON0 ;计数初值要按计算出的值来写 MOV AL,00H OUT DX,AL MOV AL,04H OUT DX,AL MOV DX,TCONTRO MOV AL,36H ;1号通道控制字需要修改 OUT DX,AL MOV DX,TCON1 MOV AL,00H ;计数初值要按计算出的值来写 OUT DX,AL MOV AL,02H OUT DX,AL JMP $ CODE ENDS END START

四、实验步骤 ⒈8253的GATE0、GATE1接+5V,OUT0接CLK1,CLK1接LED灯(L1)。 8253的CLK0插孔接分频器74LS393(左下方)的T2插孔,分频器的频 率源为8.0MHZ,T→8.0MHZ。 ⒉运行实验程序 在系统提示符“P.”状态下,联机运行程序 3. 观察实验现象,修改程序中的计数初始值,观察结果。

定时器Timer实时修改时间间隔(周期)

1.定时器Timer当时间间隔(周期)变化时,实时去修改 我项目中主要是实现在某个时间段上午8:00-12:00,下午 2:00(pm_start)-19:00(pm_end),每隔3分钟(pm_time)(可以手动设置)自动上传当前的位置(google的定位) // 执行定时任务 privateboolean bool= true;// true表示服务器与本地数据相同,false表示服务器与本地数据不相同 privatevoid start_schedule_pm() { final Timer timer = new Timer(); timerTask = new TimerTask() { @Override publicvoid run() { //当不相同时取消timer重新new一个timer if (!bool) { if (timer != null) { Log.e("%%%%", bool + ""); timerTask.cancel(); timer.cancel(); start_schedule_pm(); bool = true;

return; } } if ((getCurrentTime() - 12) >= Double.valueOf(pm_end)) { timerTask.cancel(); timer.cancel(); //我的是在android service里跑的程序,所以关闭了service stopSelf(); return; } if (!AppUtils.checkNet(getApplicationContext())) { Log.d("data", "网络未连接"); return; } Log.d("data", "新任务开始");

定时器T的用法

第九讲定时器T2的用法 定时器 声明,定时器T2只有52以上的芯片才有,51没有的。

捕捉模式 在捕捉模式时,两种操作模式由T2CON中的EXEN2位选择。如果EXEN2=0,Timer2作为一个16位向上定时或计数器,当溢出时将T2CON中的TF2置1。这个标志位可以产生一个中断。如果EXEN2=1,Timer2起同样的作用,但是,外部输入端T2EX上的下降延也可以使TH2和TL2中的值捕捉到RCAP2H和RCAP2L中,另外,T2EX上的下降延可以将EXF2置1,像TF2一样,也可以产生一个中断。捕捉模式详见图5。 自动重载模式

Timer2在指定为16为自动重载模式时可以编程为加计数或减计数,此功能由T2MOD 中的DCEN位决定。DCEN=0,计数器向上计数,默认置为0,DCEN=1时,Timer2的加或减由T2EX的值决定。 图6显示Timer2在DCEN=0时自动向上计数。在这个模式时,T2CON的EXEN2为可以选择两种操作。EXEN2=0,Timer2向上计数到0FFFFH时将TF2为置1,溢出可以把RCAP2H和RCAP2L 中的16为值重新加载到定时寄存器中。捕捉模式时RCAP2H和RCAP2L中的值由软件预先设定。EXEN2=1,既可以由溢出重载也可以由T2EX引脚的下降延触发重载。TF2和EXF2都可以产生中断。设置DCEN为可以时Timer2向上或向下计数,如图6所示,此模式下,T2EX 脚控制计数方向。T2EX如果为1,Timer2向上计数。计数器到0FFFFH时溢出并将TF2置1。溢出可以使RCAP2H和RCAP2L中的16为值重新加载到定时寄存器中。T2EX如果为0,Timer2向下计数,当TH2和TL2中的值和RCAP2H和RCAP2L相等时向下溢出。溢出使TF2置1并 将0FFFFH重新加载到计时寄存器中。

关于定时器初值的设定

深入理解需要精通定时器溢出原理: 晶振时钟12分频后得到机器时钟,定时器启动后会按机器时钟进位,16bit模式,定时器溢出频率就是机器时钟除以定时器多余“空间”, 例如定时器初值是0xffff,则每1个机器时钟都会溢出,产生中断 例如定时器初值是0xfffe,则每2个机器时钟会溢出 …… 例如定时器初值是【65535(0xffff)-999】,则每1000个机器时钟会溢出,或 例如定时器初值是【65536-1000】,则每1000个机器时钟会溢出 …… 依次类推 实例 例如:设T0工作方式1定时,定时时间为2ms,在P1.0引脚上输出周期为4ms的方波,设单片机的晶振频率为12MHz。 解:要在P1.0输出周期为4ms的方波,即要使P1.0每隔2ms取反1次。 T0方式1定时,则T0的方式字为:TMOD=01H 计算2ms定时T0的初值: 12M晶振,机器周期为1M,2ms就是X个机器周期 X=T(2ms)/T0(1s/(12M/12))=0.002/1/1000000=2000 定时器初值就是65536-X=65536-2000=63536=F830H 其中将高8位F8H赋给TH0,低8位30H赋给TL0。 采用查询方法,编程如下: 1. https://www.doczj.com/doc/6817679595.html, 0000H 3.AJMP MAIN 4. https://www.doczj.com/doc/6817679595.html,O 0100H 6.MAIN: MOV TMOD,#01H 7.MOV TL0,#30H 8.MOV TH0,0F8H 9.SETB TR0 10.LOOP: JBC TF0,NEXT 11.SJMP LOOP 12.NEXT: MOV TL0,#30H 13.MOV TH0,#0F8H 14.CPL P1.0 15.SJMP LOOP 复制代码 采用中断的方法,编程如下: https://www.doczj.com/doc/6817679595.html, 0000H 2.AJMP MAIN

VC中使用定时器的方法

1.启用一个定时器直接调用函数: SetTimer(1,500,NULL);//定义时钟1,时间间隔为500ms SetTimer(2,1000,NULL);//定义时钟2,时间间隔为1000ms 可以在按钮按下时启用定时器: void CTimeDlg::OnButton1() { // TODO: Add your control notification handler code here SetTimer(1,500,NULL);//定义时钟1,时间间隔为500ms SetTimer(2,1000,NULL);//定义时钟2,时间间隔为1000ms } 2.关闭定时器:可以在按钮中调用如下函数关闭某定时器: void CTimeDlg::OnButton2() { // TODO: Add your control notification handler code here KillTimer(1); //关闭1号定时器 KillTimer(2); //关闭2号定时器 } 3.添加定时器时间到的处理代码: 1)在开发界面中Ctrl+W 进入MFCclass wizard页面2)选择Message Maps选项卡 3)在Project中选择你的工程 4)在object Ids:中选择C…..Dlg

5)在Messages:中选择WM_TIMER,此时,Member functions中自动定位到: W OnTimer ON_WM_TIMER, 6) 单击EDIT code(或双击W OnTimer ON_WM_TIMER)自动进入如下函数:void CTimeDlg::OnTimer(UINT nIDEvent) { // TODO: Add your message handler code here and/or call default switch(nIDEvent) { case 1: //1号定时器应该处理的事情 //….. break; case 2: //2号定时器应该处理的事情 //….. break; } CDialog::OnTimer(nIDEvent); //此句VC自动生成 }

89C51单片机定时器所定时间的计算以及写法

89C51单片机定时器时间的计算以及写法 今晚学单片机的时候,有一点儿问题,就去网上看了看,发现了很多人不会单片机定时,也就是具体时间的设定,不知道如何设定,而且有关方面的书籍、资料讲解又太过术语化,所以就写一篇通俗些的语言讲述一下如何定时。 为了便于理解,先讲解一点儿关于单片机内部定时器和计数器的基本知识,如果学过数字电路,就不用管这些,看下边的就好了: (1)由于单片机内部定时器、计数器均为八位,所以它们从0开始到计数计满,也就是能从0000 0000计数到1111 1111,即 2^0到2^16,转换成十进制,就是0——65536。 (2)外部的晶振电路提供的频率,到单片机内部,经过硬件电路,进行了12分频,不要问为什么,就这么记着就好了。比如外 部晶振是12MHZ的,那么到了单片机内部,用的频率就是 1MHz的。 89C51单片机常使用的晶振频率为12MHz和11.0592MHz两种,主要讲述这两种频率的,如果用其他的,只需要相应改变即可,下面分别讲述如何定时: (1)使用12MHz晶振: 单片机工作的频率f:12MHz/12=1MHz, 那么时钟周期T1:T1=1/f=1μs, 比如你要定时T2=50ms=50000μs,

你需要总时间T=T1 x T2=50000,也就是说你需要50000个周期才能走完你所要定的时间,当把数全都计满,是需要65536个周期,也就是说还有65536-50000=15536个周期没有走,那么,我们可以把这个初始值放到计数器里面,让它从15536开始计数,当计够50000个周期,也就计满了,即到达了65536。 就像水往水缸里流,你需要流满半缸水的时间,但是现在水缸是空的,你可以先把水缸灌半缸水,然后让它从半缸水开始流,当流满了的时候,也就到了你需要的那个时间。 然后,15536转成十六进制为:0x3CB0,将3C放到定时器的高8位,B0放到第8位,就完成了定时。 我们在写程序赋初始值的时候一般是这么写的,可以参考一下:TH0=0x3C; TL0=0xB0; 或者 TH0=(65536-50000)/256; TL0=(65536-50000)%256; PS:如果你定时是其他的,可以把根据我上边讲解的,把T=50000换成相应的数值即可。 (2)使用11.0592MHz晶振: 单片机工作的频率f:11.0592MHz/12=0.9216MHz, 那么时钟周期T1:T1=(1/0.9216)μs,

AVR定时器中断初值计算方法

AVR 定时器中断初值计算方法 使用芯片AT Mega16 外部晶振 定时器1 (16位定时器)寄存器TCCR1B = 0x04 设定256预分频 要利用定时器定时1秒 1,4000000 / 256 = 15625 说明定时器每 当1/15625 秒就会触发一次中断 2,65535 - 15625 = 49910 计算出要累加多少次才能在1秒后出发定时器1的溢出中断 3,49910 <==> C2 F6 将计算后的值换算成16进制 4,TCNT1H = 0xC2 ; 对寄存器赋值 TCNT1L = 0xF6 ; ================================================= 例如用16位定时器TIMER1,4MHZ晶振,256分频,100ms定时,如何求得初值赋给TCNT1 65536-(4M/256)*= 其中,4M是晶体频率,是定时时长单位秒。 对于8位的定时器

T=(2^8-计数初值)*晶振周期*分频数=(2^8-计数初值)/晶振频率*分频数计数初值=2^8-T/晶振周期/分频数=2^8-T*晶振频率/分频数 因为AVR一指令一周期 IAR For AVR 精确延时 C语言中,想使用精确的延时程序并不容易。IAR 中有这样的一个函数__delay_cycles(),该函数在头文件中定义,函数的作用就是延时N个指令周期。根据这个函数就可以实现精确的延时函数了(但不能做到100%精确度)。 实现的方法: 建立一个的头文件: #ifndef __IAR_DELAY_H #define __IAR_DELAY_H #include <> #define XTAL 8 //可定义为你所用的晶振频率(单位Mhz)#define delay_us(x) __delay_cycles ( (unsigned lon g)(x * XTAL) )

如何设定plc定时时间

如何设定PIc定时时间

作者: 日期: 2

如何设定pic定时时间 S7中定时时间由时基和定时值组成,定时时间为时基和定时时间设 定值的乘积。时基也称为定时器的计时单位,是定时器可以控制的最高精度(时间间隔)。定时时间也称为计时范围,是定时器的有效控制时间。 在定时器开始工作后,定时值不断递减,递减到零时,表示时间已到,定时器会有相应的动作。 所谓的时基是时间基准的简称。定时时间设值是以3位BCD码格式存放,位于定时器字的第0~11位。使用范围是0?999。表给出时基与相应的定时范围。 表时基与相应的定时范围

定时时间有两种表达方式: ①十六进制数。定时器使用的时间值为BCD码,给定时器赋值可以 带有时基格式。 格式为:W#16#vxyz。其中,w是时间基准,xyz是BCD码格式的时间值。设定值范围为1~999。这里,时基越小,贝y分辨率越高;时基越大,则分辨率越低,但定时时间越长。例如, 匱#1砾4?刖00 二0010001 IfHKMOKX) .1 0 0 时延I' 表示时基为1s,定时时间为300X 1 s的定时时间值,即300 s =5 min。 ②S5时间格式。也可以直接使用S5中的时间表示装入时间设定值, 其格式为: S5T#aH bM cS dMS 其中,a表示小时,b表示分钟,c表示秒,d表示毫秒。定时范围为 1MS-2H?46M H30S(1 ms~9990 s)。例如,S5T# 1H_13M_8S表示时 间为1 h13 min8 s。这里时基是由CPU自行选定的,原则是在满足

定时范围的要求下,时基单位根据设定时间值自动选择满足定时范围的最小时基。 ③设定时间的装载。S7-300/400的定时时间设定需要通过S7的装 载指令L进行。可以用两种方法设定时间与选择时间单位。允许设定的最大时间值为9990 s(2小时46分30秒)

定时器1使用总结

定时器 1 使用总结——溢出中断
1 目的说明
实现定时器最简单的溢出中断 实现定时器最简单的溢出中断,结合我手头的开发板,使得位于 P10 的 LED 灯,以 , 2HZ 的速度不断闪烁。这样的实验还是非常亲切的 这样的实验还是非常亲切的,让我想起了第一次在 51 上实现了这样的代 码,自己第一次在 CC2430 上实现 上实现,依然非常激动。
2
使用方法概述
需要使用定时器的中断, 需要知道如何操作才可以产生这个中断请求 需要知道如何操作才可以产生这个中断请求。 数据手册中提到 需要两个条件, 第一 IEN1.T1EN 需要置位 需要置位, 第二 TIMIF.OVFIM 需要置位。 代码中使用 modulo、 模式,使用该模式可以改变定时器溢出的频率 使用该模式可以改变定时器溢出的频率。
3
代码总览
先来看看所有的代码,然后再分 然后再分步解释。 //头文件 #include "hal.h" //函数声明 void Timer1_Init(); //主函数 void main(){ //初始化外部时钟 SET_MAIN_CLOCK_SOURCE(CRYSTAL); //P1_0 输出 IO_DIR_PORT_PIN(1,0,IO_OUT); //初始化定时器 1 Timer1_Init(); while(1){ }

} void Timer1_Init(){ //定时器 1 复位 TIMER1_INIT(); //设定定时器相关参数 //128 分频 0000 1100 T1CTL = 0x0c; //溢出值低 8 位 T1CC0L=0x24; //溢出值高 8 位 T1CC0H=0xF4; //定时器 T1 溢出中断使能 TIMER1_ENABLE_OVERFLOW_INT(TRUE); //定时器 T1 中断使能 INT_ENABLE(INUM_T1,INT_ON); //全局中断使能 INT_GLOBAL_ENABLE(INT_ON); //启动定时器 1 TIMER1_RUN(TRUE); } //定时器 1 中断函数 #pragma vector=T1_VECTOR __interrupt void Timer1_ISR(void) { //检查中断标志位 if(T1CTL & 0x10){ //LED 灯反转 P1_0 = !P1_0; //清中断标志 T1CTL &= ~0x10; } }
4 主函数说明
//初始化外部时钟 SET_MAIN_CLOCK_SOURCE(CRYSTAL); //P1_0 输出

相关主题
文本预览
相关文档 最新文档