(24)STM32——待机唤醒(低功耗)笔记

目录

学习目标

运行结果

待机唤醒

模式

待机模式

寄存器

配置

代码

总结 


学习目标

        本节我们讲解的是有关待机唤醒的知识,这部分知识在51中并未涉及到,我感觉还是有点意思的,有点类似与我们手机的锁屏功能和关机功能,只是选择了不同的低功耗模式。好了,接下来我们就来介绍一下待机唤醒的相关知识吧!

运行结果

待机唤醒1

待机唤醒2

待机唤醒

        在系统或电源复位以后,微控制器处于运行状态。运行状态下的 HCLK 为 CPU 提供时钟,内核执行程序代码。当 CPU 不需继续运行 时,可以利用多个低功耗模式来节省功耗,例如等待某个外部事件时。

模式

  1. 睡眠模式:内核停止,外设如NVIC,系统时钟Systick仍运行。
  2. 停止模式:所有时钟都已停止。1.8V内核电源工作。PLL,HIS和HSE RC振荡器功能禁止。寄存器和SRAM内容保留。
  3. 待机模式:1.8V内核电源关闭。只有备份寄存器和待机电路维持供电。寄存器和SRAM内容全部丢失。实现最低功耗。
  4. 在运行模式下,可以通过下面方式降低功耗:

    1、降低系统时钟。

    2、关闭APB和AHB总线上未被使用的外设时钟。

        这三种模式的功耗是逐渐降低的,特别是待机模式,功耗特别低,最低只需要 2.2uA 左右的电流。停机模式是次低功耗的,其典型的电流消耗在 350uA 左右。最后就是睡眠模式了。根据最低电源消耗,最快启动时间和可用的唤醒源等条件,选择一种最佳的低功耗模式。

待机模式

        F407的待机模式可实现 STM32F4 的最低功耗。该模式是在 CM4 深睡眠模式时关闭电压调节器。整个 1.2V 供电区域被断电。PLL、 HSI 和 HSE 振荡器也被断电。SRAM 和寄存器内容丢失。除备份域(RTC 寄存器、RTC 备份 寄存器和备份 SRAM)和待机电路中的寄存器外,SRAM 和寄存器内容都将丢失。而且有一个重要的点就是F407需要清零对应的RTC标志。

寄存器

        还是一样,不做详细介绍。 

配置

我们前面说了F407需要清除相应的标志位才能开启待机模式。

  1. 禁止 RTC 中断(ALRAIE、ALRBIE、WUTIE、TAMPIE 和 TSIE 等)。
  2. 清零对应中断标志位。
  3. 清除 PWR 唤醒(WUF)标志(通过设置 PWR_CR 的 CWUF 位实现)。
  4. 重新使能 RTC 对应中断。
  5. 进入低功耗模式。 

 1、使能电源时钟。

RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE); //使能 PWR 外设时钟

2、设置 WK_UP 引脚作为唤醒源。

PWR_WakeUpPinCmd(ENABLE); //使能唤醒管脚功能

3、设置 SLEEPDEEP 位,设置 PDDS 位,执行 WFI 指令,进入待机模式。

PWR_EnterSTANDBYMode(void);

4、最后编写 WK_UP 中断函数。

代码

实验一的代码。 

#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"
#include "key.h"
 
int main(void)
{ 
 
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置系统中断优先级分组2
	delay_init(168);    //初始化延时函数
	uart_init(115200);	//初始化串口波特率为115200
	LED_Init();				//初始化LED  
	KEY_Init();
	LED0 = 0;
	
	while(1)
	{
		if(KEY_Scan(0) == KEY0_PRES){
			RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR,ENABLE );
			PWR_BackupAccessCmd(ENABLE);//后备区域访问使能

		//这里我们就直接关闭相关RTC中断
		RTC_ITConfig(RTC_IT_TS|RTC_IT_WUT|RTC_IT_ALRB|RTC_IT_ALRA,DISABLE);//关闭RTC相关中断,可能在RTC实验打开了。
		RTC_ClearITPendingBit(RTC_IT_TS|RTC_IT_WUT|RTC_IT_ALRB|RTC_IT_ALRA);//清楚RTC相关中断标志位。
			
		PWR_WakeUpPinCmd(ENABLE );	
		PWR_ClearFlag(PWR_FLAG_WU);	
		PWR_EnterSTANDBYMode();
			
			}
	}
}

