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.

MSP430FR5968: Clock

Part Number: MSP430FR5968

Having a great deal of trouble with the clock on msp430fr5968. I have a 4MHz ceramic resonator which is oscillating on frequency.

 

However, when I set a timer for 4000 cycles, I end up with an interrupt about every 840 us. Also, the uart, set for 57.6k, seems to operate about 75k. I have done something wrong in the clock setup is my conclusion. I just can’t spot it.

 

Port J set up is:

   PJSEL0 = 0xCF;         // BITS 4 & 5 ARE IO are I/O

   PJSEL1 = 0x00;

   PJDIR = 0x00;           // all outputs (not used)

   PJOUT = 0x00;           // initial output state all low

 

Followed by the clock setup which is:

//CLOCK

   CSCTL0 = 0xA500; //set password to change clock registers

   CSCTL4 = 0xC009; //HF ON, HIGH DRIVE, OTHE OSCS OFF

   CSCTL2 = 0x0055; //HF USED FOR ALL CLOCKS

   CSCTL3 = 0x0000; //DIV BY 1 ON ALL CLOCKS

   int m = 0; //wait for clock to stabilize

   while (m < 1000)

   {

       m++;

   }

   CSCTL5 &= ~HFXTOFFG; // RESET FAULTS

 

I’ve got to be doing something really dumb but I can’t find it – so any and all help will be greatly appreciated!!!

 

Bob Scott

bobscott@jamesport.com

