STM32F1开发指南《精英版》库函数版---第五章第一,系统init时钟初始化函数使用V3.5版本的库函数,该函数在系统启动后自动调用。
在startup_stm32f10x_xx.s文件中:
; resethandlerreset _ handlerprocexportreset _ handler [ weak ] import _ mainimportsysteminitldrr 0,=system init blx r0 ldr r0
初始化后的状态: SYSCLK (系统时钟) 72MHz
AHB总线时钟(使用SYSCLK ) 72MHz
APB1总线时钟(PCLK1) 36MHz
APB2总线时钟(PCLK2) 72MHz
PLL时钟72MHz
初始化后,可以从变量SystemCoreClock中获取系统变量。 如果SYSCLK=72MHz,则变量SystemCoreClock=72000000。 二、有Systick滴答计时器1、Systick计时器、CM3、CM4核心芯片。 2、Systick计时器常用于延时或实时系统的心跳时钟
节约MCU资源,无需浪费计时器。 例如,在UCOS中,时分复用需要最小的时间戳,一般在STM32 UCOS系统中使用Systick作为UCOS心跳时钟。
3、Systick计时器是系统滴答的计时器,是24位倒计时计时器。 计数到0后,从RELOAD寄存器中自动重新加载计时器初始值。 只要不清除Systick控件和状态寄存器的使能位,它就不会停止,并在休眠模式下工作。
4、SysTick计时器与NVIC捆绑在一起,用于产生SysTick异常(异常编号: 15 )。 5、也可以设定Systick中断的优先顺序。 6、4个Systick寄存器(参考Cortex M3权威指南):CTRL SysTick控件和状态寄存器
位0:ENABLE有效位:必须设置1才能使用Systick计时器
是否发生位1(Tickint )中断
位2:CLKSOURCE时钟源(由函数SysTick_CLKSourceConfig配置) ) ) )
位16 )计数标志)读取此位时自动清除----避免误读
在STM32的情况中,外部时钟源是HCLK(AHB总线时钟)的1/8核心时钟是hclk时钟。
配置函数: SysTick_CLKSourceConfig (;
):加载棒自动重载除法寄存器
24位重载寄存器即使在32位中也仅24位有效
):VAL SysTick当前值寄存器
):CALIB SysTick校准值寄存器
7、固件库中的Systick相关函数:
p style="text-align:left;"> SysTick_CLKSourceConfig() //Systick时钟源选择 misc.c文件中void SysTick_CLKSourceConfig(uint32_t SysTick_CLKSource){ /* Check the parameters */ assert_param(IS_SYSTICK_CLK_SOURCE(SysTick_CLKSource)); if (SysTick_CLKSource == SysTick_CLKSource_HCLK) { SysTick->CTRL |= SysTick_CLKSource_HCLK; } else { SysTick->CTRL &= SysTick_CLKSource_HCLK_Div8; }} static __INLINE uint32_t SysTick_Config(uint32_t ticks){ if (ticks > SysTick_LOAD_RELOAD_Msk) return (1); /* Reload value impossible */ /* set reload register */ SysTick->LOAD = (ticks & SysTick_LOAD_RELOAD_Msk) - 1; /* set Priority for Cortex-M0 System Interrupts */ NVIC_SetPriority (SysTick_IRQn, (1<<__NVIC_PRIO_BITS) - 1); SysTick->VAL = 0; /* 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 (0); /* Function successful */}
SysTick_Config(uint32_t ticks) //初始化systick,时钟为HCLK,并开启中断 //core_cm3.h/core_cm4.h文件中(两个中断时间间隔)
8、Systick中断服务函数
void SysTick_Handler(void);
9、用中断的方式实现delay延时 static __IO uint32_t TimingDelay;void Delay(__IO uint32_t nTime){ TimingDelay = nTime; while(TimingDelay != 0);}void SysTick_Handler(void){ if (TimingDelay != 0x00) { TimingDelay--; }} int main(void) { … if (SysTick_Config(SystemCoreClock / 1000)) //systick时钟为HCLK,中断时间间隔1ms { while (1); } while(1) { Delay(200);//2ms … }} 三、delay延时函数如果使用中发现延时不一致,问题一般都是因为不同内核时钟不一样而已。修改tciks值即可。
void delay_ms(u16 nms){ u32 temp; SysTick->LOAD=(u32)nms*fac_ms;//时间加载(SysTick->LOAD为24bit)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; //清空计数器 }