找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 5360|回复: 0
收起左侧

MSP430 LaunchPAD学习笔记

[复制链接]
ID:302552 发表于 2018-4-5 22:15 | 显示全部楼层 |阅读模式
一:端口配置
   1:P1DIR   设置为1,相应管脚为输出。设置为0.相应管脚                              为输入状态。
   2:P1IE      设置为1,相应管脚具有中断功能。设置为0,                            相应管脚没有中断功能。
   3:P1IES   设置为1,选择下降沿触发方式,设置为0,选                            择上升沿触发方式。
   4:P1IFG    P1端口的中断标志寄存器,如果P1端口当某                            个管脚设置成中断管脚,当有中断触发时,想应比特为1 ;                              如果没有中断触发,相应比特为0.
5: P1IN   P1端口输入寄存器,在输入模式下,读取该寄                            存器相应管脚上的数据。
6: P1OUT   P1端口的输出去寄存器,在输出模式下,如                            果该寄存器相应比特设置为1时,相应管脚输出高电平;                            如果该寄存器相应比特为0时,相应管脚输出低电平。
7: P1SEL寄存器  P1端口功能选择寄存器,该寄存器主要                            控制P1端口的I/O管脚作为一般I/O还是外围模块的功能                            端口,该寄存器的相应比特为1时候,相应管脚为外围功能                           模块,当该寄存器为0时,相应管脚为一般I/O管脚。
二  LaunchPad 写程序的必要头文件和格式:
/*===================================================
#include"msp430g2553.h"
Void main()
{
    WDTCTL=WDTPW+WDTHOLD;//关闭看门狗。
    //WDTPW 是看门狗的密码,写错了会导致系统复位。
   **(程序)
}
=====================================================*/
三  点亮LED
  仅仅是对IO 口的输入输出操作。与51 很不相同。
