--- /dev/null
+/* This is from http://www.mtcnet.net/~henryvm/wdt/ */\r
+#ifndef _AVR_WD_H_\r
+#define _AVR_WD_H_\r
+\r
+#include <avr/io.h>\r
+\r
+/*\r
+Copyright (c) 2009, Curt Van Maanen\r
+\r
+Permission to use, copy, modify, and/or distribute this software for any\r
+purpose with or without fee is hereby granted, provided that the above\r
+copyright notice and this permission notice appear in all copies.\r
+\r
+THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES\r
+WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF\r
+MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR\r
+ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES\r
+WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN\r
+ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF\r
+OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.\r
+\r
+\r
+include usage-\r
+ #include "wd.h" //if in same directory as project\r
+ #include <avr/wd.h> //if wd.h is in avr directory\r
+\r
+set watchdog modes and prescale\r
+\r
+usage-\r
+ WD_SET(mode,[timeout]); //prescale always set\r
+\r
+modes-\r
+ WD_OFF disabled\r
+ WD_RST normal reset mode\r
+ WD_IRQ interrupt only mode (if supported)\r
+ WD_RST_IRQ interrupt+reset mode (if supported)\r
+\r
+timeout-\r
+ WDTO_15MS default if no timeout provided\r
+ WDTO_30MS\r
+ WDTO_60MS\r
+ WDTO_120MS\r
+ WDTO_250MS\r
+ WDTO_500MS\r
+ WDTO_1S\r
+ WDTO_2S\r
+ WDTO_4S (if supported)\r
+ WDTO_8S (if supported)\r
+\r
+examples-\r
+ WD_SET(WD_RST,WDTO_1S); //reset mode, 1s timeout\r
+ WD_SET(WD_OFF); //watchdog disabled (if not fused on)\r
+ WD_SET(WD_RST); //reset mode, 15ms (default timeout)\r
+ WD_SET(WD_IRQ,WDTO_120MS); //interrupt only mode, 120ms timeout\r
+ WD_SET(WD_RST_IRQ,WDTO_2S); //interrupt+reset mode, 2S timeout\r
+\r
+\r
+for enhanced watchdogs, if the watchdog is not being used WDRF should be\r
+cleared on every power up or reset, along with disabling the watchdog-\r
+ WD_DISABLE(); //clear WDRF, then turn off watchdog\r
+\r
+*/\r
+\r
+//reset registers to the same name (MCUCSR)\r
+#if !defined(MCUCSR)\r
+#define MCUCSR MCUSR\r
+#endif\r
+\r
+//watchdog registers to the same name (WDTCSR)\r
+#if !defined(WDTCSR)\r
+#define WDTCSR WDTCR\r
+#endif\r
+\r
+//if enhanced watchdog, define irq values, create disable macro\r
+#if defined(WDIF)\r
+#define WD_IRQ 0xC0\r
+#define WD_RST_IRQ 0xC8\r
+#define WD_DISABLE() do{ \\r
+ MCUCSR &= ~(1<<WDRF); \\r
+ WD_SET(WD_OFF); \\r
+ }while(0)\r
+#endif\r
+\r
+//all watchdogs\r
+#define WD_RST 8\r
+#define WD_OFF 0\r
+\r
+//prescale values\r
+#define WDTO_15MS 0\r
+#define WDTO_30MS 1\r
+#define WDTO_60MS 2\r
+#define WDTO_120MS 3\r
+#define WDTO_250MS 4\r
+#define WDTO_500MS 5\r
+#define WDTO_1S 6\r
+#define WDTO_2S 7\r
+\r
+//prescale values for avrs with WDP3\r
+#if defined(WDP3)\r
+#define WDTO_4S 0x20\r
+#define WDTO_8S 0x21\r
+#endif\r
+\r
+//watchdog reset\r
+#define WDR() __asm__ __volatile__("wdr")\r
+\r
+//avr reset using watchdog\r
+#define WD_AVR_RESET() do{ \\r
+ __asm__ __volatile__("cli"); \\r
+ WD_SET_UNSAFE(WD_RST); \\r
+ while(1); \\r
+ }while(0)\r
+\r
+/*set the watchdog-\r
+1. save SREG\r
+2. turn off irq's\r
+3. reset watchdog timer\r
+4. enable watchdog change\r
+5. write watchdog value\r
+6. restore SREG (restoring irq status)\r
+*/\r
+#define WD_SET(val,...) \\r
+ __asm__ __volatile__( \\r
+ "in __tmp_reg__,__SREG__" "\n\t" \\r
+ "cli" "\n\t" \\r
+ "wdr" "\n\t" \\r
+ "sts %[wdreg],%[wden]" "\n\t" \\r
+ "sts %[wdreg],%[wdval]" "\n\t" \\r
+ "out __SREG__,__tmp_reg__" "\n\t" \\r
+ : \\r
+ : [wdreg] "M" (&WDTCSR), \\r
+ [wden] "r" ((uint8_t)(0x18)), \\r
+ [wdval] "r" ((uint8_t)(val|(__VA_ARGS__+0))) \\r
+ : "r0" \\r
+)\r
+\r
+/*set the watchdog when I bit in SREG known to be clear-\r
+1. reset watchdog timer\r
+2. enable watchdog change\r
+5. write watchdog value\r
+*/\r
+#define WD_SET_UNSAFE(val,...) \\r
+ __asm__ __volatile__( \\r
+ "wdr" "\n\t" \\r
+ "sts %[wdreg],%[wden]" "\n\t" \\r
+ "sts %[wdreg],%[wdval]" "\n\t" \\r
+ : \\r
+ : [wdreg] "M" (&WDTCSR), \\r
+ [wden] "r" ((uint8_t)(0x18)), \\r
+ [wdval] "r" ((uint8_t)(val|(__VA_ARGS__+0))) \\r
+)\r
+\r
+\r
+//for compatibility with avr/wdt.h\r
+#define wdt_enable(val) WD_SET(WD_RST,val)\r
+#define wdt_disable() WD_SET(WD_OFF)\r
+\r
+\r
+#endif /* _AVR_WD_H_ */\r