实验二的代码。

#include "wkup.h"
#include "led.h"
#include "delay.h"	
#include "usart.h"																	   
 
//系统进入待机模式
void Sys_Enter_Standby(void)
{		
  while(WKUP_KD);			//等待WK_UP按键松开(在有RTC中断时,必须等WK_UP松开再进入待机)
 
	RCC_AHB1PeriphResetCmd(0X04FF,ENABLE);//复位所有IO口
	
	RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);//使能PWR时钟		 
	 
	PWR_BackupAccessCmd(ENABLE);//后备区域访问使能

	//这里我们就直接关闭相关RTC中断
	RTC_ITConfig(RTC_IT_TS|RTC_IT_WUT|RTC_IT_ALRB|RTC_IT_ALRA,DISABLE);//关闭RTC相关中断,可能在RTC实验打开了。
	RTC_ClearITPendingBit(RTC_IT_TS|RTC_IT_WUT|RTC_IT_ALRB|RTC_IT_ALRA);//清楚RTC相关中断标志位。
	
	PWR_ClearFlag(PWR_FLAG_WU);//清除Wake-up 标志
	
	PWR_WakeUpPinCmd(ENABLE);//设置WKUP用于唤醒
	
	PWR_EnterSTANDBYMode();	//进入待机模式
	 
}
//检测WKUP脚的信号
//返回值1:连续按下3s以上
//      0:错误的触发	
u8 Check_WKUP(void) 
{
	u8 t=0;
	u8 tx=0;//记录松开的次数
	LED0=0; //亮灯DS0 
	while(1)
	{
		if(WKUP_KD)//已经按下了
		{
			t++;
			tx=0;
		}else 
		{
			tx++; 
			if(tx>3)//超过90ms内没有WKUP信号
			{
				LED0=1;
				return 0;//错误的按键,按下次数不够
			}
		}
		delay_ms(30);
		if(t>=100)//按下超过3秒钟
		{
			LED0=0;	  //点亮DS0 
			return 1; //按下3s以上了
		}
	}
}  
//中断,检测到PA0脚的一个上升沿.	  
//中断线0线上的中断检测
void EXTI0_IRQHandler(void)
{ 		    		    				     		    
  EXTI_ClearITPendingBit(EXTI_Line0); // 清除LINE10上的中断标志位
	if(Check_WKUP())//关机?
	{		  
		Sys_Enter_Standby(); //进入待机模式 
	}
} 

//PA0 WKUP唤醒初始化
void WKUP_Init(void)
{	  
  GPIO_InitTypeDef  GPIO_InitStructure;
	NVIC_InitTypeDef   NVIC_InitStructure;
	EXTI_InitTypeDef   EXTI_InitStructure;
	
	RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);//使能GPIOA时钟 
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_SYSCFG, ENABLE);//使能SYSCFG时钟
	
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0; //PA0
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN;//输入模式
  GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; 
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; 
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_DOWN;//下拉
  GPIO_Init(GPIOA, &GPIO_InitStructure);//初始化	

	//(检查是否是正常开)机    		 
  if(Check_WKUP()==0)
	{
		Sys_Enter_Standby();	//不是开机,进入待机模式  
	}
	SYSCFG_EXTILineConfig(EXTI_PortSourceGPIOA, EXTI_PinSource0);//PA0 连接到中断线0
	
 
  EXTI_InitStructure.EXTI_Line = EXTI_Line0;//LINE0
  EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;//中断事件
  EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising; //上升沿触发 
  EXTI_InitStructure.EXTI_LineCmd = ENABLE;//使能LINE0
  EXTI_Init(&EXTI_InitStructure);//配置
	
	
	NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn;//外部中断0
  NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 0x02;//抢占优先级2
  NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0x02;//子优先级2
  NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;//使能外部中断通道
  NVIC_Init(&NVIC_InitStructure);//配置NVIC
	
 
}
#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"
#include "wkup.h"
  