P1DIR|=BIT0;//设置P1.0 为输出方向。===P1DIR|=0x01;
//{P1DIR=BIT0;是设置P1.0 为输出,其他全部为输入方向。}
//注意:LaunchPad 中很多操作是与,或,非等操作组成,时刻注意。
P1OUT|=BIT0;//这条指令就是设置P1.0 输出为高电平。
这样,就点亮了LED(接在P1.0 上的LED);
具体程序:
#include"msp430g2553.h"
Void main()
{
WDTCTL=WDTPW+WDTHOLD;
P1DIR|=BIT0;
P1OUT|=BIT0;
While(1);
}
四: 闪烁LED
LaunchPad 上面自带有2 个LED,一个接在P1.0 上,一个接在P1.6 上。
我们用2 个交替闪烁。
#include"msp430g2553.h"
Void main();第一个字母大写
{
WDTCTL=WDTPW+WDTHOLD;
P1DIR|=BIT0+BIT6;//设置P1.0 和P1.6 为输出
P1OUT|=BIT0;//线让LED0 亮。
While(1)
{
Unsigned int i=50000;
While(i--);
P1OUT^=0x41;//对P1.0 和P1.6 取反,所以LED0 和LED1 会交替闪烁。
}
}
五:中断系统
LaunchPad 的中断系统功能相当强大,51 只有5 个中断源,2 个定时,2 个外部,
一个串行口。但是LaunchPad 的中断源几乎是所有的引脚和所用的定时器。
在这里,最重要的就是中断向量的判断了。
定时器一般都是:
vector=TIMER0_A0_VECTOR
vector=TIMER0_A1_VECTOR
vector=TIMER1_A0_VECTOR
vector=TIMER1_A1_VECTOR
引脚中断的向量:
vector=PORT1_VECTOR;    P1 口的中断向量。
判断是哪个引脚的话,有2 种办法:
举例子:P1.3 和P1.4 都是中断的输入引脚。现在进了中断,我如何判断是那个引
脚引起的呢?
第一种方法:
vector=PORT1_VECTOR
__interruput void Port1 (void)
{
If(P1IFG&BIT3);判断的是P1.3 产生的中断。
{
;要执行的函数。
P1IFG=0x00;//清0 中断标志位。
}
If(P1IFG&BIT4)
{
;P1.4 产生的中端,执行相应的函数。
P1IFG=0x00;
}
}
第二种方法:
vector=PORT1_VECTOR
__interruput void Port1 (void)
{
P1IFG&=BIT3+BIT4;//因为只用到了P1.0 和P1.4,其他的中断标志全部清零。
(或者:P1IFG=P1IFG&0x18)
Switch(P1IFG)
{
Case 0x08: vector=3;break; //P1.3 产生的中断
Case 0x10:vector=4;break;//P1.4 产生的中断
}
}
切记:进入中断函数后要做的第一件事是,清除中断标志。
例程:
#include<msp430g2553.h>
Void main(void)
{
  WDTCTL=WDTPW+WDTHOLD;
  P1DIR|=BIT0;  //                            设置P1.0输出
  P1IES |=BIT3;  //     设置从高到底跳变触发
  P1IFG&=~BIT3//                清除中断标志位
  P1IE |=BIT3   //                   使P1.3能中断
  _BIS_SR(LPM_bits+GIE);//              启动LMP4节能模式
}
#proagma vector=PORT1_VECTOR
_interrupt  void Port_1(void)
{
   If(P1IFG&BIT3)
  {
P1OUT^=BIT0;   
P1IFG&=~BIT3;
  }
}
程序一开始
1   WDTCTL=WDTPW+WDTHOLD;  HOLD住看门狗
2   P1DIR|=BIT0;将P1.0              设置为输出口。lunchpad上的P1.O接有一个LED.
3. 接下来到P1IES |= BIT3; 在上一节中已经介绍了,P1IES 寄存器是中断沿选择寄存器。这里是选择位下降沿触发中断。
4. P1IFG &= ~BIT3; 为清除中断标志,保证程序正常运行,当然此句可以不写,这里只是做为例子
5. P1IE |= BIT3; 在上一节中已经介绍了,P1IE寄存器是使能中断事件发生的寄存器。
  • _BIS_SR(LPM4_bits + GIE);这里使程序进入最低功耗(LPM4)状态。靠中断来触发唤醒CPU,在文章开始已经介绍有,假如在中断函数中没有写有退出低功耗状态的指令,程序会在进入低功耗的下一句中卡死,不再运行下去。另外_BIS_SR(GIE); 为打开总中断的意思。
  • 接下来到中断函数的编写。以此为例,详细介绍中断函数的编写。如上所示,中断函数编写的规则为
#pragma vector= 中断向量源
__interrupt void 函数名(void)

摁住“Ctrl  +  左键”点击PORT1_VECTOR即可查看到所有的“中断向量”
在上面的中断向量中,加黑的位中断向量源,写入中断函数编写语法规则里面即可。而函数名则可以任意编写。比如我要编写一个有定时器1,CCR0寄存器溢出产生的中断,则可以这样编写
#pragma vector= TIMER1_A0_VECTOR
__interrupt void T1A0Int(void)
{
//程序代码。。。
}
假如是多IO输入中断,则如下所写。
vector=PORT1_VECTOR
__interrupt void Port1()
{

//以下为参考处理程序,不使用的端口应当删除其对于中断源的判断。
if((P1IFG&BIT0) == BIT0)
{
P2OUT&=~BIT0; //处理P1IN.0中断
P1IFG &= ~BIT0; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT1) ==BIT1)
{
P2OUT&=~BIT1; //处理P1IN.1中断
P1IFG &= ~BIT1; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT2) ==BIT2)
{
P2OUT&=~BIT2; //处理P1IN.2中断
P1IFG &= ~BIT2; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT3) ==BIT3)
{
//处理P1IN.3中断
P1IFG &= ~BIT3; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT4) ==BIT4)
{
P2OUT&=~BIT4; //处理P1IN.4中断
P1IFG &= ~BIT4; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT5) ==BIT5)
{
//处理P1IN.5中断
P1IFG &= ~BIT5; //清除中断标志
//以下填充用户代码
}
else if((P1IFG&BIT6) ==BIT6)
{
//处理P1IN.6中断
P1IFG &= ~BIT6; //清除中断标志
//以下填充用户代码
}
else
{
//处理P1IN.7中断
P1IFG &= ~BIT7; //清除中断标志
//以下填充用户代码
}
LPM3_EXIT; //退出中断后退出低功耗模式。若退出中断后要保留低功耗模式,将本句屏蔽
}
六   定时器模块
文先,介绍几个英文缩写的意思以及一些注意的地方。
1. Timer0/1 定时器0/1,在User's Guide中用的是TimerA/B,所指的也是Timer0/1 。G2553Datasheet中用的是Timer0/1 ,本文以G2553Datasheet为准。全文以Timer0为例,Timer1类同。
2. TAxR(x = 0/1)定时器x对应的计数器,这是一个只读寄存器。硬件自动驱动计数。
  • EQUyy = 0/1/2)计数事件发生寄存器,当TAxR  =  TAxCCRyEQUy1
