AnsweredAssumed Answered

LPTMR does not work on FRDM-K20D50M

Question asked by Yasuhiko Koumoto on Sep 21, 2014
Latest reply on Sep 22, 2014 by Yasuhiko Koumoto

Hi all.,

 

I am trying the wakeup from the low power mode by LPTMR on FRDM-K20D50M biard,.

However, it does not work.

The same code works well on the FRDM-KL25Z board.

I added  LLWUI bit to SMC_PMCTRL for Kinetis K.

Could anyone let me know the solution for FRDM-K20D50M?

 

The sample code is as follows.

The code was made by referring to the 'low_power_demo' of KL25 Sample Code.

 

--------[snip]-------

#include "common.h"

#define LPTMR_USE_IRCLK 0
#define LPTMR_USE_LPOCLK 1
#define LPTMR_USE_ERCLK32 2
#define LPTMR_USE_OSCERCLK 3

#define STOP_MODE  0x0
#define VLPS_MODE  0x2
#define LLS_MODE   0x3
#define VLLSx_MODE 0x4
#define VLLS0_MODE 0x0
#define VLLS1_MODE 0x1
#define VLLS2_MODE 0x2
#define VLLS3_MODE 0x3

#define  LLWU_irq_no            7  // Vector No 23
#define  LPTMR_irq_no           28  // Vector No 44

#define LOW_PWR_MODE  STOP_MODE
//#define LOW_PWR_MODE  VLPS_MODE
//#define LOW_PWR_MODE  LLS_MODE
//#define LOW_PWR_MODE  VLLSx_MODE

#define LOW_PWR_SMODE VLLS0_MODE
//#define LOW_PWR_SMODE VLLS1_MODE
//#define LOW_PWR_SMODE VLLS2_MODE
//#define LOW_PWR_SMODE VLLS3_MODE

void LPTMR_init()
{
    //SIM_SCGC5 |= SIM_SCGC5_LPTMR_MASK;
    SIM_SCGC5 |= 1; // SIM_SCGC5_LPTMR_MASK was not defined in FRDM-K20D50M

    LPTMR0_PSR = ( LPTMR_PSR_PRESCALE(0) // 0000 is div 2
                 | LPTMR_PSR_PBYP_MASK   // LPO feeds directly to LPT
                 | LPTMR_PSR_PCS(LPTMR_USE_LPOCLK)) ; // use the choice of clock
            
    LPTMR0_CMR = LPTMR_CMR_COMPARE(1000);  //Set compare value (100ms)

    LPTMR0_CSR =(  LPTMR_CSR_TCF_MASK   // Clear any pending interrupt
                 | LPTMR_CSR_TIE_MASK   // LPT interrupt enabled
                 | LPTMR_CSR_TPS(0)     //TMR pin select
                 |!LPTMR_CSR_TPP_MASK   //TMR Pin polarity
                 |!LPTMR_CSR_TFC_MASK   // Timer Free running counter is reset
                                        //  whenever TMR counter equals compare
                 |!LPTMR_CSR_TMS_MASK   //LPTMR0 as Timer
                );
    LPTMR0_CSR |= LPTMR_CSR_TEN_MASK|LPTMR_CSR_TFC_MASK;   //Turn on LPT and start counting
}

void STOP_Mode(void)
{
  /* Write to PMPROT to allow AVLP/LLS/AVLLS power modes this write-once
     bit allows the MCU to enter the AVLP/LLS/AVLLS low power mode*/
  SMC_PMPROT = SMC_PMPROT_AVLP_MASK
             | SMC_PMPROT_ALLS_MASK
             | SMC_PMPROT_AVLLS_MASK; 
  /* Set the STOPM field to 0b011 for LLS mode  */
  SMC_PMCTRL &= ~SMC_PMCTRL_STOPM_MASK;
  SMC_PMCTRL |=  SMC_PMCTRL_STOPM(LOW_PWR_MODE)|0x80;
#if (LOW_PWR_MODE == VLLSx_MODE)
  SMC_STOPCTRL &= ~SMC_STOPCTRL_VLLSM_MASK;
  SMC_STOPCTRL |= LOW_PWR_SMODE;
#endif
  /*wait for write to complete to SMC before stopping core */ 
  while((SMC_PMCTRL & SMC_PMCTRL_STOPM_MASK) != LOW_PWR_MODE);
  /* Now execute the stop instruction (deep sleep) to go into LLS */
  stop();
}

char *LOW_PWR_MODE_NAME[5]={
  "STOP",   "",   "VLPS",   "LLS",   "VLLSx"};

char *LOW_PWR_SMODE_NAME[4]={
  "VLLS0",   "VLLS1",   "VLLS2",   "VLLS3"};

int main (void)
{
      DisableInterrupts;
      enable_irq(LLWU_irq_no);
      enable_irq(LPTMR_irq_no);
      LLWU_ME = 1;  //Set up more modules to wakeup up
      LPTMR_init(); //LLS wake up after 100 ms
     
      printf("\nEntering %s mode\n\n\r",
            (LOW_PWR_MODE != VLLSx_MODE)?  LOW_PWR_MODE_NAME[LOW_PWR_MODE]
                                        :  LOW_PWR_SMODE_NAME[LOW_PWR_SMODE]);
      MCG_C6 &= ~MCG_C6_CME0_MASK;// set 0 before the MCG enters any Stop mode.
      STOP_Mode();
      MCG_C6 |= MCG_C6_CME0_MASK;
      LPTMR0_CSR &= ~LPTMR_CSR_TEN_MASK;
      printf("Back in RUN mode   \r");// dummy
      printf("Back in RUN mode \n\r");
      printf("FINISH\n");
}

--------[snip]-------

 

Best regards,

Yasuhiko Koumoto.

Outcomes