a

Fork of Watchdog by Bernard Remond

Committer:
suads
Date:
Tue Sep 26 20:47:06 2017 +0000
Revision:
7:098b53d90b3d
Parent:
6:40f189c7795b
xx

Who changed what in which revision?

UserRevisionLine numberNew contents of line
WiredHome 2:2873f068f325 1 /// @file Watchdog.cpp provides the interface to the Watchdog module
WiredHome 2:2873f068f325 2 ///
WiredHome 2:2873f068f325 3 /// This provides basic Watchdog service for the mbed. You can configure
WiredHome 2:2873f068f325 4 /// various timeout intervals that meet your system needs. Additionally,
WiredHome 2:2873f068f325 5 /// it is possible to identify if the Watchdog was the cause of any
WiredHome 2:2873f068f325 6 /// system restart.
WiredHome 2:2873f068f325 7 ///
WiredHome 2:2873f068f325 8 /// Adapted from Simon's Watchdog code from http://mbed.org/forum/mbed/topic/508/
WiredHome 2:2873f068f325 9 ///
WiredHome 2:2873f068f325 10 /// @note Copyright © 2011 by Smartware Computing, all rights reserved.
WiredHome 2:2873f068f325 11 /// This software may be used to derive new software, as long as
WiredHome 2:2873f068f325 12 /// this copyright statement remains in the source file.
WiredHome 2:2873f068f325 13 /// @author David Smart
WiredHome 2:2873f068f325 14 ///
nbremond 5:ea5595e2698b 15 /// @note Copyright © 2015 by NBRemond, all rights reserved.
nbremond 5:ea5595e2698b 16 /// This software may be used to derive new software, as long as
nbremond 5:ea5595e2698b 17 /// this copyright statement remains in the source file.
nbremond 5:ea5595e2698b 18 ///
nbremond 5:ea5595e2698b 19 /// Added support for STM32 Nucleo platforms
nbremond 5:ea5595e2698b 20 ///
nbremond 5:ea5595e2698b 21 /// @author Bernaérd Remond
nbremond 5:ea5595e2698b 22 ///
nbremond 5:ea5595e2698b 23
suads 7:098b53d90b3d 24 //#define LPC
suads 7:098b53d90b3d 25 #define ST_NUCLEO
nbremond 5:ea5595e2698b 26
nbremond 5:ea5595e2698b 27
WiredHome 0:7a316f14da9c 28 #include "mbed.h"
WiredHome 0:7a316f14da9c 29 #include "Watchdog.h"
WiredHome 0:7a316f14da9c 30
WiredHome 0:7a316f14da9c 31
WiredHome 0:7a316f14da9c 32 /// Watchdog gets instantiated at the module level
WiredHome 0:7a316f14da9c 33 Watchdog::Watchdog() {
suads 7:098b53d90b3d 34 /*
nbremond 5:ea5595e2698b 35 #ifdef LPC
WiredHome 2:2873f068f325 36 wdreset = (LPC_WDT->WDMOD >> 2) & 1; // capture the cause of the previous reset
nbremond 5:ea5595e2698b 37 #endif
suads 7:098b53d90b3d 38 */
nbremond 5:ea5595e2698b 39 #ifdef ST_NUCLEO
nbremond 5:ea5595e2698b 40 // capture the cause of the previous reset
nbremond 5:ea5595e2698b 41 /* Check if the system has resumed from IWDG reset */
suads 7:098b53d90b3d 42 printf("Watchdog()\n");
suads 7:098b53d90b3d 43
nbremond 5:ea5595e2698b 44 if (__HAL_RCC_GET_FLAG(RCC_FLAG_IWDGRST)) {
nbremond 5:ea5595e2698b 45 wdreset = true;
nbremond 5:ea5595e2698b 46 }
nbremond 5:ea5595e2698b 47 else {
nbremond 5:ea5595e2698b 48 wdreset = false;
nbremond 5:ea5595e2698b 49 }
suads 7:098b53d90b3d 50
nbremond 5:ea5595e2698b 51 wdreset = false;
nbremond 5:ea5595e2698b 52 #endif
nbremond 5:ea5595e2698b 53
WiredHome 0:7a316f14da9c 54 }
WiredHome 0:7a316f14da9c 55
WiredHome 0:7a316f14da9c 56 /// Load timeout value in watchdog timer and enable
nbremond 5:ea5595e2698b 57 void Watchdog::Configure(float timeout) {
suads 7:098b53d90b3d 58 /*
nbremond 5:ea5595e2698b 59 #ifdef LPC
WiredHome 0:7a316f14da9c 60 LPC_WDT->WDCLKSEL = 0x1; // Set CLK src to PCLK
WiredHome 0:7a316f14da9c 61 uint32_t clk = SystemCoreClock / 16; // WD has a fixed /4 prescaler, PCLK default is /4
nbremond 5:ea5595e2698b 62 LPC_WDT->WDTC = (uint32_t)(timeout * (float)clk);
WiredHome 0:7a316f14da9c 63 LPC_WDT->WDMOD = 0x3; // Enabled and Reset
suads 7:098b53d90b3d 64 #endif
suads 7:098b53d90b3d 65 */
nbremond 5:ea5595e2698b 66 #ifdef ST_NUCLEO
nbremond 5:ea5595e2698b 67 // see http://embedded-lab.com/blog/?p=9662
nbremond 5:ea5595e2698b 68 #define LsiFreq (45000)
suads 7:098b53d90b3d 69 printf("Configure\n");
nbremond 5:ea5595e2698b 70 uint16_t PrescalerCode;
nbremond 5:ea5595e2698b 71 uint16_t Prescaler;
nbremond 5:ea5595e2698b 72 uint16_t ReloadValue;
nbremond 5:ea5595e2698b 73 float Calculated_timeout;
nbremond 5:ea5595e2698b 74
nbremond 5:ea5595e2698b 75 if ((timeout * (LsiFreq/4)) < 0x7FF) {
nbremond 5:ea5595e2698b 76 PrescalerCode = IWDG_PRESCALER_4;
nbremond 5:ea5595e2698b 77 Prescaler = 4;
nbremond 5:ea5595e2698b 78 }
nbremond 5:ea5595e2698b 79 else if ((timeout * (LsiFreq/8)) < 0xFF0) {
nbremond 5:ea5595e2698b 80 PrescalerCode = IWDG_PRESCALER_8;
nbremond 5:ea5595e2698b 81 Prescaler = 8;
nbremond 5:ea5595e2698b 82 }
nbremond 5:ea5595e2698b 83 else if ((timeout * (LsiFreq/16)) < 0xFF0) {
nbremond 5:ea5595e2698b 84 PrescalerCode = IWDG_PRESCALER_16;
nbremond 5:ea5595e2698b 85 Prescaler = 16;
nbremond 5:ea5595e2698b 86 }
nbremond 5:ea5595e2698b 87 else if ((timeout * (LsiFreq/32)) < 0xFF0) {
nbremond 5:ea5595e2698b 88 PrescalerCode = IWDG_PRESCALER_32;
nbremond 5:ea5595e2698b 89 Prescaler = 32;
nbremond 5:ea5595e2698b 90 }
nbremond 5:ea5595e2698b 91 else if ((timeout * (LsiFreq/64)) < 0xFF0) {
nbremond 5:ea5595e2698b 92 PrescalerCode = IWDG_PRESCALER_64;
nbremond 5:ea5595e2698b 93 Prescaler = 64;
nbremond 5:ea5595e2698b 94 }
nbremond 5:ea5595e2698b 95 else if ((timeout * (LsiFreq/128)) < 0xFF0) {
nbremond 5:ea5595e2698b 96 PrescalerCode = IWDG_PRESCALER_128;
nbremond 5:ea5595e2698b 97 Prescaler = 128;
nbremond 5:ea5595e2698b 98 }
nbremond 5:ea5595e2698b 99 else {
nbremond 5:ea5595e2698b 100 PrescalerCode = IWDG_PRESCALER_256;
nbremond 5:ea5595e2698b 101 Prescaler = 256;
nbremond 5:ea5595e2698b 102 }
nbremond 5:ea5595e2698b 103
nbremond 5:ea5595e2698b 104 // specifies the IWDG Reload value. This parameter must be a number between 0 and 0x0FFF.
nbremond 5:ea5595e2698b 105 ReloadValue = (uint32_t)(timeout * (LsiFreq/Prescaler));
nbremond 5:ea5595e2698b 106
nbremond 5:ea5595e2698b 107 Calculated_timeout = ((float)(Prescaler * ReloadValue)) / LsiFreq;
suads 7:098b53d90b3d 108 printf("WATCHDOG set with prescaler:%d reload value Nucleo: 0x%X - timeout:%f\n",Prescaler, ReloadValue, Calculated_timeout);
nbremond 5:ea5595e2698b 109
nbremond 5:ea5595e2698b 110 IWDG->KR = 0x5555; //Disable write protection of IWDG registers
nbremond 5:ea5595e2698b 111 IWDG->PR = PrescalerCode; //Set PR value
nbremond 5:ea5595e2698b 112 IWDG->RLR = ReloadValue; //Set RLR value
nbremond 5:ea5595e2698b 113 IWDG->KR = 0xAAAA; //Reload IWDG
nbremond 5:ea5595e2698b 114 IWDG->KR = 0xCCCC; //Start IWDG - See more at: http://embedded-lab.com/blog/?p=9662#sthash.6VNxVSn0.dpuf
nbremond 5:ea5595e2698b 115 #endif
nbremond 5:ea5595e2698b 116
WiredHome 0:7a316f14da9c 117 Service();
WiredHome 0:7a316f14da9c 118 }
WiredHome 0:7a316f14da9c 119
WiredHome 0:7a316f14da9c 120 /// "Service", "kick" or "feed" the dog - reset the watchdog timer
WiredHome 0:7a316f14da9c 121 /// by writing this required bit pattern
WiredHome 0:7a316f14da9c 122 void Watchdog::Service() {
suads 7:098b53d90b3d 123 /*
nbremond 5:ea5595e2698b 124 #ifdef LPC
WiredHome 0:7a316f14da9c 125 LPC_WDT->WDFEED = 0xAA;
WiredHome 0:7a316f14da9c 126 LPC_WDT->WDFEED = 0x55;
suads 7:098b53d90b3d 127 #endif
suads 7:098b53d90b3d 128 */
nbremond 5:ea5595e2698b 129 #ifdef ST_NUCLEO
suads 7:098b53d90b3d 130 // printf("Service\n");
nbremond 5:ea5595e2698b 131 IWDG->KR = 0xAAAA; //Reload IWDG - See more at: http://embedded-lab.com/blog/?p=9662#sthash.6VNxVSn0.dpuf
nbremond 5:ea5595e2698b 132 #endif
WiredHome 0:7a316f14da9c 133 }
WiredHome 0:7a316f14da9c 134
WiredHome 0:7a316f14da9c 135 /// get the flag to indicate if the watchdog causes the reset
WiredHome 0:7a316f14da9c 136 bool Watchdog::WatchdogCausedReset() {
suads 7:098b53d90b3d 137 printf("WatchdogCausedReset\n");
WiredHome 0:7a316f14da9c 138 return wdreset;
WiredHome 0:7a316f14da9c 139 }
WiredHome 0:7a316f14da9c 140
suads 7:098b53d90b3d 141 bool Watchdog::dsable(){
suads 7:098b53d90b3d 142
suads 7:098b53d90b3d 143 }
WiredHome 0:7a316f14da9c 144
suads 7:098b53d90b3d 145