定时器简介
MSPG2553共有两个定时器,Timer0、Timer1,他们都是十六位的定时、计数器,内含三个捕获、比较寄存器。两个定时器均支持多个捕获、PWM输出、间歇性计时,定时器包含多个中断源,可以是计数溢出中断、捕获中断等等。
定时器包含:
同步十六位定时,计数器运行模式。
时钟源从MCLK、SMCLK、ACLK任意选择
三个比较,捕获寄存器。
中断向量寄存器能快速解码的所有定时器中断
Timer0组成框图
下面简要介绍一下该硬件框图的意思,从左上角看,首先是一个时钟源选择寄存器TASSELx,通过该寄存器选择定时器的时钟源,选择了时钟源后有一个分频器Divider,相应的设置寄存器是IDx,再过来就到一个定时器的核心部分,一个16位的定时器TAR。其右侧有一个定时器的计数模块,MCx寄存器用来设置计数模式。接下来,TAR正下方有三个横线,右侧标有CCR0、CCR1、CCR2,意思是CCR1、CCR0的框图和下方CCR2的框图是一样的。此处省略不写。在CCR中,左上角为一个捕获源选择寄存器。可以从CCI2A、CCI2B、GND或者VCC选择捕获源,选择捕获源后有一个选择捕获模式寄存器Capture Mode,然后过来有一个捕获溢出状态寄存器COV,SCS同步/异步捕获模式选择位,然后连接到捕获比较寄存器。下方为模式选择寄存器,具体设置可以查看相应的寄存器设置。
这里仅是大概介绍一下Timer0的寄存器,具体的设置使用还看参考相应的寄存器并结合例程慢慢学习理解。
定时器运行方式
下面简要重点介绍定时器计数模块的四种模式以及7种输出模式。
Timer0有一个在不断计数的只读寄存器TA0R。计数器的计数模式共有四种,
停止模式(Stop mode)、连续增计数模式(Up mode)、递增计数模式(continuous mode)、增减计数模式(Up/down mode)。由上图可知,这四种模式可以通过MCx寄存器进行设置。
以上四种模式可以由下图可以很好理解。
1. Stop模式计数器不工作。
2. 连续计数模式为计数器从零开始连续增计数一直到0xFFFF即65535,然后又重新从零开始计数。
3. 递增计数模式与连续计数模式仅有一点点区别,递增模式为计数器连续增加到TA0CCR0(即图中的CCR0)中的值后又重新从零开始计数。TA0CCR0的值时可以在程序中直接赋值的。
4. 递增递减模式也很好理解,计数器从零开始计数到CCR0后又自动减数,到零后又增计数,就像三角波一样。
每一个捕获比较模块都有一个输出单元,这个输出单元专门用来产生以下如PWM的波形信号,每一个输出单元都可以通过配置OUTMOD寄存器的值来设定八种信号输出模式,
接下来再介绍一下定时器的捕获/比较功能,具体应查看技术手册。
捕获模式
捕获模式可以用来速度计算或时间测量.CCIxA ,CCIxB的捕获源可以连接到外部引脚或者内部信号,可以设定CCIDx,CMx,位让寄存器捕获上升,下降,或者两个信号的边缘.输入信号的电平可以通过CCI位的读取.
当设置寄存器CAP=1时,使能捕获模块.
比较模式
比较模式设置CAP = 0的情况向,比较模式用于产生PWM信号。或者在指定时间里输出终端信号,当TAxR计数到TACCRx时
建立起CCIFG位
中断事件发生标志位EQUx=1
EQUx的隐含改变将影响输出模式
输入信号CCI被锁上SCCI
  • 增计数模式下的输出
   

