1 概述
1.1 资源概述
开发板:正点原子STM32F103 Nano开发板
CUBEMX版本:1.3.0
MDK版本:5.23
主控芯片型号:STM32F103RBT6
1.2 实现功能
1,修改:将HAL官方例程工程PWR提出,driver对应的多余文件进行删除,形成一个独立的工程包;
2,include路径进行了重新定义;
3,LED(DS0)灯点亮5S,然后进入待机模式,按下KEYUP按键退出待机模式;
4,支持正点原子F103 nano开发板。
2 程序实现
2.1实现原理
待机模式的进入和退出条件如下表。
芯片对应的PA00为芯片的Wakeup功能键,对应正点原子wake
up按键。我们需要将此按键初始化这个功能即可。
2.2 程序源码
在原官方例程上增加了LED2,用来指示单板是否进入了待机模式。LED2采用单板上的DS0。
- int main(void)
- {
- /* STM32F103xB HAL library initialization:
- - Configure the Flash prefetch
- - Systick timer is configured by default as source of time base, but user
- can eventually implement his proper time base source (a general purpose
- timer for example or other time source), keeping in mind that Time base
- duration should be kept 1ms since PPP_TIMEOUT_VALUEs are defined and
- handled in milliseconds basis.
- - Set NVIC Group Priority to 4
- - Low Level Initialization
- */
- HAL_Init();
- /* Configure the system clock to 64 MHz */
- SystemClock_Config();
- /* Configure the system Power 配置系统电源 */
- SystemPower_Config();
- /* Check and handle if the system was resumed from Standby mode 确认系统是否从待机模式恢复*/
- if (__HAL_PWR_GET_FLAG(PWR_FLAG_SB) != RESET)
- {
- /* Clear Standby flag 如果恢复则清楚待机标志位*/
- __HAL_PWR_CLEAR_FLAG(PWR_FLAG_SB);
- }
- /* -2- Configure IO in output push-pull mode to drive external LEDs初始化LED2灯,上电时点亮 */
- LED2_GPIO_CLK_ENABLE();
- GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
- GPIO_InitStruct.Pull = GPIO_PULLUP;
- GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
- GPIO_InitStruct.Pin = LED2_PIN;
- HAL_GPIO_Init(LED2_GPIO_PORT, &GPIO_InitStruct);
- HAL_GPIO_WritePin(LED2_GPIO_PORT,LED2_PIN,GPIO_PIN_RESET);
- /* Insert 5 seconds delay 延时5S*/
- HAL_Delay(5000);
- /* The Following Wakeup sequence is highly recommended prior to each Standby mode entry
- mainly when using more than one wakeup source this is to not miss any wakeup event.
- - Disable all used wakeup sources,
- - Clear all related wakeup flags,
- - Re-enable all used wakeup sources,
- - Enter the Standby mode.
- */
- /* Disable all used wakeup sources: PWR_WAKEUP_PIN1 */
- HAL_PWR_DisableWakeUpPin(PWR_WAKEUP_PIN1);
- /* Clear all related wakeup flags*/
- __HAL_PWR_CLEAR_FLAG(PWR_FLAG_WU);
- /* Enable WakeUp Pin PWR_WAKEUP_PIN1 connected to PA.00 使能PA00的唤醒功能*/
- HAL_PWR_EnableWakeUpPin(PWR_WAKEUP_PIN1);
- /* Enter the Standby mode进入待机模式 */
- HAL_PWR_EnterSTANDBYMode();
- /* This code will never be reached!如果没有进入待机模式则进入此循环 */
- while (1)
- {
- /* Insert delay 500 ms */
- HAL_Delay(500);
- HAL_GPIO_TogglePin(LED2_GPIO_PORT, LED2_PIN); //用于检测是否进入待机模式,若没进入将500ms一次闪烁LED2灯
- }
- }
复制代码
其中HAL_PWR_EnableWakeUpPin(PWR_WAKEUP_PIN1)函数的作用是使能PWR_CSR的相关寄存器,用于使能唤醒按键的操作。
HAL_PWR_EnterSTANDBYMode 函数则是对进入的条件写了一遍
- void HAL_PWR_EnterSTANDBYMode(void)
- {
- /* Select Standby mode */
- SET_BIT(PWR->CR, PWR_CR_PDDS);
- /* Set SLEEPDEEP bit of Cortex System Control Register */
- SET_BIT(SCB->SCR, ((uint32_t)SCB_SCR_SLEEPDEEP_Msk));
- /* This option is used to ensure that store operations are completed */
- #if defined ( __CC_ARM)
- __force_stores();
- #endif
- /* Request Wait For Interrupt */
- __WFI();
- }
复制代码
移植野火程序的经验总结
在使用待机功能时,需要一开始就使能时钟。函数名为
- _HAL_RCC_PWR_CLK_ENABLE();
复制代码
否则将会导致进入待机模式里无法使用WKUP唤醒。使用WKUP按键时,需要一开始对其按键进行初始化为输入下拉,否则将出现不按下WKUP也能自动唤醒的情况。
3 SVN简介
SVN运行用户将程序保存在云端(第三方的服务器),方便使用者备份,回退版本,保存多个版本等,是一个非常好用的工具,我使用的是SVNBUCKET,免费版本提供100M的空间,对于STM简单的例程是足够用了。如果文件进行了修改,文件符号会出现一个问号,可以进行提交(传到网上的服务器上),将服务器版本进行更新。假如改错了,可以回滚到之前版本,而不用关心是否已经提交。还可以对提交的代码进行比较。这里不详细介绍,可以在B站上找到介绍视频。使用非常灵活。
下面是我在SVNBUCKET上提交的两个项目,使用了3MB。当然对于自己开公司的或者重要大项目还是建议保存本地备份,以免SVN服务提供商哪天黄了或者跑路。
4官方例程库driver精简
为了充分利用SVN的100M,我对Driver文件夹进行了精简,下面是精简的文件夹结构,删除掉多余LL库,第三方器件支持等
BSP即为Board support pack,文件夹下为单板支持的一个头文件和一个C文件
Device为芯片平台支持的文件夹,三个文件。
Hal_drive 文件夹即为Hal函数的库文件(函数声明)和C文件(函数定义)。可以依据项目需要进行裁剪。
项目的.S文件放置工程文件夹中MDK_ARM中。最后精简后的工程可以进行独立编译,大小仅为5MB
头文件进行了重新指向,否则工程将会报错,找不到目标文件。
5实验结果
实验结果在Nano板上实现,符合预期。
|