AnsweredAssumed Answered

RTC - Timestamp when the RTC's power supply is VBAT.

Question asked by bompart.romy on Dec 3, 2013
Hi everyone, 

    I am trying to figure out how make work the RTC timestamp feature when this peripheral is supplied by VBAT and when a Tamper detection occurs. And be sure about my RTC configuration , because the RTC is not keeping the time or is not running, when the power supply is turned off.

      I read this:  

                     "A tamper detection event resets all backup registers (RTC_BKPxR)."                                               (RM0090 Reference manual, Page 791).

          So  when a TAMPER event occurs, all backup data registers are erased. In this case, I am using the backup data register 0 to write a 0x32F2, thus when I turn on the power supply this data should be there at the moment to read the register data to tell the program " HEY!, you don't have to configure me again", but if a TAMPER event occurs this register is erased. Maybe it is happening.
     
        Question : What do you recommend me to solve it?

     Note: I have measure the signal in osc32_in and osc32_out whe the power supply is turned off and there is a 32.678 Khz wave. So the VBAT is supplying the RTC peripheral. 

     My code:

/* The code in my .h */
 
#ifndef __USER_STM32F4xx_RTC_H
#define __USER_STM32F4xx_RTC_H
/* Uncomment the corresponding line to select the RTC Clock source */
#define RTC_CLOCK_SOURCE_LSE   // LSE used as RTC source clock */
//#define RTC_CLOCK_SOURCE_LSI */ // LSI used as RTC source clock. The RTC Clock
#include <stm32f4xx_rtc.h>
#include <stm32f4xx_pwr.h>
#include <stm32f4xx_exti.h>
#include <stdio.h>
#include "Uart_Hardware.h"
 
 
#define ALREADY_CONFIG  0x32F2
 
extern void User_RTC_TAMP1_Init(void);
static void User_RTC_Config(void);
static void User_TAMPER_Config(void);
static void Time_Config_first_time(void);
extern void RTC_TimeShow(void);
extern void RTC_DateShow(void);
extern void Usart_Set_Calendar_RTC(void);
#endif
 
/* The code in my .c*/
 
#include "User_stm32f4xx_RTC.h"
 
RTC_InitTypeDef RTC_InitStructure;
RTC_TimeTypeDef RTC_TimeStructure;
RTC_DateTypeDef RTC_DateStructure;
 
__IO uint32_t SynchPrediv =0, AsynchPrediv =0;
char RTC_Buffer[50];
 
/**
  * @brief  Configure the RTC peripheral with the Tamper feature at the beginning of its use
  * @param  None
  * @retval None
  */
