turning avrcalc timer calculations into code

Go To Last Post
14 posts / 0 new
Author
Message
#1
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

I want to obtain 1hz interrupt with 8bit timer on atmega88.

attached are the calculations made by k avrcalc by Mr M. Rosenberg Kevin

 

 

 

On arduino, (just for compilation test since 16mhz clock with give me 488.28125 times more than the intended speed) I get the error

 

 

wiring.c.o (symbol from plugin): In function `__vector_16':
(.text+0x0): multiple definition of `__vector_16'
sketch\sketch_jun24a.ino.cpp.o (symbol from plugin):(.text+0x0): first defined here
collect2.exe: error: ld returned 1 exit status
exit status 1
Error compiling for board Arduino Nano.

 

for the code

 

int ledState = LOW; 
int count=0;
void setup() {
  // put your setup code here, to run once:
    Serial.begin(9600);
  pinMode(LED_BUILTIN, OUTPUT);
  TCCR0A = 0x00;
  TCCR0B = B00000101;  

TIMSK0 = B00000010;  
OCR0 = 0xFF; 
  sei();
    Serial.write("0");
}

void loop() {
  // put your main code here, to run repeatedly:

}
 ISR (TIMER0_OVF_vect) // timer0 overflow interrupt
 {
  
  if ((count%60) == 0)
  {Serial.println(count);  
  }
  digitalWrite(LED_BUILTIN, ledState);
  ledState=!ledState;  
  count++;
  
  }

 

Last Edited: Fri. Jun 24, 2022 - 03:39 PM
  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0


That's gecause behind the scenes Arduino is already using TIMER0_OVF_vect for its own purposes and it already defines ISR(TIMER0_OVF_vect). It uses it for all the timing stuff like millis().

 

Suggest you pick a different timer.

 

By the way:

 

then looking at the code of wiring.c (which could be said to be the "core" file of Arduino) you find:

volatile unsigned long timer0_overflow_count = 0;
volatile unsigned long timer0_millis = 0;
static unsigned char timer0_fract = 0;

#if defined(TIM0_OVF_vect)
ISR(TIM0_OVF_vect)
#else
ISR(TIMER0_OVF_vect)
#endif
{
	// copy these to local variables so they can be stored in registers
	// (volatile variables must be read from memory on every access)
	unsigned long m = timer0_millis;
	unsigned char f = timer0_fract;

	m += MILLIS_INC;
	f += FRACT_INC;
	if (f >= FRACT_MAX) {
		f -= FRACT_MAX;
		m += 1;
	}

	timer0_fract = f;
	timer0_millis = m;
	timer0_overflow_count++;
}

unsigned long millis()
{
	unsigned long m;
	uint8_t oldSREG = SREG;

	// disable interrupts while we read timer0_millis or we might get an
	// inconsistent value (e.g. in the middle of a write to timer0_millis)
	cli();
	m = timer0_millis;
	SREG = oldSREG;

	return m;
}

which gives you a taste for how millis() is implemented using that interrupt. Above the code is:

// the prescaler is set so that timer0 ticks every 64 clock cycles, and the
// the overflow handler is called every 256 ticks.
#define MICROSECONDS_PER_TIMER0_OVERFLOW (clockCyclesToMicroseconds(64 * 256))

// the whole number of milliseconds per timer0 overflow
#define MILLIS_INC (MICROSECONDS_PER_TIMER0_OVERFLOW / 1000)

// the fractional number of milliseconds per timer0 overflow. we shift right
// by three to fit these numbers into a byte. (for the clock speeds we care
// about - 8 and 16 MHz - this doesn't lose precision.)
#define FRACT_INC ((MICROSECONDS_PER_TIMER0_OVERFLOW % 1000) >> 3)
#define FRACT_MAX (1000 >> 3)

So Arduino is already running the timer to interrupt every 64 clock cycles (actually that is a LOT of CPU over-head if it does it that frequently!!)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Oh. So it's an arduino problem?

So my code should run fine with microchip studio, if I'm not mistaken. Right?

