当前位置: 首页 > news >正文

ueditor是做网站的吗商丘企业网站建设公司

ueditor是做网站的吗,商丘企业网站建设公司,大朗镇仿做网站,网站顶部布局2.1 STM32 的时钟系统 STM32 芯片为了实现低功耗#xff0c;设计了一个功能完善但却非常复杂的时钟系统。普通的MCU 一般只要配置好 GPIO 的寄存器就可以使用了#xff0c;但 STM32 还有一个步骤#xff0c;就是开启外设时钟。 图2-1 STM32的时钟树在 STM32 中#xff0c;…2.1 STM32 的时钟系统 STM32 芯片为了实现低功耗设计了一个功能完善但却非常复杂的时钟系统。普通的MCU 一般只要配置好 GPIO 的寄存器就可以使用了但 STM32 还有一个步骤就是开启外设时钟。    图2-1 STM32的时钟树 在 STM32 中有五个时钟源为 HSI、 HSE、 LSI、 LSE、 PLL。 从时钟频率来分可以分为高速时钟源和低速时钟源在这 5 个中 HIS HSE 以及 PLL 是高速时钟 LSI 和 LSE 是低速时钟。从来源可分为外部时钟源和内部时钟源外部时钟源就是从外部通过接晶振的方式获取时钟源其中 HSE 和 LSE 是外部时钟源其他的是内部时钟源。下面我们看看 STM32 的 5 个时钟源我们讲解顺序是按图中红圈标示的顺序 ①HSI 是高速内部时钟 RC 振荡器频率为 8MHz。 ②HSE 是高速外部时钟可接石英 /陶瓷谐振器或者接外部时钟源频率范围为4MHz~16MHz。 我们的开发板接的是 8M 的晶振。 ③LSI 是低速内部时钟RC 振荡器频率为 40kHz。独立看门狗的时钟源只能是 LSI同时 LSI 还可以作为 RTC 的时钟源。 ④LSE 是低速外部时钟接频率为 32.768kHz 的石英晶体。这个主要是 RTC 的时钟源。 ⑤PLL 为锁相环倍频输出其时钟输入源可选择为 HSI/2、HSE 或者 HSE/2。倍频可选择为2~16 倍但是其输出频率最大不得超过 72MHz。 图中我们用 A~E 标示我们要讲解的地方。 A. MCO 是 STM32 的一个时钟输出 IO(PA8)它可以选择一个时钟信号输出 可以选择为 PLL 输出的 2 分频、 HSI、 HSE、或者系统时钟。这个时钟可以用来给外部其他系统提供时钟源。 B. 这里是 RTC 时钟源从图上可以看出 RTC 的时钟源可以选择 LSI LSE以及HSE 的 128 分频。 C. 从图中可以看出 C 处 USB 的时钟是来自 PLL 时钟源。 STM32 中有一个全速功能的 USB 模块其串行接口引擎需要一个频率为 48MHz 的时钟源。该时钟源只能从 PLL 输出端获取可以选择为 1.5 分频或者 1 分频也就是当需要使用 USB模块时 PLL 必须使能并且时钟频率配置为 48MHz 或 72MHz。 D. D 处就是 STM32 的系统时钟 SYSCLK它是供 STM32 中绝大部分部件工作的时钟源。系统时钟可选择为 PLL 输出、 HSI 或者 HSE。系统时钟最大频率为 72MHz当然你也可以超频不过一般情况为了系统稳定性是没有必要冒风险去超频的。 E. 这里的 E 处是指其他所有外设了。从时钟图上可以看出其他所有外设的时钟最终来源都是 SYSCLK。 SYSCLK 通过 AHB 分频器分频后送给各模块使用。这些模块包括 ①AHB 总线、内核、内存和 DMA 使用的 HCLK 时钟。 ②通过 8 分频后送给 Cortex 的系统定时器时钟也就是 systick 了。 ③直接送给 Cortex 的空闲运行时钟 FCLK。 ④送给 APB1 分频器。 APB1 分频器输出一路供 APB1 外设使用(PCLK1最大频率 36MHz)另一路送给定时器(Timer)2、 3、 4 倍频器使用。 ⑤送给 APB2 分频器。 APB2 分频器分频输出一路供 APB2 外设使用(PCLK2最大频率 72MHz)另一路送给定时器(Timer)1 倍频器使用。 其中需要理解的是 APB1 和 APB2 的区别 APB1 上面连接的是低速外设包括电源接口、备份接口、 CAN、 USB、 I2C1、 I2C2、 UART2、 UART3 等等 APB2 上面连接的是高速外设包括 UART1、 SPI1、 Timer1、 ADC1、 ADC2、所有普通 IO 口(PA~PE)、第二功能 IO 口等。 SystemInit()函数中设置的系统时钟大小  SYSCLK系统时钟 72MHz  AHB 总线时钟(使用 SYSCLK) 72MHz  APB1 总线时钟(PCLK1) 36MHz  APB2 总线时钟(PCLK2) 72MHz  PLL 时钟 72MHz 具体代码清读者查看工程文件的system_stm32f10x.c文件。   2.2 Systick系统定时器工作原理分析 SysTick 定时器被捆绑在 NVIC 中用于产生 SysTick 异常异常号 15。在以前操作系统和所有使用了时基的系统都必须有一个硬件定时器来产生需要的“滴答”中断作为整个系统的时基。滴答中断对操作系统尤其重要。例如操作系统可以为多个任务分配不同数目的时间片确保没有一个任务能霸占系统 或者将每个定时器周期的某个时间范围赐予特定的任务等操作系统提供的各种定时功能都与这个滴答定时器有关。因此需要一个定时器来产生周期性的中断而且最好还让用户程序不能随意访问它的寄存器以维持操作系统“心跳”的节律。 Cortex-M3 在内核部分包含了一个简单的定时器——SysTick。因为所有的 CM3 芯片都带有这个定时器软件在不同芯片生产厂商的 CM3 器件间的移植工作就得以简化。该定时器的时钟源可以是内部时钟FCLKCM3 上的自由运行时钟或者是外部时钟 CM3 处理器上的 STCLK 信号。不过STCLK 的具体来源则由芯片设计者决定因此不同产品之间的时钟频率可能大不相同。因此需要阅读芯片的使用手册来确定选择什么作为时钟源。在 STM32 中 SysTick 以 HCLKAHB 时钟或 HCLK/8 作为运行时钟见图 1- 1。 SysTick 定时器能产生中断CM3 为它专门开出一个异常类型并且在向量表中有它的一席之地。它使操作系统和其他系统软件在 CM3 器件间的移植变得简单多了因为在所有 CM3 产品间SysTick 的处理方式都是相同的。SysTick 定时器除了能服务于操作系统之外还能用于其他目的如作为一个闹铃、用于测量时间等。Systick 定时器属于Cortex 内核部件可以参考《ARM Cortex-M3 权威指南》英JosephYiu 著宋岩译北京航空航天大学出版社出版或“STM32xxx-Cortex-M3programmingmanual”这是 ST 官方提供的电子版编程手册可以在 ST 官网下载来了解。 2.3 Systick系统定时器寄存器分析 在传统的嵌入式系统软件按中通常实现 Delay(N) 函数的方法为 for(i 0; i x; i ); x --- ;   对于STM32系列微处理器来说执行一条指令只有几十个 ns进行 for 循环时要实现 N 毫秒的 x 值非常大而且由于系统频率的宽广很难计算出延时 N 毫秒的精确值。针对 STM32 微处理器需要重新设计一个新的方法去实现该功能以实现在程序中使用 Delay(N)。 Cortex-M3 的内核中包含一个 SysTick 时钟。SysTick 为一个 24 位递减计数器SysTick 设定初值并使能后每经过 1 个系统时钟周期计数值就减 1。计数到 0 时SysTick 计数器自动重装初值并继续计数同时内部的 COUNTFLAG 标志会置位触发中断 (如果中断使能情况下)。 在 STM32 的应用中使用 Cortex-M3 内核的 SysTick 作为定时时钟设定每一毫秒产生一次中断在中断处理函数里对 N 减一在Delay(N) 函数中循环检测 N 是否为 0不为 0 则进行循环等待若为 0 则关闭 SysTick 时钟退出函数。 注 全局变量 TimingDelay , 必须定义为 volatile 类型 , 延迟时间将不随系统时钟频率改变。 STM32中的Systick 部分内容属于NVIC控制部分一共有4个寄存器名称和地址分别是  STK_CTRL, 0xE000E010 – 控制寄存器  表2-1 SysTick控制及状态寄存器   第0位ENABLESystick 使能位 0关闭Systick功能1开启Systick功能 第1位TICKINTSystick 中断使能位 0关闭Systick中断1开启Systick中断 第2位CLKSOURCESystick时钟源选择 0使用HCLK/8 作为Systick时钟1使用HCLK作为Systick时钟 第16位COUNTFLAGSystick计数比较标志如果在上次读取本寄存器后SysTick 已经数到了0则该位为1。如果读取该位该位将自动清零  STK_LOAD, 0xE000E014 – 重载寄存器  表2-2 SysTick重装载数值寄存器   Systick是一个递减的定时器当定时器递减至0时重载寄存器中的值就会被重装载继续开始递减。STK_LOAD 重载寄存器是个24位的寄存器最大计数0xFFFFFF。  STK_VAL, 0xE000E018 – 当前值寄存器  表2-3 SysTick当前数值寄存器   也是个24位的寄存器读取时返回当前倒计数的值写它则使之清零同时还会清除在SysTick 控制及状态寄存器中的COUNTFLAG 标志。  STK_CALRB, 0xE000E01C – 校准值寄存器  表2-4 SysTick校准数值寄存器   校准值寄存器提供了这样一个解决方案它使系统即使在不同的CM3产品上运行也能产生恒定的SysTick中断频率。最简单的作法就是直接把TENMS的值写入重装载寄存器这样一来只要没突破系统极限就能做到每10ms来一次 SysTick异常。如果需要其它的SysTick异常周期则可以根据TENMS的值加以比例计算。只不过在少数情况下 CM3芯片可能无法准确地提供TENMS的值如 CM3的校准输入信号被拉低所以为保险起见最好在使用TENMS前检查器件的参考手册。 SysTick定时器除了能服务于操作系统之外还能用于其它目的如作为一个闹铃用于测量时间等。要注意的是当处理器在调试期间被喊停 halt时则SysTick定时器亦将暂停运作。   2.4 Systick系统定时器具体代码分析 SysTick 库函数  SysTick_CLKSourceConfig 设置 SysTick 时钟源  SysTick_SetReload 设置 SysTick 重装载值  SysTick_CounterCmd 使能或者失能 SysTick 计数器  SysTick_ITConfig 使能或者失能 SysTick 中断  SysTick_GetCounter 获取 SysTick 计数器的值  SysTick_GetFlagStatus 检查指定的 SysTick 标志位设置与否。 2.4.1main文件分析 int main(void) { /* LED 端口初始化 */LED_GPIO_Config();/* 配置SysTick 为10us中断一次 */SysTick_Init(); for(;;) { LED1( ON ); Delay_us(10000); // 10000 * 10us 100ms //Delay_ms(100); LED1( OFF ); LED2( ON ); Delay_us(10000); // 10000 * 10us 100ms //Delay_ms(100); LED2( OFF ); LED3( ON ); Delay_us(10000); // 10000 * 10us 100ms //Delay_ms(100); LED3( OFF ); } } 在 main 函数中SysTick_Init() 和 Delay_us() 这两个函数比较陌生它们的功能分别是配置好 SysTick 定时器和进行精确延时。整个 main 函数的流程就是初始化 LED 及SysTick 定时器之后就进入死循环轮流点亮 LED1、LED2、LED3点亮的时间为精确的 100 ms。 2.4.2 stm32f103_SysTick.c文件分析  配置并启动 SysTick 我们看一下 SysTick_Init() 这个函数其功能是启动系统滴答定时器 SysTick 并将 SysTick 配置为 10 μs 中断一次。 void SysTick_Init(void) {/* SystemFrequency / 100000 10us中断一次* SystemFrequency / 1000000 1us中断一次*/ // if (SysTick_Config(SystemFrequency / 100000)) // ST3.0.0库版本if (SysTick_Config(SystemCoreClock / 100000)) // ST3.5.0库版本 { /* Capture error */ while (1); } // 关闭滴答定时器 SysTick-CTRL ~ SysTick_CTRL_ENABLE_Msk; } } 本函数实际上只是调用了 SysTick_Confi g() 函数它是属于内核层的 Cortex-M3 通用函数位于 core_cm3.h 文件中。若调用 SysTick_Confi g() 配置 SysTick 不成功则进入死循环初始化 SysTick 成功后先关闭定时器在需要的时候再开启。SysTick_Confi g() 函数无法在STM32 外设固件库文件中找到其使用方法。所以我们在 Keil 环境下直接跟踪这个函数到 core_cm3.h 文件查看函数的定义。 static __INLINE uint32_t SysTick_Config(uint32_t ticks) { if (ticks SysTick_LOAD_RELOAD_Msk) return (1); /* Reload value impossible */ SysTick-LOAD (ticks SysTick_LOAD_RELOAD_Msk) - 1; /* set reload register */ NVIC_SetPriority (SysTick_IRQn, (1__NVIC_PRIO_BITS) - 1); /* set Priority for Cortex-M0 System Interrupts */ 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 并把它配置为计数至 0 时引起中断 输入的参数 ticks 为两个中断之间的脉冲数即相隔 ticks 个时钟周期会引起一次中断 配置 SysTick 成功时返回 0出错时返回 1。但是这段注释并没有告诉我们它把 SysTick 的时钟设置为 AHB 时钟还是 AHB/8这是一个十分关键的问题于是我们将对这个函数的具体实现进行分析与大家再分享一下如何分析底层库函数。分析底层库函数要有 SysTick 定时器工作分析的知识准备。  检查输入参数 SysTick_Confi g() 第 3 行代码是检查输入参数 ticks因为 ticks 是脉冲计数值要被保存到重载寄存器 STK_LOAD 寄存器中再由硬件把 STK_LOAD 值加载到当前计数值寄存器 STK_VAL 中使用STK_LOAD 和 STK_VAL 都是 24 位的所以当输入参数 ticks 大于其可存储的最大值时将由这行代码检查出错误并返回。  位指示宏及位屏蔽宏 检查 ticks 参数没有错误后就稍稍处理一下把 ticks-1 赋值给 STK_LOAD 寄存器要注意的是减 1若 STK_VAL 从 ticks−1 向下计数至 0实际上就经过了 ticks 个脉冲。这句赋值代码使用了宏 SysTick_LOAD_RELOAD_Msk与其他库函数类似这个宏是用来指示寄存器的特定位置或进行位屏蔽的。 /* SysTick Control / Status Register Definitions */ #define SysTick_CTRL_COUNTFLAG_Pos 16 /*! SysTick CTRL: COUNTFLAG Position */ #define SysTick_CTRL_COUNTFLAG_Msk (1ul SysTick_CTRL_COUNTFLAG_Pos) /*! SysTick CTRL: COUNTFLAG Mask */ #define SysTick_CTRL_CLKSOURCE_Pos 2 /*! SysTick CTRL: CLKSOURCE Position */ #define SysTick_CTRL_CLKSOURCE_Msk (1ul SysTick_CTRL_CLKSOURCE_Pos) /*! SysTick CTRL: CLKSOURCE Mask */ #define SysTick_CTRL_TICKINT_Pos 1 /*! SysTick CTRL: TICKINT Position */ #define SysTick_CTRL_TICKINT_Msk (1ul SysTick_CTRL_TICKINT_Pos) /*! SysTick CTRL: TICKINT Mask */ #define SysTick_CTRL_ENABLE_Pos 0 /*! SysTick CTRL: ENABLE Position */ #define SysTick_CTRL_ENABLE_Msk (1ul SysTick_CTRL_ENABLE_Pos) /*! SysTick CTRL: ENABLE Mask */ /* SysTick Reload Register Definitions */ #define SysTick_LOAD_RELOAD_Pos 0 /*! SysTick LOAD: RELOAD Position */ #define SysTick_LOAD_RELOAD_Msk (0xFFFFFFul SysTick_LOAD_RELOAD_Pos) /*! SysTick LOAD: RELOAD Mask */ /* SysTick Current Register Definitions */ #define SysTick_VAL_CURRENT_Pos 0 /*! SysTick VAL: CURRENT Position */ #define SysTick_VAL_CURRENT_Msk (0xFFFFFFul SysTick_VAL_CURRENT_Pos) /*! SysTick VAL: CURRENT Mask */ /* SysTick Calibration Register Definitions */ #define SysTick_CALIB_NOREF_Pos 31 /*! SysTick CALIB: NOREF Position */ #define SysTick_CALIB_NOREF_Msk (1ul SysTick_CALIB_NOREF_Pos) /*! SysTick CALIB: NOREF Mask */ #define SysTick_CALIB_SKEW_Pos 30 /*! SysTick CALIB: SKEW Position */ #define SysTick_CALIB_SKEW_Msk (1ul SysTick_CALIB_SKEW_Pos) /*! SysTick CALIB: SKEW Mask */ #define SysTick_CALIB_TENMS_Pos 0 /*! SysTick CALIB: TENMS Position */ #define SysTick_CALIB_TENMS_Msk (0xFFFFFFul SysTick_VAL_CURRENT_Pos) /*! SysTick CALIB: TENMS Mask */ /*}*/ /* end of group CMSIS_CM3_SysTick */   其中寄存器位指示宏 SysTick_xxx_Pos 宏展开后即为 xxx 在相应寄存器中的位置如控制 SysTick 时钟源的 SysTick_CTRL_CLKSOURCE_Pos 宏展开为 2这个寄存器位正是寄存器 STK_CTRL 中的 Bit2。 而寄存器位屏蔽宏 SysTick_xxx_Msk宏展开是 xxx 的位全部置 1 后左移SysTick_xxx_Pos 位。如控制 SysTick 时钟源的 SysTick_CTRL_CLKSOURCE_Msk宏展开为“1ul SysTick_CTRL_CLKSOURCE_Pos” 把 无 符 号 长 整 型 数 值ul 1 左移 2 位 得 到 了 一 个 只 有 Bit2 CLKSOURCE 位被置 1其他位为 0 的数值这样的数值配合位操作 按位与、| 按位或可以很方便地修改寄存器的某些位。假如控制 CLKSOURCE 需 要 4 个 寄 存 器 位 这 个 宏 就 应 该 被 改 为 0xf ul SysTick-CTRL | SysTick_CTRL_ENABLE_Msk; // 使能滴答定时器 SysTick-CTRL ~ SysTick_CTRL_ENABLE_Msk; // 关闭滴答定时器    定时时间的计算 在调用SysTick_Config()函数时向它输入的参数为SystemCoreClock / 100000SystemCoreClock为定义了系统时钟SYSCLK频率的 宏即等于 AHB的时钟频率。在本书的所有例程中AHB 都是被配置为 72 MHz 的也就是这个 SystemCoreClock 宏展开为数值 7200 0000。 根据前面对 SysTick_Confi g() 函数的介绍它的输入参数为 SysTick 将要计时的脉冲数经过 ticks 个脉冲经过 ticks 个时钟周期后将触发中断触发中断后又重新开始计数。由此我们可以算出定时的时间下面为计算公式  Tticks×(1/f) 其中T 为要定时的总时间 ticks 为 SysTick_Confi g() 的输入参数 1/ f 即为SysTick 使用的时钟源的时钟周期f 为该时钟源的时钟频率当时钟源确定后为常数。 例如 本实验例子中使用时钟源为 AHB 时钟其频率被配置为 72 MHz。调用函数时把 ticks 赋值为 ticksSystemFrequency / 10 000 720表示 720 个时钟周期中断一次 1/f 是时钟周期的时间此时1/f 1/72 μs所以最终定时总时间 T720×1/72为720 个时钟周期正好是 10 μs。 SysTick 定时器的定时时间配置为触发中断即为中断周期由 ticks 参数决定最大定时周期不能超过 224 个。  编写中断服务函数 一旦我们调用了 Delay_us() 函数SysTick 定时器就被开启按照设定好的定时周期递减计数当 SysTick 的计数寄存器的值减为 0 时就进入中断函数当中断函数执行完毕之后重新计时如此循环除非它被关闭。 void Delay_us(__IO u32 nTime) { TimingDelay nTime; // 使能滴答定时器 SysTick-CTRL | SysTick_CTRL_ENABLE_Msk; while(TimingDelay ! 0); }   使能了 SysTick 之后就使用 whileTimingDelay ! 0语句等待 TimingDelay 变量变为 0这个变量是在中断服务函数中被修改的。因此我们需要编写相应的中断服务程序在本实验室中我们配置为 10μs 中断一次每次中断把 TimingDelay 减 1。中断程序在 stm32f10x_it.c 中实现。 void SysTick_Handler(void) {TimingDelay_Decrement(); }   SysTick中断属于系统异常向量在stm32f10x_it.c文件中已经默认有了它的中断服务函数SysTick_Handler()但内容为空。我们找到这个函数其调用了用户函数TimingDelay_Decrement()。后者是由用户编写的一个应用程序。 void TimingDelay_Decrement(void) {if (TimingDelay ! 0x00){ TimingDelay--;} }   每次进入 SysTick 中断就调用一次 TimingDelay_Decrement()函数使全局变量TimingDelay 自减一次。用户函数 Delay_us ()在TimingDelay 被减至0时才退出延时循环即我们对 TimingDelay 赋的值为要中断的次数。所以总的延时时间  T 延时 T 中断周期 ×TimingDelay 至此SysTick 的精确延时功能讲解完毕。 参考资料http://www.makeru.com.cn/               创客学院嵌入式学习交流群561213221转载于:https://www.cnblogs.com/huan-huan/p/8967055.html
http://wiki.neutronadmin.com/news/291023/

