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.

TM4C1294NCPDT: SYSCLK is not what it is supposed to be.

Part Number: TM4C1294NCPDT
Other Parts Discussed in Thread: EK-TM4C1294XL

Tool/software:

Hi,

I might have a problem with the PLL.

I discovered the problem when I was power cycling my custom board on and off.

The problem is very rare and happens only every 100...4000 cycles.

The board uses a 25MHz crystal and we setup the PLL to generate the 120MHz system clock.

In addition, we use the clock output pin (PQ4) to generate a 8.33MHz clock (25MHz/3) and a PWM to generate a 780kHz clock on PF1.

Furthermore we use I2C for some sensor data.

On failure, we see:

- PQ4 8.33MHz -> good

- PWM clock is ~48kHz -> bad

- I2C clock is ~3kHz -> bad

- Delay times longer than expected -> bad

We had an old TivaWare in usage, but we updated it to latest (2.2.0.295), cause of SYSCLT#22 and SYSCTL#23.

I can only post code blocks here.

Here is my code. Any ideas how this could happen?

// The system clock frequency.
uint32_t g_ui32SysClock;

int main(void)
{
    ///////////////////////////////////////////////////////////////////////////
    // Initialization
    ///////////////////////////////////////////////////////////////////////////

    g_ui32SysClock = init_CPU();
    init_CLKOut();
    init_M0PWM1_MC();
    
    // more code
    ...
    ...
    ...
}

uint32_t init_CPU(void)
{
    uint32_t ui32SysClock;

    //
    // Make sure the main oscillator is enabled because this is required by
    // the PHY.  The system must have a 25MHz crystal attached to the OSC
    // pins.  The SYSCTL_MOSC_HIGHFREQ parameter is used when the crystal
    // frequency is 10MHz or higher.
    //
    MAP_SysCtlMOSCConfigSet(SYSCTL_MOSC_HIGHFREQ);

    // Run from the PLL at 120 MHz.
    // Note: SYSCTL_CFG_VCO_240 is a new setting provided in TivaWare 2.2.x and
    // later to better reflect the actual VCO speed due to SYSCTL#22.
    //
    ui32SysClock = MAP_SysCtlClockFreqSet((SYSCTL_XTAL_25MHZ |
                                           SYSCTL_OSC_MAIN |
                                           SYSCTL_USE_PLL |
                                           SYSCTL_CFG_VCO_240), 120000000);

    return(ui32SysClock);
}

void init_CLKOut(void)
{
    //
    // Enable pin PQ4 for CLK-Output for FPGA
    // use the Main Oscillator (MOSC) = 25MHz and divided by 3
    // 25MHz / 3 = 8.333MHz
    // CLK-Output is enabled
    //
    MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOQ);

    //
    // Wait for the GPIOQ module to be ready.
    //
    while(!MAP_SysCtlPeripheralReady(SYSCTL_PERIPH_GPIOQ))
    {
    }

    MAP_GPIOPinConfigure(GPIO_PQ4_DIVSCLK);
    GPIOPinTypeDIVSCLK(GPIO_PORTQ_BASE, GPIO_PIN_4);
    MAP_SysCtlClockOutConfig(SYSCTL_CLKOUT_EN | SYSCTL_CLKOUT_MOSC, 3);
}

