STM32F0 RTC on external crystal issue - Page 1
Forum section: electronics / general

author: pyrohaz
author_rank: Regular Contributor
timestamp: August 27, 2014, 09:03:30 pm
content: Hi All,I've tried asking over on the dedicated ST forum but I seemed to get absolutely zilcho reply so I'm going to ask here with the hope that the many of you who are smarter than me can help answer my question!I've got an STM32F0F6 running on my breadboard (its a TSSOP package, with a breakout board, fits in my breadboard!) and I've got it running my LCD too (based on an ILI9163 -http://hsel.co.uk/2014/08/23/colour-graphics-library-with-the-ili9163-128x128-lcd/). I'm currently using an external crystal of 8MHz and this is correctly clocking the STM32F0 chip. I'm not after accurate frequency representation from the crystal as of yet. I now know that capacitance can effect this quite drastically so please ignore that part!The problem I'm struggling with is driving the internal RTC from this HSE crystal (high speed external - according to ST language). With the low speed internal oscillator, this RTC clocks just fine and I can see the numbers updating every second on my LCD. When I change just two lines in the code for which it should run off HSE, I get nothing! Its obviously a register synchronisation problem because aslong as I don't remove power, the microcontroller retains its previous RTC values and if I then reprogram to change back to LSI, the RTC picks up from where its left.My code is:Code:RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);PWR_BackupAccessCmd(ENABLE);RCC_LSICmd(ENABLE);while(RCC_GetFlagStatus(RCC_FLAG_LSIRDY) == RESET);//RCC_RTCCLKConfig(RCC_RTCCLKSource_HSE_Div32);RCC_RTCCLKConfig(RCC_RTCCLKSource_LSI);RCC_RTCCLKCmd(ENABLE);RTC_WaitForSynchro();R.RTC_AsynchPrediv = 100;//R.RTC_SynchPrediv = 2499;R.RTC_SynchPrediv = 399;R.RTC_HourFormat = RTC_HourFormat_24;RTC_Init(&R);As you can see, if I uncommentRCC_RTCCLKConfig(RCC_RTCCLKSource_HSE_Div32);and comment:RCC_LSICmd(ENABLE);while(RCC_GetFlagStatus(RCC_FLAG_LSIRDY) == RESET);andRCC_RTCCLKConfig(RCC_RTCCLKSource_LSI);And I change the synchronous predivider to suit the new clock, this should work but it doesn't! Could anybody provide me with some insight please?Thanks!

author: pyrohaz
author_rank: Regular Contributor
timestamp: August 27, 2014, 09:42:54 pm
content: By doesn't work, I mean there is no value displayed on the screen meaning the value for time within the RTC registers is equal to 0. Sorry about the ambiguity!

author: drobe011
author_rank: Newbie
timestamp: September 01, 2014, 01:48:33 pm
content: You cannot change the clock source unless you reset the RTC domain first. What I do if I need to change the RTC clock source is just power cycle the device.From the ST Ref manual:Note:Wait states are inserted in case of successive accesses to this register.The LSEON, LSEBYP, RTCSEL and RTCEN bits of the RTC domain control register(RCC_BDCR) are in the RTC domain. As a result, after Reset, these bits are write-protectedand the DBP bit in the Power control register (PWR_CR) has to be set before these can bemodified. Refer to Section 6.1.2 on page 78 for further information. These bits are only resetafter a RTC domain Reset (see Section 7.1.3: RTC domain reset). Any internal or externalReset will not have any effect on these bits.-Dave

author: pyrohaz
author_rank: Regular Contributor
timestamp: September 02, 2014, 08:50:17 pm
content: Hi Dave,Thanks for the reply! Well after some arduous coding and testing to see what the hell will actually work, I think I've managed it! I never realised that I needed to reconfigure the clock after reset. I've used the RCC_BackupResetCmd() function to reset the RTC backup domain. I'll attach the whole test code here for future users!Code:#include <stm32f0xx_rcc.h>#include <stm32f0xx_rtc.h>#include <stm32f0xx_gpio.h>#include <stm32f0xx_pwr.h>RTC_InitTypeDef R;RTC_TimeTypeDef RT;int main(void){RCC_APB1PeriphClockCmd(RCC_APB1Periph_PWR, ENABLE);RCC_HSEConfig(RCC_HSE_ON);while(RCC_GetFlagStatus(RCC_FLAG_HSERDY) == RESET);RCC_SYSCLKConfig(RCC_SYSCLKSource_HSE);PWR_BackupAccessCmd(ENABLE);RCC_RTCCLKConfig(RCC_RTCCLKSource_HSE_Div32);RCC_RTCCLKCmd(ENABLE);RCC_BackupResetCmd(ENABLE);RCC_BackupResetCmd(DISABLE);RCC_RTCCLKConfig(RCC_RTCCLKSource_HSE_Div32);RCC_RTCCLKCmd(ENABLE);R.RTC_AsynchPrediv = 99;R.RTC_SynchPrediv = 2499;R.RTC_HourFormat = RTC_HourFormat_24;RTC_Init(&R);uint16_t Sec = 0;while(1){RTC_GetTime(RTC_Format_BIN, &RT);Sec = RT.RTC_Seconds;}}