/** **************************************************************************** * @file rtc_service_port_k1921vk028.c * @brief Порт RTC Service для семейства K1921VK028 (plib028). **************************************************************************** */ #include "rtc_service_port.h" #include "rtc_service_types.h" #include "plib028_bflash.h" #include "plib028_rtc.h" #include "plib028_rcu.h" #include #include /* Вывод: в данном HAL API явного выбора источника LSE/LSI на уровне C API нет, поэтому конфигурирование делается как AUTO с флагом активного источника AUTO. */ RtcService_PortResult RtcService_Port_InitClock(RtcService_ClockSource preferred_source, RtcService_ClockSource* actual_source) { if (actual_source != NULL) { *actual_source = RTC_SERVICE_CLOCK_SOURCE_AUTO; } if (preferred_source != RTC_SERVICE_CLOCK_SOURCE_AUTO) { /* На текущей ревизии драйвер NIIЭТ не предоставляет стабильных API для ручного * выбора LSE/LSI через публичные функции. Рекомендуется использовать AUTO. */ return RTC_SERVICE_PORT_RESULT_UNSUPPORTED_CLOCK; } /* Включение тактирования RTC в RCC */ RCU_APBClk0Cmd(RCU_APBClk0_RTC, ENABLE); return RTC_SERVICE_PORT_OK; } void RtcService_Port_EnableRtcClock(void) { /* На K1921VK028 дополнительной явной подготовки источника после включения тактирования * RTC/APB-блока, как правило, не требуется. Реализация оставлена явной для port API. */ (void)0; } uint8_t RtcService_Port_IsPowerOnReset(void) { /* TODO: при наличии отдельного API/регистра статуса сброса заменить на реальную проверку. * Безопасная дефолтная стратегия — считать, что это не cold reset. */ return 0U; } RtcService_PortResult RtcService_Port_ReadRtc(RtcService_DateTime* dt) { if (dt == NULL) return RTC_SERVICE_PORT_RESULT_HW_ERROR; RTC_Time_TypeDef t = {0}; RTC_Date_TypeDef d = {0}; RTC_GetTime(RTC_Format_BIN, &t); RTC_GetDate(RTC_Format_BIN, &d); dt->year = (uint16_t)d.Year; dt->month = (uint16_t)d.Month; dt->day = (uint16_t)d.Day; dt->weekday = (uint16_t)d.Weekday; dt->hour = (uint16_t)t.Hour; dt->minute = (uint16_t)t.Minute; dt->second = (uint16_t)t.Second; return RTC_SERVICE_PORT_OK; } RtcService_PortResult RtcService_Port_WriteRtc(const RtcService_DateTime* dt) { RTC_Time_TypeDef t = {0}; RTC_Date_TypeDef d = {0}; if (dt == NULL) return RTC_SERVICE_PORT_RESULT_HW_ERROR; t.PSecond = 0U; t.Hour = dt->hour; t.Minute = dt->minute; t.Second = dt->second; d.Year = dt->year; d.Month = dt->month; d.Day = dt->day; d.Weekday = (RTC_Weekday_TypeDef)dt->weekday; RTC_SetTime(RTC_Format_BIN, &t); RTC_SetDate(RTC_Format_BIN, &d); RTC_ShadowCmd(DISABLE); RTC_ShadowCmd(ENABLE); return RTC_SERVICE_PORT_OK; } RtcService_PortResult RtcService_Port_ReadBackup(uint32_t* buffer, size_t words) { if ((buffer == NULL) || (words == 0U)) return RTC_SERVICE_PORT_RESULT_HW_ERROR; for (size_t i = 0U; i < words; ++i) { BFLASH_ReadData((uint32_t)i, &buffer[i], BFLASH_Region_NVR); } return RTC_SERVICE_PORT_OK; } RtcService_PortResult RtcService_Port_WriteBackup(const uint32_t* buffer, size_t words) { if ((buffer == NULL) || (words == 0U)) return RTC_SERVICE_PORT_RESULT_HW_ERROR; for (size_t i = 0U; i < words; ++i) { BFLASH_WriteData((uint32_t)i, (uint32_t*)&buffer[i], BFLASH_Region_NVR); } return RTC_SERVICE_PORT_OK; } RtcService_PortResult RtcService_Port_EraseBackup(void) { BFLASH_ErasePage(0UL, BFLASH_Region_NVR); return RTC_SERVICE_PORT_OK; }