10
Laborator 3 1. Intreruperi externe. 2. Tastatura PMod KYPD. Conectarea si utilizarea acestei tastaturi 1. Intreruperile externe Intreruperile externe sunt un alt mod de a percepe activitatea unor pini externi. Exista opt intreruperi externe disponibile, comune cu pinii 0..3 ai portului D si cu pinii 4..7 ai portului E. Pentru Cerebot 1: Pentru Cerebot 2: Pentru ilustarea mecanismului intreruperilor, vom scrie un program care va aprinde unul dintre cele patru led-uri de pe placa, in functie de unul dintre cele patru butoane ale modulului Pmod BTN. Vom conecta modulul cu butoane la intreruperile externe INT0…INT3: - JE, pentru Cerebot 1 - JD, randul de jos, pentru Cerebot 2

Laborator 3 - UTClujusers.utcluj.ro/~rdanescu/pmp-lab3.pdfcablul 12pini la 2x6 pini. Capatul cu 12 pini il vom conecta la tastatura, cu semnul in dreptul VCC, ca in imaginile de mai

  • Upload
    others

  • View
    9

  • Download
    0

Embed Size (px)

Citation preview

Laborator 3

1. Intreruperi externe.

2. Tastatura PMod KYPD. Conectarea si utilizarea acestei tastaturi

1. Intreruperile externe

Intreruperile externe sunt un alt mod de a percepe activitatea unor pini externi. Exista opt

intreruperi externe disponibile, comune cu pinii 0..3 ai portului D si cu pinii 4..7 ai portului E.

Pentru Cerebot 1:

Pentru Cerebot 2:

Pentru ilustarea mecanismului intreruperilor, vom scrie un program care va aprinde unul dintre

cele patru led-uri de pe placa, in functie de unul dintre cele patru butoane ale modulului Pmod

BTN. Vom conecta modulul cu butoane la intreruperile externe INT0…INT3:

- JE, pentru Cerebot 1

- JD, randul de jos, pentru Cerebot 2

Atentie la polaritate! Conectati PmodBTN cu butoanele in sus!

Programul pentru identificarea butoanelor este urmatorul:

.include "m64def.inc"

.org 0x0000 ; adresa absoluta pentru intreruperea RESET

rjmp reset

.org 0x0002 ; adresa absoluta pentru intreruperea externa 0

rjmp btn1

.org 0x0004 ; adresa absoluta pentru intreruperea externa 1

rjmp btn2

.org 0x0006 ; adresa absoluta pentru intreruperea externa 2

rjmp btn3

.org 0x0008 ; adresa absoluta pentru intreruperea externa 3

rjmp btn4

reset: ; programul principal, initializarile

ldi r16, low(ramend) ; stiva

out SPL, r16

ldi r16, high(ramend)

out SPH, r16

ldi r16, 0xff ; PORTE iesire, conectat la leduri

out DDRE, r16

ldi r16, 0b11111111 ; se configureaza declansarea intreruperilor externe pe front

sts EICRA, r16 ; crescator (buton apasat). EICRA e in spatiul I/O extins

ldi r16, 0b00001111 ; se activeaza intreruperile externe 0, 1, 2, 3

out EIMSK, r16

sei ; activare intreruperi

donothing: ; programul se blocheaza in acest ciclu infinit

rjmp donothing

btn1:

ldi r16, 0b00010000 ; aprindem LED1 (conectat la PE4)

out PORTE, r16

reti ; return from interrupt

btn2:

ldi r16, 0b00100000 ; aprindem LED2 (conectat la PE5)

out PORTE, r16

reti

btn3:

ldi r16, 0b01000000 ; aprindem LED3 (conectat la PE6)

out PORTE, r16

reti

btn4:

ldi r16, 0b10000000 ; aprindem LED4 (conectat la PE7)

out PORTE, r16

reti

Prima parte a programului asociaza pentru fiecare adresa absoluta corespunzatoare intreruperilor

externe 0..3 cate o procedura (ISR – interrupt service routine), care se va executa in momentul in

