MSP430F5529 LaunchPad™ Development Kit
(MSP‑EXP430F5529LP)
一、新建工程
二、时钟树
时钟系统结构
(1)5个时钟来源
时钟系统模块具有5个时钟来源。
① XT1CLK:低频/高频振荡器,可以使用32768Hz的手表晶振、标准晶体、谐振器或4~32MHz的外部时钟源;
② VLOCLK:内部超低功耗低频振荡器,典型频率12kHz;
③ REFOCLK:内部调整低频参考振荡器,典型值为32768Hz;
④ DCOCLK:内部数字时钟振荡器,可由FLL稳定后得到;
⑤ XT2CLK:高频振荡器,可以是标准晶振、谐振器或4~32MHz的外部时钟源。
(2)3个时钟信号
时钟系统模块可以产生3个时钟信号供CPU和外设使用。
① ACLK:辅助时钟(Auxiliary Clock)。可以通过软件选择XT1CLK、REFOCLK、VLOCLK、DCOCLK、DCOCLKDIV或XT2CLK(当XT2CLK可用时)。DCOCLKDIV是FLL模块内DCOCLK经过1/2/4/8/16/32分频后获得的。ACLK主要用于低速外设。ACLK可以再进行1/2/4/8/16/32分频,ACLK/n 就是ACLK 经过1/2/4/8/16/32分频后得到的,也可以通过外部引脚进行输出。
② MCLK:主时钟(Master Clock)。MCLK的时钟来源与ACLK相同,MCLK专门供CPU使用,MCLK配置得越高,CPU的执行速度就越快,功耗就越高。一旦关闭MCLK,CPU也将停止工作,因此在超低功耗系统中可以通过间歇启用MCLK的方法降低系统功耗。MCLK也可经1/2/4/8/16/32分频后供CPU使用。
③ SMCLK:子系统时钟(Subsystem Master Clock)。SMCLK的时钟来源与ACLK相同,SMCLK主要用于高速外设,SMCLK也可以再进行1/2/4/8/16/32分频。
时钟系统的原理
(1)内部超低功耗低频振荡器(VLO)
内部超低功耗低频振荡器在无须外部晶振的情况下,可提供12kHz的典型频率。VLO为不需要精确时钟基准的系统提供了一个低成本、超低功耗的时钟源。当VLO被用作ACLK、MCLK或SMCLK时(SELA={1}、SELM={1}或SELS={1}),VLO被启用。
(2)内部调整低频参考时钟振荡器(REFO)
在不要求或不允许使用晶振的应用中,REFO可以用作高精度时钟。经过内部调整,REFO的典型频率为32768Hz,并且可以为FLL模块提供一个稳定的参考时钟源。REFOCLK与FLL的组合,在无须外部晶振的情况下,提供了灵活的大范围系统时钟。当不使用REFO时,REFO不消耗电能。
(3)XT1振荡器(XT1)
如图所示。MSP430单片机的每种器件都支持XT1振荡器,MSP430F5xx/6xx系列单片机的XT1振荡器支持两种模式:LF(低频模式)和HF(高频模式)。
(4)XT2振荡器(XT2)
如图所示,XT2振荡器用来产生高频的时钟信号XT2CLK,其工作特性与XT1振荡器工作在高频模式相似,晶振的选择范围为4 ~32MHz,具体范围由XT2DRIVE控制位进行设置。高频时钟信号XT2CLK可以分别作为辅助时钟ACLK、主时钟MCLK和子系统时钟SMCLK的基准时钟信号,也可提供给锁频环模块(FLL),可以利用XT2OFF控制位实现对XT2模块的启用(0)和关闭(1)。
(5)锁频环(FLL)
如图所示,FLL的参考时钟FLLREFCLK可以来自于XT1CLK、REFOCLK或XT2CLK中的任何一个时钟源,通过SELREF控制位进行选择。由于这3种时钟的精确度都很高,倍频后仍然能够得到准确的频率。FLL能够产生两种时钟信号:DCOCLK和DCOCLKDIV,其中DCOCLKDIV信号为DCOCLK时钟经1/2/4/8/16/32分频后得到(分频系数为D)。
锁频环是一种非常巧妙的电路,它的核心部件是数控振荡器和一个频率积分器。数控振荡器能够产生DCOCLK时钟,频率计数器实际上是一个加减计数器,“+”输入端上的每个脉冲将使计数值加1,“-”输入端上的每个脉冲将使计数值减1。FLLREFCLK经过1/2/4/8/12/16分频后输入频率积分器的“+”输入端(分频系数为n),DCOCLKDIV经过(N+1)分频后输入频率积分器的“-”输入端,频率积分器的运算结果又输出给数控振荡器,改变数控振荡器的输出频率DCOCLK,构成反馈环。经过反馈调整,最终的结果使频率积分器的“+”输入端的频率与“-”输入端的频率相同,即
所以,数控振荡器的最终输出频率为
其中,D由3位FLLD控制位确定,取值为1,2,4,8,16,32;
N由10位FLLN控制位确定,取值范围为1~1023;
n由3位FLLREFDIV控制位确定,取值为1,2,4,8,12,16。
(6)内部模块振荡器(MODOSC)
如图所示,UCS时钟模块还包含一个内部模块振荡器MODOSC,能够产生约4.8MHz的MODCLK时钟。Flash控制器模块、ADC_12模块等片内外设都可使用MODCLK作为内部参考时钟。
为了降低功耗,当不需要使用MODOSC时,可将其关闭。当产生有条件或无条件启用请求时,MODOSC可自动开启。设置MODOSCREQEN控制位,将允许有条件启用请求使用MODOSC模块。对于利用无条件启用请求的模块无须置位MODOSCREQEN控制位,例如Flash控制器、ADC_12等。
(7)时钟模块失效及安全操作
MSP430单片机的时钟模块包含检测XT1、XT2和DCO振荡器故障失效的功能。振荡器故障失效检测逻辑如图所示。
晶振故障失效条件有以下4种。
① XT1LFOFFG:XT1振荡器在低频模式(LF)下失效;
② XT1HFOFFG:XT1振荡器在高频模式(HF)下失效;
③ XT2OFFG:XT2振荡器失效;
④ DCOFFG:DCO振荡器失效。
时钟树配置实战
这里我打算将MCLK、SMCLK配置为25MHz,它们的时钟源设为倍频后的DCOCLK,FLL时钟源设为XT2CLK。
由原理图可知,XT2输入引脚为P5.2、P5.3
复用P5.2、P5.3
GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P5, GPIO_PIN2);
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P5, GPIO_PIN3);
根据自己的开发板,选择合适的参数启用XT2
MSP430F5529 LaunchPad™ Development Kit 板载XT2晶振为CSTCR4M00G15L99,4MHz
UCS_turnOnXT2 (UCS_XT2_DRIVE_4MHZ_8MHZ);
MSP430为了省电默认状态下核心电压默认设置为1.8V来节省功耗,高频工作需要较高的核心电压,本次实验不需要低功耗模式,故我们直接将核心电压设为最高级。
PMM_setVCore(PMM_CORE_LEVEL_3);
UCS_initClockSignal用于设置各时钟的时钟源和分频系数。
UCS_initFLLSettle用于设置锁相环倍频系数。
故将XT2的4MHz经8分频进入锁相环,再倍频50倍后即可得到25MHz的DCOCLK
(4MHz经4分频再倍频24倍、25倍只能得到24MHz,26倍得到26MHz,我暂且蒙在鼓里)
最后将MCLK、SMCLK的时钟源选为DCOCLK
UCS_initClockSignal(UCS_FLLREF, UCS_XT2CLK_SELECT, UCS_CLOCK_DIVIDER_8);
UCS_initFLLSettle(25000, 50);
UCS_initClockSignal(UCS_MCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
UCS_initClockSignal(UCS_SMCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
综上,最后将MCLK和SMCLK通过P7.7、P2.2复用输出
#include "driverlib.h"
int main(void)
{
WDT_A_hold(WDT_A_BASE);
GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P5, GPIO_PIN2);
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P5, GPIO_PIN3);
UCS_turnOnXT2 (UCS_XT2_DRIVE_4MHZ_8MHZ);
PMM_setVCore(PMM_CORE_LEVEL_3);
UCS_initClockSignal(UCS_FLLREF, UCS_XT2CLK_SELECT, UCS_CLOCK_DIVIDER_8);
UCS_initFLLSettle(25000, 50);
UCS_initClockSignal(UCS_MCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
UCS_initClockSignal(UCS_SMCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P2, GPIO_PIN2); //SMCLK Output
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P7, GPIO_PIN7); //MCLK Output
while(1)
{
}
}
测得对应时钟已升至25MHz
三、点灯工程师
如原理图所示,P4.7控制LED2,高电平点亮
在程序中加入
#define MCLK_IN_HZ 25000000
#define delay_us(x) __delay_cycles((MCLK_IN_HZ/1000000*(x)))
#define delay_ms(x) __delay_cycles((MCLK_IN_HZ/1000*(x)))
将P4.7设为输出模式
GPIO_setAsOutputPin(GPIO_PORT_P4, GPIO_PIN7);
while(1)
{
GPIO_toggleOutputOnPin (GPIO_PORT_P4, GPIO_PIN7);
delay_ms(500);
}
即可观察到LED2以1Hz的频率闪烁
封装好的初始化函数
void SystemClock_Init(void)
{
PMM_setVCore(PMM_CORE_LEVEL_3); //高主频工作需要较高的核心电压
//XT1引脚复用
GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P5, GPIO_PIN4);
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P5, GPIO_PIN5);
//起振XT1
UCS_turnOnLFXT1(UCS_XT1_DRIVE_3,UCS_XCAP_3);
//XT2引脚复用
GPIO_setAsPeripheralModuleFunctionInputPin(GPIO_PORT_P5, GPIO_PIN2);
GPIO_setAsPeripheralModuleFunctionOutputPin(GPIO_PORT_P5, GPIO_PIN3);
//起振XT2
UCS_turnOnXT2(UCS_XT2_DRIVE_4MHZ_8MHZ);
//XT2作为FLL参考时钟,先8分频,再50倍频 4MHz / 8 * 50 = 25MHz
UCS_initClockSignal(UCS_FLLREF, UCS_XT2CLK_SELECT, UCS_CLOCK_DIVIDER_8);
UCS_initFLLSettle(25000, 50);
//XT1作为ACLK时钟源 = 32768Hz
UCS_initClockSignal(UCS_ACLK, UCS_XT1CLK_SELECT, UCS_CLOCK_DIVIDER_1);
//DCOCLK作为MCLK时钟源 = 25MHz
UCS_initClockSignal(UCS_MCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
//DCOCLK作为SMCLK时钟源 = 25MHz
UCS_initClockSignal(UCS_SMCLK, UCS_DCOCLK_SELECT, UCS_CLOCK_DIVIDER_1);
//设置外部时钟源的频率,使得在调用UCS_getMCLK, UCS_getSMCLK 或 UCS_getACLK时可得到正确值
UCS_setExternalClockSource(32768, 4000000);
}