Aktyw Forum

Zarejestruj się na forum.ep.com.pl i zgłoś swój akces do Aktywu Forum. Jeśli jesteś już zarejestrowany wystarczy, że się zalogujesz.

Sprawdź punkty Zarejestruj się

Interpretacja wartości z A/C w Atmega8

Sławek5
-
-
Posty: 485
Rejestracja: 15 sie 2003, o 16:40
Lokalizacja: Szczecin
Kontaktowanie:

Interpretacja wartości z A/C w Atmega8

Postautor: Sławek5 » 17 wrz 2006, o 08:52

Cześć.
Potrzebuje pomocy. Mam takie dwa fragmenty kodu do obsługi przetwornika A/C w Atmega8. Przetwornik jest ustawiony na lewostronne wyrównanie wyniku. Jest ustawiony bit ADLAR=1.
Pierwsza część ta odczytuje wartość A/C

Kod: Zaznacz cały

int16_t adc_smp; adc_smp = ((int16_t) ADC) - 0x8000;

Nstępna część ma służyć jako wskaźnik przekroczenia zakresu:

Kod: Zaznacz cały

/* overdrive indicator */ if((((adc_smp & 0xff00) >> 8) < -120) || (((adc_smp & 0xff00) >> 8) > 120)) { PORTC |= _BV(PC3); } else { PORTC &= ~_BV(PC3); } PORTC &= (~_BV(PC2)) & 0xff;
Ta część z odjęciem to podobno odjęcie składowej stałej z wejscia A/C.

Teraz mam probem.
Jeżeli jest left adjustment czyli ADLAR=1 to po odczycie z pierwszego fragmentu co jest odczytywane, Ponieważ A/c jest 10 bitowy to to oznacza że wszystkie bity są odczytane czy tylko 8 najstarszych a dwa pozostałe są pmninęte.

Jak to w ogóle działa i co dokładnie robi odjęcie 0x8000.

A teraz wskaźnik przekroczenia zakresu, Przy jakiej max warości podanej na wejście on zadziała. Niby sygnał H oznacza przekroczenie zakresu.

napięcie referencyjne dla przetwornika to 2.5 V
Program jest kompilowany przez AVR-Gcc (WinAVR)

a_antoniak
-
-
Posty: 645
Rejestracja: 13 sty 2005, o 18:38
Lokalizacja: Krasnystaw
Kontaktowanie:

Re: Interpretacja wartości z A/C w Atmega8

Postautor: a_antoniak » 17 wrz 2006, o 09:55

Cześć.
Potrzebuje pomocy. Mam takie dwa fragmenty kodu do obsługi przetwornika A/C w Atmega8. Przetwornik jest ustawiony na lewostronne wyrównanie wyniku. Jest ustawiony bit ADLAR=1.
Pierwsza część ta odczytuje wartość A/C

Kod: Zaznacz cały

int16_t adc_smp; adc_smp = ((int16_t) ADC) - 0x8000;
IMHO lepiej napisac tak:

Kod: Zaznacz cały

adc_smp = ((int16_t) ADC) >> 6 - 0x200;
i operowac na normalniejszych wartosciach. Po co uzywasz ADLAR=1?
Nstępna część ma służyć jako wskaźnik przekroczenia zakresu:

Kod: Zaznacz cały

/* overdrive indicator */ if((((adc_smp & 0xff00) >> 8) < -120) || (((adc_smp & 0xff00) >> 8) > 120)) { PORTC |= _BV(PC3); } else { PORTC &= ~_BV(PC3); } PORTC &= (~_BV(PC2)) & 0xff;
Ta część z odjęciem to podobno odjęcie składowej stałej z wejscia A/C.
tak
Teraz mam probem.
Jeżeli jest left adjustment czyli ADLAR=1 to po odczycie z pierwszego fragmentu co jest odczytywane, Ponieważ A/c jest 10 bitowy to to oznacza że wszystkie bity są odczytane czy tylko 8 najstarszych a dwa pozostałe są pmninęte.
Odczytane zostaja wszystkie bity, z tym, ze przez ADLAR=1 sa "niemilo" (z punktu widzenia chyba wiekszoaci zastosowan) polozone w rejestrach ADCH i ADCL. Zobacz datasheet ATMega8, strona 205.
A teraz wskaźnik przekroczenia zakresu, Przy jakiej max warości podanej na wejście on zadziała. Niby sygnał H oznacza przekroczenie zakresu.

napięcie referencyjne dla przetwornika to 2.5 V
Wyglada na to, ze napiecia graniczne dla wskaznika wynosza:

-2,5V*121*4/1024 = ok. -1.18V

2,5V*121*4/1024 = ok. 1.18V

czyli wysteruje on PC3 dla napiec spoza zakresu -1.18V ... 1.18V.

Sławek5
-
-
Posty: 485
Rejestracja: 15 sie 2003, o 16:40
Lokalizacja: Szczecin
Kontaktowanie:

Postautor: Sławek5 » 17 wrz 2006, o 10:27

CZeść.
Podaję poniżej fragment wypowiedzi na PW:
Jeżeli jest tak jak u mnie (Ustawiony bit ADLAR), a zmienna przechowująca wynik konwersji jest typu signed (domyślny typ w C, dlatego nie ma go w deklaracjach, u mnie zresztą jest deklarowane chyba jako int16_t, czyli 16 bitów ze znakiem), to wynik możesz przesuwać w prawo za pomocą operatora >> i nic nie trzeba wtedy dodawać / odejmować, bo składowa stała zostaje już usunięta przez odjęcie 0x8000.