2. 递增计数模式下的输出
*
  • 第增/第减计数模式下的输出
**************************************************************** /
  / ******************************************************************
   *                    TACTL寄存器,Timer_A 控制寄存器
   * TASSEL_x:TA时钟源选择寄存器
   *     00 TACLK
   *     01 ACLK
   *     10 SMCLK
   *     11 INCLK
   * IDx:     时钟源分频寄存器。为输入时钟分频选择
   *       00  /1
   *       01  /2
   *       10  /4
   *       11  /8
   *  * ************************************************************** /
   *              定时计数模块 =四中模式+7种输出方式
/ *****************************************************************
   *
   * MCx:    计数模式寄存器   模式控制,当TA不用于节省功耗时,将MCx=00h
   *     00  停止模式:定时器停止
   *     01  增模式  :定时器计数到TACCR0
   *     10  连续模式:定时器计数到0FFFFh
   *     11  增减模式:定时器计数到TACCR0 然后减到000h
   *
   * TACLR:  定时器清零。置位时会复位TAR,时钟分频和计数方向。
   *     TACLR位会自动复位并读出值为零。
   *
   * TAIE:   TA中断允许。改为允许TAIFG中断请求
   *     0 中断禁止
   *     1 中断允许
   * TAIFG:  TA中断标志位
   *     0 无中断挂起
   *     1 中断挂起
   * ************************************************************** /
/ *****************************************************************
*
*
   *             TACCTLx,捕获比较控制寄存器
   * CMx:  捕获模式
   *   00 不捕获
   *   01 上升沿捕获
   *   10 下降沿捕获
   *   11 上升和下降同时捕
   * CCISx: 捕获比较选择,改为选择TACCRx的输入信号
   *   00 CCIxA
   *   01 CCIxB
   *   10 GND
   *   11 VCC
   * SCS:  同步捕获源,改为用于将捕获通信和同步时钟
   *   0 异步捕获
   *   1 同步捕获
   * SCCI:同步的捕获/比较输入,所选择的输入信号由EQUx信号所存,
   *   并可通过该位读取
   * CAP:  捕获模式
   *   0 比较模式
   *   1 捕获模式
   *OUTMODx:输出模式位,对TACCR0无效
   *         000 OUT 位的值
   *         001 置位
   *         010 翻转/复位
   *         011 复位/复位
   *         100 翻转
   *         101 复位
   *         110 翻转/置位
   *         111 复位/置位
   * CCIE: 捕获比较中断允许位
   *   0 中断禁止
   *   1 中断允许
   * CCI:  捕获比较输入
   * OUT:  对于输出模式0,该位直接控制输出状态
   * COV:  捕获溢出位。该位表示一个捕获溢出发生,由软件复位
   * CCIFG:捕获比较中断标志位
   *   0 没有中断挂起
   *   1 有中断挂起
   * ***************************************************************/
#include <msp430g2553.h>
unsigned  int A=10,  B=20 ;  void main (void)
{
  WDTCTL = WDTPW + WDTHOLD;
  TACTL|=TASSEL_2+TACLR+MC_1+ID_3;  // SMCLK时钟 ;定时器清零;增模式   8分频
  CCTL0=CCIE;                       //捕获中断允许
  CCR0=B;                         //TACCR0 装载值
  CCTL1=OUTMOD_7;                   //输出模式复位
  CCR1=A;
// BCSCTL1
  P1DIR=BIT6;
  P1SEL=BIT6;
// _EINT();                          //使能所有中断
  while(1);
}
/*#pragma vector=TIMER0_A0_VECTOR
__interrupt void  ta0_isr(void)
{
  unsigned  int i;
  for(i=0;i<num;i++)
    pwm=i;
}*/