int main(void)
{ 
 
	NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置系统中断优先级分组2
	delay_init(168);    //初始化延时函数
	uart_init(115200);	//初始化串口波特率为115200
	LED_Init();				//初始化LED  
	WKUP_Init();				//待机唤醒初始化	 
	while(1)
	{
		LED0=!LED0;
		delay_ms(250);//延时250ms
	}
}

总结 

        本节介绍的是低功耗模式,主要介绍了待机模式,希望对大家有所帮助,谢谢大家了!

  • 4
    点赞
  • 19
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
1设计要求 要求系统按如下方式进入和退出睡眠模式: 在系统启动2秒后,将RTC在3秒钟之后配置为产生一个报警事件,接着通过WFI指令使系统进入停机模式。 如果要唤醒系统到正常模式,可通过按Key按钮;否则,在3秒钟后,会产生RTC报警中断自动将系统唤醒。 一旦退出停机模式,系统时钟被配置成先前的状态(在停机模式下,外部高速振荡器HSE和PLL是不可用的)。 经过一段延时之后,系统将再次进入停机状态,并可按上述操作无限重复。 2 硬件电路设计 硬件电路采用与7.1小节应用实例一样硬件电路,可见图7-10。其中Key按钮用于通过PB9产生一个外部中断, LED1、LED2、LED3、LED4则用于显示处理器所处的模式和中断触发情况。 3 软件程序设计 根据任务要求,程序内容主要包括: (1) 配置GPIOB口,配置RTC,配置外部中断; (2) 配置PB口第9个引脚作为外部中断,下降延触发;配置RTC报警中断,上升沿触发; (3) 两个中断服务子程序的内容分别是:切换LED2和LED3灯的状态; 整个工程包含3个源文件:STM32F10x.s、stm32f10x_it.c和main.c,其中STM32F10x.s为启动代码,所有中断 服务子程序均在stm32f10x_it.c中,其它函数则在main.c中。下面分别介绍相关的函数,具体程序清单见参考程序。 函数SYSCLKConfig_STOP用于当处理器从停机模式唤醒之后,配置系统时钟、使能HSE和PLL,并以PLL作为系统时钟源。当处理器处理停机模式的时候,HSE、PLL是不可用的。 函数GPIO_Configuration用于配置GPIO的PC6、PC7、PC8、PC9和PB9。 函数EXTI_Configuration用于配置外部中断线9(PB9)和17(RTC报警)。 函数NVIC_Configuration配置NVIC及中断向量表,这里主要是配置外部中断线9和17。 函数EXTI9_5_IRQHandler处理按钮Key(PB9)所触发的中断,其主要作用是将LED2灯的状态翻转一次。 函数RTCAlarm_IRQHandler处理RTC报警所触发的中断,其主要作用事将LED3 灯的状态翻转一次,如果设置了唤醒标志则清除之。 运行过程: (1) 使用Keil uVision3 通过ULINK 2仿真器连接EduKit-M3实验平台,打开实验例程目录PWR_TEST子目录下的PWR.Uv2 例程,编译链接工程; (2) 选择软件调试模式,点击MDK 的Debug菜单,选择Start/Stop Debug Session项或Ctrl+F5键,在逻 辑分析仪中添加GPIOC_ODR.6、GPIOC_ODR.7、GPIOC_ODR.8、GPIOC_ODR.9,点击Run按钮即可在逻辑分析 仪中看到如图7-14,还可用Peripherals-General Port-GPIOB来模拟KEY按钮的动作; (3) 选择硬件调试模式,选择Start/Stop Debug Session项或Ctrl+F5键,下载程序并运行,观察LED灯 的变化情况。注意,当目标系统进入停机模式之后,将无法使用仿真器进行调试了; (4) 退出Debug模式,打开Flash菜单>Download,将程序下载到EduKit-M3实验平台的Flash中,按RESET键复位,观察 LED灯的情况,正常情况应为:系统处于运行模式时LED1亮、LED4灭;系统处于停机状态时LED1灭、LED4亮; 当按下KEY按钮时LED2灯状态发生反转;当发生RTC报警时LED3状态发生反转。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值