void User_RTC_TAMP1_Init(void)
{
        /*Declaring variables for Interruption configuration*/
        NVIC_InitTypeDef NVIC_InitStructure;
        EXTI_InitTypeDef  EXTI_InitStructure;
     
        /* Enable the PWR clock */
        RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);
     
      /* Allow access to RTC */
        PWR_BackupAccessCmd(ENABLE);
       
        /* Configure one bit for preemption priority */
        NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
       
        /*Clearing the RTC_IT_TAMP1 Flag*/
        RTC_ClearITPendingBit(RTC_IT_TAMP1);
     
      /* Enable The external line21 interrupt */
        EXTI_ClearITPendingBit(EXTI_Line21);
        EXTI_InitStructure.EXTI_Line = EXTI_Line21;  /*The line 21 is connected to RTC Tamper and Time Stamp events*/
        EXTI_InitStructure.EXTI_Mode = EXTI_Mode_Interrupt; /*Although there is an specific handler for TAMP_STAMP */
        EXTI_InitStructure.EXTI_Trigger = EXTI_Trigger_Rising;
        EXTI_InitStructure.EXTI_LineCmd = ENABLE;
        EXTI_Init(&EXTI_InitStructure);
        /* Enable TAMPER IRQChannel */
        NVIC_InitStructure.NVIC_IRQChannel = TAMP_STAMP_IRQn;
        NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1;
        NVIC_InitStructure.NVIC_IRQChannelSubPriority = 0;
        NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE;
        NVIC_Init(&NVIC_InitStructure);
     
        if (RTC_ReadBackupRegister(RTC_BKP_DR0) != ALREADY_CONFIG)
        
            /*RTC Configuring for the first time*/
            User_RTC_Config();
            /* Setting and configuring the time*/
            Time_Config_first_time();
            /*TAMPER Configuration for the first time*/
            User_TAMPER_Config();
            /*Write to the first RTC Backup Data Register the user flag ALREADY_CONFIG*/
            RTC_WriteBackupRegister(RTC_BKP_DR0, ALREADY_CONFIG);
        }
        else
        {
            /* Check if the Power On Reset flag is set */
            if (RCC_GetFlagStatus(RCC_FLAG_PORRST) != RESET)
            {
                Usart_Send("\r\n Ocurrio un Power On Reset ....\n\r",USARTPC);
            }
            /* Check if the Pin Reset flag is set */
         if (RCC_GetFlagStatus(RCC_FLAG_PINRST) != RESET)
            {
                Usart_Send("\r\n Ocurrio un Reset Externo ....\n\r",USARTPC);
            }
 
            Usart_Send("\n\r No se requiere configurar RTC....\n\r",USARTPC);
            /* Enable the RTC Clock */
          RCC_RTCCLKCmd(ENABLE);
            /* Wait for RTC APB registers synchronisation */
            RTC_WaitForSynchro();
        }
        /*Disabling the RTC ALARM*/
        RTC_AlarmCmd(RTC_Alarm_A, DISABLE);
    }
 
/**
  * @brief  Configure the RTC peripheral by selecting the clock source.
  * @param  None
  * @retval None
  */
void User_RTC_Config(void)
{
//   /* Enable the PWR clock */
//   RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);
 
//   /* Allow access to RTC */
//   PWR_BackupAccessCmd(ENABLE);
     
#if defined (RTC_CLOCK_SOURCE_LSI)  /* LSI used as RTC source clock*/
/* The RTC Clock may varies due to LSI frequency dispersion. */  
  /* Enable the LSI OSC */
  RCC_LSICmd(ENABLE);
 
  /* Wait till LSI is ready */ 
  while(RCC_GetFlagStatus(RCC_FLAG_LSIRDY) == RESET)
  {
  }
 
  /* Select the RTC Clock Source */
  RCC_RTCCLKConfig(RCC_RTCCLKSource_LSI);
   
  SynchPrediv = 0xFF;
  AsynchPrediv = 0x7F;
 
#elif defined (RTC_CLOCK_SOURCE_LSE) /* LSE used as RTC source clock */
  /* Enable the LSE OSC */
  RCC_LSEConfig(RCC_LSE_ON);
 
  /* Wait till LSE is ready */ 
  while(RCC_GetFlagStatus(RCC_FLAG_LSERDY) == RESET)
  {
  }
 
  /* Select the RTC Clock Source */
  RCC_RTCCLKConfig(RCC_RTCCLKSource_LSE);
   
  SynchPrediv = 0xFF;
  AsynchPrediv = 0x7F;
 
#else
  #error Please select the RTC Clock source inside the main.c file
#endif /* RTC_CLOCK_SOURCE_LSI */
   
  /* Enable the RTC Clock */
  RCC_RTCCLKCmd(ENABLE);
  /* Wait for RTC APB registers synchronisation */
  RTC_WaitForSynchro();
}
 
/**
  * @brief  Configuration of Tamper
  * @param  None
  * @retval None
  */
