Sari la conținut
ELFORUM - Forumul electronistilor

Probleme ADC ATMEGA8


Vizitator polbacisergiu

Postări Recomandate

Vizitator polbacisergiu

Buna am si eu nevoie de putin ajutor... :(

 

Am un Atmega 8 cu un lcd si doresc sa folosesc adc pt a citi o tensiune. 

Am creat codul si am simulat in proteus pana aici totul merge perfect(am atasat schema din proteus). Dar cand am construit schema pe placuta de test nu mai funcioneza cum trebuie. 

 

Mod de testare:

1. Am alimetat AVCC cu 5V . Am conecat vref la masa,nu conteza ce tensiune aplic pe pinul adc el are o valoare de  1023. 

2. Am alimetat AVCC cu 5V . Si am lesat in gol vref. Are un comportament diferti. Dca aplic o tesniune de 0 voliti valoarea din adc este 0 insa daca apic 1.57v loare este de 1023.

 

A mai avut cineva parte de un asemenea comportament? Ma poate ajuta cu o schema sau ceva sfaturi pt ca nu imi mai dau seama ce as putea face. 

 

Va multumesc!

 

 

Link spre comentariu
  • Răspunsuri 10
  • Creat
  • Ultimul Răspuns

Top autori în acest subiect

  • Liviu M

    2

  • nico_2010

    2

  • Elison

    1

  • costi002

    1

Top autori în acest subiect

Imagini postate

Ai citit capitolul Analog-to-Digital Converter din manualul ATMEGA8? Stii ce inseamna Vref, stii ca Vref poate fi atat intern cat si extern?Noi nu stim ce ai programat.Daca vrei sa-ti fim de ajutor, trebuie sa ne oferi cat mai multe informatii.

Link spre comentariu

@polbacisergiu: Desi ai vrut sa postezi schema nu ti-a reusit. Mai incearca.

Pe de alta parte, posteaza softul folosit. Si nu in ultimul rand - si asta este valabil si pentru userul costi002 - Vref se conecteaza printr-un condensator de 100 - 330n la masa si se foloseste setarea:

ADMUX |=(1<<REFS0);

pentru a folosi tensiunea de referinta AVCC, cu toate masurile ce se iau (vezi pagina 245 din DS).

Sau se foloseste o referinta de tensiune externa.

Link spre comentariu
Vizitator polbacisergiu

Nico_2010 iti multumesc mult de informati. Uite am facut modificarile de care ziceai am pus si un condesator intre masa si vref si tot nu merge . Am atasat la cest mesaj  codul poate reuesti sa ma ajuti. Iti multumesc anticipat. 

 

Nu stiu daca conteza sau nu dar vreau sa mentionez ca nu am oscilator extern.

#include <avr/io.h>#include "lcd.c"#include <util/delay.h>#include <math.h>#include <stdlib.h>//ADC  values and functions initializationint adc_read(int ch);int adc;char buf[10];float vm=0;//voltmeter Functions// initialize adcvoid adc_init(){						ADMUX |= (1<<REFS0);      //Set reference Voltage at 0V	// ADC Enable and prescaler of 128	// 8000000/128 = 62500	ADCSRA = (1<<ADEN)|(1<<ADPS2)|(1<<ADPS1)|(1<<ADPS0);}// read adc valueint adc_read(int ch){	// select the corresponding channel 0~7	// ANDing with '7' will always keep the value	// of 'ch' between 0 and 7	ch &= 0b00000111;  // AND operation with 7	ADMUX = (ADMUX & 0xF8)|ch;     // clears the bottom 3 bits before ORing		// start single conversion	// write '1' to ADSC	ADCSRA |= (1<<ADSC);		// wait for conversion to complete	// ADSC becomes '0' again	// till then, run loop continuously	while(ADCSRA & (1<<ADSC));		return (ADCW);}int main(void){		// Declare your local variables here	int adc_int[41];	int i=0,max=0;   DDRC = 0x00;      // initialize Lcd  lcd_init();  // initialize adc  adc_init();       /* Replace with your application code */    while (1)     {				for(i=0; i<=39; i++){			adc_int[i] = adc_read(0);      // read adc value at PORTC.0		}		max=adc_int[0];		for(i=0; i<=40; i++){						if(max<adc_int[i])			max=adc_int[i];		}				adc=max;		itoa(max,buf,10);				//vm = (float)(adc* 0.2744140625); // 280/1024		//adc = (int)vm;				itoa(adc,buf,10);				 lcd_setcursor(0,0);		 lcd_string(buf);		 lcd_string("Volti");		 _delay_ms(700);         lcd_clear();		    }}
Link spre comentariu
Vizitator polbacisergiu

 

Linia urmatoare cred ca e gresita. Cred ca trebuie && in loc de &

while(ADCSRA & (1<<ADSC));

 

 

Am incerca cu modificarea facuta de tine dar asa nu mai functioneza nici pe simulator.   MS oricum. 

Link spre comentariu

pune schema, poate ai gresit ceva la pini de exemplu.

e corect

while(ADCSRA & (1<<ADSC));

asigura-te ca esti in timp real cu delay-urile alea inainte de tot. proteus nu prea simuleaza in timp real.

 

cu

ADMUX |= (1<<REFS0);

AREF e [N/C] teoretic,  nu il conectezi, dar e mai eleganta solutia propusa de nico

 

 

nu stiu daca e corect aici

ADMUX = (ADMUX & 0xF8)|ch;
Editat de Vizitator
Link spre comentariu

Schimba subrutina de citire a ADC cu asta:

uint16_t ReadADC(uint8_t ADCchannel){ADMUX = (ADMUX & 0xF0) | (ADCchannel & 0x0F);	//single conversion mode	ADCSRA |= (1<<ADSC);	// wait until ADC conversion is complete	while( ADCSRA & (1<<ADSC) );        return ADC;}		

Si verifica buna functionare. Ca idee, valoarea ADC nu reprezinta direct valoarea tensiunii masurate.

Poate totusi postezi si schema.

Link spre comentariu

Creează un cont sau autentifică-te pentru a adăuga comentariu

Trebuie să fi un membru pentru a putea lăsa un comentariu.

Creează un cont

Înregistrează-te pentru un nou cont în comunitatea nostră. Este simplu!

Înregistrează un nou cont

Autentificare

Ai deja un cont? Autentifică-te aici.

Autentifică-te acum



×
×
  • Creează nouă...

Informații Importante

Am plasat cookie-uri pe dispozitivul tău pentru a îmbunătății navigarea pe acest site. Poți modifica setările cookie, altfel considerăm că ești de acord să continui.Termeni de Utilizare si Ghidări