中断技术基本时钟和定时器Word格式.docx
- 文档编号:22516048
- 上传时间:2023-02-04
- 格式:DOCX
- 页数:28
- 大小:346.27KB
中断技术基本时钟和定时器Word格式.docx
《中断技术基本时钟和定时器Word格式.docx》由会员分享,可在线阅读,更多相关《中断技术基本时钟和定时器Word格式.docx(28页珍藏版)》请在冰豆网上搜索。
P2SEL2&
P2OUT|=BIT5;
P2REN|=BIT5;
P2DIR&
P2IES|=BIT5;
P2IFG&
P2IE|=BIT5;
另外#pragmavector=PORT1_VECTOR需要修改为:
#pragmavector=PORT2_VECTOR;
中断子程中的清零指令修改为:
P2IFG&
在硬件连接上需要将P2.5连接至KEY6。
即可实现程序的修改。
2.中断程序编程练习
(1)程序设计思路
当程序中没有收到中断请求时,L5灯循环闪烁,该功能可以由main函数中的循环实现,即设置某引脚为输出引脚,并控制L5,则实现L5的循环闪烁则很容易实现。
要求中中断源有两个,P1.2和P1.7均可以触发中断。
由于P1.2和P1.7两个引脚共享一个中断类型号,所以两个引脚的关于中断的设置相同,但是在中断子程中需要对两个中断进行判断,使得两个中断对应执行不同的指令。
(2)硬件连接图
(3)C语言程序
#include"
io430.h"
in430.h"
voiddelay()//延时子函数
{unsignedintj;
for(j=0;
j<
0xffff;
j++);
}
voidblink1()//LED5闪烁控制子函数
{P2OUT&
=~BIT4;
delay();
P2OUT|=BIT4;
voidblink2()//LED2闪烁控制子函数
{
for(inti=0;
i<
2;
i++)
{
P2OUT&
=~BIT1;
P2OUT|=BIT1;
};
voidBuzz()//蜂鸣器控制子函数
{
=~BIT2;
P2OUT|=BIT2;
intmain(void)
//Stopwatchdogtimertopreventtimeoutreset
WDTCTL=WDTPW+WDTHOLD;
//****输出端口设置***//
P2SEL&
=~(BIT4+BIT1+BIT2);
P2SEL2&
P2DIR|=(BIT4+BIT1+BIT2);
P2OUT|=(BIT4+BIT1+BIT2);
//****中断相关设置****//
P1SEL&
=~(BIT2+BIT7);
P1SEL2&
//设置GPIO类型
P1DIR&
//设置两个引脚为输入引脚
P1REN|=(BIT2+BIT7);
//上拉/下拉电阻允许
P1OUT|=(BIT7+BIT2);
//上拉电阻
P1IES|=(BIT2+BIT7);
//下降沿触发
P1IFG&
//清零中断标志位
P1IE|=(BIT2+BIT7);
//中断分控允许
_EINT();
//中断总控允许
for(;
;
)
{blink1();
};
//LED5循环闪烁
#pragmavector=PORT1_VECTOR
__interruptvoidport_1()//中断子程
if((P1IFG&
BIT2)!
=0)//如果是P1.2产生的中断,执行下面的内容
{Buzz();
if((P1IFG&
BIT7)!
=0)//如果是P1.7产生的中断
{blink2();
=~BIT7;
}
(3)思考题
1)如果将按键K2,K7分别接在P2.1和P2.6上时,此时的中断向量应该变为了P2.0~P2.7八个端口。
首先需要将上面程序main函数中的中断相关的设置改为下面:
//****中断相关设置****//
=~(BIT1+BIT6);
P2DIR&
P2REN|=(BIT1+BIT6);
P2OUT|=(BIT6+BIT1);
P2IES|=(BIT1+BIT6);
P2IFG&
P2IE|=(BIT1+BIT6);
另外由于在上面的程序中用P2.1来控制LED2的闪烁,所以需要将控制LED2的闪烁的引脚改为P2.3。
中断子程也应该进行相关的修改,如下所示:
#pragmavector=PORT2_VECTOR
__interruptvoidport_2()//中断子程
if((P2IFG&
BIT1)!
if((P2IFG&
BIT6)!
=~BIT6;
2)如果按键K2,K7分别接在P1.0和P2.4上,此时中断会用到P1.0~P1.7和P2.0~P2.1两个中断源。
在进行程序修改时,也是应该对中断相关端口的设置和中断子程进行相关的修改。
修改如下所示:
对于中断相关端口的设置:
=~BIT0;
P1REN|=BIT0;
P1OUT|=BIT0;
P1IES|=BIT0;
P1IE|=BIT0;
P2REN|=BIT4;
P2OUT|=BIT4;
P2IES|=BIT4;
P2IE|=BIT4;
中断子程的修改如下:
#pragmavector=PORT1_VECTOR
__interruptvoidport_1()//中断子程1
Buzz();
P1IFG&
__interruptvoidport_2()//中断子程2
blink2();
另外由于原程序中用P2.4来控制LED5的闪烁,所以与这里中断中用到的引脚冲突,所以可以利用P2.5来控制LED5,即将原P2.4对应程序改为P2.5即可。
3.采用事件标志处理中断
(1)功能描述:
在将P1.4和某一按键相连,P1.6与蜂鸣器相连的情况下,两个程序实现的功能是相同的,都是在没有按键的情况下程序不执行任何指令,在按下键时产生中断,蜂鸣器发出一声警报声。
(2)两者在编程实现上的不同:
程序L7_intA对于蜂鸣器控制的指令在中断子程中,即在按键时,执行中断子程,使蜂鸣器发出一声警报,然后跳出中断子程继续执行空的循环。
而在程序L7_intB中,多了一个标志变量flag,在不执行中断子程中flag一直为0,虽然在main函数循环中存在对蜂鸣器引脚操作的指令,但是由于flag为0,所以不执行。
当按键时,执行中断子程,在中断子程中只是将flag变量置位,然后跳出中断子程,由于此时flag为1,所以蜂鸣器会发出一声警报之后,flag又被置零。
所以两个程序实现的功能是相同的,但是L7_intB中中断子程的执行时间较L7_intA短很多。
(3)对任务二的程序进行改编,如下所示:
voiddelay()
voidblink1()
voidblink2()
voidBuzz()
intflag1=0;
intflag2=0;
if(flag1==0&
&
flag2==0)
if(flag1!
=0)
{Buzz();
flag1=0;
if(flag2!
flag2=0;
__interruptvoidport_1()
=0)
{flag1=1;
{flag2=1;
4.(提高)按键抖动处理
(1)延时函数应该加在按键中断程序的最后,因为若延时加在中断程序的开始,则在执行中断时对有效指令的执行也会产生相同的延时。
将延时放在中断中的最后,则当产生按键下降延时,立即执行中断的内容,但是由于在中断程序最后加上了延时,在这段延时中产生的抖动不会再次触发中断,达到防抖的目的。
对中断程序的修改如下所示:
#pragmavector=PORT1_VECTOR
__interruptvoidport_int(void)
{unsignedinti;
{number++;
P2OUT=~number;
}
P1IFG&
for(i=0;
0xfff;
i++);
//延时环节
(2)延时函数不能加的太短,加的太短不能有效地去除抖动的影响;
同时也不能加的太长,否则会影响下一次按键,经过查阅资料得知毛刺一般时间为毫秒级,故选择计数到“0xfff”即延时了大约两毫秒。
(3)经过查找发现,防抖用的最多的方法就是延时,另外还有用对于按键连续检测的方法实现防抖的,其大致思路是当按键下降沿进入中断子程中,先对按键的装态连续检测几次,若这几次的按键状态相同则说明不是抖动。
据此,编写的中断子程如下所示:
{unsignedinti;
unsignedintcount=0;
//按键检测计数
8;
i++)//连续检测八次
if((P1IN&
BIT2)==0)
{count++;
}//若检测到按键均按下则count等于8
if(((P1IFG&
=0)&
(count==8))
count=0;
1.了解MSP430G2553基本时钟模块的工作原理,掌握其控制方法;
2.了解MSP430定时器A的工作原理,掌握MSP430定时器A的控制方法。
1.数字示波器的使用
(1)将信号源波形在示波器上显示出来,掌握测量周期、频率、峰峰值的方法;
(2)用导线将实验板上的地信号与示波器地信号相连,测量实验板上的Vcc电源信号是否正常;
用示波器观察到Vcc信号为3.6V直流信号,故正常。
2.测试上电复位系统的ACLK和SMCLK的时钟频率
实验编程分别用P1.0和P1.4将ACLK和SMCLK输出并使用示波器观察,编程如下所示:
P1SEL|=BIT0;
P1DIR|=BIT0;
//P1.0输出ACLK
P1SEL|=BIT4;
P1DIR|=BIT4;
//P1.4输出SMCLK
【思考题】
(1)将JP8中的两个插针接到32.768KHZ晶振侧测得的ACLK为32.768KHZ,当将两个插针接到P2.6和P2.7侧时,得不到ACLK的信号,这是因为当接到P2.6和P2.7时,并没有将端口连接到晶振处,所以不能输出。
(2)通过测量得到结果如下表所示:
DIVAxx与ACLK的关系
DIVA1
DIVA0
ACLK频率值/KHz
作用
1
16.393
二分频
4.086
八分频
可见DIVAxx用来控制ALCK输出的频率,其主要通过分频来实现,DIVA1,DIVA0分别为“00,01,10,11”时分别对应1,2,4,8分频。
DIVSxx与SMCLK的关系
DIVS1
DIVS0
SMCLK频率值/KHz
274.7
四分频
137.55
可见DIVSxx用来控制SMLCK输出的频率,其主要通过分频来实现,DIVS1,DIVS0分别为“00,01,10,11”时分别对应1,2,4,8分频。
LFXT1Sxx和ACLK的关系
LFXT1S1
LFXT1S0
时钟来源
32.768
晶振
10.219
内部振荡器
(3)经示波器测试,上电复位之后,CPU工作的时钟信号MCLK的频率为1MHz。
3.掌握基本时钟模块的编程控制
(1)ACLK=16.384KHz;
(时钟源外部晶振二分频)
在上电复位情况下,ACLK接外部晶振,所以只需将外部晶振进行二分频即可,所以编程如下所示:
BCSCTL1|=DIVA0;
BCSCTL1&
=~DIVA1;
//二分频
将ACLK通过P1.0输出并用示波器进行观察,得到的ACLK波形如下所示,由示波器测得的ACLK频率为16.385KHz,即实现了二分频。
(2)ACLK=1.5KHz;
(时钟源VCLOCK八分频,即12KHz/8)
编程如下:
BCSCTL1|=DIVA0;
BCSCTL1|=DIVA1;
//八分频
BCSCTL3|=LFXT1S1;
BCSCTL3&
=~LFXT1S0;
通过示波器观察得到的结果如下:
由于受各种因素的影响,单品机上的外部晶振其频率并不是12KHz,而是10.1KHz,所以最终分频得到的频率不是1.5KHZ,而是1.274KHZ。
思考题:
可否通过对时钟模块进行编程在引脚P2.4上输出ACLK?
为什么?
不可以,因为输出引脚已经由硬件确定了,没有时钟输出功能的引脚不能够通过编程实现时钟的输出。
4.DCO出厂校验值的频率检验
(1)利用出厂校验值,编程使DCO分别为1MHZ、16MHZ,通过P1.4输出,并用示波器测量实际值。
//P1.4输出DCOCLK
if(CALBC1_1MHZ!
=0xff)//利用出厂校验值1MHZ
BCSCTL1=CALBC1_1MHZ;
DCOCTL=CALDCO_1MHZ;
通过示波器得到的两个校验值对应输出的实测值如下所示:
可见校验值1MHZ对应的实测值为993.5KHZ,校验值16MHZ对应的实测值是16.3MHZ,即校验值和实测值之间存在一定的误差。
(2)(提高)在实验4的例程test_2553.c的基础上使系统时钟工作在不同的频率下,观察灯的亮灭速度。
由于例程在实验四中有,为简洁说明,这里不再将程序完整地给出,而只给出对于系统时钟的相关设置指令。
1设置主系统时钟MCLK=复位频率/8
BCSCTL2|=DIVM0+DIVM1;
只需在程序中加入上面语句,对SMCLK进行八分频;
2设置主系统时钟MCLK=16MHZ
if(CALBC1_16MHZ!
=0xff)
BCSCTL1=CALBC1_16MHZ;
DCOCTL=CALDCO_16MHZ;
通过观察发现在两种不同的主时钟控制下,16MHZ主时钟时对应的程序灯闪烁的要比复位频率/8的主时钟时对应的灯闪烁的快很多。
由于程序执行都是在主系统时钟的控制下进行的,所以当主系统时钟频率较高时,对应的程序执行速度也较快,由于在例程中灯的闪烁快慢是由延时函数实现的,当主频较高时,延时函数的延时时间较短,所以对应的灯的闪烁速度较快。
5.定时器A的定时功能学习
(1)设计思路
通过定时器A实现1s的定时中断,在中断中利用变量计数实现当前秒值的记录,并将该变量的值取反后赋给P1.0~P1.7端口,控制LED等闪烁。
并且可以通过计数变量是否是五的倍数来控制蜂鸣器。
选择计数时钟为ACLK默认值32768HZ,所以要使每1s产生一次中断,则需要取TA0CCR0为32767。
(3)C语言编程
#inc
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 中断 技术 基本 时钟 定时器
![提示](https://static.bdocx.com/images/bang_tan.gif)