嵌入式应用之-初始化部分
main 是我们的一个入口函数,那么再开始运行任务之前我们应该做些什么?
main
1、
问题:stm32 睡眠模式默认debug端口不打开,设置DBGMCU_STANDBY可以打开。
问题:在调试模式下,内核被调试器停止时,相关外设是否同时停止. 比如定时器输出,如果是连接了电机什么的时候,调试到某个地方断点了,默认定时器会继续跑,这时电机电流可能会失控烧电路,设置了对应的位后,定时器会停止,输出会固定在CCMR设置的电平. 对于串行通信,内核停止并且设置了对应的位,数据就有可能发了一半停下来,等内核跑了再继续发,这样数据时序就不对了,但这种情况对于分析内核与数据间的时序是有帮助的.
因此我们可以在程序开始时设置DBGMCU.
DBGMCU_Config(DBGMCU_STANDBY,ENABLE);
- 1
stm32f10x_dbgmcu.c 库函数:
void DBGMCU_Config(u32 DBGMCU_Periph, FunctionalState NewState)
{
/* Check the parameters */
assert_param(IS_DBGMCU_PERIPH(DBGMCU_Periph));
assert_param(IS_FUNCTIONAL_STATE(NewState)); if (NewState != DISABLE)
{
DBGMCU->CR |= DBGMCU_Periph;
}
else
{
DBGMCU->CR &= ~DBGMCU_Periph;
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
2、
/=========关闭JTAG-DP,启用SW-DP,SWJ_CFG[2:0]=010===========/
#if(SYSTEM_RUN_IN_DEBUG==GAL_YES)
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE); GPIO_PinRemapConfig(GPIO_Remap_SWJ_JTAGDisable,ENABLE);
#else
RCC_APB2PeriphClockCmd(RCC_APB2Periph_AFIO,ENABLE); GPIO_PinRemapConfig(GPIO_Remap_SWJ_Disable,ENABLE);
#endif
- 1
- 2
- 3
- 4
- 5
- 6
- 7
3、PWR包括功耗管理和低功耗模式选择。(电源管理也是必不可少的)
void WKUP_Init(FunctionalState nEn)
{ GPIO_InitTypeDef GPIO_InitStructure; RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE); RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA, ENABLE); GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IPD; GPIO_InitStructure.GPIO_Pin = (GPIO_Pin_0); GPIO_Init(GPIOA, &GPIO_InitStructure); PWR_ClearFlag(PWR_FLAG_WU); PWR_WakeUpPinCmd(nEn);
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
4、看门狗是防止程序跑飞
void ClearWatchDog(void)
{
#if(SYSTEM_RUN_IN_DEBUG==GAL_NO)
IWDG_ReloadCounter();
#endif
}
- 1
- 2
- 3
- 4
- 5
- 6
5、低功耗处理I/O口
void InitialIOInLowCost(void)
{
//以下代码是控制低功耗的关键。
//RCC_AHBPeriphClockCmd(RCC_AHBPeriph_SRAM, DISABLE);
// RCC_AHBPeriphClockCmd(RCC_AHBPeriph_FLITF, DISABLE);
RCC_APB1PeriphClockCmd(RCC_APB1Periph_ALL, DISABLE); //S1:关闭除RCC_APB1Periph_PWR外的全部时钟;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ALL, ENABLE);
//---- 把GPIO_Init 的结果直接运行,降低运行时间-------
GPIOA->CRL=0X44444444;
GPIOA->CRH=0X44444444;
GPIOB->CRL=0X44444444;
GPIOB->CRH=0X44444444;
GPIOC->CRL=0X44444444;
GPIOC->CRH=0X44444444;
GPIOD->CRL=0X44444444;
GPIOD->CRH=0X44444444;
GPIOE->CRL=0X44444444;
GPIOE->CRH=0X44444444;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ALL, DISABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_GPIOB|RCC_APB2Periph_GPIOC|RCC_APB2Periph_GPIOD, ENABLE);/* 唤醒按键和电源检测输入口时钟使能 */
uInitIRWakeupStatus(); /* 红外唤醒初始化 */
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
}
5、初始化应该是个连续的过程应该这里有相关数据的初始化,但不能保证初始化过程中不会掉电,因此我们这里还要增加掉电复位等处理。
首先看看我们的运行模式有哪些:
#define AC_POWER_ON 0
#define AC_POWER_OFF 1
#define SYSTEM_RESET 1
#define POWER_ON 0
#define WAIT_MODE 2
#define STOP_MODE 3
#define IDLE_MODE 4
#define POWER_OFF 5
#define SYSTEM_GETRTC 6
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
检测函数:
unsigned char GetACPowerStatus(void) //交流电检测
{
GPIO_InitTypeDef GPIO_InitStructure;
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIO_InitStructure.GPIO_Speed = GPIO_Speed_2MHz;
//--AA是否是市电上电判断管脚AA-- GPIO_InitStructure.GPIO_Pin = (IN_PECHK_PIN );
GPIO_Init(IN_PECHK_PORT, &GPIO_InitStructure); if(IfPowerDown())
{
return (AC_POWER_OFF);
}
else
{
return (AC_POWER_ON);
}
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
#
/掉电检测
uchar IfPowerDown(void)
{ uchar ucTem,ucData; ucTem=8; ucData=0; while(ucTem) { ucData+=GetPowerSupplyStatus(); ucTem--; } if(ucData<4) { return 1; } return 0;
// if(1==GetPowerSupplyStatus())
// {
// return 0;
// }
// return 1;
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
#
#define GetPowerSupplyStatus() (GPIO_ReadInputDataBit(IN_PECHK_PORT,IN_PECHK_PIN))
- 1
判断后初始化函数:
uchar RunCPUToDifferentPowerMode(uchar Mode)
uchar RunCPUToDifferentPowerMode(uchar Mode)
{
//ulong ulTempTest;
#if(CONFIG_METER_PREPAY_MODE != CONFIG_METER_PREPAY_MODE_DISABLE) uchar ucTempStatus;
#endif
uchar ucTemp1;
uchar Staks;
InitWatchDog();
ClearWatchDog(); switch(Mode) { case SYSTEM_RESET: ; case POWER_ON: ; case POWER_OFF: ; default: ; }
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
#
InitializeVariable
uchar InitializeVariable(uchar Mode)
{
ulong ulTempTest, ulTime;
uchar ucTempStatus;
uint ucRemteTimesCount;
#if(HAVING_PROGRAMKEY== GAL_YES)
uint uiTempProgramTime;
#endif
// uchar ucSystemRestOk;
//STR_CALENDAR FMtime;
uchar Staks,uchannel;
//gucSystemRestOk=0; switch(Mode) { case SYSTEM_RESET: ///停电唤醒初始化 ; case POWER_ON: ; case POWER_OFF: ; default : ; }
}
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
文章来源: xuesong.blog.csdn.net,作者:内核笔记,版权归原作者所有,如需转载,请联系作者。
原文链接:xuesong.blog.csdn.net/article/details/78143707
- 点赞
- 收藏
- 关注作者
评论(0)