11.07.2015 Views

Laboratorium Systemów wbudowanych Ćwiczenie nr l Podstawy ...

Laboratorium Systemów wbudowanych Ćwiczenie nr l Podstawy ...

Laboratorium Systemów wbudowanych Ćwiczenie nr l Podstawy ...

SHOW MORE
SHOW LESS

Create successful ePaper yourself

Turn your PDF publications into a flip-book with our unique Google optimized e-Paper software.

<strong>Laboratorium</strong> Systemów <strong>wbudowanych</strong>Wyższa Szkoła Zarządzania i Bankowości, Informatyka studia inżynierskieĆwiczenie <strong>nr</strong> l<strong>Podstawy</strong> programowania mikrokontrolerów rodziny AVR8opracował dr inż. Wojciech ZaborowskiPlan ćwiczenia:Ćwiczenie wykonywane jest z wykorzystaniem zestawu uruchomieniowego ZL15AVRfirmy Kamami. Zestaw uruchomieniowy zbudowany jest w oparciu o mikrokontrolerATMEL Atmega32. Szczegółowe informacje na temat budowy zestawu można uzyskaćz jego dokumentacji (http://www.kamami.pl/dl/zl15avr.pdf). Do programowaniamikrokontrolera wykorzystany zostanie pakiet oprogramowania AVR Studio 4 wrazz pakietem WinAVR. Połączenie tych dwóch pakietów pozwala w prosty sposóbprogramować mikrokontrolery rodziny AVR z poziomu języka C z wykorzystaniemgraficznego interfejsu użytkownika.Zestaw jest zasilany z portu USB komputera. Dodatkowo do programowaniamikrokontrolera wykorzystuje się dedykowany programator z interfejsem JTAG(ZL15PRG) podłączony do drugiego portu USB.1 Zadanie 1Uruchomić środowisko AVR Studio 4. Skopiować i rozpakować na lokalny dysk projekt onazwie LED. Przy pomocy polecenia Project→Open Project wczytać projekt (wczytać pliko nazwie led.aps).W pliku źródłowym led.c w sekcji komentarza opatrzonej słowem DESCRIPTIONSznajduje się opis połączeń, jakie należy wykonać przy pomocy dostępnych przewodów.Wykonanie wymienionych połączeń jest niezbędne do poprawnego uruchomieniaprzykładu i zaobserwowania efektów jego działania.UWAGA !!! – Wszelkie połączenia pomiędzy urządzeniami peryferyjnymia mikrokontrolerem mogą być dokonywane wyłącznie przy odłączonym zasilaniu.Po wykonaniu połączeń opisanych w sekcji DESCRIPTION należy poprosić osobęprowadzącą zajęcia o sprawdzenie poprawności ich wykonania. Dopiero po uzyskaniuzgody można włączyć zasilanie zestawu.Aby stworzyć pliki niezbędne do zaprogramowania mikrokontrolera, należyprzeprowadzić kompilację projektu. Wykonuje się to poleceniem Build→Build lub zwykorzystaniem klawisza skrótu F7. Po poprawnej kompilacji projektu możnaprzystąpić do programowania wewnętrznej pamięci FLASH mikrokontrolera.Jeśli jest to pierwsza próba programowania, należy wcześniej przeprowadzićkonfigurację programatora/debugera. Dokonuje się tego przy pomocy polecenia


<strong>Laboratorium</strong> Systemów Wbudowanych – Wyższa Szkoła Zarządzania i Bankowości w KrakowieTools→Program AVR→Connect… Wybranie tego polecenia powoduje pojawienie się oknawyboru przedstawionego na Rys. 1. (Uwaga – w niektórych sytuacjach poprawneskonfigurowanie programatora może wymagać uprawnień administratora na danymkomputerze – w takiej sytuacji należy się zwrócić o pomoc do prowadzącego zajęcia )Rys. 1 Okno konfiguracji programatoraZ listy programatorów znajdujących się w oknie po lewej stronie należy wybraćJTAG ICE. Port komunikacyjny pozostawiamy na Auto, lub jeśli było wybrane inneustawienie wybieramy Auto. Następnie wciskamy przycisk Connect… .Jeśli połączenia między komputerem, programatorem oraz zestawemuruchomieniowym funkcjonują poprawnie i konfiguracja przebiegła prawidłowo naekranie pojawi się następujące okno:Rys. 2 Okno programatora w trybie JTAGNajważniejsze opcje i polecenia znajdują się na zakładce Program. Przycisk Erase Devicepowoduje wykasowanie wewnętrznej pamięci FLASH mikrokontrolera (co jestrównoznaczne z usunięciem zapisanego w niej programu).2


<strong>Laboratorium</strong> Systemów Wbudowanych – Wyższa Szkoła Zarządzania i Bankowości w KrakowieDo zaprogramowania tej pamięci wykorzystywać będziemy sekcję Flash. Powinna w niejbyć zaznaczona opcja Input HEX File (jak na Rys. 2). W polu obok należy wskazać plik,którym ma zostać zaprogramowana pamięć FLASH. Zwykle taki plik wynikowy posiadanazwę taką jak nazwa projektu, rozszerzenie .hex . Kompilator tworzy ten plikw podkatalogu ./default znajdującym się w katalogu z plikami projektu. Przedprogramowaniem należy zwrócić uwagę czy wskazany jest właściwy plikstanowiący rezultat kompilacji projektu nad którym aktualnie pracujemy, a nieprzypadkowy plik mogący być pozostałością po pracy innych grup. Po wciśnięciuprzycisku Program pamięć FLASH jest zapisywana zawartością pliku .hex i następujeautomatyczne uruchomienie wczytanego programu, co w przypadku projektu ledpowinno być widoczne w postaci zapalających się i gasnących diod świecących D0-D7.Po prawidłowym wykonaniu wszystkich etapów związanych z uruchomieniem przykładowego projektu o nazwie led dokonać modyfikacje w programie tak aby uzyskaćefekt wędrującego światła (zapalamy diodę D0, w kolejnym kroku zapalamy diodę D1 igasimy D0, w kolejnym zapalamy D2 i gasimy D1 itd. gdy zapalimy diodę D7 w kolejnymkroku zapalamy D6 i gasimy D7 itd. aż dojdziemy do diody D0.2 Zadanie 2 – obsługa wejść i wyjść binarnychPunktem wyjścia będzie projekt o nazwie buzzer. W pierwszej kolejności należyrozpakować pliki umieszczone w archiwum buzzer.zip. Następnie wykonać niezbędnepołączenia i zaprogramować mikrokontroler.Wykonać zestaw eksperymentów pozwalający określić w jaki sposób kontroluje sięwysokość i czas trwania generowanych dźwięków.Odłączyć zasilanie. Wykonać dodatkowe połączenia Podłączyć wyjściaczteroprzyciskowej klawiatury SW0÷SW3 znajdujące się na złączu Con19 dowyprowadzeń portu PB0÷PB3 mikrokontrolera (Con16) w następujący sposób:SW0→PB0, SW1→PB1, SW2→PB2, SW3→PB3.Rozbudować projekt buzzer aby w zależności od wciśniętego przycisku generowany byłdźwięk o różnych parametrach.Z punktu widzenia mikrokontrolera działanie przycisków SW0-SW3 jest następujące:• gdy przycisk nie jest wciśnięty, na linię portu, do której przycisk jest podłączonypodawany jest stan wysoki (mikrokontroler „widzi” tą linie jako 1).• gdy przycisk jest wciśnięty, na linię portu do której jest podłączony podawanyjest stan niski (mikrokontroler „widzi” tą linie jako 0).Zestaw przydatnych wiadomości na temat programowania mikrokontrolerów rodzinyAVR8 z użyciem kompilatora AVR-GCC (wykorzystywanego w pakiecie AVR Studio 4)można znaleźć pod adresem http://hobby.abxyz.bplaced.net/index.php?pid=4&aid=2.Linie we/wy mikrokontrolera ATmega32 pogrupowane są w cztery ośmiobitowe portyA, B, C, D. Do obsługi tych portów wykorzystywane są trzy rejestry specjalne, oddzielnedla każdego portu:• rejestr kontroli kierunku portu DDRx,3


<strong>Laboratorium</strong> Systemów Wbudowanych – Wyższa Szkoła Zarządzania i Bankowości w Krakowie• wykorzystywany już wcześniej rejestr wyjściowy PORTx• rejestr wejściowy PINx(za x należy wstawić odpowiednią nazwę portu. I tak dla Portu A mamy dedykowanerejestry PORTA, PINA, DDRA itp.). Pozwala to praktycznie dowolnie konfigurowaćposzczególne linie.Odczytywanie stanu poszczególnych linii portów wiąże się z manipulacjami napojedynczych bitach. W związku z tym warto przypomnieć sobie w jaki sposób iz użyciem jakich operatorów języka C takie manipulacje można wykonywać.W języku C jest sześć operatorów bitowych:|,&,^,,~. Zasadę ich działanianajprościej jest objaśnić na przykładach. Liczby używane w przykładach przedstawionesą w postaci dwójkowej.operator "|" - bitowa alternatywa lub inaczej suma logiczna (OR)0 1 0 1 0 1 0 1| 0 0 1 1 0 0 1 1= 0 1 1 1 0 1 1 1operator "&" - bitowa koniunkcja lub inaczej iloczyn logiczny (AND)0 1 0 1 0 1 0 1& 0 0 1 1 0 0 1 1= 0 0 0 1 0 0 0 1operator "^" - bitowa alternatywa wykluczająca (XOR)0 1 0 1 0 1 0 1^ 0 0 1 1 0 0 1 1= 0 1 1 0 0 1 1 0operator ">" określa o ile bitów należy przesunąć. Przy przesuwaniu o każdy bit,na najbardziej znaczącej pozycji wpisywana jest wartość 0)operator "~" - dopełnienie jedynkowe lub inaczej negacja każdego bitu~ 1 0 0 1 1 0 0 1= 0 1 1 0 0 1 1 0Aby móc odczytać stan przycisków SW0-3 podłączonych do linii PB0-PB3mikrokontrolera musimy zacząć od odpowiedniego skonfigurowania portu PB.Wykonuje się to poprzez wpisanie do rejestru DDRB odpowiedniej wartości. Zasadykonfiguracji linii portów są identyczne dla każdego z nich. Wpisanie do rejestru DDRx,na odpowiadającej danemu wyprowadzeniu pozycji bitowej wartości 1, konfiguruje tąlinię jako wyjście, natomiast umieszczenie tam wartości 0 ustawia linię jako wejście.4


<strong>Laboratorium</strong> Systemów Wbudowanych – Wyższa Szkoła Zarządzania i Bankowości w Krakowie(polecenie DDRB = 0x0F; konfiguruje cztery starsze linie – PB4-PB7 jako wejścia, acztery młodsze linie – PB0-PB3 jako wyjścia).Odczyt stanu linii wejściowych portu wykonuje się poleceniem PINx :DDRB = 0x00; // konfiguracja wszystkich linii PB jako wejsciaprzyciski = PINB; // przypisanie zmiennej wynik aktualnego// linii portu PB stanuJak wspomniano wcześniej, wciśnięcie przycisku powoduje, że na odpowiednim bicie wrejestrze PINx jest ustawiana wartość 0. Aby zatem stwierdzić fakt wciśnięciaktóregokolwiek przycisku należy sprawdzić, które bity w momencie odczytu stanu portuB miały wartość 0 (powiedzmy, ze będziemy rozważać wciśnięcie przycisku S2podłączonego do linii PB2).Pierwszym krokiem jest odrzucenie zbędnych informacji o stanie pozostałych liniiportu. Najczęściej stosowanym rozwiązaniem jest tu wyzerowanie wszystkich bitówz wyjątkiem tego, który nas interesuje (w rozważanym przykładzie interesuje nas stanlinii PB2 odwzorowywany na drugim bicie wartości odczytanej z portu B – dlaprzypomnienia bity w bajcie numerujemy od 0).Wyzerowania bitów dokonuje się poprzez operację iloczynu logicznego (operator &) naodczytanej poleceniem PINB wartości z tzw. maską. W rozważanym przypadku maskaposiada wyłącznie jeden bit o wartości 1 na pozycji, która ma pozostać nie zmieniona.Na pozostałych pozycjach bitowych umieszczone są zera. Zatem dla sprawdzenia stanulinii PB2 maska będzie miała wartość 0b00000100 lub 0x04 w zapisie szesnastkowym.Stan przycisku S2 podłączonego do portu PB2 można zatem ustalić, jako wyniknastępującej operacji:przycisk_s2 = przyciski & 0b00000100; //w zm. przyciski// przechowywany jest stan portu B odczytany wcześniej// poleceniem PINBjeśli zmienna przycisk_s2 przyjmie wartość 0 oznaczać to będzie, że bit 2 w rejestrzePINB miał wartość 0 co prowadzi do wniosku, że przycisk S2 był wciśnięty. Jeślinatomiast wynik tej operacji będzie różny od zera oznacza to, że przycisk wciśnięty niebył.Aby nie marnować pamięci mikrokontrolera na deklaracje niepotrzebnych zmiennych,sprawdzenia zwykle dokonuje się za pomocą pojedynczej instrukcji if:if ( (przycisk_s2 & 0b00000100) == 0 ){// tu będzie procedura obsługi naciśnięcia przycisku S2}lub jeszcze prościejif (!((przyciski &0b00000100))){// tu będzie procedura obsługi naciśnięcia przycisku S2}5


<strong>Laboratorium</strong> Systemów Wbudowanych – Wyższa Szkoła Zarządzania i Bankowości w Krakowie3 Zadanie 3 – Ciekłokrystaliczny wyświetlacz znakowyZnakowy wyświetlacz LCD jest często stosowanym i stosunkowo prostym w obsłudzeurządzeniem wyjściowym stosowanym w układach zbudowanych z wykorzystaniemróżnych mikrokontrolerów jednoukładowych. Jedną z najbardziej popularnychkonstrukcji są wyświetlacze oparte o kontroler zgodny HD44780. Kontrolery teposiadają możliwość sterowania wyświetlaczem ciekłokrystalicznym wyposażonym wpole odczytowe od 1x8 do 4x40 znaków. W minimalnej konfiguracji podłączeniewyświetlacza z mikrokontrolerem sterującym wykonywane jest przy użyciu 6 lub 7 liniiwe/wy.Przeanalizować i uruchomić przykładowy projekt umieszczony archiwum char_lcd.zip.Zapoznać się ze sposobem wyświetlania różnych informacji tekstowych.3.1 Definiowanie własnych znaków.LCD ma miejsce dla ośmiu znaków zdefiniowanych przez użytkownika. Znaki teposiadają kody o wartościach od 00H do 07H. Dane te są przechowywane w pamięciwyświetlacza, która nazywa się CGRAM. Przed użyciem wzorce znaków muszą byćwysłane do wyświetlacza. Zwykle wykonywane jest to zaraz po jego inicjalizacji(wzorce znaków są tracone bezpowrotnie po wyłączeniu zasilania lub inicjalizacjiwyświetlacza).Każdy zdefiniowany znak wymaga 8 bajtów danych. Ósmym bajtem jest zazwyczaj $00,ponieważ jest to miejsce przeznaczone dla linii kursora. Standardowa czcionkawyświetlacza ma 5 pikseli szerokości i 7 pikseli wysokości. Jeden rząd pikseli na samymdole jest zarezerwowany na podkreślający znak kursora.Kształt znaku jest taki jaki jest układ zer i jedynek w bicie danych. Jedynka zaświecapiksel, zero pozostawia piksel zgaszonym. Oto przykład znaku zdefiniowanego przezużytkownika:6


Poniżej zamieszczono fragment programu prezentujący w jaki sposób definiuje sięi wykorzystuje własne znaki. (wystarczy go umieścić w przykładowym projekciewykorzystywanym w tej części ćwiczenia, zamieniając odpowiedni fragment koduźródłowego).//-------------------------------------// main program//-------------------------------------uint8_t znak[] = {0, 10, 10, 0, 17, 14, 6, 0}; //wlasny znak - buzkaint main(void){char temp, i;LCD_Initialize();LCD_ProgrammChar(0, znak);LCD_GoTo(0,0);LCD_WriteText("- Wlasne znaki -");// wyswietlenie zdefiniowanego znakuLCD_GoTo(0,1);LCD_WriteData(0);while(1){}return 0;}Na podstawie analizy przykładu przedstawionego powyżej zaprojektować zestawpolskich znaków diakrytycznych, aby możliwe było poprawne wyświetlenie tekstu„żółwik”.Wersja z dnia 2011-10-27 09:577

Hooray! Your file is uploaded and ready to be published.

Saved successfully!

Ooh no, something went wrong!