定时器中断
这里以定时器0为例,定时器1同。
定时器的中断可有定时器TA0CCR0溢出产生,也可由TA0CCRx(x =1/2)溢出产生、捕获/比较事件发生引起的中断,前者有一个专用的中断向量,TIMER0_A0_VECTOR,而后者用的TIMER0_A1_VECTOR,至于是哪一个中断时间发生,还要根据标志位来判断。
下面以官方例程LaunchPad Lab2为例介绍定时器A的操作。
例一
#include <msp430g2553.h>
void main(void)
{
WDTCTL = WDTPW + WDTHOLD; // Stop watchdog timer
if (CALBC1_1MHZ ==0xFF || CALDCO_1MHZ == 0xFF)
{
while(1); // If calibration constants erased, trap CPU!!
}
BCSCTL1 = CALBC1_1MHZ; // Set range
DCOCTL = CALDCO_1MHZ; // Set DCO step + modulation
BCSCTL3 |= LFXT1S_2; // LFXT1 = VLO
P1DIR = 0x40; // P1.6 output (green LED)
P1OUT = 0; // LED off
IFG1 &= ~OFIFG; // Clear OSCFault flag
BCSCTL1 |= DIVA_3; // ACLK = VLO/8
BCSCTL2 |= SELM_3 + DIVM_3 + DIVS_3; // MCLK = DCO/8, SMCLK = DCO/8
// Configure TimerA
TACTL = TASSEL_1 + MC_1 + TAIE; // Source: ACLK, UP mode
CCR0 = 5100; //Timer count 5100
CCR1 = 2000; //Timer count 100
CCTL0 = CCIE; //CCR0 interrupt enabled
CCTL1 = CCIE; //CCR1 interrupt enabled
_BIS_SR(GIE);
for(;;);
}
// Timer A0 interrupt service routine
#pragma vector=TIMER0_A0_VECTOR
__interrupt void Timer_A0 (void)
{
P1OUT |= BIT6; // P1.6 output High
}
// Timer A1 Interrupt Vector (TA0IV) handler
#pragma vector=TIMER0_A1_VECTOR
__interrupt void Timer_A1(void)
{
switch( TA0IV )
{
case 2: P1OUT &= ~BIT6; // P1.6 output Low
break;
case 10:
break;
}
}
程序一开始关闭看门狗,if语句作为时钟校准的范例,可以删去。BCSCTL3 |= LFXT1S_2; 选择超低频时钟源。然后设定输出口,清除中断标志,时钟源分频设定,接下里组建定时器A,即定时器0,在详细介绍代码之前,首先看头文件关于定时器相关寄存器的设定。
例二
  下面举一个无需中断服务函数、硬件自动实现产生两路PWM的例子。
代码很简单,初始化一下即可。
#include<msp430g2553.h>
void Set_TimerB_PWM(void)
{
//使用系统初始化时的默认时钟1MHz,定时器B专门用于产生PWM 波形。
TA1CTL = TASSEL_2 + MC_1 + TACLR;//使用系统次主机SMCKL、增计数模式、清楚定时器B时钟
TA1CCR0 = 5001 - 1;//在1MHz的主频率下,1*10^6/5000=200Hz的中断频率
TA1CCR1 = 3751 - 2;//当寄存器TACCR1的值小于3750时,输出口保持高电平。5000*3/4=3750,此路产生3:1的PWM波形。
TA1CCR2 = 1251 - 2;//当寄存器TACCR1的值小于1250时,输出口保持高电平。5000*1/4=1250,产生1:3的PWM波
TA1CCTL1 = OUTMOD_7;//输出模式7,计数器计数到5000计数器自动置位,无需中断服务子函数。
TA1CCTL2 = OUTMOD_7;//输出模式7,计数器计数到5000计数器自动置位,无需中断服务子函数。
P2SEL |= BIT1 + BIT5;//只有这两路可选(为什么是这两路?在G2553Datasheet中有特别指明)。做第二功能使用(PWM输出)
P1DIR |= BIT6; //电机控制口CTL//这里与本例无关
P1OUT &= ~BIT6; //start with 0 -->IN2,4为1,灭//这里与本例无关
}
  初始化时钟后直接调用该函数即可。