Jeżeli nie miałbyś ustawionego bitu ADLAR, to zamiast 0x8000 musisz odjąć (już nie można dodać, jak w wypadku 0x8000) 0x0200 (1024/2).

Jeżeli wynik konwersji przechowujesz jako unsigned to nie możesz odejmować, bo wyjdą głupoty, więc musi być signed

Ale polacem wykonywanie konwersji z wynikiem przesuniętym w lewo, zwiększa to dokładność obliczeń, a jest to szczególnie ważne przy FFT.

Czyli poprzez instrukcję adc_smp=ADC; następuje odczyc ADH i ADL do jedne zmiennej 16 bitowej, tak.A jaką wartośc mają te nie używane w ADL, chyba 0.

POdejrzewam ,że maksymalnie w zmiennej adc_spm po powyższe instr. w zapisie bin to
1111111111000000 i to będzie odpowiadało podaniu na wejscie napiecia 2,5V, czy tak.
A powiedz mi jeszcze jak doszedłeś to tego że jest to +/- 1.8V. Skąd ta 4.


A i jeszcze zapomniałem, czy mozna przetaktować przettwornik A/C, czyli ustawiając go na taktownie z f=500kHz

a_antoniak
-
-
Posty: 645
Rejestracja: 13 sty 2005, o 18:38
Lokalizacja: Krasnystaw
Kontaktowanie:

Postautor: a_antoniak » 17 wrz 2006, o 10:58

...Ale polacem wykonywanie konwersji z wynikiem przesuniętym w lewo, zwiększa to dokładność obliczeń, a jest to szczególnie ważne przy FFT.
W FFT w kolejnych krokach wartosci zwiekszaja sie a nie zmniejszaja, wiec nie rozumiem, ale nie znam calosci rozwiazania o ktorym mowa, wiec polemizowac nie moge :).

Czyli poprzez instrukcję adc_smp=ADC; następuje odczyc ADH i ADL do jedne zmiennej 16 bitowej, tak.A jaką wartośc mają te nie używane w ADL, chyba 0.
Pewnie 0, ale najlepiej pozbyc sie nieuzywanych bitow wykonujac odpowiedni AND.
POdejrzewam ,że maksymalnie w zmiennej adc_spm po powyższe instr. w zapisie bin to
1111111111000000 i to będzie odpowiadało podaniu na wejscie napiecia 2,5V, czy tak.
Tak, z tym, ze wartosc maksymalna nie odpowiada pelnemu napieciu referencyjnemu, a napiecu Vref - LSB:
0x000 represents analog
ground, and 0x3FF represents the selected reference voltage minus one LSB.
czyli: 1023/1024*2,5 = 2.49755...
A powiedz mi jeszcze jak doszedłeś to tego że jest to +/- 1.8V. Skąd ta 4.
4=2^2, z wyniku pobierane jest 8 najbardziej znaczacych bitow, 2 bity najmniej znaczace sa ignorowane.
A i jeszcze zapomniałem, czy mozna przetaktować przettwornik A/C, czyli ustawiając go na taktownie z f=500kHz
Oj, IMHO nie, ale kto wie : :mrgreen:.

Sławek5
-
-
Posty: 485
Rejestracja: 15 sie 2003, o 16:40
Lokalizacja: Szczecin
Kontaktowanie:

Postautor: Sławek5 » 17 wrz 2006, o 12:50

Póbuję rozpracować ten wskaźnik przesterwowania.
Bo ja to tak roumiem.
Na wejsciu referencyjnym jest napięcie Vref=2,5V.
Do wejscia np AD0 jest poprzez dzielnik rezystancyjny doprowadzona połowa nap. referencyjnego czyli wystepuje tam napiecie 1,25V, do tego poprzez kondenstaor doprowadzone jest napiecie zmienne (cos jak wzmacniacz operacyjne w układzie nieodrwacajacym w któryn na wej. + jest dzielnik i poprzez C doprowadzony sygnał).
Czyli jakie jest napiecie zmienne doprowadzone do kondenatora, króre jest traktowane jako przesterowanie.

nastepnie czy liczba w Twoim wzorze 121 to nie powinno być 120? Skąd 121?


Jeszcze o samym przetworniku A/C. Jezeli jest ustawiony bit ADLAR=1 to jak odczytuję sam rejest ADH (biti 0 i 1 sa pomijane) to jak teraz okreslic rozdzielczośc.
Rejest ADH ma zakres od 0 do FF
Jak wtedy interpretować ten wynik.

[ Dodano: 17-09-2006, 16:23 ]
Próbowałem w AvrStudio4 jak przebiegają obliczenia na wynikach otrzymanych z przetwornika A/C.
Chodzi o ten wzór

Kod: Zaznacz cały

adc_smp = ((int16_t) ADC) - 0x8000;
Nijak sie mi to ma do tego co wydaje sie że powinno wyjśc przy normalnych obliczeniach robionych na piechotę czyli przesunięcie z powrotem bitów w prawo o 6 pozycji i odjęcie składowej stałej (połowy przetwornika czyli 512).

Powiem że nic z tego nie rozumiem o co tu chodzi, czy AvrStudio cos namieszał czy ja niewidzę jakiegoś szczegółu który pozwoli to wyjaśnić.

Wróć do „AVR/AVR32”

Kto jest online

Użytkownicy przeglądający to forum: Obecnie na forum nie ma żadnego zarejestrowanego użytkownika i 42 gości