相关文章:

  • 企业网站建设成本费用WordPress主题MX互动
  • 双桥网站建设access网站开发
  • 网站制作公司深圳北京免费建站网络营销
  • 国外对网站开发的研究wordpress首页如何增加模块
  • 国外知名设计网站大全wordpress插件选项
  • 百度教育网站桂林论坛网app
  • 南京网站设计公司大全中国科技成果
  • 找工作去哪个网站织梦做的网站图片显示不了
  • 做一个推广网站多少钱网站案例分析教育
  • 免费做网站的平台南昌seo计费管理
  • 网站建设英语要几级现货交易平台代理
  • 贵阳市小程序网站开发公司连云港市网站优化
  • 云南建设学校网站青岛网站建设公司怎么样
  • 东莞企业网站后缀长沙招聘信息最新招聘
  • 网站维护流程个人做交通违章查询网站违法吗
  • 陕西培训网站建设外海网站如何做网站的推广
  • 建模e-r跟做网站有什么关系网站建设如何制作
  • 宝应县天宇建设网站互联网建设企业网站
  • 企业检索网站建设一个完整网页的制作案例
  • 免费网站模板源码下载网络设计工资有多少
  • 天津网站建设企业wordpress安装使用教程
  • 网站改版 域名dw网站制作效果怎么做
  • asp 免费网站模板芜湖哪里做网站
  • 源码网站推荐广州模板网站建设费用
  • 广告公司的网站建设网站备案幕布
  • 一个公司网站后台怎么做有的网站打开慢
  • 做网站素材图片千图网官网素材
  • 可信的手机网站建设怎样做网站才不能被攻破
  • ppt模板免费下载完整版免费网站wordpress简约企业商城
  • 自己制作图片文字图片seo是什么意思网络用语