STM32单片机

1、前言

CM4内核的处理和CM3一样,内部都包含了一个SysTick定时器,SysTick 是一个24 位的倒计数定时器,当计到0 时,将从RELOAD 寄存器中自动重装载定时初值。只要不把它在SysTick 控制及状态寄存器中的使能位清除,就永不停息。这样可以用systick来实现延时定时功能,不用再占用系统定时器。systick也多用做系统的时钟节拍,如freeRTOS等OS,再启动调度器的时候,就会将systick配置成其系统时钟,给系统提供心跳。systick中有4个寄存器CTRL、LOAD、VAL、CALIB


2、systick配置注意事项

使用CubeMX配置生成的代码中,会自动生成一个 SystemClock_Config() 的函数,用于配置单片机时钟,其中就会配置systick

void SystemClock_Config()
{
    ...........
    LL_SYSTICK_SetClkSource(LL_SYSTICK_CLKSOURCE_HCLK);
    LL_SetSystemCoreClock(32000000);
#ifndef SYSTICK_IRQ
    LL_Init1msTick(32000000); //使能systick但是不开启systick中断
#else
    SysTick_Config(SystemCoreClock / 1000);//使能systick同时开启systick中断
#endif
}

但是这里 需要注意的是,是不是需要开启 systick 中断!!!!

1、如果只是想用systick来作为延时用,程序不想被中断打断,就只需要使能systick而不用开启systick中断,调用 LL_Init1msTick 即可

void LL_Init1msTick(uint32_t HCLKFrequency)
    ---> LL_InitTick(HCLKFrequency, 1000U);
        ---> __STATIC_INLINE void LL_InitTick(uint32_t HCLKFrequency, uint32_t Ticks)
            {
                  /* Configure the SysTick to have interrupt in 1ms time base */
                  SysTick->LOAD  = (uint32_t)((HCLKFrequency / Ticks) - 1UL);  /* set reload register */
                  SysTick->VAL   = 0UL;  /* Load the SysTick Counter Value */
                  SysTick->CTRL  = SysTick_CTRL_CLKSOURCE_Msk |
                                   SysTick_CTRL_ENABLE_Msk; /* Enable the Systick Timer */
            }

但是需要自己编写延时函数,不能使用HAL库提供的HAL_Delay()。原因如下:HAL_Delay的实现是依靠一个uwTickFreq变量,uwTickFreq是在HAL_IncTick中累加的,需要在 SysTick_Handler中断函数中周期调用,这样HAL_Delay才会有一个基准

__weak void HAL_IncTick(void)
{
  uwTick += uwTickFreq;
}
__weak uint32_t HAL_GetTick(void)
{
  return uwTick;
}
__weak void HAL_Delay(uint32_t Delay)
{
  uint32_t tickstart = HAL_GetTick();
  uint32_t wait = Delay;
 
  /* Add a period to guaranty minimum wait */
  if (wait < HAL_MAX_DELAY)
  {
    wait += (uint32_t)(uwTickFreq);
  }
 
  while((HAL_GetTick() - tickstart) < wait)
  {
  }
}

自定义的us延时

void my_delay_us(uint32_t nus)
{		
	uint32_t temp;	
	uint32_t fac_us = SystemCoreClock/1000000;	  //为系统时钟的1/1000000  	
	SysTick->LOAD   = nus*fac_us; 			      //时间加载	  		 
	SysTick->VAL    = 0x00;        			      //清空计数器
	SysTick->CTRL  |= SysTick_CTRL_ENABLE_Msk ;	  //开始倒数	  
	do
	{
		temp = SysTick->CTRL;
	}
	while((temp & 0x01) &&! (temp&(1 << 16)));	 //等待时间到达   
	SysTick->CTRL &= ~ SysTick_CTRL_ENABLE_Msk;	 //关闭计数器
	SysTick->VAL = 0X00;      					 //清空计数器	 
}

2、如果想用systick座系统的时钟节拍,需要开启systick中断,可以直接调用 SysTick_Config 来配置,也可以使用 HAL_Init 来配置,HAL_Init 配置最终也会调用 SysTick_Config 函数

 HAL_Init(void)
    ---> HAL_InitTick(uint32_t TickPriority)
        ---> SysTick_Config(uint32_t ticks)
            {
              if ((ticks - 1UL) > SysTick_LOAD_RELOAD_Msk)
              {
                return (1UL);                                                   /* Reload value impossible */
              }
            
              SysTick->LOAD  = (uint32_t)(ticks - 1UL);                         /* set reload register */
              NVIC_SetPriority (SysTick_IRQn, (1UL << __NVIC_PRIO_BITS) - 1UL); /* set Priority for Systick Interrupt */
              SysTick->VAL   = 0UL;                                             /* Load the SysTick Counter Value */
              SysTick->CTRL  = SysTick_CTRL_CLKSOURCE_Msk |
                               SysTick_CTRL_TICKINT_Msk   |
                               SysTick_CTRL_ENABLE_Msk;                         /* Enable SysTick IRQ and SysTick Timer */
              return (0UL);                                                     /* Function successful */
            }

这样配置完成之后,还需要再systick的中断中调用 osSystickHandler 和 HAL_IncTick

void SysTick_Handler(void)
{
	osSystickHandler();//为OS提供系统时钟节拍
	HAL_IncTick();//为HAL库提供时钟基准
}