void init_M0PWM1_MC(void)
{
    //
    // Enable M0PWM1
    //
    MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_PWM0);

    //
    // Wait for the PWM0 module to be ready.
    //
    while(!MAP_SysCtlPeripheralReady(SYSCTL_PERIPH_PWM0))
    {
    }

    //
    // Set the PWM clock source to the system clock divided by 1.
    // 120MHz / 1 = 120MHz
    //
    MAP_PWMClockSet(PWM0_BASE, PWM_SYSCLK_DIV_1);
    
    //
    // Enable GPIO-F
    //
    MAP_SysCtlPeripheralEnable(SYSCTL_PERIPH_GPIOF);
    
    //
    // Wait for the GPIO module to be ready.
    //
    while(!MAP_SysCtlPeripheralReady(SYSCTL_PERIPH_GPIOF))
    {
    }

    //
    // Configure the GPIO pin muxing to select M0PWM1 functions for these pins.
    // This step selects which alternate function is available for these pins.
    // This is necessary if your part supports GPIO pin function muxing.
    // Consult the data sheet to see which functions are allocated per pin.
    //
    MAP_GPIOPinConfigure(GPIO_PF1_M0PWM1);

    //
    // Configure the PWM function for PF1.
    // Consult the data sheet to see which functions are allocated per pin.
    //
    MAP_GPIOPinTypePWM(GPIO_PORTF_BASE, GPIO_PIN_1);

    //
    // Configure the M0PWM to count up/down without synchronization.
    //
    MAP_PWMGenConfigure(PWM0_BASE, PWM_GEN_0, PWM_GEN_MODE_UP_DOWN |
                        PWM_GEN_MODE_NO_SYNC);

    //
    // Set the PWM period to 780kHz.  To calculate the appropriate parameter
    // use the following equation: N = (1 / f) * SysClk.  Where N is the
    // function parameter, f is the desired frequency, and SysClk is the
    // system clock frequency.
    // In this case you get: (1 / 780kHz) * (120MHz/1) = 154 cycles.  Note that
    // the maximum period you can set is 2^16.
    //
    MAP_PWMGenPeriodSet(PWM0_BASE, PWM_GEN_0, 154);

    //
    // Set PWM0 to a duty cycle of 50%.  You set the duty cycle as a function
    // of the period.  Since the period was set above, you can use the
    // PWMGenPeriodGet() function.  For this example the PWM will be high for
    // 50% of the time or 77 clock ticks (154 / 2).
    //
    MAP_PWMPulseWidthSet(PWM0_BASE, PWM_OUT_1, 77);

    //
    // Disables (false) the PWM0 Bit1 (PF1) output signal.
    //
    MAP_PWMOutputState(PWM0_BASE, PWM_OUT_1_BIT, false);

    //
    // Enables the timer/counter for a PWM generator block.
    //
    MAP_PWMGenEnable(PWM0_BASE, PWM_GEN_0);
}

  • Hi,

      You can output a divided System Clock too instead of a divided MOSC.

      -Do you see a wrong divided System Clock?

      -Is this happening on only one board or many boards?

      -What is the failure rate?

      -Do you see the same problem on both the old and new/latest TivaWare versions?

  • Hi,

    thanks for reply. As I wrote on my first post:

    On failure, we see:

    - PQ4 8.33MHz -> good

    - PWM clock is ~48kHz -> bad

    - I2C clock is ~3kHz -> bad

    - Delay times longer than expected -> bad

    We see wrong PWM clock, I2C clock and delay/processing times are longer.

    If I calculate the wrong PWM clock back to SysClk I get something aroung 7.5MHz (48.68kHz * 154).

    The return value of init_CPU() is good -> 120MHz.

    Do I need somewhere more delay time between init_CPU() and init_M0PWM1_MC()?

    Is this happening on only one board or many boards?

    This happen on more than one board.

    What is the failure rate?

    Every 100...4000 cycles, but often more than 1000 cylces.

    Do you see the same problem on both the old and new/latest TivaWare versions?

    Yes.

  • As I wrote on my first post:

    On failure, we see:

    - PQ4 8.33MHz -> good

    - PWM clock is ~48kHz -> bad

    - I2C clock is ~3kHz -> bad

    I understand you output on DIVSCLK pin the MOSC/3 which is 8.33Mhz using SYSCTL_CLKOUT_MOSC flag. Although the ui32SysClock is returned with 120Mhz, I want to see the real SYSCLK output which is supposed to be 40Mhz for SYSCLK/3 if you use the SYSCTL_CLKOUT_SYSCLK flag. 

    We see wrong PWM clock, I2C clock and delay/processing times are longer.

    If I calculate the wrong PWM clock back to SysClk I get something aroung 7.5MHz (48.68kHz * 154).

    I want to know know if DIVSCLK is equal to 7.5/3=2.6Mhz instead of 40Mhz as expected if SYSCTL_CLKOUT_SYSCLK  is used with a /3 divider. 

    Do I need somewhere more delay time between init_CPU() and init_M0PWM1_MC()?

    If it only fails once after a thousand power cycles then I don't think it is a software issue.

    This happen on more than one board.

    What is the failure rate?

    Every 100...4000 cycles, but often more than 1000 cylces.

    Do you see the same problem on both the old and new/latest TivaWare versions?

    Yes.

    I don't know what is the cause of the problem. I will suggest a few things. 

     - Can you run the stock TivaWare example C:\ti\TivaWare_C_Series-2.2.0.295\examples\boards\ek-tm4c1294xl\pwm_invert. Please run as-is and do not modify it. This example produces a 15Mhz PWM with either 25% or 75% PWM. Do you see a correct PWM period? 

    - Do you have any board that has no problem?

    - If you have a board that has no problem at all then please do a ABA swap test. Swap the MCU from the suspected board to the known good board. Can you repeat the same problem? Also swap the known good MCU from the good board to your suspected board. Can you repeat the same problem. The ABA swap test will us if the problem is isolated to the MCU or to the board. This is assuming you have some known good boards that do not show the problem. 

     - If all of your boards fail then can you repeat the same problem on a EK-TM4C1294XL LaunchPad board? Please be aware that PQ4 on the LaunchPad cannot be used for outputting DIVSCLK due to PQ4 is used as power monitor input. Therefore, if you are going to try on the LaunchPad, make sure you comment out the code for outputting DIVSCLK or you would need to hack the board a bit. Refer to this post. https://e2e.ti.com/support/microcontrollers/arm-based-microcontrollers-group/arm-based-microcontrollers/f/arm-based-microcontrollers-forum/345762/tiva-c-series-tm4c1294-connected-launchpad

  • Okay, thanks for help.

    I change the clock output source to MAP_SysCtlClockOutConfig(SYSCTL_CLKOUT_EN | SYSCTL_CLKOUT_SYSCLK  , 15) so that my clock is still something around 8MHz (120MHz / 15).

    The pwm_invert demo project can I not run as it, cause of we use PF2 on our custome board.

  • Hi,

      If MAP_SysCtlClockOutConfig(SYSCTL_CLKOUT_EN | SYSCTL_CLKOUT_SYSCLK  , 15) produces 8MHz on PQ4 pin then it tells me the SYSCLK that is derived from PLL is correct. Refer to the clock tree diagram in the datasheet. Also see below. 

    The pwm_invert demo project can I not run as it, cause of we use PF2 on our custome board.

    Can you modify the pwm_invert to output PWM signal on other pin? I just want to make sure it is not your software issue. The pwm_invert is a proven example. If it also fails on your board then it would be the hardware to investigate. 

    You have not told me what is the result when running your own code on the LaunchPad.

  • I change the pin from the pwm_invert demo to pin PF1 and it runs on our board.

    Few things that I notice in your demo:

    - you don't use SysCtlMOSCConfigSet(SYSCTL_MOSC_HIGHFREQ)

    - you don't wait for the peripheral to become ready as you describe it in [FAQ] Common TM4C Solved Issues and General Information

    You have not told me what is the result when running your own code on the LaunchPad.

    My code also runs on the LaunchPad (didn't test PQ4 output yet).

    Both are just one-shot test and no cycle test.

  • Hi,

    change the pin from the pwm_invert demo to pin PF1 and it runs on our board.

    There must be some subtle difference between your code and the example or perhaps the hardware itself but I just can't tell what it is at this moment. Is it possible for you to cycle through 4000 times and can you replicate the problem? If you can replicate a bad PWM frequency running the example then we can come up with the next steps on how to diagnose the problem.

    Few things that I notice in your demo:

    - you don't use SysCtlMOSCConfigSet(SYSCTL_MOSC_HIGHFREQ)

    - you don't wait for the peripheral to become ready as you describe it in [FAQ] Common TM4C Solved Issues and General Information

    Correct. For all the TivaWare examples I haven't seen one that calls SysCtlMOSCConfigSet before SysCtlClockFreqSet although I don't think calling SysCtlMOSCConfigSet would create any negative effect. Can you comment out SysCtlMOSCConfigSet to see if it make a difference?

    Waiting for the peripheral to become ready is a good practice. The example should add it although it does. Normally, it takes a very few cycles for the peripheral to become ready. It is a matter to enable the clock to the peripheral. Without the wait, by the time the processor accesses the peripheral, the peripheral is normally ready. 

    We had an old TivaWare in usage, but we updated it to latest (2.2.0.295), cause of SYSCLT#22 and SYSCTL#23.

    I tend to think you are picking up the correct library but can you make sure in your CCS project settings that you are pointing to the driverlib.lib of the latest TivaWare version, not your old version. 

  • I have a automatic cycle test for my full project.

    This weekend the failure happened again.

    With the change to MAP_SysCtlClockOutConfig(SYSCTL_CLKOUT_EN | SYSCTL_CLKOUT_SYSCLK  , 15) I should see 8MHz (120MHz/15), but I see 500kHz. So the SYSCLK is wrong with 7.5MHz (7.5MHz/15 = 500kHz).

    I tend to think you are picking up the correct library but can you make sure in your CCS project settings that you are pointing to the driverlib.lib of the latest TivaWare version, not your old version. 

    There is only the newest installed. I deinstalled the old one.

  • Hi,

      Sorry for the delay. We lost power in the office as well as from home due to the recent hurricane hitting Texas. Most of the time I have no cell phone service.  Not sure when we will get back to normal.

      Do you have any board that is working without the problem? If you have at least one working board can you do a ABA swap test. 

      If you don't have any working board then can you do your automatic test on a Launchpad?

      With all the info you provided so far, I'm unable to diagnose the problem why it would fail after a few thousand power cycles with a corrupted PLL output.