Skip to content

Instantly share code, notes, and snippets.

@lbussy
Last active November 8, 2020 16:04
Show Gist options
  • Save lbussy/1205a3da0222e499570d55a6a0e60720 to your computer and use it in GitHub Desktop.
Save lbussy/1205a3da0222e499570d55a6a0e60720 to your computer and use it in GitHub Desktop.
A safe "blocking" delay for use with watchdog timers

Safe Delay for μControllers

Most microcontroller platforms implement a watchdog timer that resets the controller if it detects a freeze. It does that by checking to see if the code has yielded. On some, a delay() that exceeds the watchdog timer's limits will initiate a reset.

This "safe" delay yields to the stack every tick to create a "blocking" delay in user code; however, internal functions like the watchdog timer are not blocked. It optionally prints a dot every second.

//////////////////////////////////////////////////////////////////////////
//
// _delay: A safe delay() replacement. Delay by defined 32-bit number
// of milliseconds (1 to 4,294,967,295 millis) or up to
// 4,294,967 seconds. Yields to the stack every millisecond
// in order to create a "blocking" delay in terms of user code
// however internal functions like the watchdog timer are not
// blocked. Optionally print a dot every second.
//
// Args:
// delayMillis: Unsigned Long in millis()
// printDot: (optional) Print dot every second
//
//////////////////////////////////////////////////////////////////////////
#include <Ticker.h>
#include <Arduino.h>
void _delay(unsigned long delayMillis, bool printDot = false)
void _dot();
void setup() {
Serial.begin(74880);
Serial.println("\n");
Serial.print("Start = ");
Serial.println(millis());
// Delay for 5 seconds, print dots each second
_delay(5000, true);
Serial.print("Finish = ");
Serial.println(millis());
Serial.println("Done.");
}
void loop() {}
void _delay(unsigned long delayMillis, bool printDot)
{
// Safe blocking delay() replacement
Ticker _dottimer;
if (printDot)
{
_dottimer.attach(1.0, _dot);
}
unsigned long ulNow = millis();
unsigned long ulThen = ulNow + delayMillis;
while (ulThen > millis())
{
yield();
}
if (printDot)
{
Serial.println();
_dottimer.detach();
}
}
void _dot()
{
Serial.print(".");
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment