Electronic – arduino – Using Prescaler above 64 on ATTiny45

arduinoattinytimer

I'm trying to setup Timer0 on an ATTiny45 using the arduino-tiny core. TIM0_COMPA_vect works fine for prescalers 1,8 and 64, but 256 and 1024 cause the ISR to not fire. I am running the chip at 1MHz.

Setup code is as follows:

void setup()
{
  ADCSRA &= ~(1<<ADEN); //Disable ADC
  ACSR = (1<<ACD); //Disable the analog comparator
  DIDR0 = 0x3F; //Disable digital input buffers on all ADC0-ADC5 pins.

  DDRB |= _BV(PINB0); // Set Pin 5 (PB0) as output;
  PORTB &= ~_BV(PINB0); //Set it to low, just to be safe

  //cli();
  TCCR0A |= _BV(WGM01); //CTC Mode
  TCCR0B |= (_BV(CS02) | _BV(CS00)); //Prescale 1024
  TIMSK  |= _BV(OCIE0A); //enable CTC interrupt
  OCR0A = 243; 

  sei();
}

fuses are:

low_fuses=0x62
high_fuses=0xD7
extended_fuses=0xFF

Any thoughts on why this might be the case?

Update: Not only do prescalers /256 and /1024 not work for COMPA or COMPB but they do not work for the overflow ISR either. I don't really get it since according to table 11-6 in the ATTinyx5 datasheet, it supports prescalers /1, /8, /64, /256, and /1024 via the TCCR0B register.

Best Answer

I suspect the Arduino startup code is setting the timer registers, especially TCCR0B to a value other than the startup default of zero. Try the following code that removes the OR:

TCCR0B = (_BV(CS02) | _BV(CS00)); //Prescale 1024

Looking at the datasheet / 256 and /1024 both have CS02 set to one. If CS01 is set to one by the Arduino code that will be enabling the external clock source when you're trying to set the higher divisor values.

The only other thing worth pointing out is that Arduino tends to use TIMER0 for functions like delay() and millis(). Once you've changed the timer setup those functions won't operate as per usual so you might need to write your own timing routines if required.