版权声明:本文为CSDN博主 hurryddd 的原创文章,
遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
原文链接:
https://blog.csdn.net/m0_37845735/article/details/108439464

围观 2

1、前言

单片机内部的FLASH除了存储固件以外,经常将其分成多个区域,用来存储一些参数或存储OTA升级的待更新的固件,这时就会涉及到单片机内部FLASH的编程和擦除操作,STM32不同系列的单片机内部FLASH特性和扇区大小都不太一样,如果不注意这些细节,那就等着爬坑吧

1、FLASH的分区以及扇区大小

FLASH擦除是按照扇区擦的,所以这个很重要,在工程中全局搜索 FLASH_PAGE_SIZE 宏就可以查看该芯片的页(扇区)大小,改宏在 stm32xxx_hal_flash.h中有定义

2、FLASH擦拭后的状态

F1和F4系列的芯片FLASH在擦除后会是0xFFFFFFFF,而L1系列的芯片FLASH在擦除后是0x00000000!!!!!

3、FLASH的编程速度

L1芯片内部FLASH编程速度比F1慢50倍!!!所以在使用L1芯片写入数据时相对于F1慢是正常的

2、STM32 F1、F4、L1系列内部FLASH分区及大小

1、STM32F1系列

对于F1系列的芯片大容量产品的FLASH主存储器每页大小为2K,如【下图】,而中容量和小容量的产品每页大小只有1K


2、STM32F4系列

分为2个Bank,每个Bank分为12个扇区,前4个扇区为16KB大小,第五个扇区是64KB大小,剩下的7个扇区都是128K大小


3、STM32L1系列

3、STM32 F1、F4、L1系列内部FLASH编程时间

信息参考对应芯片的数据手册的 Electrical characteristics 章节


1、STM32F1系列

可以看出F1系列内部FLASH页擦除时间最大为40ms,半字写入的时间为52.2us,比如按字写入1024字节数据,需要26.8ms,还是比较快的


2、STM32F4系列

可以看出F4系列内部不同扇区擦除时间也不一样的,字写入的时间为16us,比如按字写入1024字节数据,只需要4ms,非常快


3、STM32L1系列

可以看出L1系列内部FLASH页擦除和编程的时间都是3.28ms,比如按字写入1024字节数据,需要840ms,非常慢;但是擦除是比较快的


版权声明:本文为CSDN博主 hurryddd 的原创文章,
遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
原文链接:
https://blog.csdn.net/m0_37845735/article/details/108439644

围观 9

基于STM32F103单片机的IAP实现(虽然该篇文章不会详细写出实现细节,但是会从一个全局的角度讲述,实际的实现细节只需根据datasheet即可完成)。

一、基础概念

什么是IAP?IAP即在应用中编程(In-Application Programming IAP),简单的说就像是一个用户自定义的升级程序。实际上,STM32单片机的程序烧写有多种方法,可以用JTAG,也可用串口通过ISP软件烧写新程序。

JTAG的方式需要专用的烧写工具,在产品布置到现场后,更新产品程序比较麻烦,而通过串口的ISP软件升级方法可以直接使用常见的串口线升级程序,十分方便,这种方法用的是ISP。ISP可以说是单片机默认的bootloader,

正常情况下,单片机系统启动后,会直接从用户程序执行,而升级程序时,单片机会进入bootloader,在ISP中一直运行。ISP虽然方便了升级,但是还是没法解决用户自定义和远程升级的问题。对于用户来说,有时候可能需要在单片机

flash不同地址烧写多个应用程序,用于根据不同条件启动不同应用程序;有时候,产品分布到全国各地,去所有现场升级程序明显不理智,解决方法是将升级程序放到服务器上,发送远程升级指令,设备进入IAP升级程序,从远程

获取升级应用程序,实现在线升级。

二、IAP实现

1. 硬件

STM32单片机的启动方式有三种,


单片机根据boot0和boot1的引脚来确定启动方式。主闪存存储器即为用户程序空间,IAP启动将会从这里开始,系统存储器是ISP启动,内置SRAM不讨论。正常情况下,boot0管脚接入低电平,单片机从应用程序开始执行;当使用ISP升级时,boot0为1,boot1为0,系统进入ISP程序,等待串口升级,升级完成后,需要断电,改变boot电平,重新启动,让单片机从应用程序执行。(所以ISP升级时,还需要关注有关boot脚的电平开关问题。)

IAP升级不需要改变任何管脚电平,因为它实际上就是一个应用程序,只是让单片机启动时先执行它,执行完后,跳转到真正的应用程序执行。

注意:单片机第一次烧写时,是需要通过JTAG或ISP烧写IAP的,如果打算用ISP,那最好留一个boot脚的硬件拨码开关用于首次ISP升级hex文件。

2. 软件

弄清楚硬件之后,就知道什么样的硬件boot对应什么样的启动方式。加入IAP之后,系统启动时会先执行IAP程序用于判断是否达到升级条件和执行什么样的升级配置,相应的逻辑类似于下图:


用户可以根据自己的需求来设计IAP程序,详细设计可以参考ST官方资料:

《使用STM32F10xxx的USART 实现在应用中编程》,而且官方也给出了例程,资料比较全面,实现起来也很简单。

最后,提醒注意一点的是,在IAP后面的应用程序都要在系统启动时重新定义中断向量表。

本文转自:https://www.cnblogs.com/Victor-Tian/p/5958851.html

围观 15
订阅 RSS - STM32单片机