烟台网站建设 熊掌号,小程序登录不了怎么办,WordPress用云数据库,做aelogo动效有什么好的网站文章目录#xff1a;
一#xff1a;低功耗模式
1.睡眠模式测试程序
NVIC.h
NVIC.c
key.h
key.c
main.c
2.停机模式测试程序
main.c
3.待机模式测试程序
main.c
二#xff1a;看门狗
1.独立看门狗测试程序
iwdg.h
iwdg.c
main.c
2.窗口看门狗测试程序
wwdg…文章目录
一低功耗模式
1.睡眠模式测试程序
NVIC.h
NVIC.c
key.h
key.c
main.c
2.停机模式测试程序
main.c
3.待机模式测试程序
main.c
二看门狗
1.独立看门狗测试程序
iwdg.h
iwdg.c
main.c
2.窗口看门狗测试程序
wwdg.h
wwdg.c
main.c
三TIM定时器
tim.h
tim.c
main.c
四CRC循环冗余校验计算单元与芯片ID
1.CRC功能测试程序
main.c
2.芯片ID读取程序
main.c
五还需要补充的知识 这些是单片机的辅助功能
一低功耗模式 单片机内部功率是各功能部分功率的总和低功耗模式是通过关掉部分内部功能达到省电STM32F103单片机共有3种低功耗模式不同模式会对系统正常工作有一定影响需要按实际情况选择低功耗模式只针对单片机内部功能外接电路产生的功耗不在其内单片机最小系统电路功耗不精确测量值√正常模式:10mA√睡眠模式:2mA√停机模式:20uA√待机模式:2uA睡眠模式在ARM内核无事可做的时候可以进入睡眠模式例如电脑的CPU空闲状态就是单片机睡眠模式睡眠模式的应用不多因只关闭ARM内核节能有限很少在非操作系统程序裸机中使用在嵌入式操作系统中会采用睡眠模式优点:对系统影响最小缺点:节能效果最差停机模式因SRAM内容不消失程序不复位可在唤醒后继续运行节能效果与待机模式近似却有着更多优势主要用于电池供电的设备上提高电池寿命在电池供电的产品中必须使用在外部供电的产品中没必要使用优点:节能效果好程序不会复位缺点:恢复时间较长待机模式由于SRAM内容消失唤醒后程序必须复位从头开始运行因为待机和停机之间的功耗差别是uA级的几乎没有差别所以开发者大多使用停机模式待机模式极少使用在一些偶尔需要工作的场合且工作量不大、不复杂的情况下待机模式可以保证最低的功耗比如应用在室外温度测量产品上每1小时测量一次。可用RTC闹钟唤醒测量完再待机。、优点:最节能缺点:程序会复位只有少数条件可唤醒1.睡眠模式测试程序 NVIC.h #ifndef __NVIC_H
#define __NVIC_H
#include sys.hextern u8 INT_MARK;//中断标志位void KEY_INT_INIT (void);#endif NVIC.c #include NVIC.hu8 INT_MARK;//中断标志位void KEY_INT_INIT (void){ //按键中断初始化NVIC_InitTypeDef NVIC_InitStruct; //定义结构体变量EXTI_InitTypeDef EXTI_InitStruct;RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); //启动GPIO时钟 需要与复用时钟一同启动 RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO , ENABLE);//配置端口中断需要启用复用时钟GPIO_EXTILineConfig(GPIO_PortSourceGPIOA, GPIO_PinSource0); //定义 GPIO 中断EXTI_InitStruct.EXTI_LineEXTI_Line0; //定义中断线EXTI_InitStruct.EXTI_LineCmdENABLE; //中断使能EXTI_InitStruct.EXTI_ModeEXTI_Mode_Interrupt; //中断模式为 中断EXTI_InitStruct.EXTI_TriggerEXTI_Trigger_Falling; //下降沿触发EXTI_Init( EXTI_InitStruct);NVIC_InitStruct.NVIC_IRQChannelEXTI0_IRQn; //中断线 NVIC_InitStruct.NVIC_IRQChannelCmdENABLE; //使能中断NVIC_InitStruct.NVIC_IRQChannelPreemptionPriority2; //抢占优先级 2NVIC_InitStruct.NVIC_IRQChannelSubPriority2; //子优先级 2NVIC_Init( NVIC_InitStruct);}void EXTI0_IRQHandler(void){if(EXTI_GetITStatus(EXTI_Line0)!RESET){//判断某个线上的中断是否发生 INT_MARK1;//标志位置1表示有按键中断EXTI_ClearITPendingBit(EXTI_Line0); //清除 LINE 上的中断标志位}
} key.h #ifndef __KEY_H
#define __KEY_H
#include sys.h//#define KEY1 PAin(0)// PA0
//#define KEY2 PAin(1)// PA1#define KEYPORT GPIOA //定义IO接口组
#define KEY1 GPIO_Pin_0 //定义IO接口
#define KEY2 GPIO_Pin_1 //定义IO接口void KEY_Init(void);//初始化#endif key.c #include key.hvoid KEY_Init(void){ //微动开关的接口初始化GPIO_InitTypeDef GPIO_InitStructure; //定义GPIO的初始化枚举结构 RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); GPIO_InitStructure.GPIO_Pin KEY1 | KEY2; //选择端口号0~15或all GPIO_InitStructure.GPIO_Mode GPIO_Mode_IPU; //选择IO接口工作方式 //上拉电阻
// GPIO_InitStructure.GPIO_Speed GPIO_Speed_50MHz; //设置IO接口速度2/10/50MHz GPIO_Init(KEYPORT,GPIO_InitStructure);
} main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include NVIC.h //中断向量控制器int main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化OLED_DISPLAY_8x16_BUFFER(0, SLEEP TEST ); //显示字符串INT_MARK0;//标志位清0NVIC_Configuration();//设置中断优先级KEY_INT_INIT();//按键中断初始化PA0是按键中断输入NVIC_SystemLPConfig(NVIC_LP_SEVONPEND,DISABLE); //SEVONPEND: 0只有使能的中断或事件才能唤醒内核。1任何中断和事件都可以唤醒内核。0DISABLE1ENABLE) NVIC_SystemLPConfig(NVIC_LP_SLEEPDEEP,DISABLE); //SLEEPDEEP: 0低功耗模式为睡眠模式。1进入低功耗时为深度睡眠模式。NVIC_SystemLPConfig(NVIC_LP_SLEEPONEXIT,DISABLE); //SLEEPONEXIT: 0: 被唤醒进入线程模式后不再进入睡眠模式。1被唤醒后执行完相应的中断处理函数后进入睡眠模式。while(1){GPIO_WriteBit(LEDPORT,LED1,(BitAction)(1)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, CPU SLEEP! ); //显示字符串delay_ms(500); //__WFI(); //进入睡眠模式等待中断唤醒
// __WFE(); //进入睡眠模式等待事件唤醒GPIO_WriteBit(LEDPORT,LED1,(BitAction)(0)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, CPU WAKE UP! ); //显示字符串delay_ms(500); //}} 2.停机模式测试程序 main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include NVIC.hint main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化OLED_DISPLAY_8x16_BUFFER(0, STOP TEST ); //显示字符串INT_MARK0;//标志位清0NVIC_Configuration();//设置中断优先级KEY_INT_INIT();//按键中断初始化PA0是按键中断输入RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR,ENABLE); //使能电源PWR时钟while(1){GPIO_WriteBit(LEDPORT,LED1,(BitAction)(1)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, CPU STOP! ); //显示字符串delay_ms(500); //PWR_EnterSTOPMode(PWR_Regulator_LowPower,PWR_STOPEntry_WFI);//进入停机模式RCC_Configuration(); //系统时钟初始化停机唤醒后会改用HSI时钟需要重新对时钟初始化 GPIO_WriteBit(LEDPORT,LED1,(BitAction)(0)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, CPU WAKE UP! ); //显示字符串delay_ms(500); //}} 3.待机模式测试程序 对开发板跳线进行设置 触摸按键将最上方的PA0跳线断开 main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.hint main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED I2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化OLED_DISPLAY_8x16_BUFFER(0, STANDBY TEST ); //显示字符串RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR,ENABLE); //使能电源PWR时钟PWR_WakeUpPinCmd(ENABLE);//WKUP唤醒功能开启待机时WKUP脚PA0为模拟输入GPIO_WriteBit(LEDPORT,LED1,(BitAction)(0)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, CPU RESET! ); //显示字符串delay_ms(500); //GPIO_WriteBit(LEDPORT,LED1,(BitAction)(1)); //LED控制OLED_DISPLAY_8x16_BUFFER(4, STANDBY! ); //显示字符串delay_ms(500); //PWR_EnterSTANDBYMode();//进入待机模式//因为待机唤醒后程序从头运行所以不需要加while(1)的主循环体。
} 二看门狗
是单片机系统功能的一个辅助功能帮助单片机自我检查、 监控单片机程序是否正常工作 看门狗定时器WDTWatch Dog Timer是单片机的一个组成部分它实际上是一个计数器一般给看门狗计数值程序开始运行后看门狗开始倒计数如果程序运行正常过一段时间CPU应发出指令让看门狗复位重新开始倒计数如果看门狗减到0就认为程序没有正常工作强制整个系统复位看门狗是一个计数器启动后开始倒计时每过一段时间CPU要重新写入计数值喂狗)CPU能重写计数值表示程序运行正常如果程序运行出错或死机则不能重写计数值当计数值减到O时看门狗会让整个单片机复位看门狗的作用看门狗的主要目的是监控单片机程序如果程序不断喂狗就证明单片机工作正常如果程序没有喂狗就说明单片机出了问题看门狗不能检查问题的原因只能通过复位单片机让程序重新开始运行类型独立看门狗、窗口看门狗 独立看门狗可在计数到O前随时喂狗用于监控程序是否正常运行 窗口看门狗必须在规定的时间范围内喂狗作用是监控单片机运行时效是否精确 1.独立看门狗测试程序 新建文件夹 Basic文件夹——iwdg文件夹——iwdg.c iwdg.h iwdg.h #ifndef __IWDG_H
#define __IWDG_H
#include sys.h//看门狗定时时间计算公式:Tout(预分频值*重装载值)/40 (单位ms)
//当前pre为64rlr为625计算得到Tout时间为1秒大概值。#define pre IWDG_Prescaler_64 //分频值范围4,8,16,32,64,128,256
#define rlr 625 //重装载值范围00xFFF4095void IWDG_Init(void);
void IWDG_Feed(void);#endif iwdg.c #include iwdg.hvoid IWDG_Init(void){ //初始化独立看门狗IWDG_WriteAccessCmd(IWDG_WriteAccess_Enable); //使能对寄存器IWDG_PR和IWDG_RLR的写操作IWDG_SetPrescaler(pre); //设置IWDG预分频值IWDG_SetReload(rlr); //设置IWDG重装载值IWDG_ReloadCounter(); //按照IWDG重装载寄存器的值重装载IWDG计数器IWDG_Enable(); //使能IWDG
}void IWDG_Feed(void){ //喂狗程序IWDG_ReloadCounter();//固件库的喂狗函数
} main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include iwdg.hint main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化---------------OLED_DISPLAY_8x16_BUFFER(0, IWDG TEST ); //显示字符串OLED_DISPLAY_8x16_BUFFER(4, RESET! ); //显示字符串delay_ms(800); //OLED_DISPLAY_8x16_BUFFER(4, ); //显示字符串IWDG_Init(); //初始化并启动独立看门狗while(1){IWDG_Feed(); //喂狗if(!GPIO_ReadInputDataBit(KEYPORT,KEY1)){delay_s(2); //延时2秒使程序不能喂狗而导致复制}}
} 2.窗口看门狗测试程序 新建文件夹 Basic文件夹——wwdg文件夹——wwdg.c wwdg.h wwdg.h #ifndef __WWDG_H
#define __WWDG_H
#include sys.h//窗口看门狗定时时间计算公式:
//上窗口超时时间单位us 4096*预分频值*(计数器初始值-窗口值)/APB1时钟频率单位MHz
//下窗口超时时间单位us 4096*预分频值*(计数器初始值-0x40)/APB1时钟频率单位MHz#define WWDG_CNT 0x7F //计数器初始值范围0x400x7F
#define wr 0x50 //窗口值上窗口边界范围0x400x7F
#define fprer WWDG_Prescaler_8 //预分频值取值1,2,4,8//如上三个值是0x7f0x508时上窗口48MS下窗口64MS。void WWDG_Init(void);
void WWDG_NVIC_Init(void);
void WWDG_Feed(void);#endif wwdg.c #include wwdg.hvoid WWDG_Init(void){ //初始化窗口看门狗RCC_APB1PeriphClockCmd(RCC_APB1Periph_WWDG, ENABLE); // WWDG 时钟使能WWDG_SetPrescaler(fprer); //设置 IWDG 预分频值WWDG_SetWindowValue(wr); //设置窗口值WWDG_Enable(WWDG_CNT); //使能看门狗,设置 counterWWDG_ClearFlag(); //清除提前唤醒中断标志位WWDG_NVIC_Init(); //初始化窗口看门狗 NVICWWDG_EnableIT(); //开启窗口看门狗中断
}void WWDG_NVIC_Init(void){ //窗口看门狗中断服务程序被WWDG_Init调用NVIC_InitTypeDef NVIC_InitStructure;NVIC_InitStructure.NVIC_IRQChannel WWDG_IRQn; //WWDG 中断NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority 2; //抢占 2 子优先级 3 组 2NVIC_InitStructure.NVIC_IRQChannelSubPriority 3; //抢占 2,子优先级 3,组 2NVIC_InitStructure.NVIC_IRQChannelCmdENABLE;NVIC_Init(NVIC_InitStructure); //NVIC 初始化
}void WWDG_Feed(void){ //窗口喂狗程序WWDG_SetCounter(WWDG_CNT); //固件库的喂狗函数
}void WWDG_IRQHandler(void){ //窗口看门狗中断处理程序WWDG_ClearFlag(); //清除提前唤醒中断标志位//此处加入在复位前需要处理的工作或保存数据
} main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include wwdg.hint main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化---------------OLED_DISPLAY_8x16_BUFFER(0, WWDG TEST ); //显示字符串OLED_DISPLAY_8x16_BUFFER(4, RESET! ); //显示字符串delay_ms(800); //OLED_DISPLAY_8x16_BUFFER(4, ); //显示字符串WWDG_Init(); //初始化并启动独立看门狗while(1){delay_ms(54); //用延时找到喂狗的窗口时间 避开计数初始值到上窗口边界这段时间WWDG_Feed(); //喂狗if(!GPIO_ReadInputDataBit(KEYPORT,KEY1)){delay_s(2); //延时2秒使程序不能喂狗而导致复制}}
} 三TIM定时器 定时器的3种功能捕获器:测量波形的频率和宽度比较器:分为模拟比较器和输出比较器模拟比较器:比较两组输入电压的大小(STM32F103无此功能)输出比较器:产生可调频率和可调占空比的脉冲波形PWM:脉宽调制器产生固定频率但占空比可调的脉冲波形普通定时器定时器可以用于独立时间计时功能原理和嘀嗒定时器、看门狗基本相同定时时间到时可等待CPU检查标志位查寻方式)或产生“定时器中断”—般都是让定时器产生中断捕获器捕获什么? 输入接口的电平变化上升沿或下降沿)上升沿:从低电平到高电平下降沿:从高电平到低电平有什么用? 可测量脉冲的宽度或者测量脉冲频率宽度T1是上沿捕获的定时器值T2是下沿捕获的定时器值T2-T1高电平宽度值频率T1是第1次上沿捕获值T2是第2次上沿捕获值T2-T1一个周期时间值频率)工作过程! 当接口产生上升沿或下降沿时将当前定时器值保存输出比较器可输出脉冲可调占空比和频率每一个周期的长度都可以不同每一个周期内的占空比都可以不同PWM只能调占空比也是可以通过程序调频率但不方便随时调)输出比较器可随时调占空比和频率输出比较器主要用于步进电机、伺服电机的控制定时器中断测试程序 新建文件夹 Basic文件夹——tim文件夹——tim.c tim.h tim.h #ifndef __PWM_H
#define __PWM_H
#include sys.hvoid TIM3_Init(u16 arr,u16 psc);
void TIM3_NVIC_Init (void);#endif tim.c #include led.h //因在中断处理函数中用到LED驱动#include tim.h//定时器时间计算公式Tout ((重装载值1)*(预分频系数1))/时钟频率;
//例如1秒定时重装载值9999预分频系数7199void TIM3_Init(u16 arr,u16 psc){ //TIM3 初始化 arr重装载值 psc预分频系数TIM_TimeBaseInitTypeDef TIM_TimeBaseInitStrue;RCC_APB1PeriphClockCmd(RCC_APB1Periph_TIM3,ENABLE);//使能TIM3TIM3_NVIC_Init (); //开启TIM3中断向量TIM_TimeBaseInitStrue.TIM_Periodarr; //设置自动重装载值TIM_TimeBaseInitStrue.TIM_Prescalerpsc; //预分频系数TIM_TimeBaseInitStrue.TIM_CounterModeTIM_CounterMode_Up; //计数器向上溢出TIM_TimeBaseInitStrue.TIM_ClockDivisionTIM_CKD_DIV1; //时钟的分频因子起到了一点点的延时作用一般设为TIM_CKD_DIV1TIM_TimeBaseInit(TIM3,TIM_TimeBaseInitStrue); //TIM3初始化设置TIM_ITConfig(TIM3, TIM_IT_Update, ENABLE);//使能TIM3中断 TIM_Cmd(TIM3,ENABLE); //使能TIM3
}void TIM3_NVIC_Init (void){ //开启TIM3中断向量NVIC_InitTypeDef NVIC_InitStructure;NVIC_InitStructure.NVIC_IRQChannel TIM3_IRQn; NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority 0x3; //设置抢占和子优先级NVIC_InitStructure.NVIC_IRQChannelSubPriority 0x3;NVIC_InitStructure.NVIC_IRQChannelCmd ENABLE;NVIC_Init(NVIC_InitStructure);
}void TIM3_IRQHandler(void){ //TIM3中断处理函数if (TIM_GetITStatus(TIM3, TIM_IT_Update) ! RESET){ //判断是否是TIM3中断TIM_ClearITPendingBit(TIM3, TIM_IT_Update);//此处写入用户自己的处理程序GPIO_WriteBit(LEDPORT,LED1,(BitAction)(1-GPIO_ReadOutputDataBit(LEDPORT,LED1))); //取反LED1}
}main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include tim.hint main (void){//主程序delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化---------------OLED_DISPLAY_8x16_BUFFER(0, TIM TEST ); //显示字符串TIM3_Init(9999,7199);//定时器初始化定时1秒99997199while(1){//写入用户的程序//LED1闪烁程序在TIM3的中断处理函数中执行}
} 四CRC循环冗余校验计算单元与芯片ID
1.CRC功能测试程序 CRC(循环冗余校验)计算单元使用一个固定的多项式发生器从一个32位的数据字产生一个CRC码在众多的应用中基于CRC的技术被用于验证数据传输或存储的一致性在EN/IEC 60335-1标准的范围内它提供了一种检测闪存存储器错误的手段CRC计算单元可以用于实时地计算软件的签名并与在链接和生成该软件时产生的签名对比。√CRC是用于数据正确性校验的√由一个32位的数据字产生√可应用在FALSH检测√可用于软件签名及对比特点写入和读出都是同一个寄存器但内容却不同 main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.hint main (void){//主程序u32 a,b;u8 c;u32 y[3]{0x87654321,0x98765432,0x09876543};delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYI2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化---------------OLED_DISPLAY_8x16_BUFFER(0, CRC TEST ); //显示字符串RCC_AHBPeriphClockCmd(RCC_AHBPeriph_CRC, ENABLE);//开启CRC时钟while(1){CRC_ResetDR();//复位CRC需要清0重新计算时先复位CRC_CalcCRC(0x12345678);//CRC计算一个32位数据。参数32位数据。返回值32位计算结果CRC_CalcCRC(0x23456789);//CRC计算一个32位数据。参数32位数据。返回值32位计算结果a CRC_CalcCRC(0x34567890);//CRC计算一个32位数据。参数32位数据。返回值32位计算结果CRC_ResetDR();//复位CRC需要清0重新计算时先复位b CRC_CalcBlockCRC(y,3);//CRC计算一个32位数组。参数32位数组名数组长度。返回值32位计算结果CRC_SetIDRegister(0x5a);//向独立寄存器CRC_IDR写数据。参数8位数据。c CRC_GetIDRegister();//从独立寄存器CRC_IDR读数据。返回值8位数据。//此时a存放的是3个独立数的CRC结果。32位//b存放的是数组y中3个数据CRC计算结果。32位//c存放的是我们写入的独立寄存器数据0x5a。8位}
}// 以下是CRC固件库函数可在主程序中直接调用 //// RCC_AHBPeriphClockCmd(RCC_AHBPeriph_CRC, ENABLE);//开启CRC时钟主程序开始时调用
// CRC_ResetDR();//复位CRC需要清0重新计算时先复位
// uint32_t CRC_CalcCRC(uint32_t Data);//CRC计算一个32位数据。参数32位数据。返回值32位计算结果
// uint32_t CRC_CalcBlockCRC(uint32_t pBuffer[], uint32_t BufferLength);//CRC计算一个32位数组。参数32位数组名数组长度。返回值32位计算结果
// uint32_t CRC_GetCRC(void);//从CRC中读出计算结果。返回值32位计算结果。// void CRC_SetIDRegister(uint8_t IDValue);//向独立寄存器CRC_IDR写数据。参数8位数据。
// uint8_t CRC_GetIDRegister(void);//从独立寄存器CRC_IDR读数据。返回值8位数据。 stm32f10x_crc. c包含了CRC的固件库函数 2.芯片ID读取程序 芯片ID√ 96位ID编码√可读出3个32位数据或8个8位数据√可以以字节(8位)为单位读取也可以以半字(16位)或者全字(32位)读取√每个芯片编码是唯一的出厂时固化不可修改√ 可用于产品序列号√用来作为密码提高安全性 √用来保护程序的不可复制main.c #include stm32f10x.h //STM32头文件
#include sys.h
#include delay.h
#include relay.h
#include oled0561.h
#include led.h
#include key.h#include usart.hint main (void){//主程序u32 ID[3];delay_ms(500); //上电时等待其他器件就绪RCC_Configuration(); //系统时钟初始化 RELAY_Init();//继电器初始化LED_Init();//LED KEY_Init();//KEYUSART1_Init(115200); //串口初始化参数是波特率I2C_Configuration();//I2C初始化OLED0561_Init(); //OLED初始化---------------OLED_DISPLAY_8x16_BUFFER(0, CHIP ID TEST ); //显示字符串ID[0] *(__IO u32 *)(0X1FFFF7E8); //读出3个32位ID 高字节ID[1] *(__IO u32 *)(0X1FFFF7EC); // ID[2] *(__IO u32 *)(0X1FFFF7F0); // 低字节//08表示后面的数据不足8位就补0显示printf(ChipID: %08X %08X %8X \r\n,ID[0],ID[1],ID[2]); //从串口输出16进制IDif(ID[0]0x066EFF34 ID[1]0x3437534D ID[2]0x43232328){ //检查ID是否匹配printf(chipID OK! \r\n); //匹配}else{printf(chipID error! \r\n); //不同}while(1){}
} 五还需要补充的知识 1.仿真仿真接口有JTAG、SW接口仿真器又有ST-LINK、J-LINK等还有纯软件仿真Proteus等2.HEL库3.内置USB接口USB鼠标、键盘、U盘4.显示屏除OLED之外还能外扩LCD1602、12864等显示屏的类型还有VOG屏、TFT屏等每种屏的接口也分好多种5.定时器的复杂功能TIM1高级定时器的使用单脉冲模式输出比较器的使用捕获器的使用定时器的DMA设置6.中断的复杂功能中断嵌套应用与优先级问题外部中断的端口映射问题7.单片机内部功能WIFI、蓝牙、GPS模块、2.4G模块、彩屏的人机界面、RTOS嵌入式操作系统....