volatile uint16_t count=0; //Main revolution counter
#define F_CPU 16000000UL // 16 MHz
#include <avr/io.h>
#include <avr/interrupt.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <util/delay.h>
#include "lcd.h"
volatile uint16_t rpm=0; //Revolution per minute
volatile uint16_t rps=0; //Revolution per second
volatile uint8_t minute;
volatile uint16_t current_rps;
void main()
{
char rpm_lcd[50],rps_lcd[50];
DDRE &= ~(1 << PIN4);
PORTE |= (1 << PIN4);
DDR_D.b0 = 1;
DDR_D.b1 = 1;
DDR_D.b2 = 1;
DDR_D.b3 = 1;
DDR_D.b4 = 1;
DDR_D.b5 = 0; //button input
DDRA = 0xFF;
lcd_init();
lcd_cmd(0x01);
lcd_string("Heartbeat Meter");
lcd_cmd(0xC0);
lcd_string("by Bianchi");
_delay_ms(1500);
EICRB = _BV(ISC41); //Falling edge on INT4 triggers interrupt.
EIMSK = _BV(INT4);
TCCR1B|=((1<<WGM12)|(1<<CS12)|(1<<CS10));
OCR1A=15624; //1 second
TIMSK|=(1<<OCIE1A); //Output compare 1A interrupt enable
sei();
DDRD|=(1<<PD7);
lcd_cmd(0x01);
while(1)
{
cli();
current_rps = rps;
sei();
if (minute==1)
{
lcd_cmd(0x01);
sprintf(rps_lcd,"u",current_rps);
sprintf(rpm_lcd,".2f", current_rps * 60.0);
lcd_xy(0,0);
lcd_string("RPS = ");
lcd_string(rps_lcd);
lcd_xy(1,0);
lcd_string("RPM = ");
lcd_string(rpm_lcd);
if(PINE & (1<<PE4))
{
PORTD|=(1<<PD7);
}
else
{
PORTD&=(~(1<<PD7));
}
_delay_ms(2000);
minute = 0;
}//end of minute counter
}//end while
}//end main
ISR(INT4_vect)
{
count++;
}
ISR(TIMER1_COMPA_vect)
{
//CPU Jumps here every 1 sec exactly!
static uint8_t seconds;
seconds += 1;
if (seconds == 60)
{
minute = 1;
seconds = 0;
}
rps=count;
rpm=rps*60;
count=0;
}