I'm trying to control an Arduino Barebone from an arduino with relays. Basically when the attiny starts it should switch on the arduino for 4 seconds. The Arduino sends a signal back to a digital pin of the attiny and as long as it is set to high the attiny should leave it working. If it is low the attiny should switch the relay of.
the problem is some changes to the code make the interrupt reset the attiny (which would switch of the arduino) othertimes- in this case. the interrupt doesn't work at all.
#include <avr/sleep.h>
#include <avr/wdt.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#ifndef cbi
#define cbi(sfr, bit) (_SFR_BYTE(sfr) &= ~_BV(bit))
#endif
#ifndef sbi
#define sbi(sfr, bit) (_SFR_BYTE(sfr) |= _BV(bit))
#endif
int pinBoard = 0;
bool boardOn = false;
bool startBoard_flag = false;
int pinBoardReturn = 3;
volatile boolean f_wdt = 1;
void setup() {
cli();//disable interrupts during setup
pinMode(pinBoard, OUTPUT);
pinMode(pinBoardReturn, INPUT);
setup_watchdog(9);
cbi(ADCSRA, ADEN); // switch Analog to Digitalconverter OFF
// cli();//disable interrupts during setup
for (int i = 0; i < 10; i++) {
digitalWrite(pinBoard, HIGH);
delay(100);
digitalWrite(pinBoard, LOW);
delay(100);
}
PCMSK |= (1 << PCINT1); //sbi(PCMSK,INTERRUPTPIN) also works but I think this is more clear // tell pin change mask to listen to pin2 /pb3 //SBI
GIMSK |= (1 << PCIE); // enable PCINT interrupt in the general interrupt mask //SBI
startBoard();
DDRB &= ~(1 << DDB1); //cbi(DDRB, DATADIRECTIONPIN);// set up as input - pin2 clear bit - set to zero
PORTB |= (1 << PB1); //cbi(PORTB, PORTPIN);// disable pull-up. hook up pulldown resistor. - set to zero
}
void startBoard() {
digitalWrite(pinBoard, HIGH);
boardOn = true;
startBoard_flag = false;
cli(); // Disable interrupts
delay(4000);
}
void shutdownBoard() {
digitalWrite(pinBoard, LOW);
boardOn = false;
}
void loop() {
if (f_wdt == 1) { // wait for timed out watchdog / flag is set when a watchdog timeout occurs
f_wdt = 0; // reset flag
if (startBoard_flag) {
startBoard();
}
bool boardReturn = digitalRead(pinBoardReturn);
if (boardOn && !boardReturn) {
shutdownBoard();
}
system_sleep();
}
}
//****************************************************************
// set system into the sleep state
// system wakes up when wtchdog is timed out
void system_sleep() {
// GIMSK |= _BV(PCIE); // Enable Pin Change Interrupts
// PCMSK |= _BV(PCINT3); // Use PB3 as interrupt pin
set_sleep_mode(SLEEP_MODE_PWR_DOWN); // replaces above statement
sleep_enable(); // Sets the Sleep Enable bit in the MCUCR Register (SE BIT)
sleep_cpu(); // sleep
// PCMSK &= ~_BV(PCINT3); // Turn off PB3 as interrupt pin
sleep_disable(); // Clear SE bit
// sei(); // Enable interrupts
}
//****************************************************************
// 0=16ms, 1=32ms,2=64ms,3=128ms,4=250ms,5=500ms
// 6=1 sec,7=2 sec, 8=4 sec, 9= 8sec
void setup_watchdog(int ii) {
byte bb;
int ww;
if (ii > 9 ) ii = 9;
bb = ii & 7;
if (ii > 7) bb |= (1 << 5);
bb |= (1 << WDCE);
ww = bb;
MCUSR &= ~(1 << WDRF);
// start timed sequence
WDTCR |= (1 << WDCE) | (1 << WDE);
// set new watchdog timeout value
WDTCR = bb;
WDTCR |= _BV(WDIE);
}
//****************************************************************
// Watchdog Interrupt Service / is executed when watchdog timed out
ISR(WDT_vect) {
f_wdt = 1; // set global flag
}
ISR(PCINT_VECTOR) {
for (int i = 0; i < 4; i++) {
digitalWrite(pinBoard, HIGH);
delay(1000);
digitalWrite(pinBoard, LOW);
delay(1000);
}
startBoard_flag = true;
f_wdt = 1; // set global flag
}