Using Two Timers at Once?

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

I'm working with a Teensy2++, which has an AT90USB1287 onboard. Looking at the datasheet, I've got 4 Timers, but it looks like they all use the same prescaler. I assume I can use all 4 timers independently of each other, at the same time, but are there any caveats to watch out for while doing this? I've glanced through Dean's Timer Tutorial, but it doesn't talk about using more than one timer at the same time, and I haven't been able to find much else on the topic.

Thanks!

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

Quote:

Looking at the datasheet, I've got 4 Timers, but it looks like they all use the same prescaler.

The datasheet of the Teensy2++, or the datasheet of the AVR?

Have you looked at this?

Quote:
12. Timer/Counter0, Timer/Counter1, and Timer/Counter3 Prescalers

Timer/Counter0, 1, and 3 share the same prescaler module, but the Timer/Counters can have
different prescaler settings. The description below applies to all Timer/Counters. Tn is used as a
general name, n = 0, 1 or 3.

Except for rare instances such as Output Compare Modulator (OCM) you can consider AVR8 timers as being independent of each other.

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

Yeah, I noticed that in the datasheet, but I seem to be running into an issue that when I enable the second timer, the first one gets screwed up.

I'm using TIMER1 (16 Bits) to generate a 1Hz interrupt:

/** Timer 1 - 1 Second Interrupt Generator **/
	// Set CTC Mode
	TCCR1B |= (1 << WGM12);
	// Set Output Compare Channel A for 1 Hz @ 16 MHz / 256
	OCR1A = 62499;
	//
	TIMSK1 |= (1 << OCIE1A);

I start/stop that with an interrupt:

ISR(INT7_vect)
{
	/* Stopwatch Start/Stop Switch */
	TCCR1B ^= (1<<CS12);
}

I'm doing some internal timekeeping and turning that 1Hz pulse into a MM:SS display on a 4 digit 7 segment display. This works great.

Now I'm trying to add in an IR remote control using the NEC encoding technique, which is basically varying pulse lengths to indicate 0/1. Logical solution, set up a second timer to count pulses, along with a Overflow interrupt to monitor a timeout scenario.

	/*	Set up interrupt pin for the IR Decoder	*/
	DDRD &= (0<<3);
	PORTD &= (1<<3);

	EICRA = (1<<ISC31 | 0<<ISC30);
	EIMSK |= (1<<INT3);
	
	/* Set up Timer 0 to count pulse length */
	TCCR0A = (0<<COM0A1 | 0<<COM0A0 | 0<<COM0B1 | 0<<COM0B0 | 0<<WGM01 | 0<<WGM00);
	TCCR0B = (0<<FOC0A | 0<<FOC0B | 0<<WGM02 | 0<<CS02 | 0<< CS01 | 0<<CS00);
	TCNT0 = 0x00;
	TIMSK0 |= 1<<TOIE0;

Start/stopping the timer isn't written yet, but would be handled by an interrupt (INT3) where the IR Receiver is plugged into. However, just setting TIMER0 up, or more, the Overflow interrupt, seems to break TIMER1, and I'm not sure why. It's like TIMER1 can never start counting if the TIMER0 Overflow interrupt is enabled.

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

Do you have an ISR to "catch" the event?

-- Show a complete test program that demonstrates the symptoms
-- Tell how you are testing, what results you expect, and what results you get
-- Try to capture the reset cause and see what it says

Quote:

I start/stop that with an interrupt:
Code:
ISR(INT7_vect)
{
/* Stopwatch Start/Stop Switch */
TCCR1B ^= (1<<CS12);
}

-- Buttons bounce. You are likely to get more than one "hit". And if closer together than can be serviced it could be an unexpected odd/even number.

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

iwoloschin wrote:

	DDRD &= (0<<3);
	PORTD &= (1<<3);


Those two lines don't make much sense.

Sid

Life... is a state of mind

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

ChaunceyGardiner wrote:
iwoloschin wrote:

	DDRD &= (0<<3);
	PORTD &= (1<<3);


Those two lines don't make much sense.

That was an error, it's supposed to be input w/ pullup enabled.

Regarding bounce, I know there's bouncing going on, but for what I'm doing, it's fine for now. Eventually the start/stop will be controlled by the remote, which shouldn't exhibit bouncing, but I wanted to make sure the stopwatch worked before I tackled the remote :).

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

Quote:

That was an error, it's supposed to be input w/ pullup enabled.

But that would be:

DDRD &= ~(1 < 3);
PORTD |= (1 << 3);

You missed ~ in the first and used 0 not 1.
You used the wrong operator all together in the second. It should be OR not AND.

If you don't understand why it must be like this go to the Tutorial Forum and read "Bit Manpulation - Programming 101"

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

clawson wrote:
But that would be:

DDRD &= ~(1 < 3);
PORTD |= (1 << 3);


He'd have more luck with
DDRD &= ~(1 << 3);
PORTD |= (1 << 3);

Sid

Life... is a state of mind

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

Yup I must learn to type :oops:

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

clawson wrote:
Yup I must learn to type :oops:

It's cool, I'm having the same problems :). At least your's is just on the forums, and not in code...