care se declanseaza intreruperea. Adresele absolute sunt luate din datasheet-ul

microcontrollerului:

In continuare, programul initializeaza stiva, si directia portului E (iesire). Apoi, pentru fiecare

intrerupere externa folosita, se configureaza modul ei de declansare (in cazul nostru, pe front

crescator, corespunzator evenimentului apasare buton). Configurarea se face prin scrierea

registrului EICRA, registru din spatiul de adrese I/O extins (accesibil doar cu instructiuni de tip

Load si Store).

Intreruperile sunt apoi activate prin scrierea bitilor din registrul EIMSK. Sistemul global de

intreruperi se activeaza prin instructiunea sei, iar apoi programul principal este blocat intr-un

ciclu infinit.

2. Tastatura PMod KYPD. Conectarea si utilizarea acestei tastaturi

Tastatura cu 4x4 taste PMod KYPD este un dispozitiv pasiv, cu patru linii si patru coloane,

apasarea unei taste realizand un contact intre electrodul liniei si cel al coloanei. Electrozii linie si

coloana sunt conectati la pinii dispozitivului conform tabelului de mai jos.

Schema electrica a dispozitivului este prezentata in figura urmatoare.

Pentru identificarea unei taste, trebuie sa baleiem coloanele pe rand, punand cate o valoare logica

‘0’ pe cate o coloana, si valoarea logica ‘1’ pe toate celelalte. In acest timp, randurile sunt legate

la VCC prin intermediul unor rezistente “pull up”. La apasarea unei taste, daca tasta este pe

coloana ce primeste valoarea ‘0’, randul tastei va fi tras la ‘0’. Astfel, tasta va fi identificata prin

perechea (coloana cu valoare ‘0’, rand cu valoare ‘0’).

Pseudocodul pentru identificarea unei taste este:

Repeat:

For c = 0 to 3 do

Coloane[0]=Coloane[1]=Coloane[2]=Coloane[3]=1

Coloane[c]=0

port_iesire_coloane = Coloane

Delay()

Randuri = citeste_port_rand

For r = 0 to 3 do

If (Randuri[r]==0)

Tasta = c * 4 + r

End if

End for

End for

Goto Repeat

Codul tastei, un numar intre 0 si 15, va fi generat prin formula 4*c+r. In acest moment, nu ne

intereseaza ca acest cod sa corespunda cu numarul scris pe tasta, ci doar ca acest cod sa fie unic

pentru fiecare tasta in parte. Inmultirea cu 4 se poate face prin doua deplasari la stanga.

Conform pseudocodului, avem nevoie de doua porturi: unul de iesire, unde vom scoate valoarea

pentru coloane, pentru a realiza procedul de baleiere, si unul de intrare, unde vom citi starea

randurilor. Totusi, in continuare vom prefera o alta abordare. In loc sa citim starea randurilor si

sa vedem care dintre ele devine zero, vom folosi mecanismul de intreruperi, si vom conecta pinii

randurilor la intreruperile externe INT0…INT3. Pseudocodul se transforma astfel:

Configurare intreruperi externe INT0…INT3 pentru declansare pe front descrescator

c – variabila globala, contorul coloanelor

Repeat:

For c = 0 to 3 do

Coloane[0]=Coloane[1]=Coloane[2]=Coloane[3]=1

Coloane[c]=0

port_iesire_coloane = Coloane

Delay()

End for

Goto Repeat

INT0_ISR – se declanseaza cand apare 0 pe randul 0

Tasta = c * 4 + 0

PORTE = TASTA << 4

Reti

INT1_ISR – se declanseaza cand apare 0 pe randul 1

Tasta = c * 4 + 1

PORTE = TASTA << 4

Reti

INT2_ISR – se declanseaza cand apare 0 pe randul 2

Tasta = c * 4 + 2

PORTE = TASTA << 4

Reti

INT3_ISR – se declanseaza cand apare 0 pe randul 3

Tasta = c * 4 + 3

PORTE = TASTA << 4

