Is this timer set correctly for Arduino Mega? It should count exactly one second. And why when I print in serial monitor (seconds_passed++) is it incremented by 2 not by 1?

Full code on Pastebin: LINK

//set and initialize the TIMER1

TCCR1A = 0; // set entire TCCR1A register to 0
TCCR1B = 0; // set entire TCCR1B register to 0
TCCR1B |= (1 << CS12);
TIMSK1 |= (1 << TOIE1);
TCNT1 = 3036;

attachInterrupt(digitalPinToInterrupt(ignition_pin), ignitionSignal, CHANGE);

ISR(TIMER1_OVF_vect) {
  //TIMER1 overflow interrupt -- occurs every 1sec --
  LPG_injector_open_duration = 0;
  unleadinj_Open_Duration = 0;
  vss_pulses = 0;
  TCNT1 = 3036;
  • I am not an expert on this, but Mega runs at 16 MHz. your prescaler is 256 so TCMT1 should be 16000000/256 for 1 second? – Juraj Aug 7 '19 at 14:24
  • You asked a new question about the same topic, instead of improving your previous question. At least delete your previous question now – chrisl Aug 7 '19 at 18:28

Your timer configuration is ok so far. Never the less I recommend using the TIMER1_COMPA_vect interrupt vector instead of TIMER1_OVF_vect which has the advantage of better readability (in my oppinion) and TCNT1 doesn't have to be reset in the ISR (instead, OCR1A is just initialized with 62500 once in setup()). Therefore, TIMER0 has to run in CTC (clear timer on compare match) mode and WGM12 has to be set in TCCR1B.

The reason why seconds_passed is incremented twice is because you Serial.print(seconds_passed++) in instantSpeed(). Printing on the serial interface is damn slow and using it in an ISR is a no-go!

| improve this answer | |
  • Thanks, do you mean something like this: TCCR1A = 0; // undo the Arduino's timer configuration TCCR1B = 0; // ditto TCNT1 = 0; // reset timer OCR1A = 62500 - 1; // period = 62500 clock tics TCCR1B = _BV(WGM12) // CTC mode, TOP = OCR1A | _BV(CS12); // clock at F_CPU/256 TIMSK1 = _BV(OCIE1A); // interrupt on output compare A – Adam Aug 7 '19 at 16:09
  • I can't guarantee because I don't have an atmega2560 available right now, so there might be little things to fix. What is TOP=OCR1A supposed to do? I don't think that's neccessary. Also I think, OCR1A=62500 is theoretically correct (there is no "tick" at 0), but probably you won't recognize any difference... – Sim Son Aug 7 '19 at 16:27
  • It is only comment. – Adam Aug 7 '19 at 16:30
  • Allright! I suggest you try this standalone by blinking an led, just to see. If it doesn't work, feel free to ask! – Sim Son Aug 7 '19 at 16:32
  • @Adam: Avoid writing code in comments: it's not very readable. Post a link instead. @SimSon: 1. Adam copy-pasted from this answer. 2. The timer counts from 0 to OCR1A inclusive. If you want a period of 62500, then OCR1A should be set to 62500−1=62499. – Edgar Bonet Aug 7 '19 at 17:56

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.