This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

MSP430FR6972: cannot get an accurate clock from the timer.

Part Number: MSP430FR6972

Hi team,

Customer cannot get an accurate clock from the timer using the IC. Below is the details.

"

I am developing a project using MSP430FR6972. I cannot get an accurate clock from the timer. I set a time of 60 seconds, but it is always a few milliseconds less than the time I set, such as 1 millisecond, 2 milliseconds, or even 10 milliseconds. I used an external 32768Hz crystal oscillator as the clock source, divided by 64 as the timing pulse.

void THIS_UCS_init(void)
{
GPIO_setAsPeripheralModuleFunctionInputPin(
GPIO_PORT_PJ,
GPIO_PIN4 + GPIO_PIN5,
GPIO_PRIMARY_MODULE_FUNCTION
);

//Set DCO frequency to 1 MHz
CS_setDCOFreq(CS_DCORSEL_0,CS_DCOFSEL_0);
//Set external clock frequency to 32.768 KHz
CS_setExternalClockSource(32768,0);
//Set ACLK=LFXT
CS_initClockSignal(CS_ACLK,CS_LFXTCLK_SELECT,CS_CLOCK_DIVIDER_1);
//Set SMCLK = DCO with frequency divider of 1
CS_initClockSignal(CS_SMCLK,CS_DCOCLK_SELECT,CS_CLOCK_DIVIDER_1);
//Set MCLK = DCO with frequency divider of 1
CS_initClockSignal(CS_MCLK,CS_DCOCLK_SELECT,CS_CLOCK_DIVIDER_1);
//Start XT1 with no time out
CS_turnOnLFXT(CS_LFXT_DRIVE_3);
}

void TIMER_B0_init()
{
Timer_B_initContinuousModeParam initContParam = {0};

//Start timer in continuous mode sourced by ACLK
initContParam.clockSource = TIMER_B_CLOCKSOURCE_ACLK;
initContParam.clockSourceDivider = TIMER_B_CLOCKSOURCE_DIVIDER_64;
initContParam.timerInterruptEnable_TBIE = TIMER_B_TBIE_INTERRUPT_DISABLE;
initContParam.timerClear = TIMER_B_DO_CLEAR;
initContParam.startTimer = true;
Timer_B_initContinuousMode(TIMER_B0_BASE, &initContParam);

/*TIMER_B0_RN_start(TIMER_B_CAPTURECOMPARE_REGISTER_0, 10000);
Timer_B_startCounter( TIMER_B0_BASE, TIMER_B_CONTINUOUS_MODE);*/
}

#pragma vector=TIMER0_B0_VECTOR
__interrupt void TIMER0_B0_ISR (void)
{
printf("test2");
TIMER_B0_RN_reload(MAIN_TIMER_REGISTER, systemstate.upperiod*90000);
}

#pragma vector=TIMER0_B0_VECTOR
__interrupt void TIMER0_B0_ISR (void)
{
printf("test2");
TIMER_B0_RN_reload(MAIN_TIMER_REGISTER, systemstate.upperiod*60000);
}

"

Thank you in advance.

Regards,
Maynard

  • 1) What crystal are you using? Over 60 seconds, a 20ppm crystal can be off by 60 seconds * .000020 = 1.2ms.

    2) How are you testing this? I suggest that printf() will not be a very accurate indicator. Consider wiggling a GPIO and watching it on a scope. Even better: Configure e.g. P2.5 as TB0.0 with OUTMOD=4, which gets rid of all the software latency.

    3) What does TIMER_B0_RN_reload() do? If it's clearing the TB0R, that will introduce an error based on the latency through TIMER0_B0_ISR().