void User_TAMPER_Config(void)
{
    /* Disable the Tamper 1 detection */
  RTC_TamperCmd(RTC_Tamper_1, DISABLE);
  /* Clear Tamper 1 pin Event(TAMP1F) pending flag */
  RTC_ClearFlag(RTC_FLAG_TAMP1F);
    /*Selecting PC13 as a Tamper pin*/
    RTC_TamperPinSelection(RTC_TamperPin_PC13);
    /* Precharge time*/
    RTC_TamperPinsPrechargeDuration(RTC_TamperPrechargeDuration_4RTCCLK);
  /* Configure the Tamper 1 Trigger */
  RTC_TamperTriggerConfig(RTC_Tamper_1, RTC_TamperTrigger_RisingEdge);
  /* Enable the Tamper interrupt */
  RTC_ITConfig(RTC_IT_TAMP, ENABLE);
  /* Clear Tamper 1 pin interrupt pending bit */
  RTC_ClearITPendingBit(RTC_IT_TAMP1);
    /* Enable The TimeStamp */
    RTC_TimeStampOnTamperDetectionCmd(ENABLE);
  /* Enable the Tamper 1 detection */
  RTC_TamperCmd(RTC_Tamper_1, ENABLE);
}
 
/**
  * @brief  Time Configuration
  * @param  None
  * @retval None
  */
void Time_Config_first_time(void)
{
    /* Set the Time */
  RTC_TimeStructure.RTC_Hours   = 9;
  RTC_TimeStructure.RTC_Minutes = 30;
  RTC_TimeStructure.RTC_Seconds = 0;
 
  /* Set the Date */
  RTC_DateStructure.RTC_Month = RTC_Month_September;
  RTC_DateStructure.RTC_Date = 22; 
  RTC_DateStructure.RTC_Year = 13;
  RTC_DateStructure.RTC_WeekDay = RTC_Weekday_Friday;
 
  /* Calendar Configuration */
  RTC_InitStructure.RTC_AsynchPrediv = AsynchPrediv;
  RTC_InitStructure.RTC_SynchPrediv =  SynchPrediv;
  RTC_InitStructure.RTC_HourFormat = RTC_HourFormat_12;
  RTC_Init(&RTC_InitStructure);
   
    /* Check on RTC init */
  if (RTC_Init(&RTC_InitStructure) == ERROR){Usart_Send("\n\r/!\\***** Falla al inicializar el RTC ********/!\\ \n\r",USARTPC);}
   
    /* Set Current Time and Date */
  if (RTC_SetTime(RTC_Format_BCD, &RTC_TimeStructure) == ERROR){Usart_Send("\n\r/!\\***** Falla al setear el tiempo del RTC ********/!\\ \n\r",USARTPC);} 
  if (RTC_SetDate(RTC_Format_BCD, &RTC_DateStructure) == ERROR){Usart_Send("\n\r/!\\***** Falla al setear la fecha del RTC ********/!\\ \n\r",USARTPC);}
}
 
/**
  * @brief  Display the current time on the Hyperterminal.
  * @param  None
  * @retval None
  */
void RTC_TimeShow(void)
{
  /* Get the current Time */
  RTC_GetTime(RTC_Format_BIN, &RTC_TimeStructure);
  sprintf(RTC_Buffer,"\n\r  El tiempo actual es :  %0.2d:%0.2d:%0.2d \n\r", RTC_TimeStructure.RTC_Hours, RTC_TimeStructure.RTC_Minutes, RTC_TimeStructure.RTC_Seconds);
    Usart_Send(RTC_Buffer,USARTPC);
}
/**
  * @brief  Display the current date on the Hyperterminal.
  * @param  None
  * @retval None
  */
void RTC_DateShow()
{
    /* Get the current Time */
  RTC_GetDate(RTC_Format_BIN, &RTC_DateStructure);
  sprintf(RTC_Buffer,"\n\r  La Fecha es  :  %0.2d-%0.2d-%0.2d \n\r", RTC_DateStructure.RTC_Date, RTC_DateStructure.RTC_Month, RTC_DateStructure.RTC_Year);
    Usart_Send(RTC_Buffer,USARTPC);
}


    

Outcomes