AT90CAN128 adc and timer0 interrupts problem

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

Hi. This is just a part of my program. I want to read values from three adc inputs and then, after a certain delay, read them again. I'm using timer0 to count in the background for a specified amount of time. And so, after I read all 3 values, I set a delay in an appropriate variable. The interrupt handling routine from timer0's compare match, counts the time and after the delay variable equals 1 it starts the ADC once again. The thing is, that when the program is started, the adc values are quite credible. But after my program gets to the second round of adc conversion, all the values are equal. My adc inputs are connected to IR distance sensor. Here's the code:

#include   
#include   
#include   

#define ev_int4 0 
#define ev_int5 1
#define ev_int6 2
#define ev_int7 3
#define ev_adc 4 
#define ev_start 6

unsigned int timetable[7]; 
unsigned char sensors[3]; 
unsigned char sensor_nr;

ISR (SIG_OUTPUT_COMPARE0) {

	unsigned char i;

	for (i = 0;i<7;i++) {
		if (timetable[i] > 0) {
			if (timetable[i] == 1) {

				switch (i) {
					case ev_int4: break;
					case ev_int5: break;
					case ev_int6: break;
					case ev_int7: break;
					case ev_adc: {
						ADMUX = 0x40;
						ADCSRA = 0xcf;
						break;
						};

					case ev_start: break;
					};
		
				};

			timetable [i]--;
			};

		};	

	};

ISR (SIG_ADC) {

	sensors [sensor_nr] = ADCL;

          if (sensor_nr == 2) {

		sensor_nr = 0;
		ADMUX = 0x40 + sensor_nr; 
		ADCSRA = 0xbf;
		timetable[ev_adc] = 100;
		}
	
	else {
		sensor_nr++;
		ADMUX = 0x40 + sensor_nr;
		ADCSRA = 0xcf;	
		};

	};

int main (void) {
	
	//init ADC
	ADMUX = 0x40;
	ADCSRA = 0x0f;
	ADCSRB = 0;
	DDRE = 0;
	PINE = 0x8;
	DIDR0 = 0xf0;	

	//init timer0
	TCCR0A = 0x45;
	OCR0A = 0xff;
	TIMSK0 = 2; 

	sei();

	ADCSRA = 0xcf;
	while (1) {

	};


	};

What am I doing wrong. Thanks in advance for any help

P.S. I just wanted to add that I'm using JTAG for programming and debugging. However I'm not using ADC ports colliding with JTAG, so there shouldn't be any problems with that. Can this be the reason of my problems?

  • 1
  • 2
  • 3
  • 4
  • 5
Total votes: 0
   sensors [sensor_nr] = ADCL; 

If the CAN128 ADC works the way the other AVR ADCs work, you Must
read ADCH after reading ADCL or you leave the register pair (ADCH/L)
locked, so the ADC unit can't update it.

It's a bit odd that you're only interested in the low 8 bits, since that ignores
75% of your range, but that's your call. At the least you need to read ADCH
and throw it away.

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

That was just where the problem was. Thanks very much for your help - my robot started seeing :) Maybe your're right about the 10bit resolution too - I'll have to check on that.