(Need someone so check my mistake if any)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Try it out. Studio 7 is a free download and because it has a simulator you don't even need any physical hardware to try stuff like seeing how many CPU cycles between each time a timer interrupt is hit. 

 

Obviously when you leave the world of Arduino and hit the real world you aren't going to have luxuries like Serial.println or even simple stuff like pinMode and digitalWrite so you are going to have to find alternative ways to do those things.

 

In part it's what makes Arduino both nice (a load of complex stuff is already done for you) but a bit of a pain (you don't learn how to do low level stuff because it HAS already been done for you). A bit of a two edged sword. 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

So you are going to run your Mega88 at a crippled main clock speed of 32 kHz just to get the 8-bit timer to reach one second?

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

BTW, if you are indeed running at that speed, how are you going to get the serial stuff to work?

 

Or if this is just a paper exercise then why not skip the Arduino framework and writ a complete program?

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Oh. The serial was there just for a test. The application I intend it for, will never need serial. (wall clock)

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Raj69_71 wrote:
The application I intend it for, will never need serial. (wall clock)

What display have you chosen ?

Depending on the interface, updating that could become somewhat slow at 32KHz CPU clock.

 

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

It's a simple multiplexed led display, and that part of code works. Just need to get the timings right.

The problem is, I have no way of telling if the "RTC code" is working correctly or not. I don't have access/can't make a frequency counter yet.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Raj69_71 wrote:

It's a simple multiplexed led display...I have no way of telling if the "RTC code" is working correctly or not. I don't have access/can't make a frequency counter yet.

 

But you do have a frequency counter. Your eyes. Just blink an LED at 1Hz. Count the pulses in one minute. Right there you have a frequency counter accurate to a few percent.

#1 Hardware Problem? https://www.avrfreaks.net/forum/...

#2 Hardware Problem? Read AVR042.

#3 All grounds are not created equal

#4 Have you proved your chip is running at xxMHz?

#5 "If you think you need floating point to solve the problem then you don't understand the problem. If you really do need floating point then you have a problem you do not understand."

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Raj69_71 wrote:
Oh. The serial was there just for a test. The application I intend it for, will never need serial. (wall clock)
theusch wrote:
So you are going to run your Mega88 at a crippled main clock speed of 32 kHz just to get the 8-bit timer to reach one second?

If you are really making a clock, and are really going to use a "watch crystal", most of us would connect it to timer2 of that AVR model and use that for timekeeping -- but not as the main AVR clock.  If this is an LED clock then obviously low power draw is not a consideration.

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Indeed, but then I'll be adding a lot of delays to slow the main code down anyway.

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

Raj69_71 wrote:

Indeed, but then I'll be adding a lot of delays to slow the main code down anyway.


 

nope, use INTERRUPTS.  
 

as Lee notes, if you must use a watch crystal, connect that to a timer and run the core at something much faster for updating your display, etc..

 

jim

I would rather attempt something great and fail, than attempt nothing and succeed - Fortune Cookie

 

"The critical shortage here is not stuff, but time." - Johan Ekdahl

 

"Step N is required before you can do step N+1!" - ka7ehk

 

"If you want a career with a known path - become an undertaker. Dead people don't sue!" - Kartman

"Why is there a "Highway to Hell" and only a "Stairway to Heaven"? A prediction of the expected traffic load?"  - Lee "theusch"

 

Speak sweetly. It makes your words easier to digest when at a later date you have to eat them ;-)  - Source Unknown

Please Read: Code-of-Conduct

Atmel Studio6.2/AS7, DipTrace, Quartus, MPLAB, RSLogix user

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0

jgmdesign wrote:
nope, use INTERRUPTS.  

And/Or go to sleep.

 

As

theusch wrote:
If this is an LED clock then obviously low power draw is not a consideration.
, what difference does it make how many main-loops-per-second? 

You can put lipstick on a pig, but it is still a pig.

I've never met a pig I didn't like, as long as you have some salt and pepper.