|
|
mikrokontrolery.net |
||||||||||||||||||
|
Cześć 2 - obsługa klawiatury W ćwiczeniu tym zapoznamy się z obsługą prostej klawiatury.
Aby przeprowadzić to ćwiczenie musimy do portu P2 podłączyć przełączniki
zwierające wyprowadzenia portu do masy w momencie naciśnięcia przycisku,
tak jak pokazano na rysunku
. Podłączenie diod LED jest identyczne jak w przykłądzie poprzednim. Nie
nadaje się do tego celu port P0 ze względu na brak wewnętrznych rezystorów
podciągających. Jeżeli chcemy do portu P0 podłączyć klawiaturę to musimy
"podciągnąć" piny porto P0 do plusa zasilania poprzez dolączenie
pomiędzy wyprowadzenia portu a szynę zasilającą rezystorów o wartości
kilku- do kilkudziesięciu kiloomów. Przykład 2.1
Przykład 2.1.ASM
$INCLUDE (ATMEL/REG8252.INC) P02_01_ASM SEGMENT CODE RSEG P02_01_ASM Przykład 2.1.C #include <ATMEL/REG8252.h> void main(void) Przykład 2.1.BAS Do Omówienie W powyższym przykładzie stan linii portu P2 jest kopiowany do portu P0.
Przeprowadˇmy teraz analizę kodu wynikowego powyższego programu
wygenerowanego poprzez każdy z użytych kompilatorów. Przykład 2.1.ASM.D51 Przykład 2.1.C.D51 ; END OF main Przykład 2.1.BAS.D51 . ; Pominięte zostały instrukcje powrotu
; Tutaj rozpoczyna się właściwy program Kompilator każdego z języków użył do zrealizowania podanego
zadania jednej instrukcji "MOV direct1, direct2", a więc zrealizował
to zadanie optymalnie. Jedyną wątpliwość budzi użycie przez Bascoma trzybajtowej
instrukcji "LJMP" do zrealizowania pętli nieskończonej. Ponieważ
skok następuje do poprzedniej instrukcji wystarczyło użyć dwubajtową instrukcję
"SJMP" , ewentualnie także dwubajtową instrukcję "AJMP".
Świadczy to o tym, że Bascom nie sprawdza zakresu skoku i zawsze wstawia
instrukcję obejmującą największy obszar pamięci i niepotrzebnie zajmującą
jeden bajt pamięci prgramu więcej. Natomiast kompilator jezyka C użył
do zrealizowania pętli najbardziej optymalnej instrukcji "SJMP". Przykład 2.2
Przykład 2.2.ASM
$INCLUDE (ATMEL/REG8252.INC) P02_01_ASM SEGMENT CODE RSEG P02_01_ASM S1 EQU P2.0 START: DALEJ: SJMP START END Przykład 2.2.C
sbit S1 = P2^0; void main(void) Przykład 2.2.BAS S1 Alias P2.0 W tym przykładzie doskonale widać, który z języków oferuje najlepszą czytelność kodu. Asembler oczywiście nie zapewnia tej jakże ważnej cechy. Moim zdaniem najbardziej czytelny jest program napisany w języku C, choć zwolennicy Bascoma zapewne nie przyznają mi racji. Przykład 2.3 Program w tym przykładzie po naciśnięciu przycisku S1 zapala diodę D1 a po ponownym naciśnięciu przycisku S1 gasi tą diodę. Przykład 2.3.ASM $INCLUDE (ATMEL/REG8252.INC) P02_01_ASM SEGMENT CODE RSEG P02_01_ASM S1 EQU P2.0 START: END Przykład 2.3.C sbit S1 = P2^0; void main(void) Przykład 2.3.BAS Opis: Przykład 2.4.ASM START: CZEKAJ: Przykład 2.4.C void czekaj(void) void main(void) Przykład 2.4.BAS Opis: Instrukcja "MOV R1, #255" służy do ustawienia licznika pętli L2. Instrukcja "MOV R0, #255" służy do ustawienia licznika pętli L1. Użycie dwóch pętli zagnieżdżonych podyktowane jest małym zakresem powtórzeń realizowanych przez instrukcję "DJNZ" (maksymalnie 256 razy, gdy licznik pętli ustawimy na "0"). Do zrealizowania pętli służy instrukcja "DJNZ Rn, rel". W naszym przykładzie w pierwszej kolejności jest realizowana pętla L1 (255 powtórzeń, co daje ok. 510 us, przy zegarze 12 MHz). Pętla ta jest z kolei powtarzana 255 razy w pętli L2. W sumie daje to opóˇnienie ok. 130 ms. W języku C procedura opóˇniająca wygląda następująco: void czekaj(void) W pierwszym wierszu procedury deklarujemy dwie zmienne, które posłużą nam jako liczniki pętli. Instrukcja "for(x = 255; x >0; --x)" realizuje pętlę, w której jest zagnieżdżona druga pętla, podobna do pierwszej. Skonstruowanie tych pętli, jako liczących "w dół" narzucone zostało przez architekturę mikrokontrolera i występowanie w języku asemblera instrukcji pętli wykorzystujących dekrementację licznika pętli. Daje to bardziej zwięzły kod wynikowy niż z realizująca tą samą liczbę powtórzeń pętla "for(x = 0; x < 255, ++x)". W języku BASCOM do opóˇnienia wykorzystana została specjalnie do tego celu przeznaczona instrukcja "WAITMS x". Jest ona najprostsza w użyciu, bowiem podajemy liczbowo czas opóˇnienia w milisekundach nie musimy mozolić się z obliczaniem ilości powtórzeń i czasu realizowania pętli, jak w przypadku C i asemblera. Porównajmy teraz kod wynikowy tych trzech programów. Już
samo porównanie rozmiaru plików *.BIN daje nam jasny obraz efektywności
każdego z trzech języków: Przykład 2.4.BAS.D51 . ; Pominięte zostały instrukcje powrotu
X002e: mov r0,a
|
||||||||||||||||||
|
|
|||||||||||||||||||
|
|
|||||||||||||||||||
|
|
|||||||||||||||||||
|
(c) 2004-2008 Radosław Kwiecień |