STM32GX低功耗学习笔记一

最近要用到低功耗功能,看了下手册,把学习过程记录下,其中也有一些不明白的地方期望和大家进行交流。

首先来看看低功耗模式有哪些:

再看看怎么进入低功耗:

在这里我选择了STOP0模式:

 

在这里,我有一点疑惑就是进入STOP0之前,手册说不能有事件或者中断位产生,否则就不能进入低功耗模式

而是继续运行。这里怎么避免产生事件或者中断位?

上代码:

1、使能PWR时钟

    /*##-1- Enables the PWR Clock and Enables access to the backup domain #######*/
    /* To change the source clock of the RTC feature (LSE, LSI), you have to:
     - Enable the power clock
     - Enable write access to configure the RTC clock source (to be done once after reset).
     - Reset the Back up Domain
     - Configure the needed RTC clock source */
    LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_PWR);

    LL_PWR_EnableBkUpAccess();

2、配置RTC

static void rtc_init(void)
{
    if(!LL_RCC_LSI_IsReady()){
        LL_RCC_LSI_Enable();
        NOP();
        NOP();
        NOP();
        NOP();
        while(!LL_RCC_LSI_IsReady());//Èý¸öLSIÖÜÆÚÖ®ºó²Å¸üÐÂ
    }
    LL_RCC_ForceBackupDomainReset();
    LL_RCC_ReleaseBackupDomainReset();
    LL_RCC_SetRTCClockSource(LL_RCC_RTC_CLKSOURCE_LSI);

    /* USER CODE BEGIN RTC_Init 0 */

    /* USER CODE END RTC_Init 0 */

    LL_RTC_InitTypeDef RTC_InitStruct = {0};
    LL_RTC_TimeTypeDef RTC_TimeStruct = {0};
    LL_RTC_DateTypeDef RTC_DateStruct = {0};
    LL_RTC_AlarmTypeDef RTC_AlarmStruct = {0};

    /* Peripheral clock enable */
    LL_RCC_EnableRTC();

    /* USER CODE BEGIN RTC_Init 1 */
    /* Enable RTC APB clock  */
    LL_APB1_GRP1_EnableClock(LL_APB1_GRP1_PERIPH_RTC);
    /* USER CODE END RTC_Init 1 */
    RTC_InitStruct.HourFormat = LL_RTC_HOURFORMAT_24HOUR;
    RTC_InitStruct.AsynchPrescaler = RTC_ASYNCH_PREDIV;
    RTC_InitStruct.SynchPrescaler = RTC_SYNCH_PREDIV;
    LL_RTC_Init(RTC, &RTC_InitStruct);
    RTC_TimeStruct.Hours = 0x12;
    RTC_TimeStruct.Minutes = 0x00;
    RTC_TimeStruct.Seconds = 0x00;
    LL_RTC_TIME_Init(RTC, LL_RTC_FORMAT_BCD, &RTC_TimeStruct);
    RTC_DateStruct.WeekDay = LL_RTC_WEEKDAY_FRIDAY;
    RTC_DateStruct.Month = LL_RTC_MONTH_DECEMBER;
    RTC_DateStruct.Day = 0x29;
    RTC_DateStruct.Year = 0x16;
    LL_RTC_DATE_Init(RTC, LL_RTC_FORMAT_BCD, &RTC_DateStruct);
    /** Enable the Alarm A 
    */
    RTC_AlarmStruct.AlarmTime.Hours = 0x12;
    RTC_AlarmStruct.AlarmTime.Minutes = 0x00;
    RTC_AlarmStruct.AlarmTime.Seconds = 0x05;
    RTC_AlarmStruct.AlarmMask = LL_RTC_ALMA_MASK_DATEWEEKDAY;
    RTC_AlarmStruct.AlarmDateWeekDaySel = LL_RTC_ALMA_DATEWEEKDAYSEL_DATE;
    RTC_AlarmStruct.AlarmDateWeekDay = 0x1;
    LL_RTC_ALMA_Init(RTC, LL_RTC_FORMAT_BCD, &RTC_AlarmStruct);
    /* USER CODE BEGIN RTC_Init 2 */

    /* Disable the write protection for RTC registers */
    LL_RTC_DisableWriteProtection(RTC);

    /* Enable Alarm*/
    LL_RTC_ALMA_Enable(RTC);

    /* Clear the Alarm interrupt pending bit */
    LL_RTC_ClearFlag_ALRA(RTC);

    /* Enable IT Alarm */
    LL_RTC_EnableIT_ALRA(RTC);

    /* Enable the write protection for RTC registers */
    LL_RTC_EnableWriteProtection(RTC);

    /* RTC Alarm Interrupt Configuration: EXTI configuration */
    LL_EXTI_ClearRisingFlag_0_31 (LL_EXTI_LINE_19);
    LL_EXTI_EnableIT_0_31(LL_EXTI_LINE_19);
    LL_EXTI_EnableRisingTrig_0_31(LL_EXTI_LINE_19);

    /*## Configure the NVIC for RTC Alarm ##################################*/
    NVIC_SetPriority(RTC_TAMP_IRQn, 0x0F);
    NVIC_EnableIRQ(RTC_TAMP_IRQn);

    /* USER CODE END RTC_Init 2 */
}

3、中断配置

void RTC_TAMP_IRQHandler(void)
{
    /* Get the Alarm interrupt source enable status */
    static uint8_t i=1;
    if (LL_RTC_IsEnabledIT_ALRA(RTC) != 0)
    {
        /* Get the pending status of the Alarm Interrupt */
        if (LL_RTC_IsActiveFlag_ALRA(RTC) != 0)
        {
            /* Alarm callback */
            //Alarm_Callback();
            SystemClock_Config();
            TRACE_INFO("RTC=%d\r\n",i);
            i++;
            /* Clear the Alarm interrupt pending bit */
            LL_RTC_ClearFlag_ALRA(RTC);
        }
    }
    /* Clear the EXTI's Flag for RTC Alarm */
    LL_EXTI_ClearFallingFlag_0_31(LL_EXTI_LINE_19);
}

4、进入STOP0模式

    LL_RTC_ClearFlag_ALRA(RTC);
    LL_EXTI_ClearRisingFlag_0_31 (LL_EXTI_LINE_19);
    LL_PWR_SetPowerMode(LL_PWR_MODE_STOP0);
    //LL_PWR_SetPowerMode(LL_PWR_MODE_STANDBY);
    LL_LPM_EnableDeepSleep();
    //LL_PWR_SetPowerMode(LL_PWR_MODE_STOP0);
#if defined ( __CC_ARM)
    __force_stores();
#endif
    //__WFE();
    __WFI();

这里有一点问题,就是WIE不起作用,目前没有想明白。

如果是进入STANDBY模式,仅仅把LL_PWR_SetPowerMode(LL_PWR_MODE_STOP0);

修改为LL_PWR_SetPowerMode(LL_PWR_MODE_STANDBY);即可

经过试验,得出如下结论:

1、STANDBY被RTC唤醒,则会复位;

2、STOP0被RTC唤醒,则会继续运行,但是时钟需要重新配置下。

目前能够休眠和唤醒了,哎,我也该睡觉了,困,剩下的问题以后找到答案再贴上来。。。。。。。

 

 

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值