0k6410定时器详细分析
看到一篇很好的博文,分析2410定时器中断的使用的,很详细,和大家分享一下
转载来源于http://www.cnblogs.com/Neddy/archive/2011/07/01/2095176.html
s3c2410提供了5个16位的Timer(Timer0~Timer4),其中Timer0~Timer3支持Pulse
Width Modulation—— PWM(脉宽调制 )。Timer4是一个内部定时器(internal timer),
PCLK是Timer的信号源,我们通过设置每个Timer相应的Prescaler和Clock
Divider把PCLK转换成输入时钟信号传送给各个Timer的逻辑控制单元(Control
Logic),事实上每个Timer都有一个称为输入时钟频率(Timer input clock
Frequency)的参数,这个频率就是通过PCLK,Prescaler和Clock Divider确定下来的,每个Timer
的逻辑控制单元就是以这个频率在工作。下面给出输入时钟频率的公式:
Timer input clock Frequency = PCLK / {prescaler value+1} /
{clock divider }
{prescaler value} = 0~255
{ clock divider } = 2, 4, 8, 16
然而并不是每一个Timer都有对应的Prescaler和Clock
Divider,从上面的原理图我们可以看到Timer0,Timer1共用一对Prescaler和Clock
Divider,Timer2,Timer3,Timer4共用另一对Prescaler和Clock
Divider,s3c2410的整个时钟系统模块只存在两对Prescaler和Clock Divider。
我曾经在讨论watchdog的文章中提到,watchdog也是一种定时器,他的工作就是在一个单位时间内对一个给定的数值进行递减和比较的操作,而我们这篇文章讨论的定时器他的工作内容和watchdog在本质上是一样的。定时器在一个工作周期(Timer
input clock cycle)内的具体工作内容主要有3个。分别是:
1. 对一个数值进行递减操作
2. 把递减后的数值和另一个数值进行比较操作
3. 产生中断或执行DMA操作
在启用Timer之前我们会对Timer进行一系列初始化操作,这些操作包括上面提到的设置Prescaler和Clock
Divider,其中还有一个非常重要的就是要给Timer两个数值,我们分别称之为Counter(变量,用于递减)和Comparer(定值,用于比较),Counter会被Timer
加载到COUNT BUFFER REGISTER(TCNTB),而Comparer会被Timer 加载到和COMPARE BUFFER
REGISTER(TCMPB),每个Timer都有这样两个寄存器。当我们设置完毕启动Timer之后,Timer在一个工作周期内所做的就是先把TCNTB中的数值(Counter)减1,之后把TCNTB中的数值和TCMPB中的数值(Comparer)进行对比,若Counter已经被递减到等于Comparer,发生计数超出,则Timer产生中断信号(或是执行DMA操作)并自动把Counter重新装入TCNTB(刷新TCNTB以重新进行递减)。以上就是Timer的工作原理。
下面我们结合代码具体说明如何对Timer0进行初始化并开启它。
首先我假设我的PCLK是50700000Hz
// define Timer register
#define rTCFG0 (*(volatile unsigned int *)0x51000000)
#define rTCFG1 (*(volatile unsigned int *)0x51000004)
#define rTCON (*(volatile unsigned int *)0x51000008)
#define rTCNTB0 (*(volatile unsigned int *)0x5100000C)
#define rTCMPB0 (*(volatile unsigned int *)0x51000010)
#define rTCNTO0 (*(volatile unsigned int *)0x51000014)
#define rTCNTB1 (*(volatile unsigned int *)0x51000018)
#define rTCMPB1 (*(volatile unsigned int *)0x5100001C)
#define rTCNTO1 (*(volatile unsigned int *)0x51000020)
#define rTCNTB2 (*(volatile unsigned int *)0x51000024)
#define rTCMPB2 (*(volatile unsigned int *)0x51000028)
#define rTCNTO2 (*(volatile unsigned int *)0x5100002C)
#define rTCNTB3 (*(volatile unsigned int *)0x51000030)
#define rTCMPB3 (*(volatile unsigned int *)0x51000034)
#define rTCNTO3 (*(volatile unsigned int *)0x51000038)
#define rTCNTB4 (*(volatile unsigned int *)0x5100003C)
#define rTCNTO4 (*(volatile unsigned int *)0x51000040)
void timer0_config()
{
rTCFG0=119
rTCFG1=3;
rTCNTB0=26406;
rTCMPB0=0;
}
由于我们的PCLK是50700000Hz, 根据Timer input clock
Frequency的计算公式我们如下计算Timer0的时钟输入频率:
prescaler value = 119
divider value = 1/16
PCLK= 50700000
Timer input clock Frequency =50700000/ (119+1)/(1/16)=26406
也就是说通过设置prescaler和divider
value之后,Timer0的工作频率为26406,也就是说一秒内Timer0会进行26406次递减和比较操作,假设我们现在是要让Timer0每1秒产生一次中断的话,我们应该设置Counter=26406和Camparer=0,既:
rTCNTB0=26406;
rTCMPB0=0;
如果我们要让Timer0每0.5秒产生一次中断,则我们应该设置Counter=26406/2和Camparer=0,既:
rTCNTB0=13203;
rTCMPB0=0;
如果我们要让Timer0每0.25秒产生一次中断,则我们应该设置Counter=26406/4和Camparer=0,既:
rTCNTB0=6601;
rTCMPB0=0;
初始化完Timer后我们要开启它。
void timer0_start()
{
rTCON|=1<<1;
rTCON=0x09;
}
附件:
0k6410定时器详细分析的更多相关文章
- 详细分析 Java 中实现多线程的方法有几种?(从本质上出发)
详细分析 Java 中实现多线程的方法有几种?(从本质上出发) 正确的说法(从本质上出发) 实现多线程的官方正确方法: 2 种. Oracle 官网的文档说明 方法小结 方法一: 实现 Runnabl ...
- ZIP压缩算法详细分析及解压实例解释
最近自己实现了一个ZIP压缩数据的解压程序,觉得有必要把ZIP压缩格式进行一下详细总结,数据压缩是一门通信原理和计算机科学都会涉及到的学科,在通信原理中,一般称为信源编码,在计算机科学里,一般称为数据 ...
- 1125MySQL Sending data导致查询很慢的问题详细分析
-- 问题1 tablename使用主键索引反而比idx_ref_id慢的原因EXPLAIN SELECT SQL_NO_CACHE COUNT(id) FROM dbname.tbname FORC ...
- LinkedList详细分析
一.源码解析1. LinkedList类定义2.LinkedList数据结构原理3.私有属性4.构造方法5.元素添加add()及原理6.删除数据remove()7.数据获取get()8.数据复制clo ...
- android ListView 九大重要属性详细分析、
android ListView 九大重要属性详细分析. 1.android ListView 一些重要属性详解,兄弟朋友可以参考一下. 首先是stackFromBottom属性,这只该属性之后你做好 ...
- C语言中的static 详细分析
转自:http://blog.csdn.net/keyeagle/article/details/6708077/ google了近三页的关于C语言中static的内容,发现可用的信息很少,要么长篇大 ...
- Linux内核OOM机制的详细分析(转)
Linux 内核 有个机制叫OOM killer(Out-Of-Memory killer),该机制会监控那些占用内存过大,尤其是瞬间很快消耗大量内存的进程,为了 防止内存耗尽而内核会把该进程杀掉.典 ...
- iOS开发——实用OC篇&多种定时器详细介绍
多种定时器详细介绍 在软件开发过程中,我们常常需要在某个时间后执行某个方法,或者是按照某个周期一直执行某个方法.在这个时候,我们就需要用到定时器. 然而,在iOS中有很多方法完成以上的任务,到底有 ...
- Android-Native-Server 启动和注册详细分析
Android-Native-Server 启动和注册详细分析 以mediaService为实例来讲解: mediaService的启动入口 是一个 传统的 main()函数 源码位置E:\ ...
随机推荐
- TeamTalk源码分析(十) —— 开放一个TeamTalk测试服务器地址和几个测试账号
由于TeamTalk是用于企业内部的即时通讯软件,一般客户端并不提供账号注册功能.如果你仅对TeamTalk的客户端感兴趣,你可以仅仅研究pc端和移动端代码.官方的测试服务器地址已经失效,所以我已经部 ...
- 原生js面向对象写法
Mouse就是一个类,有自己的成员变量和成员方法,成员方法一定加上prototype,避免js原型的坑. var Mouse = function(id) { this.id = id; this.n ...
- Consul做服务发现
使用Consul做服务发现的若干姿势 https://www.cnblogs.com/bossma/p/9756809.html 从2016年起就开始接触Consul,使用的主要目的就是做服务发现,后 ...
- 【spring源码学习】spring的IOC容器在初始化bean过程
[一]初始化IOC的bean的时候Spring会执行的一些回调方法 (1)spring bean创建的前置处理 =>ApplicationContextAwareProcessor 在创建bea ...
- #51单片机#超声波测距(HC-SR04)的使用方法
#51单片机#超声波测距(HC-SR04)的使用方法
- 为什么新生代内存需要有两个Survivor区?
对于常见的GC算法,我们都应该知道,例如:标记清除算法.复制算法.标记整理算法等.标记清除算法由于回收之后存在大量的内存碎片,存在效率和空间问题!为了解决效率问题,引出了复制算法!熟悉GC算法的小伙伴 ...
- 【android】Socket简单用法
Socket通常也称做”套接字“,用于描述IP地址和端口,废话不多说,它就是网络通信过程中端点的抽象表示.值得一提的是,Java在包java.net中提供了两个类Socket和ServerSocket ...
- Java 传递可变参数和方法重载
形式:类型... 参数名 示例:public void show(int... a) {}; 可变参数在方法中被当作数组来处理 可变参数传值的四种方式: 一个值也不传,可变参数会接收到长度为0的数组 ...
- css3作3D旋转视频展示
代码如下: <!doctype html> <html lang="en"> <head> <meta charset="UTF ...
- php redis 命令合集
1.https://www.cnblogs.com/aipiaoborensheng/p/5666005.html 2.https://www.cnblogs.com/doanddo/p/734908 ...