Reti

Fiecare intrerupere se declanseaza doar cand randul corespunzator ei devine zero, adica atunci

cand pe acest rand exista o tasta apasata. Dar o tasta apasata nu va duce la o valoare zero pe rand

daca coloana acestei taste nu este activata prin valoarea zero. Astfel, in momentul in care apare

zero pe un rand, coloana este cunoscuta (coloana activa), si randul este de asemenea cunoscut,

deci tasta este complet identificata.

In continuare, vom conecta tastatura la placa Cerebot II. Pentru realizarea conexiunii, vom utiliza

cablul 12pini la 2x6 pini. Capatul cu 12 pini il vom conecta la tastatura, cu semnul in dreptul

VCC, ca in imaginile de mai jos:

Cele doua capete de 6 pini ale cablului sunt conectate, in acest moment, astfel:

- Capatul marcat cu A este conectat la coloane

- Capatul marcat cu B este conectat la randuri

Capatul A trebuie conectat la placa Cerebot la pinii unui port de iesire, unde vom trimite valori

de genul 0111, 1011, 1101, 1110, in mod repetat. In figura de mai jos acest capat este conectat la

JA, randul de sus, corespunzator bitilor PA3…PA0.

Capatul B trebuie conectat la conectorul unde gasim intreruperile externe INT0… INT3. Pentru

placa Cerebot II, acest conector este JD, randul de jos.

Pentru baleierea coloanelor puteti folosi urmatorul cod:

ldi r16, 0 ; r16, numarul coloanei

baleiere:

rcall codecol ; functie care genereaza numar ‘0’ pe pozitia indicata in r16

out PORTA, r17 ; transmitem pe portul atasat coloanelor

rcall delay ; intarziere necesara

inc r16 ; crestem numarul coloanei

cpi r16, 4 ; am trecut de 3 ?

brne baleiere

ldi r16, 0 ; daca da, reluam baleierea de la prima coloana

rjmp baleiere

Functia codecol foloseste operatia de deplasare pentru a pozitiona valoarea de activare pe pozitia

specificata de intrarea r16:

; input r16, number of col, from 0 to 7

; output r17, col made zero, others one

codecol:

push r16

ldi r17, 1

shift:

cpi r16, 0

breq shift_done

lsl r17

dec r16

rjmp shift

shift_done:

com r17

pop r16

ret

Pentru verificarea functiei de baleiere, conectati la portul de iesire, in locul capatului A al

cablului de la tastatura, un bloc de led-uri, ca in figura de mai jos. Daca baleierea este corecta, se

va observa cum led-urile se sting pe rand.

Pentru conectarea tastaturii la Cerebot 1, vom utiliza pentru baleiere portul F, ai carui pini

sunt accesabili prin conectorul JF. Portul F este in spatial I/O extins, astfel incat pentru

configurarea directiei veti scrie:

sts DDRF, r16

Pentru transmiterea unei valori la iesire se va scrie:

sts PORTF, r16

Capatul B il vom atasa la conectorul JE, unde se afla intreruperile externe.

Daca baleierea este corecta, apasarea unei taste va produce un front descrescator pe pinul

corespunzator randului. Acest front se detecteaza configurand intreruperile externe sa sesizeze

frontul descrescator.

Lucru individual

1) Compilati si rulati programul pentru verificarea intreruperilor externe. Modificati modul

de detectie al intreruperilor (front crescator, nivel). Activati si dezactivati intreruperi

individuale.

2) Conectati tastatura la placa, urmand instructiunile corespunzatoare placii pe care o aveti.

Verificati baleierea folosind led-urile.

3) Identificati tasta si afisati codul acesteia pe led-urile de pe placa, folosind intreruperi.

4) Folosind un LUT, decodificati tasta astfel incat numarul afisat pe led-uri sa corespunda

cifrei hexazecimale desenata pe tasta.

5) Extra: afisati codul tastei pe SSD (e suficienta 1 cifra, fara baleiere)

Documente suplimentare:

PModKYPD_rm.pdf