我正在尝试在STM32F469I-DISCO板上初始化RTC。由于我仍在学习,因此我尝试使用HAL API,使我可以完成一些项目,直到我对这种微 Controller 有了足够的了解,可以直接与寄存器一起使用。无论如何,我的代码使用了CubeF4的STM32F469I-DISCO模板,该模板允许直接加载HAL层和系统时钟(通过8 MHz HSE振荡器获得180 MHz)。为了初始化RTC,我遵循了UM1725 : Description of STM32F4 HAL and LL drivers中给出的说明。在页面715,第55.2.4节中,您具有使用HAL_RTC API的说明。第一点说,有必要启用“RTC域访问”。这一点在上面的部分(55.2.3,同一页)中进行了说明。我做了要求做的事情。这是我的代码(简化后,我只允许RTC Init部分和系统时钟配置):#include "main.h"RTC_HandleTypeDef rtcHandle;RTC_InitTypeDef rtcInit;RTC_TimeTypeDef rtcTime;RTC_DateTypeDef rtcDate;static void SystemClock_Config(void);static void Error_Handler(void);int main(void){ HAL_Init(); SystemClock_Config(); ////////////////// RTC HAL_PWR_EnableBkUpAccess(); __HAL_RCC_RTC_CONFIG(RCC_RTCCLKSOURCE_LSE); __HAL_RCC_RTC_ENABLE(); rtcInit.HourFormat = RTC_HOURFORMAT_24; rtcInit.AsynchPrediv = 0x7F; rtcInit.SynchPrediv = 0xFF; rtcInit.OutPut = RTC_OUTPUT_DISABLE; rtcInit.OutPutPolarity = RTC_OUTPUT_POLARITY_HIGH; rtcInit.OutPutType = RTC_OUTPUT_TYPE_OPENDRAIN; rtcHandle.Instance = RTC; rtcHandle.Init = rtcInit; HAL_RTC_Init(&rtcHandle); rtcTime.Hours = 12; rtcTime.Minutes = 30; rtcTime.Seconds = 40; rtcDate.WeekDay = RTC_WEEKDAY_WEDNESDAY; rtcDate.Month = RTC_MONTH_APRIL; rtcDate.Date = 4; rtcDate.Year= 17; HAL_RTC_SetTime(&rtcHandle, &rtcTime, RTC_FORMAT_BCD); while (1) { }}static void SystemClock_Config(void){ RCC_ClkInitTypeDef RCC_ClkInitStruct; RCC_OscInitTypeDef RCC_OscInitStruct; /* Enable Power Control clock */ __HAL_RCC_PWR_CLK_ENABLE(); __HAL_PWR_VOLTAGESCALING_CONFIG(PWR_REGULATOR_VOLTAGE_SCALE1); /* Enable HSE Oscillator and activate PLL with HSE as source */ RCC_OscInitStruct.OscillatorType = RCC_OSCILLATORTYPE_HSE; RCC_OscInitStruct.HSEState = RCC_HSE_ON; RCC_OscInitStruct.PLL.PLLState = RCC_PLL_ON; RCC_OscInitStruct.PLL.PLLSource = RCC_PLLSOURCE_HSE;#if defined(USE_STM32469I_DISCO_REVA) RCC_OscInitStruct.PLL.PLLM = 25;#else RCC_OscInitStruct.PLL.PLLM = 8;#endif /* USE_STM32469I_DISCO_REVA */ RCC_OscInitStruct.PLL.PLLN = 360; RCC_OscInitStruct.PLL.PLLP = RCC_PLLP_DIV2; RCC_OscInitStruct.PLL.PLLQ = 7; RCC_OscInitStruct.PLL.PLLR = 6; if(HAL_RCC_OscConfig(&RCC_OscInitStruct) != HAL_OK) { Error_Handler(); } /* Enable the OverDrive to reach the 180 Mhz Frequency */ if(HAL_PWREx_EnableOverDrive() != HAL_OK) { Error_Handler(); } RCC_ClkInitStruct.ClockType = (RCC_CLOCKTYPE_SYSCLK | RCC_CLOCKTYPE_HCLK | RCC_CLOCKTYPE_PCLK1 | RCC_CLOCKTYPE_PCLK2); RCC_ClkInitStruct.SYSCLKSource = RCC_SYSCLKSOURCE_PLLCLK; RCC_ClkInitStruct.AHBCLKDivider = RCC_SYSCLK_DIV1; RCC_ClkInitStruct.APB1CLKDivider = RCC_HCLK_DIV4; RCC_ClkInitStruct.APB2CLKDivider = RCC_HCLK_DIV2; if(HAL_RCC_ClockConfig(&RCC_ClkInitStruct, FLASH_LATENCY_5) != HAL_OK) { Error_Handler(); }}/** * @brief This function is executed in case of error occurrence. * @param None * @retval None */static void Error_Handler(void){ /* User may add here some code to deal with this error */ while(1) { }}#ifdef USE_FULL_ASSERT/** * @brief Reports the name of the source file and the source line number * where the assert_param error has occurred. * @param file: pointer to the source file name * @param line: assert_param error line source number * @retval None */void assert_failed(uint8_t* file, uint32_t line){ /* User can add his own implementation to report the file name and line number, ex: printf("Wrong parameters value: file %s on line %d\r\n", file, line) */ /* Infinite loop */ while (1) { }}#endif而且它不起作用。深入研究最低层后,我设法找到了不起作用的地方。我只是不知道为什么。HAL_RTC_Init()调用返回HAL_ERROR状态。出现此HAL_ERROR是因为HAL_RTC_Init()调用RTC_EnterInitMode()并返回HAL_TIMEOUT状态,因为在预期时间内未达到条件。以下是功能:HAL_StatusTypeDef HAL_RTC_Init(RTC_HandleTypeDef *hrtc){ /* Check the RTC peripheral state */ if(hrtc == NULL) { return HAL_ERROR; } /* Check the parameters */ assert_param(IS_RTC_HOUR_FORMAT(hrtc->Init.HourFormat)); assert_param(IS_RTC_ASYNCH_PREDIV(hrtc->Init.AsynchPrediv)); assert_param(IS_RTC_SYNCH_PREDIV(hrtc->Init.SynchPrediv)); assert_param (IS_RTC_OUTPUT(hrtc->Init.OutPut)); assert_param (IS_RTC_OUTPUT_POL(hrtc->Init.OutPutPolarity)); assert_param(IS_RTC_OUTPUT_TYPE(hrtc->Init.OutPutType)); if(hrtc->State == HAL_RTC_STATE_RESET) { /* Allocate lock resource and initialize it */ hrtc->Lock = HAL_UNLOCKED; /* Initialize RTC MSP */ HAL_RTC_MspInit(hrtc); } /* Set RTC state */ hrtc->State = HAL_RTC_STATE_BUSY; /* Disable the write protection for RTC registers */ __HAL_RTC_WRITEPROTECTION_DISABLE(hrtc); /* Set Initialization mode */ if(RTC_EnterInitMode(hrtc) != HAL_OK) { /* Enable the write protection for RTC registers */ __HAL_RTC_WRITEPROTECTION_ENABLE(hrtc); /* Set RTC state */ hrtc->State = HAL_RTC_STATE_ERROR; return HAL_ERROR; } else { /* Clear RTC_CR FMT, OSEL and POL Bits */ hrtc->Instance->CR &= ((uint32_t)~(RTC_CR_FMT | RTC_CR_OSEL | RTC_CR_POL)); /* Set RTC_CR register */ hrtc->Instance->CR |= (uint32_t)(hrtc->Init.HourFormat | hrtc->Init.OutPut | hrtc->Init.OutPutPolarity); /* Configure the RTC PRER */ hrtc->Instance->PRER = (uint32_t)(hrtc->Init.SynchPrediv); hrtc->Instance->PRER |= (uint32_t)(hrtc->Init.AsynchPrediv << 16U); /* Exit Initialization mode */ hrtc->Instance->ISR &= (uint32_t)~RTC_ISR_INIT; hrtc->Instance->TAFCR &= (uint32_t)~RTC_TAFCR_ALARMOUTTYPE; hrtc->Instance->TAFCR |= (uint32_t)(hrtc->Init.OutPutType); /* Enable the write protection for RTC registers */ __HAL_RTC_WRITEPROTECTION_ENABLE(hrtc); /* Set RTC state */ hrtc->State = HAL_RTC_STATE_READY; return HAL_OK; }}和 :HAL_StatusTypeDef RTC_EnterInitMode(RTC_HandleTypeDef* hrtc){ uint32_t tickstart = 0U; /* Check if the Initialization mode is set */ if((hrtc->Instance->ISR & RTC_ISR_INITF) == (uint32_t)RESET) { /* Set the Initialization mode */ hrtc->Instance->ISR = (uint32_t)RTC_INIT_MASK; /* Get tick */ tickstart = HAL_GetTick(); /* Wait till RTC is in INIT state and if Time out is reached exit */ while((hrtc->Instance->ISR & RTC_ISR_INITF) == (uint32_t)RESET) { if((HAL_GetTick() - tickstart ) > RTC_TIMEOUT_VALUE) { return HAL_TIMEOUT; } } } return HAL_OK;}因此,如果我进行了仔细的调查,问题是该条件: hrtc-> Instance-> ISR&RTC_ISR_INITF ==(uint32_t)RESET为true所有时间(因为TIMEOUT条件升高)。我不明白的是根据上面的函数(EnterInitMode),RTC_ISR_INITF和ISR变量似乎很清楚地定义,因此按位运算值不为0(RESET)。“ISR”直接在函数中定义,并且是RTC_INIT_MASK(在stm32f4xx_hal_rtc.h中使用#xfine定义0xFFFFFFFF值)“RTC_ISR_INITF”是一个宏:(0x1U 如果我说“&”运算不为0,那我错了吗?您知道我为什么要提出此超时条件吗?提前致谢 ! (adsbygoogle = window.adsbygoogle || []).push({}); 最佳答案 晚安之后,我解决了我的问题。我忘记了在SystemClock_Config()例程中初始化LSE Clock ...我只是在SystemClock_Config()中添加以下代码。RCC_OscInitTypeDef RCC_OscInitLSE;RCC_OscInitLSE.OscillatorType = RCC_OSCILLATORTYPE_LSE;RCC_OscInitLSE.LSEState = RCC_LSE_ON;if(HAL_RCC_OscConfig(&RCC_OscInitLSE) != HAL_OK){ Error_Handler();}之后,我使用STM Studio进行了测试,以可视化变量的演变。而且效果很好(以前没有)。带来不便敬请谅解。 (adsbygoogle = window.adsbygoogle || []).push({});
09-25 21:06