stm32最小系统板实现待机模式与唤醒(一)

初学者分享,各位大佬指正!!

项目:stm32f103c8t6待机模式与唤醒

现象:

正常模式:按下PB5,实现控制PA1小灯(非开关小灯);

待机模式:按下PA0 3s,实现待机,PA1小灯灭;

唤醒:按一下PA0,恢复到正常模式;

接线图:

1.待机模式/唤醒说明:

1.1 待机条件:

1.当进入睡眠模式时,使能外部的SLEEPDEEP信号,以允许停止系统时钟。

2.电源控制寄存器(PWR_CR)中PDDS位,设置为1。

3.电源控制/状态寄存器(PWR_CSR) 中EWUP位,设置为1。

1.2 唤醒条件(4选1):

条件:WKUP引脚的上升沿(给PA0一个高电平)(选择这一个)

2. 代码:

四个.c文件,直接复制就能跑(按照上图接好线)

2.1 Standby.c

#include "stm32f10x.h" 
#include "Standby.h"
#include "Delay.h"
#include "LED.h"


/* 按下PB5按键 正常点亮关闭小灯PA1,长按3sPA0进入待机模式,小灯熄灭,按一下PA0唤醒*/

//待机模式
void Sys_Standby(void)
{  
    RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);    //使能PWR外设时钟
    PWR_WakeUpPinCmd(ENABLE);  //使能唤醒管脚功能,在WkUp的上升沿进行
    PWR_EnterSTANDBYMode();      //进入待机(STANDBY)模式 设置相应的进入条件(已经封装成了完整的函数)     
}

//系统进入待机模式
//1.复位所有的io
//2.待机模式设置
void Sys_Enter_Standby(void)
{             
    RCC_APB2PeriphResetCmd(0x01fc,DISABLE);//复位
    Sys_Standby();//启动待机模式
}

//检测WKUP脚的信号
u8 Check_WKUP(void) 
{
    uint16_t t=0;    //记录按下的时间
    while(1)
    {
     
        if(GPIO_ReadInputDataBit(GPIOA,GPIO_Pin_0))//判断按下的时间
        {
            t++;            //已经按下了 
            Delay_ms(30);
            if(t>=100)        //按下超过3秒钟
            {
                return 1;     //按下3s以上了
            }
        }
        else 
        { 
            return 0;
        }

    }
}  


//中断
void EXTI9_5_IRQHandler(void)

        EXTI_ClearITPendingBit(EXTI_Line5); // 清除中断标志位
        
        if (Check_WKUP()) // 检查按键是否长按3秒
        {        
            Sys_Enter_Standby(); // 进入待机模式
        }
    
}

//PA0 WKUP唤醒初始化
void WKUP_Init(void)
{    
    GPIO_InitTypeDef  GPIO_InitStructure;            
    NVIC_InitTypeDef NVIC_InitStructure;
    EXTI_InitTypeDef EXTI_InitStructure;
 
//    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA | RCC_APB2Periph_AFIO, ENABLE);//使能GPIOA和复用功能时钟
 
    GPIO_InitStructure.GPIO_Pin =GPIO_Pin_0;    
    GPIO_InitStructure.GPIO_Mode =GPIO_Mode_IPD; 
    GPIO_Init(GPIOB, &GPIO_InitStructure);    

    //使用外部中断方式
     GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource0);    //中断线0连接GPIOA.0
 
    EXTI_InitStructure.EXTI_Line = EXTI_Line0;    //设置按键所有的外部线路
    EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt;            //设外外部中断模式:EXTI线路为中断请求
    EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising;  //上升沿触发
       EXTI_InitStructure.EXTI_LineCmd = ENABLE;
    EXTI_Init(&EXTI_InitStructure);    // 初始化外部中断
 
    NVIC_InitStructure.NVIC_IRQChannel = EXTI0_IRQn; //使能按键所在的外部中断通道
    NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 2; //先占优先级2级
    NVIC_InitStructure.NVIC_IRQChannelSubPriority = 2; //从优先级2级
    NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //使能外部中断通道
    NVIC_Init(&NVIC_InitStructure); //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器
 
//    if(Check_WKUP()) Sys_Standby();    //按键未按下或按下时间不足 3 秒,进入待机模式  
}

 
2.2 main.c

#include "stm32f10x.h"                  // Device header
#include "Delay.h"
#include "Key.h"
#include "LED.h"
#include "Standby.h"

uint8_t Key = 0;

int main(void)
{
    GPIO_Config();
    LED_Init();
    WKUP_Init();
    
    while (1)
    {
        Key = Key_GetNum();
        if (Key == 1)
        {
            GPIO_WriteBit(GPIOA, GPIO_Pin_1,Bit_SET);
            Delay_ms(100);
            Key = 0;
        }
        GPIO_WriteBit(GPIOA, GPIO_Pin_1,Bit_RESET);
    }
}
 

2.3 LED.c

#include "stm32f10x.h"                  // Device header

void LED_Init(void)
{
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE);
    
    GPIO_InitTypeDef GPIO_InitStructure;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_Out_PP;
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_1;
    GPIO_InitStructure.GPIO_Speed = GPIO_Speed_50MHz;
    GPIO_Init(GPIOA, &GPIO_InitStructure);
}

2.4 Key.c

#include "stm32f10x.h"                  // Device header
#include "Delay.h"


// 初始化GPIO
void GPIO_Config(void) 
{
    // 使能GPIOA和GPIOB时钟
    RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE);
  
    GPIO_InitTypeDef GPIO_InitStructure;
  
    // 配置PB5为浮空输入模式
    GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5;
    GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPU;
    GPIO_Init(GPIOB, &GPIO_InitStructure);
}


uint8_t Key_GetNum(void)
{
    uint8_t Keyum = 0;
    if (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_5) == 0)
    {
        Delay_ms(20);
        while (GPIO_ReadInputDataBit(GPIOB, GPIO_Pin_5) == 0);
        Delay_ms(20);
        Keyum = 1;
    }
    
    
    return Keyum;
}

 参考:

1.STM32之待机唤醒 (转载)_stm32待机唤醒-CSDN博客

2.Stm32待机模式的进入与唤醒_stm32单片机休眠唤醒 程序-CSDN博客

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值