Hi!
I had a problem with using a sketch Gammon Forum : Electronics : Microprocessors : Timers and counters "Another frequency counter
// Frequency timer
// Author: Nick Gammon
// Date: 10th February 2012"
to measure the time of the pulse. I assembled the oscillator with a quadrature signal output at 328p. See below:
int tim=18;
void setup()
{
pinMode(5, OUTPUT); // A
pinMode(6, OUTPUT); // B
tim = 18;
noInterrupts (); // protected code
}
void loop()
{
digitalWrite(6, HIGH);
delayMicroseconds (tim) ;
digitalWrite(5, HIGH);
delayMicroseconds (tim) ;
digitalWrite(6, LOW);
delayMicroseconds (tim) ;
digitalWrite(5, LOW);
delayMicroseconds (tim) ;
}
The problem lies in the fact that if you reduce the delay from 500 to 100-50 ms, then on the serial console, sometimes elapsedTime have about 4500000000 jumps, approximately equal to the maximum value for unsigned long .
// Frequency timer
// Author: Nick Gammon
// Date: 10th February 2012
// Input: Pin D2
volatile boolean first;
volatile boolean triggered;
volatile unsigned long overflowCount;
volatile unsigned long startTime;
volatile unsigned long finishTime;
// here on rising edge
void isr ()
{
unsigned int counter = TCNT1; // quickly save it
// wait until we noticed last one
if (triggered)
return;
if (first)
{
startTime = (overflowCount << 16) + counter;
first = false;
return;
}
finishTime = (overflowCount << 16) + counter;
triggered = true;
detachInterrupt(0);
} // end of isr
// timer overflows (every 65536 counts)
ISR (TIMER1_OVF_vect)
{
overflowCount++;
} // end of TIMER1_OVF_vect
void prepareForInterrupts ()
{
// get ready for next time
EIFR = bit (INTF0); // clear flag for interrupt 0
first = true;
triggered = false; // re-arm for next time
attachInterrupt(0, isr, RISING);
} // end of prepareForInterrupts
void setup ()
{
pinMode( 13, OUTPUT); //test
// Serial.begin(57600);
// Serial.println("Frequency Counter");
// reset Timer 1
TCCR1A = 0;
TCCR1B = 0;
// Timer 1 - interrupt on overflow
TIMSK1 = bit (TOIE1); // enable Timer1 Interrupt
// zero it
TCNT1 = 0;
overflowCount = 0;
// start Timer 1
TCCR1B = bit (CS10); // no prescaling
// set up for interrupts
prepareForInterrupts ();
} // end of setup
void loop ()
{
if (!triggered)
return;
unsigned long elapsedTime = finishTime - startTime;
if ((elapsedTime<=1400)||(elapsedTime>=1600))
{digitalWrite(13, HIGH);}
//Serial.print (elapsedTime);
// so we can read it
delay (50);
digitalWrite(13, LOW);
prepareForInterrupts ();
} // end of loop
I assumed that this is somehow related to the transfer of data on the serial port. Therefore, I disabled this transmission and inserted a test of the time value with LED (the generator produces signal approximately = 1500). The result remains the same - LED sometimes flashes. What is the reason for this? Can the generator lose impulses?Maybe this is due to some requests from Bootloader? Or problems in the measurement program?
Thank you!