#include <stdbool.h>
#include <avr/io.h>
#include <avr/interrupt.h>
#include "mydefs.h"

inline void init(void);
inline void check_pulse(void);
inline void process_output(void);

volatile uint8_t counts;
uint8_t wdog_cntdown = 255;

int main(void) {
  init();
  while( 1 ) {
    check_pulse();
    process_output();
  }
  return 0;
}

inline void init(void) {
  CCP    = CCP_SIG;
  CLKPSR = 0;
  OSCCAL = CAL_12_MHZ;
#ifdef INVERTED_OUT
  PORTB  = OUT;
#endif
  PUEB   = IN;
  DDRB   = OUT | CLK;
  TCCR0B = (1 << WGM02) | (1 << CS00);
  OCR0A  = F_CPU / DEBOUNCE - 0.5;
  TIMSK0 = (1 << OCIE0A);
}

inline void check_pulse(void) {
  cli();
  uint8_t tmp = counts;
  if( tmp )
    counts = 0;
  sei();
  if( tmp ) {
    if( (tmp > 1) && (tmp < 64) ) {
      if( wdog_cntdown )
        wdog_cntdown--;
    } else {
      wdog_cntdown = 255;
    }
  }
}

inline void process_output(void) {
  if( wdog_cntdown )
    Poff();
  else
    Pon();
}

ISR (TIM0_COMPA_vect) {
  static uint8_t counter;
  static bool oldLevel;
  bool newLevel;

  PINB |= CLK;
  newLevel = (bool) ( PINB & IN );
  if( oldLevel == newLevel ) {
    if( counter < 64 )
      counter++;
    else
      counts = counter;
  } else {
    oldLevel = newLevel;
    counts   = counter;
    counter  = 0;
  }
}