我这里使用的是定时器B(即Timer1)。详细的介绍见以上备注。  
七  时钟配置
  时钟源:

     外部晶体振荡器
     超低频率振荡器(VLO)
     数字控制振荡器(DCO)

  时钟信号:


     ACLK :Auxiliary clock.辅助时钟。
     MCLK :Master clock主时钟。
     SMCLK :Second Master clock次主机时钟。
内部晶体振荡器产生时钟后经过DCOR、SCG0、RSELx、DCO等各个寄存器为MCLK、SMCLK提供时钟源
内部时钟还有一个超低频率内置晶体振荡器(VLO)在上图的最上方。可作为低频时钟源。
另外一个部分是系统的外部时钟,外部晶振经过LFXT等各个寄存器设置后可以为MCLK、ACLK提供时钟源。
上图中SELM、SELS为时钟源选择寄存器。
上图中DIVA、DIVM、DIVS都是分频器,时钟源可以经过1/2/4/8分频后为CPU提供时钟,以降低功耗。
   



ADC10的时钟部分框图



Timer_A的结构框图
     Timer_A不能选择MCLK作为Timer_A的时钟


CPU是处理器的核心部分,它使用的时钟始终是MCLK。
上电后,系统默认使用的主系统时钟MCLK和子系统时钟SMCLK是同为DCOCLK产生的1MHz时钟,而辅助时钟ACLK则为内部VLOCLK产生的12KHz时钟
MSP430低功耗模式
    单片机中,功耗最低的单片机要MSP430单片机,这是做手持设备最优选择,MSP430中,用到5种低功耗,LPM0,LPM1,LPM2,LPM3,LPM4,这五种低功耗各种解释如下 :
LPM0:CPU停止工作,MCLK时钟停止,SMCLK、ACLK时钟还在工作。
LPM1:CPU停止工作,MCLK时钟停止,在活动模式如果DCO没有作为MCLK和SMCLK时钟时,则直流发生器被禁止,否则就保持活动状态,SMCLK、ACLK时钟依然还在工作。
LPM2:CPU停止工作,MCLK、SMCLK时钟停止工作,如果DCO没有作为MCLK、SMCLK,自动被禁止直流发生器保持有效,ACLK还处于工作中。
LPM3:CPU停止工作,MCLK、SMCLK时钟停止工作,DCO时钟也停止工作,仅ACLK时钟还处于工作状态。
LPM4:CPU停止工作,MCLK、SMCLK时钟停止工作,DCO时钟也停止工作,ACLK也停止工作。此时功耗最低。
一般情况下,处理器进入低功耗模式后,由中断来唤醒,外部中断或内部中断。
如果想进入低功耗1,则程序可以为:_BIS_SR(LPM1_bits + GIE);退出低功耗1,则程序可以为:LPM1_EXIT; 进入其他低功耗和退出低功耗一样。
低功耗执行的一个过程:程序从main函数入口开始执行程序,当遇到进入低功耗程序时,如:_BIS_SR(LPM1_bits + GIE);此时相当于下面的程序处于停止状态不再执行,当有一个中断来到,则会进入中断处理程序,自动退出低功耗,如果在中断中没有没有退出低功耗,当中断服务程序执行完成后,又会重新进入低功耗。

完整的Word格式文档51黑下载地址:
MSP430学习笔记 .doc (488 KB, 下载次数: 152)
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表