214.673.1439

 

  • Hi Bob,

    Can you reduce your code to the smallest possible and still demonstrates the problem, then attach it to your reply.

  • Below are files “main.c” and “main.h”.  It took a bit to get it reduced.

    Really appreciate the help. The problem is easiest to see if you look at the TEST output (P1.7) which shows only 800us or so between interrupts. You can also look at the TxData for UART which shows similar timing.

     

    Thanks again – Regards Bob Scott

    bobscott@jamesport.com

    214.673.1439

     

    Main.C:

     

    #include "main.h"

    #include "msp430fr5968.h"

     

    WORD   flags_comm;                     //++ to put flags into

    WORD            msecs = 0;

    WORD   secmsec = 0;

    WORD   delay; //++ used to delay transmissionof response to island terminal

     

    WORD   msecs5 = 0;

    WORD   state1On = 0; //++for PH debounce for on state

    WORD   state1Off = 0;//++ for PH debounce for off state

    WORD   state2On = 0; //++ same

    WORD   state2Off = 0; //++same

     

    void     main(void)

    {

     

    WDTCTL = WDTPW + WDTHOLD;       // Stop WDT interrupt

       PMMCTL0 = 0XA540; //UNLOCK PMM REGS

     

       PM5CTL0 = ~LOCKLPM5; //turn on io port config ability

       UCA1CTLW0 = 0X00E1;             // hold in reset to setup

     

       UCA1BRW = 0x0004;         // 57,600 based on 4 MHz clock

       UCA1MCTLW = 0x5551;             // 57,600 based on 4 MHz clock

     

           // init main registors do port selection first for hfxtl

       FRCTL0 = 0xA501; //setwrite protect for FR memory

     

            // init io ports

     

       P1SEL0 = 0x03;         // P1.0 & 1 are analog vref

       P1SEL1 = 0x03;

    //++   The next two lines are for testing only

    //++ For real service, the next P1DIR should be used

    //++   P1DIR = 0x0D;           // all inputs except P1-0, P1-2, P1-3

       P1DIR = 0x80 ;   //**++ for testing only, P1 bit 1 is an output for time testing

     

    //++ need int now   P1IE = 0x00;           // initial interrupts disabled (offhook setup for polling 1 msec)

       P1IES = 0x30;       // initial interrupts enabled pulser enable this later

       P1OUT = 0x00;           // initial output state all low

     

       P1IFG = 0; //TRYING TO CLEAR INT FLAGS

       P1IE = 0x30;

     

           // Set up port 2

     

       P2SEL0 = 0x00;         // all pins are I/O change for bit 7 use compair

       P2SEL1 = 0x60; //uart on 5 & 6

       P2DIR = 0xBF;           // all outputs except RXD

       P2IE = 0x00;           // interrupts disabled

       P2OUT = 0x6F;           // initial output state LED's off (high)

     

           // Set up port 3

     

       P3SEL0 = 0x00;         // use uart 0 (P3-4,5) other half I/O             // change need for two uarts

       P3SEL1 = 0x0C;   // comparator c14 - c15

       P3DIR = 0xF3;           // all outputs except comparator                  // changes needed for two uarts

       P3OUT = 0x00;           // initial output state all low (RS485 RX)

     

     

           // Set up port 4

     

       P4SEL0 = 0x00;           // all pins are I/O

       P4SEL1 = 0x10;

       P4DIR = 0xF0;           // lower half inputs, upper half outputs

       P4OUT = 0x00;           // initial output state all low

     

           // Set up port J

     

       PJSEL0 = 0xCF;         // BITS 4 & 5 ARE IO are I/O

       PJSEL1 = 0x00;

       PJDIR = 0x00;           // all outputs (not used)

       PJOUT = 0x00;          // initial output state all low

     

       //CLOCK

     

       CSCTL0 = 0xA500; //set password to change clock registers

     

       CSCTL4 = 0xC009; //HF ON, HIGH DRIVE, OTHE OSCS OFF

     

       CSCTL2 = 0x0055; //HF USED FOR ALL CLOCKS

     

       CSCTL3 = 0x0000; //DIV BY 1 ON ALL CLOCKS

     

       int m = 0; //wait for clock to stabilize

       while (m < 1000)

       {

           m++;

       }

     

       CSCTL5 &= ~HFXTOFFG; // RESET FAULTS

     

           // init uarts RS485

     

       //UCTL0 = 0x01;

     

       UCA1CTLW0 = 0X00E0;                 // Initialize USART0 state machine (~SWRST) release reset

       UCA1IE = UCRXIE;                 // Enable usart RX interrupt (ONLY rx)

     

          

                            // init timers

          

                TA0CTL   = 0x0212;                //0x01D6;     // SMCLK, count up to TACCR0 (CCR0), clear timer, enable interrupt

                TA0CCTL0 = 0x0010; //enable compare int

                TA0CCR0 = 0x0F9E;                                    // 1 msec interrupt

                TA0CCTL1 = 0;

                TA0CCTL2 = 0;

                TA0R = 0x0001 ; // start timer

     

                _EINT();

     

                P2OUT = RS485_TE;

           while(1)

           {

               while ((UCA1IFG & UCTXIFG) == 0)

                   {}

              

               UCA1TXBUF = 0X55;

           }

                           

    }

     

    #pragma vector=TIMER0_A0_VECTOR

    __interrupt void TIMER0_A0_int(void)

     

    {

    ++msecs;

    P1OUT |= TEST;

    P1OUT &= ~TEST; //TEST TO CHECK CLOCKS

    P1OUT |= TEST;

         P1OUT &= ~TEST; //TEST TO CHECK CLOCKS

    // this interupt occurs every millisec increments counter each time

    TA0CCTL0 &= ~CCIFG;

       TA0CTL &= ~TAIFG; // clear interrupts

     

    }

     

    Main.H

     

    #include "msp430fr5968.h"

     

    typedef            unsigned char BYTE;             //LSH 0-255

    typedef            unsigned int WORD;             //LSH 2-byte Integer 0 - 65,535

    typedef            unsigned long ULONG;           //LSH 4-byte Interger 0 - 2 billion

     

    #define     TEST               0x80           // P1_07_ debug output

    #define     P1_06_             0x40           // not used

    #define     PULSER2_           0x20           // P1_05_

    #define     PULSER1_           0x10           // P1_04_

    #define     OFFHOOK2_           0x08           // P1_03_

    #define     OFFHOOK1_           0x04           // P1_02_

    #define     P1_01_             0x02           // VREF+

    #define     P1_00_             0x01           // VREF-

     

     

     

    #define     P2_07_             0x80           // not used

    #define     RS485_RX           0x40           //P2_06_

    #define     RS485_TX           0x20           //P2_05_

    #define     RS485_TE           0x10            // P2_04_

    #define     OKLED_             0x08           //P2_03_ slow blink rate on/off 1 second rate   (500msec)

    #define     SIDE2LED_           0x04           //P2_02_ on/off with offhook2 and blinking with pulser2

    #define     SIDE1LED_          0x02           //P2_01_ on/off with offhook1 and blinking with pulser1

    #define     COMMLED_           0x01           //P2_00_ On when transmitting off when receiving

     

    // RS485 is UART0

    // RS232 is UART1

     

     

    #define     P3_07_             0x80            // NOT USED

    #define     P3_06_             0x40           //

    #define     P3_05_             0x20           //

    #define     P3_04_             0x10           //

    #define     POWER_IN_           0x08           //P3_3_   Detect DC power in level setup for interupt at 0.75V

    #define     P3_02_             0x04           //

    #define     P3_01_             0x02           //

    #define     P3_00_             0x01            //

    #define     P4_07_             0x80           // not used

    #define     P4_06_             0x40           // not used

    #define     RELAYSIDE2         0x20       // P4_05_ Relay Side 2

    #define     RELAYSIDE1         0x10       // P4_04_ Relay Side 1

    #define     SWT3_               0x08       // P4_03_ Switch bit1 spare

    #define     SWT2_               0x04           // P4_02_Switch bit1 spare

    #define     SWT1_               0x02           // P4_01_ Switch bit1 Address bit

    #define     SWT0_               0x01           // P4_00_ Switch bit0 Side 0,Side 1

    #define     PJ_07_             0x80   // HFOSC

    #define     PJ_06_             0x40   // HFOSC

    #define     PJ_05_             0x20   // OUT

    #define     PJ_04_             0x10   // OUT

    #define     PJ_03_             0x08   // TCK

    #define     PJ_02_             0x04   // TMS

    #define     PJ_01_             0x02   // TDI

    #define     PJ_00_             0x01   // TDO

     

    void                 main(void);                                            // update in process

     

     

  • Dear Dennis –

     

    I didn’t find the problem – but I seem to have fixed it – AND I HAVE NO IDEA WHY!!

     

    What I did (using the test program I sent to you) was to comment out all the lines dealing with the UART. Then the program ran with the time interrupts right on time (about 1 ms).   Then, I restored one line at a time.

     

    When all the lines were uncommented, the test program continued to work correctly.

     

    I then replaced my initialization code in the full program with that from the test program (it seemed to be identical, of course) and the full program ran correctly.

     

    I must say that, before I did the process above I made one change to the code following the suggestion of the clock code you furnished. That change was:

     

    int m = 0; //wait for clock to stabilize

           /* while (m < 1000)

           {

               m++;

           }

     

           CSCTL5 &= ~HFXTOFFG; // RESET FAULTS

           */

           do

             {

               CSCTL5 &= ~(LFXTOFFG | HFXTOFFG);       // Clear XT1 and XT2 fault flag

               SFRIFG1 &= ~OFIFG;

             }while (CSCTL5 & HFXTOFFG);                   // Test oscillator fault flag

     

    Please note that the line CSCTL5 & HFXTOFFG replaced the SFRIFG1&OFIFG statement because I continue to get a fault on the LFXT. But the change had no apparent effect on operation.

     

    I really do not know what fixed the problem and, I must admit, I would really like to know (if for no other reason to prevent it happening again).

     

    At any rate, it is fixed I suppose.  Would still like to know why.

     

    Thanx for all the help.

     

    Regards Bob Scott

    bobscott@jamesport.com

    214.673.1439

  • Hi Bob,

    I think what is happening is your 4Mhz xtal is not coming up.  I don't see in your code where you check for an oscillator fault so I think the HFXT is not running so SMCLK falls back to use MODOSC.  The MODOSC frequency can be anywhere from 4 to 5.2Mhz, typical is 4.8Mhz.  So if running your timer at 4.8Mhz I can see where your interrupts are going to not be exactly 1msec.

         do
         {
             CSCTL5 &= ~(LFXTOFFG | HFXTOFFG);       // Clear XT1 and XT2 fault flag
             SFRIFG1 &= ~OFIFG;

         }while (SFRIFG1&OFIFG);                   // Test oscillator fault flag

**Attention** This is a public forum