PropBasic: Simple reboot timer
VonSzarvas
Posts: 3,509
Here is a simple timer for a project that requires the Propeller to reboot every few minutes, regardless of what it is doing.
Set the required timeout period by adjusting:
wdTimerLoopSecs - which is the innerloop timer and can be up to 50 seconds
wdTimerReps - which is the outerloop timer, and so is multiplied by the innerloop time seconds to get the timeout value (in my example 30 seconds * 2 reps = 60 seconds timeout period)
When the task expires the propeller will reboot. You might not want the reboot, but the code might be useful for re-purposing!
Of interest is the code to make adjustments when the wdTimerEnd is calculated negative. This is necessary so that the internal timer loop can run for more than 26 seconds! This is the main reason I am posting this solution, as this "number wraparound" took some moments to solve!
Without the negative-adjustment code you must keep the wdTimerLoopSecs LESS than 26 seconds. You could remove the code, reduce the internal loop to, say 20 seconds, then increase the wdTimerReps appropriately if you wanted to save some code space. This time I wanted to solve the problem both ways and to provide a full example!
If might be fun to experiment by setting different values and logging the results.
Set the required timeout period by adjusting:
wdTimerLoopSecs - which is the innerloop timer and can be up to 50 seconds
wdTimerReps - which is the outerloop timer, and so is multiplied by the innerloop time seconds to get the timeout value (in my example 30 seconds * 2 reps = 60 seconds timeout period)
When the task expires the propeller will reboot. You might not want the reboot, but the code might be useful for re-purposing!
Of interest is the code to make adjustments when the wdTimerEnd is calculated negative. This is necessary so that the internal timer loop can run for more than 26 seconds! This is the main reason I am posting this solution, as this "number wraparound" took some moments to solve!
Without the negative-adjustment code you must keep the wdTimerLoopSecs LESS than 26 seconds. You could remove the code, reduce the internal loop to, say 20 seconds, then increase the wdTimerReps appropriately if you wanted to save some code space. This time I wanted to solve the problem both ways and to provide a full example!
If might be fun to experiment by setting different values and logging the results.
' ---------------------------------------------------------------------- '{$CODE} ' ---------------------------------------------------------------------- TASK TASK_WDTIMER_REBOOT ' ---------------------------------------------------------------------- ' VARIABLES / CONSTANTS ' ---------------------------------------------------------------------- wdTimerLoopSecs CON 30 ' ~30 seconds (Maximum ~50 seconds!) wdTimerReps VAR Long = 2 ' Reps * LoopSecs = timeout delay wdTimerStart VAR Long = 0 wdTimerEnd VAR Long = 0 wdTimerTmp VAR Long = 0 ' ---------------------------------------------------------------------- ' TASK MAIN ' ---------------------------------------------------------------------- DO UNTIL wdTimerReps = 0 wdTimerStart = CNT wdTimerEnd = _FREQ * wdTimerLoopSecs ' If wdTimerEnd is negative, make some adjustments ' Include this code if wdTimerLoopSecs > 26 seconds wdTimerTmp = SGN wdTimerEnd IF wdTimerTmp = -1 THEN DEC wdTimerEnd, $7FFFFFFF INC wdTimerStart, $7FFFFFFF ENDIF DO wdTimerTmp = CNT DEC wdTimerTmp, wdTimerStart IF wdTimerTmp > wdTimerEnd THEN ' timeout exceeded! EXIT ' Exit the inner loop, start next rep. ENDIF ' Do something here, or just pause a little if nothing else to do! PAUSE 500 LOOP DEC wdTimerReps LOOP ' Timer expired so REBOOT the propeller! CLKSET 128 ENDTASK