Sei sulla pagina 1di 207

Dipartimento di ingegneria navale, elettrica, elettronica e delle telecomunicazioni

Giuliano Donzellini

Dispensa del corso di

Elettronica dei Sistemi Digitali


Secondo semestre

Sistemi a microprocessore

Anno Accademico 2014-2015

Universit di Genova Scuola Politecnica

Indice

Introduzione ai sistemi a microprocessore

1.1
1.1.1
1.2

Elementi fondamentali di un generico calcolatore digitale


Considerazioni sulla esecuzione delle istruzioni
L'architettura a BUS comune

Le memorie

2.1
2.2
2.3
2.4
2.5
2.6
2.7
2.7.1
2.7.2

Le RAM: concetti introduttivi


La struttura interna: la singola locazione
La struttura interna: il Bus Dati
La struttura interna: la decodifica dell'indirizzo
Le connessioni del chip di memoria con l'esterno
Temporizzazioni delle RAM Statiche
Breve classificazione dei dispositivi di Memoria a Semiconduttore
Le memorie di tipo ROM
Le memorie di tipo RAM

Il microprocessore DMC8

3.1
3.2
3.3

Introduzione all'architettura del DMC8


Gli elementi dell'architettura interna del DMC8
I collegamenti del chip DMC8

Il funzionamento del microprocessore

4.1
4.1.1
4.2
4.2.1
4.3
4.3.1
4.3.2
4.3.3
4.3.4
4.4

Il microprocessore e la memoria
Il contenuto della memoria all'accensione del sistema
Il linguaggio Macchina
Esempio di programma in formato MNEMONICO Assembly
Prelievo, decodifica ed esecuzione delle istruzioni
Prelievo della istruzione (Instruction Fetch)
Decodifica della istruzione (Instruction Decode)
Esecuzione della istruzione (Instruction Execute)
Prelievo ed esecuzione delle successive istruzioni
Considerazioni sulla velocit di esecuzione

Introduzione alla programmazione in Assembly

5.1
5.1.1
5.1.2
5.2
5.2.1
5.2.2

I linguaggi di programmazione
I linguaggi ad "Alto Livello"
I linguaggi a "basso livello"
Il linguaggio Assembly del DMC8
Un primo esempio di programma scritto in Assembly
Simboli, Variabili, Etichette e Direttive in Assembly

5.2.2.1
5.2.2.2
5.2.2.3

La direttiva EQU
La direttiva ORG
Le direttive DB e DW

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

I modi di indirizzamento del microprocessore DMC8

6.1
6.2
6.3
6.3.1
6.3.2
6.4
6.5
6.6
6.7
6.8
6.9

Indirizzamento IMMEDIATO (dati a 8 bit)


Indirizzamento IMMEDIATO ESTESO (per dati a 16 bit)
Indirizzamento DIRETTO
Indirizzamento DIRETTO di dato a 8 bit:
Indirizzamento DIRETTO di dato a 16 bit:
Indirizzamento INDIRETTO tramite REGISTRO
Indirizzamento INDIRETTO tramite REGISTRO INDICE
Indirizzamento di REGISTRO
Indirizzamento IMPLICITO
Indirizzamento del BIT
Indirizzamento MODIFICATO

Le istruzioni del microprocessore DMC8

7.1
7.1.1
7.1.2
7.2
7.2.1
7.2.2
7.2.3
7.2.4
7.2.5
7.3
7.4
7.5
7.5.1
7.5.2
7.5.3
7.6
7.6.1
7.6.2
7.7
7.8

Istruzioni di Caricamento
Istruzioni di Caricamento a 8 bit
Istruzioni di Caricamento a 16 bit
Istruzioni Aritmetiche e Logiche
Istruzioni Aritmetiche a 8 bit
Istruzioni Logiche
Istruzioni Aritmetiche a 16 bit
Istruzioni di Incremento e Decremento a 8 bit
Istruzioni di Incremento e Decremento a 16 bit
Istruzioni di Rotazione e Scalamento
Istruzioni di Manipolazione del Bit
Istruzioni di Salto
Salti Incondizionati
Salti Condizionati
Un esempio di applicazione dei salti condizionati: i Cicli di Ritardo
Istruzioni di Chiamata e Ritorno da Sottoprogrammi
Lo Stack e lo Stack Pointer
I Sottoprogrammi e le Istruzioni di Chiamata e Ritorno
Istruzioni di Ingresso e Uscita
Istruzioni di Controllo della CPU

La struttura hardware di un sistema a microprocessore

8.1
8.2
8.3
8.3.1
8.3.2
8.3.3
8.3.4
8.4
8.5
8.5.1
8.5.2
8.5.3

I generatori di Clock e di Reset


Il comportamento del Bus
La temporizzazione dei dispositivi
I Cicli Macchina del DMC8
Ciclo di Prelievo dell' Istruzione (Fetch Cycle)
Accesso alla Memoria in Lettura e in Scrittura
Accesso ai Dispositivi di Ingresso e Uscita
Il progetto del sistema di memoria
Il progetto dei porti di ingresso e uscita
Il Porto di Uscita Parallelo
Il Porto di Ingresso Parallelo
La Mappa dei dispositivi di Ingresso/Uscita (I/O Map)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

ii

Interfacciamento con i dispositivi esterni

9.1
9.1.1
9.1.2
9.1.3
9.2
9.2.1
9.3
9.3.1
9.3.2
9.3.3
9.4
9.4.1
9.4.2

Esempi di gestione del protocollo di intesa (Handshake)


Handshake di tipo unidirezionale
Handshake di tipo bidirezionale
Handshake di maggiore complessita`
L'hardware in supporto alla gestione del protocollo di intesa
Esempio di Interfaccia con handshake "hardware"
Tecniche di "Polling" e di "Interruzione" nella gestione dei dispositivi
La tecnica del "Polling"
La tecnica delle interruzioni
Interfaccia con richiesta di interruzione
I temporizzatori (Timer)
Un esempio di Timer
Uso dei Timer: esecuzione concorrente di programmi

10

Applicazioni ed Esercizi Risolti

10.1
10.1.1
10.1.2
10.1.3
10.1.4
10.1.5
10.2
10.2.1
10.2.2
10.2.3

Lemulatore di microcomputer d-McE


La barra di controllo
I registri interni della CPU
La memoria di sistema
Il codice eseguibile
I porti paralleli di ingresso e uscita
Il microcomputer come componente d-DcS
Il componente DMC8 Microcomputer nel d-DcS
Il componente Interrupt Timer
Il men di contesto del componente DMC8 Microcomputer

10.2.3.1
10.2.3.2
10.2.3.3
10.2.3.4
10.2.3.5
10.2.3.6

10.2.4
10.3
10.3.1

La simulazione temporale di un sistema con microcalcolatore embedded


Esempi introduttivi
10.3.1Funzioni logiche elementari

10.3.1.1
10.3.1.2
10.3.1.3
10.3.1.4

10.3.2

Porta NOT
Porta AND (a due ingressi)
Multiplexer (due canali, una uscita)
Decoder (da 3 a 8)

Reti logiche di tipo sequenziale

10.3.2.1
10.3.2.2
10.3.2.3
10.3.2.4
10.3.2.5

10.4
10.4.1
10.4.2
10.4.3
10.4.4
10.4.5

La finestra del Codice Oggetto


La finestra dei Registri
La finestra della Memoria
La finestra dei Porti di Ingresso e Uscita
La finestra di visualizzazione del codice sorgente
La Tabella dei Simboli

Flip-Flop di tipo D PET


Flip-Flop di tipo D PET, con ingresso asincrono di Clear
Registro a scorrimento (8 bit)
Registro a scorrimento (16 bit)
Contatore sincrono avanti, modulo 256, presettabile

Esercizi risolti (senza tecniche di interrupt)


Contatore binario sincrono avanti/indietro a 12 bit
Rotazione di 8 bit su di un porto di uscita
Temporizzatore (da 0 a 25,5 S, in passi di 100 mS)
Trasmettitore seriale asincrono (6 bit, 1 mS)
Contatore a codice programmabile (binario / gray, 4 bit)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

iii

10.4.6
10.4.7
10.4.8
10.4.9
10.5
10.5.1
10.5.2
10.5.3
10.5.4
10.5.5
10.5.6
10.5.7
10.5.8
10.5.9

Lampeggiatore (4 lampadine: 800, 400, 200, 100 mS)


Lampeggiatore (3 lampadine: 500, 250, 200 mS)
Contatore sincrono BCD a 3 cifre (12 bit)
Macchina a Stati Finiti
Esercizi risolti (con tecniche di interrupt)
Macchina a Stati Finiti (con Interrupt Timer)
Macchina a Stati Finiti (con Interrupt richiesto dal porto di ingresso)
Contatore di oggetti
Contatore di oggetti di due tipi
Montacarichi
Contatore di oggetti (con selezione in base al peso)
Interfaccia a pulsanti per video gioco
Controllo della velocit di otto ruote tachimetriche
Telecomando per antifurto

11

Esercizi

11.1
Esercizi di progetto
(senza uso di tecniche di interrupt)
11.1.1
Progetto di porti e visualizzazione della ROM
11.1.2
Visualizzazione di aree di ROM (1)
11.1.3
Visualizzazione di aree di ROM (1)
11.1.4
Decodifica binaria 3-8
11.1.5
Inizializzazione di area RAM
11.1.6
Lampadine accese alternativamente
11.1.7
Accensione temporizzata di lampadine
11.1.8
Calcolo della media
11.1.9
CALL, PUSH e POP (1)
11.1.10
CALL, PUSH e POP (2)
11.1.11
Temporizzatore
11.1.12
Funzione aritmetica programmabile (1)
11.1.13
Funzione aritmetica programmabile (2)
11.1.14
Funzione aritmetica programmabile (3)
11.1.15
Funzione aritmetica (calcolo con numeri frazionari)
11.1.16
Controllo di sensori di temperatura
11.1.17
Flip-Flop JK - PET
11.1.18
Vasche con sensori di livello
11.1.19
Registro a scorrimento SISO a 5 bit
11.1.20
Registro a scorrimento PISO a 16 bit
11.1.21
Registro a scorrimento universale a 16 bit
11.1.22
Registro a scorrimento SIPO a 24 bit
11.1.23
Contatore binario sincrono avanti/indietro a 10 bit
11.1.24
Contatore sincrono avanti/indietro presettabile a 16 bit
11.1.25
Contatore sincrono binario avanti/indietro, ciclico, modulo 256
11.1.26
Visualizzazione su 8 lampadine di sequenza numerica
11.1.27
Generatore di segnale digitale

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

PN9206
PN9401
PN9305
PN9402
PN9403
PN9405
PN9404
PN9603
PN9501
PN9304
PN0203
PN0001
PN9906
PN9905
PN0002
PN9602
PN9705
PN9701
PN9804
PN9803
PN9901
PN9802
PN0204
PN9904
PN9801
PN9702
PN9604

iv

11.2
Esercizi di progetto
(con uso di tecniche di interrupt)
11.2.1
Controllore per effetti speciali di luce
11.2.2
Contatore di transiti autostradali
11.2.3
Contatore di prodotti da forno
11.2.4
Controllore di carrello industriale
11.2.5
Gestione di pulsanti (Up / Down)
11.2.6
Misuratore di velocit di rotazione
11.2.7
Conteggio di oggetti prodotti (con visualizzazione in binario)
11.2.8
Conteggio di oggetti (con trasmissione seriale a comando)
11.2.9
Conteggio di oggetti (con trasmissione seriale automatica)
11.2.10
Telecomando per sintonizzatore radio
11.2.11
Ascensore
11.2.12
Telecomando per amplificatore audio

PI011127
PI020627
PI020906
PI030204
PI030409
PI041112
PI050125
PI060123
PI070710
PI080613
PI080714
PI090115

12

Appendice: tabelle delle istruzioni DMC8

12.1
12.1.1
12.1.2
12.1.3
12.1.4
12.1.5
12.1.6
12.1.7
12.1.8
12.1.9
12.1.10
12.1.11
12.1.12
12.1.13
12.2
12.3
12.4
12.4.1
12.4.2

Tabelle delle Istruzioni DMC8


Istruzioni di Caricamento a 8 bit
Istruzioni di Caricamento a 16 bit
(prima parte)
Istruzioni di Caricamento a 16 bit
(seconda parte)
Istruzioni Aritmetiche e Logiche a 8 bit
(prima parte)
Istruzioni Aritmetiche e Logiche a 8 bit
(seconda parte)
Istruzioni Aritmetiche a 16 bit
Istruzioni di controllo della CPU
Istruzioni di Salto (Jump)
Istruzioni di Chiamata e Ritorno da sottoprogrammi (Call e Return)
Istruzioni di Rotazione e di Scalamento
(prima parte)
Istruzioni di Rotazione e di Scalamento
(seconda parte)
Istruzioni di manipolazione del Bit
Istruzioni di Ingresso / Uscita (Input / Output)
Elenco in ordine alfabetico delle istruzioni DMC8
Elenco in ordine numerico delle istruzioni DMC8
Codice ASCII (7 bit)
Caratteri ASCII Non Stampabili
Caratteri ASCII Stampabili

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

Introduzione ai Sistemi a Microprocessore


Il microprocessore uno dei dispositivi pi utilizzati in elettronica digitale. Comprende le parti
fondamentali di un calcolatore numerico, integrate su di un singolo circuito integrato. La sua
realizzazione stata resa possibile dallo sviluppo delle tecnologie di integrazione degli anni 70
(LSI, VLSI) che, a costi modesti, hanno permesso la realizzazione di circuiti integrati molto
piccoli (qualche mm di lato) ma, al contempo, adeguatamente complessi. Attualmente, a
seconda del tipo, un microprocessore pu essere costituito da un numero di transistori
compreso tra il centinaio di migliaia e alcuni milioni, integrati su di un unico chip (scheggia) di
silicio, o altro materiale semiconduttore.
Microprocessore (P') e microcalcolatore (C') non sono la stessa cosa. Semplicemente, il
microprocessore lelemento centrale di un microcalcolatore. Questultimo infatti identifica un
sistema completo che, come vedremo nel seguito, comprende oltre al microprocessore altri
dispositivi: la memoria, i circuiti di ingresso/uscita dei dati, e altro. Un Personal Computer, ad
esempio, un microcalcolatore.
Quando su di in un singolo dispositivo troviamo integrati tutti i dispositivi di un microcalcolatore,
si parla di microcalcolatore single-chip. Un particolare tipo di microcalcolatore su singolo chip
il microcontrollore. Un microcontrollore, come dice il nome, progettato per applicazioni di
controllo. Oltre agli elementi base di tutti i microcalcolatori, vi troviamo integrati anche dispositivi
di ingresso/uscita specializzati, appositamente progettati per il controllo di impianti industriali e/o
sistemi complessi. A livello della vita di tutti i giorni, ad esempio, troviamo i microcontrollori
impiegati nei televisori, nei videoregistratori, nei lettori di compact disk
Un microcalcolatore inserito allinterno di un sistema pi complesso chiamato embedded. In
una applicazione embedded lutente vede e usa lintero sistema (per esempio la propria
autovettura) senza percepire direttamente la presenza di uno o pi microcalcolatori al suo
interno.
Un altro tipo di microcalcolatore specializzato il processore digitale di segnali (DSP, Digital
Signal Processor), appositamente progettato e ottimizzato per il trattamento, con tecniche
digitali, di segnali. Si pensi al trattamento di segnali audio nei sistemi multimediali, come ad
esempio nelle schede audio dei personal computer, nei lettori MP3, o negli effetti speciali
utilizzati nel settore della produzione musicale o nella cinematografia.
Un generico calcolatore digitale adempie alle seguenti funzioni:

acquisisce dati dal "mondo esterno";


li memorizza;
li elabora, producendo dei risultati;
interviene nei riguardi del mondo esterno in base ai risultati ottenuti.

Si pensi ad esempio ad un microcalcolatore impiegato come sistema di controllo di un impianto


industriale. In questo caso il mondo esterno limpianto; i dati sono acquisiti dal calcolatore
mediante opportuni sensori e/o trasduttori collocati nellimpianto stesso (sensori di velocit, di
pressione, di temperatura; contapezzi); dopo la memorizzazione e lelaborazione dei dati, in
base ai risultati ottenuti il calcolatore interverr sullimpianto tramite specifici attuatori (motori,
elettromagneti, pistoni idraulici, elettrovalvole, elettrofreni).
Anche un sistema progettato come macchina a stati finiti (MSF) pu adempiere a queste
funzioni, ma un sistema di controllo realizzato a microprocessore presenta molti vantaggi,
consentendo potenzialit e flessibilit di gran lunga maggiori.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

1-1

La differenza pi importante tra la soluzione con MSF e quella con C consiste nel modo in cui
il progettista definisce la sequenza delle operazioni che il sistema deve compiere:

Nella soluzione con MSF la sequenza deve essere rigorosamente predefinita dal
progettista; la MSF specificatamente dedicata alla particolare applicazione. Il suo
algoritmo preveder una ben precisa evoluzione degli stati, non modificabile a posteriori se
non riprogettando da capo la macchina, poich la sua funzionalit dipende dal particolare
collegamento dei dispositivi logici che lo compongono (si parla spesso di sistema cablato,
che deriva dall'inglese "cabled", ossia collegato mediante fili).
Nella soluzione con microcalcolatore, invece, le sequenze di operazioni da compiere sono
predisposte dal progettista attraverso limpostazione di un programma, scritto in un
opportuno linguaggio di programmazione. In questi sistemi si distingue tra hardware
(letteralmente ferramenta, ossia il sistema fisico composto di circuiti elettronici) e software
(il programma che ne specializza il funzionamento). Larchitettura del sistema concepita in
modo da rendere possibile modifiche alla sequenza delle operazioni da svolgere senza
modificare i circuiti che le svolgono, ma soltanto il programma (si parla di sistema
programmato).

Un vantaggio offerto dai microcalcolatori deriva proprio dalla loro architettura di tipo generale e
modulare, che pu essere adattata alle particolari applicazioni per mezzo di una opportuna
scelta dei dispositivi che lo compongono e alla scrittura degli appositi programmi.
Sovente lo stesso hardware pu essere utilizzato in applicazioni diverse: pu essere sufficiente,
infatti, cambiare solo il programma che ne specializza il funzionamento.
La modularit e la standardizzazione delle architetture permettono di mantenere i costi di
progetto relativamente bassi, specie per i sistemi complessi, in quanto il progettista riutilizza
interamente, in tutti i progetti di cui incaricato, le stesse competenze.

1.1

Elementi fondamentali di un generico calcolatore digitale


La caratteristica peculiare di un generico calcolatore digitale la capacit di eseguire in
sequenza rigorosa, e in tempi relativamente brevi, liste di istruzioni. Una lista di istruzioni
chiamata programma e viene eseguita grazie alla particolare struttura interna del calcolatore,
che nasce specificatamente per eseguire istruzioni.
Una istruzione un ordine impartito alla macchina, ed identifica una particolare e circoscritta
sequenza di operazioni elementari che la macchina eseguir. Un dato calcolatore progettato
per eseguire un certo insieme finito di istruzioni, e solo quelle.
Ad esempio, alcune istruzioni ordinano di copiare un dato da un registro ad un altro, altre di
eseguire una somma, oppure di incrementare un numero, ecc.
L'architettura pi usata nella costruzione degli attuali calcolatori quella di Von Neumann (1)
che, in sintesi, si basa sui seguenti concetti fondamentali:
I dati e i programmi condividono lo stesso sistema di memoria;
presente una sola unit di elaborazione;
eseguita una sola istruzione per volta.
L'architettura di Von Neumann "funziona" dal 1945: questa impostazione, pensata soprattutto in
funzione della massima semplicit circuitale, e forse proprio per questo, a livello commerciale
non stata ancora soppiantata da altre, anche se i progressi della scienza dei calcolatori hanno
consentito di arrivare ai cosiddetti supercomputer e alle macchine parallele.

Johann Ludwig Von Neumann (1903-1957), matematico e scienziato di origine tedesca, docente di
fisica matematica alluniversit di Princeton (USA), ove realizz nel 1945 lEDVAC (Electronic Discrete
Variable Automatic Computer).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

1-2

Da un punto di vista logico, un calcolatore


numerico di questo tipo pu essere
scomposto in tre blocchi (Fig. 1.1):

LUnit di Memoria (MEM, Memory);


LUnit di Ingresso/Uscita
(I/O, Input/Output).
LUnit Centrale di Elaborazione
(CPU, Central Processing Unit);

In estrema sintesi, i tre moduli svolgono le


seguenti funzioni:

La Memoria contiene sia i dati, su cui il


calcolatore lavora, sia i programmi che
agiscono sui dati stessi e sul mondo
esterno;
Lunit di Ingresso/Uscita consente alla
Fig.1.1: Schema logico di un calcolatore digitale
macchina di collegarsi al mondo
esterno;
La CPU ha il compito di reperire nella memoria ed eseguire, una per una, le istruzioni che
compongo il programma; la CPU, inoltre, legge e scrive dati nella memoria e dialoga,
attraverso lunit di Ingresso/Uscita, con il mondo esterno.

La CPU gioca un ruolo fondamentale: , insieme, attore principale e regista del sistema.
Lautore del copione (il programma) il progettista. Lintero sistema una sorta di teatro in cui
i singoli attori agiscono rispettando rigorosamente lordine imposto dalla sequenza delle
istruzioni del programma, senza svolgere nulla di autonomo che non derivi dalla esecuzione di
una istruzione.
Fin dal primo momento (cio da quando il calcolatore viene acceso), la CPU preleva in memoria
una istruzione e la esegue, per poi tornare in memoria a prelevare la successiva istruzione ed
eseguire anche quella, e cos via in ciclo infinito.

1.1.1

Considerazioni sulla esecuzione delle istruzioni


Oggi possiamo osservare microcalcolatori potentissimi in grado di eseguire funzioni impensabili
solo fino a qualche anno fa (si pensi ai video-giochi delle ultime generazioni). Da questa
semplice osservazione potremmo pensare che le attuali CPU siano in grado di eseguire
istruzioni potentissime, ma in generale non cos.
Nonostante le apparenze, le singole istruzioni direttamente eseguibili da una CPU permettono
di eseguire compiti piuttosto elementari. Ci che rende il microcalcolatore in grado di eseguire
cos bene compiti come quelli sopra accennati la sua velocit: le funzioni complesse saranno
ottenute eseguendo in modo velocissimo programmi composti, in realt, di migliaia di istruzioni
elementari.
In generale, lesecuzione di una istruzione comporta semplicemente il trasferimento dei dati
dalla memoria (o dai dispositivi di ingresso) nella CPU, la loro elaborazione (somma,
sottrazione, confronto) e il trasferimento del risultato nella memoria (o nei dispositivi di
uscita).
Nel seguito si potr notare che la maggior parte del tempo (il cosiddetto tempo macchina)
speso dalla CPU nel leggere istruzioni e nel trasferire dati da una parte all'altra; nonostante
lelevata velocit complessiva di un sistema a microcalcolatore, il tempo effettivamente
impiegato per lo svolgimento dei singoli calcoli solo una piccola parte del tempo totale!
Questa osservazione sembrerebbe sminuire le possibilit dei microcalcolatori, ma occorre
subito notare che, per i sistemi ad elevata complessit, la flessibilit e le potenzialit di un
sistema programmabile restano ineguagliabili.
Infatti, se progettassimo una (o pi) MSF per ottenere lo stesso sistema, questo risulterebbe
molto pi veloce (a pari tecnologia e a pari frequenza di clock), ma sarebbe anche un ingestibile
e costosissimo mostro di complessit. Per cui, nella stragrande maggioranza dei casi, si opta
per una architettura centrata su di un microcalcolatore.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

1-3

In quei casi in cui il fattore tempo dovesse risultare prioritario, in sede di definizione della
architettura complessiva del sistema i progettisti ne individueranno gli elementi critici e
provvederanno a separare il trattamento di quei segnali che necessitano di velocit dal resto
della elaborazione. Solo questi elementi critici saranno quindi progettati localmente come
veloci MSF dedicate, ma il sistema nel suo complesso continuer ad avere al centro il
microcalcolatore.

1.2

Larchitettura a BUS comune


Un microcalcolatore basato sui concetti di Von Neumann normalmente organizzato intorno ad
un unico BUS comune (Fig. 1.2). Un BUS un insieme di fili collegato in parallelo tra le varie
unit componenti il sistema. Il suo nome deriva dallomonimo mezzo di trasporto: in effetti
tramite questo insieme di fili che linformazione viene trasportata da una unit allaltra. La
scelta
di
questo
tipo
di
collegamento

dettata
principalmente da considerazioni
di tipo economico e di praticit.
Nella figura si riconoscono i tre
blocchi fondamentali discussi in
precedenza: la comunicazione
tra di questi avviene utilizzando il
fascio di fili in comune del BUS.
Una sola unit alla volta pu
impadronirsi di questi fili per
Fig.1.2: Struttura a BUS di un microcalcolatore
inviare informazioni sul BUS,
mentre (potenzialmente) tutti i
blocchi connessi possono riceverli in contemporanea. Lunit che in un dato momento trasmette
chiamata talker; chi riceve listener. Lunit che gestisce chi pu o non pu appropriarsi dei fili
del bus in un dato momento denominata master (o arbiter), mentre le altre, che obbediscono,
sono chiamate slave. Anche se esistono sistemi multi-master (come i personal computer
multiprocessore, solo per citare un esempio), nel nostro corso esamineremo soltanto sistemi pi
semplici, aventi la CPU come unico master.
Una osservazione sullefficienza del collegamento a BUS. Ogni sotto-unit del sistema si
collega alle altre mediante lo stesso insieme di fili. Il BUS assume quindi la caratteristica di
risorsa condivisa. evidente che la condivisione dello stesso fascio di fili tra tutti i dispositivi
presenti e una limitazione funzionale: se due sotto-unit in un certo istante dialogano tra di
loro, di fatto occupano il BUS, impedendone luso alle altre sotto-unit presenti nel sistema.
Se potessimo collegare tra loro le singole unit mediante collegamenti riservati, otterremmo
potenzialmente un sistema molto pi veloce (sarebbe un sistema a stella e non pi a BUS).
Tuttavia, per un microcalcolatore basato sui concetti di Van Neumann questa limitazione non
grave, dal momento che sar eseguita una sola operazione alla volta.
Inoltre, un collegamento di tipo BUS di gran lunga pi economico che un collegamento
stellato, che richiederebbe molti pi fili per le interconnessioni dedicate.
Infine, un sistema a BUS pi osservabile di un sistema con collegamenti a stella: collegando
un opportuno strumento diagnostico sui fili del BUS potremo osservare tutto quanto viene
scambiato tra i vari moduli, permettendo una ricerca guasti e/o malfunzionamenti
ragionevolmente semplice.
Per comodit di trattazione, scendiamo ora in maggior dettaglio nella suddivisione dei blocchi
funzionali che compongono il sistema (Fig.1.3).
Lasciamo per ora in evidenza la CPU come un blocco unico (master del sistema), e
suddividiamo invece la memoria in due sotto-unit: la RAM (memoria di lettura e scrittura) e la
ROM (memoria di sola lettura), che discuteremo nel capitolo successivo.
Suddividiamo anche il sistema di I/O in vari dispositivi, che immagineremo ciascuno
specializzato per ogni particolare collegamento con il mondo esterno di cui il nostro (generico)
sistema avr bisogno.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

1-4

Osservando la figura, si nota anche la suddivisione del fascio di fili del BUS in tre sotto-insiemi
di collegamenti:

Il Bus dei DATI (Data Bus): consente il trasporto dellinformazione vera e propria (dati e
istruzioni) da e verso i vari dispositivi; dal momento che i dati possono essere trasferiti in
tutte le direzioni, lo si definisce come collegamento bidirezionale;

Il Bus degli INDIRIZZI (Address Bus): come vedremo, consente alla CPU di selezionare il
dispositivo corrente con il quale scambiare i dati di cui sopra. Poich la CPU lunico
master del nostro sistema, gli indirizzi saranno generati soltanto dalla CPU e ricevuti da
tutti gli altri elementi (vedi, nella figura, la direzione delle frecce);

Il Bus dei CONTROLLI: collegamenti di varia natura, anche funzionalmente molto diversi
tra di loro, ma necessari per il controllo dellintero sistema e per la gestione (arbitraggio)
dello scambio di informazioni sugli altri due sotto-bus.

Fig.1.3: Architettura a BUS

La CPU, master del sistema, gestisce lo scambio di informazioni pilotando opportuni segnali sul
Bus dei Controlli ma, soprattutto, definendo il dispositivo con il quale dialogare in un dato
momento, mediante il suo Indirizzo. Tutti i dispositivi presenti nel sistema possiedono un
particolare e univoco indirizzo, rappresentato da un numero di identificazione.
Supponiamo che la CPU necessiti di trasmettere un dato al dispositivo di uscita di indirizzo
<n>. La CPU invia lindirizzo <n> allintero sistema, tramite il Bus degli Indirizzi. Tutti i dispositivi
sono allascolto, ma soltanto uno riconoscer il proprio indirizzo, e solo questo dispositivo
attiver i suoi circuiti in modo da mettersi in grado di ricevere il dato. A questo punto, la CPU
trasmetter il dato sul Bus dei Dati, che sar acquisito soltanto dal dispositivo attivo. Tutto
questo avviene, naturalmente, con il supporto dei segnali di controllo e temporizzazione del Bus
dei Controlli.
Allopposto, supponiamo ora che la CPU voglia ricevere un dato da un dispositivo di ingresso
di indirizzo <m>. Anche in questo caso la CPU invia lindirizzo <m> allintero sistema, tramite il
Bus degli Indirizzi. Soltanto un dispositivo riconoscer l indirizzo <m>, e solo questo dispositivo
attiver i suoi circuiti in modo da mettersi in grado di inviare il dato. Ottenuto questo, la CPU si
mette in attesa del dato, che il dispositivo attivo invier tramite il Bus dei Dati. Anche in questo
caso, il supporto dei segnali del Bus dei Controlli fondamentale affinch le operazioni si
svolgano nella giusta sequenza.
Le memorie, come vedremo nel prossimo capitolo, sono internamente suddivise in locazioni. Il
criterio dellindirizzo si applica ad ogni singola locazione, per cui se, ad esempio, nel nostro
sistema abbiamo 65.536 (216) locazioni di memoria, ciascuna sar identificata da un indirizzo
(da 0 a 65.535). La CPU acceder, sia in scrittura che in lettura, ad una sola locazione di
memoria alla volta, specificando sul Bus degli Indirizzi il particolare indirizzo della locazione,
esattamente come se ciascuna locazione di memoria fosse un dispositivo diverso: quanto
esemplificato qui sopra per i dispositivi di ingresso e uscita si pu ripetere per le singole
locazioni di memoria.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

1-5

Le memorie
Nel capitolo precedente abbiamo visto che in un microcalcolatore necessario un supporto
fisico per la memorizzazione dei dati e dei programmi. Durante lesecuzione di un
programma il microcalcolatore utilizza i dati presenti nella memoria, produce dei risultati
intermedi, e infine i risultati finali. La memoria risulta indispensabile per memorizzare, pi o
meno temporaneamente, i dati e i risultati.
Per fare un esempio, quando scrivete un programma in linguaggi ad alto livello come il C, il
C++, il Pascal, il Java utilizzate delle variabili per mantenere i dati e i risultati dei calcoli: da
un punto di vista fisico, durante lesecuzione del programma, le variabili coincideranno con
opportune locazioni di memoria disponibili nel microcalcolatore.
Il microcalcolatore necessita di una memoria adeguatamente veloce, ossia rapidamente
accessibile locazione per locazione attraverso il bus. Per questo motivo le memorie che si
affacciano direttamente al bus sono memorie realizzate a stato solido.
Esistono memorie di tipo ROM (Read Only Memory ossia Memorie a Sola Lettura) e altre di
tipo RAM (Random Access Memory ossia Memorie ad Accesso Arbitrario, scrivibili e
leggibili). Poco pi avanti rivedremo meglio la classificazione delle memorie; per il momento ci
concentriamo sulle RAM, in particolare del tipo pi semplice: le RAM statiche, che sono le pi
adatte per comprendere i concetti generali.
Spesso programmi, dati e risultati sono memorizzati anche su dischi magnetici, su dischi
ottici o altri dispositivi, al fine di garantire una archiviazione duratura delle informazioni. Nella
architettura dei microcalcolatori, questi dispositivi di memorizzazione (definiti in generale come
Memorie di Massa) non fanno parte della memoria direttamente affacciata sul bus, ma sono
connessi tramite opportuni dispositivi di Ingresso/Uscita (Controllori di Disco, di Nastro). Da
un punto di vista architetturale, cio, sono visti come sistemi di archiviazione esterni al mondo
che si affaccia al bus.

2.1

Le RAM: concetti introduttivi


L'elemento base di una RAM statica il Flip-Flop D-Latch. Una RAM statica ne contiene
migliaia su di un unico chip (ad esempio 32.768, oppure 262.144, o pi). Come possibile
gestire in modo semplice ed ordinato una tale mole di informazioni elementari? Gli aspetti base
della organizzazione interna si possono schematizzate nella Fig.2.1:
1. I singoli bit della memoria sono
raggruppati in locazioni (sinonimi:
celle, parole, words), costituite da un
certo numero di flip-flop (nella figura la
locazione da 8 bit);
2. I bit costituenti la locazione non sono
scrivibili o leggibili separatamente tra
di loro, ma sempre insieme (la
locazione indivisibile);
3. Le migliaia di locazioni presenti nello
stesso circuito di memoria si
Fig.2.1: Concetti di Locazione ed Indirizzo
distinguono tramite un indirizzo: sono
tutte numerate, da zero in avanti;
4. Le locazioni possono essere scritte o lette una sola alla volta: tra le tante, una sola
locazione sar di volta in volta disponibile allo scambio dei dati con l'esterno, quella
indirizzata.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-1

Un circuito di memoria viene venduto dal costruttore definendone il cosiddetto taglio


(dimensione) e la larghezza che, rispettivamente, indicano il numero di locazioni contenute e il
numero di bit di ognuna. Per esempio, un circuito di memoria da 32K x 8 (si legge: 32 kappa
per 8) costituito da
un insieme di 32.768
locazioni da 8 bit
ciascuna.
Altri esempi possono
essere: 16K x 8, 32K
x 4, 128K x 8, ecc.

Fig.2.2: Generico dispositivo di memoria RAM statica

Per avere un idea


concreta di come si
presenta un generico
dispositivo integrato di
memoria di tipo RAM,
nella Fig.2.2 sono
riportate le sue usuali
terminazioni, le cui
funzioni sono descritte
nella tabella qui sotto.

Indirizzi. In ingresso al chip, ossia gli n fili necessari per selezionare una
tra le 2n locazioni di memoria che il chip contiene;
Dati. Gli m fili necessari per trasferire i bit di dato da e verso la memoria;
Dm-1D0
sono di tipo 3-state bidirezionale, in numero pari ai bit di una locazione;
Selezione del chip. Un controllo che permette di attivare la funzione
Chip Select
delll'intero chip: se non asserito, TUTTI gli altri segnali sono ignorati;
Output Enable Abilitazione della lettura. Un controllo che, quando asserito, permette la
lettura dei dati memorizzati nella cella indirizzata (abilita i buffer 3-state);
Comando di scrittura. Un controllo che permette la scrittura dei dati nella
Write Enable
cella selezionata. I dati devono ovviamente provenire dall'esterno.

An-1A0

Vediamo adesso, per sommi capi, con quali modalit la CPU, master di un generico sistema,
utilizza un chip di memoria (Fig.2.3). La CPU invia per prima cosa al circuito di memoria
l'indirizzo della locazione di suo
interesse, tramite il bus degli indirizzi.
Trascorso un certo tempo (il tempo di
accesso),
tale
locazione
sar
disponibile alle terminazioni del chip.
La CPU a questo punto potr
effettuarvi una "scrittura" (inserimento
informazioni), oppure una "lettura"
(recupero informazioni). Tutte queste
operazioni vengono eseguite dalla
CPU attivando gli opportuni segnali di
Fig.2.3: Criterio generale di utilizzo della memoria
controllo in ingresso al circuito di
memoria, come vedremo tra breve.

2.2

La struttura interna: la singola locazione


Ripassiamo il comportamento di un singolo Flip-Flop di tipo D-Latch con Enable (Fig.2.4). Se il
segnale di controllo EN attivo basso, il Flip-Flop trasparente, ossia l'uscita DO ricopia
l'ingresso DI. Se EN viene portato alto, sull'uscita DO rimane memorizzata l'informazione che
era stata presentata per ultima al suo ingresso. Utilizzando il D-Latch come circuito di memoria
elementare da 1 bit, la sequenza delle operazioni risulter la seguente (Fig.2.4):

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-2

1. Si presenta un valore ( o zero o uno)


all'ingresso DI;
2. Si porta basso per un breve periodo di
tempo il controllo EN , per cui il nuovo valore
si presenter all'uscita DO del flip-flop;
3. Si riporta alto EN : con il fronte di salita viene
memorizzato il nuovo dato;
4. Da ora in avanti, per EN alto, l'ingresso
diventa indifferente: nessuna variazione si
osserver sull'uscita DO.
Questo circuito in grado di memorizzare un
singolo bit: normalmente necessario
memorizzare dei dati pi complessi, come ad
esempio un numero intero compreso nel range
0..255. In questo caso sono necessari 8 bit per
rappresentarlo, e di conseguenza si deve
utilizzare una memoria che disponga di
altrettanti bit per locazione.

In Fig.2.5 osserviamo un registro parallelo


(PIPO) costituito da 8 flip-flop di tipo D-Latch,
utilizzato come locazione di memoria. Ciascun
bit incaricato di memorizzare una delle cifre
binarie di cui composto il numero. Come in
tutti i registri, gli EN sono stati collegati insieme:
in questo modo un unico segnale, che per
l'occasione ribattezziamo WRITE , consentir di
scrivere l'intero numero presente sulle linee
DI0..7 in tutti i flip-flop, e presentarlo sulle linee di
uscita DO0..7.
Nel diagramma temporale di Fig.2.5
rappresentata la scrittura di un dato, simile a
quella vista per il singolo flip-flop, ma applicata
al nostro registro da 8 bit.
Osserviamo che:
se il segnale di controllo WRITE basso
(attivo), il circuito "trasparente", ossia un
cambiamento dell'informazione presentata
agli ingressi DI0..7 si riflette immediatamente
sulle uscite DO0..7; (intervalli 1 e 3);
Nel momento in cui il segnale di controllo
WRITE ritorna al livello inattivo, l'ultima
informazione presente agli ingressi DI0..7
viene memorizzata nei flip-flop e mantenuta
alle uscite DO0..7: se gli ingressi cambiano,
non si produce cambiamento sulle uscite;
l'informazione mantenuta se il segnale di
controllo WRITE alto (intervalli 2 e 4).

Fig.2.4: Memorizzazione di un bit (FF D-Latch)

Fig.2.5: Locazione vista come registro parallelo da


8 bit, di tipo D-Latch

Nel diagramma temporale stata utilizzata una simbologia sintetica per indicare lo stato delle
linee DI0..7 e DO0..7: sono state messe in evidenza soltanto le transizioni globali dei livelli logici e
non il valore assunto individualmente dai singoli fili. I numeri ivi riportati rappresentano il valore
codificato, in questo caso espresso in decimale, che ciascun insieme di fili assume, nei vari
intervalli di tempo.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-3

2.3

La struttura interna: il Bus Dati


Nel chip presente un bus dati interno, che permette il collegamento in scrittura ed in lettura
di tutte le locazioni. Per ragioni didattiche, immaginiamo per il momento di semplificare la sua
struttura cos come appare nella Fig.2.6.
Mettiamo in evidenza il filo di scrittura che ciascuna locazione possiede: in situazione di riposo,
tutti questi segnali di scrittura vengono lasciati inattivi, ossia ogni cella mantiene memorizzato il
suo contenuto che vi stato precedentemente registrato.
Quando si vuole scrivere
un
dato,
dobbiamo
dapprima decidere in
quale cella memorizzarlo,
supponiamo la <i>esima.
Imponiamo quindi il dato
da scrivere sul Bus
interno e attiviamo la
scrittura nella locazione
prescelta <i>, inviando un
impulso
sul
rispettivo
segnale
WRITE i
.
Ovviamente, soltanto tale
locazione ricopier al suo
interno il dato binario
presente sul bus.
Ogni registro possiede
anche un suo privato e
indipendente filo di lettura,
Fig.2.6: Il Bus Dati interno e le locazioni, connesse in lettura o in scrittura
che controlla un suo
privato buffer 3-state. Quando dovremo rileggere il dato prima scritto nella locazione <i>, ne
attiveremo il relativo buffer 3-state con il segnale READ i , ed il dato sar presentato sul bus. La
presenza dei buffer 3-state ovviamente dovuta alla necessit di accedere ai fili comuni del bus
senza generare conflitti elettrici.

2.4

La struttura interna: la decodifica dell'indirizzo


Per semplificare i collegamenti
all'interno del chip, si utilizzano due
soli fili di WRITE e di READ, che
vengono portati a tutte le locazioni.
Una opportuna logica combinatoria
permette di abilitare i segnali
READ i e WRITE i specifici per la
locazione di interesse, tramite il
controllo di una selezione SEL i
(Fig.2.7).
Per
selezionare
una
ben
determinata locazione, la CPU
fornisce al chip di memoria un
Fig.2.7: Segnali READ e WRITE e selezione della locazione
indirizzo numerico codificato in
binario. La memoria deve dunque
possedere internamente un circuito di decodifica, in grado di attivare la specifica linea SEL i
corrispondente all'indirizzo binario fornito dalla CPU. Ma questo circuito di decodifica deve
essere pi complesso di quelli che conosciamo: infatti la normale decodifica di tipo lineare non
sarebbe realizzabile, basti pensare alle migliaia di prodotti logici che dovrebbe avere, uno per
ogni locazione da attivare.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-4

I progettisti hanno fatto ricorso alla tecnica della Selezione a Matrice (Fig.2.8), che consiste
nell'utilizzare due decodificatori distinti, che selezionano per righe e colonne la matrice di celle.

da
notare
che
ciascun
decodificatore riceve in ingresso
solo una parte dei fili di indirizzo:
nell'esempio in figura, i bit meno
significativi A0..Aq-1 selezionano la
colonna, mentre gli altri Aq..An-1
attivano le righe.
In Fig.2.9 riportato un esempio,
relativo
ad
una
memoria
11
volutamente piccola, da 2 (2048)
locazioni. Un chip di questo taglio
possiede 11 fili di indirizzo A0..A10.
I fili di indirizzo A0..A5 risultano
connessi al decoder di colonna, gli
altri A6..A10 a quello di riga,
formando una matrice 32 x 64.

Fig.2.8: Decodifica a matrice dellindirizzo

Fig.2.9: Esempio di selezione a matrice

Se in un determinato momento
l'indirizzo applicato al chip
quello riportato in figura, i
decodificatori attiveranno solo
la colonna 3 e la riga 16, e le
altre rimarranno a zero. Solo la
porta logica a quellincrocio
risulter attivata, e solo la
corrispondente locazione di
memoria sar abilitata a
ricevere i segnali di READ o di
WRITE; tutte le altre celle
risulteranno disabilitate.
Sul piano realizzativo, la
struttura a matrice consente di
posizionare ordinatamente, a
scacchiera, tutti i registri di cui
composta la memoria,
utilizzando in modo ottimale la
superficie del silicio su cui
realizzato il chip.

Nota: dallanalisi della struttura della memoria, dove ogni locazione raggiungibile tramite un indirizzo,
risulta evidente che non permesso un accesso contemporaneo a pi locazioni alla volta: delle migliaia
di celle sar disponibile sempre e soltanto una sola cella, quella selezionata. Esistono tuttavia dispositivi,
le cosiddette memorie "a doppia porta", in cui possibile fornire due indirizzi e selezionare
separatamente due locazioni.

2.5

Le connessioni del chip di memoria con lesterno


Dobbiamo infine esaminare come il bus interno risulti collegato con quello esterno al chip, che
sar poi quello del microprocessore. Nella figura 2.10 sono messi in evidenza, sulla sinistra in
basso, i segnali di controllo standard CS (Chip Select), WE (Write Enable), OE (Output
Enable) e, in alto a destra, i buffer 3-state bidirezionali che uniscono il bus dati interno con
quello esterno. Per focalizzare lattenzione sui soli segnali di controllo, nella figura omessa
tutta la parte relativa alla decodifica dell'indirizzo che abbiamo da poco considerato.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-5

I buffer 3-state sono presenti con la


duplice
funzione
di
separazione
funzionale tra interno ed esterno, e di
adattamento dei livelli elettrici dei segnali
logici.
Sono attivati, in modo esclusivo nelle
due direzioni, dai segnali interni di READ
e di WRITE che, come si pu osservare,
sono generati da una semplice rete
combinatoria.
Come si vede dallanalisi di questa, per
attivare la connessione, il segnale CS
deve essere basso (attivo); in caso
contrario entrambi i segnali READ e
WRITE non vengono attivati e di
conseguenza viene inibito laccesso al
bus interno della memoria.
Fig.2.10: Segnali di controllo e buffers bidirezionali

Nella tabella seguente riportata la tavola di verit della funzione dei segnali di controllo,
peraltro ricavabile esaminando la rete combinatoria della figura precedente.

CS
1
0
0
0
0

WE
x
1
0
1
0

OE
x
1
1
0
0

Funzione
Chip Inattivo, bus in Hi-Z
Chip Attivo, bus in Hi-Z
Scrittura
Lettura
Scrittura (Protezione)

Per poter scrivere nella cella selezionata, necessario attivare (portare bassi) sia il CS che il
WE , mentre per leggere si devono attivare il CS e l' OE . La rete combinatoria presenta inoltre
una protezione logica: viene impedita la situazione anomala di WE e OE attivati insieme,
privilegiando la scrittura.

2.6

Temporizzazioni delle RAM Statiche


Consideriamo, in questo paragrafo, le temporizzazioni a cui devono sottostare i vari segnali
coinvolti durante la scrittura e la lettura nelle locazioni di memoria. In Fig.2.11 rappresentato
un generico Ciclo di Lettura. Inizialmente lesterno (la CPU) fornisce alla RAM l'indirizzo della
locazione coinvolta. Poi, mantenendo il segnale WE alto, attiva i segnali CS e OE .
Dopo un certo tempo, chiamato
Tempo di Accesso (Access
Time),
all'uscita
del
chip
saranno
disponibili
i
dati
richiesti.
Il circuito esterno (la CPU) potr
quindi leggere i dati. Quando
questi sono stati acquisiti, e non
ci interessa pi mantenere i dati
all'uscita della RAM, lesterno
disattiva i segnali CS e OE ,
portandoli alti. A causa dei
ritardi interni, il chip manterr il
dato ancora valido per il
Fig.2.11: La RAM statica: il ciclo di lettura
cosiddetto
Tempo
di
Mantenimento (Hold Time).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-6

In Fig.2.12 descritto un
generico Ciclo di Scrittura, le
cui temporizzazioni sono un
poco pi critiche. Inizialmente,
come prima, lesterno (la CPU)
deve fornire alla RAM l'indirizzo
della locazione nella quale
vuole scrivere.
Poi, mantenendo il segnale OE
alto, lesterno deve attivare il
segnale CS . Nel frattempo
lesterno (la CPU) prepara sul
bus dei dati il valore che vuole
memorizzare nella locazione
Fig.2.12: La RAM statica: il ciclo di scrittura
specificata, per poi attivare il
segnale di scrittura WE , ma solo dopo che sia trascorso il Tempo di Accesso. Il segnale di
scrittura deve poi rimanere attivo per un tempo minimo (Width Time), affinch sia riconosciuto
correttamente. Sul fronte di salita del WE si ha finalmente la memorizzazione del dato nella
memoria, nella locazione selezionata. A causa dei ritardi interni, per, il dato dovr essere
mantenuto valido dal circuito esterno ancora per un breve tempo, chiamato anche qui Tempo di
Mantenimento. A questo punto lesterno pu disattivare anche il segnale CS .

2.7

Breve classificazione dei dispositivi di memoria


Come gi accennato, le memorie si possono classificare, da un punto di vista funzionale, in due
grandi categorie: le ROM e le RAM.

2.7.1

Le memorie di tipo ROM


R.O.M. significa Read Only Memory, ossia Memorie a sola lettura. Queste memorie sono
caratterizzate dalla persistenza della informazione in esse memorizzata, anche in mancanza
della tensione di alimentazione, ma anche dalla necessit di essere pre-programmate.
La pre-programmazione pu avvenire in diversi modi, e dipende dal particolare tipo di
dispositivo. Allinizio della loro storia, le ROM erano realizzate, gi programmate, direttamente
dal produttore di circuiti integrati (MASK ROM), naturalmente su specifiche del progettista del
sistema a microprocessore. Era una soluzione molto costosa, accettabile solo per grandi volumi
di produzione. Grazie al successo ottenuto dai microprocessori e alla necessit di abbassare i
costi, da quel momento lindustria ha cominciato a proporre via via soluzioni sempre pi versatili
ed economiche, aventi il vantaggio di poter essere programmate direttamente in laboratorio. Si
sono succeduti infatti dispositivi programmabili come le PROM (Programmable ROM), le
EPROM (Erasable Programmable ROM), le EEPROM (Electrically Erasable Programmable
ROM), le EAROM (Electrically Alterable Programmable ROM), ecc
Il tipo correntemente usato
costituito dalle FLASH, che
possono essere ri-programmate
nel circuito che le ospita, senza
doverle rimuovere. Anche se
scrivibili, le memorie di tipo
FLASH non possono essere
usate come RAM poich non
ammettono la scrittura di una
singola locazione, ma soltanto
per blocchi chiamati unit di
memoria. Devono il loro nome
tecnico-commerciale proprio al
fatto che possibile cancellare
Fig.2.13: Generico dispositivo di memoria ROM
e riscrivere il loro contenuto per

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-7

blocchi in una singola azione in un flash. Le troviamo, ad esempio, sulla piastra madre dei
personal computer.
Le connessioni logiche di un dispositivo di tipo ROM (vedi fig.2.13), da un punto di vista del
microprocessore, sono simili a quelle delle RAM statiche esaminate in precedenza (fig.2.2),
salvo che ovviamente non presente il segnale di scrittura (in realt, a seconda del tipo di
ROM, il filo di scrittura e altre terminazioni per la programmazione fuori circuito possono
fisicamente esistere ma, nelle ordinarie condizioni di lavoro, non sono a disposizione del
microprocessore e quindi, dal punto di vista funzionale, come se non ci fossero).
Dal punto di vista funzionale, per la connessione con il processore saranno importanti le
seguenti terminazioni (vedi fig.2.13).

Indirizzi. In ingresso al chip, ossia gli n fili necessari per selezionare una
tra le 2n locazioni di memoria che il chip contiene;
Dati. Gli m fili necessari per leggere i bit di dato dalla memoria; di tipo 3Dm-1D0
state, in numero pari ai bit di una locazione;
Selezione del chip. Un controllo che permette di attivare la funzione
Chip Select
delll'intero chip: se non asserito, gli altri segnali sono ignorati;
Output Enable Abilitazione della lettura. Un controllo che, quando asserito, permette la
lettura dei dati memorizzati nella cella indirizzata (abilita i buffer 3-state);
An-1A0

Nel seguito non daremo molta importanza al tipo di ROM che utilizzeremo virtualmente nei
nostri sistemi a microprocessore. A livello funzionale ci baster ricordare che, se da un lato la
ROM non pu essere scritta dal processore, sar invece da noi programmabile.
Siamo in grado di caricare nelle locazioni volute della ROM i programmi e i dati di nostro
interesse perch il progettista/programmatore dispone dellopportuno dispositivo di laboratorio
in grado di programmarla.

2.7.2

Le memorie di tipo RAM


R.A.M. significa Random Access Memory, ossia Memorie ad accesso arbitrario, o Memorie
di Lettura e Scrittura. Come gi accennato, da un punto di vista storico, devono il loro nome
alla necessit di distinguerle dalle memorie ad accesso sequenziale (i nastri e dischi magnetici,
e altro). In esse possibile accedere arbitrariamente alla informazione, in qualunque momento,
senza sottostare a precedenze o a sequenze di accesso (un nastro, invece, pu necessitare il
suo riavvolgimento da capo).
Oltre alle RAM statiche, che abbiamo esaminato in precedenza, esistono le RAM Dinamiche
(Dynamic Random Access Memory, o DRAM), che attualmente sono le pi usate nellindustria
dei computer. Tuttavia, ai fini di questo corso, non sar necessario approfondire il discorso sulle
RAM dinamiche poich, da un punto di vista funzionale, lutilizzo delle RAM statiche
ampiamente sufficiente ai fini della comprensione dei concetti di base sui sistemi a
microprocessore.
Per memorizzare i singoli bit di informazione, le DRAM utilizzano, al posto dei flip-flop, le
capacit proprie dei transistori MOS che le implementano. Tuttavia queste capacit sono molto
piccole e tendono a scaricarsi rapidamente, per cui un circuito di RAM dinamica necessita
di un "rinfresco" continuo delle informazioni memorizzate, operazione effettuata da un hardware
apposito. Non approfondiamo ulteriormente il discorso in quanto sarebbe necessario scendere
al livello della fisica dei componenti elettronici e delle tecniche di microelettronica.
Sono molto pi usate delle RAM statiche in quanto molto pi economiche (nel caso dei grossi
sistemi di memoria attualmente in uso nei personal computer, ad esempio), in quanto la singola
cella di memoria molto piccola e, a parit di area (e di costo) del chip, si riescono a realizzare
RAM molto pi capienti.
Nel corso degli anni, si sono succeduti vari tipi di RAM dinamiche, via via migliorate sia in
termini di velocit che di capienza, come le FPM-DRAM (Fast Page Mode DRAM), le EDODRAM (Extended Data Out - DRAM) e le attuali e molto veloci SDRAM (Synchronous Dynamic
Random Access Memory).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

2-8

Il microprocessore DMC8
Dal momento della loro comparsa, avvenuta nei primi anni 70, i microprocessori si sono
costantemente evoluti fino a raggiungere, oggi, velocit e potenzialit di calcolo molto elevate.
Ovviamente, cresciuta di pari passo anche la loro complessit architetturale. Questo significa
che, da un punto di vista didattico, pu non essere una buona scelta introdurre largomento
facendo riferimento ad un microprocessore commerciale delle ultime generazioni.
D'altro canto, se i primi microprocessori, pi semplici, sono didatticamente pi abbordabili,
anche vero che sono stati pensati in funzione della componentistica e delle tecnologie
disponibili allora, per cui spesso incorporano funzioni accessorie e dispositivi ormai superati.
Lapproccio didattico che questo corso vuole seguire ci porta alla necessit di disporre di un
microprocessore di complessit non elevata, paragonabile a quella dei primi dispositivi
comparsi sul mercato ma, al contempo, sfrondato di quegli elementi anacronistici che giocano a
sfavore della comprensibilit dellargomento.
Per questo motivo si pensato di re-inventare un microprocessore adeguato agli obiettivi di
questo corso, ed nato cos il DMC8.
Nel concepire il DMC8, per non allontanarci troppo dalla realt dei dispositivi commerciali, ci
siamo ispirati ad un microprocessore ad 8 bit esistente e tecnicamente (e storicamente)
rilevante: lo Z80-CPU. Questo fu introdotto nel 1976 dalla Zilog, come evoluzione del
precedente (e popolare) 8080 della Intel. Grazie alla compatibilit software con questo suo
predecessore, e alle sue migliorate caratteristiche hardware, si impose rapidamente in quegli
anni come uno standard di mercato. Ancora oggi la sua architettura ed il suo set di istruzioni
sopravvivono in alcuni microcontrollori. Inoltre, intere generazioni di progettisti sono cresciute
con il suo hardware ed il suo set di istruzioni.
Il DMC8 mantiene gran parte dellarchitettura interna dello Z80-CPU, escludendo alcuni
elementi obsoleti e poco significativi. Per chi conoscesse gi lo Z80-CPU, possiamo dire che
sono stati eliminati, ad esempio, i registri finalizzati alla gestione delle memorie dinamiche e il
banco di registri alternativi. Il set di istruzioni stato in larga parte mantenuto, con lesclusione
delle istruzioni relative alle parti eliminate dallarchitettura interna.
Il DMC8 attualmente non corrisponde ad un vero dispositivo fisico, ma soltanto ad un
dispositivo idealizzato, in grado di funzionare grazie ad un emulatore che gira su personal
computer. Lemulatore incluso nellambiente di apprendimento Deeds (Digital Electronic
Education and Design Suite), sviluppato presso il Gruppo ESNG del Dipartimento di Ingegneria
Biofisica ed Elettronica (Universit di Genova). Introdurremo lemulatore ed il suo uso pi
avanti, nel corso di questa trattazione.

3.1

Introduzione allarchitettura del DMC8


La dimensione di un microprocessore si misura sulla larghezza della sua unit di calcolo:
poich la sua unit di calcolo lavora in parallelo su 8 bit, il DMC8 , dunque, un
microprocessore ad 8 bit.
Linsieme delle istruzioni eseguibili dal DMC8 piuttosto vasto. Il DMC8 appartiene alla
categoria dei CISC (Complex Instruction Set Computer). Come dice il nome, un CISC
caratterizzato da un set di istruzioni molto vario, con istruzioni specializzate per molti tipi di

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-1

operazioni
diverse.
A
questa
CISC e RISC
categoria
di
processori
si
contrappongono i RISC (Reduced
Da un punto di vista storico occorre precisare che i
Instruction Set Computer).
primi computer sono nati di fatto come CISC, quando
Il set di istruzioni del DMC8
questa distinzione non esisteva ancora. I RISC sono
nati successivamente, con lo scopo di ottenere
caratterizzato da unampia e potente
processori dalla architettura pi ordinata ed efficiente,
scelta di modi di indirizzamento che,
ottimizzati su un numero di istruzioni contenuto ma
come vedremo, consistono nella
eseguibile molto velocemente. A tuttoggi la battaglia
capacit di reperire in vari modi i dati
tra le architetture RISC e CISC non ha ancora un
su cui lavorare.
vincitore. Alle eleganti migliorie architetturali dei RISC,
Nel set di istruzioni sono presenti
infatti, i produttori dei CISC hanno risposto con la
anche istruzioni specializzate per la
cosiddetta forza bruta, cio` aumentando in modo
gestione efficiente, a basso livello, dei
incredibile la frequenza di clock. I personal computer
dispositivi di ingresso/uscita.
compatibili IBM sono basati su processori CISC; i
personal di tipo Mac, invece, sono basati su RISC.
Il DMC8, per motivi didattici,
Nel mondo industriale si usano sia gli uni che gli altri; in
possiede una gestione semplificata
questo corso non approfondiremo lo studio delle
delle cosiddette "interruzioni" da parte
architetture RISC.
dei dispositivi di ingresso/uscita (che
sar discussa pi avanti).
Dal punto di vista della sua architettura, il DMC8 organizzato intorno ai seguenti blocchi (vedi
fig. 3.1):
Una
Unit
LogicoAritmetica (ALU) ad 8 bit,
in grado di eseguire le
operazioni di calcolo vero
e
proprio
(addizione,
sottrazione, and, or, ecc.).
Pu lavorare su dati aventi
formato di Bit, Nibble e
Byte, ma anche di Word a
16 bit (scomponendo il
lavoro da eseguire in due
operazioni
da
8
bit
ciascuna);
Un certo numero di
Registri, a 8 e a 16 bit,
per la memorizzazione di
Fig. 3.1: Schema funzionale interno del DMC8
dati ed indirizzi;
Alcuni Bus (a 8 e 16 bit)
per lo scambio di dati e indirizzi tra gli elementi interni;
Alcuni collegamenti con l'esterno del chip tramite bus dedicati. I bus ed i circuiti interni sono
disaccoppiati da quelli esterni tramite buffers. Il Bus dei Dati bidirezionale e composto da
8 linee, mentre il Bus degli Indirizzi unidirezionale (verso l'esterno) e formato da 16 linee.
Il Bus dei Controlli comprende sia linee in entrata che linee in uscita (che saranno
esaminate in seguito).
Disposti un poco dietro le quinte, sono da considerare inoltre i dispositivi che si osservano
sulla destra della figura, fondamentali per il funzionamento del processore:

Un Registro dellIstruzione in cui viene caricato il codice dell'istruzione che deve essere
eseguita;
Un dispositivo di Decodifica del codice dell'istruzione presente nel registro di cui sopra;
Un dispositivo di Controllo e Temporizzazione del Sistema, detto anche Sequenziatore,
in sostanza una grossa macchina a stati finiti che genera tutti i segnali di controllo necessari
al funzionamento dei dispositivi interni e gestisce il Bus dei Controlli esterno.

Il cuore pulsante di un qualsiasi microprocessore rappresentato proprio dallinsieme


Registro dellIstruzione - Decodificatore - Sequenziatore, che di fatto costituisce il "motore
logico del microprocessore. Il suo compito principale di attivare gli elementi dellarchitettura
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-2

interna al fine di prelevare ed eseguire le istruzioni del programma. Il Sequenziatore


sincronizzato da un segnale di Clock esterno (per esempio 10 MHz) ed inizializzato da un
segnale di Reset.
In termini di occupazione di area del chip a semiconduttore, linsieme Registro dellIstruzione Decodificatore - Sequenziatore ne ricopre la parte pi grande ma, se dal punto di vista
realizzativo sicuramente la parte tecnicamente pi complessa e importante del
microprocessore, non lo ai fini della sua comprensione.
Infatti, come si vedr nel seguito, per ragioni didattiche presteremo pi attenzione agli
oggetti che compongono la scena (Registri, ALU), e alla loro importanza operativa (le
istruzioni), piuttosto che alla complessa e granulare mole di compiti svolti dal sequenziatore.
Non servir analizzare i dettagli delle singole operazioni elementari svolte internamente durante
lesecuzione delle istruzioni. Sar molto pi utile e formativo sapere cosa potranno eseguire
le istruzione disponibili, e in quanto tempo. Sar ancora pi utile imparare a mettere in
sequenza le istruzioni, al fine di comporre programmi in grado di svolgere ben precisi compiti.
Dopo i primi passi iniziali, in cui un minimo del funzionamento interno sar discusso,
utilizzeremo poi a scatola chiusa il microprocessore, imparando ad usarlo attraverso
opportune tecniche di programmazione.

3.2

Gli elementi dellarchitettura interna del DMC8


In Fig. 3.2 riportato uno schema a blocchi pi dettagliato degli elementi di calcolo e dei registri
interni al microprocessore. Il DMC8 possiede un certo numero di registri: alcuni specializzati,
altri di uso pi generale. Nel seguito riportiamo una breve descrizione di questi elementi e della
loro interconnessione: saranno considerati pi in dettaglio pi avanti, quando si esaminer da
vicino il funzionamento delle singole istruzioni.

Fig. 3.2: Registri ed elementi di calcolo del DMC8


Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-3

PC

16 bit

Program Counter

In altri contesti chiamato anche Instruction Pointer. Questo registro a 16 bit contiene
lindirizzo che punta allistruzione da eseguire. Come vedremo, le istruzioni risiedono nella
memoria, e questo registro utilizzato dal processore per indirizzare la memoria, mediante il
bus degli indirizzi, al fine di prendere la prossima istruzione da eseguire.
Il termine Contatore del Programma dovuto al fatto che, dopo il prelievo del codice di una
istruzione, lindirizzo presente nel registro automaticamente incrementato di uno, al fine di
predisporre lindirizzo per il prossimo prelievo. Il termine Puntatore all'Istruzione, invece, associa
al registro il concetto di puntatore. Nei linguaggi di programmazione, un puntatore una variabile
(in questo caso contenuta in un registro) che contiene lindirizzo di un oggetto (per esempio unaltra
variabile o, nel nostro caso, listruzione da eseguire).

SP

16 bit

Stack Pointer

Letteralmente Puntatore alla Catasta". Discuteremo in dettaglio la funzione di questo


importante registro pi avanti. Per il momento basti dire che questo registro contiene lindirizzo
della locazione in cima ad una catasta (o pila) di locazioni di memoria RAM chiamata,
appunto, Stack.
La funzione dello Stack e dello Stack Pointer legata principalmente alla esecuzione dei cosiddetti
"SottoProgrammi" e alla gestione delle "Interruzioni", che incontreremo pi avanti. La catasta una
struttura dati nella quale le informazioni sono immagazzinate una sullaltra (un po come se
riponessimo uno sullaltro dei libri su di una scrivania). Una volta impilate le informazioni, saremo
in grado di recuperarle solo svuotando la pila un elemento alla volta (in ordine inverso rispetto a
quello di riempimento). Si parla di gestione LIFO ("Last In, First Out"), ossia Lultimo che entrato
il primo ad uscire.

IX
IY

16 bit
16 bit

Index Register X
Index Register Y

Letteralmente Registri Indice IX e IY. Sono registri specializzati, utilizzati per lindirizzamento
in memoria di vettori e altre strutture dati. Si chiamano cos perch permettono di indicizzare
lindirizzamento in memoria, facilitando laccesso alle strutture dati. Saranno esaminati pi
avanti, in relazione ai cosiddetti modi di indirizzamento.

8 bit

Accumulator Register A

Il registro Accumulatore A definito anche come Registro Privilegiato", perch interviene per
default in moltissime operazioni eseguite dalla CPU. Si chiama cos per ragioni storiche, perch
per alcuni tipi di elaborazione consente di "accumulare" via via i risultati intermedi senza doverli
riporre tutte le volte in memoria. Nel nostro processore, il registro pi importante per
l'elaborazione dati.

B
C
D
E
H
L

8 bit
8 bit
8 bit
8 bit
8 bit
8 bit

B
C
D
E
H
L

Register
Register
Register
Register
Register
Register

Si tratta di registri di uso generale ad 8 bit, utilizzati per supportare e velocizzare lelaborazione
dati. Servono per memorizzare dati senza dovere accedere sempre alla memoria esterna
(operazione pi dispendiosa in termini di tempo).

In alternativa, questi registri possono essere anche usati a coppie, come 3 registri da 16 bit,
utilizzando i nomi simbolici BC, DE e HL.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-4

In questo caso, tali registri appaiono al programmatore nel modo seguente:

BC
DE
HL

16 bit
16 bit
16 bit

BC Register
DE Register
HL Register

Attenzione! I registri BC, DE, HL sono formalmente registri a 16 bit, ma non sono altri
registri: fisicamente si tratta sempre dei registri B, C, D, E, H e L, utilizzati in modo
accoppiato. Per esempio, possiamo caricare separatamente il numero B4h nel registro B e, subito
dopo, il numero F3h nel registro C. A questo punto, se utile, potremo formalmente riferirci al
registro a 16 bit BC, che conterr, quindi, il numero B4F3h.
I nomi H e L sono labbreviazione di High e Low. Infatti i registri H ed L, nella forma accoppiata
HL, sono utilizzati da molte istruzioni del processore per contenere un indirizzo di memoria (a 16
bit), pur rimanendo in grado di accedere separatamente alla parte alta e alla parte bassa.

8 bit

Flags Register

Il registro dei Flag (Segnalatori), chiamato anche Registro di Stato, non un vero registro, in
quanto costituito da un insieme di alcuni flip-flop tra loro non omogenei come significato,
raggruppati solo per comodit in un apparente unico registro da 8 bit, di cui sono utilizzati solo 6
bit. I Flag indicano lo stato del sistema di calcolo dopo l'esecuzione di una operazione aritmetica
o logica: ad esempio segnalano se c' stato riporto, oppure se il risultato delloperazione zero.
Qui di seguito descritta la posizione dei Flag nel registro e, sommariamente, logico di
ciascuno. Approfondiremo pi avanti lutilizzo dei Flag, che sono molto importanti per il
funzionamento del processore.
Bit 7

Bit 6

Bit 5

Bit 4

Bit 3

Bit 2

Bit 1

Bit 0

p/v N

Carry Flag
Memorizza il riporto dal bit pi significativo dell'accumulatore, nel caso di una operazione
di addizione, oppure il prestito nel caso di sottrazione (C=1 indica che avvenuto un
riporto o un prestito, C=0 no).

Zero Flag
Segnala che l'accumulatore si azzerato, dopo l'esecuzione di una operazione, (Z=1
indica che tutti i bit dell'accumulatore sono a zero, Z=0 indica che almeno uno non lo ).
Nel seguito vedremo, per, che non tutte le istruzioni agiranno su questo flag, come ci
potremmo aspettare. Alcune istruzioni, come quelle di trasferimento dati, non modificano
il valore di questo flag.

Sign Flag
Risulta uguale al bit pi significativo del risultato in accumulatore (infatti, nella aritmetica
in complemento a 2, S=0 indica il segno positivo del risultato di una operazione, S=1 il
segno negativo).

P/V

Parity/OverFlow Flag
Questo flag dal doppi nome (P oppure V) indica se c' stato overflow, qualora sia stata
eseguita un'operazione aritmetica tra numeri in complemento a 2 (V = 1), oppure, se
l'operazione eseguita stata di tipo logico, indica la parit del risultato (P = 1 = parit
pari).

Half-Carry Flag
Significativo solo per le istruzioni in aritmetica BCD, indica se si verificato un riporto tra
i 4 bit meno significativi e i 4 bit pi significativi dell'accumulatore.

Subtract Flag
Indica se l'ultima operazione eseguita stata una sottrazione (N=1) o altro (N=0).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-5

Attenzione! Nel caso di due sole istruzioni, che incontreremo pi avanti, il registro A e il
registro F sembrano riuniti in un registro fittizio da 16 bit, definito con il nome simbolico AF, ma il
registro AF in realt non esiste! Le istruzioni sono le PUSH AF e POP AF e saranno esaminate
a tempo debito: in esse A ed F compaiono in questo modo solo per esigenze di abbreviazione.
In ultimo, nel DMC8 presente anche un flip-flop isolato, NON incluso nel registro dei Flag F:

IFF

1 bit

Interrupt Flip Flop

Questo registro ad un bit abilita o disabilita il meccanismo delle cosiddette Interruzioni, che
incontreremo pi avanti. Se uguale a zero, le Interruzioni sono disabilitate.

3.3

I collegamenti del chip DMC8


In Fig. 3.3 sono riportati i
collegamenti esterni del
chip DMC8 (ricordiamo
per che il chip virtuale,
in quanto solo simulato nel
programma d-MCE citato
allinizio
del
capitolo).
Questa descrizione ha
quindi una valenza logica,
e non fisica.
La descrizione data nel
seguito va intesa come
presentazione introduttiva;
per ciascun segnale viene
fornito
un
breve
commento,
che
sar
ripreso pi in dettaglio pi
in seguito, al momento
opportuno.

A15 A0

Fig. 3.3: I collegamenti esterni del DMC8

(Address Bus)

Bus degli Indirizzi, 16 linee in uscita. Trasporta gli indirizzi per la memoria e per i dispositivi di
Ingresso/Uscita.

D7 D0

(Data Bus)

Bus dei Dati, 8 linee bidirezionali (utilizzano buffers 3-state). Permette lo scambio delle
informazioni da e per la memoria (dati e istruzioni) e i circuiti di Ingresso/Uscita.
Il Bus dei Controlli composto dalle linee qui di seguito descritte:

SYNC

(Synchronize)

Segnale generato dal chip, attivo basso. Segnala allesterno, quando attivato, che in quel
momento il processore sta prelevando una istruzione dalla memoria. Serve unicamente per
motivi di diagnostica, ed presente in tutti i microprocessori: grazie a questo segnale, un
dispositivo di controllo, opportunamente collegato in parallelo al microprocessore, in grado di
sincronizzarsi con le sue operazioni e decodificare la sequenza di tutte le operazioni eseguite
dal sistema a microprocessore.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-6

MEMREQ

(Memory Request)

Segnale generato dal chip, attivo basso. Quando attivato, indica ai dispositivi di memoria
presenti nel sistema di attivarsi perch la CPU ha predisposto (sul Bus degli Indirizzi) lindirizzo
della locazione di memoria che sta per essere letta o scritta.

IOREQ

(Input/Output Request)

Segnale generato dal chip, attivo basso. Quando attivato, indica ai dispositivi di Ingresso o di
Uscita presenti nel sistema di attivarsi perch la CPU ha predisposto (sul Bus degli Indirizzi)
lindirizzo del dispositivo che sta per essere letto o scritto.

READ

(Read Data)

Segnale generato dal chip, attivo basso. Quando attivato, indica ai dispositivi di memoria (o di
Ingresso/Uscita) che il processore vuole leggere un dato. attivato congiuntamente ai segnali
MEMREQ o IOREQ.

WRITE

(Write Data)

Segnale generato dal chip, attivo basso. Quando attivato, indica ai dispositivi di memoria (o di
Ingresso/Uscita) che il processore vuole scrivere un dato. attivato congiuntamente ai segnali
MEMREQ o IOREQ.

INT

(Interrupt)
Segnale ricevuto dal chip, attivo basso, ordina una Interruzione al processore. Quando il
sistema esterno attiva questo segnale, il processore termina listruzione attualmente in
esecuzione, interrompe la sequenza imposta dal programma ed inizia lesecuzione di un
opportuno programma, chiamato di gestione della interruzione. Una volta terminata
lesecuzione di questo programma, il processore riprende lesecuzione del programma
precedentemente interrotto.
Largomento complesso e sar trattato diffusamente molto pi avanti. Serve per gestire
rapidamente le richieste di intervento da parte dei dispositivi di ingresso/uscita.

INTA

(Interrupt Acknowledge)

Segnale generato dal chip, attivo basso. La sua attivazione indica allesterno che la richiesta di
interruzione, avvenuta attivando la linea INT, stata accettata e il relativo programma di
gestione delle interruzioni in corso di avvio. Si disattiva ad avviamento avvenuto.

RESET
Segnale ricevuto dal chip, attivo basso. Lattivazione del RESET azzera tutti i registri interni
del processore, disabilita gli Interrupt e inizializza il sequenziatore. In conseguenza
dellazzeramento del registro PC, il processore prelever la prima istruzione allindirizzo di
memoria 0000h.

CLOCK
Segnale ricevuto dal chip. E il segnale di orologio su cui si sincronizzano le operazioni interne.
In generale, la frequenza massima di un clock dipende dal processo di fabbricazione del chip:
nel nostro caso, essendo il chip soltanto emulato, faremo sempre lipotesi di lavorare con un
clock a onda quadra di frequenza pari a 10MHz.
Un dispositivo reale necessiter naturalmente di essere alimentato, per cui nella figura sono
rappresentati anche i collegamenti di alimentazione Vcc (+5V) e Gnd (Ground, 0 V).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

3-7

Il funzionamento del microprocessore


Dal punto di vista del funzionamento interno, il microprocessore un sistema digitale
controllato da una complessa macchina a stati finiti, progettata per eseguire un certo
insieme di compiti ben definiti. Se il sistema fosse semplicemente
cablato, ingressi opportuni ci consentirebbero di richiedere a tale
macchina, uno dopo laltro, i compiti di nostro interesse.
Il sistema , invece, programmabile: i compiti da eseguire sono
specificati da una lista di istruzioni, il cosiddetto programma, che
noi forniamo alla macchina. Ogni istruzione specifica un
determinato compito da eseguire, in ordine di lista.
La macchina a stati del microprocessore, il sequenziatore,
progettata non solo per eseguire le singole istruzioni, ma anche per
reperirle da solo. Fin dal primo momento, cio da quando il
microprocessore riceve un segnale di RESET, il sequenziatore
attiva una sequenza che prevede il prelievo di una istruzione (in
memoria), la sua decodifica (interpretazione) e quindi la sua
esecuzione. Questa sequenza prelievo-decodifica-esecuzione
sar ripetuta allinfinito, in modo da eseguire automaticamente, una
dopo laltra, le istruzioni (Fig. 4.1).
Esaminato in questi termini, come si vede, il microprocessore non
una macchina molto intelligente: non altro che un dispositivo
automatico in grado di eseguire stupidamente i compiti che trova
elencati nel programma, ma ad una velocit elevatissima.

4.1

Fig.4.1: Il ciclo infinito di


prelievo, decodifica ed
esecuzione delle istruzioni

Il microprocessore e la memoria
Prima di procedere, bene soffermarci sulle
caratteristiche di indirizzamento del microprocessore. Il
DMC8 possiede un Bus degli Indirizzi a 16 fili e quindi
(=65.536) locazioni di
pu indirizzare fino a 216
memoria. Il Bus dei Dati da 8 bit, e ogni locazione di
memoria dovr essere larga altrettanto.
Per descrivere sinteticamente il sistema di memoria il
progettista solito utilizzare una Mappa di Memoria
(Memory Map, Fig.4.2). In essa indichiamo, per
intervalli di indirizzo, il tipo di memoria a disposizione
del microprocessore, ossia quali dispositivi fisici di RAM
o di ROM sono pronti ad attivarsi in risposta agli
indirizzi e ai segnali di scrittura/lettura da esso generati.
Si soliti rappresentare la Mappa di Memoria sotto
forma grafica, mediante una striscia verticale suddivisa
in zone, come nell'esempio della figura.
In tale esempio, il microprocessore pu accedere ai dati
della RAM utilizzando gli indirizzi a partire da C000h
sino a FFFFh compresi (16K locazioni).
Il microprocessore pu inoltre leggere i dati e
programmi memorizzati nella ROM, le cui locazioni
risultano disponibili, nel nostro esempio, dall'indirizzo
0000h all'indirizzo 3FFFh (16K locazioni).

Fig.4.2: Esempio di Mappa di Memoria

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-1

Esaminando lesempio in figura, si osserva che lo spazio di memoria compreso tra gli indirizzi
4000h e BFFFh definito come libero. Questo significa semplicemente che, per decisione del
progettista, a questi indirizzi non corrispondono fisicamente circuiti di memoria. In questa area
libera, un eventuale accesso in scrittura e/o lettura privo di significato, in quanto ai segnali del
microprocessore non risponder nessun dispositivo.
un area tenuta a disposizione per future espansioni di memoria. Naturalmente, lesempio
visto si riferisce al nostro sistema, che dispone di uno spazio di indirizzamento piuttosto piccolo.
Ritroviamo per una situazione simile anche nei sistemi pi grossi, in cui lo spazio di
indirizzamento spesso occupato in modo parziale. Pensiamo ad esempio allo spazio di
indirizzamento di un microprocessore con un bus indirizzi a 32 bit: con questo sistema si
possono indirizzare circa 4 miliardi di locazioni (232), ma non sempre ci necessario.

4.1.1

Il contenuto della memoria allaccensione del sistema


Quando il sistema viene acceso, nella RAM non vi ovviamente nulla di significativo, in quanto
memoria volatile (mantiene il dato solo quando alimentata, essendo composta di flip-flop).
Per questi motivi, per le procedure necessarie all'avvio, un sistema a microprocessore deve far
riferimento alla memoria a sola lettura ROM: qui dovr risiedere il programma che, allocato ad
un indirizzo di partenza convenuto, permetter alla CPU di eseguire qualcosa di significativo nei
primi cicli "di vita".
La scelta dellindirizzo di partenza obbligata dalle caratteristiche proprie del microprocessore
in uso: nel nostro caso, il DMC8 ci impone lindirizzo 0000h come sede della prima istruzione
valida dopo ogni RESET hardware. Quindi, nel nostro sistema, la ROM deve iniziare allindirizzo
0000h e questo sar lindirizzo di RESET da cui comincer tutti i nostri programmi.
Ovviamente, microprocessori di altro tipo ci richiederanno altri indirizzi di RESET.

4.2

Il linguaggio Macchina
Abbiamo detto che il programma una lista di istruzioni che scriviamo noi e che forniamo al
microprocessore. In pratica, questa lista di istruzioni altro non che una sequenza di codici
binari predisposta in memoria: il microprocessore non e ` in grado di prelevare, riconoscere ed
eseguire niente altro che dei numeri binari.
Ogni istruzione rappresentata da un codice definito in modo univoco. Il programma, nella
forma di sequenza di codici binari, si dice scritto in Linguaggio Macchina (o Codice
Macchina, o Codice Oggetto).
Sarebbe molto scomodo programmare in linguaggio macchina: ogni operazione dovrebbe
essere specificata sotto forma di numero, uno dopo laltro! Per venire in contro all'esigenza di
scrivere programmi in modo sufficientemente mnemonico e razionale, fu introdotto, fin dai primi
computer, il linguaggio Assembly. Il linguaggio Assembly caratterizzato dalla
corrispondenza 1:1 tra le righe sorgenti scritte in modo testuale dal programmatore,
contenenti una sola istruzione, e le istruzioni elementari di codice macchina che ne derivano,
per traduzione. Per ogni tipo diverso di processore, esiste un diverso linguaggio Assembly: il
DMC8 possiede il suo (compatibile con quello dello Z80-CPU).

4.2.1

Esempio di programma in formato MNEMONICO Assembly


Osserviamo un piccolo frammento di programma, scritto da un programmatore in codice
mnemonico Assembly DMC8, composto da due istruzioni:

LD
LD

A,(0F5F0h)
B,A

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-2

Questa sequenza di istruzioni significa, riga per riga:


LD

A,(0F5F0h)

Carica (LD = Load) nel registro A del processore il contenuto della


locazione di memoria che si trova all'indirizzo esadecimale F5F0h
(lo zero non significativo, vedremo, necessario solo per ragioni di sintassi);

LD

B,A

Carica nel registro B del processore il contenuto del registro A;

Il programmatore di cui sopra ha utilizzato un calcolatore per introdurre (usando tastiera e


video) il testo del suo programma, lo ha memorizzato su disco magnetico o ottico, e quindi lo
ha tradotto in linguaggio macchina mediante un opportuno programma traduttore chiamato
Assembler (Assemblatore).
Dopo la traduzione, il programmatore ha potuto controllare su di un file prodotto
dallAssemblatore una lista formattata (Listing), che gli sar apparsa allincirca cos:
...
0100h 3Ah LD A,(0F5F0h)
0101h F0h
0102h F5h
0103h 47h LD B,A
0104h
...
Tutti i numeri sono riportati in formato esadecimale, anzich binario, per comodit di lettura
umana. Sulla sinistra, la prima colonna della lista mette in evidenza gli indirizzi delle locazioni
di memoria in cui il microprocessore trover i codici delle istruzioni. La seconda colonna riporta
invece le istruzioni, tradotte in codice macchina. La terza e seguenti ricopiano, per
comodit, le istruzioni cos come il programmatore le aveva scritte, permettendo di osservare la
corrispondenza con i rispettivi codici macchina. In particolare, i codici 3Ah e 47h rappresentano
i Codici Operativi delle istruzioni utilizzate nel nostro esempio.
Osserviamo inoltre che la prima istruzione ha richiesto tre byte di memoria per essere tradotta
(3Ah, F0h, F5h), mentre la seconda soltanto uno (47h). I motivi di questa differenza saranno
approfonditi in seguito: notate soltanto, per il momento, che nelle locazioni di memoria 0101h e
0102h stato inserito, spezzato in due byte, l'indirizzo a 16 bit che il programmatore aveva
riportato tra parentesi.

Al momento della esecuzione del programma, il microprocessore trover in memoria, locazione


dopo locazione, i seguenti codici:
Allindirizzo:

0100h
0101h
0102h
0103h
0104h
0105h

Codice
0011.1010
1111.0000
1111.0101
0100.0111

(= in Hex)
3Ah
F0h
F5h
47h

Per capire come il microprocessore eseguir questo frammento di programma in codice


macchina, nel prossimo paragrafo cercheremo di scendere nei dettagli della sequenza di
operazioni elementari che impegnano internamente il processore.

4.3

Prelievo, decodifica ed esecuzione delle istruzioni


Si premette che il livello di dettaglio nel quale stiamo per scendere ora ha soltanto un puro fine
didattico introduttivo: si vuole semplicemente fare comprendere a fondo il meccanismo di
funzionamento del microprocessore. Superato questo momento di approfondimento, lasceremo
alle spalle le tante complicazioni incontrate per concentrarci essenzialmente sul risultato
ottenuto dalle singole istruzioni, senza scendere pi in particolari cos minuti.
Se vogliamo fare un paragone automobilistico (che potrebbe sembrare banale, ma non lo ): per
imparare a guidare l'automobile, necessario imparare come funziona il suo motore, il cambio, la
frizione, ecc., ma poi non serve (anzi deleterio), continuare a pensare intensamente, durante la
normale guida in strada, al movimento di valvole e pistoni...

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-3

Ricordiamo che il microprocessore esegue tutte le operazioni cadenzato dal Clock di sistema.
Dopo il RESET hardware, che inizializza il sequenziatore, il DMC8 comincia il suo lavoro
"lanciando" sul bus degli indirizzi l'indirizzo predefinito 0000h, con l'intento di prelevare e
decodificare la prima istruzione che il microprocessore dovr eseguire. Il sequenziatore ottiene
questo collegando al bus degli indirizzi l'uscita del registro interno Program Counter (PC), che
un istante prima stato azzerato dal
citato segnale di RESET (vedi fig. 4.3).
Il PC (che in altri microprocessori
chiamato
pi
intuitivamente
IP,
Instruction Pointer) ha infatti il
compito di puntare alla locazione di
memoria ove il processore trover la
prossima istruzione da eseguire.
Dopo ogni prelievo di una istruzione, il
sequenziatore
incrementa
automaticamente il PC, in modo da
prepararlo per il prelievo della
successiva istruzione.
In fig. 4.3 si osserva che la memoria,
Fig.4.3: Al RESET del sistema, il Program Counter punta
cos indirizzata, restituisce il contenuto
alla prima istruzione da eseguire
della prima locazione, la prima
istruzione, che il processore quindi preleva, copiandola al proprio interno. Non entriamo per il
momento nei dettagli: qualunque cosa chieda questa istruzione, il processore la eseguir e, con
il PC incrementato, proceder al prelievo della istruzione successiva, e via di seguito.
A questo punto normalmente viene spontaneo chiedersi come fa il processore a capire che quello
che sta prelevando sia effettivamente una istruzione e non qualcosa daltro, per esempio un dato.
La risposta molto semplice: il processore non effettua controlli e si aspetta di trovare in quella
locazione una istruzione, e come tale la preleva e la esegue. responsabilit del programmatore
aver messo in quella locazione una istruzione significativa.

Dunque, istruzione dopo istruzione, il processore esegue il programma predisposto in memoria


dal programmatore, incrementando passo dopo passo il registro PC. Dopo un certo numero di
istruzioni, il PC si trover a puntare alla locazione di memoria 0100h, dove ipotizziamo che,
facendo fede al nostro esempio di prima, sia presente il codice 3Ah.
A questo punto scendiamo nei particolari, anche se sar necessario avere un po di pazienza nel
seguire attentamente la descrizione dei singoli passi eseguiti a basso livello dal processore.

4.3.1

Prelievo della istruzione (Instruction Fetch)


Osserviamo la fig.4.4. Per prima cosa (passo 1 in figura) il sequenziatore pone il contenuto del
registro PC (ora pari a 0100h) sul Bus degli Indirizzi, e attiva una opportuna sequenza di
segnali di controllo esterni (non riportati in figura) che indica la sua intenzione di prelevare una
istruzione (ciclo di Fetch).
La memoria, attivatasi di conseguenza in lettura, fornisce sul Bus dei Dati il contenuto della
locazione all'indirizzo 0100h (passo 2), che nel nostro esempio contiene il codice operativo
3Ah. Il sequenziatore ricopia il codice nel Registro Istruzione, che un registro preposto alla
memorizzazione temporanea dell'istruzione corrente.
A questo punto, il sequenziatore incrementa di uno il PC, preparandolo al prossimo accesso in
memoria.

4.3.2

Decodifica della istruzione (Instruction Decode)


Il Decodificatore, sulla base del codice ora caricato nel Registro Istruzione, predispone il
sequenziatore alla generazione della sequenza corrispondente. Il DMC8 prevede 660
sequenze diverse, tante quante sono le istruzioni eseguibili. Nel nostro esempio, la sequenza
predisposta sar ovviamente quella specifica per l'istruzione di codice 3Ah.
In totale, il prelievo della istruzione e la sua decodifica ha richiesto 4 cicli di clock (pi avanti, in
un prossimo capitolo, esamineremo meglio i dettagli delle temporizzazioni dei segnali coinvolti).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-4

Fig.4.4: Esecuzione della istruzione LD A,(0F5F0h): prelievo (fetch) del codice operativo

Fig.4.5: Esecuzione della istruzione LD A,(0F5F0h): prelievo parte bassa delloperando

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-5

4.3.3

Esecuzione della istruzione (Instruction Execute)


Al codice operativo 3Ah corrisponde formalmente l'istruzione in formato mnemonico LD
A,(indirizzo) che, come gi visto, chiede di copiare nel registro accumulatore A il byte
contenuto nella locazione di memoria specificata dall'indirizzo tra parentesi.
Se andiamo a rivedere quanto detto in precedenza, nella traduzione in linguaggio macchina
della istruzione, questo indirizzo era stato scomposto in due pezzi da 8 bit, sistemati nelle due
locazioni di memoria 0101h e 0102h successive al codice operativo. necessario quindi che il
microprocessore acquisisca anche questi due byte, al fine di ricomporre lindirizzo necessario
per eseguire il compito richiesto.
A tal fine, la sequenza prosegue collegando nuovamente il PC al Bus degli Indirizzi (fig.4.5,
passo 3), e attivando unaltra sequenza di segnali di controllo esterni per indicare lintenzione di
leggere un altro byte dalla memoria (ciclo di lettura dalla memoria). Lindirizzo presente sul
bus ora pari a 0101h poich il PC, come abbiamo visto, era stato incrementato di uno, dopo il
prelievo del codice operativo della istruzione.
La memoria, attivandosi in lettura, fornisce sul Bus dei Dati (passo 4) il contenuto della
locazione all'indirizzo 0101h, che nel nostro caso contiene il byte F0h. Il sequenziatore ricopia
questo byte nella parte bassa di un registro temporaneo a 16 bit. Questo registro
temporaneo agisce dietro le quinte e non appartiene al set di registri che il programmatore pu
usare esplicitamente, ma servir a ricomporre l'indirizzo completo dell'operando.
Effettuato il trasferimento del byte, il sequenziatore incrementa nuovamente il contenuto del PC,
portandolo ora al valore 0102h, pronto per il prossimo accesso in memoria (laccesso in
memoria ora effettuato ha richiesto 3 cicli di clock).
La sequenza prosegue ora (fig.4.6) con i passi 5 e 6, nella sostanza quasi identici ai passi 3 e
4, al fine di acquisire anche il byte alto delloperando, che vale F5h. Anche in questo caso, non
appena terminato laccesso in memoria (sono trascorsi altri 3 cicli di clock), il sequenziatore

Fig.4.6: Esecuzione della istruzione LD A,(0F5F0h): prelievo parte alta delloperando


Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-6

Fig.4.7: Esecuzione della istruzione LD A,(0F5F0h): trasferimento del dato dalla memoria al registro

incrementer il contenuto del PC, portandolo al valore 0103h, pronto per il prelievo della
prossima istruzione.
In questo momento il processore possiede finalmente l'indirizzo completo della locazione da
copiare nel registro accumulatore A, per cui il sequenziatore proseguir effettuando un ultimo
accesso in memoria (fig.4.7), ponendo sul Bus degli Indirizzi questa volta il contenuto del
registro temporaneo e attivando ancora una volta la sequenza di segnali che indica la sua
intenzione di leggere un byte dalla memoria (passo 7).
importante rimarcare che, rispetto ai cicli precedenti, ora sul Bus degli Indirizzi non abbiamo
pi il contenuto del PC, ma finalmente proprio l'indirizzo del byte che il programmatore
aveva specificato tra parentesi nell'istruzione.
La memoria, riconosciuta la richiesta di lettura, fornir sul Bus dei Dati il contenuto della
locazione all'indirizzo F5F0h (passo 8). In questa locazione presente un dato, ossia un
numero che il programma aveva gi calcolato e memorizzato in precedenza, e che ora il
programmatore ritiene necessario riprendere per proseguire nei suoi conti. Ai fini della presente
descrizione, questo numero pu essere qualunque: nella figura si supposto sia pari a 7Dh.
Come operazione finale di tutta la sequenza, il sequenziatore comanda la copiatura del dato
presente sul Bus dei Dati nel registro A (e anche noi possiamo finalmente tirare un sospiro di
sollievo, lesecuzione della istruzione terminata).
In totale, listruzione LD A,(indirizzo) ha richiesto complessivamente 13 cicli di clock (4+3+3+3)
per essere eseguita.

4.3.4

Prelievo ed esecuzione delle successive istruzioni


Al termine della esecuzione di una qualunque istruzione, lindirizzo contenuto nel registro PC
pronto per il prelievo della successiva. Nel nostro esempio (vedi fig.4.8), il PC vale 0103h.
Senza nessuna pausa, il sequenziatore ricomincia una nuova sequenza di prelievo e, con i
passi 9 e 10, il processore acquisisce il codice operativo 47h della prossima istruzione.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-7

Fig.4.8: Prelievo (fetch) del codice operativo ed esecuzione della istruzione LD B,A

Fig.4.9: Prelievo (fetch) del codice operativo della istruzione successiva, qualunque essa sia
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-8

Anche in questo caso, il Decodificatore ordiner al sequenziatore di eseguire la sequenza


corrispondente al nuovo codice, che sappiamo corrispondere al mnemonico LD B,A: chiede di
trasferire nel registro B il contenuto del registro A. A differenza della precedente istruzione, il
compito richiesto al processore non coinvolge la memoria: si tratta invece di attivit che il
processore eseguir al suo interno.
Questa istruzione sar quindi eseguita molto rapidamente: la sequenza delle cose che restano
da fare, dopo lavvenuto prelievo del codice operativo, limitata al caricamento nel registro B
del valore prelevato dal registro A (fig.4.8, passo 11). Pu essere utile consultare la figura 3.2
nel capitolo precedente per osservare la strada che il dato deve percorrere, tramite il bus
interno, per essere copiato dal registro sorgente al registro destinazione.
Come nei casi precedenti, anche in questo caso il PC automaticamente incrementato di uno
(varr 0104h), preparandolo per il prelievo della istruzione successiva.
Non impegnando il bus esterno in ulteriori accessi in memoria, questa istruzione stata
eseguita in soli 4 cicli di clock, giusto il tempo necessario per il prelievo del codice operativo.
Il trasferimento da B ad A viene infatti eseguito sul fronte di clock che corrisponde con lavvio
del prelievo dellistruzione successiva.
Nel nostro esempio, non abbiamo riportato le istruzioni che seguono le due che abbiamo
analizzato, ma che ovviamente saranno presenti: il processore, allindirizzo 0104h, trover in
ogni caso una istruzione (fig.4.9) che, come le altre, caricher nel registro dellistruzione (passi
12 e 13), che eseguir e continuando cos, in ciclo infinito, eseguir lintero programma.
Vedremo nel seguito che i programmi quasi sempre si richiudono ad anello (con delle
istruzioni di salto), ma che il DMC8 prevede tuttavia un istruzione di HALT (di uso
estremamente raro) in grado di fermare effettivamente il processore.

4.4

Considerazioni sulla velocit di esecuzione


Gi nel primo capitolo si sono fatte considerazioni sulla velocit di esecuzione delle istruzioni.
Ora il momento di riprendere quelle considerazioni, dal momento che abbiamo esaminato un
poco pi da vicino alcuni esempi di operazioni effettivamente eseguite dal processore.
Si puo osservare che la maggior parte delle operazioni elementari eseguite dalla CPU sono
servite soltanto per preparare l'esecuzione vera e propria della istruzione. L'esecuzione del
compito effettivamente assegnato ha comportato il dispendio di solo una minima parte del
tempo totale, che stato invece speso quasi tutto nello spostamento di informazioni dalla
memoria alla CPU. Anche nel caso pi veloce, resta comunque la necessit di prelevare
listruzione dalla memoria e decodificarla, prima di eseguirla.
La flessibilit dei microprocessori, dovuta alla programmabilit della sequenza delle operazioni
volute, si paga in termini di tempo, che viene perso soprattutto nella lettura e nella decodifica
del programma. Daltra parte, se una macchina a stati progettata per lo specifico problema
sarebbe stata teoreticamente molto pi veloce, a parit di frequenza di clock, non sarebbe stata
tuttavia n riutilizzabile, n facilmente modificabile... e, in definitiva, anti-economica. Pu
essere utile rileggere, alla luce di quanto visto in questo capitolo, il paragrafo Considerazioni
sulla esecuzione delle istruzioni del Cap.1.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

4-9

Introduzione alla programmazione in Assembly


Nel progettare, ad esempio, il sistema di controllo per un impianto industriale, avremo da
affrontare sia problemi di tipo hardware, che di tipo software. Una volta definita larchitettura del
sistema hardware, avremo a che fare con il software di gestione e controllo dellimpianto. Sar il
programma che scriveremo a caratterizzare il nostro sistema per la particolare applicazione di
controllo.
I compiti che il nostro programma deve svolgere si possono descrivere in forma algoritmica. Un
algoritmo linsieme di regole ben-definite che descrivono la soluzione di un problema
mediante una sequenza finita di passi. Un algoritmo pu essere espresso in qualsiasi
forma: ad esempio a parole o, pi produttivamente, sotto forma di diagramma di flusso. Affinch
un sistema a microprocessore possa eseguire i compiti richiesti, necessario convertire la
descrizione algoritmica in un programma.

5.1

I linguaggi di programmazione
Un programma viene scritto in un linguaggio standard, in grado di essere eseguito dal
microprocessore. Abbiamo visto che un microprocessore pu eseguire soltanto istruzioni in
linguaggio macchina, codificate in forma numerica, e che un programma "eseguibile" costituito
da una sequenza di tali istruzioni.
A meno che non si tratti di programmi estremamente piccoli, lo sviluppo di un programma
direttamente in codice macchina non certamente un compito pratico! Per questo motivo sono
stati sviluppati linguaggi di programmazione di vario livello, complessit e potenza, con i relativi
traduttori (che classifichiamo in Assemblatori, Compilatori, Interpreti) in grado di convertire i
programmi scritti in tali linguaggi nella corrispondente serie di istruzioni in codice macchina
effettivamente eseguibile dal processore.

5.1.1

I linguaggi ad Alto Livello


In un linguaggio ad alto livello, una istruzione simbolica (ad esempio la 'ReadLn' del Pascal, o la
Printf del C) corrisponde generalmente a molte istruzioni in codice macchina (centinaia,
migliaia). Linguaggi ad alto livello sono, ad esempio, il Basic, il Fortran, il Cobol, il Pascal,
lObject Pascal, il Modula2, il C, il C++, il Java, il C# (leggi si-sciarp), ecc.

5.1.2

I linguaggi a "basso livello"


I linguaggi a basso livello come gli Assembly (specifici per ogni diverso processore) sono
invece caratterizzati da istruzioni mnemonico-simboliche che hanno una corrispondenza 1:1
con le istruzioni macchina eseguibili direttamente dal microprocessore.
I programmatori, per un dato processore, usano uno specifico Assemblatore (Assembler), un
applicativo software che traduce un programma scritto in codice mnemonico Assembly nel
corrispondente programma in codice macchina.
Un linguaggio Assembly consente la manipolazione diretta, da parte del programmatore, dei
registri e dei bit all'interno della macchina. impiegato tipicamente in quei casi dove si
richiede una particolare efficienza di esecuzione da parte del processore.
La programmazione in linguaggio Assembly piuttosto onerosa, soprattutto in termini di tempo:
si deve programmare tutto, fino nei minimi dettagli, specificando anche i particolari pi
apparentemente banali. Inoltre l'Assembly, per essere usato, richiede al programmatore la
conoscenza perfetta dell'hardware su cui il programma deve 'girare'.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-1

A causa di questi svantaggi, per problemi ordinari (pi o meno complessi) si preferisce
impiegare i linguaggi ad alto livello, pi sintetici e comprensibili. Spesso si usa una tecnica
mista: si impiega un linguaggio ad alto livello per scrivere la maggior parte del codice del nostro
programma e, per le parti che devono essere ottimizzate, il linguaggio Assembly. Infatti un
linguaggio ad alto livello consente normalmente di "unire" al nostro programma dei moduli scritti
in linguaggio Assembly.
Un programma scritto in linguaggio Assembler non "portabile", cio specifico per quel
particolare microprocessore, e spesso anche per un dato hardware di contorno: riutilizzare un
tale programma su di una macchina diversa pu richiederne la riscrittura integrale.
Programmi scritti con linguaggi ad alto livello standard sono invece maggiormente
intercambiabili tra macchine diverse e tra microprocessori diversi, a patto di disporre degli
opportuni compilatori.

5.2

Il linguaggio Assembly del DMC8


In Assembly, ogni riga di codice sorgente divisa in pi campi, che devono essere separati da
spazi o caratteri di tabulazione, e ogni riga contiene una sola istruzione. Quando si scrive un
programma in Assembly, dobbiamo immaginare il nostro foglio diviso virtualmente in quattro
colonne (o campi), come in questo esempio:
Etichetta

Mnemonico

Operando

(Label)

(Mnemonic)

(Operand)

LOOP:

LD
LD
DEC
JP

A,(34F0h)
D,02Ah
D
NZ,LOOP

Commento
(Comment)

;leggo il dato dalla memoria


;predispongo il contatore
;decremento il contatore
;(JUMP)... ripeto fino ad azzerarlo

Questo il significato dei quattro campi:


Etichetta

Letichetta usata come riferimento per i "salti" del programma (analogamente a


quanto possibile fare nei linguaggi ad alto livello, dove incontriamo listruzione
"GOTO"). Naturalmente il programmatore la inserisce solo quando serve;

Mnemonico Rappresenta il codice mnemonico della istruzione;

5.2.1

Operando

Include l'operando (o gli operandi) dell'istruzione specificata dal codice


mnemonico;

Commento

Commento, facoltativo, sullo scopo della riga di programma. Questo campo deve
generalmente cominciare con un ";", ma alcuni Assemblatori accettano un
qualsiasi simbolo, cio danno per scontato che tutto ci che segue una
istruzione, riconosciuta completa, sia un commento. I commenti risultano
fondamentali per il programmatore, che pu cos rendere pi leggibile il proprio
codice (ad altri, ma soprattutto a se stesso).

Un primo esempio di programma scritto in Assembly


Nel Listato 5.1 possiamo osservare un primo esempio di programma. Effettua la somma di due
numeri, rappresentati su 8 bit: dati e risultato sono allocati nella memoria RAM del sistema.
Osservando il codice, e leggendone i commenti, possiamo distinguere quattro fasi successive:
1.
2.
3.
4.

Acquisizione (lettura) del primo operando, dalla memoria alla CPU;


Acquisizione (lettura) del secondo operando, dalla memoria alla CPU;
Somma dei due operandi, all'interno della CPU;
Memorizzazione (scrittura) del risultato, da parte della CPU, in memoria.

La prima fase stata codificata con due istruzioni elementari. Infatti il DMC8 non possiede
una istruzione del tipo "LD B,(0F000h)", e i trasferimento in B deve essere effettuato in due
tempi, passando attraverso il registro accumulatore A. Succede spesso che una istruzione
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-2

Etichetta

Mnem./Operando

Commento

SOMMA:

LD
LD
LD
ADD
LD
HALT

;carica in A il dato della locazione F000h


;porta in B il contenuto di A
;carica in A il dato della locazione F001h
;somma A e B mettendo il risultato in A
;trasferisci il risultato nella loc. F002h
;fermati nello stato di inattivit

A,(0F000h)
B,A
A,(0F001h)
A,B
(0F002h),A

Listato 5.1: Esempio di programma scritto in codice sorgente assembly

non ammetta tutti gli operandi che sintatticamente potrebbero sembrare possibili; per non
commettere errori, conviene consultare le tabelle delle istruzioni (nei capitoli pi avanti
possibile consultare le tabelle riassuntive delle istruzioni del DMC8).
Dopo l'esecuzione delle prime 3 istruzioni, il microprocessore gli operandi saranno stati
trasferiti, dalla memoria, nei registri A e B. L'istruzione ADD effettua la somma dei due
operandi in A e B, ponendo il risultato nuovamente in A. Infine la penultima istruzione
trasferisce il risultato della operazione in memoria.
Lultima istruzione HALT blocca il processore. Questa istruzione sar nel seguito utilizzata
molto raramente: ha poco senso infatti, se non in rari casi, fermare il processore.

5.2.2

Simboli, Variabili, Etichette e Direttive in Assembly


Nei linguaggi ad alto livello esiste il concetto di TIPO delle variabili. Assegnando un tipo
alle variabili nel momento in cui un vengono dichiarate, consentiamo al compilatore di darci
una mano nella scrittura del nostro codice (ad esempio, il tipo dichiarato permetter al
compilatore di avvisarci se nel nostro codice stiamo commettendo lerrore di trasferire un
numero codificato su 64 bit in una variabile da soli 16 bit).
Nei linguaggi ad alto livello non ci dobbiamo preoccupare di dove le nostre variabili saranno
allocate, di come saranno fisicamente implementate, di eventuali sovrapposizioni tra le variabili,
ecc. il compilatore che si incarica, per noi, di risolvere tutti questi importanti particolari.
Esistono anche assemblatori che consentono di assegnare un tipo alle variabili. Tuttavia, il
programmatore in Assembly deve abituarsi a manipolare i suoi dati senza fare uso dei tipi,
anche in ragione del fatto che non tutti gli Assembly, specie quelli dei microprocessori pi
piccoli e semplici, supportano la tipizzazione delle variabili. Inoltre, il programmatore in
Assembly deve spesso occuparsi di dettagli che lo costringono a non demandare
allAssemblatore la costruzione delle variabili, ma a gestirla direttamente. Dunque, il
programmatore in molti casi dovr decidere quali locazioni di memoria utilizzare per una data
variabile, quanti byte riservarle, quale significato dare ai singoli bit di ogni byte, ed altro.
Nell'esempio visto nel Listato 5.1, il programmatore ha scelto di assegnare a ciascuna variabile
in gioco un solo byte di memoria, e ha dovuto precisare anche l'indirizzo a cui queste variabili
risultano allocate: F000h e F001h per i due operandi, F002h per il risultato. Naturalmente,
questi indirizzi saranno stati individuati dal programmatore considerando lo spazio disponibile in
RAM, confrontandosi anche con le esigenze degli altri moduli di software eventualmente
presenti, tenendo presente la eventuale condivisione di aree comuni, ecc.

5.2.2.1 La direttiva EQU


Per venire incontro al programmatore, tutti gli Assemblatori consentono di etichettare le
variabili, in un modo molto simile ai linguaggi ad alto livello. Utilizzando questa possibilit,
possiamo riscrivere il programma DMC8 come appare nel Listato 5.2. In questo listato
incontriamo per la prima volta la direttiva EQU, abbreviazione di Equal (uguale).
Una direttiva non una istruzione, ma un comando, inserito nel codice sorgente, rivolto
allassemblatore. Lassemblatore utilizzer tale indicazione per tradurre in modo appropriato il
codice sorgente. Nel codice macchina tradotto, perci, non troveremo nessuna istruzione in
corrispondenza delle direttive; per questo, sono chiamate anche pseudo-istruzioni.
Grazie alla direttiva EQU (vedi Listato 5.2), nel nostro esempio dichiariamo che OPE_1 una
variabile, dichiarata allindirizzo di memoria F000h. Ma questa una "nostra" astrazione: di
fatto stiamo dichiarando solo il valore di un simbolo, una "costante". Infatti, la direttiva EQU
indica semplicemente che OPE_1 un simbolo (un etichetta) e che uguale al valore
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-3

OPE_1
OPE_2
RESULT
;
SOMMA:

EQU
EQU
EQU

0F000h
0F001h
0F002h

;dichiaro la variabile OPE_1 allind. F000h


;e la variabile OPE_2 allindirizzo F001h
;il risultato RESULT allindirizzo F002h

LD
LD
LD
ADD
LD
HALT

A,(OPE_1)
B,A
A,(OPE_2)
A,B
(RESULT),A

;carica in A il dato della variabile OPE_1


;porta in B il contenuto di A
;carica in A il dato della variabile OPE_2
;somma A e B mettendo il risultato in A
;copia il risultato nella variabile RESULT
;fermati nello stato di inattivit

Listato 5.2: L'esempio di prima, ma con uso di etichette e della direttiva EQU per definire le variabili

0F000h. solo per estensione, poi, che ci prendiamo la libert di dire che OPE_1 una
variabile, semplicemente perch pi avanti usiamo il simbolo OPE_1 al posto dellindirizzo
esplicito di una locazione di memoria, scrivendo LD A,(OPE_1).
La variabile, intesa come contenitore, si trova allindirizzo OPE_1 = F000h; possiamo quindi
identificare la variabile con il suo indirizzo, e di conseguenza abbreviare il discorso dicendo che
la variabile o si chiama OPE_1.
Per comodit di lettura, di solito il programmatore definisce gli indirizzi alle variabili dichiarando i
rispettivi simboli allinizio del programma. Quando allochiamo una variabile, oltre che al suo
indirizzo, dovremo fare attenzione anche che non si sovrapponga con altre (nel nostro
semplice esempio non succede perch le variabili hanno la dimensione di un byte).
Ricordiamoci, quindi, che in Assembly il nome della variabile non costituisce un puro riferimento
astratto, ma corrisponde effettivamente al suo indirizzo di memoria. Facciamo attenzione anche a
non commettere il superficiale errore di confondere indirizzo e contenuto: differente pensare al
NOME della variabile, che identifica DOVE questa reperibile (l'indirizzo), ed al suo
CONTENUTO, rappresentato dai bit della/delle locazioni di memoria ad essa assegnate.
Nel caso di variabili composte da pi byte, salvo casi particolari, il nome si riferisce all'indirizzo del
primo byte.

Abbiamo dei vantaggi ad utilizzare delle costanti al posto dei semplici numeri. Se in un dato
momento il programmatore vuole modificare il programma, cambiando lallocazione della
variabile OPE_1, potr farlo editando solo la riga dove il simbolo OPE_1 definito, senza
essere costretto a cercare nel codice sorgente tutte le righe in cui si fa riferimento allindirizzo
F000h (che potrebbero essere molte, e sparse qua e l).
Una regola sintattica ci obbliga a far cominciare i nomi dei simboli con un carattere alfabetico,
affinch i numeri siano distinguibili dai simboli. E per questo motivo che i numeri esadecimali,
quando iniziano con una lettera, devono essere preceduti da uno zero non significativo.
In questo modo lassemblatore risolve casi che potrebbero essere ambigui, come ad esempio
LD A,(FEBAH): largomento tra parentesi viene interpretato come un simbolo denominato
FEBAH; affinch lo interpreti come il numero FEBAH, dovremo scrivere 0FEBAH.
Nel corso della traduzione in linguaggio macchina, il programma Assemblatore si incarica di
stilare una Tabella dei Simboli (Symbol Table) contenente tutti i simboli definiti dal
programmatore, e di sostituire, ad ogni occorrenza di un particolare simbolo nelle righe del
codice sorgente, il suo corrispondente valore (ad esempio, al posto di "OPE_2", nel codice
macchina verr sostituito il valore F001h).
5.2.2.2 La direttiva ORG
Ogni istruzione, tradotta in linguaggio macchina, richiede da uno a quattro byte di memoria, e
nell'insieme tutto il programma ne occupa una certa area. In Assembly, il programmatore deve
precisare l'indirizzo da cui parte il programma stesso: ottiene questo utilizzando un altro tipo
di direttiva, nel nostro caso la ORG (Origin = origine).
La direttiva ORG <indirizzo> ordina alla Assemblatore di tradurre il codice che segue
allocandolo a partire dall'<indirizzo> precisato.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-4

OPE_1
OPE_2
RESULT
;

EQU
EQU
EQU

0F000h
0F001h
0F002h

;dichiaro la variabile OPE_1 allind. F000h


;e la variabile OPE_2 allindirizzo F001h
;il risultato RESULT allindirizzo F002h

ORG
JP

O000h
0100h

;assembla a partire dall'indirizzo di RESET


;salto alla prima locazione del programma

ORG
LD
LD
LD
ADD
LD
HALT

0100h
A,(OPE_1)
B,A
A,(OPE_2)
A,B
(RESULT),A

;assembla a partire dall'indirizzo 0100h


;carica in A il dato della variabile OPE_1
;porta in B il contenuto di A
;carica in A il dato della variabile OPE_2
;somma A e B mettendo il risultato in A
;copia il risultato nella variabile RESULT
;fermati nello stato di inattivit

;
SOMMA:

Listato 5.3: Ancora l'esempio precedente, con l'aggiunta della direttiva ORG per collegarlo al RESET

Nel Listato 5.3 riportato ancora l'esempio di prima, al quale sono state aggiunte tre righe di
codice. La prima ORG obbliga il traduttore a piazzare l'istruzione JP 0100h all'indirizzo 0000h.
In precedenza abbiamo visto che il processore inizia la sua attivit, dopo un RESET hardware,
prelevando l'istruzione presente all'indirizzo 0000h.
Con la prima ORG abbiamo quindi collegato il RESET hardware del processore all'esecuzione
del nostro programma, che sar lanciato automaticamente all'attivazione dell'ingresso
hardware di RESET!
L'istruzione JP 0100h, quando sar eseguita dal processore, causer un "salto" (JUMP) alla
istruzione presente all'indirizzo 0100h ( equivalente al GOTO dei linguaggi ad alto livello).
La seconda ORG, invece, ordina all'Assemblatore di piazzare le istruzioni che seguono a partire
dall'indirizzo 0100h.
Fate attenzione all'etichetta SOMMA: nel nostro esempio contraddistingue la prima istruzione
del programma e, fino ad ora, poteva sembrava semplicemente un'etichetta messa l per dare
un nome mnemonico alla funzione svolta dal programma. Ora acquisisce anche un significato
particolare: infatti, grazie alla ORG, il "simbolo" SOMMA viene ad assumere il valore 0100h,
poich la prima istruzione del programma verr allocata a tale indirizzo.
Ci si potrebbe chiedere perch non abbiamo allocato il programma direttamente allindirizzo
0000h, visto che il processore parte da l, invece che ricorrere ad un salto e farlo cominciare
alla 0100h. Il motivo che le locazioni che seguono la 0000h sono riservate. Ad esempio, le
locazioni a partire dalla 0038h sono riservate alla gestione delle interruzioni (che vedremo pi
avanti); ma gi allindirizzo 0008h troviamo una locazione riservata (alle istruzione di Restart).
E tradizione fare cifra tonda e scavalcare le prime 256 locazioni, saltando allindirizzo 0100h,
che si trova oltre tutte le locazioni riservate.
Osserviamo che tutti i microprocessori, anche i pi recenti, hanno questo genere di restrizioni
nelluso della memoria; le aree riservate, al variare dei modelli, sono tra loro diverse.
HARDRESET
START
OPE_1
OPE_2
RESULT
;

EQU
EQU
EQU
EQU
EQU

0000h
0100h
0F000h
0F001h
0F002h

;indirizzo di RESET hardware


;indirizzo di inizio del programma
;dichiaro la variabile OPE_1 allind. F000h
;e la variabile OPE_2 allindirizzo F001h
;il risultato RESULT allindirizzo F002h

ORG
JP

HARDRESET
SOMMA

;assembla dall'indirizzo di RESET hardware


;salto alla prima locazione del programma

ORG
LD
LD
LD
ADD
LD
HALT

START
A,(OPE_1)
B,A
A,(OPE_2)
A,B
(RESULT),A

;assembla a partire dall'indirizzo di START


;carica in A il dato della variabile OPE_1
;porta in B il contenuto di A
;carica in A il dato della variabile OPE_2
;somma A e B mettendo il risultato in A
;copia il risultato nella variabile RESULT
;fermati nello stato di inattivit

SOMMA:

Listato 5.4: Ultima modifica al nostro esempio, con un uso pi raffinato delle direttive EQU e ORG

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-5

Affiniamo adesso l'uso delle due direttive ORG e EQU. Nel Listato 5.4 si possono notare le
definizioni di due simboli in pi: HARDRESET e START, utilizzati come argomento delle due
ORG. Il risultato in termini di codice macchina identico, ma in questo modo abbiamo spostato
la definizione di tutte le costanti in testa al programma.
E interessante notare un particolare del Listato 5.4 che, sulle prime, potrebbe esserci sfuggito.
LAssemblatore, durante la traduzione del programma, quando incontra la riga contenente
listruzione JP SOMMA, non sa ancora quanto vale il simbolo SOMMA; infatti tale simbolo
definito pi sotto, implicitamente, dalla ORG START, come visto prima.
Come pu essere traducibile listruzione JP SOMMA, se non si conosce ancora il valore del
simbolo SOMMA? Alcuni assemblatori risolvono il problema utilizzando un valore provvisorio,
che sar sostituito dal valore definitivo non appena raggiunta la riga, pi avanti, che ne definisce il
valore; altri effettuano invece pi passate sul codice, la prima dedicata alla risoluzione di tutti i
simboli e alla compilazione della relativa tabella, la seconda alla traduzione vera e propria.

5.2.2.3 Le direttive DB e DW
Il programmatore spesso ha la necessit di predisporre nella ROM delle costanti. Queste
possono essere dei numeri, dei caratteri ASCII, o delle intere tabelle di numeri e caratteri. Le
direttive DB e DW permettono di ottenere questo; nel Listato 5.5 riportato un esempio del
loro utilizzo.
CONST

EQU
ORG

3Fh
1000h

;indirizzo (nella ROM)


;
;----------------------------------------------------------------------BYTES:
DB
0,1,2,3,4,
;inserisce in ROM 5 bytes:
; [00h],[01h],[02h],[03h],[04h]
;
ASCII:
DB
"ABCDEF"
;inserisce 6 car. ASCII, in sequenza
DIGITS:
DB
"0123456789"
;inserisce altri 10 caratteri;
DB
"A""B"
;inserisce 3 caratteri, pari
;pari a: [A], ["] e [B]
NUMBERS:
DB
8,-8,-58, CONST
;inserisce 4 costanti in memoria, in
;sequenza: [08h] = +8
;
[F8h] = -8 (compl. a 2)
;
[C6h] = -58 (compl. a 2)
;
[3Fh] = CONST
MIX:
DB
"XY","ZW",0,0FFh ;def. miste, inserite in sequenza
;----------------------------------------------------------------------WORDS:
DW
8,-8,1033,CONST
;inserisce 4 costanti da 16 bit in
;memoria, spezzate in byte, come
;segue:
[08h]
;
[00h] = 0008h = +8
;
[F8h]
;
[FFh] = FFF8h = -8
;
[09h]
;
[04h] = 0409h = 1003
;
[3Fh]
;
[00h] = CONST
DW
0,0,0,0,0,0,0,0
;inserisce 16 byte di zeri
Listato 5.5: Esempi di utilizzo delle direttive DB e DW

DB labbreviazione di Define Byte, e definisce una o pi costanti della dimensione di un byte


ciascuna. DW labbreviazione di Define Word, e definisce una o pi costanti della
dimensione di una word a 16 bit ciascuna, spezzate in memoria in coppie di byte (nella
sequenza byte Low, byte High).
Come si vede nel listato, usiamo delle etichette per identificare lindirizzo di memoria a cui
lassemblatore andr a caricare le nostre costanti. Per impararne luso, ricorriamo agli esempi
sul Listato 5.5, facendo alcune osservazioni.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-6

La direttiva DB etichettata come BYTES definisce 5 bytes di seguito, che risultano inseriti
nella ROM a partire dallindirizzo 1000h.
Le successive tre DB a partire alletichetta ASCII definiscono delle stringhe di caratteri
ASCII, a partire dallindizzo successivo a quelli utilizzati dalla prima DB: 1005h (= 1000h +
5).
La regola sintattica che singoli caratteri, o stringhe di caratteri, devono essere delimitati
dalla doppia virgoletta ( " ). Se intendiamo includere nella stringa una doppia virgoletta,
affinch lassemblatore la consideri come un carattere e non come un separatore, la
dobbiamo scrivere due volte di seguito ( "" ), come si vede nellesempio riportato nel listato
("A""B"), che si traduce nella sequenza di codici [41h], [22h], [42h].
Alletichetta NUMBERS, la direttiva DB definisce 4 byte. I numeri negativi sono tradotti in
complemento a 2 e quindi, poich lassemblatore li codifica su di un byte, possiamo
rappresentare soltanto i numeri negativi compresi tra -128 e -1. Lassenza del segno, o la
presenza del segno positivo +, forza lassemblatore a codificare il numero come un intero
senza segno, di valore compreso tra 0 e 255. Il programmatore deve quindi prestare
attenzione, perch, dal punto di vista del risultato prodotto dallassemblatore, scrivere -1
oppure 255, oppure 0FFh, la stessa cosa!
Come si vede, possiamo includere anche dei simboli il cui valore sia stato in precedenza
definito da una direttiva EQU: nellesempio, il simbolo CONST. Facciamo attenzione alla
differenza concettuale tra la direttiva EQU e la DB: la EQU definisce il valore di un simbolo,
che lassemblatore non copia nella memoria ROM, ma che usa per la compilazione del
programma; le DB e DW, invece, definiscono delle costanti che sono effettivamente copiate
nella memoria.
La direttiva DW, alletichetta WORDS, come descritto dal commento nel listato, definisce
alcune coppie di byte. Il numero -8, ad esempio, convertito in complemento a 2, su 16 bit,
ottenendo il numero 1111.1111.1111.1000 (in hex: FFF8h). Spezzando la word in due byte,
il byte pi significativo memorizzato allindirizzo successivo di quello del byte meno
significativo (risulta perci: [F8h], [FFh]).

Fig.5.5: Contenuto finale della ROM a seguito delle


definizioni impostate nel listato 5.1

Come riferimento, in Fig. 5.1 riportato il contenuto della memoria ROM, a partire dalla
locazione 1000h, come risulta dalla compilazione del codice che abbiamo ora visto.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

5-7

I modi di indirizzamento del microprocessore DMC8


Abbiamo visto alcuni esempi di istruzioni eseguibili dal microprocessore DMC8. Una istruzione
pu operare su uno o pi operandi. I dati su cui operano le istruzioni possono essere:
a) contenuti nei registri interni della CPU;
b) contenuti nelle locazioni della memoria;
c) provenienti da circuiti periferici di Input/Output.
Con il termine Modo di Indirizzamento si intende il metodo con cui la CPU, per una data
istruzione, ricava il riferimento al dato su cui dovr operare. Per esempio, abbiamo gi
incontrato alcune forme diverse di trasferimento dati (p.e. le istruzioni LD), che si differenziano
tra di loro per la locazione diversa degli operandi sorgente e destinazione:
LD
LD

A,(OPE_1)
B,A

;carica in A il contenuto di OPE_1


;copia in B il contenuto di A

In questo caso possiamo notare che, pur trattandosi sempre di operazioni di trasferimento
identificate dal codice mnemonico LD, gli operandi si trovano, nei due casi, in posti differenti:
nella prima riga troviamo il byte da trasferire dalla memoria esterna, nella seconda riga esso si
trova in un registro interno.
La CPU ricava questa informazione dal codice macchina, che sar ovviamente diverso nei due
casi. In generale, come gi si visto, il codice macchina di una istruzione DMC8 composto
da uno a quattro byte disposti di seguito in memoria. Il primo byte sempre il "codice operativo"
della istruzione, e contiene le indicazioni che servono al sequenziatore per "lanciare" la
sequenza di operazioni elementari interne ed esterne. Il codice operativo contiene anche
informazioni sul reperimento degli operandi, che vengono utilizzate dal sequenziatore per
eseguirne il corretto indirizzamento.
Le varianti possibili dei modi di indirizzamento del DMC8 sono i seguenti:
a)
b)
c)
d)
e)
f)
g)
h)
i)

Indirizzamento IMMEDIATO
Indirizzamento IMMEDIATO ESTESO
Indirizzamento DIRETTO
Indirizzamento INDIRETTO tramite REGISTRO
Indirizzamento INDIRETTO tramite REGISTRO INDICE
Indirizzamento di REGISTRO
Indirizzamento IMPLICITO
Indirizzamento del BIT
Indirizzamento MODIFICATO

Una istruzione pu avere uno, due o nessun operando. Per ciascun operando, l'istruzione
adotta un particolare modo di indirizzamento. Tuttavia non tutti i modi di indirizzamento sono
compatibili tra di loro: non sono ammesse tutte le combinazioni.
Per esempio, non possibile trasferire, con una sola istruzione, un byte da una locazione di
memoria ad un'altra: un istruzione del tipo "LD (3500h),(1F00h)" non prevista dal DMC8.
Quando un trasferimento non si pu realizzare con ununica istruzione, dovremo utilizzare pi
istruzioni, utilizzando un registro di transito, che spesso il registro accumulatore A. In questo
caso, ad esempio:
LD
LD

A,(1F00h)
(3500h),A

;copia in A il contenuto della locazione 1F00h


;copia nella locazione 3500h il contenuto di A

Esamineremo ora, in dettaglio, i principali modi di indirizzamento.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

6-1

6.1

Indirizzamento IMMEDIATO (dati a 8 bit)


Nel modo immediato l'operando, costituito da 8 bit, posto immediatamente dopo il codice di
istruzione. Negli esempi seguenti, il dato da caricare nel registro destinazione si trova nel byte
successivo a quello del codice operativo.
Esempi:
Istruzione:
LD
A,00h

->

LD

->

B,5Fh

Traduzione:
3Eh (codice operativo)
00h (dato immediato da trasferire in A)
06h (codice operativo)
5Fh (dato immediato da trasferire in B)

Al momento della esecuzione del programma, dopo avere eseguito il prelievo del codice
operativo, il microprocessore preleva immediatamente l'operando sorgente dal byte
successivo, utilizzando semplicemente il registro PC (Program Counter) per indirizzarlo.

6.2

Indirizzamento IMMEDIATO ESTESO (per dati a 16 bit)


Nel modo immediato esteso l'operando, costituito da 16 bit suddivisi in 2 byte, posto
immediatamente dopo il codice di istruzione, analogamente al caso precedente. Vedi esempio
seguente.
Esempio:
Istruzione:
LD
HL,1A57h

->

Traduzione:
21h (codice operativo)
57h (dato immediato, parte "Low")
1Ah (dato immediato, parte "High")

Il processore, per eseguire questa istruzione, legger i due byte che seguono il codice
operativo, trasferendoli rispettivamente nelle parti L e H del registro accoppiato HL. Anche qui
si utilizza semplicemente il registro PC (Program Counter) per indirizzare i due byte, uno dopo
laltro.
Altri esempi:
LD
SP,100Ah
LD
BC,0FAFFh

6.3

;inizializza a 100Ah lo 'Stack Pointer'


;carica il numero FAFFh nel registro 'BC'

Indirizzamento DIRETTO
L'indirizzamento DIRETTO si ha quando subito dopo il codice di istruzione si trova lindirizzo di
memoria dell'operando. Distinguiamo due sotto-modi di indirizzamento diretto, a seconda
della dimensione dell'operando:

6.3.1

Indirizzamento DIRETTO di dato a 8 bit:


Esempi:
Istruzione:
Traduzione:
LD
(0E000h),A -> 32h (codice operativo)
00h (indirizzo, parte "Low")
E0h (indirizzo, parte "High")
Istruzione:
Traduzione:
IN
A,(20h)
-> DBh (codice operativo)
20h (indirizzo ad 8 bit del Porto)

Nel primo esempio, dopo il codice operativo, troviamo l'indirizzo E000h (a 16 bit), suddiviso in
due byte, dell'operando (a 8 bit). Il processore utilizzer questo indirizzo, dopo averne
ricomposto insieme le parti Low e High, per indirizzare la memoria e scrivervi il dato (un byte),
che viene copiato dal registro accumulatore A.
Nel secondo esempio, dopo il codice operativo, il processore trova l'indirizzo, in questo caso a 8
bit) del porto di ingresso dal quale si vuole leggere un byte, che verr quindi ricopiato nel
registro A (le tecniche di ingresso/uscita saranno approfondite pi avanti).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

6-2

Notate in entrambi i casi la presenza delle parentesi intorno all'indirizzo del dato, che indicano
che l'operando lindirizzo del dato e non il dato stesso.
Altri esempi:

6.3.2

LD

A,(0E000h)

LD

(845Fh),A

OUT

(0FFh),A

;copia nel registro A il contenuto


;della locazione di memoria E000h
;copia il registro A nella locazione
;di memoria 845Fh
;copia il contenuto del registro A nel
;porto di uscita (all'indirizzo FFh)

Indirizzamento DIRETTO di dato a 16 bit:


Esempio:

Istruzione:
Traduzione:
LD
HL,(120Fh) -> 2Ah (codice operativo)
0Fh (indirizzo, parte "Low")
12h (indirizzo, parte "High")

Anche in questo esempio, dopo il codice operativo, il processore trova l'indirizzo a 16 bit
dell'operando, ma questa volta anche loperando a 16 bit (sintatticamente lo si capisce dal
fatto che la destinazione specificata un registro a 16 bit). Il processore utilizzer questo
indirizzo, dopo averne ricomposto insieme le parti Low e High, per puntare alla memoria e
prelevare:
a) il byte all'indirizzo specificato, che verr caricato nel registro L e, quindi:
b) il byte all'indirizzo specificato pi uno, che verr caricato nel registro H.
Il risultato finale il trasferimento di un dato a 16 bit, effettuato in due sotto-trasferimenti da un
byte ciascuno. Anche qui, fate attenzione alle parentesi intorno all'indirizzo del dato, che
mettono in evidenza il fatto che l'operando lindirizzo del dato e non il dato stesso.
Altri esempi:

6.4

LD

(82AFh),HL

LD

BC,(1A00h)

;copia il registro HL nelle locazioni di


;memoria 82AFh (parte L) e 82B0 (parte H)
;copia le due locazioni di memoria 1A00h
;e 1A01h rispettivamente nelle parti C
;(low) e B (high) del registro BC

Indirizzamento INDIRETTO tramite REGISTRO


In questo caso il contenuto di un registro accoppiato a 16 bit (BC, DE o HL) specificato nel
codice di istruzione, viene usato come indirizzo della locazione di memoria che contiene
loperando. Questo modo si chiama cos poich, per reperire l'indirizzo dell'operando, il
processore esegue un passaggio intermedio: la consultazione di un registro interno.
Esempio:

Istruzione:
LD
C,(HL)

->

Traduzione:
4Eh (codice operativo)

In questo esempio, nel registro C viene trasferito il byte di memoria il cui indirizzo si trova nel
registro accoppiato a 16 bit HL. Naturalmente necessario avere precedentemente inizializzato
tale registro al valore desiderato.
Notate la compattezza del codice prodotto: un solo byte. Tutto ci che serve contenuto nel
byte di codice operativo senza bisogno di ulteriori specificazioni (salvo il contenuto del registro
HL). Questo modo di indirizzamento conveniente quando si deve accedere molte volte alla
stessa locazione e quando lindirizzo della locazione deve essere calcolato", come ad
esempio nel caso di tabelle di dati (vettori) gestite da indice.
Altri esempi:

LD

(HL),3Fh

ADD

A,(HL)

LD

(BC),A

;copia il valore immediato 3Fh nella


;loc. di memoria puntata dal registro HL
;somma al registro A il contenuto della
;loc. di memoria puntata dal registro HL
;(e metti il risultato di nuovo in A)
;copia il contenuto di A nella locazione
;di memoria puntata dal registro BC

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

6-3

6.5

Indirizzamento INDIRETTO tramite REGISTRO INDICE


Questo modo simile al precedente, ma pi complesso. In questo caso l'indirizzo del byte di
memoria da scrivere o leggere calcolato sommando al contenuto di uno degli appositi
Registri Indice IX o IY il valore contenuto nel byte che segue il codice operativo
dellistruzione. Quest'ultimo numero chiamato dislocazione (displacement), una costante
che pu essere sia positiva che negativa, ma compresa nellintervallo da -128 a +127.
Esempio:
Istruzione:
Traduzione:
LD
B,(IY+2Fh) -> FDh (codice operativo, primo byte)
46h (codice operativo, secondo byte)
2Fh (dislocazione [+47 in decimale])

Il codice operativo qui composto da due bytes (FDh e 46h), seguiti dalla dislocazione che
nell'esempio vale +47 (2Fh).
L'istruzione di questo esempio trasferisce nel registro B il contenuto della locazione di memoria
il cui indirizzo viene ricavato sommando al contenuto del registro IY la dislocazione 2Fh.
Ricordiamoci che IY e IX sono registri a 16 bit, non suddivisibili in due pezzi da 8 bit.
Altri esempi:
LD
(IX+33h),A
CP

6.6

(IX+01h)

;copia il contenuto di A nella locazione


;di memoria puntata dal registro IX + 33h
;confronta il contenuto del registro A
;(sottinteso) con il contenuto della locazione
;di memoria puntata dal registro IX + 01h

Indirizzamento di REGISTRO
In questo modo di indirizzamento, nel codice operativo sono gi contenute le informazioni che
specificano il registro (o i registri) della CPU su cui lavorare. Quindi il solo codice operativo
sufficiente per capire il ruolo che avranno i registri nell'istruzione da eseguire.
Esempio:
Istruzione:
LD
A,D

->

Traduzione:
7A
(codice operativo)

In questo esempio, l'istruzione richiede di effettuare la copia del contenuto del registro D in A.
Gli operandi sono entrambi registri e non necessario specificare indirizzi.
Il modo di indirizzamento di Registro spesso presente accanto ad altri modi: ad esempio in
quelle istruzioni di trasferimento dove possibile specificare pi registri destinazione o
sorgente, come nella istruzione "LD B,(HL)", dove si pu parlare di "Indirizzamento Indiretto
tramite Registro" per l'operando sorgente (HL), mentre per la destinazione B si osserva un
semplice "Indirizzamento di Registro".
Altri esempi:
CP
B
AND

6.7

;confronta il registro A (sottinteso)


;con il registro B (risultato: nei Flag)
;calcola l'AND logico tra il registro
;A (sottinteso) ed il registro L,
;fornendo il risultato in A

Indirizzamento IMPLICITO
In alcune istruzioni, l'operazione richiesta prevede l'uso di un registro predefinito. Ad esempio,
nelle operazioni aritmetiche e logiche l'accumulatore A sottinteso essere la destinazione fissa
dei risultati (vedi alcuni degli esempi precedenti).
Esempi:
Istruzione:
ADD
A,L
SCF
NOP

->
->
->

Traduzione:
85h (codice operativo) ; A <- A + L
37h (codice operativo)
00h (codice operativo)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

6-4

L'istruzione ADD A,L specifica esplicitamente i due addendi, ma il registro A che memorizza il
risultato e` implicito.
L'istruzione SCF (Set Carry Flag) agisce esclusivamente sul bit di Carry nel registro dei flags,
forzandovi un 1; usata spesso, ma non solo, in congiunzione con le istruzioni di Rotazione e
Scalamento.
Il modo implicito lo ritroviamo pure nella NOP (=No Operation). Questa istruzione non fa niente
e di fatto serve solo a far trascorrere 4 cicli di clock. Appartiene alle istruzioni aventi
indirizzamento implicito in quanto non vi sono operandi da indirizzare.

6.8

Indirizzamento del BIT


E' usato soltanto nelle istruzioni SET, RES e BIT. Permette di specificare un singolo bit tra gli
8 che costituiscono il byte di una locazione di memoria o di un registro.
Esempio:
Istruzione:
RES
2,B

->

Traduzione:
CB
(codice operativo, primo byte)
9E
(codice operativo, secondo byte)

In questo esempio, l'istruzione azzera il bit 2 del registro B. I bit sono numerati a partire dal bit 0
(LSB) fino al 7 (MSB): la selezione del bit inclusa nel codice operativo.
Attenzione che l'indice al bit pu essere soltanto una costante compresa tra 0 e 7, e non una
variabile (il numero del bit non si pu specificare con un registro, per esempio).
Altri esempi:
BIT
0,E
SET

6.9

;controlla se il bit in posizione 0 del


;registro E '1' oppure '0'
;poni a '1' il bit in posizione 5 della
; locazione di memoria puntata dal registro HL

5,(HL)

Indirizzamento MODIFICATO
L'indirizzamento modificato utilizzato soltanto dalle istruzioni RST (Restart), che obbligano il
processore a saltare (in un modo speciale) a otto diversi indirizzi di memoria predeterminati "di
pagina zero" (0000h, 0008h 0038h), utilizzando un solo byte di istruzione.
Per capire bene questa istruzione sar necessario approfondire prima alcuni concetti che
vedremo nei prossimi capitoli comunque, in questo esempio, il microprocessore viene forzato a
saltare alla locazione 0038h.
Esempio:
Istruzione:
RST
38h

->

Traduzione:
FFh (codice operativo)

Il salto "speciale", come detto sopra, perch analogo a quello effettuato dall'istruzione CALL,
che dobbiamo ancora incontrare; si dice anche che le istruzioni RST generano degli Interrupt
Software, perch il meccanismo di esecuzione simile a quello degli Interrupt Hardware, che
vedremo.
In altri processori questa funzione e' denominata INT (interrupt) o TRAP (trappola). Forzano il
processore ad eseguire dei compiti che il programmatore ha reso accessibili tramite dei
sottoprogrammi (che vedremo nel prossimo capitolo), richiamabili velocemente tramite queste
istruzioni (erano famose le INT del sistema operativo MS-DOS, su processori 80x86).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

6-5

Le istruzioni del microprocessore DMC8


E` conveniente suddividere le istruzioni del microprocessore DMC8 in categorie funzionali.
1)
2)
3)
4)
5)
6)
7)
8)

7.1

Istruzioni di Caricamento;
Istruzioni Aritmetiche e Logiche;
Istruzioni di Rotazione e Scalamento;
Istruzioni di Manipolazione del Bit;
Istruzioni di Salto;
Istruzioni di Chiamata e Ritorno da Sottoprogrammi;
Istruzioni di Ingresso e Uscita;
Istruzioni di Controllo della CPU.

Istruzioni di Caricamento
Le istruzioni di caricamento (Load, dette anche di trasferimento) consentono di ricopiare dati da
registro a registro della CPU, oppure da registro CPU alla memoria e viceversa. Sono
previste istruzioni per lavorare sia su dati a 8 bit che su dati a 16 bit (intesi come coppie di
byte). Si presentano nelle forma seguente:
LD
<destinazione>, <sorgente>
Ossia: "ricopia l'operando <sorgente> nell'operando <destinazione>" (l'ordine rovesciato
tipico di molti linguaggi Assembly).

7.1.1

Istruzioni di Caricamento a 8 bit


A seconda del modo di indirizzamento, l'elemento sorgente pu essere:
Un valore immediato (8 bit):
Esempio:
LD

A,3Bh

;Copia in 'A' il valore 3Bh (0011.1011b)

Il contenuto di un registro a 8 bit:


Esempio:
LD

A,B

;Copia in 'A' il byte contenuto in 'B'

Il contenuto di una locazione di memoria:


Esempio:
LD

A,(0F001h)

LD

C,(HL)

;Copia in 'A' il byte di memoria che si


;trova all'indirizzo F001h
;Copia in 'C' il byte di memoria che si
;trova all'indirizzo specificato nel
;registro a sedici bit 'HL'

L'elemento destinazione pu essere:


Un registro a 8 bit:
Esempio:

LD

B,E

;Copia in 'B' il byte contenuto in 'E'

Una locazione di memoria, se l'elemento sorgente e` un registro:


Esempio:

LD

(0F305h),A

;Copia il contenuto nel registro 'A'nella loc.


;di memoria che si trova all'indirizzo F305h

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-1

Come gi detto nel capitolo precedente, questo microprocessore non ammette tutte le
combinazioni dei modi di indirizzamento, ed e` necessario verificare sulle tabelle delle istruzioni,
di volta in volta, se una certa combinazione e` ammessa.

7.1.2

Istruzioni di Caricamento a 16 bit


Le istruzioni di caricamento a 16 bit in realt sono eseguite dal processore come se si trattasse
di due istruzioni consecutive di caricamento a 8 bit. La sintassi e` uguale a quelle a 8 bit:
LD

<destinazione>, <sorgente>

Ma gli operandi sono a 16 bit. I registri che possono figurare come operandi sono i registri
"accoppiati" BC, DE e HL oppure i registri (propriamente a 16 bit) SP, IX e IY. A seconda del
modo di indirizzamento, l'elemento sorgente pu essere:
Un valore immediato (16 bit):
Esempio:
LD

BC,5F3Dh

;Copia nel registro a 16 bit 'BC'


;il valore 5F3Dh (0101.1111.0011.1101b)

Il contenuto di un registro a 16 bit:


Esempio:
LD

SP,HL

;Copia nel registro 'SP' il contenuto di 'HL'

Il contenuto di due locazioni di memoria consecutive (16 bit in totale):


Esempio:
LD

HL,(0F140h)

;Copia in 'HL' i due bytes che si trovano


;nelle locazioni di memoria agli indirizzi
;F140h (Low -> 'L') e F140h+1 (High -> 'H')

La coppia di locazioni specificata con il solo indirizzo della prima. Gli operandi a 16 bit allocati in
memoria sono caratterizzati dal byte meno significativo all'indirizzo pi basso (quello
specificato sulla riga del codice operativo mnemonico) e dal byte pi significativo all'indirizzo
successivo.

L'elemento destinazione pu essere:


Un registro a 16 bit:
Esempio:
LD

IX,8001h

;Copia nel registro 'IX' il valore 8001h

Due locazioni di memoria consecutive:


Esempio:
LD

(0F140h),HL

;Copia i due bytes che si trovano nelle parti


;Low e High del registro a 16 bit 'HL'
;rispettivamente nelle locazioni di memoria
;poste agli indirizzi F140h e F140h+1

Anche nel caso delle operazioni di caricamento a 16 bit, non tutte le combinazioni di modi di
indirizzamento sono ammesse, e si consiglia di consultare sempre le tabelle riassuntive delle
istruzioni.
Appartengono a questo gruppo anche le istruzioni di trasferimento di coppie di byte da e per
l'area di memoria chiamata Stack (Catasta), che non abbiamo ancora esaminato. Solo per
completezza riportiamo qui due esempi:
Esempi:
PUSH
POP

HL
IX

;salva in cima alla catasta il contenuto di 'HL'


;recupera dalla catasta il contenuto di 'IX'

Ne parleremo in dettaglio pi avanti, nel paragrafo relativo alle istruzioni di Chiamata e Rientro
da Sottoprogrammi. Questo tipo di istruzioni sono molto importanti, e le useremo
frequentemente.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-2

7.2

Istruzioni Aritmetiche e Logiche


Le istruzioni Aritmetiche (Arithmetic) e Logiche (Logic) consentono di lavorare con dati a 8 e a
16 bit. L'uso di questo gruppo di istruzioni, che si avvale della ALU (unit Logico-Aritmetica),
particolarmente interessante perch supportato da diversi tipi di indirizzamento, che ci
consentono una scrittura di programmi sufficientemente "eleganti".
Tuttavia, come vedremo, le operazioni supportate sono di tipo elementare: per esempio, non
abbiamo istruzioni per effettuare direttamente le moltiplicazioni e/o le divisioni. In ogni caso,
qualunque funzione non implementata si pu realizzare lo stesso, a partire dalle istruzioni
elementari. Ovviamente, la velocit di esecuzione sarebbe molto pi elevata se l'istruzione fosse
supportata da un opportuno hardware specializzato all'interno del processore (si pensi per esempio
ai cosiddetti "coprocessori matematici" dei processori pi potenti).

7.2.1

Istruzioni Aritmetiche a 8 bit


Le istruzioni aritmetiche a 8 bit del DMC8 usano l'accumulatore A come primo operando e
come destinazione del risultato, mentre il secondo operando, se c', pu essere:
a) Un valore immediato a 8 bit;
b) Il contenuto di un registro a 8 bit;
c) il contenuto di una locazione di memoria, specificata con indirizzamento indiretto tramite
HL, o i registri indice IX o IY.
Vediamo l'istruzione di somma, che ha la forma seguente, dove con l'abbreviazione s si intende
il generico operando sorgente:
ADD

A,s

;somma ad 8 bit (A = A + s)

Questa istruzione somma al registro accumulatore A la sorgente s, riponendo il risultato in A.


Il precedente contenuto di A viene ovviamente perduto. In uscita, il flag di riporto (Carry) e`
posto a uno o a zero se nella operazione si e` verificato riporto oppure no.
L'istruzione ADD, esplicitando i modi di indirizzamento ammessi per la sorgente s, pu
assumere (solo) una delle seguenti forme:
ADD
ADD
ADD
ADD
ADD

A,01h
A,B
A,(HL)
A,(IX+16)
A,(IY+16)

;un
;un
;la
;la
;la

valore immediato (qui pari a 01h)


registro (qui il registro B)
locazione di memoria puntata da HL
loc. di mem. puntata da IX +16 (per esempio)
loc. di mem. puntata da IY +16 (per esempio)

Una variante importante dell'istruzione di somma la seguente:


ADC

A,s

;somma ad 8 bit (A = A + s + Carry)

Questa istruzione come la precedente, solo che in questo caso la ADC tiene conto, nel fare il
calcolo, anche del riporto eventualmente gia` presente nel flag di Carry. In altre parole, somma
al registro accumulatore A la sorgente s, pi 1 se nel flag di Carry abbiamo memorizzato un
riporto (che proviene, naturalmente, da una operazione precedente), e ripone il risultato in A.
Come nella ADD, il precedente contenuto di A viene ovviamente perduto e, in uscita, il flag di
riporto (Carry) e` posto a uno se si e` verificato riporto in questa operazione (il precedente
valore del Carry, utilizzato nel fare il calcolo, viene sovrascritto).
Una istruzione che effettua la sottrazione la seguente:
SUB

;differenza ad 8 bit (A = A - s)

Loperando sorgente s pu essere degli stessi tipi della istruzione aritmetica ADD. Loperando
A implicito, perch la SUB non pu avere altra destinazione per il risultato. Questa istruzione
impone alla ALU di sottrarre dal registro accumulatore A la sorgente s, e di sovrascrivere
l'accumulatore stesso con il risultato (il precedente contenuto di A viene perduto). In uscita, se

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-3

la sottrazione ha richiesto un prestito, viene posto a uno il flag di riporto Carry (che quindi
viene usato anche come prestito (Borrow), non e` stato previsto un flag apposito).
Anche nel caso seguente abbiamo la variante "con il prestito in ingresso":
SBC

A,s

;differenza ad 8 bit (A = A - s - Carry)

analoga alla precedente, con la sola differenza di lavorare tenendo conto dell'eventuale
prestito presente nel flag di Carry: sottrae dal registro A la sorgente s, meno 1 se nel Carry
abbiamo 1 (il prestito). In risultato finisce nuovamente nel registro A. Il prestito in uscita e`
gestito come nella precedente SUB, e il nuovo valore del Carry sovrascriver il precedente.
Un istruzione importante, necessaria per effettuare confronti aritmetici, la seguente:
CP

;confronto a 8 bit, per differenza (A - s)

Effettua il confronto tra l'accumulatore A e la sorgente s, eseguendo di fatto una sottrazione


algebrica senza memorizzarne il risultato. Gli operandi, compreso quello contenuto
nell'accumulatore, rimangono invariati. L'informazione utile, cio il risultato del confronto (p.e. "A
maggiore di s") invece memorizzata nei flags denominati Carry, Zero e Sign, secondo la
seguente tabella:
Risultato
A>s
A=s
A<s

Carry
0
0
1

Zero
0
1
0

Sign
0
0
1

Sign significativo nel caso di confronto tra numeri con segno in complemento a due. Nel caso
di confronto tra numeri a 8 bit senza segno, sono importanti i flag di Carry e di Zero.
Poco pi avanti, esaminando le istruzioni di salto condizionato, capiremo come i flag
rivestono una grande importanza nella programmazione Assembly.

7.2.2

Istruzioni Logiche
Le istruzioni logiche del DMC8 sono soltanto a 8 bit. Si tratta delle seguenti:
AND
OR
XOR

s
s
s

; A = (A AND s), bit a bit


; A = (A OR s), bit a bit
; A = (A EXOR s), bit a bit

In queste operazioni logiche l'operando implicito sempre l'accumulatore A, mentre per


l'operando s valgono gli stessi modi di indirizzamento dell'istruzione ADD vista in precedenza. Il
risultato dell'operazione sovrascrive l'operando presente nell'accumulatore A.
L'operazione logica eseguita bit a bit, ed in realt costituita da 8 identiche operazioni
logiche in parallelo, una per ciascun bit e indipendentemente un bit dall'altro. Ad esempio, la
AND B esegue l'operazione (A and B) nel modo seguente:
A7 = A7 and B7
A3 = A3 and B3

A6 = A6 and B6
A2 = A2 and B2

A5 = A5 and B5
A1 = A1 and B1

A4 = A4 and B4
A0 = A0 and B0

Le operazioni logiche modificano il flag di Zero, che viene attivato se tutti i bit del risultato
sono zero. Per questo motivo, sono molto utili per "isolare" e testare gruppi di bit. Per
esempio, leggendo i commenti riportati nel seguente stralcio di codice:
Esempio:
LD
AND

A,(0F000h)
07h

JP

Z,ALTROVE

;Portiamo il dato nel registro A


;A = (A and 0000.0111b), i bit 7, 6, 5, 4 e 3
;sono azzerati grazie alla "maschera", mentre
;restano invariati i bit 2, 1 e 0
;Qui testiamo se i bit 2, 1 e 0 sono tutti zero
;(Salta ad ALTROVE se lo sono)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-4

In questo esempio, il dato caricato nell'accumulatore A viene "mascherato", nel senso che
alcuni bit sono forzati a zero (perch messi in AND con il corrispondente 0 della maschera),
mentre gli altri sono lasciati inalterati (perch in AND con un 1). L'istruzione successiva
controlla poi se il risultato dell'operazione zero (si tratta di un salto condizionato, che vedremo
tra poco).
Dato che i bit 7, 6, 5, 4, e 3 sono stati azzerati dalla mascheratura, il risultato "zero" dipender
soltanto dal fatto che i bit 2, 1 e 0 siano tutti a zero.
In Assembly capita spesso di utilizzare tecniche apparentemente "astruse", ma necessarie, perch
il fine di ottenere programmi il pi possibile compatti ed efficienti, anche se questo significa
sovente rendere poco "leggibili" i programmi stessi.

7.2.3

Istruzioni Aritmetiche a 16 bit


Le istruzioni aritmetiche a 16 bit del DMC8 operano usando come accumulatore il registro
accoppiato HL oppure i registri indice IX o IY. Il secondo operando pu essere soltanto un
registro interno a 16 bit e non tutte le combinazioni sono possibili. Sono possibili operazioni di
somma (con o senza riporto in ingresso) e di differenza (con prestito). Ecco alcuni esempi:
ADD
ADD
ADD

HL,BC
HL,HL
IX,DE

;Somma a 16 bit: HL = HL + BC
;Raddoppia il contenuto di HL (piccolo trucco)
;Somma a 16 bit: IX = IX + DE

Non si tratta di vere operazioni a 16 bit, perch l'ALU da 8 bit: l'operazione scomposta
internamente in due fasi successive, prima sul byte "basso" e poi sul byte "alto", ma dall'esterno
questo dettaglio non e` osservabile (se non nel tempo richiesto per effettuare l'operazione).

7.2.4

Istruzioni di Incremento e Decremento a 8 bit


Le istruzioni di incremento e decremento a 8 bit del DMC8 operano su un registro oppure su
una locazione di memoria, ottenuta per indirizzamento indiretto (HL) o indice (IX o IY).
INC
INC

B
(HL)

DEC

;incrementa il registro B
;incrementa la locazione di memoria puntata
;dal registro HL
;decrementa il registro H

L'incremento o decremento sempre di una unit, e l'operazione influenza i flag di Zero e di


Sign, ma non quello di Carry. Le operazioni di incremento e decremento sono cicliche:
Esempi:

LD
INC
INC

C,0FEh
C
C

DEC

;predispone il registro C al valore massimo -1


;incrementa il registro C, ora vale FFh
;incrementa il registro C ma (poiche`
;l'incremento e` ciclico) ora vale 00h
;decrementa il registro C, che ora vale FFh
;(anche il decremento e` ciclico)

Grazie a queste istruzioni, sar facile utilizzare i registri, per esempio, come contatori.

7.2.5

Istruzioni di Incremento e Decremento a 16 bit


Le istruzioni di incremento e decremento a 16 bit possono operare soltanto sui registri BC, DE,
HL, IX e IY, e non sulla memoria. Anche in questo caso l'incremento o il decremento di una
sola unit, e l'operazione ciclica.
INC
DEC

HL
IX

;incrementa il registro accoppiato HL


;decrementa il registro indice IX

Attenzione: purtroppo, per ragioni storiche e di realizzazione hardware, le operazioni di


incremento e decremento a 16 bit NON influenzano i flag, contrariamente al normale buon
senso, e di questo dovremo tenere conto in seguito, al momento di scrivere programmi.
Questo genere di "eccezioni" molto frequente nei microprocessori: per questo motivo questa
"anomalia", che era presente nello Z80, per motivi didattici stata mantenuta anche nel DMC8.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-5

7.3

Istruzioni di Rotazione e Scalamento


Le istruzioni di Rotazione (Rotate) e Scalamento (Shift) operano su dati sempre da 8 bit.
L'operando pu essere un qualunque registro interno a 8 bit oppure direttamente una locazione
di memoria ( una delle "eccezioni" alla solita regola che - per molte altre istruzioni - impone di
usare l'accumulatore A come tramite per operare).
Si distinguono operazioni di:
a) Rotazione;
b) Scalamento di tipo logico;
c) Scalamento di tipo aritmetico.
Esaminiamone alcuni esempi; si suggerisce poi di consultare la tabella delle istruzioni.
RLCA

; "Rotate Left Circular Accumulator"

Questa istruzione di rotazione, come si vede nella figura sulla destra dell'esempio, ruota a
sinistra i bit presenti nell'accumulatore, come se appartenessero ad un buffer circolare ad otto
posizioni. In pratica ogni bit del registro, dopo l'esecuzione della istruzione, si trover spostato
a sinistra di una posizione: il bit 7, quello pi a sinistra, verr spostato circolarmente in quello
pi a destra.
Un dettaglio importante di questa istruzione: il bit 7 viene anche ricopiato nel flag di Carry (CY).
Non si tratta ovviamente di un riporto aritmetico, ma questa propriet interessante perch
permette di testare il flag (con una istruzione di salto condizionato, vedremo) e quindi di
conoscere il valore del bit spostato ad ogni rotazione.
RR

; "Rotate Right" D

In questo esempio viene ruotato verso destra il registro D. I bit ruotano ma, a differenza del
caso precedente, il bit 0 viene trasferito nel flag di Carry, ed il contenuto precedente del Carry
nel bit 7: insomma il flag di Carry viene sfruttato come fosse un nono bit del registro. In questo
caso una rotazione completa avverrebbe eseguendo nove istruzioni consecutive di questo tipo.
SLA

; "Shift Left Arithmetic" B

Questa istruzione di scalamento sposta a sinistra i bit presenti nel registro B, inserendo da
destra uno zero. Per le istruzioni di scalamento il meccanismo simile a quello della rotazione,
solo che il bit fuoriuscito non viene riportato all'altro lato.
Facciamo un esempio. Supponiamo che nel registro B ci sia inizialmente il numero binario
0001.0100b (20, in decimale): dopo l'esecuzione della nostra istruzione avremo: 0010.1000b
(40, in decimale). Il bit fuoriuscito viene salvato nel flag di Carry (in questo esempio: 0).
Se osservate i due numeri, prima e dopo l'operazione, lo scalamento verso sinistra ed il
riempimento del bit pi a destra con uno zero, da un punto di vista aritmetico, equivale alla
moltiplicazione per due del numero iniziale (l'eventuale overflow viene memorizzato nel flag di
Carry).
Uno scalamento a destra, invece, pu essere di tipo aritmetico o logico: dipende dal
trattamento riservato al bit 7. Qui di seguito, il primo esempio riporta una operazione logica
perch, nello scorrimento, da sinistra viene semplicemente inserito uno zero:
SRL

; "Shift Right Logic" E

SRA

; "Shift Right Arithmetic" H

Nel secondo esempio, invece, l'operazione aritmetica perch il bit 7 viene ricopiato su se
stesso. Infatti, cos facendo riusciamo a mantenere il segno dell'operando (quando
rappresentato come numero con segno in complemento a due), anche dopo l'operazione di
scalamento. In questo caso l'operazione equivale ad una divisione per due, che vale anche per i
numeri negativi (in complemento a due).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-6

7.4

Istruzioni di Manipolazione del Bit


Queste istruzioni permettono di esaminare, oppure porre ad '1' o a '0', un particolare bit di
qualsiasi registro della CPU o di una locazione di memoria specificata. Il bit viene indicato con
un numero, che ne identifica la posizione: 7 [MSB], 6, 5, 4, 3, 2, 1, 0 [LSB]. Ad esempio:
BIT
BIT

3,D
7,(HL)

;testa il bit 3 (il quarto da destra) di D


;testa il bit 7 (il pi a sinistra) della
;locazione di memoria puntata dal registro HL

Queste istruzioni eseguono il test del bit richiesto, senza utilizzare l'accumulatore. Se il bit
richiesto zero, viene attivato il flag di Zero; se il bit uno, il flag di Zero viene azzerato.
Le altre due istruzioni di manipolazione del bit sono la RES e la SET, qui esemplificate:
RES
SET

5,E
7,(HL)

;azzera il bit 5 (il terzo da sinistra) di E


;metti a uno il bit 7 (il pi a sinistra) della
;locazione di memoria puntata dal registro HL

Ricordiamoci che la posizione del bit pu essere indicata soltanto con una costante.

7.5

Istruzioni di Salto
Se non esistessero le istruzioni di salto (Jump), i computer servirebbero a ben poco Questa
classe di istruzioni infatti importantissima, dal momento che consente al programmatore di
alterare in maniera controllata ed esplicita la sequenza di esecuzione del programma, come
si pu fare nei linguaggi ad alto livello (con l'istruzione GOTO). Il controllo dell'esecuzione
pu, grazie ad una istruzione di salto, essere passato da una parte all'altra del programma.
Le istruzioni di salto agiscono sul contenuto del Program Counter (PC), registro interno che,
come si visto in precedenza, responsabile della sequenza di esecuzione delle istruzioni.

7.5.1

Salti Incondizionati
Esaminando le tabelle delle istruzioni, il PC sembrerebbe inaccessibile al programmatore, nel
senso che questi, attraverso le normali istruzioni LD di trasferimento dati, non pu scrivervi o
leggervi in modo esplicito.
Tuttavia, l'esecuzione dell'istruzione di salto consiste proprio nella trascrizione dentro al
PC dell'indirizzo specificato dal programmatore nel campo operando, come se si trattasse di
una (inesistente) LD PC,<indirizzo>.
La pi usata istruzione di salto incondizionato ha la forma seguente:
JP

<indirizzo>

;salta all'indirizzo specificato

Spesso l'indirizzo (a 16 bit) viene indicato tramite un simbolo (p.e. JP START). L'esecuzione di
questa istruzione produce l'assegnazione del valore dell' <indirizzo> al Program Counter, e
quindi il prelievo della successiva istruzione sar eseguito non pi dalla locazione
successiva a quella della istruzione corrente (la JP <indirizzo>), ma dalla locazione
all'<indirizzo> specificato.
Esempio di salto in avanti (sono indicati, in questo caso, gli indirizzi delle istruzioni):
Indirizzo:
10FFh
1100h
1103h

2000h
2001h

Istruzione:
LD
A,B
JP
2000h
NOP

CP
B
LD
B,E

;Commento:
;(istruzione precedente qualunque)
;salta alla locazione 2000h
;questa istruzione non e` eseguita, poiche` il
;microprocessore "salta" alla 2000h:

;da dove riparte ad eseguire un altro


;segmento di codice

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-7

In questo esempio, il microprocessore, giunto all'indirizzo 1100h, trova un istruzione di salto


incondizionato. La successiva istruzione eseguita sar quella all'indirizzo 2000h. Tutto ci che
si trova in mezzo (nell'esempio, la NOP, ecc) viene semplicemente "scavalcato" e ignorato.
Esempio di salto all'indietro (questa volta, per esercizio, usiamo le etichette):
LOOP:

ADD
LD
ADD

AND
JP
NOP

A,D
B,A
A,D

;(istruzione precedente qualunque)


;questa e` l'istruzione a cui si saltera`
;qui continua il codice...

B
LOOP

;...ultima operazione prima del salto


;salta indietro alla istruzione definita da LOOP
;...le successive istruzioni presenti
;da qui in avanti vengono ignorate

Ricordiamo che LOOP un simbolo che rappresenta un indirizzo: l'istruzione JP LOOP indica
un salto all'indirizzo identificato dall'etichetta LOOP.
Questo un esempio di ciclo infinito: a causa del salto all'indietro alla locazione LOOP,
verranno ripetute all'infinito le istruzioni comprese tra l'etichetta LOOP ed il salto JP LOOP.
Un ciclo infinito ha generalmente scarsa rilevanza pratica, eccetto che in pochi casi: per
esempio quando si vuole che un programma ripeta sempre uno stesso gruppo di operazioni,
fino allo spegnimento fisico del sistema. Vedremo pi avanti come una Interruzione (Interrupt)
permetter al microprocessore di uscire da un ciclo infinito, e andare ad eseguire un altro
programma.
Il tipo di salto ora esaminato si chiama Incondizionato poich viene eseguito sempre, senza
sottostare a condizioni. Qui osservate la sua codifica in linguaggio macchina (tre byte):
Esempio:
JP

7.5.2

34F0h

->

C3
F0
34

;codice operativo, seguito dalle


;parti "Low" e
;"High" dell'indirizzo di salto

Salti Condizionati
I tipi di salto pi importanti dal punto di vista computazionale sono quelli Condizionati. Questi
salti sono eseguiti o no dal processore a seconda dello stato di una ben precisa condizione,
e permettono alla macchina di prendere decisioni. La sintassi generale di un'istruzione di
salto condizionato :
JP

<condizione>,<indirizzo>

Come nei salti incondizionati, anche qui l'indirizzo indica la locazione a cui saltare, mentre la
<condizione> determina se il salto pu essere effettuato o no.
Scopriamo finalmente a cosa servono i FLAG: la <condizione> di cui si parla infatti fornita
unicamente dallo stato logico dei Flag.
Tra le varie condizioni possibili, ne vediamo solo alcune, quelle pi usate:
JP

C, 11A0h

;salta alla locazione 11A0h se Carry = 1

JP

NC,3F00h

;salta alla locazione 3F00h se Carry = 0

JP

Z, 1F00h

;salta alla loc.ne 1F00h se il Flag di Zero = 1


;(cioe` se il risultato precedente e` stato ZERO)

JP

NZ,8000h

;salta alla loc.ne 8000h se il Flag di Zero = 0


;(cioe` se il ris. prec. e` stato NON ZERO)

Il salto viene eseguito solo se la condizione verificata, in caso contrario il processore


prosegue con l'istruzione successiva a quella del salto, come se niente fosse successo.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-8

Anche nel caso del salto condizionato, pu essere utile conoscerne alcuni esempi di codifica
(notate che il codice operativo cambia a seconda della condizione):
Esempi:

7.5.3

JP

Z,12BCh

JP

NC,8811h

-> CA
BC
12
-> D2
11
88

;codice operativo, seguito dalle


;parti "Low" e
;"High" dell'indirizzo di salto
;
;

(per approfondire, consultate


la tabella delle istruzioni)

Un esempio di applicazione dei salti condizionati: i Cicli di Ritardo


Esaminiamo ora una importante applicazione dei salti condizionati: i cosiddetti Cicli di Ritardo.
Molto frequentemente, un sistema a microprocessore sar chiamato a generare, nel tempo, una
sequenza di controlli e attivazioni, lasciando trascorrere precise quantit di tempo tra un'azione
e l'altra. Si pensi ad esempio ad un sistema antifurto: prima di attivare l'allarme, si dar tempo al
legittimo proprietario di disinnestare la protezione (con un'attesa di qualche secondo).
Per un microprocessore, lasciare trascorrere il tempo senza fare apparentemente nulla
significa generalmente eseguire un ciclo di ritardo. Qui ne vediamo un esempio semplice:
LOOP:

LD
DEC
JP

C,0FFh
C
NZ,LOOP

;inizializza un "Contatore"
;decrementa il contatore ad ogni ciclo
;salta indietro se il risultato del decremento
;NON e` ZERO, altrimenti esce dal ciclo

In questo esempio di ciclo a contatore:


a) viene inizializzato un contatore (il registro C) prima di entrare nel ciclo;
b) all'interno del ciclo, il contatore viene decrementato di uno, ad ogni "giro";
c) sempre ad ogni "giro", il contatore viene controllato per sapere se il conteggio terminato:
se non lo , si salta indietro a LOOP, altrimenti si prosegue.
Il test viene effettuato osservando il flag di ZERO dopo l'operazione di decremento: se tale
operazione ha azzerato il registro, allora il flag stato attivato. Cosi`, saltiamo indietro a
LOOP solo se il risultato della precedente operazione non e` zero.
L'unico effetto significativo prodotto da questo pezzo di programma di lasciar trascorrere del
tempo, ossia di generare un ritardo. Proviamo a calcolare quanto ritardo genera questo
esempio. Supponiamo che il nostro microprocessore lavori con una frequenza di clock di 10
MHz: ogni ciclo corrisponde a 100 nS. Dalle tabelle delle istruzioni, consultabili nei capitoli a
seguire, risulta che le nostre istruzioni impiegano, per essere eseguite, rispettivamente:
LOOP:

LD
DEC
JP

C,0FFh
C
NZ,LOOP

; 7 cicli (di clock)


; 4 cicli
; 10 cicli (sempre, anche se non si salta)

Dato che C = FFh all'inizio, il ciclo viene eseguito 255 volte. Il tempo risultante sar:
(7 + 255 x (4+10)) x 100 nS = 3577 x 100 nS

= 0,3577 mS

Questo tempo pu essere facilmente calibrato con precisione, sia modificando il valore
iniziale di C, sia aggiungendo, eventualmente, altre istruzioni all'interno del ciclo, al solo fine di
aumentarne la durata. Per es., inseriamo due NOP e riduciamo il valore iniziale del contatore:
LOOP:

LD
NOP
NOP
DEC
JP

C,0E3h

C
NZ,LOOP

;
;
;
;
;

7 cicli (di clock), E3h = 227 decimale


4 cicli
4 cicli
4 cicli
10 cicli (sempre, anche se non si salta)

Otteniamo cosi` un tempo di circa mezzo millisecondo:


(7 + 227 x (4+4+4+10)) x 100 nS = 5001 x 100 nS

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

= 0,5001 mS

7-9

E` importante farsi un idea dell'ordine di grandezza dei tempi ottenibili (con il nostro
microprocessore con il clock a 10 MHz):
a) ordine del microsecondo o meno per l'esecuzione di una istruzione;
b) ordine del millisecondo per un semplice ciclo su contatore ad 8 bit e, vedremo adesso:
c) ordine delle centinaia di millisecondi per un ciclo semplice con conteggio su 16 bit.
Nel caso in cui si vogliano ottenere ritardi pi lunghi, dovremo ricorrere a tecniche un poco pi
complesse, come ad esempio quella dei cicli annidati (nested loops). Ad esempio:

L_EXT:
L_INT:

LD
LD
DEC
JP
DEC
JP

D,0FFh
C,0FFh
C
NZ,L_INT
D
NZ,L_EXT

;predisponi il contatore del ciclo "esterno"


;predisponi il contatore del ciclo "interno"
;decrementa il contatore "interno"
;salta se il risultato del decremento
;NON e` ZERO, prosegui altrimenti
;decrementa il contatore "esterno"
;salta se il risultato del decremento
;NON e` ZERO, altrimenti prosegui

Riconosciamo in questo esempio il ciclo dell'esempio precedente (nelle righe centrali),


annidato all'interno di un altro loop, identico nella forma, ma che -ovviamente- usa un altro
registro come contatore. In questo esempio, il ciclo pi esterno esegue 255 giri e, per ogni suo
giro, vengono eseguiti 255 giri di quello interno.
Prestate attenzione alle inizializzazioni dei contatori, che devono precedere i rispettivi cicli!
E` intuitivo che il tempo totale sar dato, in prima approssimazione, dal prodotto del tempo
impiegato dal ciclo interno per il numero di "giri" del ciclo esterno: in definitiva il tempo risulter
circa proporzionale al prodotto dei valori che carichiamo nei due contatori. Nel nostro caso:
(7+ (7+ 255 x (4+10) +4 +10) x 255) x 100 nS = 915712 x 100 nS

= 91,5712 mS

Ossia poco meno di un decimo di secondo.


Un altro modo per ottenere tempi di ritardo simili ai precedenti costituito dall'utilizzo di registri
a 16 bit per i conteggi, come nell'esempio che segue:

LOOP:

LD
DEC
LD
OR
JP

BC,0FFFFh
BC
A,B
C
NZ,LOOP

;predisponi il contatore a 16 bit BC


;decrementa il contatore
;controlla che il registro BC sia stato
;azzerato, mediante un OR tra B e C
;salta se BC NON e` ZERO, altrimenti...
;prosegui

In questo esempio, il conteggio avviene utilizzando l'istruzione DEC BC che effettua un


"decremento a 16 bit". Purtroppo questa categoria di istruzioni a 16 bit, come abbiamo visto,
non controlla i flag, e quindi siamo costretti a testare noi, dopo il decremento, l'effettivo
azzeramento del registro BC.
Dobbiamo quindi inserire nel programma una istruzione che modifica i flag: in questo caso,
aggiungiamo due istruzioni per effettuare una OR tra la parte alta B e la parte bassa C del
registro BC. Solo quando tutti i bit del registro BC saranno a zero, questa OR produrr un
risultato nullo, e quindi attiver il flag di Zero; altrimenti tale flag rimane non attivato e il
processore continuer a ciclare.
Trasferiamo una delle due met del registro BC nell'accumulatore A perch, per tutte le operazioni
aritmetiche e logiche ad 8 bit, avremo in questo registro sempre uno dei due operandi.

Facendo precisamente i conti, otteniamo per questo esempio i seguenti tempi:


(10+ 65535 x (6 +4 +4 +10)) x 100 nS = 1572850 x 100 nS

= 157,285 mS

In ultimo, ovviamente possibile combinare tutti questi metodi, in modo da ottenere ritardi
anche molto lunghi.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-10

7.6

Istruzioni di Chiamata e Ritorno da Sottoprogrammi


Prima di parlare delle Istruzioni di Chiamata (Call) e Ritorno (Return) da Sottoprogrammi,
occorre esaminare il funzionamento di una area speciale di memoria RAM, denominata Stack
(catasta, o pila, nel senso di catasta di oggetti).

7.6.1

Lo Stack e lo Stack Pointer


Lo Stack (la sua traduzione italiana si usa poco) e` un'area di memoria privilegiata, dove il
microprocessore pu salvare momentaneamente e poi recuperare dati di varia natura.
Precisiamo subito che quest'area e` speciale solo per l'uso che ne facciamo: dal punto di
vista hardware non ha niente di strano, anzi, e` semplicemente un'area della normale memoria
RAM. La differenza fondamentale nell'uso di un'area di memoria normale e di un'area Stack
risiede nel modo con cui vengono scritti e letti i dati.
In una memoria gestita normalmente, il programmatore fa eseguire al microprocessore delle
istruzioni ordinarie di trasferimento dati, scrivendo e leggendo dati in locazioni il cui indirizzo
viene deciso esplicitamente dal programmatore. Per esempio:
LD

LD

(2000h),A

;scrivo un dato in memoria

A,(2000h)

;rileggo il dato dalla memoria

In alcuni casi pero`, e` comodo non essere obbligati a conoscere esplicitamente l'indirizzo
del dato da trasferire. Questo e` possibile se nel processore si dispone di un meccanismo
automatico che faccia le nostre veci nel decidere gli opportuni indirizzi di memoria, mentre noi
ci occupiamo soltanto dei dati da trasferire.
Una catasta vi permette di sistemare una serie di oggetti uno sopra l'altro, senza preoccuparvi
di altro che della sequenza con cui li riponete e li recuperate. L'apparente svantaggio e`
rappresentato dal fatto che non potrete accedere immediatamente agli oggetti sottostanti la
cima della catasta: per evitare che la catasta crolli, sarete costretti a svuotare e riempire la
catasta ordinatamente per recuperare gli oggetti sottostanti.
In determinati casi, invece, questa limitazione costituisce un vantaggio: tra poco vedremo che,
prima di eseguire una specifica procedura, ci far comodo riporre provvisoriamente dei dati
in cima alla catasta e poi, 'a cose fatte', andarceli a riprendere. Nel fare questo, se disponiamo
di un dispositivo hardware interno al processore che risolve la gestione della catasta, non
dovremo preoccuparci esplicitamente dell'indirizzo delle locazioni di memoria che la
costituiscono, ma solo stare attenti all'ordine con cui vi riporremo i nostri dati, per poterli
recuperare nell'ordine corretto (inverso).
Il dispositivo hardware e` presente all'interno del microprocessore, ed e` costituito da un registro
speciale, chiamato Stack Pointer (SP, "Puntatore alla Catasta"), opportunamente gestito dal
sequenziatore.
Attenzione a non confondere i nomi: dentro al microprocessore troviamo solo il registro puntatore
alla catasta (lo Stack Pointer) e la sua logica di gestione, mentre la catasta vera e propria (lo
Stack) risiede fuori, nella normale RAM collegata al microprocessore. Nota: una memoria "gestita
a catasta" viene anche denominata anche struttura LIFO (Last Input - First OutPut), ossia "l'ultimo
dato inserito e` sempre il primo ad essere ripreso".

Il DMC8 non pre-definisce quale area della memoria si debba usare come catasta. Il
programmatore pu scegliere liberamente una qualsiasi zona della RAM disponibile nel nostro
hardware: deve semplicemente fare eseguire, tra le prime istruzioni del programma che
avvia il sistema a microprocessore, un istruzione come la seguente:
LD

SP,nn

;predisponi lo Stack Pointer al valore 'nn' dove


; 'nn' e` un indirizzo a 16 bit di memoria RAM

Attraverso questa predisposizione, il programmatore definisce la base della catasta, che


risulter quindi allocata all'indirizzo 'nn'.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-11

Il DMC8 consente di riporre sulla catasta soltanto word da 16 bit. Dato che la memoria ha
locazioni da 8 bit, quanto vi viene riposto e` suddiviso nei due byte "basso" e "alto" (come in altri
casi gi incontrati). Quando il programmatore vuole posare e riprendere dati dalla catasta, usa
le due istruzioni:
PUSH

POP

ss

;copia il registro (a 16 bit) 'ss' sulla cima


;della catasta (dividendolo in due byte).

dd

;riprende dalla cima della catasta una coppia di


;byte, che ricompone nel registro a 16 bit 'dd'

Gli operandi 'ss' e 'dd' possono essere soltanto i seguenti: AF, BC, DE, HL, IX e IY. Si tratta di
tutti i registri a 16 bit gi incontrati, pi la notazione anomala AF, che identifica i due registri A e
F, e non rappresenta propriamente un registro a 16 bit.
Il registro AF infatti non esiste: e` accettato dalla sintassi di questa istruzione per brevit. La
notazione AF, come registro a 16 bit, e` priva di significato in tutti gli altri casi. Scrivere "PUSH AF"
significa semplicemente che verranno riposti, sulla cima della catasta, prima l'Accumulatore A e poi
il registro fittizio dei flag F.

Nella figura 7.1 possiamo esaminare come funzionano le istruzioni PUSH e POP. Lo Stack e`
rappresentato in figura come una specie di bicchiere, inizialmente vuoto. In questa prima fase,
lo Stack Pointer punta
al fondo della catasta,
essendo questa vuota.
Il programmatore ha
infatti definito l'indirizzo
del fondo dello Stack,
assegnando
un
valore
iniziale
al
registro Stack Pointer,
con una istruzione
inserita tra le prime
eseguite al momento
del RESET, come si
pu
osservare
nell'esempio seguente:

START:

ORG
JP
ORG
LD

0000h
0100h
0100h
SP,0FFF0h

Fig. 7.1: Lo Stack e le istruzioni PUSH


;collegamento al RESET hardware

;inizializza il fondo dello Stack a FFF0h

Pi avanti nel programma, il processore incontra due istruzioni di PUSH, come le seguenti:
PUSH
PUSH

BC
HL

;salva sullo Stack il registro BC


;e poi il registro HL

Quando l'istruzione PUSH BC viene eseguita, il contenuto del registro BC e` ricopiato sulla
catasta, suddiviso nei soliti due byte Low e High. La cima della catasta si e` cosi` inalzata di
due posizioni, e lo Stack Pointer (pari a FFEEh) punta ora all'ultima locazione piena sulla
cima.
Tutto questo e` avvenuto grazie al registro Stack Pointer, che e` stato impiegato dal
processore per indirizzare la memoria al momento delle due scritture, decrementandolo ogni
volta di una unita`. Infatti, se su questo disegno la catasta cresce verso l'alto, in realt gli
indirizzi di memoria, salendo nella figura, decrescono (si tratta di una scelta progettuale,
peraltro condivisa con quasi tutti gli altri microprocessori in commercio).
Immaginiamo ora che venga eseguita la seconda istruzione PUSH HL: anche il contenuto del
registro HL sar ricopiato sulla catasta, e lo Stack Pointer si trover, a fine esecuzione, a
puntare (FFECh) alla nuova ultima locazione piena, in cima allo stack.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-12

Avere copiato (meglio: salvato) il contenuto di questi due registri nello Stack ci consente ora di
utilizzare tali registri liberamente per altri scopi computazionali.
Infatti, nel momento in cui ci interesser recuperarne i precedenti contenuti, quelli salvati nello
Stack, dovremo semplicemente eseguire le seguenti due istruzioni:.
POP
POP

HL
BC

;recupera dallo Stack il registro HL


;e poi il registro BC

In
figura
7.2,
l'esecuzione
della
prima POP HL causa
la trascrizione nel
registro HL dei due
byte attualmente in
cima alla catasta, ed
il
conseguente
abbassamento
di
questa (a tutti gli
effetti svuotata di due
byte).
Lo Stack Pointer si
trover
ancora
a
puntare alla cima
della catasta, ora pi
Fig. 7.2: Lo Stack e le istruzioni POP
bassa
di
due
locazioni.
Infine, eseguendo la POP BC, recupereremo il vecchio valore salvato prima: sar ricopiato nel
registro BC, e la catasta risulter di nuovo vuota, con lo Stack Pointer al valore iniziale FFF0h.
Vediamo ora un esempio in cui si effettua un salvataggio completo di tutti i registri interni della
CPU, prima di usarli per altri scopi.

PUSH
PUSH
PUSH
PUSH
PUSH
PUSH

AF
BC
DE
HL
IX
IY

;salva nello Stack tutti i registri


;interni, nell'ordine:
;A e F, BC, DE, HL, IX, IY

;fatto...

... Qui in mezzo: qualunque calcolo che impieghi tali registri...

POP
POP
POP
POP
POP
POP

IY
IX
HL
DE
BC
AF

;recupera dallo Stack il contenuto


;di tutti i registri interni
;
;

!!! IMPORTANTE: !!!


OSSERVATE l'ordine inverso !!

Evidentemente il programmatore aveva bisogno di usare tutti i registri interni alla CPU, in un
qualche compito "locale", ma senza perderne il contenuto. A valle della esecuzione di tutte le
POP, la situazione precedente sar stata completamente ripristinata.
Osserviamo che:
a) il programmatore non ha dovuto indirizzare esplicitamente le locazioni di memoria usate;
b) un certo numero di PUSH 'ss' deve essere sempre seguito da un numero identico di
POP 'dd' (altrimenti lo Stack di riempie senza svuotarsi o viceversa);
c) la sequenza di recupero deve essere rovesciata rispetto a quella di salvataggio.
Dopo queste necessarie considerazioni sul funzionamento dello Stack, vediamone finalmente la
sua principale applicazione: la Chiamata e il Ritorno dai sottoprogrammi.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-13

7.6.2

I Sottoprogrammi e le Istruzioni di Chiamata e Ritorno


Per sottoprogramma si intende un programma che viene richiamato ed eseguito da un altro
programma. Un sottoprogramma pu richiamare a sua volta altri sottoprogrammi.
In
programmazione, l'uso dei sottoprogrammi comporta:
a) un netto miglioramento nella leggibilit del codice sorgente;
b) un migliore utilizzo della memoria, perch un certo compito sar scritto una sola volta
e poi richiamato da pi parti e pi volte;
c) una maggiore riutilizzabilit del codice.
Nel nostro Assembly, la chiamata di un sottoprogramma si ottiene con l'istruzione:
CALL

<indirizzo>

;"chiama il sottoprogramma all' <indirizzo> dato"

Il sottoprogramma, dal canto suo, DEVE necessariamente terminare con l'istruzione:


RET

;(return) = "ritorna al programma chiamante"

Per capire l'uso delle istruzioni CALL e RET, ma non solo, analizziamo l'esempio seguente:
ORG
JP
ORG

O000h
0100h
0100h

;collegamento al RESET hardware

START:

LD
LD

SP,0E000h
IX,0A000h

;inizializza il fondo dello Stack a E000h


;inizializza il registro indice IX
; seguono altre inizializzazioni

LOOP:

LD
B,(IX)
LD
C,(IX+1)
CALL SUBPROG
LD
(9000h),A
altro

LD
B,(IX+3)
LD
C,(IX+4)
CALL SUBPROG
CP
E
altro

JP
LOOP

;ciclo principale del programma


;prepara i dati in B e C, per esempio
;prendendoli da qualche parte in memoria
;chiama il sottoprogramma SUBPROG
;memorizza il risultato restituito in A

;prepara altri dati in B e C


;chiama ancora il sottoprogramma SUBPROG
;confronta con E il risultato in A

;il programma principale cicla su se stesso


;
;=== Sottoprogramma ===================================
; calcola la media aritmetica dei valori tra B e C:
;
SUBPROG: LD
A,B
;sposta in A il contenuto di B, per
ADD
A,C
;poterlo sommare a C, quindi il risultato in A
SRL
A
;viene diviso per 2 (scalandolo a destra di uno);
RET
;infine ritorna al chiamante...

Il sottoprogramma SUBPROG calcola la media aritmetica tra due dati. I due numeri vengono
"passati dal chiamante" tramite i due registri B e C, mentre il risultato "restituito al
chiamante" attraverso il registro A.
Tra l'altro, questo un esempio di come, in Assembly, un programma possa "passare dei
parametri" ad un sottoprogramma, e di come questo possa "restituire un valore" al chiamante.

La prima volta, il programma principale prepara in B e C due valori di cui vuole calcolare la
media, e chiama il sottoprogramma con una CALL. Il microprocessore eseguir un salto
speciale al sottoprogramma, che inizia all'indirizzo con etichetta SUBPROG.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-14

Il sottoprogramma viene quindi eseguito, la media calcolata e, in fondo al codice, il processore


incontra l'istruzione di ritorno RET. Questa istruzione obbliga il microprocessore ad effettuare un
altro salto speciale, con il quale ritorna al programma chiamante, riprendendo ad eseguire le
sue istruzioni a partire da quella immediatamente successiva alla CALL che ha chiamato il
sottoprogramma (in questo caso l'istruzione "LD (9000h),A").
Poco pi sotto, il processore incontra nuovamente una chiamata allo stesso sottoprogramma,
che si svolge in maniera simile al caso precedente. Si tratta di osservare attentamente la sottile
ma importante differenza che si riscontra nella esecuzione della istruzione RET.
Ovviamente, ci aspettiamo che questa volta il processore, nel ritornare al programma
chiamante, ricominci a lavorare eseguendo l'istruzione immediatamente successiva alla
seconda delle due CALL, quella che ha effettivamente chiamato la seconda volta il
sottoprogramma, e cosi` accade (ricomincia dalla "CP E").
Ma, se approfondiamo l'osservazione, ci rendiamo conto che non e` affatto banale ritornare
al chiamante, a meno di non salvare da qualche parte l'indirizzo di ritorno, al momento della
chiamata, che necessariamente e` diverso per ogni diversa chiamata.
Se volessimo, il salto al sottoprogramma
potremmo effettuarlo anche con un semplice
salto (p.e. con una JP SUBPROG), dato che
ne
conosciamo
l'indirizzo
(identificato
dall'etichetta SUBPROG); ma la stessa cosa
non si pu fare per il ritorno, perch non lo
stesso nei due casi!
Infatti, il sottoprogramma dovrebbe tornare al
chiamante, nel primo e nel secondo caso, con
due istruzioni di salto diverse, perch diversi
sarebbero gli indirizzi di ritorno.
Noi vogliamo invece che il sottoprogramma
sia unico, usabile senza preoccuparci di chi
lo chiama e di dove dovr ritornare!

Fig. 7.3: Lo Stack e l'istruzione CALL

Grazie alla disponibilit dello Stack, il microprocessore risolve in forma completamente


automatica le chiamate ed i ritorni (vedi figure 7.3 e 7.4).
Listruzione CALL, prima di essere eseguita come un normale salto all'indirizzo specificato,
effettua il salvataggio automatico dell'indirizzo di ritorno sulla cima dello Stack.
Tale indirizzo, al momento della esecuzione
della CALL, non deve essere calcolato dal
processore, in quanto gi automaticamente
presente nel Program Counter dopo il prelievo
della istruzione e il prelievo del suo operando.
La prima cosa che la CALL esegue, quindi, e` il
salvataggio del Program Counter corrente
(alias l'indirizzo di ritorno) in cima allo Stack.
Immediatamente dopo, il processore continua
eseguendo
un
normale
salto
al
sottoprogramma, passando cosi` il controllo
dell'esecuzione a questo.
Anche l'istruzione RET assomiglia ad una
istruzione di salto. Il processore preleva dalla
Fig. 7.4: Lo Stack e l'istruzione RET
cima dello Stack due byte, li ricompone
insieme formando un indirizzo a 16 bit, e lo
ricopia nel Program Counter, eseguendo di fatto un salto assoluto a tale indirizzo (e quindi
alla prima istruzione successiva alla CALL che aveva chiamato).
Nota: abbiamo visto come il meccanismo di salvataggio e recupero dell'indirizzo di ritorno sia
completamente automatico e trasparente al programmatore, ma questi deve preoccuparsi di
definire lo Stack, inizializzando, all'inizio del programma principale, lo Stack Pointer.
La responsabilit del programmatore inizia nel momento in cui sia necessario utilizzare
ulteriormente lo Stack tramite le istruzioni di PUSH e di POP.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-15

Esaminiamo ora alcuni esempi: uno corretto e altri con qualche errore da principiante".
Il sottoprogramma seguente e` corretto: salva sullo Stack i registri B, C, A e i Flag e poi, dopo
avere usato questi registri le sue esigenze di calcolo, prima di "restituire il controllo" al
chiamante, ne recupera i valori dallo Stack. In questo modo, il programma chiamante ritrova il
contenuto dei registri intatto, come lo aveva lasciato:
SUBPROG: PUSH BC
;salva alcuni registri
PUSH AF

...corpo del sotto-programma, che necessita


...di usare i registri B, C, A e i Flag;

POP
AF
;recupera il contenuto dei registri
POP
BC
;prima salvati
RET
;ritorna al chiamante (il contenuto dei
;registri e` stato preservato)

L'esempio seguente, invece, contiene un grave errore:


SUBPROG: PUSH
PUSH

POP
RET

BC
AF

;salva B, C, A ed i flag F

BC

;... manca un "POP" !!! GRAVE ERRORE !!!

Infatti, il programmatore ha dimenticato la POP AF, con alcune "interessanti" conseguenze:


a) non viene ripristinato il valore salvato prima di A e dei Flag, e che quindi risulteranno
sporcati dal sottoprogramma stesso;
b) la POP BC preleva dalla cima dello Stack quello che era il contenuto di A e dei Flag, e
non da BC;
c) la RET preleva dalla cima dello Stack quello che crede essere l'indirizzo di ritorno, e
che invece era il precedente contenuto del registro BC;
d) di conseguenza, l'esecuzione del programma proseguir in modo del tutto errato e
soprattutto imprevedibile, dal momento che il processore ritorner ad un indirizzo
completamente sbagliato (questa e` la conseguenza pi grave di tutte, perch causer
inevitabilmente il Crash del nostro programma).
Anche l'esempio seguente contiene una svista significativa:
SUBPROG: LD
...
...
CALL
...
...
RET

A,B

SUBPROG

; !!! ERRORE !!!

L'errore consiste nel fatto che il programmatore non si e` accorto di avere chiamato il
sottoprogramma da dentro se stesso, innescando un meccanismo di ricorsione non
controllata. Il processore non arriva mai ad eseguire la RET, in quanto incontra prima la CALL
che richiama nuovamente il sottoprogramma.
Il vero problema e` dovuto allo Stack: ogni volta che si esegue la CALL, viene salvato un
nuovo indirizzo di ritorno sulla cima dello Stack, e quindi questo crescer in continuazione,
senza mai ridiscendere.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-16

Non essendo previsto, in questo processore ed in altri simili, nessun automatismo di controllo
del valore assunto dallo Stack Pointer, entro pochi millisecondi lo Stack sar cresciuto tanto da
invadere altre aree di memoria. Potrebbe succedere, ad esempio, che il programma stesso, si
sovrascriva da solo, mandando tutto in Crash anche in questo caso (con un linguaggio
"moderno", potremmo dire di avere creato un "virus" in grado di distruggere il sistema).
Questo caso limite propone
un altro potenziale problema:
abbiamo
visto
che
il
programmatore decide dove
allocare il fondo dello
Stack, ma che non esiste un
controllo sulla sua crescita.
Ora,
dall'interno
di
un
sottoprogramma si possono
chiamare altri sottoprogrammi
e apparentemente potrebbe
sembrare che non esista
limite alle chiamate annidate
(figura 7.5).
In realt un eccessivo livello
di annidamento potrebbe
causare un traboccamento
dello Stack dallo spazio che il
programmatore aveva deciso
di riservarvi.
Per evitare problemi, e` bene
sovradimensionare la zona
di memoria destinata allo
Fig. 7.5: Esempio di chiamate a sottoprogrammi e dei relativi ritorni
Stack, cercando di stimare le
proprie necessit in termini di annidamenti ed uso normale delle PUSH e POP. Microprocessori
pi recenti e pi evoluti possiedono dei meccanismi di protezione contro questo tipo di
devastazioni della memoria.
Le istruzioni CALL e RET presentano anche la forma condizionata, analoga a quella dei salti
condizionati. Nel seguente esempio si riporta un esempio di CALL condizionata al risultato di
una operazione e, sotto, la stessa cosa ottenuta con un normale salto condizionato. Si nota che
nel primo caso il programma e` pi "leggibile":

;esempio di uso di CALL condizionata:


DEC
B
;il decremento potrebbe dare ZERO come risultato
CALL Z,SUBPROG
;se ZERO, chiama il sottoprogramma
LD
D,E
;...prosegui con il programma...

;esempio equivalente, con uso di un salto condizionato:


DEC
B
;il decremento potrebbe dare ZERO come risultato
JP
NZ,NOEXEC
;se non ZERO, salta la chiamata al sottoprogramma
CALL SUBPROG
;se ZERO, chiama il sottoprogramma
NOEXEC: LD
D,E
;...prosegui con il programma...

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-17

7.7

Istruzioni di Ingresso e Uscita


Le istruzioni di Ingresso e Uscita (Input/Output) consentono al microprocessore di comunicare
con gli omonimi dispositivi. Poich di questi non si ancora parlato, al momento possibile
introdurre queste istruzioni soltanto ad un livello funzionale. Infatti queste istruzioni
interagiscono con i dispositivi di Ingresso e Uscita che, per loro natura, non sono dispositivi
standard, e possono implementare le funzionalit pi svariate. Pi avanti riprenderemo il
discorso scendendo in maggiori dettagli.
Tralasciando per ora i particolari, diremo soltanto che lo spazio di indirizzamento della
memoria separato, da un punto di vista logico, dallo spazio di indirizzamento dei dispositivi di
Ingresso e Uscita. Questi sono indirizzati dal microprocessore DMC8 utilizzando soltanto gli 8
fili meno significativi del bus degli indirizzi: A7A0; nel nostro sistema, quindi, possono
essere implementati soltanto 256 dispositivi di ingresso e 256 dispositivi di uscita.
Nel seguito faremo riferimento al generico dispositivo di Ingresso e Uscita con il nome di Porto,
traduzione letterale del termine inglese Port. Questo termine stato erroneamente tradotto, in
passato, come Porta, ma il termine originale ha un altro significato (porto di mare, attracco),
per cui nel seguito useremo il termine correttamente tradotto di Porto.
Ecco due esempi di istruzioni di Ingresso e Uscita:
IN

A,(34h)

;copia nel registro A il contenuto del porto 34h

OUT

(5Dh),A

;copia nel porto 5Dh il contenuto del registro A

Listruzione IN, nella forma qui esemplificata,


ammette come <destinazione> soltanto il
registro A. Quando eseguita, listruzione IN
chiamer in causa il dispositivo di ingresso
(Input Port) allocato allindirizzo 34h: questo
risponder fornendo sul Bus dei Dati il byte in
ingresso al dispositivo, che sar ricopiato
dal microprocessore nel registro A (Fig. 7.6).
Anche listruzione OUT utilizzata nellesempio
di sopra ammette come <sorgente> soltanto il
registro A. Al momento della esecuzione,
listruzione OUT metter sul Bus dei Dati il
contenuto del registro A, e chiamer in causa il
dispositivo di uscita (Output Port) allocato
allindirizzo 5Dh, che risponder acquisendo il
byte, e portandolo in uscita (Fig. 7.6).

Fig. 7.6: I porti di ingresso e di uscita dell'esempio

In questo esempio non e` possibile entrare in maggiori particolari hardware, per i motivi detti
prima: la figura e` volutamente molto schematica.
Esiste unaltra forma per le istruzioni di Ingresso e Uscita, per la quale possibile precisare
quale registro del processore si vuole utilizzare (qui indicato con r, pu essere A, B, C, D, E,
H oppure L). Tuttavia, in questa forma lindirizzo del porto non pu essere specificato da un
numero, ma deve essere predisposto nel registro C (si tratta di una forma di indirizzamento
indiretto a 8 bit, mediante il registro C):
IN

r,(C)

OUT

(C),r

;copia nel registro r il contenuto del porto


;(il cui indirizzo specificato dal registro C)
;copia nel porto (il cui indirizzo specificato
;dal registro C) il contenuto del registro r

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-18

Il seguente programma acquisisce in continuazione un byte da un porto di ingresso, ne inverte i


4 bit meno significativi, azzera i 2 bit pi significativi, pone a uno i rimanenti e restituisce il byte
modificato su di un porto di uscita:
Input
Output
;

;
LOOP:

7.8

EQU
EQU

020h
021h

;indirizzo del porto di ingresso


;indirizzo del porto di uscita

ORG
JP
ORG

O000h
0100h
0100h

;(parte con il RESET)

IN
XOR
AND
OR
OUT
JP

A,(Input)
0Fh
3Fh
30h
(Output),A
LOOP

;copia in A il contenuto del porto di ingresso


;inverte i 4 bit meno significativi
;azzera i 2 bit pi significativi
;mette a uno gli altri due bit
;copia sul porto di uscita il contenuto di A
;ripeti allinfinito

Istruzioni di Controllo della CPU


Questo gruppo di istruzioni permette per esempio di abilitare o disabilitare il meccanismo dele
Interruzioni, e di controllare lo stato della CPU.
Le istruzioni relative al controllo degli Interrupt saranno esaminate nel capitolo relativo:
EI
DI

;abilita il meccanismo degli Interrupt


;disabilita il meccanismo degli Interrupt

A questo gruppo appartiene l'istruzione:


NOP

;nessuna operazione

L'unico effetto di questa istruzione e` quello di far incrementare il Program Counter (PC) per
eseguire l'istruzione seguente, e pu essere utilizzata come ritardo (4 cicli di clock).
Inoltre, l'istruzione:
HALT

;ferma l'esecuzione del programma

L'esecuzione del programma si blocca perch viene "congelato" il sequenziatore interno in uno
stato di attesa. Il processore manifesta la situazione tramite l'arresto dell'attivit esterna.
La CPU pu uscire dallo stato di HALT solo attraverso un RESET oppure una richiesta di
interruzione INT. Sappiamo che nel caso del RESET l'esecuzione del programma riprende
dall'indirizzo 0000h, mentre nel caso di Interrupt (come vedremo in un prossimo capito) viene
eseguita la relativa routine di servizio e, dopo avere eseguito questa, l'esecuzione del
programma riprende dall'istruzione successiva a quella di HALT.
In ultimo, anche le seguenti due istruzioni appartengono a questo gruppo:
SCF
CCF

;poni a 'uno' il Flag di Carry


;complementa il Flag di Carry

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver. 06/02/2015

7-19

La struttura hardware di un sistema a microprocessore


Nei primi capitoli abbiamo considerato la struttura del sistema a microprocessore da un punto di
vista logico: abbiamo esaminato cioe` le relazioni che esistono tra i vari elementi del sistema,
ma non siamo scesi in dettagli implementativi. In questo capitolo, invece, vogliamo esaminare
piu` da vicino la struttura fisica del sistema. Esamineremo gli elementi base che incontreremo
sempre in un sistema a microprocessore, dal piu` semplice al piu` complesso. Naturalmente,
faremo riferimento al nostro sistema semplificato.

8.1

I generatori di Clock e di Reset


Abbiamo visto che il microprocessore necessita di un segnale di clock per sincronizzare tutte le
sue operazioni interne. Nel sistema sara` quindi presente un generatore di onda quadra, di
frequenza opportuna. Nella fig. 8.1 e` rappresentato con il nome di CLOCK GEN (Clock
Generator). Il simbolo che compare sopra il generatore rappresenta un cristallo di quarzo:
infatti i generatori di clock utilizzano normalmente tale dispositivo per stabilizzare la frequenza
del segnale emesso (si rimanda la descrizione dei circuiti che implementano i generatori di
clock ai corsi di elettronica analogica). Nel nostro sistema didattico la frequenza del segnale di
clock e` di 10 MHz, e il duty cycle dellonda quadra e` del 50%. Nella figura si osserva che il
clock e` ovviamente collegato alla CPU (il microprocessore), ma e` reso disponibile anche sul
bus dei controlli, affinch possa essere usato, se necessario, dai dispositivi di ingresso/uscita.

Fig. 8.1: I generatori di Clock e di Reset

In altri sistemi, molto piu` complessi, si utilizzano clock polifase: il generatore produce non uno
ma piu` segnali ad onda quadra, tutti alla stessa frequenza ma sfasati tra di loro (ad esempio
quattro segnali a 90 gradi uno dallaltro).
Inoltre, nei sistemi che impiegano microprocessori molto veloci, spesso la frequenza del
generatore di clock viene moltiplicata allinterno del chip del microprocessore, al fine di
ottenere un segnale interno di sincronizzazione a frequenza molto alta (e spesso polifase). Il
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-1

processore sincronizza il segnale di clock, rigenerato internamente, con il segnale in ingresso


mediante tecniche ad aggancio di fase (PLL, Phase Locked Loop). Per esempio, possiamo
avere un generatore a 50MHz, che il processore utilizza per agganciare e sincronizzare il suo
generatore interno alla frequenza di 350MHz (sette volte piu` elevata).
Dal punto di vista del clock, esistono dispositivi molto diversi tra loro: troviamo ad esempio
microcomputer su singolo chip che includono il generatore di clock completo di cristallo, altri
che necessitano del solo cristallo (da connettere ai piedini), altri che richiedono un generatore di
clock esterno.
Osservazione: non e` detto che la frequenza del generatore debba essere sempre la piu` elevata
possibile, in tutti i sistemi. Quando non e` necessario andare veloci ma, ad esempio, si deve tenere
conto del risparmio energetico, il clock e` generato a frequenze molto basse: ad esempio, esistono
dei termostati dambiente computerizzati che lavorano con un periodo di clock pari a 1 secondo!

Nella fig. 8.1, rappresentato con il nome di RESET GEN, si osserva anche un modulo
essenziale per il corretto avviamento del sistema: il generatore di RESET. Questo circuito
serve ad inviare il segnale di RESET alla CPU e, tramite il bus dei controlli, allintero sistema.
Normalmente il segnale e` generato in automatico, allaccensione del sistema, ma spesso un
pulsante, a disposizione dellutente, permette di re-inizializzare il sistema manualmente.
Nel caso dellattivazione manuale, alla pressione del pulsante, il generatore di RESET attiva la
linea in modo impulsivo, per un tempo dellordine del centinaio di millisecondi.
Nel caso dellattivazione automatica, il generatore di RESET provvede ad inizializzare
correttamente il sistema al momento della sua accensione. Il circuito e` progettato in modo da
attivare il segnale di RESET fin dai primi istanti di vita del circuito di alimentazione, in modo da
congelare nello stato di RESET tutti i dispositivi presenti nel sistema durante liniziale
transitorio di alimentazione.
Non appena la tensione di alimentazione ha raggiunto il valore nominale, il generatore mantiene
per sicurezza il RESET ancora attivo per una frazione di secondo, per poi rilasciarlo e
permettere al sistema di iniziare a lavorare.
Per quanto riguarda lattivazione automatica del Reset, occorre tenere presente che un qualunque
sistema elettronico e` alimentato tramite un opportuno alimentatore (power supply), o una
batteria. Allatto dellaccensione, a causa dei condensatori di elevata capacita` presenti nel
circuito, la tensione di alimentazione del sistema non va a regime immediatamente ma, a seconda
dei casi, puo` impiegare anche alcuni secondi prima di stabilizzarsi al valore nominale. Durante
questo lungo transitorio di alimentazione, il congelamento dellinterno sistema consente di
evitare che possa succedere di tutto alle uscite del sistema digitale.

8.2

Il comportamento del Bus


Il BUS permette il transito dellinformazione da un modulo allaltro del sistema, ma il suo reale
comportamento, in senso fisico, puo` non essere cosi` semplice come sulle prime potrebbe
sembrare. Normalmente, quando pensiamo ad un segnale che viene generato da una porta
logica e ricevuto da unaltra, siamo portati ad ignorare il ritardo con cui il segnale stesso si
propaga lungo la connessione tra le due porte. Questo perche` diamo per scontato che il
percorso sia corto: ad esempio, sulla superficie di un chip, ove la distanza tra due porte logiche
puo` essere anche molto piccola (dellordine del m).
Nel vuoto, la velocita` di propagazione di unonda elettromagnetica e` pari a quella della luce:
un metro viene percorso in circa 3,3 nS. Nei materiali la velocita` si riduce, in dipendenza dalle
caratteristiche fisico-geometriche del mezzo di propagazione. Per i segnali che viaggiano tra
due porte logiche, possiamo indicativamente riferirci a tempi di propagazione dellordine dei
20 nS a metro. Questo tempo e` purtroppo confrontabile con i tempi propri dei dispositivi logici:
in particolare il suo effetto pesa maggiormente la` dove si utilizzano dispositivi molto veloci.
I tempi finiti di propagazione permettono inoltre di osservare altri fenomeni, studiati tipicamente
nella teoria delle linee, come ad esempio la riflessione avanti e indietro dei segnali che
viaggiano lungo una connessione lunga.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-2

Quando la connessione tra due dispositivi avviene tramite un BUS, la lunghezza delle linee in
gioco e` tale da obbligarci a non trascurare i tempi di ritardo e le riflessioni del segnale, ma non
solo: entrano in gioco altri parametri fisici fin qui non ancora citati, come le capacita` e le
induttanze parassite, il mutuo accoppiamento tra i fili, le correnti di dispersione dei componenti
collegati, le correnti di uscita dei buffers che pilotano le linee, e altro
La conseguenza piu` immediata di queste valutazioni e` che un determinato bus, avente
caratteristiche elettriche e geometriche ben precise, mostrera` dei limiti nella velocita` di
trasferimento dei dati, di cui il progettista dovra` tenere conto.

8.3

La temporizzazione dei dispositivi


Oltre ai limiti fisici dovuti alle caratteristiche del bus, occorre tenere in considerazione le
caratteristiche temporali imposte dai dispositivi utilizzati. Il processore, le memorie e i
dispositivi di ingresso /uscita devono dialogare tra di loro, e quindi il comportamento nel
tempo di ciascun elemento deve risultare compatibile con gli altri. La temporizzazione dei
segnali su di un BUS e` normalmente definita da quella del processore (il master del sistema): il
progettista dovra` adattare a questa temporizzazione il comportamento degli altri dispositivi.
Nel caso del processore DMC8, il suo comportamento nel tempo ai morsetti puo` essere
descritto in modo semplice, poiche` viene scomposto in un numero molto limitato di sequenze
standard (i cosiddetti Cicli Macchina). Piu` sequenze standard, combinate insieme,
descrivono il comportamento dei terminali del processore durante lesecuzione delle istruzioni (i
Cicli di Istruzione).

8.3.1 I Cicli Macchina del DMC8


Nel DMC8, il singolo Ciclo di Clock provoca l'avanzamento di uno stato all'interno del
microprocessore. Tra le sequenze standard osservabili alle terminazioni del processore,
troviamo i Cicli Macchina denominati:

Ciclo di Prelievo dellIstruzione


Cicli di Accesso alla Memoria (in lettura e in scrittura)
Cicli di Accesso ai Dispositivi di Ingresso (in lettura) e Uscita (in scrittura)
Ciclo di Riconoscimento dellInterruzione

Nel capitolo precedente abbiamo esaminato l'esecuzione dellistruzione LD A,(0F5F0h). Questa


istruzione, ad esempio, dall'esterno pu essere vista come una successione di quattro Cicli
Macchina standard:
Un ciclo di Prelievo dellIstruzione (lettura del suo codice operativo)
Due cicli di Accesso alla Memoria (lettura dei due byte di cui e` composto loperando)
Un ulteriore ciclo di Accesso alla Memoria (lettura del dato dalla memoria)
Qui di seguito esaminiamo i cicli macchina principali, rinviando quello relativo alle interruzioni al
capitolo dedicato allargomento.

8.3.2 Ciclo di Prelievo dell Istruzione (Fetch Cycle)


La sequenza di prelievo in memoria del primo byte di una istruzione, il codice operativo, e
standard per tutte le istruzioni (vedi Fig. 8.2). Il Ciclo di Prelievo dura in totale quattro cicli di
clock, suddivisi in una prima parte di tre cicli, in cui il microprocessore effettua il vero e proprio
prelievo del codice operativo, seguiti da un altro ciclo di clock, necessario per la decodifica e
lavvio dellesecuzione dellistruzione.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-3

Con il fronte di salita del ciclo di clock C1, il processore invia il contenuto del registro Program
Counter (PC) sul bus degli indirizzi. Con il fronte di discesa dello stesso ciclo sono attivati i
segnali di richiesta di memoria ( MEMREQ ) e di lettura ( READ ).
La ragione di questo spostamento sul fronte di discesa risiede nella necessita` di evitare conflitti
elettrici sul bus dei dati, in corrispondenza dei momenti in cui i buffer tri-state dei vari dispositivi in
gioco commutano il loro stato di attivazione/disattivazione.

In risposta ai segnali di richiesta, la memoria si attiva e, trascorso il suo tempo di accesso,


pone sul bus dei dati D0..D7 il contenuto della locazione specificata dal bus indirizzi: il codice
dellistruzione puntata dal Program Counter. Il microprocessore cattura questo codice sul
fronte di discesa del ciclo di clock C3, disattivando poi i segnali MEMREQ e READ . Il codice
e` caricato dal processore nel Registro dellIstruzione.
Affiche` questo trasferimento del codice dellistruzione abbia successo, e` importante che la
memoria mantenga valido il contenuto del bus dei dati intorno al fronte di cattura, rispettando i
Tempi di Set-Up e di Hold richiesti dalle specifiche del microprocessore. Nellesempio di fig. 8.2, il
bus dei dati, per il resto del tempo in Alta Impedenza (Hi-Z), viene pilotato dai buffer tri-state
della memoria a partire dal momento in cui questa fornisce il suo contenuto (nel corso del ciclo C2)
fino alla disattivazione dei segnali di MEMREQ e READ .

A partire dal fronte di discesa di C3 inizia, nel processore, la decodifica del codice operativo
dellistruzione; con la fine del ciclo di clock C4 il sequenziatore inizia lesecuzione della stessa.
Quale che sia il codice dellistruzione, al fronte di salita del successivo ciclo di clock C1, il
processore incrementa il Program Counter, che si predispone per il successivo accesso in
memoria.

Fig. 8.2: Il ciclo di prelievo dellistruzione (Fetch Cycle)

Nel caso delle istruzioni che richiedono soltanto di accedere ai registri interni, lesecuzione
dellistruzione termina direttamente con il fronte di salita che termina il ciclo C4 e inizia il ciclo
C1. Ad esempio, cosi` si concludera` listruzione LD A,B : sul fronte di salita suddetto avra`
luogo il caricamento del contenuto del registro B nel registro A.
Se invece il codice dellistruzione richiede altri accessi esterni, nel ciclo C4 il sequenziatore si
prepara per gestire uno o piu` cicli macchina di accesso (alla memoria o ai dispositivi di I/O),
che saranno eseguiti immediatamente di seguito.
Durante i cicli di clock C1, C2 e C3 il processore attiva il segnale SYNC , per indicare
allesterno che stiamo prelevando in memoria il codice operativo di unistruzione. Il segnale
SYNC e` da considerare come segnale di sincronismo che permette di capire, dall'esterno,
cosa stia facendo il processore. Il segnale SYNC , presente in tutti i microprocessori, utilizzato
dalla strumentazione diagnostica che, collegata con una specie di pinza (POD) in parallelo al
microprocessore, consente di tracciare in tempo reale il comportamento dei programmi in
esecuzione.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-4

8.3.3 Accesso alla Memoria in Lettura e in Scrittura


I cicli macchina di lettura e di scrittura dati in memoria consistono di tre cicli di clock ciascuno
(vedi fig. 8.3 e fig. 8.4). In entrambi i casi, all'inizio del ciclo C1 viene posto sul bus degli indirizzi
l'indirizzo della locazione che la CPU vuole scrivere o leggere: l'indirizzo permane valido fino
alla fine del ciclo C3.
La sequenza temporale del ciclo macchina di lettura dati dalla memoria e` molto simile a quella
del ciclo di prelievo dellistruzione appena esaminato. In questo caso, pero`, lindirizzo del
dato puo` essere fornito da vari registi interni a 16 bit, tra cui anche il Program Counter.
Inoltre, il byte letto dalla memoria sara` ricopiato in un registro dati, e il segnale di SYNC non
e` (ovviamente) attivato.

Fig. 8.3: Il ciclo di lettura di un dato dalla memoria

Fig. 8.4: Il ciclo di scrittura di un dato in memoria

Nel ciclo di scrittura dati in memoria il segnale WRITE attivato dalla CPU sul fronte di discesa
di C2, un ciclo dopo lattivazione del segnale MEMREQ . Viene poi rilasciato assieme a
quest'ultimo, sul fronte di discesa di C3, fronte con cui la memoria memorizza il dato.
La ragione di questo apparente ritardo nella emissione del segnale di scrittura risiede nella
necessita` di concedere tempo ai circuiti della memoria, che devono terminare di selezionare la
locazione prima di passare alla scrittura effettiva, per non "sporcare" locazioni non richieste (a
causa delle alee che si verificano nel transitorio della decodifica dell'indirizzo).
In lettura questo problema non esiste, in quanto eventuali selezioni spurie non distruggono niente e
si traducono solo in una temporanea non validit delle linee del dato.

Si osservi tra laltro che il processore predispone sul bus dei dati il byte da scrivere piuttosto
presto, e lo mantiene fino alla fine del ciclo C3.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-5

8.3.4 Accesso ai Dispositivi di Ingresso e Uscita


I cicli macchina di ingresso e uscita presentano una durata di quattro cicli di clock ciascuno
(vedi fig. 8.5 e fig. 8.6). Queste sequenze sono generate dal processore solo durante
lesecuzione delle istruzioni IN e OUT.
Allinizio del ciclo C1 viene posto, sulla parte bassa A0..A7 del bus degli indirizzi, l'indirizzo del
dispositivo di Ingresso o Uscita (il Porto) con il quale la CPU vuole comunicare: tale indirizzo
permane valido fino alla fine del ciclo C4. Il segnale di SYNC non e` attivato.
Ricordiamoci che il processore puo` indirizzare soltanto 256 diversi porti di ingresso e altrettanti
in uscita. Lindirizzo del porto puo` essere fornito direttamente dalloperando dellistruzione,
oppure, se questa lo specifica, dal registro interno a 8 bit C.

Fig. 8.5: Il ciclo di lettura di un dato da un porto di ingresso (istruzione IN)

Fig. 8.6: Il ciclo di scrittura di un dato in un porto di uscita (istruzione OUT)

Con il fronte di discesa del ciclo C1 viene attivato il segnale di IOREQ (richiesta di attivazione di
dispositivo di ingresso/uscita, che sar poi disattivato sul fronte di discesa del ciclo C4.
Durante lesecuzione dellistruzione IN, il segnale di READ richiede al dispositivo di ingresso
selezionato di fornire il dato sul bus. Questo deve essere valido sul fronte di discesa del ciclo
C4, istante in cui il processore lo cattura e lo ricopia nel registro specificato dallistruzione.
Durante laccesso ad un porto di uscita (istruzione OUT), il segnale di WRITE avvisa il
dispositivo di uscita selezionato di acquisire il dato che il processore ha nel frattempo posto sul
bus. Il dato fornito dal processore sul fronte di discesa del ciclo C1, e mantenuto fino alla fine
di C4. Il dispositivo tipicamente acquisisce il dato sul fronte di salita del segnale di WRITE .

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-6

8.4

Il progetto del sistema di memoria


Abbiamo visto che il DMC8 controlla un Bus Indirizzi di 16 fili (A15..A0), e quindi puo` indirizzare
fino a 216 (=65.536, 64K) locazioni di memoria. Si e` visto anche che questo spazio puo` essere
utilizzato tutto, oppure in parte, e che la memoria e` costituita sia da RAM che da ROM. Per
descrivere la memoria presente in un sistema a microprocessore, dal punto di vista della sua
programmazione, abbiamo usato semplicemente la cosiddetta mappa di memoria.
E` arrivato il momento di vestire i panni del progettista hardware e, sulla base di quanto
abbiamo visto fino ad ora, progettare il sistema di memoria per il nostro sistema.
Esaminiamo i segnali che saranno coinvolti nel progetto. Intanto osserviamo in via preliminare
che i diagrammi temporali delle sequenze del processore, se messi a confronto con quelli
relativi ai dispositivi di memoria visti in precedenza, mettono in evidenza tra di essi una forte
compatibilit, come poteva essere prevedibile.
Come si e` visto nei precedenti paragrafi, il DMC8 controlla l'accesso alle memorie attraverso i
segnali MEMREQ , READ e WRITE (vedi fig. 8.3 e 8.4). Il segnale MEMREQ viene attivato
dal microprocessore per distinguere il ciclo di accesso alla memoria da quello di accesso ai
dispositivi di ingresso / uscita (come abbiamo visto, questi ultimi rispondono invece
all'attivazione del segnale IOREQ ). Dunque, nel progettare il sistema di memoria dobbiamo
tenere conto che questo deve attivarsi in risposta al segnale MEMREQ . Ovviamente, per
attivare le memorie nei rispettivi modi di lettura e di scrittura, dobbiamo utilizzare anche i segnali
del READ e WRITE .
Il Bus degli Indirizzi entra a far parte del circuito che collega le memorie al microprocessore. In
generale, un sistema di memoria risulta composto di piu` chip di memoria a semiconduttore, sia
RAM, che ROM. Dovendo ripartire su piu` chip le richieste di accesso del processore,
abbiamo la necessita` di utilizzare l'indirizzo per due scopi concomitanti:
1) attivare un solo chip di memoria (quello che contiene la locazione indirizzata);
2) selezionare la locazione desiderata (all'interno del chip attivato).
Per risolvere il punto 1), dobbiamo prima di tutto ripartire lo spazio di indirizzamento sui singoli
chip di RAM e di ROM che si vogliono utilizzare, e quindi progettare un opportuno circuito di
decodifica dell'indirizzo, in grado di pilotare i rispettivi ingressi di selezione (Chip Select) a
seconda della zona di indirizzo a loro assegnata.
0000h
Il punto 2), come vedremo qui di seguito, si
...
(32 Kbyte)
risolve collegando ai singoli chip la parte dei fili
7FFFh
del bus degli indirizzi che non entra nel
8000h
decodificatore.

(32 Kbyte)
Nel nostro sistema, dato che lo spazio di
FFFFh
indirizzamento e` limitato a 64 Kbyte, per
Fig. 8.7: La Mappa di Memoria semplificata
semplicita` utilizziamo due
soli chip, uno per la RAM e
uno per la ROM. Infatti sul
mercato
sono
disponibili
dispositivi da 32K byte, sia di
RAM che di ROM. Con questi
due dispositivi, la mappa di
memoria del nostro sistema
risulta molto semplice (fig.
8.7): lo spazio di memoria
disponibile viene occupato
tutto.
La ROM inizia allindirizzo
0000h
poiche`,
come
abbiamo visto, al RESET il
Fig. 8.8: Le connessioni dei due chip di memoria qui impiegati
processore si aspetta di

ROM
RAM

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-7

trovare a questo indirizzo la prima istruzione da eseguire. La RAM inizia allindirizzo 8000h e
termina in fondo allo spazio disponibile.
Lo schema a blocchi dei due chip di ROM e di RAM permette di esaminare i segnali coinvolti
(fig. 8.8): 8 fili di dato D7..D0, 15 fili di indirizzo A14..A0 (215 = 32K), un filo di attivazione CS ed
un controllo di lettura OE , oltre al filo di scrittura WE della RAM.
Riprendiamo in modo piu` dettagliato la mappa di memoria, mettendo in evidenza gli indirizzi in
forma binaria (fig. 8.9). Come si puo` osservare, la linea piu` significativa degli indirizzi, A15,
discrimina direttamente tra il chip di ROM (A15=0) e quello di RAM (A15=1): utilizzeremo questo
filo per attivare luno o laltro dei chip, a seconda dellindirizzo.
A15
0
0
0
.

.
0
0
0
1
1
1
.

.
1
1
1

A14
0
0
0
.
.
.
.
1
1
1
0
0
0
.
.
.
.
1
1
1

A13
0
0
0

A12
0
0
0

A11
0
0
0

A10
0
0
0

A9
0
0
0

A8
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1

1
1
1

1
1
1

1
1
1

1
1
1

1
1
1

A7
0
0
0
.
.
.
.
1
1
1
0
0
0
.
.
.
.
1
1
1

A6
0
0
0

A5
0
0
0

A4
0
0
0

A3
0
0
0

A2
0
0
0

A1
0
0
1

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

1
1
1
0
0
0

0
1
1
0
0
1

1
1
1

1
1
1

1
1
1

1
1
1

1
1
1

0
1
1

A0
0
1
0
.
.
.
.
1
0
1
0
1
0
.
.
.
.
1
0
1

HEX
0000h
0001h
0002h
.

.
7FFDh
7FFEh
7FFFh
8000h
8001h
8002h
.

.
FFFDh
FFFEh
FFFFh

CHIP

ROM
32K

RAM
32K

Fig. 8.9: Mappa di memoria dettagliata del sistema con 32K di ROM e di RAM

Le altre 15 linee (A14..A0) possono essere collegate direttamente agli omonimi fili dei due chip,
in parallelo. In questo modo lasciamo ai dispositivi di decodifica interni al chip (selezionato dal
bit A15), il compito di attivare la cella di memoria richiesta dal processore.

Fig. 8.10: La rete completa del sistema di memoria

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-8

In conclusione, la rete complessiva della memoria e della relativa decodifica degli indirizzi
risultera` piuttosto semplice. La fig. 8.10 mostra come il filo A15, con un semplice NOT, controlla
la selezione dei due chip: se A15=0 sara` attivato CSROM (il CS della ROM), altrimenti
CSRAM (il CS della RAM). La selezione e` volutamente abilitata solo se attivo il segnale
MEMREQ , che agisce tramite i due OR.
Landamento nel tempo dei segnali di selezione dei chip, CSROM e CSRAM , a parte i ritardi
della logica combinatoria, risultera` uguale a quello del segnale MEMREQ del processore.
Analogamente, i segnali di OE e WE delle memorie ricopiano rispettivamente i segnali di
READ e WRITE del processore.
Curiosita`: per connettere i dispositivi di memoria al processore abbiamo aggiunto una piccola
quantita` di componenti: nel gergo anglosassone dellelettronica, si dice che abbiamo aggiunto
della Glue Logic, della logica che permette di incollare insieme i dispositivi

8.5

Il progetto dei porti di ingresso e uscita


Nel capitolo dedicato alla classificazione delle istruzioni, abbiamo incontrato le istruzioni di IN e
OUT, e in questo capitolo le temporizzazioni relative a queste. Dobbiamo ora approfondire
maggiormente il discorso.
Con il termine Porto di Ingresso ci si riferisce ad un dispositivo in grado di ricevere dei dati
provenienti dalle unit periferiche esterne al nostro sistema. Unita` di ingresso esterne
possono essere, ad esempio, la tastiera, i dischi magnetici, il CDROM, il DVD, il Modem, la
scheda di rete ma anche tali dispositivi come sensori di temperatura, pressione, velocita`,
conta-pezzi, e altro.
Con il termine Porto di Uscita ci riferiamo ad un dispositivo che puo` trasferire dati dal
microprocessore (o dalla memoria) verso unita` esterne, quali ad esempio: la stampante, la
scheda grafica, i dischi magnetici, il masterizzatore di CD e DVD, il Modem, la scheda di rete, e
attuatori di impianto, come i controllori di motori passo-passo, teleruttori di potenza, regolatori di
luce
Nei sistemi piu` piccoli (e nei sistemi embedded) troviamo spesso porti di ingresso e uscita
dedicati alla lettura di pulsanti/interruttori e alla accensione di lampadine (o piccoli
display), come ad esempio nei prodotti di largo consumo (lettori di CD e MP3, telefoni cellulari,
televisori).
In questo capitolo, per semplicit,
prendiamo in considerazione proprio
questi ultimi esempi: esaminiamo i
cosiddetti porti di ingresso e uscita di
tipo parallelo, facendo riferimento
proprio alla lettura di interruttori e alla
attivazione di lampadine (fig. 8.11).
Teniamo presente che tutti i porti di
ingresso/uscita piu` complessi si
basano, in ogni caso, sui concetti che
esamineremo adesso: infatti la struttura
dei porti paralleli e` necessariamente
sempre
presente
in
qualunque
progetto, costituendone una sorta di
mattoncino fondamentale.

Fig. 8.11: Porti di ingresso e uscita paralleli: lettura di


interruttori e attivazione di lampadine

Nella figura sono rappresentati in modo schematico gli interruttori e le lampadine: nella realt
saranno necessari alcuni elementi circuitali (analogici) per consentire il collegamento degli
interruttori e delle lampadine ai porti, che qui omettiamo per concentrare lattenzione sulla parte
logica della rete. I porti qui considerati sono da 8 bit, semplicemente perche` il nostro
processore e` un processore da 8 bit.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-9

Nella fig. 8.11, gli otto interruttori sono letti in


parallelo dal processore tramite il porto di
ingresso, mediante unistruzione di tipo IN
(nellesempio, alcuni sono a uno, altri a zero: il
processore acquisisce il byte 11010001).
A proposito delle lampadine, invece, il processore
scrive in parallelo otto bit sul porto di uscita,
tramite unistruzione di tipo OUT: il valore dei bit
controlla lo stato di accensione delle lampadine
(nellesempio, alcune sono accese, altre spente: il
byte scritto dal processore valeva, come sopra,
11010001).

Lindirizzamento dei Porti

Se torniamo ad osservare i diagrammi temporali del


processore che abbiamo discusso in questo
capitolo, ci accorgiamo che tra i cicli di accesso alla
memoria e quelli di ingresso/uscita non vi sono
differenze sostanziali. Lunica differenza, rilevante
solo per la progettazione delle decodifiche degli
indirizzi, e` che viene attivato il segnale IOREQ
invece che MEMREQ per la richiesta di attivazione
dei dispositivi. Per il resto, landamento dei segnali
e` simile.

Troviamo applicato il primo metodo nei


processori come il 68000 e discendenti,
ma il secondo e` preferito da molti altri
processori (come quelli Intel, e lo Z80).

Possiamo aspettarci che il progetto di dispositivi


come quelli di Fig. 8.11 non sia molto dissimile da
quello dei dispositivi di memoria, anzi, piu`
semplice, poiche` il singolo dispositivo puo`
assomigliare ad una sorta di cella di memoria, ma
isolata dalle altre.
I segnali del DMC8 coinvolti nel progetto sono:

gli 8 fili del bus dei dati: D7..D0;

gli 8 fili bassi del bus degli indirizzi: A7..A0


(il processore prevede al massimo 256 porti
di uscita e 256 porti di ingresso);

i segnali di controllo: IOREQ , READ e


WRITE ;

le 8 linee di ingresso o di uscita.

In generale, esistono due modi distinti per


collegare dal punto di vista logico l'unit
centrale con i dispositivi di ingresso e
uscita. La distinzione riguarda
lindirizzamento dei porti, che puo`
avvenire:
Tramite la condivisione dello spazio
indirizzabile tra memorie e dispositivi di
ingresso e uscita (I/O Memory Mapped);
Tramite uno spazio di indirizzamento
separato (I/O Standard).

I microprocessori che utilizzano il metodo


Memory Mapped non possiedono
istruzioni specializzate per lingresso e
luscita, perche` da un punto di vista
hardware il processore non distingue tra
dispositivi di memoria e di ingresso/uscita.
Lunico spazio di indirizzamento e`
utilizzato sia per i chip di memoria, sia per i
porti, e la distinzione tra i vari elementi si
ottiene soltanto per mezzo dellindirizzo.
Per scrivere e leggere nei porti di I/O si
usano le stesse istruzioni utilizzate per la
memoria. Si ritiene che questo da un punto
di vista della programmazione sia un
vantaggio, per certi versi, in quanto
permette di applicare ai porti la potenza
delle istruzioni utilizzate per la memoria,
ma che costituisca anche uno svantaggio,
poiche` lassenza di istruzioni specializzate
per lingresso/uscita rendono molto meno
leggibile il codice assembly.
Occorre notare che la realizzazione di porti
Memory Mapped in un sistema Standard
non e` impedita da nulla, nel caso lo si
ritenesse necessario.
Il nostro processore appartiene alla
categoria che implementa l I/O Standard.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-10

8.5.1 Il Porto di Uscita Parallelo


Se analizziamo il diagramma temporale di fig. 8.6, osserviamo che il processore produce sul
bus il dato da scrivere nel porto, e si aspetta che questo lo catturi sul fronte di discesa del ciclo
di clock C4. E` necessario quindi prevedere un registro da 8 bit (come avevamo fatto per le
memorie), che possa catturare il dato: scegliamo anche qui un registro D-latch.
Dal diagramma temporale citato si osserva che il segnale WRITE , per il suo andamento nel
tempo, sarebbe adatto per funzionare da segnale di scrittura per il registro. Infatti, quando il
processore attiva WRITE , al fronte di salita di C2, il dato da scrivere e` gia` presente sul bus e
puo` quindi comparire in uscita al registro (questo, con il segnale di scrittura basso, funziona in
modalit` trasparente). Con il fronte di salita di WRITE il dato sarebbe infine catturato nel
registro, per esservi mantenuto fino ad una successiva scrittura nello stesso.
Si tratta quindi di utilizzare il segnale WRITE , ma condizionandolo allattivita` del segnale
IOREQ e, molto importante, alla presenza sui fili A7..A0 dellindirizzo prescelto dal progettista
hardware per distinguere il porto.

Fig. 8.12: Il porto di uscita parallelo, composto dal registro e dalla decodifica

Ricordiamoci che il programmatore richiede la scrittura in un ben determinato porto di uscita


mediante luso di una istruzione OUT, ad esempio OUT (0F0h),A. In questo esempio
lindirizzo che il processore porra` sul bus degli indirizzi e` appunto pari a F0h.
Tutte le considerazioni fatte si traducono infine nel progetto del porto cos come riportato nella
fig. 8.12. I segnali IOREQ , WRITE e lindirizzo A7..A0 sono combinati in un decodificatore che
produce il segnale di scrittura per il registro, REGWRITE .
Nella figura, il decodificatore e` progettato per attivare REGWRITE solo se lindirizzo F0h e`
presente sul bus, coerentemente con lesempio sopra riportato.

REGWRITE ricopia nel tempo il segnale WRITE , se e` attivo IOREQ e se lindirizzo e` quello
corretto. Sulle linee L7..L0 potremo collegare qualunque dispositivo compatibile, come ad
esempio dei circuiti per accendere lampadine, come introdotto dalla precedente fig. 8.11.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-11

8.5.2 Il Porto di Ingresso Parallelo


Se questa volta prendiamo in considerazione il diagramma temporale di fig. 8.5, si nota che il
processore si aspetta che il dato da leggere sia fornito dal dispositivo di ingresso intorno al
fronte di discesa del ciclo di clock C4 (il processore lo cattura su questo fronte).
Affinch un dato possa essere portato sul bus dei dati, occorre utilizzare la tecnica dei buffer
tri-state, come fanno gli altri dispositivi che si affacciano sul bus dei dati. E` necessario quindi
prevedere un buffer tri-state da 8 bit (come le memorie), che possa fornire il dato sul bus,
attivandosi a richiesta. Lattivazione dovra` essere fornita da un opportuno circuito di decodifica,
simile a quello utilizzato per il porto di uscita.
Nota: non serve nessun registro, almeno nella forma piu` semplice del porto di ingresso: in casi
piu` complessi introdurremo anche un registro, ma questo fatto sara` esaminato piu` avanti.

Dal diagramma temporale di fig. 8.5 si osserva che il segnale READ , per il suo andamento nel
tempo, e` adatto per funzionare da segnale di attivazione del buffer. Infatti, il processore
disattiva READ dopo il fronte di discesa di C4, ossia dopo avere catturato il dato da leggere.
Lattivazione del segnale di lettura avviene in modo da non creare sovrapposizione nel tempo
con gli altri dispositivi presenti sul bus, in modo da evitare conflitti elettrici dovuti a
contemporanee attivazioni di buffer tri-state.
In modo simile a porto di uscita, si tratta quindi di utilizzare qui il segnale READ , condizionato
allattivita` del segnale IOREQ e alla presenza sui fili A7..A0 del solito indirizzo identificativo,
scelto dal progettista hardware. Il programmatore puo` leggere da un porto di ingresso
tramite una istruzione IN, come nellesempio IN A,(1Fh). Al momento della esecuzione,
lindirizzo che il processore porra` sul bus degli indirizzi in questo esempio e` pari a 1Fh.

Fig. 8.13: Il porto di ingresso parallelo, composto dal buffer e dalla decodifica

Nella fig. 8.13 possiamo osservare lo schema del porto, conseguenza delle considerazioni fatte.
I segnali IOREQ , READ e lindirizzo A7..A0 sono combinati in un decodificatore che produce il
segnale di attivazione del buffer tri-state, BUFREAD .
Nella figura, coerentemente con lesempio qui sopra, il decodificatore e` progettato per attivare
BUFREAD solo se e` presente sul bus lindirizzo 1Fh. BUFREAD ricopia nel tempo il segnale
READ , se e` attivo IOREQ e se lindirizzo e` quello corretto.
Immaginiamo di collegare alle linee di ingresso I7..I0 qualunque dispositivo compatibile, per
esempio dei circuiti che traducono la posizione meccanica di un interruttore in uno stato logico,
come presentato nella fig. 8.11.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-12

Possiamo rileggere un porto di uscita?


La risposta e`: No.
Non dimentichiamo un particolare importante: il porto di uscita e` ad una sola direzione.
Differentemente da una locazione di memoria, non pu essere riletto, a meno che non si
aggiunga fisicamente lhardware necessario allo scopo, ossia un altro porto, ma di ingresso,
collegato in modo da rileggere le linee del porto di uscita.
Di solito non si provvede lhardware per la rilettura, per semplici ragioni di economia: infatti,
la soluzione economicamente pi vantaggiosa, qualora il software avesse necessit di
ricordare la configurazione di zeri e uni prodotta sul porto di uscita, quella di mantenerne
una copia software in una locazione di memoria RAM.

8.5.3 La Mappa dei dispositivi di Ingresso/Uscita (I/O Map)


In modo similare a quanto fatto per la memoria, si e` soliti rappresentare una mappa dei
dispositivi di ingresso/uscita presenti nel sistema. Un sistema molto semplice, dove sono
presenti solo porti paralleli, puo` ad esempio essere descritto dalla mappa di I/O in fig. 8.14.
Notate come allindirizzo 63h possano coesistere insieme un porto di uscita e uno di
ingresso. Infatti i due dispositivi non potranno mai andare in conflitto, poiche` sono attivati in
modo esclusivo, uno in scrittura e laltro in lettura.
Inoltre, fate attenzione al fatto che il contenuto di questo porto di ingresso non ha nulla a che
vedere con quanto scritto sul porto di uscita che si trova allo stesso indirizzo: si tratta di due
hardware indipendenti.
A7
0
0
0
0
.
.
0
0
.
.
1
1
1
1

A6
0
0
0
0

A5
0
0
0
0

A4
0
0
0
0

A3
0
0
0
0

A2
0
0
0
0

A1
0
0
1
1

A0
0
1
0
1

1
1

1
1

0
0

0
0

0
0

1
1

1
1

1
1
1
1

1
1
1
1

1
1
1
1

1
1
1
1

1
1
1
1

0
0
1
1

0
1
0
1

HEX
00h
01h
02h
03h
.
.
63h
63h
.
.
FCh
FDh
FEh
FFh

Porti (esempio di descrizione)


Ingresso: 8 sensori di presenza
Ingresso: 8 sensori di massimo livello vasche
Ingresso: 8 sensori di minimo livello vasche
Ingresso: 8 pulsanti utente

Ingresso: 4 interruttori, x due joystick utente


Uscita: 8 lampadine sul pannello di controllo

Uscita: 2 display BCD a 7 segmenti (Low)


Uscita: 2 display BCD a 7 segmenti (High)
Uscita: 8 relais (per 8 elettrovalvole di carico)
Uscita: 8 relais (per 8 elettrovalvole di scarico)

Fig. 8.14: Esempio di mappa dei porti di ingresso / uscita, per un semplice sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

8-13

Interfacciamento con i dispositivi esterni


Nel capitolo precedente abbiamo visto dei porti di tipo parallelo, impiegati per leggere degli
interruttori e accendere delle lampadine. In questo semplice caso gli interruttori e le
lampadine rappresentano, per il sistema, dei dispositivi periferici (o, semplicemente, delle
periferiche). Nel nostro caso non osserviamo problemi di sincronizzazione tra le periferiche
e il processore. Infatti le lampadine risultano in ogni istante "disponibili" al processore (che puo`
accenderle e spegnerle quando vuole) e, analogamente, anche gli interruttori (che possono
essere letti in qualunque momento).
Ma in generale, una periferica puo` essere qualcosa di piu` complesso, come ad esempio una
stampante, una tastiera, un modem o un mouse Una stampante, nel momento in cui il
processore cerca di utilizzarla, pu ad esempio essere spenta, oppure priva di carta, o ancora
in stato di blocco a causa di un precedente errore di funzionamento (come un inceppamento
della carta). Inoltre, e` normale che molti tipi di periferica possano rimanere occupati per un
certo intervallo di tempo, impossibilitati ad accettare o inviare un dato. Per molti tipi di
periferica, quindi, da parte del processore si render necessario un controllo circa la
disponibilit della periferica stessa allo scambio di informazioni.
Il trasferimento dei dati sara` gestito mediante un opportuno protocollo di sincronizzazione,
chiamato handshake. Questo si realizza (Fig. 9.1a, e 9.1b) aggiungendo un certo numero di
collegamenti tra il microcomputer e le periferiche, necessari per lo scambio di opportuni
segnali di controllo. Questi segnali risultano indispensabili per sincronizzare correttamente il
colloquio tra i dispositivi interessati senza perdita (o duplicazione) di dati. Detti segnali sono
necessari sia nel caso in cui e` il microcalcolatore a trasmettere i dati alla periferica (Fig.10.1a),
che nel caso contrario (Fig. 9.1b). I segnali di controllo saranno poi gestiti dal software e da un
hardware locale dedicato. Si dice che dobbiamo interfacciare i dispositivi periferici al sistema.
Uninterfaccia, dal punto di
vista hardware, consiste in
un insieme di porti di
ingresso - uscita e di
logica specifica hardware e
software che permettono di
collegare una certa periferica
al sistema computerizzato.
Fig. 9.1a: Interfacciamento di una periferica in uscita con lausilio di
Per
meglio
capire
la
segnali di controllo (per gestire lhandshake).
situazione,
riprendiamo
lesempio della stampante,
che immaginiamo connessa
ad un personal computer. Si
consideri il caso di dover
stampare un documento
molto lungo. Quando il
microprocessore invia alla
stampante il documento, Fig. 9.1b: Interfacciamento di una periferica in ingresso con lausilio di
segnali di controllo (per gestire lhandshake).
utilizza la memoria presente
in
questa.
Una
volta
accettata una certa percentuale del documento, la stampante non sara` pi in grado di
riceverne il resto fino a quando non ne avra` stampato la prima parte, liberando la sua memoria.
Affinch la stampa abbia luogo, deve trascorrere un intervallo di tempo notevolmente lungo se
paragonato ai normali tempi di funzionamento del microprocessore: in quellintervallo sara`
necessario arrestare temporaneamente la trasmissione dei dati, per riprenderla quando la
stampante avra` liberato la sua memoria di lavoro.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-1

Analoga situazione si presenta nel caso dellingresso di dati provenienti da una periferica. Si
pensi, ad esempio, ad una tastiera. La velocit di battitura non costante (dipende
dall'operatore umano), e potrebbe passare anche molto tempo tra due battute. Anche in questo
caso sara` necessario che il processore rivolga attenzione alla tastiera solo quando necessario,
o molto di rado.

9.1

Esempi di gestione del protocollo di intesa (Handshake)


Nel realizzare una specifica interfaccia, e` necessario progettare una opportuna rete di
sincronizzazione fra il processore e il dispositivo periferico. Tale rete puo` essere
implementata in molti modi. Come visto nelle figure precedenti, e` necessario introdurre fili
aggiuntivi nella connessione, oltre a quelli relativi ai dati. Tramite questi fili aggiunti, entrambe
le parti connesse genereranno una serie di segnali di chiamata e di risposta, in entrambe le
direzioni (da cui il nome handshake, ovvero "stretta di mano").
Occorre notare che non esiste una soluzione universale, e che ogni dispositivo diverso
richiedera` scelte particolari, caso per caso. Esistono ovviamente in commercio, per ogni tipo di
processore, dispositivi di ingresso e uscita gia` pronti, di uso generale o specializzati per
determinate applicazioni, in grado di soddisfare le piu` svariate esigenze di collegamento alle
periferiche. Qui nel seguito seguiremo un approccio di tipo progettuale, in modo da affrontare
gradualmente alcuni esempi di connessione, partendo dalle nostre conoscenze di base.

9.1.1

Handshake di tipo unidirezionale


In Fig. 9.2 osserviamo un dispositivo Tx che trasmette dati verso un altro dispositivo Rx. Nel
seguito del discorso, Tx e Rx possono essere rispettivamente un computer e una periferica, o
il contrario, o anche due computer
connessi tra di loro.
Nellesempio in figura il dispositivo
che trasmette Tx segnala l'invio del
dato per mezzo di un opportuno
impulso di validazione del dato
stesso, qui denominato Strobe
(impulso, segnalazione). Il ricevitore
Rx, grazie al fronte di salita
dellimpulso (per esempio), potra`
catturare e acquisire il dato.
Fig. 9.2: Handshake di tipo unidirezionale
Occorre notare che questo schema
di handshake funziona correttamente
soltanto nei casi in cui il dispositivo ricevente sia molto veloce a trattare i dati ricevuti e, di
conseguenza, sia sempre pronto a ricevere i dati inviati dal trasmettitore. Se questa
condizione non e` verificata, occorrera` scegliere un meccanismo di handshake piu` complesso,
come vedremo nel prossimo paragrafo.
Osservazione: limpulso di strobe si rende necessario perch il ricevitore deve essere avvisato
del fatto che il trasmettitore gli abbia effettivamente inviato un dato. Basti pensare, ad esempio, alla
trasmissione del contenuto di un file di testo, carattere dopo carattere. Si potrebbe cadere
nellerrore di pensare che per il ricevitore sia sufficiente osservare le linee del dato per capire
quando un nuovo dato gli viene passato, ma non e` cosi`. Infatti nel file di testo saranno ad
esempio sicuramente presenti caratteri ripetuti piu` volte di seguito (consonanti doppie, cornicette
di caratteri, ecc.): se non fosse trasmesso un impulso ad ogni carattere, come potrebbe, il
ricevitore, capire di quanti asterischi sia composta una certa cornicetta?

Esempio
Utilizzando quanto appreso sui porti paralleli nel capitolo precedente, cerchiamo ora di
progettare un esempio di interfaccia di questo primo tipo, ipotizzando che il Tx sia il nostro
sistema computerizzato, e che sia necessario inviare dei dati verso un altro dispositivo, veloce
abbastanza da acquisire tutti i dati che invieremo.
Per i dati veri e propri, sara` sufficiente predisporre un porto di uscita parallelo da 8 bit, come
quello gia` esaminato. Per la parte riguardante il segnale Strobe, possiamo utilizzare anche qui
un porto di uscita come il precedente, utilizzandone solo un filo tra gli otto disponibili.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-2

In Fig. 9.3 si osservano i due porti


di uscita: il Porto del Dato e il
Porto
di
Controllo
(cosi`
chiameremo, in generale, i porti
destinati al controllo, diretto o
indiretto, dei segnali di handshake).
Il porto di uscita del dato, in questo
esempio, e` allocato allindirizzo di
I/O 40h; il porto di controllo, invece,
allindirizzo 41h. Del porto di
controllo, per generare il segnale
Strobe, usiamo solo la linea in
posizione 4, qui denominata C4.
Questo hardware, per poter
funzionare,
deve
essere
completato da un opportuno
software
di
gestione,
come
nellesempio qui di seguito:
...
...
; definizione indirizzi
DATA EQU 40h
CONTR EQU 41h
...
...
; inizializzazione
LD
A,00h
OUT
(DATA),A
OUT
(CONTR),A
...
...
; prende e scrive il dato
Fig. 9.3: Interfaccia parallela con handshake unidirezionale
LD
A,(dalla memoria)
OUT
(DATA),A
LD
A,10h
; quindi porta a uno la linea Strobe
OUT
(CONTR),A
CALL RITARDO
; mantiene la linea alta per un tempo convenuto
LD
A,00h
; riporta a zero la linea Strobe
OUT
(CONTR),A
...
In questo stralcio di programma, allinizio, i due porti sono inizializzati. Poi, quando necessario,
viene attivata la procedura di invio del dato, che viene reperito in memoria e scritto nel Porto
del Dato. Quindi, la prima scrittura nel Porto di Controllo porta alta la linea Strobe. La
chiamata alla routine di ritardo in generale puo` essere o non essere necessaria: qui e` stata
inserita per rimarcare che la durata dellimpulso deve essere spesso regolata in funzione delle
specifiche della periferica.
A questo punto la periferica, avvertita, puo` catturare il dato e utilizzarlo. Termina la sequenza
una ulteriore scrittura nel Porto di Controllo, per riportare allo stato iniziale (zero) la linea
Strobe, predisponendo lhardware per la trasmissione del prossimo dato.

9.1.2

Handshake di tipo bidirezionale


Nei casi in cui il dispositivo ricevente non sia sufficientemente veloce, il trasmettitore deve
regolare la propria velocita` di trasmissione. Naturalmente, questo non e` ottenuto rallentando il
clock del microcomputer (sarebbe un vero spreco di risorse), ma aggiungendo nella scena del
meccanismo di handshake un ulteriore segnale, questa volta diretto dalla periferica al sistema.
In Fig. 9.4 osserviamo il solito dispositivo Tx che trasmette dati verso un altro dispositivo Rx.
Rispetto alla Fig. 9.2, in questa figura compare un filo in piu`: Busy (occupato). Grazie al
segnale di Busy, la periferica e` in grado di riferire al microcomputer circa il suo stato. Nel

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-3

nostro esempio, possiamo convenire


che Busy, quando a uno, indichi
che la periferica e` impegnata in
qualche compito (e non e` in grado
di ricevere dati); se a zero, la
periferica e` libera, pronta a ricevere
il prossimo dato.
Nella Fig. 9.5 viene proposto un
hardware in grado di gestire,
mediante un opportuno programma,
la sequenza delle operazioni in
gioco. E` evidente che, rispetto al
caso
precedente,
qui
il
microcomputer, prima di inviare un
dato, dovra` controllare la linea
Busy, in un certo senso chiedendo
il permesso alla periferica.
Lo schema e` identico a quello visto
in precedenza, ma con laggiunta di
un porto di ingresso, il Porto di
Stato, necessario per leggere la
linea Busy. In questo esempio la
linea e` collegata al bit in posizione 7
(S7 nello schema).
Il programma di gestione sara`
simile al precedente, con laggiunta
del test preventivo della linea Busy,
ottenuto leggendo il Porto di Stato,
come riportato qui di seguito:
...
; definizione indirizzi
DATA EQU 40h
CONTR EQU 41h
STATO EQU 42h
...
; inizializzazione
LD
A,00h
OUT
(DATA),A
OUT
(CONTR),A
...
; controlla la linea Busy,
; se periferica occupata,
; salta altrove
IN
A,(STATO)
BIT
7,A
JP
NZ, ALTROVE
;
; prende e scrive il dato
LD
A,(dalla memoria)
OUT
(DATA),A
;
; impulso su Strobe
LD
A,10h
OUT
(CONTR),A
CALL RITARDO
LD
A,00h
OUT
(CONTR),A
...

Fig. 9.4: Handshake di tipo bidirezionale

Fig. 9.5: Interfaccia parallela in uscita con handshake


bidirezionale

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-4

9.1.3

Handshake di maggiore complessita`


E` possibile che dispositivi piu` complessi richiedano ulteriori linee di controllo per la loro
gestione. Per esempio, in alcuni casi compare un ulteriore filo, denominato Ack (Acknowledge,
accettazione), come ulteriore risposta da parte della periferica (vedi Fig. 9.6). In questo caso
tale filo non serve a regolare la
velocita` di trasmissione, come il
segnale Busy, ma viene utilizzato
come conferma che il dato sia stato
effettivamente
ricevuto
dalla
periferica. Prima dellavvento delle
interfacce USB, per esempio, le
stampanti dei personal computer
erano normalmente connesse a
questi con interfacce standard di
tipo parallelo Centronics: questo
Fig. 9.6: Handshake di tipo piu` complesso
tipo di interfaccia prevedeva diverse
linee di collegamento, tra cui quelle
viste di Strobe, Busy e Ack.
Non approfondiremo questo caso; diciamo soltanto che le modalit` di handshake di alcune
interfacce standard possono essere anche molto complesse (come ad esempio per i Modem).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-5

9.2

Lhardware in supporto alla gestione del protocollo di intesa


Nella Fig. 9.5 abbiamo visto un esempio di interfaccia parallela in uscita. Proviamo ora a
rovesciare il punto di vista della connessione, progettando la corrispondente interfaccia
parallela in ingresso (Fig. 9.7), ricavandola intuitivamente da quella vista in Fig. 9.5.
Come si nota dalla Fig. 9.7, ora il porto del dato e` un porto in ingresso, predisposto per
ricevere dati dalla periferica. Inoltre, poich riceviamo il segnale di Strobe dall'esterno, il porto
ad esso relativo e` anchesso in ingresso (porto di stato). Siamo invece noi a generare il
segnale di Busy tramite il porto di controllo.
Diciamo subito che questa interfaccia,
cosi`, non e` progettata bene: il
processore risulter troppo impegnato
nella sua gestione. Se consideriamo la
successione delle operazioni che la
CPU dovra` svolgere, osserviamo che
questa dovr monitorare "in tempo
reale" il porto di stato, perennemente
in attesa dellarrivo del segnale di
Strobe.
Una
volta
arrivato,
il
processore dovr inviare il segnale di
risposta Busy attraverso il porto di
controllo e, nel frattempo, acquisire
anche il dato attraverso il porto del
dato.
Dobbiamo riflettere su alcuni vincoli che
questo hardware ci obbliga a rispettare.
Per esempio, il dispositivo esterno
dovr mantenere valido il dato fino a
quando non lo avremo effettivamente
letto. Inoltre, la durata del segnale di
Strobe dovr essere sufficientemente
lunga da permettere di essere letto dal
processore. Pi Strobe "corto", pi
frequentemente
il
processore

obbligato a "interrogare" il porto di


stato. E` evidente che in casi estremi,
obbligheremmo la CPU a non fare
assolutamente niente altro, dovendo
dedicarsi al completo servizio di questa
interfaccia, per non rischiare di perdere
dei dati.
E` evidente la necessita` di aggiungere
qualche accorgimento hardware, oltre
ai semplici porti base di ingresso e di
uscita. Per esempio, potrebbe essere
utile catturare via hardware sia il
dato in arrivo che il segnale di Strobe,
liberando il processore dallincombenza
di inseguire il loro arrivo. Lavvenuta
cattura del dato dovrebbe poi essere
segnalata al processore che, non
appena
possibile,
procedera`
al
prelievo del dato. In questo modo, la
CPU potrebbe occuparsi di tuttaltro,
dedicando allinterfaccia solo il tempo
indispensabile.

Fig. 9.7: Interfaccia parallela in ingresso con handshake


bidirezionale

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-6

9.2.1

Interfaccia con handshake hardware


In Fig. 9.8 osserviamo una possibile implementazione di interfaccia parallela per dati in
ingresso, con handshake gestito dallhardware, dalle caratteristiche decisamente migliori della
precedente. Sono utilizzati solo due porti di ingresso, il porto del dato e il porto di stato
(allocati, in questo esempio, agli indirizzi A0h e A1h). Non presente un Porto di Controllo, in
quanto la funzionalit del segnale Busy realizzata dal circuito stesso, automaticamente via
hardware, senza una partecipazione diretta, "software", del processore.
La novita` consiste nel fatto che il porto di stato consente al processore di controllare (sul bit
pi significativo S7) lo stato dellinterfaccia: ossia se arrivato un dato da processare, oppure
no. Nel circuito e` presente, come si puo` osservare, un ulteriore registro tampone (di tipo DLatch), deputato alla memorizzazione temporanea del dato ricevuto dalla periferica, ed un
Flip-Flop di tipo D-PET. Il FF genera un segnale che ha insieme il significato di Busy per la
periferica e di Ready (ossia Dato Pronto) per il processore.
Supponiamo che allinizio
il FF sia azzerato: la linea
Busy sara` bassa.
Quando la periferica avr
pronto un carattere da
inviare, poiche` il segnale
Busy
lo
consente,
predisporr il dato sulla
linea del dato e invier un
impulso (di breve durata)
sulla linea Strobe.
Come si puo` dedurre
dallanalisi dello schema
in figura, l'impulso Strobe
ottiene due effetti: carica il
dato
nel
registro
tampone e porta a 1 il
FF, tramite lingresso di
Preset.
La linea di Busy e` cosi`
portata
alta
automaticamente,
indicando alla periferica
che
non
possiamo
ricevere altri dati, per il
momento (infatti il dato
ricevuto e` attualmente
nel registro tampone, ma
non e` stato ancora
acquisito dal processore).
La linea Busy assume per
il processore, invece, il Fig. 9.8: Interfaccia parallela in ingresso con handshake bidirezionale gestito
con il supporto dellhardware
significato di Ready (nel
senso di flag di dato
pronto).
Il processore, per sapere se e` arrivato un dato, deve semplicemente leggere il porto di stato,
e testare il bit S7. Se il bit indica che un dato e` stato catturato nel registro e attende di essere
letto dal processore, questo dovr intervenire per acquisire il dato: semplicemente, leggera` il
porto del dato. Qui interviene un altro particolare del circuito: il segnale EN , generato dalla
decodifica dellindirizzo del porto del dato, e` collegato anche al clock del FF: la lettura del dato
da parte del processore causer, "via-hardware", l'azzeramento delle linee di Busy e di Ready,
permettendo ora alla periferica di inviare un ulteriore dato e cancellando la segnalazione di dato
pronto rivolta al processore stesso.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-7

Riassumendo, la nostra interfaccia:


Permette la gestione automatica del segnale di Busy;
Consente di utilizzare un segnale di Strobe di breve durata, senza obbligare il processore a
passare il suo tempo unicamente a controllare il suo arrivo;
La segnalazione di Dato Pronto mantenuta dal circuito, a disposizione del processore,
lasciando libero questo di continuare ad eseguire altri compiti;
Il processore puo` acquisire il dato ricevuto quando vuole;
La semplice lettura del dato consente il ripristino automatico del meccanismo di handshake.
Ecco un esempio di codice di gestione di questa interfaccia:
...
DATA
EQU 0A0h
;definiamo l'indirizzo dei porti
STATO
EQU 0A1h
...
...
IN A,(STATO)
;interroga lo stato del dispositivo
BIT 7,A
;controlliamo il flag di Ready
JP Z,ALTROVE
;se Ready=0, non abbiamo ricevuto niente
;
; qui il processore arriva se Ready = 1 (dato pronto)
IN A,(DATA)
;il dato viene caricato in A
LD (mem),A
;e salvato in una variabile in memoria
...
...
Come si pu notare, l'intera gestione dellhandshake viene risolta dallhardware
dellinterfaccia. Lhandshake risulta invisibile al processore: non se ne ha traccia, infatti, nel
programma di gestione, salvo la presenza del test della segnalazione di Dato Pronto.

9.3

Tecniche di Polling e di Interruzione nella gestione dei dispositivi


In questi esempi si e` visto che il processore necessita di interagire con le interfacce presenti
nel sistema, permanendo in una sorta di continua ricerca delle periferiche che necessitano di
scambiare dati con il processore. Vedremo che, in questa ricerca, il processore dovra` risolvere
due necessita`:
-

9.3.1

Riconoscere il dispositivo che necessita intervento, e


Gestire le priorit di intervento nei confronti di quei dispositivi che dovessero richiedere
servizio contemporaneamente.

La tecnica del Polling


Normalmente, in un sistema saranno presenti numerose interfacce: attraverso i relativi Porti di
Stato, il processore potr effettuare unindagine ciclica alla ricerca delle periferiche da
servire. Usando il termine inglese, si dice che il processore effettua il Polling dei dispositivi. Le
interfacce dei dispositivi dovranno essere progettate in modo da consentire un Polling
efficiente, come nellultimo esempio esaminato qui sopra.
Con il Polling dei dispositivi il problema del riconoscimento e` risolto implicitamente, in quanto
la stessa indagine ciclica consente ovviamente di individuare il dispositivo da servire. Il
problema della priorit si risolve testando piu` frequentemente, e per primi, i dispositivi a priorit
maggiore.
La tecnica del Polling non e` tuttavia la tecnica migliore per gestire i dispositivi periferici, in
quanto con essa il processore rimane comunque impegnato per una certa parte del suo tempo
nellinterrogazione delle interfacce. Specie nei casi in cui i dispositivi sono molti e/o necessitino
di intervento veloce, la gestione dei dispositivi periferici pu essere piu` efficientemente
organizzata sulla tecnica delle Interruzioni (Interrupt).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-8

9.3.2

La tecnica delle interruzioni


Questo tipo di approccio consiste nella possibilit, da parte delle periferiche, di interrompere il
normale funzionamento del processore, per richiedere un particolare servizio. Questa tecnica,
in sostanza, differisce dalla precedente per il fatto di non richiedere un controllo continuato
delle periferiche da parte del processore.
Inoltre, esistono situazioni particolari (come ad esempio nel caso di una segnalazione di allarme
dovuta al verificarsi di una anomalia in un impianto industriale) nelle quali non accettabile il
ritardo con il quale, nel caso di gestione Polling, il processore interviene mandando in
esecuzione il servizio richiesto: in questi casi si ricorre alla tecnica delle interruzioni.
La tecnica delle interruzioni e` possibile
perche` i processori sono provvisti
dellhardware necessario allo scopo. Dal
punto di vista esterno, il metodo si
basa sulla presenza di almeno un
ingresso specializzato ( INT , nel caso
del DMC8), tramite il quale possibile
segnalare al processore la necessit di
un intervento.
L'ingresso privilegiato e non richiede
un controllo periodico in Polling da
parte del processore: il meccanismo
infatti gestito in maniera automatica dal
sequenziatore interno.
Nel momento in cui arriva una
segnalazione di Interruzione (vedi Fig.
9.9), viene interrotta la normale
sequenza di esecuzione delle istruzioni
e, con una sorta di salto speciale a
sottoprogramma, viene eseguita la
Routine di Interruzione. Questa
routine provvedera` a gestire l'opportuno
servizio richiesto. Al termine della sua
esecuzione, la normale esecuzione del
programma prima interrotto verr poi
ripresa, come se si tornasse da un
sottoprogramma.
Occorre
prestare
attenzione al fatto che tuttavia questo
Fig. 9.9: Il concetto di Interruzione (a grandi linee)
sottoprogramma non e` stato lanciato
da una istruzione CALL (si dice in
modo sincrono), ma da un evento hardware, che per sua natura puo` avvenire in qualunque
momento (si dice che la routine di interruzione e` lanciata in modo asincrono).
Lingresso INT del DMC8 e` attivo basso e viene preso in considerazione dal sequenziatore
interno al termine dellesecuzione dellistruzione corrente. Lhardware consente che una
richiesta di interruzione possa essere mascherata, ossia ignorata (Maskable Interrupt).
L'architettura interna del DMC8 prevede un Interrupt Flip-Flop (IFF), la cui funzione e` quella
di abilitare, quando a 1, il meccanismo delle Interruzioni.

IFF = 1
IFF = 0

Interruzioni abilitate
Interruzioni non abilitate

Al momento del Reset hardware, anche il flip-flop IFF viene resettato a zero: successivamente
a questo evento il processore si trova con il meccanismo di interruzione disabilitato. Sar
compito del programmatore assicurarsi che le interruzioni vengano abilitate, se richieste
dallarchitettura del sistema. Sono disponibili allo scopo due istruzioni, che di fatto vanno a
scrivere rispettivamente 1 o 0 nel flip-flop IFF:

EI
DI

Enable Interrupt
Disable Interrupt

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-9

Il programmatore dovra` quindi inserire listruzione EI tra le istruzioni che provvederanno


allinizializzazione del sistema. Inoltre, grazie a queste istruzioni si ha la possibilit di imporre al
processore, in certi momenti, di ignorare temporaneamente e poi riabilitare le richieste di
interruzione (pu capitare che ci si trovi nella condizione, ad esempio, di dover rispettare precisi
limiti di tempo durante l'esecuzione di particolari parti di codice).
Nota: la EI non abilita immediatamente le interruzioni, ma ha la particolarit` di rimandarne
labilitazione al termine della esecuzione dellistruzione successiva. Il motivo di questo sara`
chiarito poco piu` avanti.

Spesso i processori in commercio dispongono di piu` ingressi di richiesta di interruzione. In


particolare, uno di questi spesso consente di scavalcare leventuale disabilitazione del
meccanismo, provocando una interruzione incondizionata (si parla di Non Maskable Interrupt,
NMI). Il DMC8, essendo un processore semplificato, supporta soltanto interruzioni
mascherabili, e il modo piu` semplice di risposta alle interruzioni (lex modo 1 dello Z80).
Nota: nel sistema possono essere presenti molte periferiche: supponiamo che tutte, grazie ad una
semplice logica combinatoria, possano accedere alla linea INT del processore in modo che, per
attivarla, sia sufficiente la richiesta di una sola di esse.

Il meccanismo di risposta allinterruzione del DMC8 e` rappresentato in dettaglio in Fig. 9.10.


Supponiamo che il processore stia eseguendo un qualunque programma: ad un certo istante,
lingresso di interruzione INT viene attivato da una periferica. Questa la sequenza:
1) Listruzione corrente viene terminata, e linterruzione viene presa in considerazione solo
alla sua conclusione.
2) La sequenza di interruzione non viene eseguita se IFF indica che le interruzioni sono
disabilitate (IFF=0).
3) Se le interruzioni sono abilitate, invece, il flip-flop IFF viene azzerato, disabilitando ulteriori
interruzioni (questo e` necessario perche` la linea INT , che puo` essere ancora attiva nel
momento in cui la routine di servizio viene eseguita, potrebbe causare una ricorsione di
interruzioni).
4) Lindirizzo della successiva istruzione, quella non ancora eseguita del programma che
stiamo interrompendo, in questo momento presente nel Program Counter (PC), viene
salvato nello Stack (in modo simile a quanto succede nel caso della istruzione CALL).
5) Il processore infine esegue un salto alla locazione predefinita 0038h, dove il
programmatore avra` allocato la routine di servizio della interruzione.

Fig. 9.10: La sequenza, in dettaglio, del meccanismo di Interruzione del DMC8

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-10

La sequenza ora descritta ha una durata complessiva di 11 cicli di clock, di cui 6 utilizzati dal
processore per il salvataggio nello Stack dellindirizzo di ritorno. Nel corso dei primi 5 cicli di
questa sequenza, il processore avvisa lesterno che ha accettato la richiesta di interruzione,
attivando (a livello basso) luscita INTA .
Tale sequenza esemplificata, in modo semplificato, nel diagramma temporale di Fig. 9.11,
dove si osserva che, inizialmente, un dispositivo attiva la richiesta di interruzione INT del
processore, portandola a 0. Si suppone che gli interrupt siano abilitati (IFF = 1): infatti al
termine della esecuzione della istruzione corrente (invece di procedere con il prelievo della
successiva istruzione), il processore inizia la sequenza di interruzione.
Nella figura messa in evidenza lattivazione delluscita INTA . Dopo 5 cicli di clock, durante i
quali il processore si prepara internamente per le successive operazioni, la linea INTA
riportata nello stato di riposo e, durante i 6 cicli che seguono, il processore effettua il
salvataggio del contenuto del PC sullo Stack. Si noti che il PC in questo momento contiene
lindirizzo della istruzione che sarebbe stata eseguita se il processore non fosse stato
interrotto: in pratica sullo Stack viene salvato lindirizzo di ritorno.
Subito dopo, il PC, forzato al valore 0038h, consente al processore di iniziare ad eseguire, a
quellindirizzo, la routine di interruzione.

Fig. 9.11: Sequenza di interruzione e attivazione dei segnali !INT e !INTA

Se il PC salvato automaticamente, la stessa cosa non succede per gli altri registri del
processore, per cui la routine di servizio per prima cosa dovr salvare nello Stack, con alcune
PUSH, il contenuto dei registri, in modo che questi possano essere ripristinati, a fine servizio,
con altrettante POP.
La necessit di questa operazione dipende dal fatto che la routine di interruzione eseguita in
modo del tutto asincrono rispetto al programma che stato interrotto, per cui occorre
provvedere affinch questo, alla sua ripresa, ritrovi nei registri interni esattamente i contenuti
che vi aveva lasciato. Si dice che la routine di interruzione deve lasciare inalterato lo stato
del processore.
Se nel sistema presente un solo dispositivo in grado di interrompere il processore, a questo
punto la routine di servizio assolve, senza ambiguit, il compito richiesto. Tuttavia, nel caso pi
generale, quando sono presenti molti dispositivi, la routine di servizio dovr per prima cosa
individuare quello che ha richiesto servizio, eseguendo un test su tutti i dispositivi che possono
avere avanzato la richiesta (Polling Post Interrupt). Una volta riconosciuto il dispositivo, la
routine di interruzione eseguir il compito corrispondente. Lordine di esecuzione del test
consente di assegnare una scala di priorit tra i vari dispositivi, in modo da eseguire per
primo, in caso di richieste contemporanee, il codice relativo al dispositivo piu` prioritario.
Infine, dopo il ripristino dello stato interno del processore, la routine termina con una normale
istruzione RET, come nel caso dei normali sottoprogrammi, ma dopo avere eseguito una EI. In
questo modo le interruzioni, disabilitate in automatico prima del lancio della routine di servizio,
saranno nuovamente riabilitate. Come gi detto, listruzione EI posticipa labilitazione delle
interruzioni al termine della esecuzione della istruzione seguente, nel nostro caso la RET: in
questo modo le interruzioni sono riabilitate solo dopo avere concluso la routine di servizio,
evitando cos che possano avvenire chiamate ricorsive di interruzione.
La RET riporter il controllo al programma interrotto, che continuer indisturbato il suo compito.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-11

9.3.3

Interfaccia con richiesta di interruzione


Riprendiamo il circuito di una interfaccia esaminata in precedenza: quello della Fig. 9.8.
Abbiamo visto che tale interfaccia necessitava della tecnica che abbiamo chiamato di Polling: il
processore, periodicamente, doveva testare il Porto di Stato per sapere se era stato ricevuto un
dato, oppure no. Vogliamo modificare il circuito in modo da avvantaggiarci della tecnica delle
interruzioni. Lo schema modificato, riportato in Fig. 9.12, analogo al precedente: stato solo
aggiunto un not.
La linea di Ready, gia` disponibile al processore per il Polling attraverso il porto di stato, viene
qui utilizzata anche per richiedere interruzione al processore. L'arrivo di un dato dalla
periferica produrr una segnalazione di interruzione al processore, che potr cosi` intervenire
sul dispositivo solo quando necessario, senza essere impegnato periodicamente ad
interrogare il porto di stato, in Polling.
Questo rappresenta un grosso vantaggio: il processore potr tranquillamente continuare a
lavorare su altri compiti senza doversi preoccupare di controllare periodicamente i dispositivi
presenti, gestendo le richieste di questi soltanto all'atto del loro effettivo bisogno.
Si noti comunque il mantenimento in questo circuito del porto di stato, dovuto alla necessita` di
cercare, a seguito della interruzione, il dispositivo che lha richiesta, mediante "Polling Post
Interrupt". Questo porto non sarebbe necessario, ovviamente, se questo fosse l'unico
dispositivo presente in grado di inviare la richiesta di interrupt (caso piuttosto raro).

Fig. 9.12: Interfaccia parallela in ingresso con handshake bidirezionale gestito con il supporto
dellhardware e la tecnica delle interruzioni

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-12

DATA
STATO
...

EQU 0A0h
EQU 0A1h

;definiamo l'indirizzo dei porti

ORG 0000h
JP 0100h

;collegamento al reset

;*************** Interrupt
ORG 0038h
INTERRUPT: PUSH AF
PUSH
;
IN A,(STATO)
BIT 7,A
JP Z,ALTRI
;
IN A,(DATA)
LD (mem),A
JP ESCI
...
ALTRI:
...
...
...
;
ESCI:
POP
POP AF
EI
RET
;*************** Programma
ORG 0100h
START:
LD SP,0FFFFh
LD A,00h
...
IN A,(DATA)
EI
...
;
MAINLOOP: NOP
NOP
...
...
NOP
NOP
JP MAINLOOP

Routine ********************************
;salva i registri utilizzati

;interroga lo stato del dispositivo


;controlliamo il flag di Ready
;salta se non ha richiesto intervento
;abbiamo un dato, lo acquisiamo
;salvandolo in memoria

;qui prosegue con il test su altri disp.

;ripristina il contenuto nei registri


;riabilita gli interrupt
;torna al programma interrotto
principale ****************************
;iniz. STACK POINTER
;varie inizializzazioni
;inizializzazione dellinterfaccia (*)
;abilitazione degli interrupt

;segnaposti per indicare il codice


;del programma principale

;il programma principale e` ciclico

Fig. 9.13: Esempio di gestione tramite interrupt dellinterfaccia

In Fig. 9.13 riportiamo un esempio di codice di gestione tramite interrupt dellinterfaccia. Il


processore, nel programma principale, subito dopo il Reset hardware, alletichetta START
esegue alcune inizializzazioni tra cui quella del nostro dispositivo, ottenuta leggendo il Porto
del Dato con una IN A,(DATA) [annotata nel codice con (*)].
Il dato letto dal porto non e` significativo in questo caso, ma questa operazione inizializza a 0
il flip-flop D che governa la gestione hardware dellhandshake. Dopo questa inizializzazione, il
meccanismo delle interruzioni viene attivato, nella CPU, eseguendo una EI.
Il processore entra quindi nel loop principale del programma, nel quale eseguira` i compiti
assegnati dalle specifiche di progetto (omessi nellesempio).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-13

Ogni volta che la periferica esterna fornir un dato alla nostra interfaccia, il gestore hardware
dellhandshake attiver luscita Busy e, quindi, anche la richiesta di interruzione INT . Poich
la EI aveva abilitato il meccanismo delle interruzioni, al termine dellistruzione corrente il
processore si interromper, saltando alla routine di gestione INTERRUPT.
Tale routine salva con alcune PUSH tutti i registri coinvolti, e quindi controlla, in ordine di
priorit, i dispositivi presenti, tramite la lettura dei rispettivi porti di stato. Nellesempio, il nostro
dispositivo e` appunto quello prioritario, in quanto testato per primo.
Se linterruzione non fosse stata chiesta dalla nostra interfaccia, il test proseguirebbe sugli altri
dispositivi presenti (nel codice: ALTRI: ). Altrimenti, con una istruzione IN il processore
acquisisce il dato, provocando al contempo sia la re-inizializzazione del dispositivo hardware
di handshake che la disattivazione della linea INT .
Questo e` un particolare importante: la routine di interruzione deve preoccuparsi di resettare la
richiesta di interruzione, una volta che sia stata soddisfatta.
Infine, con alcune POP, la routine ripristina i contenuti precedenti dei registri del
processore, recuperandoli dallo Stack, ed esegue una EI, tornando infine al programma
interrotto con una RET. Ricordiamo che le interruzioni risulteranno effettivamente ri-abilitate
solo al termine della istruzione successiva alla EI, ossia nel momento in cui la RET conclude la
sua esecuzione. A questo punto, se la linea di INT ritorna attiva, il processore riparte con
unaltra sequenza di interruzione...

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-14

9.4

I temporizzatori (Timer)
Abbiamo visto che, se un sistema non utilizza le interruzioni, il processore esegue di fatto un
unico e solo programma. Questo programma pu essere composto da molti moduli diversi tra
loro, ma saranno sempre eseguiti sotto stretto controllo di un programma principale. Nel
caso di semplici sistemi questo metodo pu essere utilizzato, ma in generale ci troveremo di
fronte a casi reali dove il processore dovr soddisfare eventi esterni che si presenteranno nel
tempo in maniera del tutto imprevedibile, e spesso urgenti e irrevocabili.
Ad esempio, nel caso di un sistema che riceve allarmi da un impianto, i vari dispositivi di
ingresso/uscita coinvolti devono richiedere intervento al processore via interrupt, in modo da
essere serviti nel pi breve tempo possibile. Per citare un altro esempio: in un sistema che
acquisisce dati da uno o pi sensori, luscita di questi non pu essere trascurata dal
processore (se non per brevi intervalli di tempo), pena la perdita di dati importanti.
Esistono poi altri casi, le cui specifiche richiedono lesecuzione di compiti ad intervalli di
tempo precisi, come ad esempio la richiesta di visualizzare dei dati su di un pannello ad
intervalli regolari, o la loro trasmissione periodica ad una sala di controllo.
Se provassimo a risolvere il problema mediante un approccio puramente software, dovremmo
scrivere un programma che si occupi di misurare il tempo, mentre nel frattempo svolge altri
compiti, come ad esempio controllare ciclicamente un sensore. Potremmo scrivere una routine
di ritardo, includendo nel ciclo le istruzioni per il controllo del sensore.
Questo metodo applicabile solo nel caso di sistemi molto semplici. Se i sensori ed i rispettivi
compiti da eseguire fossero tanti e magari a tempi diversi tra loro, il codice sorgente
risulterebbe molto complesso ed involuto.
E evidente che dovremo scegliere una strada diversa: per questo motivo che tra i dispositivi
di I/O di un generico sistema a microprocessore troveremo spesso uno o pi dispositivi
hardware di temporizzazione (Timer), in grado di interrompere il processore ad intervalli
prefissati.
Questi dispositivi in generale sono programmabili, nel senso che prevedono dei porti di controllo
attraverso cui il programma pu attivarli, disattivarli, definirne lintervallo di temporizzazione,
impostarne la modalit non periodica (one shot mode) o periodica (cyclic mode), e altro.
I Timer sono basati sulluso di contatori pre-caricabili, temporizzati dal clock di sistema e
collegati a porti che il processore usa per programmarli.

9.4.1

Un esempio di Timer
Immaginiamo
di
utilizzare
un
dispositivo
Timer
dallhardware predefinito e quindi non programmabile via
software (vedi Fig. 9.14).
In questo esempio semplificato, il Timer interagisce con il
processore DMC8 soltanto con due linee: INT e INTA . Non
vogliamo esaminare la rete interna del dispositivo: lo
descriviamo invece da un punto di vista comportamentale.
Il nostro Timer ha un funzionamento ciclico, con periodo di
T, per esempio 50 mS. Si parla di Timer Tick: al termine
di ogni intervallo T, il dispositivo attiva la richiesta di
interrupt INT del processore e questo, se gli interrupt sono
abilitati, inizia al suo interno la sequenza di interruzione.
Sappiamo che il DMC8 segnala linizio di questa sequenza,
attivando luscita INTA : il nostro Timer predisposto in
modo da resettare la richiesta di interruzione INT nel
momento in cui riceve il segnale INTA , come descritto dal
tracciato temporale mostrato in Fig. 9.15.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

Fig. 9.14: Un generico Timer


(non programmabile)

9-15

Fig. 9.15: Tracciato temporale della sequenza di interruzione da Timer

In figura, al momento della richiesta di interruzione (a), una istruzione in corso di esecuzione,
e viene terminata; allistante (b) inizia la sequenza di interruzione, con lattivazione di INTA ; a
seguito di questo segnale, il Timer disattiva la richiesta di interruzione (c); infine, dopo la
sequenza di interruzione (11 cicli di clock), durante la quale salvato lindirizzo di ritorno,
allistante (d), il processore lancia la routine di interruzione.
La necessit di resettare la richiesta di interruzione INT discende dal fatto che questa attiva
a livello e non sul fronte: se la linea INT fosse ancora attiva nel momento delluscita dalla
routine di interruzione, il processore verrebbe nuovamente interrotto, mentre si vuole che
questo avvenga soltanto allo scadere del prossimo intervallo T.
Si noti che la richiesta di interruzione pu essere disattivata soltanto a seguito della sua
accettazione da parte del processore stesso. Se il Timer generasse la richiesta INT con un
impulso della durata di un tempo prefissato, la richiesta potrebbe essere ignorata dal
processore, se in quel momento le interruzioni fossero state (temporaneamente) disabilitate
dal programma in corso di esecuzione (mediante le istruzioni DI e EI). In altre parole, il
processore non ricorda le richieste di interruzione, necessario che queste vengano
mantenute attive fino a quando non vengono accettate.
Per questo motivo, un qualunque dispositivo che interrompe non resetta mai la richiesta di
interruzione di sua iniziativa, ma in generale aspetta che ci sia una risposta da parte del
processore. Nel nostro semplice caso, utilizziamo la risposta pi semplice e immediata che si
possa avere, come abbiamo visto, ma nei casi reali pi complessi, dove avremo sempre molti
dispositivi in grado di generare linterruzione, non sar possibile resettare le richieste tramite la
linea INTA , in quanto la loro disattivazione dovr avvenire solo dopo che la routine di
interruzione avr individuato il dispositivo richiedente, in modo selettivo. Questa operazione di
disattivazione ottenuta, di solito, tramite dei porti di I/O dedicati allo scopo e connessi al
dispositivo che interrompe.
Nel caso dellinterfaccia esaminata in precedenza (Fig. 9.12), per esempio, loperazione di
disattivazione della richiesta di interruzione ottenuta direttamente tramite la lettura del porto
del dato: in questo caso, quindi, non necessaria una ulteriore ed esplicita operazione di I/O
su di un porto dedicato.

9.4.2

Uso dei Timer: esecuzione concorrente di programmi


Quando abbiamo un solo programma che gira nel nostro sistema, la sequenza delle
operazioni determinata rigorosamente dal programmatore. In un sistema dove sono presenti
molti dispositivi gestiti tramite interruzione, sar generalmente presente una routine di risposta
per ognuno. La routine di servizio che compete al particolare dispositivo, potr essere lanciata
dalla richiesta di interruzione in un qualunque momento, cio in un modo totalmente
asincrono rispetto al programma principale. A maggior ragione, le routine di servizio sono
asincrone tra di loro.
Se una operazione B necessita dei risultati di una operazione A, ovviamente necessario
prevedere lesecuzione delle operazioni nellordine corretto: prima A e poi B. Nel momento in
cui le operazioni A e B sono eseguite da due distinti programmi tra loro asincroni occorre
garantire che la corretta successione sia rispettata.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-16

Problemi di questo genere sono di normale amministrazione nei sistemi operativi multiprocesso (Unix, Linux, Windows...), che consentono allutente di fare girare
contemporaneamente molti programmi applicativi (si parla di processi concorrenti).
Nel caso dei nostri semplici sistemi, dal momento che si ipotizza di non disporre di un sistema
operativo di supporto, dovremo garantire la sincronizzazione tra processi nel modo pi
appropriato al caso particolare da risolvere. Il Timer un elemento importante per affrontare
questo genere di problemi.
Facciamo un esempio: il programma principale Main acquisisce in continuazione dati da una
interfaccia audio, mentre la routine di interrupt IntR, lanciata periodicamente tramite Timer
Tick, gestisce la loro archiviazione sul disco magnetico. Come possiamo garantire la giusta
sincronizzazione tra i due processi Main e IntR in esecuzione? Come fa IntR a sapere che
Main gli ha preparato dei dati?
Potremmo ipotizzare che il processo Main, nel momento in cui possiede dei dati da passare al
processo IntR, li trasferisca in unarea di memoria dedicata e quindi scriva in una variabile
SYNC, unaltra locazione di memoria, il numero di byte da trasferire.
Il processo IntR, che eseguito periodicamente, controlla se nella variabile SYNC presente
un numero diverso da zero. Se zero, termina senza fare altro, altrimenti provvede a
trasmettere i byte (prendendoli dallarea di memoria dedicata) al sistema di scrittura del disco.
Solo dopo avere finito la trasmissione dei dati, il processo IntR si preoccupa di azzerare la
variabile SYNC, in modo da impedire che nel frattempo il processo Main sposti dei nuovi dati
nellarea di memoria dedicata. Il processo Main, quindi, attende che SYNC sia azzerato
dallaltro processo, prima di procedere a ricopiare altri dati nellarea; al termine di questa
operazione, il processo Main scrive nella variabile SYNC il nuovo numero di byte.
La variabile SYNC si comporta come un semaforo, che consente ai due processi di scambiarsi
dati in modo sincronizzato, mediante unarea di memoria condivisa tra i due processi.
Nota:
Loperazione di sincronizzazione deve avere caratteristiche atomiche, ossia deve essere indivisibile, e quindi
deve essere scrivibile e/o leggibile dal processore con una sola istruzione, come nellesempio ora descritto.
Se per scrivere o leggere la variabile di sincronizzazione fossero necessarie pi istruzioni (nel caso in cui fosse
composta da pi byte), la routine di interruzione potrebbe essere eseguita durante laggiornamento della variabile
e si troverebbe quindi una variabile aggiornata per met (e priva di significato).
In casi come questi, una soluzione rappresentata dalluso delle istruzioni di abilitazione e disabilitazione delle
interruzioni: prima di aggiornare la variabile, li disabilitiamo con una istruzione DI, e li riabilitiamo subito dopo, con
la EI. In questo modo si impedisce alla routine di interrupt di interrompere le operazioni nel momento sbagliato.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

9-17

10

Applicazioni ed esercizi risolti


In questo capitolo sono presentati alcuni esempi di programmazione in Assembly DMC8.

10.1

Lemulatore di microcomputer d-McE


Il microcomputer basato sul DMC8 a cui facciamo riferimento quello emulato dallambiente di
simulazione Deeds (Digital Electronics Education and Design Suite). Il Deeds stato
sviluppato presso il Gruppo Sistemi Elettronici e Reti (ESNG) del Dipartimento di Ingegneria
Biofisica ed Elettronica (DIBE) dellUniversit degli Studi di Genova, ed reperibile sul sito:
http://www.esng.dibe.unige.it/Deeds .
In Fig. 10.1 riportata larchitettura del sistema, dove si osservano, tra laltro, 4 porti paralleli di
ingresso (IA, IB, IC, ID) e 4 porti paralleli di uscita (OA, OB, OC, OD). Il clock del sistema di
10 MHz, ed presente un generatore di Reset.
Oltre che con le linee dei porti di ingresso e di uscita, il sistema comunica con lesterno con gli
ingressi di controllo:
!Reset, inizializza il sistema (attivo basso);
!Int, chiede una interruzione alla CPU (attivo basso).

Fig.10.1: Il microcomputer, basato sul microprocessore DMC8, come modellato nel Deeds
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-1

Sono disponibili, poi, le uscite:


!RsOut, indica che il sistema correntemente in fase di Reset (attivo basso);
CkOut, riporta in esterno il Clock usato internamente dal microprocessore;
!IntA, o Interrupt Acknowledge, indica allesterno che il processore ha iniziato una
sequenza di interruzione;
!Sync, riporta in esterno luscita omonima del DMC8;
!rA, !rB, !rC, !rD, riportano in esterno i segnali di read dei porti di ingresso;
!wA, !wB, !wC, !wD, riportano in esterno i segnali di write dei porti di uscita.
Nel Deeds disponibile il Micro Computer Emulator (d-McE), che permette di scrivere e
provare programmi per questo microcomputer.
In Fig. 10.2, un file di codice sorgente in assembly DMC8 aperto nelleditor del d-McE.
Lassemblatore, disponibile tra i comandi, sulla barra degli strumenti, consente di tradurre il
sorgente in codice eseguibile; questo viene poi automaticamente caricato nella memoria ROM
del sistema emulato, pronto per essere eseguito.

Fig.10.2: Leditor dellemulatore di microcomputer d-McE, del Deeds, basato sul microprocessore DMC8

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-2

Fig.10.3: Il debugger interattivo dellemulatore di microcomputer d-McE, del Deeds

Il debugger del d-McE visibile in Fig. 10.3. Il programma, dopo la traduzione in codice
eseguibile, ora caricato nella memoria del sistema emulato, ed pronto per essere testato
mediante le funzioni interattive del debugger. Nella finestra di questo si osservano diversi
riquadri, esaminati pi in dettaglio nel seguito.

10.1.1 La barra di controllo


La barra di controllo, visibile in alto nella finestra, riportata ingrandita in Fig. 10.4. In tale barra
sono presenti, sulla sinistra, alcuni pulsanti per lesecuzione interattiva del codice.
[Step]

Permette lesecuzione passo-passo, ossia di una sola istruzione alla volta;

[Animate] Consente lesecuzione delle istruzioni una dopo laltra, in automatico, ma


rallentate da un temporizzatore, la cui cadenza definibile dal cursore poco pi
avanti nella stessa barra;
[Run]

Lancia lemulazione del programma alla massima velocit consentita dal proprio
hardware a disposizione (allincirca, su di personal computer con una CPU da 2
GHz, la velocit corrisponde ad un sistema reale da circa 2 MHz di clock);

[Pause]

Mette in pausa lemulazione, se precedentemente avviata con i pulsanti


[Animate] e [Run]. In questa modalit si pu riprendere lesecuzione come si
vuole, per esempio con il pulsante [Step];

Fig.10.4: La barra di controllo del debugger interattivo

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-3

[Over]

Questo pulsante ha due posizioni fisse, e definisce il modo di esecuzione dei


programmi nelle modalit [Step] e [Animate].
Quando [Over] attivato (premuto gi), le chiamate a sottoprogramma (le CALL)
sono eseguite per intero dallemulatore alla massima velocit, senza entrare
passo-passo nel sottoprogramma stesso. La visualizzazione dellesecuzione
rimane al livello del programma chiamante e la CALL eseguita in un unico
passo, come se fosse una qualunque altra istruzione.
Invece, se il pulsante [Over] in posizione di riposo (modalit di default), le
CALL sono eseguite allinterno, istruzione per istruzione; la visualizzazione del
programma segue, quindi, il livello delle chiamate alle subroutine;

[Animation Speed]

Come accennato sopra, questo cursore permette di regolare la


velocit di animazione della esecuzione in [Animate]. La velocit
regolabile da un minimo di un secondo per istruzione in su.

Il riquadro del clock visualizza, in alto, il numero di cicli di clock trascorsi a partire dal Reset del
sistema. Letichetta [Partial] in realt un pulsante, e permette di azzerare il numero riportato
nel campo in basso, che riporta in numero di cicli di clock contati a partire dallazionamento di
[Partial]. Questo contatore azzerabile utile in diverse situazioni, come ad esempio la verifica
del tempo di esecuzione di un sottoprogramma, o di una routine di ritardo.
I due pulsanti pi a destra:
[Reset]

Questo pulsante controlla, in modo manuale, lingresso di !Reset del


microcomputer. Quando premuto, il sistema mantenuto azzerato; quando
rilasciato, il sistema torna a rispondere ai vari comandi di [Step], [Animate] ecc.
(a seconda della modalit impostata);

[Int]

Questo pulsante controlla lingresso di !Int del microcomputer, e consente di


richiedere, in modo manuale, interruzione al processore. Serve per testare le
routine di Interruzione.

10.1.2 I registri interni della CPU


Il riquadro di visualizzazione dei registri interni alla CPU riportato in Fig. 10.5. Nel riquadro
abbiamo anche la possibilit di modificare manualmente il valore dei registri, sia in binario,
agendo sui piccoli pulsanti tondi dei singoli bit, sia in modo testuale inserendo il numero nel
campo alla destra di ciascun registro (una apposita voce del men di contesto di questo
riquadro consente di impostare il formato in decimale o in esadecimale).

Fig.10.5: Il riquadro di visualizzazione dei registri interni alla CPU

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-4

Modificare il contenuto dei registri utile, in fase di prova di un programma, per accorciare i
tempi di test: per esempio, se nel codice presente un ciclo di ritardo, in certe circostanze pu
essere utile causare unuscita anticipata dal ciclo stesso modificando a mano il valore del
registro utilizzato come contatore del ciclo.
I Flag sono editabili soltanto in binario, data la loro natura di singoli bit; i nomi dei Flag, non
immediatamente visibili, sono visualizzabili soffermandoci sopra il mouse. La modifica manuale
del valore di un Flag pu essere utile in fase di debug, ad esempio, per causare (o impedire) un
salto condizionato, a scopo di test.
Il contenuto del Program Counter non liberamente editabile: possibile assegnare ad esso
soltanto gli indirizzi delle istruzioni del programma attualmente caricato in memoria. La modifica
del valore del Program Counter consente di scavalcare parti del codice, quando utile, per
andare a testare singoli pezzi del programma.

10.1.3 La memoria di sistema


Il riquadro di visualizzazione della memoria visibile in Fig. 10.6. Sulla sinistra, in esadecimale,
riportato lindirizzo della locazione di memoria il cui contenuto visibile in prima colonna.
Lindirizzo delle altre locazioni sulla stessa riga dato da quellindirizzo, pi il valore riportato in
cima alla colonna stessa. Per esempio, nella figura, nella riga identificata dallindirizzo 0100h, la
locazione che contiene 3Eh si trova allindirizzo 0103h (0100h + 03h).

Fig.10.6: Il riquadro di visualizzazione della memoria (in esadecimale, sulla sinistra, e in codice ASCII, a destra)

Il riquadro diviso in due parti: quella a sinistra visualizza il contenuto delle locazioni di
memoria in formato esadecimale; le stesse locazioni sono anche visualizzate sulla destra, in
formato ASCII ( utile per visualizzare stringhe di testo).
Per nostra comodit, il debugger colora in modo differente lo sfondo delle differenti aree di
memoria, a seconda della loro destinazione: ROM [indirizzi 0000h..7FFFh], RAM [indirizzi
8000h..FFFFh], area non inizializzata, area contenente codice, ecc.
Nel riquadro abbiamo anche la possibilit di modificare manualmente il contenuto delle
locazioni della memoria, ma solo nellarea di RAM. Per editare una locazione, sufficiente farvi
sopra click con il mouse, cancellare il precedente valore e scrivere il nuovo numero (soltanto in
esadecimale).
Con il men di contesto (tasto destro del mouse) possibile spostarsi rapidamente su di un
altro indirizzo (la scroll bar sulla destra poco pratica per spostamenti grandi).
Nota:
Solo la RAM editabile, perch il debugger pone lutente sullo stesso piano della CPU (che non pu
scrivere nella ROM). La ROM stata programmata nella fase precedente, a seguito delle operazioni
di compilazione del programma; quando lutente apre il debugger, la ROM ormai pronta per essere
utilizzata e, come in un sistema reale, non pi modificabile al run-time.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-5

10.1.4 Il codice eseguibile


Un riquadro molto importante, da un punto di vista operativo, quello del codice eseguibile
(Fig. 10.7). In questa finestra osserviamo pi colonne. Le prime due sulla sinistra riportano, in
esadecimale, il codice macchina dellistruzione, accanto al corrispondente indirizzo di
allocazione. Le successive colonne riportano il corrispondente codice sorgente che,
assemblato, ha dato origine a tale istruzione (etichetta, codice mnemonico e operando,
commento).

Fig.10.7: Il riquadro del codice eseguibile

Facciamo ora un esempio, per imparare a leggere questo modo di rappresentare il codice.
Nella figura, allindirizzo 0111h presente il codice operativo C3h , seguito nellordine dai due
byte 10h e 01h (nella casella leggiamo: C31001). Questa istruzione occupa, come si vede, 3
byte: lindirizzo della successiva istruzione infatti 0114h (= 0111h+3).
Dagli altri campi della riga si vede che listruzione sorgente da cui stato ottenuto questo
codice il salto JP MAINLOOP.
E interessante notare che MAINLOOP letichetta della precedente istruzione: in fase di
compilazione, lassemblatore ha assegnato al simbolo MAINLOOP il valore 0110h, in quanto
indirizzo assegnato alla istruzione con tale etichetta. Come abbiamo visto qui sopra, il valore
0110h compare, smontato nei due byte Low (=10h) e High (=01h), subito dopo il codice
operativo C3h del salto JP MAINLOOP.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-6

Il men di contesto di questa finestra offre la possibilit di scegliere tra due modi di
visualizzazione del codice. Oltre a quello ora visto (Compact) possibile scegliere il modo
Extended, come visibile in Fig. 10.8. In questa modalit possibile esaminare meglio i
contenuti della memoria, per intero, anche nelle zone in cui non stato allocato codice
eseguibile. Tuttavia, per il test del programma pi pratica e conveniente laltra modalit.

Fig.10.8: Il codice eseguibile rappresentato in modalit Extended.

Quando testiamo il nostro programma, mediante i pulsanti [Step] o [Animate], le istruzioni in


corso di esecuzione sono evidenziate, riga per riga, in questa finestra. Quando lesecuzione
in pausa, listruzione evidenziata la prossima non ancora eseguita.
E possibile inserire nel codice dei punti di interruzione (Break Point), cio possiamo
obbligare lemulatore a fermarsi, quando lesecuzione [Animate] o [Run], allatto di eseguire
una data istruzione.
Questa possibilit molto comoda, perch permette di eseguire in [Run], e quindi molto
velocemente, parti di codice gi testate e di fermarsi l dove invece occorre esaminare pi da
vicino le operazioni. Per inserire o eliminare un punto di interruzione, occorre selezionare nella
tabella la riga della istruzione alla quale vogliamo che lemulazione si fermi, e poi agire con il
menu di contesto (Vedi Fig. 10.9).

Fig.10.9: Il men di contesto per inserire o eliminare un Break Point

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-7

10.1.5 I porti paralleli di ingresso e uscita


In Fig. 10.10 rappresentato il riquadro dello stato dei porti di ingresso e uscita. Questa finestra
consente di modificare lo stato dei porti di ingresso IA, IB, IC e ID, in modo simile a quanto visto
per il riquadro dei registri.

Fig.10.10: Il riquadro di visualizzazione dei porti paralleli di Ingresso e Uscita

Lo stato dei porti di uscita OA, OB, OC e OD, invece, non modificabile da parte dellutente,
trattandosi di uscite generate dal microcomputer.
Lindirizzo a cui i porti sono allocati definibile: possiamo modificare tali indirizzi tramite il men
principale, o con il men di contesto di questo riquadro, attivando la finestra di dialogo di
Fig.10.11 (nellesempio raffigurato compaiono gli indirizzi di default).

Fig.10.11: La finestra di dialogo per la definizione degli indirizzi dei porti

A questo proposito, conviene considerare la struttura hardware dei porti di ingresso e di uscita
su cui lemulatore si basa. In Fig. 10.12 riportiamo il modello hardware del porto parallelo di
ingresso IA: gli altri porti di ingresso IB, IC e ID sono identici, salvo sostituire, nella figura, i nomi
dei relativi segnali coinvolti.
Come si osserva in Fig. 10.12, lindirizzo di ciascun porto definibile mediante un insieme
(array) di interruttori: possiamo assegnare al porto un indirizzo qualunque tra tutti quelli
possibili (da 00h a FFh), salvo il fatto che, ovviamente, non possiamo allocare pi porti di
ingresso allo stesso indirizzo.
Si noti la presenza della linea in uscita denominata !rA (= reading A): questa linea viene
attivata tutte le volte che viene eseguita una istruzione di tipo IN riferita al porto IA. Segnala la
effettiva lettura del porto da parte del microprocessore e segue landamento temporale del
segnale !READ (vedi: ciclo di lettura del porto di ingresso, figura 8.5). Nellemulatore d-McE
lattivazione di questo segnale non direttamente visibile: invece utilizzabile nel d-DcS, come
si vedr nel seguito. Anche gli altri porti di ingresso posseggono lo stesso segnale
(rispettivamente !rB, !rC, !rD per i porti IB, IC e ID).
Da un esame della struttura del circuito del porto di ingresso, notiamo inoltre che non
presente nessuna struttura di memorizzazione dei dati. La responsabilit di mantenere stabili i
dati, durante lesecuzione della istruzione IN, demandata alla rete esterna che ce li fornisce.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-8

Fig.10.12: La struttura del porto parallelo di ingresso IA

La struttura dei porti di uscita riportata in Fig. 10.13, dove si osserva il porto parallelo OA. Gli
altri porti di uscita OB, OC e OD sono identici, salvo sostituire, anche qui, i nomi dei relativi
segnali coinvolti.
Si noti la presenza, in uscita, di un registro. Ogni volta che il processore esegue una istruzione
OUT, indirizzata a questo porto, un nuovo contenuto sostituisce il precedente nel registro.
Linformazione memorizzata, in uscita, dalla precedente scrittura fino alla successiva.

Fig.10.13: La struttura del porto parallelo di uscita OA

Anche per i porti di uscita lindirizzo definibile mediante degli interruttori, con le stesse regole
viste per i porti di ingresso. Si noti che non possiamo allocare pi porti di uscita allo stesso
indirizzo, ma che un porto di uscita e uno di ingresso possono invece condividere senza
conflitti lo stesso indirizzo. Infatti, i loro circuiti sono indipendenti tra di loro, uno risponde
allistruzione IN, lalto allistruzione OUT mediante segnali differenti (!READ e !WRITE).
Anche il porto di uscita possiede una linea, denominata !wA (= writing A), che viene attivata
ogni volta che viene eseguita una istruzione OUT sul porto: segnala leffettiva scrittura del porto
e segue landamento temporale del segnale !WRITE (vedi: ciclo di scrittura del porto di uscita,
figura 8.6).
Anche gli altri porti di uscita (OB, OC e OD) hanno un analogo segnale (!wB, !wC e !wD).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-9

10.2

Il microcomputer come componente d-DcS


Le caratteristiche del microcomputer emulato nel d-McE, lo rendono adatto per applicazioni
embedded, nelle quali il microcomputer esegue una particolare funzione allinterno di un
sistema, rimpiazzando altre strutture hardware. Per questo motivo, il microcomputer
disponibile, come componente (DMC8 Microcomputer), anche nella libreria del simulatore
digitale d-DcS, e pu essere inserito in un sistema digitale complesso.

10.2.1 Il componente DMC8 Microcomputer nel d-DcS


In Fig. 10.14 ne riportato un esempio elementare di utilizzo. Il componente rende disponibili le
terminazioni definite in precedenza (vedi Fig. 10.1), riportate sul contorno del componente.

Fig.10.14: Il componente DMC8 microcomputer, disponibile nel d-DcS del Deeds

Non sono resi disponibili allesterno i bus: il collegamento dati con lesterno si svolge, quindi,
soltanto tramite i porti paralleli di ingresso e di uscita. Le connessioni ai porti di ingresso IA, IB,
IC e ID si trovano sui lati sinistro e in alto del componente; i porti di uscita OA, OB, OC e OD,
invece, sui lati destro e in basso. Abbiamo quindi un totale di 32 linee in ingresso e 32 in uscita.
Accanto alle connessioni di ciascun porto troviamo i rispettivi segnali di controllo (esaminati nel
paragrafo precedente): !rA, !rB, !rC e !rD per i porti di ingresso, e !wA, !wB,!wC e !wD per i
porti di uscita. Si presti attenzione al fatto che, sia per i porti di ingresso che per quelli di uscita,
queste sono linee in uscita dal componente.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-10

Il microcomputer ha un suo generatore di clock interno, la cui frequenza di 10 MHz: questo


segnale reso disponibile in uscita sulla linea CkOut.
Il componente possiede un ingresso di !Reset: quando attiviamo questo segnale (a 0), il
microcomputer viene inizializzato, e riprender a funzionare solo dopo la sua disattivazione. Si
tenga presente che il microcomputer possiede una rete di reset automatico al suo interno,
per cui non siamo obbligati ad attivare, allinizio della simulazione, lingresso di !Reset.
Correlata alla funzionalit del reset automatico, il microcomputer possiede luscita !RsOut, che
attivata dal componente allavvio della simulazione (per 8 cicli di CkOut). Inoltre, luscita
!RsOut si attiva anche quando attiviamo lingresso !Reset.
La linea in uscita !Sync, disponibile sul componente in alto a destra, proviene direttamente
dalla CPU ed attivata a 0 durante il ciclo di prelievo dellistruzione.
In ultimo, ma non meno importante, il componente rende disponibili le linee di !Int e di !IntA,
consentendo cos la realizzazione di sistemi embedded funzionanti su base interrupt.

10.2.2 Il componente Interrupt Timer


Nella Fig. 10.14, a destra in basso, si osserva limpiego del componente Interrupt Timer.
Questo timer, per ragioni di semplicit, non programmabile via software, ma pu essere
configurato dal progettista al momento della definizione dello schema. un contatore ciclico in
avanti, con modulo di conteggio programmabile, che conta i fronti di salita che riceve
sullingresso Ck.
Ogni volta che raggiunge il massimo numero del conteggio, attiva a 0 la linea !Int, che usata
per richiedere interruzione al microcomputer. Luscita !Int del timer, a differenza del normale
Terminal Count di un contatore, una volta attivata, rimane attiva fino a che lattivazione del
suo ingresso !IntA, proveniente dal microcomputer, non la ripristina al valore di riposo.

Fig.10.15: La finestra delle propriet del componente Interrupt Timer

La finestra delle propriet del componente, attivabile tramite il men di contesto, consente di
definirne il tempo di ciclo (vedi Fig. 10.15). La finestra ha due modalit di lavoro: in quella pi
semplice (a sinistra nella figura), inseriamo direttamente il modulo di conteggio nel campo
Interval. Nellaltra modalit (a destra), questo numero pu essere assegnato in modo semiautomatico, indicando il tempo di ciclo desiderato e la frequenza di clock utilizzata (tipicamente
10 MHz, se collegato direttamente al DMC8 microcomputer).

10.2.3 Il men di contesto del componente DMC8 Microcomputer


Il DMC8 Microcomputer, non appena inserito nello schema nel d-DcS, ha la ROM vuota: per
programmarla necessario avere prima scritto il programma utilizzando il d-McE. Il men di
contesto del componente microcomputer (vedi Fig. 10.16) presenta una specifica voce per
programmare la ROM, utilizzando direttamente il file prodotto con il d-McE.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-11

Fig.10.16: Il men di contesto del DMC8 Microcomputer

Il sistema legge il file, lo traduce in codice macchina, ed infine programma la ROM del
microcomputer (emulando la presenza di uno specifico modulo hardware dedicato).
La ROM pu essere ri-programmata quante volte si vuole. Si faccia attenzione che, in fase di
simulazione, questa voce di men non accessibile.

Fig.10.17: Il debugger accessibile tramite il men di contesto del Microcomputer

Il men di contesto rende disponibile anche una serie di voci per interagire con il Debugger del
DMC8 Microcomputer (vedi Fig. 10.17). Le prime quattro attivano altrettante finestre, che altro
non sono che quelle disponibili nel d-McE:

La finestra del Codice Oggetto;


La finestra dei Registri;
La finestra della Memoria;
La finestra dei Porti di Ingresso e Uscita

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-12

Queste finestre, rispetto al d-McE, sono tra loro separate e visualizzabili a discrezione
dellutente, e possono essere piazzate dove si vuole sullo schermo.
Le altre due voci di men (sempre in Fig. 10.17) permettono di attivare:
la finestra di visualizzazione (in sola lettura) del codice sorgente del programma;
la Tabella dei Simboli, ricavata dallassemblatore.

10.2.3.1

La finestra del Codice Oggetto

La finestra del codice oggetto funzionalmente molto simile a quella che gi abbiamo
esaminato a riguardo del d-McE, come si vede in Fig. 10.18, ma posizionabile e
dimensionabile come si vuole sullo schermo.

Fig.10.18: La finestra del codice oggetto, ed il relativo men di contesto

Il men di contesto permette di inserire, anche per la simulazione nel d-DcS, dei punti di
interruzione (Break Point), molto utili per fermare lesecuzione in punti opportuni. Le ultime
due voci del men permettono di attivare da qui, senza tornare nelleditor, le altre finestre del
Debugger, e di posizionare questa finestra in modo che rimanga sempre in primo piano.
In Fig. 10.18, in alto a sinistra, si osserva il pulsante [Instruction Step], che compare quando si
attiva la simulazione interattiva nelleditor, con i clock NON animati. Durante la simulazione
interattiva possiamo attivare (o meno) lanimazione dei clock: in Fig. 10.19 evidenziato
lapposito comando, disponibile sia sulla barra del men principale (a sinistra, in figura), che nel
men di contesto del componente (a destra).

Fig.10.19: I comandi per labilitazione (o disabilitazione) della animazione dei clock

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-13

In simulazione interattiva abbiamo quindi due possibilit:


Clock animati:

Non compare il pulsante [Instruction Step] nella finestra del codice.


Usiamo i punti di interruzione per fermare lesecuzione del programma.
Regoliamo la velocit di esecuzione con il cursore disponibile sulla
barra del men principale ed il suo moltiplicatore X1, X10, X100 posto
accanto al cursore (vedi Fig. 10.19).
Vediamo eseguire automaticamente il programma, istruzione dopo
istruzione, mantenendo linterazione con tutto il resto della rete logica
presente nelleditor.

Clock NON animati:

Compare il pulsante [Instruction Step] nella finestra del codice.


Premendo con il mouse questo pulsante, possiamo far avanzare il
programma di una istruzione alla volta.
Lesecuzione di una istruzione sposta in avanti il tempo della simulazione
di tanti clock quanti sono necessari al completamento della istruzione
stessa. Il tempo si sposta in avanti, ovviamente, anche per il resto della
rete eventualmente collegata al CkOut del microcomputer.

10.2.3.2

La finestra dei Registri

La finestra dei registri interni del processore identica a quella gi esaminata per il d-McE, ma
ha la possibilit di essere visualizzabile e posizionabile dove si vuole sullo schermo (Fig. 10.20).

Fig.10.20: La finestra dei registri interni al DMC8

10.2.3.3

La finestra della Memoria

Analogamente, anche la finestra di visualizzazione della memoria identica a quella del d-McE,
con in pi la possibilit di essere posizionabile e dimensionabile a piacimento sullo schermo
(vedi Fig. 10.21).

Fig.10.21: La finestra di visualizzazione della memoria del microcomputer DMC8

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-14

10.2.3.4

La finestra dei Porti di Ingresso e Uscita

La finestra dei porti di ingresso e uscita (Fig. 10.22) simile a quella del d-McE, ma qui non
consente la modifica dei valori dei porti di ingresso, in quanto il loro valore determinato dai
componenti collegati ai porti nello schema della rete.

Fig.10.22 La finestra di visualizzazione dei porti di Ingresso e Uscita

10.2.3.5

La finestra di visualizzazione del codice sorgente

La finestra di visualizzazione del codice sorgente consente di esaminare il codice originale,


prodotto nel d-McE, ma senza poterlo editare (Fig. 10.23). La finestra dimensionabile e
spostabile dove vi vuole; in basso alla finestra sono visualizzate informazioni sul file originale,
che era stato caricato al momento della programmazione della ROM. Si tenga presente che il
file d-McE stato da quel momento inglobato nel file del data base della rete: nel caso che lo si
voglia modificare, necessario disporre del file originale d-McE.

Fig.10.23: La finestra di visualizzazione del codice sorgente originale, come appare nel d-McE

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-15

10.2.3.6

La Tabella dei Simboli

In alcuni casi pu essere utile consultare la tabella dei simboli del programma (Fig. 10.24).
Questa tabella stata generata dallassemblatore, al momento della programmazione della
ROM, e riporta il nome dei simboli ed il loro valore, per nostra comodit, in decimale,
esadecimale e binario.

Fig.10.24: La finestra di visualizzazione della Tabella dei Simboli, usati nel programma sorgente

10.2.4 La simulazione temporale di un sistema con microcalcolatore embedded


In Fig. 10.25 si osserva il diagramma temporale del d-DcS, durante una sessione di
simulazione temporale. Nellesempio in figura, il microcomputer compare nel diagramma con
una traccia, espansa in sottotracce, etichettata con il nome che abbiamo assegnato, nello
schema, al componente (Data Processor).

Fig.10.25: Il diagramma temporale e le tracce relative al microcomputer embedded

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-16

La traccia principale visualizza lindirizzo ed il codice sorgente delle istruzioni che sono state
eseguite (nellesempio di Fig. 10.25, si leggono i riferimenti a due istruzioni OR A e JP
Z,PROCESS). I dettagli intermedi della esecuzione della istruzione non sono rappresentati.
La traccia pu essere espansa in sottotracce agendo sul piccolo pulsante tondo (
), o
richiusa. Per default, visualizzata soltanto una sottotraccia: il clock interno del microcomputer,
utile quale riferimento temporale per esaminare il tracciato. Possiamo scegliere, prima di
iniziare la simulazione, quali sottotracce visualizzare, agendo sul men di contesto della traccia
principale (Fig. 10.26).

Fig.10.26: Il men di contesto della traccia relativa al DMC8 microcomputer

Facendo click sulla voce Select Signals to Trace, compare una finestra di dialogo che
consente di scegliere, tra quelli disponibili, i segnali da visualizzare sulle sottotracce (Fig. 10.27:
i segnali selezionati in questo esempio sono quelli che compaiono in Fig. 10.26). Si faccia
attenzione che i valori dei porti di ingresso ed uscita, nelle sottotracce del diagramma
temporale, sono rappresentati in esadecimale.

Fig.10.27: La finestra di dialogo per scegliere i segnali del microcomputer da visualizzare

Ai fini di una corretta ed esaustiva simulazione temporale, le finestre del debugger (che
abbiamo visto prima) sono disponibili anche qui, tramite la relativa voce di men (Fig. 10.28).
In particolare molto utile visualizzare la finestra del codice oggetto e fare avanzare la
simulazione a piccoli passi temporali (al momento non disponibile, nel diagramma temporale,
una funzione di avanzamento della simulazione di tipo passo-passo).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-17

Fig.10.28: Il sottomen del Debugger, per visualizzare le sue finestre di lavoro

In Fig. 10.29, una rete contenente un microcomputer DMC8 analizzata nei suoi
comportamenti hardware e software grazie alla simulazione temporale, affiancata dalla
visualizzazione del codice oggetto.
Fermando la simulazione ad un certo istante, possibile esaminare lo stato della rete del
sistema ed in particolare del microcomputer. Nella finestra del codice oggetto evidenziata la
riga corrispondente allistruzione in corso di esecuzione. E possibile inserire dei punti di
interruzione, per eseguire la simulazione fino alloccorrenza di una data istruzione (la
simulazione si ferma un istante prima del prelievo dellistruzione dalla memoria).

Fig.10.29: Simulazione temporale affiancata dalla finestra del codice oggetto


Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-18

10.3

Esempi introduttivi
Gli esercizi presentati in questo paragrafo consentono di avvicinarsi alla programmazione in
assembly di un sistema embedded proponendo semplici compiti di tipo procedurale,
principalmente ispirati a funzioni logiche tipiche della componentistica digitale.
Da un punto di vista dellapprendimento, il punto rilevante di questa piccola classe di esercizi
consiste nellessere obbligati a riprodurre in forma algoritmica procedurale (eseguendo una
operazione alla volta) il comportamento di sistemi in cui i processi logici avvengono
normalmente in forma parallela (pi operazioni svolte contemporaneamente).
La necessit di riprodurne il funzionamento con un linguaggio a basso livello come
lassembly ci impone una forma di scomposizione logica del funzionamento dei dispositivi,
macchine a stati comprese.
Per motivi di semplicit tutti gli esempi si baseranno sul microcomputer esaminato allinizio del
capitolo, utilizzando i necessari porti paralleli di ingresso e di uscita.

10.3.1 Funzioni logiche elementari


In una rete combinatoria, le uscite sono una funziona diretta degli ingressi, a parte i ritardi. Un
sistema procedurale che emula questo comportamento deve controllare continuamente gli
ingressi e produrre le uscite corrispondenti.

10.3.1.1

Porta NOT

Per la porta NOT, colleghiamo al nostro sistema embedded, utilizzando due porti, un filo di
ingresso e uno di uscita, come qui descritto, e colleghiamo a 0 gli ingressi non usati.
Porto IA (00h)

Ingresso

Porto OA (00h)

Uscita

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

!X

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Il codice che ne risulta il seguente:


; Porta NOT
;
INPORT
EQU
OUTPORT
EQU
;
ORG
JP
;
ORG
START:
IN
XOR
OUT
JP

00h
00h

; Definisco un nome simbolico


; per i porti di ingresso e uscita

0000h
0100h

; Indirizzo di partenza forzato dal Reset Hardware


; Salto allindirizzo 0100h

0100h
A,(INPORT)
01h
(OUTPORT),A
START

;
;
;
;
;

Leggo lingresso, che vale 0000.000X


Nego solo il bit che mi interessa
Mando il risultato in uscita
Ripeto dalla lettura dellingresso, il loop
infinito (fino allo spegnimento del sistema)

Da notare che i simboli INPORT e OUTPORT sono stati definiti nelle prime righe, prima del loro
utilizzo nel codice. Ricordiamo inoltre che il RESET hardware obbliga il processore ad eseguire
la prima istruzione allocata allindirizzo 0000h, dove inseriamo un salto (JP) allindirizzo 0100h.

10.3.1.2

Porta AND (a due ingressi)


Ingressi
Uscita

Porto IA (00h)
Porto OA (00h)

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

XY

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-19

Nellesempio precedente ci siamo limitati a leggere un ingresso, negarlo e riportare il valore in


uscita: non abbiamo effettuato nessun test sullingresso.
Esistono diversi modi per testare uno o pi bit di un porto e il primo che andremo a vedere
detto controllo bit a bit . Consiste nel testare solo il bit che ci interessa e, a seconda del valore
trovato, scegliere fra due diverse sequenze. Le istruzioni per il test del bit sono le seguenti:
BIT

n,r

Testa il bit n del registro r. Loperando n una costante


compresa fra 0 e 7, loperando r specifica un registro
interno a 8 bit.
Se il bit n uguale a zero, il Flag di zero posto a 1,
altrimenti posto a 0.

JP
JP

NZ,<indirizzo>
Z,<indirizzo>

Salti condizionati al valore del Flag di Zero. Si salta a


<indirizzo> se la condizione NZ (Not Zero) oppure Z
(Zero) verificata.

Un primo programma che realizza la porta AND ha la struttura seguente:


1. Si legge lingresso e si testano i bit che interessano;
2. In base al valore di questi bit si agisce coerentemente, preparando in A il valore di uscita;
3. Si manda in uscita il valore preparato in A e si ripete tutto da capo.
;--------- Porta AND -----------------------------------------------------------;
INPORT
EQU
00h
; Definisco un nome simbolico
OUTPORT
EQU
00h
; per i porti di ingresso e uscita
ORG
0000h
JP
0100h
;
ORG
0100h
START:
IN
A,(INPORT)
; Leggo il porto, devo testare i due ingressi X e Y
BIT
0,A
; Testo X
JP
Z,OUT0
; Se X=0 allora XY=0 salto all indirizzo OUT0
BIT
1,A
; Se X=1 testo Y
JP
Z,OUT0
; X=1 Y=0, quindi XY=0 salto a OUT0
OUT1:
LD
A,01h
; Altrimenti X=Y=1 cio XY=1, pongo A=0000.0001
JP
OUTPUT
; Salto ad OUTPUT dove mander A in uscita
OUT0:
LD
A,00h
; In OUT0 pongo A=0000.0000 e proseguo ad OUTPUT
OUTPUT:
OUT
(OUTPORT),A
JP
START

Una seconda versione del programma considera congiuntamente il valore di pi bit, con
lutilizzo di una maschera: questo metodo risulta di solito pi rapido e sintetico del test bit a bit.
Per maschera intendiamo un byte di zeri e uni che useremo come operando di una operazione
di AND bit a bit, come spiegato dalla soluzione proposta:
;--------- Porta AND (con test
;
INPORT
EQU
00h
OUTPORT
EQU
00h
ORG
0000h
JP
0100h
;
ORG
0100h
START:
IN
A,(INPORT)
XOR
0FFh
AND
03h

OUT0:
OUT1:
OUTPUT:

JP
LD
JP
LD
OUT
JP

Z,OUT1
A,00h
OUTPUT
A,01h
(OUTPORT),A
START

eseguito su pi bit contemporaneamente) ---------; Definisco un nome simbolico


; per i porti di ingresso e uscita

;
;
;
;
;
;
;

nego tutti i bit in input, anche quelli non usati


maschero a zero i bit 7-2; (invariati i bit 1-0)
il flag Zero sar posto a 1 se !X e !Y sono a zero
se gli originali X e Y erano a 1, si salta,
altrimenti luscita preparata a zero in A.
salto ad OUTPUT dove mander A in uscita
in OUT1 pongo A= 00000001b e proseguo ad OUTPUT

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-20

In generale, utilizzando una maschera intendiamo porre ad un valore noto (o zero o uno),
mediante unoperazione logica un insieme di bit, per poter valutare, in ununica operazione, il
valore degli altri bit, quelli non mascherati.
A seconda del risultato cercato, il byte che contiene i bit da controllare, contenuto in A, sar
messo in AND oppure OR con una opportuna maschera, nel modo seguente:

Per mascherare a 0 il bit n di A, si fa un AND con un numero binario avente il bit in


posizione n uguale a 0, e tutti gli altri a 1. Listruzione AND 1100.0111b, ad esempio,
maschera a 0 i bit 5,4 e 3 di A.
Per mascherare a 1 il bit n di A, si fa un OR con un numero binario avente il bit in
posizione n uguale a 1, e tutti gli altri a 0. Listruzione OR 0000.1110b, ad esempio,
maschera a 1 i bit 3,2 e 1 di A.

Nella programmazione Assembly, la pratica di mascherare i bit indesiderati per poter poi
effettuare test di tipo logico e/o aritmetico sul gruppo di bit restante (solitamente corrispondenti
a ingressi o a risultati di altre operazioni) molto comune.

10.3.1.3

Multiplexer (due canali, una uscita)

Vediamo ora la simulazione di multiplexer a due canali. Il test degli ingressi effettuato bit a bit.
Ingressi
Uscita

Porto IA (00h)
Porto OA (00h)

Bit7

Bit6

Bit5

Bit4

Bit3

S2 S1 SEL
Bit2

Bit1

Bit0

OUT

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Le specifiche del componente sono queste:

OUT=S1 con SEL=0

OUT=S2 con SEL=1

;--------- Multiplexer ---------------------------------------------------------;


INPORT
EQU
00h
OUTPORT
EQU
00h
ORG
0000h
JP
0100h
ORG
0100h
;
START:
IN
A,(INPORT)
BIT
0,A
; Leggo SEL
JP
NZ,S2
; Se SEL=1 mando in uscita S2 altrimenti S1
S1:
BIT
1,A
; Leggo l ingresso S1
JP
Z,OUT0
; S1=0 mando 0 in uscita
JP
OUT1
; S1=1 mando 1 in uscita
;
S2:
BIT
2,A
; Analogamente per S2
JP
Z,OUT0
JP
OUT1
;
OUT0:
LD
A,00h
JP
OUTPUT
OUT1:
LD
A,01h
OUTPUT:
OUT
(OUTPORT),A
JP
START

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-21

10.3.1.4

Decoder (da 3 a 8)

Un decoder da 3 a 8 dispone di tre ingressi C, B e A, ove lesterno imposta un numero binario


CBA (di valore compreso fra 000b e 111b), e otto uscite (numerate da 0 a 7). Il dispositivo attiva
luscita corrispondente al numero CBA lasciando inattive le altre sette.
Useremo un metodo di test mediante exor, effettuato sulle tre linee di ingresso, confrontando
lingresso con tutti i valori compresi fra 0 e 7 (con un ciclo) e aggiornando un registro con
luscita corrispondente: quando lingresso coincide con il valore testato si salta alluscita.
Questa volta supponiamo che i
bit del porto di ingresso, non
usati dal decoder, siano
collegati a linee utilizzate per
altri compiti (che non sono qui
descritti): non possiamo pi
ipotizzare che siano a zero e
dovremo mascherare i bit che
non servono.
Ingressi
Uscite

Porto IA (00h)
Porto OA (00h)

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

U7 U6 U5 U4 U3 U2 U1 U0
Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

;--------- Decodificatore 3-8 ---------------------------------------------------;


INPORT
EQU
00h
OUTPORT
EQU
00h
ORG
0000h
JP
0100h
ORG
0100h
;
START:
IN
A,(INPORT)
AND
00000111b
; MASCHERO i bit che non mi interessano eliminando
; lambiguit sui bit non di nostra competenza
LD
C,A
; C <- A, ma delle sole linee CBA
LD
B,10000000b ; preparo luscita in B (per il caso CBA = 111)
LD
D,00000111b
LOOP:
XOR
D
; Se A = 00000111b questa operazione dar 0 come
; risultato, salto a
JP
Z,OUTPUT
; OUTPUT dove mander in uscita B= 1000.0000 cio
; attiver il bit corrispondente al numero in ingresso
SRL
B
; altrimenti, scalo verso destra i bit di B
; (B= 01000000b dopo il primo scalamento)
DEC
D
; D= 00000110b
LD
A,C
; rimetto in A il valore delle linee CBA
JP
LOOP
; ripeto da capo, ma con D diminuito di uno
;
OUTPUT:
LD
A,B
; Per mandare in uscita B devo prima copiarlo in A:
OUT
(OUTPORT),A ; solo A pu essere utilizzato con la istruzione OUT
JP
START

Data lesiguit dei registri su cui possiamo effettuare calcoli, si noti che in questo programma si
salvato un valore in un altro registro (C) per non perderlo e poterlo ricaricare in accumulatore
(senza doverlo rileggere).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-22

10.3.2 Reti logiche di tipo sequenziale


In una rete sequenziale sincrona avremo la necessit di eseguire compiti in risposta ai fronti
attivi di un segnale in ingresso che ne rappresenta il segnale di sincronizzazione (il clock della
rete sequenziale di cui stiamo riproducendo il funzionamento).
Dovremo scrivere una subroutine che rilevi i fronti attivi di questo segnale. Questo si pu
ottenere controllando il valore della linea in esame e restituendo il controllo al chiamante (il
programma principale) non appena riscontrato un fronte di salita.
Eccone una possibile realizzazione:
;--- Subroutine per rilevare il fronte di salita di un segnale in ingresso -----;
WAITL:
IN
A,(INPORT)
; Leggo il valore del segnale (sul bit 0)
BIT
0,A
; Se a 1 ritorno a WAITL,
JP
NZ,WAITL
; attendendo il fronte di discesa
;
WAITH:
IN
A,(INPORT)
; Quando il segnale a 0, attendo la sua salita:
BIT
0,A
; rileggo lingresso e testo nuovamente il bit
JP
Z,WAITH
; se = 0 aspetto, tornando a WAITH
;
RET
; quando il segnale passa a 1 (un fronte di salita),
; restituisco il controllo al chiamante

10.3.2.1

Flip-Flop di tipo D PET


Ingressi
Uscita

Porto IA (00h)
Porto OA (00h)

IN

CK

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

OUT

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

;--------- FLIP-FLOP di tipo D-Pet ---------------------------------------------;


INPORT
EQU
00h
OUTPORT
EQU
00h
ORG
0000h
JP
0100h
ORG
0100h
;
LD
SP,0FFFFh
; Poich uso le istruzioni CALL, RET, PUSH, POP,
; che usano lo stack, inizializzo lo Stack Pointer
START:
CALL WAITL
; Allinterno di un ciclo principale, chiamo la
; subroutine che mi restituir il controllo sul fronte
; di salita del segnale di sincronizzazione. Nel
; registro A, uscendo dalla soubroutine, abbiamo
; ancora quanto letto sul porto, anche il bit IN
BIT
1,A
; e quindi lo controllo
JP
NZ,OUT1
; se IN=1 vado a mettere 1 in A
LD
A,00h
; altrimenti metto 0 in A e vado a mandare A in
JP
OUTPUT
; uscita
OUT1:
LD
A,01h
OUTPUT:
OUT
(OUTPORT),A
JP
START
; ripeto tutto
;
WAITL:
IN
A,(INPORT)
; questa la routine descritta prima
BIT
0,A
JP
NZ,WAITL
WAITH:
IN
A,(INPORT)
BIT
0,A
JP
Z,WAITH
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-23

10.3.2.2

Flip-Flop di tipo D PET, con ingresso asincrono di Clear

In presenza di ingressi di controllo asincroni, come ad esempio il Clear di un flip-flop, la logica


del nostro programma si complica un poco: dato che lingresso asincrono pu cambiare in
qualunque momento, dovremo continuamente controllarlo.
Ingressi
Uscite

Porto IA (00h)
Porto OA (00h)

Bit7

Bit6

Bit5

Bit4

Bit3

CLEAR IN
Bit2

CK

Bit1

Bit0

OUT

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Allo scopo, modificheremo la routine che controlla il segnale di sincronizzazione, aggiungendo il


controllo dellingresso asincrono. Nel caso in cui tale ingresso si attivi, si dovr chiamare una
subroutine che esegua le azioni dovute alla funzione di tale ingresso, per poi ritornare nel ciclo
di attesa del fronte attivo del segnale di sincronizzazione.
;--------- Flip-Flop D PET con CLEAR asincrono -------------------------------;
INPORT
EQU
00h
; Questo il FF-D visto prima, la differenza sta
OUTPORT
EQU
00h
; nelle routine WAITL e CLEAR.
ORG
0000h
JP
0100h
ORG
0100h
;
LD
SP,0FFFFh
START:
CALL WAITL
;
BIT
1,A
JP
NZ,OUT1
LD
A,00h
JP
OUTPUT
OUT1:
LD
A,01h
OUTPUT:
OUT
(OUTPORT),A
JP
START
;
;--------------------------------------------------------------------------WAITL:
IN
A,(INPORT)
; Prima di controllare il clock, testo il Clear:
BIT
2,A
; e se trovo CLEAR attivo (basso),
CALL Z,CLEAR
; chiamo il sottoprogramma CLEAR
;
BIT
0,A
; ma continuo sempre il test sullingresso CK
JP
NZ,WAITL
;
WAITH:
IN
A,(INPORT)
; Naturalmente ripeto il test del Clear anche nel
BIT
2,A
; loop WAITH e, se attivo,
CALL Z,CLEAR
; chiamo il sottoprogramma CLEAR
;
BIT
0,A
; e continuo ad aspettare il fronte di salita di CK
JP
Z,WAITH
;
BIT
2,A
; larrivo del fronte di salita, se il Clear
JP
Z,WAITL
; attivo, deve essere ignorato, per cui non esco dalla
; subroutine se Clear attivo, ma ripeto il ciclo
RET
; Quando Clear sar disattivato, il controllo
; torner al programma principale.
;
;--------------------------------------------------------------------------CLEAR:
PUSH AF
; salvo A, perch in A c la lettura del porto
LD
A,00h
; La subroutine di CLEAR azzera semplicemente
OUT
(OUTPORT),A ; luscita
POP
AF
; recupero il contenuto precedente di A
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-24

10.3.2.3

Registro a scorrimento (8 bit)

Per replicare via software il comportamento di una rete sequenziale occorre tenere conto dello
stato interno della rete. Possiamo simulare lo stato dei Flip-Flop assegnando ognuno di essi
ad un bit di un registro interno del processore; qualora il numero di Flip-Flop fosse troppo
elevato per la capienza dei registri, utilizzeremo delle locazioni di memoria RAM.
Prendiamo in esame un registro a scorrimento a 8 bit come quello in figura:

Associamo lo stato dei singoli flip-flop ai bit del registro interno B, in questo modo:
Registro B

Q7 Q6 Q5 Q4 Q3 Q2 Q1 Q0
Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Mappiamo cos le terminazioni del componente sui porti di ingresso e uscita:


Ingressi
Uscite

Porto IA (00h)
Porto OA (00h)

IN

CK

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Q7

Q6 Q5 Q4 Q3 Q2 Q1

Q0

Bit7

Bit6

Bit0

Bit5

Bit4

Bit3

Bit2

Bit1

Da un punto di vista algoritmico, ad ogni fronte attivo dellingresso CK, dovremo:


1. far scorrere tutti i bit (del registro B) da Q0 verso Q7, ossia verso sinistra (dal punto di
vista del registro);
2. immettere il valore attuale dellingresso IN sul Flip-Flop Q0 (nel bit 0 di B);
3. generare le nuove uscite Q0..Q7, prelevandole dal nuovo stato in B.
Lo scorrimento dei bit potr essere ottenuto ad esempio con listruzione SLA B che fa scorrere
verso sinistra ciascun bit ponendo a 0 il bit 0 e perdendo il valore precedente del bit 7.
Listruzione SET 0,B copia lingresso IN sul bit 0 di B.
;--------- Registro a scorrimento da 8 bit -------------------------------------;
INPORT
EQU
00h
OUTPORT
EQU
00h
ORG
0000h
JP
0100h
ORG
0100h
;
LD
SP,0FFFFh
LD
B,00h
; inizializzo B, che conterr lo stato del registro
;
START:
CALL WAITL
; attendiamo il fronte di salita di CK
;
SLA
B
; a seguito del fronte di salita, lo shift:
;
BIT
1,A
; Testo l ingresso IN ( gi in A)
JP
Z,OUTPUT
; Se IN = 0 non faccio nulla, con la SLA: B0 = 0
SET
0,B
; Se invece IN = 1, pongo B0 = 1
;
OUTPUT:
LD
A,B
; mandiamo in uscita l intero registro B
OUT
(OUTPORT),A
JP
START

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-25

WAITL:

IN
BIT
JP
IN
BIT
JP
RET

WAITH:

10.3.2.4

A,(INPORT)
0,A
NZ,WAITL
A,(INPORT)
0,A
Z,WAITH

; (questa routine gi stata analizzata)

; in A rimane il valore del porto (i bit IN e CK)

Registro a scorrimento (16 bit)

Per un registro a scorrimento come quello precedente, ma a 16 o pi bit, si deve ricorrere a 2 o


pi registri interni, e in questo caso non baster una sola istruzione per far scorrere tutti i bit.
Utilizziamo i registri interni H e L per memorizzare lo stato del registro:
Q15 Q14 Q13 Q12 Q11 Q10

Registro interno H
Registro interno L

Q9

Q8

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Q7

Q6

Q5

Q4

Q3

Q2

Q1

Q0

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Lo scorrimento a 16 bit si pu realizzare con la seguente sequenza di operazioni:


1. con listruzione SLA L il bit 7 di L si sposta nel flag di Carry (
), i bit 0-6 di
scorrono verso sinistra di una posizione, e nel bit 0 entra 0;
), nel bit 0 di H
2. con listruzione RL H i bit 0-6 di H ruotano verso sinistra (
ricopiato lattuale flag di Carry (ovvero il bit 7 di L prima dello scorrimento), e infine il bit 7
di H si sposta nel flag di Carry (ma questultimo spostamento non ci interessa);
3. infine, lingresso seriale IN viene ricopiato nel bit 0 di L.
Registro H

Registro L

Q15 Q14 Q13 Q12 Q11 Q10 Q9


Carry

H7

H6

H5

H4

H3

H2

H1

Q8

Q7 Q6 Q5 Q4 Q3 Q2 Q1 Q0

H0

Carry

L7

L6

L5

L4

L3

L2

L1

IN

L0

Mappiamo le terminazioni del componente sui porti di ingresso e uscita:


Ingressi
Uscite

Porto IA (00h)
Porto OA (00h)

IN

CK

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

L7 L6 L5 L4 L3 L2 L1

L0

Bit7

Porto OB (01h)

Bit6

Bit1

Bit0

H7 H6 H5 H4 H3 H2 H1

H0

Bit7

Bit0

Bit6

Bit5

Bit5

Bit4

Bit4

Bit3

Bit3

Bit2

Bit2

Bit1

;--------- Registro a scorrimento da 16 bit ------------------------------------INPORT


EQU
00h
;
OUTL
EQU
00h
OUTH
EQU
01h
ORG
0000h
JP
0100h
ORG
0100h
LD
SP,0FFFFh
LD
L,00h
; inizializziamo i registri H e L = 0
LD
H,L
START:
CALL WAITL
; attendiamo il fronte di salita (WAITL qui omessa)
;
SLA
L
; scorrimento a 16 bit esaminato prima
RL
H
BIT
1,A
; controllo IN (che ancora in A)
JP
Z,OUTPUT
; se IN diverso da zero,
SET
0,L
; lo copiamo nel bit 0 di L
;
OUTPUT:
LD
A,L
; mando in uscita la parte Low
OUT
(OUTL),A
LD
A,H
; e poi quella High dello stato del componente
OUT
(OUTH),A
JP
START
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-26

10.3.2.5

Contatore sincrono avanti, modulo 256, presettabile

Vediamo ora, come ultimo esempio di rete sequenziale, la realizzazione di un contatore


sincrono. Il contatore possiede un ingresso sincrono Preset per il caricamento in parallelo del
contatore. Quando Preset a 1, sul
fronte di salita del Clock, il numero
P7..P0 caricato sulle uscite Q7..Q0.
Se Preset pari a zero, ad ogni
fronte di salita del Clock il contatore
avanza di una unit. Il conteggio
avviene modulo 256, ossia ciclico
(0,1,2 254, 255, 0, 1...). TC
(Terminal Count) indica il passaggio
per il numero massimo del conteggio
(11111111b=255).
Mappiamo ingressi e uscite del componente sui porti del microcomputer:
Porto IA (00h)

Ingressi

Porto IB (01h)

PRESET

Clock

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

P7 P6 P5 P4 P3 P2 P1 P0
Bit7

Porto OA (00h)

Uscite

;---------;
INPORT
INDATA
OUTDATA
OUTPORT

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Q7 Q6 Q5 Q4 Q3 Q2 Q1 Q0
Bit7

Porto OB (01h)

Bit6

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

TC

Bit7

Bit6

Bit5

Bit4

Bit3

Bit2

Bit1

Bit0

Contatore Avanti - Modulo 256 Presettabile -----------------------EQU


EQU
EQU
EQU
ORG
JP
ORG

00h
01h
00h
01h
0000h
0100h
0100h

;
;
;
;

Preset (bit 1), Clock (bit 0)


Ingressi P7..P0
Uscite Q7..Q0
TC (bit 0)

LD
LD

SP,0FFFFh
C,00h

; C lo stato del contatore!

CALL

WAITL

; (questa qui omessa, la stessa dei casi visti)

BIT
JP

1,A
NZ,PRESET

; se il Preset attivo, si salta a PRESET


; altrimenti si prosegue con il normale conteggio

INC
LD
CP
JP
LD
JP
LD
OUT

C
A,C
0FFh
Z,TC_ON
A,00h
TC_OUT
A,01h
(OUTPORT),A

; incremento il valore dello stato interno in C

LD
OUT
JP

A,C
(OUTDATA),A
START

; il nuovo stato interno copiato sulle uscite

IN
LD
JP

A,(INDATA)
C,A
OUTPUT

; Preset attivo: leggiamo INDATA,


; aggiorniamo lo stato del contatore in C
; salta e aggiorna luscita

;
START:
;

TC_ON:
TC_OUT:
;
OUTPUT:

;
PRESET:

; controllo se C = 255 (vado ad attivare TC)


; altrimenti TC lo azzero

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-27

10.4

Esercizi risolti

(senza tecniche di interrupt)

In questo paragrafo sono presentati alcuni esercizi risolti. In tutti gli esempi, il processore
esegue i compiti richiesti senza far ricorso a tecniche di interrupt.

10.4.1 Contatore binario sincrono avanti/indietro a 12 bit


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INP (indirizzo 20h) e due porti
paralleli di uscita UH e UL (indirizzi 30h e 31h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un
contatore binario sincrono avanti/indietro a 12 bit (ciclico, modulo 4096), che abbia le seguenti
specifiche:
Ingressi:
CK:
DIR:

Clock di conteggio, attivo sui fronti di salita;


Ingresso sincrono per impostare la direzione di conteggio (conta in avanti se a
livello alto);
STEP2: Ingresso sincrono di impostazione del passo di conteggio (se basso, sul fronte
attivo di CK, il contatore incrementa o decrementa di uno; se alto, di due);
CLEAR: Ingresso sincrono di azzeramento (se alto, il contatore e` azzerato al fronte
attivo del clock).

Uscite:
U11..0:

Uscite di conteggio a 12 bit.

Si supponga di collegare gli ingressi CK, DIR, STEP2 e CLEAR al porto INP (rispettivamente ai
pin 0, 1, 2 e 3). Le uscite U11..0 saranno collegate ai porti UH e UL (UL0 = U0; i bit non utilizzati
devono essere azzerati). Il programma deve essere attivato al RESET del sistema.

Proposta di soluzione

;
START:
CLEAR:

;
OUTPUT:

;
INDIETRO:

;
AVANTI:

ORG
JP
ORG

0000H
0100H
0100H

;il programma parte al reset ma


;deve saltare le prime istruzioni
;perch riservate agli interrupt

LD
LD
LD
LD

SP,0FFFFh
A,00h
H,A
L,A

;inizializzazione stack pointer


;iniz. A,H e L

LD
OUT
LD
OUT
CALL
BIT
JP
BIT
JP

A,L
(31h),A
A,H
(30h),A
CLOCK
3,A
NZ,CLEAR
1,A
NZ,AVANTI

;output dello stato attuale del contatore

DEC
BIT
JP
DEC
JP

HL
2,A
Z,OUTPUT
HL
OUTPUT

;conteggio indietro...
;se lingresso STEP2 attivo...

INC
BIT
JP
INC
JP

HL
2,A
Z,OUTPUT
HL
OUTPUT

;conteggio avanti...
;se lingresso STEP2 attivo...

;attendiamo il fronte di salita di CK


;se lingresso CLEAR attivo, si salta
;se lingresso DIR attivo, si salta

;si decrementa ancora


;e, ogni volta, si aggiorna luscita

;si incrementa ancora


;e, ogni volta, si aggiorna luscita

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-28

;
CLOCK:

LOOP:

IN
BIT
JP
IN
BIT
JP
RET

A,(20h)
0,A
NZ,CLOCK
A,(20h)
0,A
Z,LOOP

;attesa del fronte di salita del clock

10.4.2 Rotazione di 8 bit su di un porto di uscita


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INPUT (indirizzo 22h) e un
porto parallelo di uscita OUTPUT (indirizzo 33h).
Si chiede di scrivere, in linguaggio assembly, un programma che faccia ruotare, sul porto di
uscita OUTPUT, una configurazione di zeri e uni acquisita dal porto di ingresso INPUT.
Specifiche:
La rotazione avviene ciclicamente sui 7 bit meno significativi del porto di uscita; e`
richiesto che il bit piu` significativo rimanga impostato a zero;
La configurazione dei bit da ruotare e` ricopiata direttamente dai 7 bit meno significativi
del porto di ingresso;
La rotazione avviene nella direzione impostata dal bit 7 del porto di ingresso, e a passi di
circa mezzo secondo (se bit 7 = 1: rotazione verso destra, MSB LSB);
Alla fine di ogni rotazione completa sui 7 bit il programma rilegge il porto di ingresso,
aggiorna la configurazione dei bit da ruotare e ne imposta la direzione di rotazione.
Nota: il programma deve andare automaticamente in esecuzione al RESET hardware del
sistema.

Proposta di soluzione
Nota: occorre tenere conto che la rotazione avviene su sette bit e non su otto.
INPUT
OUTPUT

START:

;
SINISTRA:

RES_UNO:
SET_UNO:
RIT_SIN:

EQU
EQU
ORG
JP
ORG

22H
33H
0000H
0100H
0100H

;definisco lindirizzo
;ingresso come normali
;il programma parte al
;deve saltare le prime
;perch riservate agli

dei porti di
costanti
reset ma
istruzioni
interrupt

LD
LD
IN
BIT
JP

SP,0FFFFH
B,07H
A,(INPUT)
7,A
NZ,DESTRA

;inizializzo lo stack pointer


;iniz. il contatore del numero di rotazioni
;leggo il porto di ingresso
;testo il bit che indica il senso di rotazione
;se uno -> destra, se zero -> sinistra

AND
OUT
RLCA

01111111b
(OUTPUT),A

BIT
JP
RES
JP
SET
CALL
DEC
JP
JP

7,A
NZ,SET_UNO
0,A
RIT_SIN
0,A
DELAY
B
NZ,SINISTRA
START

;Considero solo i sette da visualizzare


;Visualizzo sul porto di uscita i bit di dati
;ruoto tutto il byte di una pos.ne a sinistra:
;l'ultimo dei sette bit finisce nell'ultima
;posizione del registro poich la rotazione
; su sette bit. Bisogna considerare il valore
;dell'ultimo bit e spostarlo nella pos. giusta
;Testo l'ottavo bit, per il
;motivo precedente e pongo nella
;giusta posizione il bit
;ruotato poi chiamo la funzione
;di ritardo per far passare
;il mezzo secondo
;Decremento il contatore dei cicli
;Controllo se la rotazione terminata,
;se no ricomincio il ciclo. Se ho finito
;ricomincio con un altra serie di dati

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-29

DESTRA:

RES_SETTE:
SET_SETTE:
RIT_DEST:

AND
OUT
RRCA
JP
RES
JP
SET
CALL
DEC
JP
JP

01111111b
(OUTPUT),A
C,SET_SETTE
6,A
RIT_DEST
6,A
DELAY
B
NZ,DESTRA
START

;Considero solo i sette da visualizzare


;Visualizzo sul porto di uscita i bit di dati
;Ruoto A di una posizione a destra
;poich la rotazione su sette bit devo
;considerare il giusto valore del primo bit
;Analogamente al caso sinistra

;Ricomincia il ciclo

;Subroutine di ritardo
DELAY:
LOOP:

PUSH
LD
DEC
PUSH
POP
PUSH
POP
PUSH
POP
PUSH
POP
LD
OR
JP
POP
RET

AF
HL,0B4D9H
HL
AF
AF
AF
AF
AF
AF
AF
AF
A,H
L
NZ,LOOP
AF

;salvo il contenuto del registro A


;inizializzo il numero di cicli
;durata 6 cicli
;durata 11 cicli
;durata 10 cicli
;durata 11 cicli
;durata 10 cicli
;durata 11 cicli
;durata 10 cicli
;durata 11 cicli
;durata 10 cicli
;durata 4 cicli
;durata 4 cicli
;durata 10 cicli
;recupero il contenuto di A
;ritorno

Una nota a parte merita la subroutine DELAY, il cui unico effetto quello di far trascorrere il
tempo. Le push e la pop non fanno nulla di particolare, tranne che far trascorrere il tempo
necessario. Supposto un clock di 10MHz, per ottenere un ritardo di circa 0,5S ho bisogno di
5000000 cicli di clock del processore: linterno del loop dura 108 cicli, e quindi 5000000 / 108 =
(circa) 4629710 = B4D9H

10.4.3 Temporizzatore (da 0 a 25,5 S, in passi di 100 mS)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, due porti paralleli di ingresso INPUT e TIME (indirizzi 30h e
31h) e un porto parallelo di uscita OUTPUT (indirizzo 44h).
Si chiede di scrivere, in linguaggio assembly, un programma che emuli il funzionamento di un
temporizzatore avente le caratteristiche descritte nel seguito.
Il temporizzatore ha un ingresso di comando TRIG, 8 ingressi di dato T7..T0, e una uscita
PULSE. In condizioni di riposo, luscita PULSE e` a zero, e il dispositivo attende un fronte di
salita sullingresso TRIG. Allarrivo del fronte di salita sullingresso TRIG, il dispositivo attiva
luscita PULSE per una durata proporzionale al valore letto sugli ingressi T7..T0. Per il
temporizzatore, lunita` di tempo e` 100 mS, per cui la durata massima dellimpulso risultera`
pari a 25,5 secondi (se il valore impostato sugli ingressi T7..T0 e` zero, limpulso non e`
generato).
Durante la generazione dellimpulso il dispositivo controlla (almeno ogni 100 mS) lingresso
TRIG. Se questo ritorna basso, la generazione dellimpulso e` terminata anzitempo. Al termine
della generazione di un impulso, il dispositivo si pone nuovamente in attesa di un fronte di salita
sullingresso TRIG.
Si supponga lingresso TRIG collegato al bit 0 del porto INPUT, gli ingressi T7..T0 al porto TIME,
luscita PULSE al bit 7 del porto OUTPUT.
Nota: il programma deve andare automaticamente in esecuzione al RESET hardware del
sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-30

Proposta di soluzione
La soluzione composta da un programma principale e da due sotto-programmi. TRIG
individua il fronte di salita del segnale di ingresso TRIG, e WAIT genera un ritardo pari allunit
di tempo del temporizzatore.
INPUT
TIME
OUTPUT

CLEAR:

;
LOOP:

EQU
EQU
EQU

30h
31h
44h

;porto dingresso INPUT allindirizzo 30h


;porto dingresso TIME allindirizzo 31h
;porto di uscita OUTPUT allindirizzo 44h

ORG
JP
ORG

0000h
0100h
0100h

;il programma lanciato al RESET hardware


;scavalchiamo le locazioni riservate
;indirizzo di inizio del programma

LD
LD
OUT
CALL
IN
LD
OR
JP

SP,0FFFFh
A,00h
(OUTPUT),A
WAITTRIG
A,(TIME)
B,A
A
Z,CLEAR

;inizializzo lo STACK POINTER


;inizializzo luscita PULSE

LD
OUT

A,10000000b
(OUTPUT),A

;attendiamo il fronte di salita di TRIG


;leggo il valore dellingresso TIME
;carico il valore di A (TIME) nel registro B
;trucco assembler: controllo se TIME zero
;se TIME zero torno in attesa del fronte
;di salita di TRIG azzerando PULSE
;se TIME non zero attivo luscita PULSE

IN
BIT
JP

A,(INPUT)
0,A
Z,CLEAR

;controllo lingresso TRIG


;ora nel bit 0 di A
;se TRIG = 0 torno indietro, azzerando
;luscita PULSE e aspettando un nuovo TRIG

CALL
DEC
JP
JP

R100mS
B
NZ,LOOP
CLEAR

;attendo circa 100 millisecondi


;decremento B (alias il tempo rimanente)
;se non terminato, continuo il ciclo
;altrimenti attendo un nuovo fronte di TRIG

Il sotto-programma WAITTRIG attende il fronte di salita del segnale di ingresso TRIG:


WAITTRIG:

WAIT1:

IN
BIT
JP
IN
BIT
JP
RET

A,(INPUT)
0,A
NZ,WAITTRIG
A,(INPUT)
0,A
Z,WAIT1

Il sotto-programma R100mS genera un ritardo pari allunit di tempo richiesta (circa 100 ms).
Teniamo presente che il periodo del clock di 100 nS, per cui occorre un ritardo di un milione di
cicli.
R100mS:
RLOOP:

LD
DEC
LD
OR
JP
RET

DE,41666
DE
A,D
E
NZ,RLOOP

;=(circa un milione di cicli)


;decremento il contatore

;ritorno al programma chiamante

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-31

10.4.4 Trasmettitore seriale asincrono (6 bit, 1 mS)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INPUT (indirizzo 12h) e un
porto parallelo di uscita OUTPUT (indirizzo 14h).
Si chiede di scrivere, in linguaggio assembly, un programma che, alla ricezione di un dato
parallelo sul porto INPUT, ritrasmetta questo in formato seriale sul bit 0 del porto OUTPUT. Il
programma deve andare automaticamente in esecuzione al RESET hardware del sistema.
Il dato ricevuto sul porto INPUT e` rappresentato da 6 bit (linee INPUT6 .. INPUT1). La linea
INPUT7 e` collegata a zero. La linea INPUT0 viene utilizzata come segnale di convalida del
dato: un nuovo dato si intende valido alla transizione da zero a uno di INPUT0.
Lo standard da utilizzare per la trasmissione seriale prevede:
- Un bit di start a 1;
- I sei bit di dato (ordine dei bit: INPUT1 .. INPUT6);
- Un bit di stop a 0;
- Una durata del tempo di bit di un millisecondo.
Nota: ai fini della soluzione, e` accettabile che il tempo di bit sia ottenuto con una certa
approssimazione.

Proposta di soluzione
INPUT
OUTPUT

;
Inizio:

EQU
EQU
ORG
JP
ORG

12h
14h
0000h
0100h
0100h

;definiamo delle costanti


;con l'indirizzo dei porti di I/O
;origine al reset
;salta la zona riservata agli interrupt
;area programma

LD
LD
OUT

SP,0FFFFh
A,00000000b
(OUTPUT),A

;inizializzo lo stack pointer


;inizializzo il porto di uscita

CALL
Call

DatoPar
InviaSer

;attendo che il dato parallelo sia valido


;invio il dato seriale caricato in precendenza
;in 'A' dalla sub. Convalida
;ripete il ciclo

JP
Inizio
;
;routine di lettura dal porto parallelo
DatoPar:
IN
A,(INPUT)
;attendo che ci sia '0' nel bit
BIT
0,A
;di convalida
JP
NZ,DatoPar
WaitH:
IN
A,(INPUT)
;attendo una transizione
BIT
0,A
;testo il bit di validit del dato
JP
Z,WaitH
RET

Nota: in A abbiamo il dato caricato; il bit 0 gi ad 1 per cui lo usiamo come bit di start.
InviaSer:
;
LOOPTX:

LD
LD

B,08h
C,A

;carico il contatore
;in C il byte da trasmettere

LD
AND
OUT
CALL
SRL
DEC
JP

A,C
00000001b
(OUTPUT),A
Wait1ms
C
B
NZ,LOOPTX

;bit da trasmettere
;azzero i bit non di interesse
;esce lennesimo bit da trasmettere
;attende un millisecondo (circa)
;scalo a destra i bit da trasmettere
;decremento il contatore (invio 8 bit)
;se non ho ancora inviato tutti i bit
;di C continuo il ciclo
;ritorna dalla sub

RET

Per attendere 1ms si utilizzata una subroutine di attesa classica, con un loop che
decrementa un registro:
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-32

Wait1ms:
loopWait:

LD
DEC
LD
OR
JP
RET

DE,01A1h
DE
A,D
E
NZ,loopWait

;numero di cicli per attendere 1ms


;decremento DE (6 cicli) e controllo con un
; "trucco" se DE a zero (la DEC a 16 bit
;non tocca i flag) (totale 8 cicli)
;eseguo il test (10 cicli)
;esco quando passato 1ms

10.4.5 Contatore a codice programmabile (binario / gray, 4 bit)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INPUT (indirizzo 88h) e un
porto parallelo di uscita OUTPUT (indirizzo 81h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un
contatore a 4 bit, a codice programmabile (binario o Gray), in avanti, sincrono e ciclico.
Ingressi:
CK:
CODE:

Clock di conteggio, attivo sui fronti di salita;


Ingresso sincrono di impostazione del codice di conteggio (se basso, il contatore
conta in codice binario puro; se alto, in codice Gray. Non e` richiesto il
mantenimento dello stato del contatore nel passaggio da un codice allaltro);
CLEAR: Ingresso asincrono di azzeramento (se alto, il contatore e` azzerato in modo
asincrono).

Uscite:
U3..0:

Uscite di conteggio.

Si supponga di collegare gli ingressi CK, CODE e CLEAR al porto INPUT (rispettivamente ai
pin 0, 1 e 2). Le uscite U3..0 saranno collegate al porto OUTPUT (i bit non utilizzati devono
essere azzerati). Il programma deve essere attivato al RESET del sistema.
Nota: un numero in codice Gray G3G2G1G0 e` ottenuto dal numero binario B3B2B1B0 nel modo
seguente:
G3 = B3

G2 = B2 exor B3

G1 = B1 exor B2

G0 = B0 exor B1

Proposta di soluzione

INIZIO:
MAIN:

OUTVAL:

ORG
JP
ORG

OOOOh
0100h
0100h

LD
CALL
CALL
BIT
JP
INC
LD
AND
OUT
JP

SP,0F000h
CLEAR
CKA
1,A
NZ,GRAY
B
A,B
00001111b
(81h),A
MAIN

INC
LD
SLA
XOR
SRL
JP

B
A,B
A
B

IN
BIT
CALL
BIT
JP

A,(88h)
2,A
NZ,CLEAR
0,A
NZ,CKA

;inizializzazione Stack Pointer


;iniz. stato e porto di uscita
;attesa del fronte di salita
;se richiesto, salta al GRAY
;incrementa il valore del contatore
;e lo facciamo uscire

GRAY:

;incrementa in binario il contatore


;operazione che trasforma il binario
;in codice GRAY (vedi testo)

OUTVAL

CKA:

;attesa preventiva del fronte di discesa


;con controllo, nel frattempo,
;del CLEAR asincrono, e sua attuazione

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-33

;
CKB:

IN
BIT
CALL
BIT
JP
BIT
JP
RET

A,(88h)
2,A
NZ,CLEAR
0,A
Z,CKB
2,A
NZ,CKA

;attesa del fronte di salita


;con controllo, nel frattempo,
;del CLEAR asincrono, e sua attuazione

PUSH
LD
LD
OUT
POP
RET

AF
A,00h
B,A
(81h),A
AF

;iniz. stato e porto di uscita

;prosegue se trova il fronte di salita...


;se trovato, ma il CLEAR attivo,
;non esce e torna ad inseguire il CK

CLEAR:

10.4.6 Lampeggiatore (4 lampadine: 800, 400, 200, 100 mS)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso CNT (indirizzo 27h) e un porto
parallelo di uscita LITES (indirizzo 28h).
Si chiede di scrivere, in linguaggio assembly, un programma che faccia lampeggiare quattro
lampade L3, L2, L1 e L0, collegate ai bit 3, 2, 1 e 0 del porto di uscita LITES, in funzione dei
segnali di controllo presenti sul porto di ingresso CNT. Il programma deve andare
automaticamente in esecuzione al RESET hardware del sistema.
Le quattro lampade si devono accendere e spegnere continuamente, ciascuna con un periodo
di lampeggio differente, secondo la seguente tabella:
Lampada
L3
L2
L1
L0

Periodo
800 ms
400 ms
200 ms
100 ms

Il programma controlla ciclicamente i bit 7 e 6 del porto CNT:


Se il bit 7 e` a zero, le lampade vengono spente, se a uno riprendono a lampeggiare;
Se il bit 6 e` a uno, i tempi di lampeggio sono raddoppiati.
Nota: il ciclo di accensione/spegnimento di ogni lampada ha un duty cycle (rapporto
pieno/vuoto) del 50%.

Prima proposta di soluzione


CNT
LITES

START:

EQU
EQU

27h
28h

;indirizzo del porto di ingresso


;indirizzo del porto di uscita

ORG
JP
ORG

0000h
0100h
0100h

;faccio partire il programma al reset


;lascio libero lo spazio riservato

LD
LD

SP,0FFFFh
A,00001111b

CALL
LD
CALL
LD
CALL
LD

USCITA
A,00001110b
USCITA
A,00001101b
USCITA
A,00001100b

;
;
;
;
;
;

inizializzo lo Stack Pointer


metto in A il numero binario che
rappresenta lo stato delle luci
chiamo la subroutine di uscita(vedi sotto)
di seguito sono riportati tutti i casi
che permettono il lampeggio richiesto

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-34

CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
LD
CALL
JP

USCITA
A,00001011b
USCITA
A,00001010b
USCITA
A,00001001b
USCITA
A,00001000b
USCITA
A,00000111b
USCITA
A,00000110b
USCITA
A,00000101b
USCITA
A,00000100b
USCITA
A,00000011b
USCITA
A,00000010b
USCITA
A,00000001b
USCITA
A,00000000b
USCITA
START

; ritorno all' inizio del programma

La routine di attesa deve essere impostata su 50ms, poich in un periodo la lampadina per
met accesa e per met spenta. Inoltre, 50ms il minimo comune multiplo di tutti i semiperiodi.
La frequenza del clock del microprocessore di 10 MHz quindi ogni ciclo dura 100 nS. Le
operazioni all'interno di PAUSA fanno passare 66 cicli di clock. Si verifica facilmente che da
(7500*66) * 100nS si ottengono (circa) i 50mS richiesti.
S50MS:
PAUSA:

;
USCITA:

LAMP:
LAMP1:

NORMAL:

PUSH
LD
PUSH
PUSH
POP
POP
DEC
LD
OR
JP
POP
RET

AF
BC,7500d
HL
BC
BC
HL
BC
A,B
C
NZ,PAUSA
AF

;salva i dati di A ed F nello Stack


;carica in BC il numero di cicli di conteggio
;queste 4 operazioni non fanno
;nulla di significativo
;ma servono solo a far passare 42 cicli

LD
IN

B,A
A,(CNT)

LD
BIT
JP
LD
JP
LD
OUT
CALL
BIT
JP
CALL
RET

H,A
7,H
NZ,LAMP
A,00h
LAMP1
A,B
(LITES),A
S50MS
6,H
Z,NORMAL
S50MS

;salva in B il valore impostato in A


;carica in A i dati del porto di ingresso
;per controllare ciclicamente i bit 6 e 7
;memorizza i dati di CNT in H
;controlla il bit 7 di CNT
;se a zero le lampade sono spente

;decremeta BC di una unit


;queste due operazioni controllano che BC
;arrivi a zero (DEC BC non modifica i flag)
;attende che BC sia zero
;recupera i dati precedenti in A ed F

;se a uno riprendiamo il pattern...


;accende le luci come richiesto
;attende 50 millisecondi
;controlla il bit 6 di CNT
;se a zero, il semiperiodo di 50ms
;altrimenti il semiperiodo viene raddoppiato
;ritorno

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-35

Seconda proposta di soluzione


Questa seconda soluzione pi compatta.

;
START:
;
CLEAR:

LOOP:

ORG
JP
ORG

0000h
0100h
0100h

LD

SP,0FFFFh

;init SP

LD

C,00000000b

;lampade tutte spente (L3,L2,L1,L0)


;C pi sotto utilizzato come contatore
;in avanti: la lampada L0 si accende
;un ciclo s e uno no, la lampada L1
;due cicli s e due no, la lampada L3
;quattro cicli s e quattro no, la lampada
;L4 otto cicli s e otto no

LD
OUT

A,C
(28h),A

IN
BIT
JP
BIT
JP
CALL
CALL

A,(27h)
7,A
Z,CLEAR
6,A
Z,SINGOLO
RITARDO
RITARDO

;leggiamo il porto dingresso di controllo


;testiamo il bit 7
;se a zero torniamo a CLEAR, altrimenti...
;testiamo il bit 6
;se questo a zero dimezziamo i tempi
;altrimenti eseguiamo 2 volte il ritardo

INC

LD
CP
JP
JP

A,00010000b
C
NZ,CLEAR
LOOP

;C viene utilizzato come un contatore


;in avanti, la lampada L0 si accende
;un ciclo s e uno no, la lampada L1
;due cicli s e due no, la lampada L3
;quattro cicli s e quattro no, la lampada
;L4 otto cicli s e otto no
;test del max del contatore: = 1111b + 1

PUSH
PUSH
LD
DEC
LD
OR
JP
POP
POP
RET

AF
BC
HL,208Dh
HL
A,H
L,A
NZ,RIT
BC
AF

;scrive sul porto che pilota le lampade

SINGOLO:
;

;
RITARDO:

RIT:

;se abbiamo superato il max, ricomincia


;altrimenti saltiamo a LOOP
;salva nello Stack i registri
;interni AF,BC
;inizializza il contatore a 16 bit
;decrementa il contatore
;controlla che il registro HL sia stato
;azzerato mediante un OR tra H e L
;torna a RIT se non zero
;recupera dallo Stack i registri
;torna al chiamante

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-36

10.4.7 Lampeggiatore (3 lampadine: 500, 250, 200 mS)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso ENABLE (indirizzo 40h) e un
porto parallelo di uscita LAMPS (indirizzo 80h).
Si chiede di scrivere, in linguaggio assembly, un sottoprogramma che, quando chiamato,
faccia lampeggiare tre lampade collegate alle linee del porto di uscita LAMPS, in funzione dei
segnali di controllo presenti sul porto di ingresso ENABLE.
Le tre lampade L2, L1 e L0 si devono accendere e spegnere ciclicamente, ciascuna con tempi di
lampeggio differenti, secondo la seguente tabella:
Lampada
L2
L1
L0

Accesa per
500 ms
250 ms
200 ms

Spenta per
500 ms
250 ms
200 ms

Il sottoprogramma controlla ciclicamente i bit 0 e 1 del porto ENABLE:


Se il bit 0 viene letto a zero, il sottoprogramma ritorna al chiamante. In particolare, se il bit 0
e` a zero fin dallinizio, torna immediatamente al chiamante senza attivare le lampade.
Se il bit 1 viene letto a uno, i tempi di lampeggio sono raddoppiati (per tutte le lampade).
Le lampade si suppongano tutte spente al momento della chiamata del sottoprogramma;
dovranno essere spente al momento della uscita dal sottoprogramma.
Nota: si supponga esistente un programma chiamante; questo provvede alla inizializzazione
dello Stack Pointer prima di chiamare il sottoprogramma. Il sottoprogramma deve preservare
intatto il contenuto dei registri del processore.

Proposta di soluzione
Questo esercizio apparentemente simile al precedente, ma la tabella dei tempi dimostra che i
tempi di accensione e spegnimento non seguono le potenze del due... e questo ci obbliga a
risolvere il problema tenendo conto che questi tempi sono in questo caso multipli di 50 mS.
ENABLE
LAMPS

EQU
EQU

40h
80h

SOTTOPROG:

PUSH
PUSH
PUSH
IN
BIT
JP

AF
BC
DE
A,(ENABLE)
0,A
Z,FINE

;un sottoprogramma salva i registri

LD
OUT
LD
LD
LD
CALL
DEC
CALL
DEC
CALL
DEC
CALL
OUT
LD
IN
BIT
JP
LD
JP

A,00000111b
(LAMPS),A
B,0Ah
C,05h
D,04h
DELAY
B
Z,LAMP_2
C
Z,LAMP_1
D
Z,LAMP_0
(LAMPS),A
E,A
A,(ENABLE)
0,A
Z,FINE
A,E
LOOP

;accendo tutte e tre le lampadine

;test del bit 0 del porto di IN


;se zero, si torna subito al chiamante

LOOP:

;iniz. contatori: poich la routine di ritardo


; unica e di 50 ms, per avere un tempo pari
;a 500 ms occorre eseguirla 10 volte, 5 volte
;per 250ms (05h), 4 volte per 200 ms (04h)

;unica OUT per tutte e 3 le lampade


;la IN successiva modifica A: lo salviamo in E
;test del bit 0 del porto IN
;(viene cos effettuato ogni 50 ms)
;se necessario interrompiamo e usciamo
;ripristino il contenuto corretto di A
;si ricomincia con la scansione delle lampade

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-37

LAMP_2:

LAMP_1:

LAMP_0:

;
DELAY:

LOOP_INT:

;
RADDOPPIO:
;
FINE:

XOR
LD
RET
XOR
LD
RET
XOR
LD
RET

00000100b
B,0Ah

;inverte lo stato (On/Off) della lampada 2


;ripristina il contatore al valore iniziale

00000010b
C,05h

;idem per la lampada 1

00000001b
D,04h

;e per la lampada 0

PUSH
PUSH
IN
BIT
JP
LD
DEC
LD
OR
JP
POP
POP
RET

AF
HL
A,(ENABLE)
1,A
NZ,RADDOPPIO
HL,20833
HL
A,H
L
NZ,LOOP_INT
HL
AF

;qui necessario salvare i registri


;di cui qui variamo il contenuto
;test del bit 1 del porto di IN

LD
JP

HL,41666
LOOP_INT

;valore necessario per un tempo di 100ms

LD
OUT
POP
POP
POP
RET

A,00000000b
(LAMPS),A
DE
BC
AF

;spengo le lampade,

;valore necessario per un tempo di 50ms (*)


;6 cicli
;4 cicli
;4 cicli
;10 cicli

;ripristino il contenuto dei registri

;e infine torno al programma chiamante

(*) I valori iniziali con cui caricato il registro HL per le routine di ritardo di 50 e 100 ms sono
espressi per maggior chiarezza in notazione decimale e si riferiscono al DMC8 che lavora con
frequenza pari a 10 MHz. Il calcolo (approssimato) da effettuarsi infatti il seguente:
50ms = (6 + 4 + 4 + 10) * x / (10 MHz), da cui risulta (in decimale) x = 20833.
Analogamente per 100ms.

10.4.8 Contatore sincrono BCD a 3 cifre (12 bit)


Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32
Kbytes di ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INPUT (indirizzo 15h) e due
porti paralleli di uscita PH e PL (indirizzi 04h e 05h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un
contatore sincrono BCD a 3 cifre (12 bit), ciclico, con le seguenti specifiche:
Ingressi:
CLK:
Clock di conteggio, attivo sui fronti di discesa;
STEP: Ingresso sincrono di impostazione del passo di conteggio (se basso, sul fronte
attivo di CLK, il contatore incrementa di uno; se alto, di dieci);
RES:
Ingresso sincrono di azzeramento (se 1, il contatore e` azzerato al fronte attivo di
CLK).
Uscite:
UC3..0, Uscite di conteggio: cifre UC (centinaia), UB (decine), UA (unita`).
UB3..0,
UA3..0.
Si supponga di collegare gli ingressi CK, STEP e RES al porto INPUT (rispettivamente ai pin 0,
1 e 2). Le uscite UC, UB e UA saranno collegate, in un ordine conveniente, ai porti PH e PL.
Il programma deve essere attivato al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-38

Proposta di soluzione
Nota: il programma non inizializza lo Stack Pointer perch non lo usa.
INPUT
PH
PL

INIZ:

;
OUTBCD:

;
WAIT1:

WAIT0:

EQU
EQU
EQU

15h
04h
05h

;definisco gli indirizzi dei porti di I/O

ORG
JP
ORG

0000h
0100h
0100h

;cos il programma connesso al RESET HW

LD
LD
LD

B,00h
C,00h
D,00h

;B = conteggio centinaia
;C = conteggio decine
;D = conteggio unit

LD
RLCA
RLCA
RLCA
RLCA
OR
OUT
LD
OUT

A,C

;sposto le decine sul nibble high


;con 4 rotazioni a sinistra

D
(PL),A
A,B
(PH),A

;vi sovrappongo le unit


;e visualizzo decine e unit

IN
BIT
JP
IN
BIT
JP

A,(INPUT)
0,A
Z,WAIT1
A,(INPUT)
0,A
NZ,WAIT0

;aspetto che la linea del clock sia alta

BIT
JP

2,A
NZ,INIZ

;controllo il bit di RES


;e, se richiesto, azzero le uscite

BIT
JP

1,A
NZ,DIECI

;controllo il bit di STEP


;(+1 O +10)

;e poi visualizzo le centinaia

;e quindi aspetto il fronte di discesa

;
STEP:

;
;--- STEP AVANTI di 1 ---UNO:
INC
D
LD
A,D
CP
10
JP
NZ,OUTBCD
LD
D,0
;
;--- STEP AVANTI di 10 ---DIECI:
INC
C
LD
A,C
CP
10
JP
NZ,OUTBCD
LD
C,0
;
CENT:
INC
B
LD
A,B
CP
10
JP
NZ,OUTBCD
LD
B,0
JP
OUTBCD

;incremento le unit
;controllo che non abbiano superato il 9
;se no, torniamo su, visualizziamo il numero
;se si, azzero le unit e passo alle decine

;incremento le decine
;controllo che non abbiano superato il 9
;se no, torniamo su, visualizziamo il numero
;se si, le azzero e passo alle centinaia
;incremento le centinaia
;controllo che non abbiano superato il 9
;se no, torniamo su, visualizziamo il numero
;se si, azzero le centinaia
;e torno su comunque

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-39

10.4.9 Macchina a Stati Finiti


Un sistema basato sul microprocessore DMC8 possiede 32Kbytes di ROM (indirizzi
0000h..7FFFh) e 32Kbytes di RAM (indirizzi 8000h..FFFFh). Tra i suoi dispositivi di ingressouscita troviamo, tra laltro, un porto parallelo di ingresso INPUTS (indirizzo 55h), i cui bit 0, 1
sono collegati rispettivamente alle linee di ingresso CK e UP, ed un porto parallelo di uscita
OUTPUTS (indirizzo 88h), di cui sono significative le linee W1 e W0.

Si chiede di scrivere, in linguaggio assembly, un programma attivato al reset hardware che


realizzi lalgoritmo della MSF sincrona descritta dal diagramma ASM riportato nella figura qui
riportata. Le uscite della MSF, W1 e W0, rappresentano i numeri da 00 a 11.

Proposta di soluzione
Nella figura seguente abbiamo lo schema d-DcS, secondo le specifiche date: CK e UP sono
stati collegati al porto di ingresso IA, le uscite W1 e W0 al porto di uscita OA. I fili non usati di IA
sono stati collegati a 0; lingresso di !Int, non usato, posto a 1.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-40

Nella seguente soluzione, la linea del clock non controllata attendendo prima il fronte di
discesa e poi quello di salita. Si scelto di controllare ciclicamente se il valore della linea
cambiato: se cos, si controlla il valore attuale e, se pari a 1 (ossia si tratta di un fronte di
salita), si valuta il prossimo stato.
INPUTS
OUTPUTS

EQU
55h
EQU
88h
ORG
0000h
JP
START
ORG
0100h
;---------------------------------------------------------------------------START:
LD
SP,0FFFFh
; inizializzazione dello stack pointer
IN
A,(INPUTS)
; leggo dal porto dingresso
AND
01h
; visibile solo il bit di CK
LD
E,A
; in E c il valore di CK allistante precedente
;
STATO_A:
LD
A,00h
OUT
(OUTPUTS),A ; lo stato_a ha le uscite W1 e W0 entrambe a zero
CALL CK
; chiamata della subroutine CK dalla quale uscir
; solo alla rilevazione del fronte di salita
LD
A,C
; A<-C, il contenuto del porto dingresso
; letto sul fronte di salita del CK
AND
02h
; visibile solo il bit di UP
JP
Z,STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_B:
LD
A,01h
; se UP=1 passo nello stato_b
OUT
(OUTPUTS),A ; lo stato_b ha le uscite W0=1 e W1=0
CALL CK
LD
A,C
AND
02h
JP
Z,STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_C:
LD
A,02h
; se UP=1 passo nello stato_c
OUT
(OUTPUTS),A ; lo stato_c ha le uscite W0=0 e W1=1
CALL CK
LD
A,C
AND
02h
JP
Z,STATO_B
; se UP=0 vado nello stato_b, altrimenti
;
STATO_D:
LD
A,03h
; se UP=1 passo nello stato_d
OUT
(OUTPUTS),A ; lo stato_d ha le uscite W0=1 e W1=1
CALL CK
LD
A,C
AND
02h
JP
Z,STATO_C
; se UP=0 vado nello stato_c, altrimenti
JP
STATO_D
; se UP=1 ritorno nello stato_d
;
CK:
IN
A,(INPUTS)
; leggo sul porto dingresso
LD
C,A
; salvo il contenuto di tale porto
AND
01h
; rendo visibile solo il bit di CK
CP
E
; confronto il valore precedente e attuale del ck
JP
Z,CK
; se i due valori sono uguali, vado a rileggere il
; valore del porto, non c stato alcun fronte
AND
01h
; rendo visibile solo il bit di CK
JP
NZ,SALITA
; se CK=1 c stato un fronte di salita altrimenti
DISCESA:
LD
E,00h
; (CK=0) il era di discesa e quindi aggiorno E
JP
CK
; e vado a rileggere il clock
SALITA:
LD
E,01h
; aggiorno il valore di E
RET
; esco dalla subroutine CK, stato rilevato
; un fronte di salita del clock

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-41

10.5

Esercizi risolti

(con tecniche di interrupt)

In questo paragrafo sono presentati alcuni esercizi risolti facendo ricorso a tecniche di interrupt.

10.5.1 Macchina a Stati Finiti (con Interrupt Timer)


Nota: il testo di questo esercizio quasi identico a quello risolto in precedenza, ma si richiede
una soluzione basata sulluso delle interruzioni.
Un sistema basato sul microprocessore DMC8 possiede 32Kbytes di ROM (indirizzi
0000h..7FFFh) e 32Kbytes di RAM (indirizzi 8000h..FFFFh). Tra i suoi dispositivi di ingressouscita troviamo, tra laltro, un porto parallelo di ingresso INPUT (indirizzo 55h), il cui bit 1
collegato alla linea di ingresso UP, ed un porto parallelo di uscita OUTPUTS (indirizzo 88h), di
cui sono significative le linee W1 e W0.
Si chiede di scrivere, in
linguaggio assembly, un
programma attivato al reset
hardware
che
realizzi
lalgoritmo
della
MSF
sincrona
descritta
dal
diagramma ASM riportato in
figura. Le uscite della MSF,
W1 e W0, rappresentano i
numeri da 00 a 11.
Si supponga che il clock CK
sia fornito da un timer che
interrompe il processore
ogni 400 S.
Una possibile soluzione
Nello schema d-DcS che segue, UP collegato al porto di ingresso IA, e le uscite W1 e W0 al
porto di uscita OA. I fili non usati di IA sono stati collegati a 0. Al microcomputer affiancato
un timer che genera ogni 400 S una richiesta di interruzione su !Int: lattivazione di !IntA, da
parte del processore, disattiva, nel timer, la richiesta stessa.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-42

Nel codice che segue, il registro D utilizzato come variabile di comunicazione tra il
programma di interruzione ed il programma principale. La subroutine CK, una volta chiamata,
ritorna al programma principale solo quando D = 1: solo il programma di interruzione,
lanciato dalla richiesta del timer, pone D = 1. D azzerato, poi, dalla subroutine CK, che
provvede anche a valutare lingresso UP.
Suggerimento: provate questo programma nel d-McE, attivando la modalit [Over]. Animando
lesecuzione, osserverete che la subroutine CK viene chiamata, ma il controllo non ritorna al
programma principale se non dopo avere richiesto interrupt con il pulsante [INT]. Se, nel
frattempo, cambiate il valore di UP (porto IA, bit 1), osserverete la MSF cambiare di stato.
INPUTS
EQU 55h
OUTPUTS
EQU 88h
;---------------------------------------------------------------------------ORG 0000h
JP
START
ORG 0038h
JP
INTERRUPT
;---------------------------------------------------------------------------ORG 0100h
;
START:
LD
SP,0FFFFh
; inizializzazione dello stack pointer
LD
D, 0
; D='1' se c' stato un fronte di salita di CK
EI
; abilita gli interrupt!
;
STATO_A:
LD
A, 00h
OUT
(OUTPUTS),A ; lo stato_A ha le uscite W1 e W0 entrambe a zero
CALL CK
; dalla subroutine uscir al fronte di salita
JP
Z, STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_B:
LD
A, 01h
; se UP=1 passo nello stato_b
OUT
(OUTPUTS),A ; lo stato_b ha le uscite W0=1 e W1=0
CALL CK
JP
Z, STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_C:
LD
A, 02h
; se UP=1 passo nello stato_c
OUT
(OUTPUTS),A ; lo stato_c ha le uscite W0=0 e W1=1
CALL CK
JP
Z, STATO_B
; se UP=0 vado nello stato_b, altrimenti
;
STATO_D:
LD
A, 03h
; se UP=1 passo nello stato_d
OUT
(OUTPUTS),A ; lo stato_d ha le uscite W0=1 e W1=1
CALL CK
JP
Z, STATO_C
; se UP=0 vado nello stato_c, altrimenti
JP
STATO_D
; se UP=1 ritorno nello stato_d
;
;--------------------------------------------------------------------------------; CK
Controlla se arrivato il fronte di salita, e testa l'ingresso UP
;--------------------------------------------------------------------------------CK:
LD
A,0
Test:
CP
D
; il registro D ancora uguale a zero?
JP
Z,Test
; rimaniamo nella subroutine se cos...
; se D <> 0, invece, c' stato un fronte di salita:
LD
D,A
; ripristino D = 0
IN
A, (INPUTS) ; leggo sul porto d'ingresso
AND
02h
; maschero via tutti i bit, tranne il bit UP (bit 1)
RET
; esco dalla subroutine CK...
; con il Flag di Zero che mi dice quanto vale UP
;--------------------------------------------------------------------------------; Interrupt Routine
;--------------------------------------------------------------------------------INTERRUPT: LD
D,1
; segnala, con D=1, l'avvenuto interrupt,
EI
; ossia l'arrivo del fronte attivo del CK
RET
;---------------------------------------------------------------------------------

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-43

10.5.2 Macchina a Stati Finiti (con Interrupt richiesto dallinterfaccia di ingresso)


Nota: si tratta di una ulteriore versione del precedente esercizio.
Un sistema basato sul microprocessore DMC8 possiede 32Kbytes di ROM (indirizzi
0000h..7FFFh) e 32Kbytes di RAM (indirizzi 8000h..FFFFh). Tra i suoi dispositivi di ingressouscita troviamo, tra laltro, un porto parallelo di ingresso INPUT (indirizzo 55h), il cui bit 1
collegato alla linea di ingresso UP, ed un porto parallelo di uscita OUTPUTS (indirizzo 88h), di
cui sono significative le linee W1 e W0.
Si chiede di scrivere, in
linguaggio assembly, un
programma attivato al reset
hardware
che
realizzi
lalgoritmo
della
MSF
sincrona
descritta
dal
diagramma ASM riportato in
figura. Le uscite della MSF,
W1 e W0, rappresentano i
numeri da 00 a 11.
Il clock CK fornito
dallesterno alla circuiteria
di interrupt visibile nella
figura seguente.

Una possibile soluzione


Analizziamo il funzionamento della logica di interruzione. Il flip-flop D-Pet, allarrivo del fronte di
salita del clock CK, carica un 1 sulla sua uscita Q e 0 su !Q, che collegata alla richiesta di
interruzione !Int. Il segnale !IntA non utilizzato, in questo caso: la routine di interruzione che
si occupa di resettare la richiesta, leggendo il porto IA. Infatti, con la lettura di IA, oltre ad
acquisire il valore di UP, resettiamo anche il flip-flop tramite il !Clear collegato al segnale !rA
(generato alla lettura del porto).
Il dato letto copiato nel registro E, mentre il registro D utilizzato, anche in questo caso, come
variabile di comunicazione tra il programma di interruzione ed il programma principale, come
nel precedente esercizio.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-44

INPUTS
EQU 55h
OUTPUTS
EQU 88h
;---------------------------------------------------------------------------ORG 0000h
JP
START
ORG 0038h
JP
INTERRUPT
;---------------------------------------------------------------------------ORG 0100h
;
START:
LD
SP,0FFFFh
; inizializzazione dello stack pointer
LD
D, 0
; D='1' se c' stato un fronte di salita di CK
LD
E, 0
; in E copiamo il porto di ingresso
EI
; abilita gli interrupt!
;
STATO_A:
LD
A, 00h
OUT
(OUTPUTS),A ; lo stato_A ha le uscite W1 e W0 entrambe a zero
CALL CK
; dalla subroutine uscir al fronte di salita
JP
Z, STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_B:
LD
A, 01h
; se UP=1 passo nello stato_b
OUT
(OUTPUTS),A ; lo stato_b ha le uscite W0=1 e W1=0
CALL CK
JP
Z, STATO_A
; se UP=0 ritorno nello stato_a, altrimenti
;
STATO_C:
LD
A, 02h
; se UP=1 passo nello stato_c
OUT
(OUTPUTS),A ; lo stato_c ha le uscite W0=0 e W1=1
CALL CK
JP
Z, STATO_B
; se UP=0 vado nello stato_b, altrimenti
;
STATO_D:
LD
A, 03h
; se UP=1 passo nello stato_d
OUT
(OUTPUTS),A ; lo stato_d ha le uscite W0=1 e W1=1
CALL CK
JP
Z, STATO_C
; se UP=0 vado nello stato_c, altrimenti
JP
STATO_D
; se UP=1 ritorno nello stato_d
;
;------------------------------------------------------------------------------; CK
Controlla se arrivato il fronte di salita, e testa l'ingresso UP
;------------------------------------------------------------------------------CK:
LD
A,0
Test:
CP
D
; il registro D ancora uguale a zero?
JP
Z,Test
; rimaniamo nella subroutine se cos...
; se D <> 0, invece, c' stato un fronte di salita:
LD
D,A
; ripristino D = 0
;
LD
A,E
; in E c' quanto stato letto sul porto di ingresso
AND
02h
; maschero via tutti i bit, tranne il bit UP (bit 1)
RET
; esco dalla subroutine CK...
; con il Flag di Zero che mi dice quanto vale UP
;
;------------------------------------------------------------------------------; Interrupt Routine
;------------------------------------------------------------------------------INTERRUPT: PUSH AF
; salvo A e i flag
;
LD
D,1
; segnala, con D=1, l'avvenuto interrupt,
IN
A, (INPUTS) ; leggo il porto d'ingresso, resetto l'int. request
LD
E,A
;
POP
AF
; recupero A e i flag
EI
; ossia l'arrivo del fronte attivo del CK
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-45

Una seconda soluzione


La logica di interruzione gi stata esaminata nei commenti precedenti. In questo caso, il
programma principale non esegue nulla (in un caso pi generale, potremmo eseguire nel
programma principale altri compiti). Lalgoritmo della MSF , nella soluzione proposta, eseguito
esclusivamente dalla routine di interrupt. Questa salva nella variabile STATO, che allocata in
memoria, lo stato della MSF. Ogni volta che la routine chiamata, controlla lo stato della MSF
e, di conseguenza, passa nel prossimo stato, aggiornando le uscite corrispondenti.
Questa soluzione molto generale e consente di essere ragionevolmente adattata ad altri
problemi risolvibili in termini di MSF. La sua apparente complessit compensata dal fatto che,
in realt, il suo codice molto ripetitivo.
INPUTS
OUTPUTS

EQU
EQU

55h
88h

; DMC8 input port 'IA'


; DMC8 output port 'OA'

STATO
Code_a
Code_b
Code_c
Code_d

EQU
EQU
EQU
EQU
EQU

8000h
00h
01h
02h
03h

; "Stato" della MSF


;= 00000000b = stato
;= 00000001b = stato
;= 00000010b = stato
;= 00000011b = stato

'a'
'b'
'c'
'd'

;---------------------------------------------------------------------------ORG 0000h
JP
START
ORG 0038h
JP
INTERRUPT
;---------------------------------------------------------------------------ORG 0100h
;
START:
LD
SP,0FFFFh
; iniz. dello stack
LD
A,Code_a
LD
(STATO),A
; stato iniziale = stato 'a'
OUT
(OUTPUTS),A ; uscite a zero per lo stato 'a'
EI
; enable Interrupts
;
MAINLOOP:
NOP
; qui il programma principale
NOP
; esegue "un qualunque compito"
NOP
JP
MAINLOOP
;
;---------------------------------------------------------------------------;gestore dell'interrupt
;
INTERRUPT: PUSH AF
LD
A,(STATO)
CP
Code_a
JP
Z,STATO_A
CP
Code_b
JP
Z,STATO_B
CP
Code_c
JP
Z,STATO_C
JP
STATO_D
; per esclusione
;
;---------------------------------------------------------------------------STATO_A:
IN
A,(INPUTS)
; leggo il porto, resetto l'interrupt request
BIT
1,A
; test di 'UP'
JP
Z, EXIT
; non cambia stato se UP = '0'
;UP = '1', andiamo nello stato 'b':
LD
A,Code_b
LD
(STATO),A
LD
A,01h
; uscite dello stato 'b': W0=1 e W1=0
OUT
(OUTPUTS),A
JP
EXIT
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-46

;---------------------------------------------------------------------------STATO_B:
IN
A,(INPUTS)
; leggo il porto, resetto l'interrupt request
BIT
1,A
; test di 'UP'
JP
Z,GOstatoA
;UP = '1', andiamo nello stato 'c':
LD
A,Code_c
LD
(STATO),A
LD
A,02h
; uscite dello stato 'c': W0=0 e W1=1
OUT
(OUTPUTS),A
JP
EXIT
;UP = '0', andiamo nello stato 'a':
GOstatoA:
LD
A,Code_a
LD
(STATO),A
LD
A,00h
; uscite dello stato 'a': W0=0 e W1=0
OUT
(OUTPUTS),A
JP
EXIT
;---------------------------------------------------------------------------STATO_C:
IN
A,(INPUTS)
; leggo il porto, resetto l'interrupt request
BIT
1,A
; test di 'UP'
JP
Z,GOstatoB
;UP = '1', andiamo nello stato 'd':
LD
A,Code_d
LD
(STATO),A
LD
A,03h
; uscite dello stato '3': W0=1 e W1=1
OUT
(OUTPUTS),A
JP
EXIT
;UP = '0', andiamo nello stato 'b':
GOstatoB:
LD
A,Code_b
LD
(STATO),A
LD
A,01h
; uscite dello stato 'a': W0=1 e W1=0
OUT
(OUTPUTS),A
JP
EXIT
;---------------------------------------------------------------------------STATO_D:
IN
A,(INPUTS)
; leggo il porto, resetto l'interrupt request
BIT
1,A
; test di 'UP'
JP
NZ,EXIT
;UP = '0', andiamo nello stato 'c':
LD
A,Code_c
LD
(STATO),A
LD
A,02h
; uscite dello stato 'c': W0=0 e W1=1
OUT
(OUTPUTS),A
JP
EXIT
;---------------------------------------------------------------------------EXIT:
POP AF
EI
RET
;----------------------------------------------------------------------------

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-47

Una terza soluzione


In questo caso si esula un po da una lettura alla lettera del diagramma ASM della MSF, e il
problema risolto distinguendo, sulla base del valore dellingresso, la direzione del conteggio, e
quindi incrementando o decrementando lo stato (con un controllo sui valori estremi).
Anche qui il programma principale non esegue nulla. Lalgoritmo vero e proprio eseguito dalla
routine di interrupt. Questa soluzione trae vantaggio dal caso descritto e risulta molto semplice
e lineare: rilegge la MSF in termini di contatore non ciclico bidirezionale).
INPUT
OUTPUTS
STATE
;

EQU
EQU
EQU

55h
88h
8000h

;mantiene in RAM lo stato del porto OUTPUTS

ORG
0000h
JP
START
ORG
0038h
JP
INTERRUPT
;----------------------------------------------------------ORG
0100h
;
START:
LD
SP,0FFFFh
;inizializzazione SP
LD
A,00h
;inizializzo OUTPUTS con lo stato W1=0, W0=0
LD
(STATE),A
;e salvo il valore nella variabile di stato
OUT
(OUTPUTS), A
EI
;
MAIN:
NOP
JP
MAIN
;
;-----------------------------------------------------------INTERRUPT: PUSH AF
;ogni volta che il circuito esterno richiede un'INT,
IN
A,(INPUT)
;acquisisco i dati da INPUT
BIT
1,A
;testo il valore di UP
JP
NZ,SALITA
;UP=1 ==> passo allo stato successivo
JP
DISCESA
;UP=0 ==> passo allo stato precedente
;
SALITA:
LD
A,(STATE)
;carico in A lo stato attuale di OUTPUTS
CP
03h
;se ho raggiunto lo stato W1=1, W0=1 allora
JP
Z,EXIT
;non posso incrementare e resto nello stato attuale
INC
A
;se non sono al massimo valore, lo incremento
;
LD
(STATE),A
;salvo il nuovo stato in STATE e scrivo OUTPUTS
OUT
(OUTPUTS),A
JP
EXIT
;
DISCESA:
LD
A,(STATE)
;carico in A lo stato attuale di OUTPUTS
CP
00h
;se ho raggiunto lo stato W1=0, W0=0 allora
JP
Z,EXIT
;non posso decrementare e resto nello stato attuale
DEC
A
;se non sono al minimo valore, lo decremento
;
LD
(STATE),A
;salvo il nuovo stato in STATE e scrivo OUTPUTS
OUT
(OUTPUTS),A
;
EXIT:
POP
AF
EI
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-48

10.5.3 Contatore di oggetti


Nel nostro sistema, oltre ai normali
dispositivi di ROM e RAM, come si
osserva in figura, troviamo:
a) un porto parallelo di ingresso,
denominato
FD
(allocato
allindirizzo di I/O A0h); questo
porto utilizzato per leggere
sulla linea di ingresso F7 luscita
di un sensore ottico che troviamo
posizionato ai lati di un nastro
trasportatore;
b) due porti paralleli di uscita
denominati LH e LL (allocati agli
indirizzi di I/O A5h e A6h); i due
porti pilotano una fila di 16
lampadine poste su di un
pannello (se il caso fosse reale,
avremmo un dispositivo pi
leggibile, per esempio un display
a 7 segmenti, ma per semplicit
di soluzione immaginiamo una
rappresentazione
binaria,
espressa con una fila di
lampadine).
c) Un Timer predisposto per
attivare, ogni 500 mS, la linea di
richiesta di interruzione.
Il programma di gestione del sistema deve controllare il sensore, contando il passaggio degli
oggetti sul nastro trasportatore. Periodicamente, ogni 10 secondi, il sistema aggiorna sulle
lampadine, in binario, il numero di oggetti contati, ricominciando poi il conteggio degli oggetti
da zero. Per richiamare lattenzione delloperatore, ogni volta che il numero sulle lampadine
deve essere aggiornato, le lampadine vengono prima spente (per un secondo), e poi riaccese
con il nuovo numero.
Questa specifica complica un poco la soluzione, obbligando il programmatore alluso degli
interrupt, perch viene richiesto che il sistema valuti degli intervalli di tempo ben definiti,
durante i quali, in ogni caso, deve continuare a contare gli oggetti. Cio, non potremo usare
delle routine di ritardo per lattesa dei vari intervalli indicati nelle specifiche, a meno di non
complicare notevolmente il codice.
Quindi, separiamo i compiti tra il programma principale, che seguir il passaggio degli oggetti, e
la routine di interrupt che, lanciata dal timer ogni mezzo secondo, si preoccuper della gestione
della visualizzazione.
Per quanto riguarda il programma principale, ogni volta che un oggetto passa davanti al
sensore, deve incrementarne il conteggio. Lombra delloggetto azzera luscita del sensore. Per
incrementare il conteggio, si deve aspettare che loggetto sia passato oltre, e che quindi luscita
del sensore sia tornata a uno: in altre parole, il programma principale dovr attendere e contare
i fronti di salita rilevati sulla linea F7. Il testo dice anche che il numero di oggetti al secondo ,
al massimo, 50: questo ci dice che ogni 10 secondi potremmo avere contato 500 oggetti,
obbligandoci quindi ad utilizzare una variabile da 16 bit.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-49

Una possibile soluzione


Nel programma principale, per prima cosa il programma inizializza lo Stack Pointer. Poi
azzera i porti di uscita LH e LL (anche se non richiesto dalle specifiche dellesercizio,
comunque ragionevole, al reset, predisporre tutte spente le lampadine). Il programma inizializza
il registro a 16 bit BC, che utilizziamo per contare degli oggetti che passano davanti al sensore,
e il contatore del tempo (il registro D). Laggiornamento delle uscite avviene ogni 10 secondi: il
programma utilizza il Timer (500 mS) per misurare questo tempo: 20 x 500mS = 10 secondi.
Abilitiamo poi il meccanismo delle interruzioni con listruzione EI: da questo momento, ogni volta
che il Timer attiver la linea di richiesta di interruzione INT, il processore salter alla routine di
gestione degli interrupt. I due cicli di attesa servono a valutare il passaggio di un oggetto
davanti al sensore, aspettando che esca dal campo visivo (verifichiamo il fronte di salita):
incrementiamo quindi il conteggio e ritorniamo in attesa del prossimo oggetto (INC BC).
;------------------------------------------------------------------------LH
EQU
0A5h
LL
EQU
0A6h
FD
EQU
0A0h
;
;------------------------------------------------------------------------ORG
0000h
JP
START
ORG
0038h
JP
INTERRUPT
;
;------------------------------------------------------------------------; Programma principale
ORG
0100h
;
START:
LD
SP,0FFF0h
;iniz. stack pointer
LD
A,00h
;iniz. I porti di uscita
OUT
(LL),A
OUT
(LH),A
;
LD
BC,0000h
;iniz. le variabili
LD
D,20
EI
;abilita gli interrupt
;
LOOP:
IN
A,(FD)
;ciclo principale
BIT
7,A
JP
NZ,LOOP
;
LOOP1:
IN
A,(FD)
BIT
7,A
JP
Z,LOOP1
;...di attesa di un fronte di salita
;
INC
BC
;incrementa il conteggio degli oggetti
JP
LOOP
;-------------------------------------------------------------------------

La routine di gestione dellinterruzione si occupa invece della parte di visualizzazione: viene


lanciato ogni 500 mS, e ogni volta decrementiamo il contatempo D. Al raggiungimento della
ventesima interruzione, saranno trascorsi 10 secondi e salteremo alletichetta DISPLAY. Se,
invece, manca ancora un secondo allo scadere del tempo (D = 2), andremo a spegnere le
lampadine, saltando a SWOFF. Prima di uscire dalla routine di interrupt, re-inizializziamo i
contatori degli oggetti e del tempo.
In ultimo, un commento sulla possibilit di utilizzare routine di ritardo per lattesa di un secondo
tra lo spegnimento delle lampadine ed il display del valore. Questa tecnica sarebbe ben poco
pratica, perch una routine di ritardo impegnerebbe totalmente il processore nellattesa del
termine dellintervallo di tempo richiesto. Saremmo costretti a controllare il sensore nel
frattempo, dando luogo ad un programma con diverse criticit, sia sul piano della corretta
temporizzazione, che dal punto di vista della chiarezza e leggibilit. La soluzione su base
interrupt, con luso di un timer, molto pi funzionale.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-50

;------------------------------------------------------------------------INTERRUPT: PUSH AF
;
DEC
D
JP
Z,DISPLAY
;10 seconds elapsed: display number
LD
A,D
CP
2
JP
Z,SWOFF
; 9 seconds: switch off the lamps
;
EXIT:
POP
AF
EI
RET
;
;---------------------------------------------SWOFF:
LD
A,00h
; switch off the lamps
OUT
(LL),A
OUT
(LH),A
JP
EXIT
;---------------------------------------------DISPLAY:
LD
A,B
; display BC count
OUT
(LH),A
LD
A,C
OUT
(LL),A
;
LD
BC,0000h
; re-init. BC
LD
D,20
; and time count
JP
EXIT

10.5.4 Contatore di oggetti di due tipi


Il sistema hardware in figura molto simile a quello del precedente testo. In particolare,
cambiano gli indirizzi e i nomi simbolici dei porti, e sul porto di ingresso troviamo collegati due
sensori invece che uno.
Il Timer identico: ogni 500mS
interromper il processore.
Le linee F0 e F7 del porto parallelo
di ingresso CNT sono collegate a
due sensori ottici, posizionati uno
sopra laltro, a lato di un nastro
trasportatore. Grazie alla diversa
posizione in altezza dei due sensori,
posti sulla medesima verticale, il
sistema in grado di distinguere gli
oggetti bassi da quelli alti che
transitano lungo il nastro.
Il sistema conta separatamente gli
oggetti bassi e gli oggetti alti che
passano davanti ai sensori; ogni 30
secondi aggiorna sulle lampadine,
in binario, il numero di oggetti
contati,
ricominciando
poi
il
conteggio degli oggetti da zero
(OBL = conto oggetti bassi, OBH =
conto oggetti alti). Dalle specifiche,
sappiamo che passano al massimo
4 oggetti al secondo: sufficente
un registro ad 8 bit per contare al
massimo 120 oggetti ogni 30
secondi.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-51

Anche qui viene richiesto di spegnere le lampadine (per mezzo secondo), prima di visualizzare
il nuovo numero; nellintervallo di tempo in cui le lampadine sono spente, il sistema deve
continuare a contare gli oggetti.

Una possibile soluzione


Potremmo seguire lo schema di risoluzione del precedente esercizio, ma ne approfittiamo per
individuare un algoritmo un poco diverso (ricordiamoci inoltre che il programma principale qui
controlla contemporaneamente due sensori). Inoltre, in questa soluzione sono stati commentati
sommariamente quegli elementi del codice gi discussi nellesercizio precedente.
Prima di tutto, definiamo i simboli usati nel codice: i nomi dei porti e di una variabile in
memoria (utilizzata per contare il tempo):
CNT
OBH
OBL
PERIODO

EQU
EQU
EQU
EQU

00h
05h
06h
8000h

;i nomi dei porti

;una variabile intera da 8 bit (1 byte)

Il programma, al RESET, prima di iniziare il compito richiesto, inizializza le variabili. Solo dopo
avere inizializzato ogni cosa, sono abilitati gli interrupt:

START:

ORG
JP
ORG

0000h
0100h
0100h

;il programma parte al RESET

LD
LD
LD
LD
LD
LD
OUT
OUT
EI

SP,0FFFFh
A,60
(PERIODO),A
B,0
C,0
A,0
(OBH),A
(OBL),A

;inizializzo lo Stack Pointer,


;e la variabile di conteggio del tempo
;azzero B e C, rispettivamente usati per
;il conto degli oggetti bassi e alti
;spengo preventivamente tutte le lampade
;abilito gli interrupt

Ora il programma entra nel ciclo principale, un ciclo infinito dal quale non esce pi, e nel quale
si preoccupa soltanto di seguire il passaggio degli oggetti, controllando in prima battuta soltanto
il sensore basso. Nel momento in cui un oggetto oscura il sensore basso, controlliamo se
oscura anche quello alto:
CHECK:

IN
BIT
JP

A,(CNT)
0,A
Z,CHECK

;aspetto che un generico pezzo entri nel campo


;visivo, controllando il sensore basso

BIT
JP

7,A
NZ,ALTO

;guardo se il pezzo alto,


;salto se lo ...

A seconda del tipo di pezzo, aspetto che sia uscito dal campo visivo, e quindi incremento il
rispettivo conteggio:
BASSO:

ALTO:

IN
BIT
JP
INC
JP

A,(CNT)
0,A
NZ,BASSO
B
CHECK

;guardo se il pezzo basso passato

IN
BIT
JP
INC
JP

A,(CNT)
7,A
NZ,ALTO
C
CHECK

;guardo se il pezzo alto passato

;se si, incremento il contatore dei pezzi


;bassi e torno in attesa del prossimo pezzo

;se si, incremento il contatore dei pezzi


;alti e torno in attesa del prossimo pezzo

La routine di gestione dellinterruzione si occupa anche in questo caso della parte di


visualizzazione. Viene lanciata dal timer ogni mezzo secondo, e ogni volta decrementa il
conteggio del tempo di uno. Quando il conteggio raggiunge 1, sono spente le lampadine.
Quando si azzera, il valore attuale del conteggio visualizzato, e quindi ri-azzerato:
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-52

INTERRUPT:

ORG
PUSH
LD
DEC
LD

OO38h
AF
A,(PERIODO)
A
(PERIODO),A

CP
JP
CP
JP
POP
EI
RET

A,1
Z,SPENGO
A,0
Z,DISPLAY
AF

LD
OUT
OUT
POP
EI
RET

A,00
(OBH),A
(OBL),A
AF

;vale 1, tempo di spegnere le lampadine

LD
OUT
LD
OUT
LD
LD
LD
POP
EI
RET

A,C
(OBH),A
A,B
(OBL),A
BC,0000h
A,60
(PERIODO),A
AF

;carico in a il numero di pezzi alti


;e li visualizzo...
;carico in a il numero di pezzi bassi
;e li visualizzo...
;e quindi ri-azzero il conteggio

;salvo A ed i Flags
;carico in A il conto del tempo
;lo decremento
;e ri-aggiorno la variabile in memoria

;
SPENGO:

;
DISPLAY:

;se vale 1, spengo le lampadine


;se vale 0, visualizzo il conteggio
;altrimenti esco, ripristinando A e i Flag
;e labilitazione degli interrupt

;e di uscire...

;re-inizializzo il conto del tempo


;ed esco...

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-53

10.5.5 Montacarichi
Un
sistema
basato
sul
microprocessore d-Mc8 controlla un
montacarichi ad uso industriale. Il
montacarichi
(semplificato
per
ragioni didattiche) pu essere
descritto come nel seguito.
Prevede 5 piani (Piano terra, piano
1, piano 2, piano 3, piano 4).
controllato dalloperatore mediante
un solo pannello con 5 pulsanti per
la scelta del piano di destinazione.
provvisto di un codificatore che
indica la posizione verticale della
cabina.
Come riportato nella figura qui a lato,
la pulsantiera connessa al porto di
ingresso COMMAND (indirizzo 20h).
I pulsanti T, 1, 2, 3, e 4 sono
collegati rispettivamente ai bit 0, 1,
2, 3 e 4 del porto (se premuti,
generano un livello alto).
Il porto di ingresso FLOOR (indirizzo
21h) legge luscita del codificatore di
posizione. Questo consente di
sapere dove si trova lascensore:
genera un codice a quattro bit
(P3P2P1P0), secondo la tabella del
Codice di Richiesta qui riportata.
ll porto di uscita MOTOR (indirizzo 22h) consente di attivare il
motore di elevazione: il dispositivo di potenza che controlla il
motore riceve due bit di comando: ON (bit 0: se a 1, accende il
motore), e UP (bit 1: se a 1 fa girare il motore in salita, se 0 in
discesa).
Un Timer attiva ogni 50 mS la linea di richiesta di
interrupt INT del processore: allaccettazione della
interruzione, la risposta del processore INTA disattiva
in
modo
automatico
la
linea
INT .
Il sistema inoltre provvisto di 32 Kbytes di ROM e 32
Kbytes di RAM.

Si chiede di scrivere, in linguaggio assembly, il


programma di controllo del montacarichi, seguendo le
specifiche qui riportate.

Piano
4
3
2
1
T

Codice

0000.1000
0000.0110
0000.0100
0000.0010
0000.0000

Codice di richiesta

Posizione cabina
4 piano (alla porta)
Tra il 3 e il 4 piano
3 piano (alla porta)
Tra il 2 e il 3 piano
2 piano (alla porta)
Tra il 1 e il 2 piano
1 piano (alla porta)
tra Terra e il 1 piano
Terra (alla porta)

P3P2P1P0

1
0
0
0
0
0
0
0
0

0
1
1
1
1
0
0
0
0

0
1
1
0
0
1
1
0
0

0
1
0
1
0
1
0
1
0

Il sistema, nel programma di interruzione, legge la


Codice di posizione
pulsantiera a disposizione delloperatore. Per evitare il
fenomeno dei rimbalzi meccanici dei pulsanti, lo stato
di questi deve essere convalidato da due letture consecutive, distanti tra loro 50 mS. La
routine si preoccupa anche di codificare la richiesta secondo la tabella riportata qui a lato, e di
rendere disponibile questo codice al programma principale nella variabile REQUEST. Se
nessun tasto risulta premuto, la variabile REQUEST non deve essere aggiornata.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-54

Il programma principale, invece, ha il compito di gestire lattivazione e la direzione del


motore, attuando la richiesta delloperatore codificata dal programma di interruzione nella
variabile REQUEST, portando il montacarichi al piano voluto. Il codificatore di posizione
fornisce in ogni momento al sistema la posizione verticale della cabina secondo i codici
riportati nella seconda tabella (Codice di Posizione).
Note:
- Nellindividuare il pulsante premuto dalloperatore, si deve tenere conto della possibilit che
questi possa premere erroneamente pi pulsanti nello stesso momento. Deve essere
effettuata una codifica a priorit, prendendo in considerazione, tra i pulsanti premuti,
soltanto quello relativo al piano pi alto.
- Il codice di richiesta, riportati nella prima tabella, sono stati scelti in modo da poter essere
confrontati agevolmente con i codici forniti dal codificatore di posizione.
- Il programma deve essere attivato automaticamente al RESET hardware del sistema.

Una possibile soluzione


;-------------------------------------------------------------------;
COMMAND
EQU
20h
;porto par. di ingresso (COMMAND)
FLOOR
EQU
21h
;porto par. di ingresso (FLOOR)
MOTOR
EQU
22h
;porto par. di uscita (MOTOR)
;
REQUEST
EQU
8000h
;variabile in memoria (REQUEST)
PREVIOUS
EQU
8001h
;variabile in memoria (PREVIOUS)
;------------------------------------------------------------------ORG
0000h
JP
0100h
;------------------------------------------------------------------; Interrupt Routine (Gestione del Timer da 50 mS)
ORG
0038h
;
INTERPT:
PUSH AF
;salva i registri utilizzati
PUSH BC
;
LD
A,(PREVIOUS) ;'stato precedente' dei pulsanti
LD
B,A
;
IN
A,(COMMAND) ;leggi i pulsanti di comando
AND
1Fh
;maschera via i bit non utilizzati
LD
(PREVIOUS),A ;salva il 'prossimo stato precedente'
CP
B
;confrontali con lo 'stato precedente'
JP
NZ,ESCI
;esci se diversi (pu essere un rimbalzo)
;
;-- la lettura stata confermata uguale alla precedente ----------OR
A
;controlla che ci sia almeno un
JP
Z,ESCI
;pulsante premuto, esci se no
;
;-- almeno un tasto premuto (e confermato) ----------------------RLA
;sposta U4..U0 a sinistra, sui bit
RLA
;
b7..b3
RLA
;ai fini del prox test
;
;-- loop di controllo, a priorit, del tasto premuto, e produzione
;-- del codice di richiesta al programma principale. Non ci sono
;-- problemi di sincronizzazione tra i due processi, perch la
;-- variabile "REQUEST" viene aggiornata in un solo passo elementare
;-- di scrittura (l'operazione eseguita "atomica" = "indivisibile"

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-55

;
GENCODE:

;
SETCODE:
;
ESCI:

LD
RLA
JP
DEC
DEC
JP

C,00001000b

;codice di richiesta: piano 4


;testa i pulsanti, priorit da sinistra
;se premuto, in C abbiamo il codice
;prepara il prossimo codice del piano
;..che usiamo anche come contatore loop
;Nota: il caso "nessun tasto" escluso

C,SETCODE
C
C
GENCODE

LD
LD

A,C
(REQUEST),A

;passa il codice di richiesta al main

POP
POP
EI
RET

BC
AF

;recupera il contenuto prec. dei registri

;------------------------------------------------------------------; Main
ORG
0100H
START:
LD
SP,0FFFFh
;iniz. STACK POINTER
;
LD
A,0FFh
;codice "impossibile", affinch lo
LD
(PREVIOUS),A ;'stato precedente', sia diverso...
;
IN
A,(FLOOR)
;leggi la posizione del montacarichi
AND
0Eh
;richiesta: il piano in cui sono, o
LD
(REQUEST),A ;porta l'ascensore al piano di sotto
;se al''accensione tra due piani
EI
;abilita gli interrupt
;
MAINLOOP:
LD
A,(REQUEST) ;leggo la richiesta corrente
LD
B,A
;e la metto in 'B'
;
IN
A,(FLOOR)
;leggo la posizione del montacarichi
AND
0Fh
SUB
B
;confronto con la richiesta corrente
;
JP
Z,STOP
;salta se coincide, ferma il motore
JP
C,GOUP
;salta se occorre salire
;
GODOWN:
LD
A,00000001b ;discesa
OUT
(MOTOR),A
;in 'A' il codice di controllo del motore
JP
MAINLOOP
;
GOUP:
LD
A,00000011b ;salita
OUT
(MOTOR),A
JP
MAINLOOP
;
STOP:
LD
A,00000000b ;fermo
OUT
(MOTOR),A
JP
MAINLOOP
;-------------------------------------------------------------------

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-56

10.5.6 Contatore di oggetti (con selezione in base al peso)


Si consideri disponibile un sistema di controllo industriale, basato sul microprocessore d-Mc8,
configurato con 32 Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in
figura. Il porto parallelo di ingresso TRACK (allindirizzo 00h) permette di leggere le uscite di
due sensori.
Il primo, un sensore di
presenza, posizionato sopra
un nastro trasportatore (ed
collegato al bit F7 del porto).
Il secondo, posizionato nello
stesso punto del nastro, un
sensore di peso, che riporta il
peso delloggetto che sta
transitando (in una scala
convenzionale tra 0 e 15,
numero codificato in binario, bit
F3F0 del porto).
I due porti paralleli di uscita
HIGH e LOW (indirizzi 05h e
06h) pilotano rispettivamente
due file indipendenti di 8
lampadine, poste su di un
pannello.
Un dispositivo hardware di
temporizzazione (Timer) attiva
ogni 20 mS la linea di richiesta
di
interrupt
INT
del
processore. La risposta del
processore sulluscita INTA ,
allaccettazione
della
interruzione, disattiva in modo
automatico la linea INT .

Si chiede di scrivere, in linguaggio assembly, il programma di gestione del sistema, in base alle
specifiche qui riportate.
Il sistema in grado di selezionare, sulla base del loro peso, gli oggetti che transitano.
Il sistema, nel programma principale, controlla continuamente i due sensori. Ogni volta che il
sistema riscontra la presenza di un oggetto, a seconda che il suo peso superi o meno il valore
8, incrementa il conto degli oggetti pesanti, o di quelli leggeri.
Mediante il programma di interruzione, ogni 10 secondi il sistema aggiorna sulle lampadine, in
binario, il numero di oggetti contati in tale intervallo di tempo. Il numero degli oggetti leggeri
riportato sul porto LOW, quello degli oggetti pesanti sul porto HIGH.
Per richiamare loperatore, se gli oggetti pesanti sono pi di 30 nellintervallo considerato, le
lampadine sono attivate lampeggianti (accese per 400 mS, spente per 400 mS).
Note e suggerimenti:

o
o
o
o

Conviene contare il tempo, scandito dal timer, in sotto-intervalli di 400 mS:


(20 mS x j = 400 mS; 400 mS x k = 10 S).
Si suppone che il numero totale di oggetti che transita in 10 secondi sia inferiore a 255.
Un oggetto si considera presente quando viene rivelato un fronte di salita del segnale
uscente dal sensore di presenza.
Il programma deve essere eseguito automaticamente al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-57

Una possibile soluzione


TRACK
HIGH
LOW
;
PREC
LEG
PES
ONOFF
;

EQU
EQU
EQU

00h
05h
06h

; porti di ingresso/uscita

EQU
EQU
EQU
EQU

8000h
8001h
8002h
8003h

; variabili

ORG
JP

0000h
0100h

; salto, al reset

;
;-----------------------------------------------------------------------; Routine di gestione delle interruzioni
ORG
0038h
;
INT:
PUSH AF
;
DEC
D
; conto 400 mS (20 mS x 20)
JP
NZ, ESCI
LD
D, 20
; ri-inizializzo il contatore
DEC
E
; conto 10 S (400 mS x 25)
JP
Z, CONTR
LD
A, (ONOFF)
; controllo il flag ONOFF
CP
0Fh
; se ONOFF=0Fh vuol dire che sto
JP
Z, LAMP
; lampeggiando e vado a LAMP
JP
ESCI
CONTR:

LD
LD
LD
LD
LD
LD

E, 25
A, L
(LEG), A
A, H
(PES), A
HL, 00h

; ri-inizializzo il contatore
; salvo in memoria il numero di
; oggetti contati, passati 10 S

CP
JP

00011110b
NC, LAMP

; controllo se i pesanti sono pi


; di 30 e se cos vado a LAMP

LD
OUT
LD
OUT

A, (PES)
(HIGH), A
A, (LEG)
(LOW), A

; altrimenti faccio uscire i valori


; sulle uscite

LD
LD
JP

A, 00h
(ONOFF),A
ESCI

; salvo su ONOFF un codice diverso da 0Fh

LD
LD

A, 0Fh
(ONOFF),A

LD
RR
LD
JP

A, E
E
E, A
C, ACCENDI

LD
OUT
OUT
JP

A, 00h
(HIGH), A
(LOW), A
ESCI

LD
OUT
LD
OUT

A, (PES)
(HIGH), A
A, (LEG)
(LOW), A

; e ri-inizializzo contatori

;
LAMP:

; salvo su ONOFF il codice di lampeggio

;
SPEGNI:

;
ACCENDI:

; divido E per 2, se dispari avr


; resto e accender lampade, se
; pari non avr resto e le spegner

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-58

ESCI:

POP
EI
RET

AF

;
;-----------------------------------------------------------------------; Programma principale che controlla lo stato dei sensori
;
ORG
0100h
INIT:
LD
SP, 0FFFFh
LD
A, 00h
OUT
(HIGH), A
OUT
(LOW), A
LD
(PREC), A
LD
(ONOFF),A
LD
BC, 00h
LD
HL, 00h
LD
D, 20
LD
E, 25
EI
;
MAIN:
IN
A, (TRACK)
; leggo lo stato attuale...
LD
B, A
; ... e lo salvo su registro
LD
A, (PREC)
; leggo lo stato precedente...
CPL
; ...lo nego...
AND
B
; ...e faccio l'AND tra questo
LD
C, A
; e il valore attuale e salvo
LD
A, B
LD
(PREC), A
; salvo il valore attuale
BIT
7, C
; controllo che sia avvenuto
JP
Z, MAIN
; fronte di salita(unico "1")
;
AND
00001111b
; valore attuale in A: solo i bit del peso
CP
8
; confronto il peso
JP
C, INCLEG
; salta se pesano da 0 a 7 (leggeri),
INC
H
; pesano da 8 a 15 (pesanti)
JP
MAIN
INCLEG:
INC
L
JP
MAIN
;
;Ricordiamo qui come variano i flag a seguito di una SUB, SBC oppure CP,
;applicando la tabella nel caso di confronto con una costante (qui: 8).

Se
A>8
A=8
A<8

Carry
0
0
1

Zero
0
1
0

Sign
0
0
1

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-59

10.5.7 Interfaccia a pulsanti per video gioco


Si consideri disponibile un piccolo
sistema di controllo, basato sul
microprocessore
d-Mc8,
configurato con 32 Kbytes di ROM,
32 Kbytes di RAM, e i dispositivi di
I/O rappresentati in figura.
Il porto parallelo di ingresso USER
(indirizzo 12h) permette di leggere,
tramite le linee U3 U0, i quattro
pulsanti dellinterfaccia utente di un
video gioco.
Il porto parallelo di uscita SEROUT
(indirizzo 16h) collega il nostro
sistema con lunit di gioco,
attraverso
la
linea
seriale
asincrona SER (collegata sul bit 0).
Un
dispositivo
hardware
di
temporizzazione (Timer) attiva
ogni 2 mS la linea di richiesta di
interrupt INT del processore. La
risposta del processore sulluscita
INTA ,
allaccettazione
della
interruzione, disattiva in modo
automatico la linea INT .
Si chiede di scrivere, in linguaggio assembly, il programma di gestione dellinterfaccia di gioco,
rispettando le specifiche riportate qui di seguito.
Ai fini del progetto, il programma principale non esegue operazioni significative per la nostra
interfaccia, salvo la necessaria inizializzazione del sistema al RESET hardware. Subito dopo,
il programma principale entra in un ciclo infinito nel quale non fa nulla, delegando il controllo
del sistema al programma di interruzione.
Il programma di interruzione si occupa di eseguire la lettura dei pulsanti ed effettuare un
controllo antirimbalzo sullo stato degli stessi. Ogni volta che lo stato dei pulsanti cambia,
questo viene inviato in formato seriale, tramite la linea SER, alla unit di gioco.
Pi in dettaglio, i pulsanti sono campionati con un periodo di 12 mS, e il controllo antirimbalzo
consiste nel verificare che la configurazione letta sia identica a quella letta 12 mS prima.
Questo controllo serve ad evitare che i rimbalzi meccanici dei contatti inducano in errore il
sistema.
La lettura, cos convalidata, viene comparata con lo stato dei pulsanti convalidato in precedenza
e, se diverso, la nuova configurazione viene salvata per essere inviata sulla linea SER.
Il nuovo stato dei pulsanti viene serializzato bit a bit sulla linea SER del porto parallelo
SEROUT. Il protocollo di trasmissione seriale, asincrono, prevede la trasmissione di un bit
ogni 2 mS. Il pacchetto di trasmissione composto (vedi figura) da un bit di start a 1, dai 4
bit del dato (lo stato del pulsante 3 trasmesso per primo), e da un bit di stop a 0.
Note:

Il programma principale deve essere eseguito automaticamente al RESET del sistema.


La serializzazione dei bit viene temporizzata dal programma di interruzione senza
limpiego di routine di ritardo.
Occorre prestare attenzione al fatto che la trasmissione del pacchetto (6 bit) dura
complessivamente proprio 12 mS, e che le operazioni di controllo dei pulsanti e quelle
della trasmissione dei dati non devono escludersi a vicenda, ma svolte in parallelo dove
si rivelasse necessario.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-60

Una possibile soluzione

(Timer = 20000 clock cycles)


;------------------------------------------------------------------USER
EQU
12H
;porti di ingresso/uscita
SEROUT
EQU
16H
TIME
EQU
8000H
;conteggio del tempo
;'B' = valore precedente letto sul porto USER
;'D' = valore confermato precedente
;'E' = usato per la trasmissione seriale
;------------------------------------------------------------------ORG
0000H
JP
START
ORG
0038h
JP
INTERRUPT
;------------------------------------------------------------------; Main
ORG
0100H
START:
LD
SP,0FFFFH
;iniz. stack pointer
;
LD
A,6
LD
(TIME),A
;6 = (12 mS / 2 mS di timer tick)
;iniz. registri
LD
B,00H
;'B' = valore precedente letto sul porto USER
LD
D,00H
;'D' = valore confermato precedente
LD
E,00H
;'E' = usato per la trasmissione seriale
;
EI
;abilita gli interrupt
LOOP:

NOP
JP

;ciclo idle
LOOP

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-61

; -------------------- programma di interrupt ------------------------; ad ogni attivazione dell'INT il registro 'E' viene mandato in uscita,
; e poi scalato a destra per predisporre sul bit 0 l'uscita successiva;
; Inizialmente, in 'E': bit 0
= start bit
;
bit 1,2,3,4 = dato (nell'ordine: U3, U2, U1, U0)
;
bit 5, ecc. = stop bit (e idle bits)
;
INTERRUPT: LD
A,E
;serializza il prossimo bit
AND
00000001b
OUT
(SEROUT),A
SRL
E
;scala i bit per la volta dopo
;
LD
A,(TIME)
;conta il tempo (12 mS)
DEC
A
LD
(TIME),A
JP
NZ,END
;JUMP ed esci se < 12mS
;
LD
A,6
;re-iniz. contatore tempo
LD
(TIME),A
;
IN
A,(USER)
;lettura pulsanti
AND
00001111b
LD
C,A
;in C il valore attuale letto
XOR
B
;confronto con il valore precedente (in 'B').
;... testato dal JP pi sotto
LD
B,C
;salva il valore attuale come precedente
;per il prossimo controllo tra 12 mS
JP
NZ,END
;se v. attuale diverso dal precedente,
;esci (ignorando il nuovo valore letto)
;
; si prosegue qui se il valore attuale = precedente, e quindi
; stato "confermato". Il nuovo valore confermato deve essere ora
; confrontato con il precedente valore confermato, per decidere
; se inviare o meno in uscita il nuovo stato dei pulsanti
;
LD
A,C
;il valore attuale confermato (in 'C')
XOR
D
; confrontato con il precedente (in 'D')
LD
D,C
;salva il valore attuale confermato come
;"precedente" per il prox controllo tra 12 mS
CALL NZ,TRASM
;se vi sono variazioni, trasmetto il nuovo stato.
;
END:
EI
;uscita dall'interrupt
RET
;
;------------------------------------------------------------------------------; Impostazione del contenuto del "registro di trasmissione"
; Devo invertire l'ordine dei bit, in modo da presentare sul bit 0 del
; porto per primo il bit U3 (e poi U2, U1, U0). Un bit alla volta, per
; 4 bit in totale, scalo l'attuale dato in 'C' verso destra e, tramite
; il Carry, lo reinserisco da destra in 'E'. Infine, inserisco "in testa"
; ad 'E' il bit di start
;
TRASM:
LD
A,4
;conta i 4 bit da inserire in 'E'
INS:
SRL
C
;fa uscire i bit dei pulsanti da 'C', da dx
RL
E
;e li reinserisce in 'E' verso sinistra
DEC
A
JP
NZ,INS
;'loop' 4 volte
;
SLA
E
;scala a sinistra per fare spazio per
SET
0,E
;il bit di start, che impongo a '1'
RET
;-----------------------------------------------------------------

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-62

10.5.8 Controllo della velocit di otto ruote tachimetriche


Si consideri disponibile un
sistema di controllo industriale,
basato sul microprocessore dMc8, configurato con 32
Kbytes di ROM, 32 Kbytes di
RAM, e i dispositivi di I/O
rappresentati in figura.
Il porto parallelo di ingresso
WHEELS
(indirizzo
00h)
permette di leggere, tramite le
linee W7..W0, le uscite di otto
ruote tachimetriche.
Ogni ruota tachimetrica
costituita da un disco forato,
solidale con la rotazione di un
asse meccanico, e da un
sensore ottico.
Il sensore ottico in grado di
vedere il passaggio di 32 fori,
posizionati in modo regolare
lungo il bordo del disco.
Quando il disco ruota, il
sensore genera unalternanza
di impulsi: 32 impulsi indicano,
ovviamente, che il disco ha
compiuto
una
rotazione
completa. Contando il numero
di impulsi in un secondo, si
ricava la velocit di rotazione.
Il porto parallelo di ingresso VELREF (indirizzo 01h) permette al sistema di leggere sugli otto bit
R7..R0 un valore numerico binario (sar usato dal sistema come velocit di riferimento). Si
faccia attenzione che anche la velocit di riferimento viene impostata in termini di impulsi al
secondo. Il porto parallelo di uscita ERROR (indirizzo 02h) collega il nostro sistema con il resto
dellimpianto industriale.
Un dispositivo hardware di temporizzazione (Timer) attiva ogni 50 mS la linea di richiesta di
interrupt INT del processore. La risposta del processore sulluscita INTA , allaccettazione della
interruzione, disattiva in modo automatico la linea INT .
Il sistema, nel programma principale, controlla continuamente, in parallelo, i sensori delle otto
ruote tachimetriche. Ogni volta che uno dei sensori presenta un fronte di salita, incrementa il
corrispondente conteggio degli impulsi.
ll programma di interruzione si occupa di valutare i valori di velocit delle ruote, e di produrre i
risultati. Ogni secondo riporta su ciascuna delle uscite un 1 se la velocit della ruota
corrispondente pi alta di quella di riferimento, oppure 0 se pi bassa. Le uscite E7..E0
corrispondono, nellordine, alle ruote tachimetriche collegate alle linee W7..W0.
Si chiede di scrivere, in linguaggio assembly, il programma di gestione del sistema, rispettando
le specifiche descritte.
Note:
Si supponga che la velocit di rotazione massima delle ruote sia di circa 200 impulsi al secondo.
Il programma deve essere eseguito automaticamente al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-63

Una possibile soluzione


;----------------------------------------------------------------------------------WHEELS
EQU
00h
;porti di ingresso/uscita
VELREF
EQU
01h
ERROR
EQU
02h
;
TIME
EQU
8000h
;variabile che tiene conto del tempo trascorso
VEL_0
EQU
8001h
;indirizzo del primo elemento dell'array di 8
;byte che serve per contare il numero di fori
;rilevati dai sensori per ogni ruota
ORG
0000h
JP
0100h
;----------------------------------------------------------------------------------; Routine di gestione delle interruzioni
;
ORG
0038h
;
INTERRUPT: PUSH AF
;salva nello stack tutti i registri utilizzati
PUSH BC
;nel programma principale
PUSH DE
PUSH HL
;
LD A, (TIME)
;controlla se passato un secondo
DEC A
LD (TIME), A
JP NZ, FINE_INT
;se non passato un secondo non aggiorna
;
AGGIORNA:
IN A, (VELREF)
LD B, A
;salva in "B" il contenuto del porto
;
LD E, 00h
;"E" viene usato come 'registro di stato'
LD C, 8
;"C" un contatore
LD HL, VEL_0
;"HL" contiene l'indir. del primo elemento dell'array
;
LOOP:
LD A, (HL)
SUB B
;se A < B c' una richiesta di carry (carry flag = 1)
RR E
;che viene salvato nel 'registro di stato' "E"
LD (HL), 00h
;azzero il contatore dei fori per la ruota corrente
INC HL
;"HL" punta all'elemento successivo del vettore
DEC C
JP NZ, LOOP
;
OUTPUT:
LD A, E
;generiamo l'uscita...
CPL
;Per ogni singola ruota, se la velocit maggiore di
;quella di riferimento, facendo la sottrazione non c'
OUT (ERROR), A
;carry: il testo dice che il bit deve essere a "1"
;
RE_INIT:
LD A, 20
;inizializzo nuovamente il contatore del tempo
LD (TIME), A
;
FINE_INT:
POP HL
POP DE
POP BC
POP AF
;
EI
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-64

;-----------------------------------------------------------------------; Programma principale che controlla lo stato dei sensori


;
ORG
0100h
INIT:

LD A, 20
LD (TIME), A

;inizializzo il contatore del tempo

INIT_LOOP:

LD HL, VEL_0
LD C, 8
LD A, 00h
LD (HL), A
INC HL
DEC C
JP NZ, INIT_LOOP

;inizializzo a "00h" tutte le locazioni di memoria che


;contengono il numero di fori contati per ogni ruota

;
LD B, A
OUT (ERROR), A
LD SP, 0FFFFh
EI

;azzero il reg. "B" che contiene lo stato del porto


;"WHEELS" al 'campionamento' precedente
;inizializzo lo stack pointer
;abilito gli interrupt

;
;Ciclo di controllo dei sensori del porto "WHEELS"
;
START:
IN A, (WHEELS)
LD C, A
;metto in "C" lo stato attuale dei sensori
LD A, B
;prendo da "B" ho lo stato precedente dei sensori
CPL
;individuo i fronti di salita dei sensori facendo il
AND C
;complemento dello stato prec. e l'AND con lo stato
;attuale (se c' un fronte di salita -> "1")
LD B, C
;salvo lo stato attuale come 'precedente'
;per il prossimo controllo
JP Z, START
;se non ho fronti di salita, chiudi il loop
;
FORO:
LD HL, VEL_0
LD C, 8
;
LOOP_FORO: RRA
;test del bit relativo ad un sensore
JP NC, SALTA_INC
;se carry non a "1" significa che il sensore
;non ha rilevato un fronte di salita
INC (HL)
;incrementa il contatore, nell'ARRAY
SALTA_INC: INC HL
;"HL" punta alla locazione successiva
DEC C
JP NZ, LOOP_FORO
JP START

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-65

10.5.9 Telecomando per antifurto


Si consideri disponibile il sistema di controllo di un antifurto, basato sul microprocessore d-Mc8,
configurato con 32 Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in
figura. Il porto parallelo di ingresso USER (indirizzo 38h) permette di leggere, tramite le linee
P7P0, gli otto pulsanti (numerati da 0 a 7) a disposizione dell'utente.

Il porto parallelo di uscita TXOUT (indirizzo 40h) collega il nostro sistema con lunit di gestione
dell'antifurto, attraverso la linea seriale asincrona TX (collegata sul bit 1 del porto).
Un dispositivo hardware di temporizzazione (Timer) attiva ogni 10 mS la linea di richiesta di
interrupt INT del processore. L'accettazione INTA della interruzione, da parte del processore,
disattiva in modo automatico la linea INT .
Si chiede di scrivere, in linguaggio assembly, il programma di gestione del sistema, rispettando
le specifiche riportate qui di seguito.
Ai fini del progetto, il programma principale non esegue operazioni significative per la nostra
interfaccia, salvo la necessaria inizializzazione del sistema al RESET hardware. Subito dopo,
il programma principale entra in un ciclo infinito nel quale non fa nulla, delegando il controllo
del sistema al programma di interruzione.
Il programma di interruzione si
occupa di eseguire la lettura dei pulsanti
ed effettuare un controllo antirimbalzo
sullo stato degli stessi. Ogni volta che la
pressione di un nuovo pulsante
convalidata, il codice del tasto
inviato in formato seriale, tramite la
linea TX, all'unit centrale dell'antifurto.
Se nessun tasto premuto, il sistema
non invia alcun codice.
Pi in dettaglio, i pulsanti sono esaminati ogni 100 mS, e il controllo antirimbalzo consiste nel
verificare che la configurazione letta sul porto sia identica a quella letta 100 mS prima. Questo
primo controllo serve ad evitare che i rimbalzi meccanici dei contatti inducano in errore il
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-66

sistema: quando le ultime due letture del porto dei pulsanti risultano identiche, lo stato della
pulsantiera convalidato.
Lo stato attuale convalidato della pulsantiera poi comparato con quello convalidato in
precedenza e, se diverso e corrispondente alla pressione di almeno un pulsante, la nuova
configurazione viene codificata su 3 bit (CBA), secondo la tabella qui riportata, per essere
inviata sulla linea TX. La codifica "a priorit": se l'utente preme per sbaglio pi pulsanti
insieme, considerato premuto solo quello corrispondente al numero pi alto.
Il nuovo stato dei pulsanti viene serializzato bit a bit sulla linea TX del porto parallelo TXOUT. Il
protocollo di trasmissione seriale, asincrono, prevede la trasmissione di un bit ogni 10 mS. Il
pacchetto di trasmissione composto (vedi figura) da un bit di start a 1, dai 3 bit del dato (il
bit 'A' trasmesso per primo), e da un bit di stop a 0. La trasmissione dei bit deve essere
effettuata senza limpiego di routine di ritardo.
Nota: il programma principale deve essere eseguito automaticamente al RESET del sistema.

Una possibile soluzione


;------------------------------------------------------------------USER
EQU
38h
;porti di ingresso/uscita
TXOUT
EQU
40h
TIME
EQU
8000h
;conteggio del tempo
TXBUFF
EQU
8001h
;"buffer" di trasmissione
PREV
EQU
8002h
;precedente valore letto
CONV
EQU
8003h
;precedente valore convalidato
;------------------------------------------------------------------ORG
0000H
JP
START
ORG
0038h
JP
INTERRUPT
;------------------------------------------------------------------; Main
;
START:
LD
SP,0FFFFh
;iniz. stack pointer
;
LD
A,10
LD
(TIME),A
;10 = (100 mS / 10 mS di timer tick)
;
LD
A,0
;iniz. "buffer" di trasmissione
LD
(TXBUFF),A
LD
(PREV),A
;iniz. precedente valore letto
LD
(CONV),A
;iniz. precedente valore convalidato
;
OUT
(TXOUT),A
;iniz. porto uscita
EI
;
LOOP:
NOP
NOP
NOP
JP
LOOP

;
;
;
;
;
;
;
;

-------------------- programma di interrupt ------------------------ad ogni attivazione dell'INT la variabile TXBUFF scalata a destra
e viene mandato in uscita il solo bit 1.
Inizialmente, in TXBUFF , prima degli scalamenti:
bit 2
= start bit
bit 3,4,5
= dato (nell'ordine: A, B, C)
bit 6, ecc. = stop bit (e idle bits)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-67

INTERRUPT:

PUSH
PUSH

AF
DE

LD
SRL
LD
AND
OUT

A,(TXBUFF)
A
(TXBUFF),A
00000010b
(TXOUT),A

;buffer di TX
;scalalo a destra
;risalvalo
;solo il bit di interesse

LD
DEC
LD
JP

A,(TIME)
A
(TIME),A
NZ,EXIT

;conta il tempo (100 mS)

LD
LD

A,10
(TIME),A

;re-iniz. contatore tempo

LD
LD
IN
CP
LD
JP

A,(PREV)
D,A
A,(USER)
D
(PREV),A
NZ,EXIT

;precedente lettura -> 'D'

;JUMP ed esci se < 100 mS

;lettura pulsanti
;confronto attuale <-> precedente
;salva attuale lettura come 'precedente'
;esci se attuale diversa dalla precedente

;
; si prosegue qui se il valore attuale = precedente, e quindi
; stato "confermato". Il nuovo valore confermato deve essere ora
; confrontato con il precedente valore confermato
;
LD
A,(CONV)
;precedente lettura convalidata
CP
D
;controllo diversit dall'attuale
JP
Z,EXIT
;esci se uguale
;
LD
A,D
LD
(CONV),A
;salva nuova lettura convalidata
OR
A
;controllo che ci sia almeno un tasto premuto
JP
Z,EXIT
;esci se nessun tasto premuto
;
LD
A,00000111b ;codice pulsante, ma anche contatore del loop
DECODE:
RL
D
;nel Carry il pulsante
JP
C,TXCODE
;se a '1', trasmetti il codice
DEC
A
JP
DECODE
;
TXCODE:
SLA
A
;sposta il codice in posizione
SLA
A
SLA
A
OR
00000100b
;start bit a '1'
LD
(TXBUFF),A
;salvalo per la trasmissione
;
EXIT:
POP
DE
;exit code
POP
AF
EI
RET

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

10-68

11

Esercizi
In questo capitolo sono proposti, in ordine di difficolt crescente, esercizi di analisi e sintesi di
codice in linguaggio assembly (DMC8). In generale gli argomenti qui proposti coprono, a
livello introduttivo, unampia casistica di funzionalit richieste nella progettazione dei sistemi
embedded. In particolare, gli esercizi della parte finale del capitolo riguardano la progettazione
di piccoli sistemi di controllo, impostati su base interrupt.

11.1

Esercizi di progetto

(senza uso di tecniche di interrupt)

Questo gruppo di esercizi richiede di scrivere dei semplici programmi in linguaggio assembly,
senza fare ricorso alle tecniche di interrupt.

11.1.1

Progetto di porti e visualizzazione della ROM

PN9206

Un sistema basato sul microprocessore DMC8 possiede gia` 8 Kbytes di ROM (indirizzi: 0000h..1FFFh)
e 8 Kbytes di RAM (indirizzi: E000h..FFFFh). Ad esso devono essere aggiunti un porto di ingresso e un
porto di uscita, entrambi paralleli (indirizzi: F0 e F1h): il porto di ingresso deve leggere lo stato di 1
interruttore; il porto di uscita deve pilotare 8 lampadine. Si richiede di:
a)
b)

Progettare l'hardware dei suddetti porti;


Scrivere in linguaggio assembly un sottoprogramma che, quando chiamato, a seconda dello
stato dell'interruttore, visualizzi in sequenza il contenuto delle prime 16 locazioni della ROM
oppure della RAM, byte dopo byte, sulle lampadine. Ciascun byte deve rimanere visualizzato
almeno un secondo. Ignorare il problema degli eventuali rimbalzi meccanici dei contatti
dell'interruttore, che deve essere acquisito una volta all'inizio del sottoprogramma.

Si richiede che il sottoprogramma conservi intatto il contenuto dei registri interni alla CPU.

11.1.2

Visualizzazione di aree di ROM (1)

PN9401

Un sistema basato sul microprocessore DMC8 possiede: 8 Kbytes di ROM (indirizzi: 0000h..1FFFh);
16 Kbytes di RAM (indirizzi: C000h..FFFFh); un porto di ingresso che legge lo stato di due linee di
controllo (bit D1 e D0, indirizzo E4h); un porto di uscita parallelo che pilota 8 lampadine (indirizzo C8h).
Si chiede di scrivere in linguaggio assembly un sottoprogramma che, quando chiamato, acquisisca lo
stato delle due linee di controllo e quindi visualizzi sulle lampadine il contenuto di 4 locazioni di ROM, in
accordo con la seguente tabella:
D1
0
0
1
1

D0
0
1
0
1

Indirizzi delle locazioni da visualizzare:


0000h 0003h
0010h 0013h
0020h 0023h
0030h 0033h

La visualizzazione deve avvenire in sequenza, locazione per locazione, per indirizzi di memoria
crescenti; ogni valore deve rimanere leggibile per circa due secondi. Il sottoprogramma deve
preservare il contenuto dei registri interni della CPU. Si supponga inoltre che lo STACK sia stato
inizializzato in precedenza dal programma chiamante.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-1

11.1.3

Visualizzazione di aree di ROM (1)

PN9305

Un sistema basato sul microprocessore DMC8 possiede: 8 Kbytes di ROM (indirizzi: 0000h..1FFFh);
16 Kbytes di RAM (indirizzi: C000h..FFFFh); un porto di ingresso che legge lo stato di una linea di
controllo (bit D0, indirizzo 40h); un porto di uscita parallelo che pilota 8 lampadine (indirizzo FFh).
Si chiede di scrivere in linguaggio assembly:
a) un sottoprogramma che, quando chiamato, acquisisca lo stato della linea, restituendo questa
informazione al programma chiamante;
b) un altro sottoprogramma che, chiamando il precedente, tenga conto dello stato della linea per
decidere se visualizzare, sulle lampadine, le prime o le ultime 16 locazioni della ROM,
rispettivamente se la linea e` a "0" o a "1".
La visualizzazione deve avvenire in sequenza, locazione per locazione, per indirizzi di memoria
crescenti; ogni valore deve rimanere leggibile almeno per un secondo. Il sottoprogramma di cui al
punto b) deve preservare il contenuto dei registri interni della CPU. Si supponga inoltre che lo STACK
sia stato inizializzato in precedenza dal programma chiamante.

11.1.4

Decodifica binaria 3-8

PN9402

Un sistema basato sul microprocessore DMC8 possiede: 32 Kbytes di ROM (indirizzi: 0000h..7FFFh);
32 Kbytes di RAM (indirizzi: 8000h..FFFFh); un porto di ingresso che legge il valore di tre linee di
controllo (bit D2 ... D0, indirizzo 80h); un porto di uscita parallelo che pilota 8 lampadine (indirizzo 81h).
Si chiede di scrivere in linguaggio assembly un sottoprogramma che, quando chiamato, acquisisca lo
stato delle linee di controllo e decodifichi il loro valore binario, visualizzando sulle lampadine la
configurazione corrispondente, come in figura:
000
001
010
011
100
101
110
111

La visualizzazione deve avvenire in modo lampeggiante, con un periodo di circa mezzo secondo, per
un totale di circa cinque secondi.
Il sottoprogramma deve preservare il contenuto dei registri interni della CPU.

11.1.5

Inizializzazione di area RAM

PN9403

Un sistema basato sul microprocessore DMC8 possiede: 32 Kbytes di ROM (indirizzi: 0000h..7FFFh);
32 Kbytes di RAM (indirizzi: 8000h..FFFFh); un porto di ingresso che legge il valore di due linee di
controllo (bit D1, D0, indirizzo 33h).
Si chiede di scrivere, in linguaggio assembly, un sottoprogramma che acquisisca lo stato delle linee di
controllo e inizializzi tutte le locazioni della RAM comprese tra gli indirizzi 9000h e FFFFh con un valore
dipendente dallo stato di tali linee, secondo la tabella seguente:
D1
0
0
1
1

D0
0
1
0
1

Valore
0001.0001
0010.0010
0100.0100
1000.1000

Il sottoprogramma deve preservare il contenuto dei registri interni della CPU.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-2

11.1.6

Lampadine accese alternativamente

PN9405

Un sistema basato sul microprocessore DMC8 possiede: 32 Kbytes di ROM (indirizzi: 0000h..7FFFh);
32 Kbytes di RAM (indirizzi: 8000h .. FFFFh); un porto di ingresso che legge 4 linee (bit T3 ... T0,
indirizzo 34h); un porto di uscita che pilota due lampadine (indirizzo 55h) connesse ai bit L7 e L3.
Si chiede di scrivere in linguaggio assembly un sottoprogramma che, quando chiamato, acquisisca il
numero (0..15) presente sulle linee di ingresso e faccia lampeggiare alternativamente le lampadine, per
un totale di alternanze pari al numero letto.
Al numero 0 deve corrispondere la non accensione delle lampadine. In uscita dal sottoprogramma le
lampadine devono essere spente. Ogni lampadina deve rimanere accesa, mentre l'altra e` spenta, per
un tempo pari a circa 300 mS.
Il sottoprogramma deve preservare il contenuto dei registri interni della CPU.

11.1.7

Accensione temporizzata di lampadine

PN9404

Un sistema basato sul microprocessore DMC8 possiede: 32 Kbytes di ROM (indirizzi: 0000h .. 7FFFh);
32 Kbytes di RAM (indirizzi: 8000h .. FFFFh); un porto di ingresso che legge 5 linee (bit T4 ... T0,
indirizzo 00h); un porto di uscita parallelo che pilota una lampadina (indirizzo 01h) connessa al bit L7.
Si chiede di scrivere in linguaggio assembly un sottoprogramma che, quando chiamato, acquisisca il
numero (0..31) presente sulle linee di ingresso e accenda la lampadina per un tempo proporzionale a
tale numero.
Al numero 0 deve corrispondere la non accensione della lampadina, al numero 31 una durata di 15,5
secondi circa, tenendo conto di una unita` di tempo base pari a circa 500 mS. In uscita dal
sottoprogramma la lampadina deve essere spenta. Il sottoprogramma deve preservare il contenuto dei
registri interni della CPU.

11.1.8

Calcolo della media

PN9603

Un sistema basato sul microprocessore DMC8 possiede 32Kbytes di ROM (indirizzi 0000h..7FFFh) e
32Kbytes di RAM (indirizzi 8000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro, un
porto parallelo di uscita MEAN (indirizzo EEh), le cui 8 linee sono connesse ad altrettante spie luminose.
Si chiede di scrivere, in linguaggio assembly, un sottoprogramma che, quando chiamato, calcoli il
valore medio aritmetico dei contenuti delle prime 256 locazioni di RAM e lo visualizzi, arrotondato per
difetto, sulle 8 spie luminose connesse al porto di uscita MEAN.
Note: i valori nella RAM vanno considerati come interi senza segno; il sottoprogramma deve preservare
il contenuto dei registri interni della CPU.

11.1.9

CALL, PUSH e POP (1)

PN9501

Analizzare il programma seguente (scritto in assembly DMC8), prestando molta attenzione a come il
programmatore ha usato le istruzioni CALL, PUSH e POP:
Indir. Label
Istruzione
ORG
1A00h
PORT
EQU
88h
1A00h
BEGIN:
LD
SP,0E000h
1A03h
LD
A,00h
1A05h
LD
C,02h
1A07h
CALL TOGGLE
1A0Ah
HALT
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-3

1A0Bh
1A0Dh
1A0Eh
1A10h
1A11h
1A14h
1A17h
1A19h
1A1Ah

TOGGLE: OUT
PUSH
XOR
DEC
JP
CALL
SKIP:
OUT
POP
RET

(PORT),A
AF
80h
C
Z, SKIP
TOGGLE
(PORT),A
AF

Commentare quanto viene svolto dal programma, nell'ordine in cui il processore esegue le istruzioni
(non nell'ordine in cui sono scritte), analizzando in particolare i contenuti dell'area di Stack e i valori
assunti dai bit 7 e 6 del porto di uscita.

11.1.10

CALL, PUSH e POP (2)

PN9304

Un sistema basato sul microprocessore DMC8 possiede 16 Kbytes di ROM (indirizzi: 0000h..3FFFh) e
16 Kbytes di RAM (indirizzi: C000h..FFFFh). Inoltre un porto di uscita parallelo ad 8 bit risulta allocato
all'indirizzo di I/O 80h.
Si chiede di esaminare il seguente programma (in linguaggio assembly), nel quale le istruzioni CALL,
PUSH e POP sono usate in modo "poco ortodosso", ma corretto:
ORG
0100h
1)
MAIN:
LD
SP,FF00h
2)
LD
A,00h
3)
LOOP:
CALL SUB_1
4)
CALL SUB_3
5)
HALT
6)
7)
8)
9)
10)
11)
12)
13)
14)
15)
16)
17)
18)
19)

SUB_1:

SUB_2:

SUB_3

XOR
OUT
CALL
RET
POP
POP
DEC
DEC
DEC
PUSH
RET
XOR
OUT
RET

0FFh
(80h),A
SUB_2
HL
DE
DE
DE
DE
DE

A,55h
(80h),A

Descrivere dettagliatamente il comportamento del programma, in ordine di esecuzione, istruzione dopo


istruzione, incentrando l'attenzione sui contenuti dello Stack. Descrivere cosa si osserva sulle linee del
porto di uscita.
Suggerimenti: a) il programma "manipola" lo Stack (indirizzi di ritorno); b) Alcune istruzioni e la "SUB_3"
non sono mai eseguite; c) anche se non sono presenti "Salti", il programma esegue un ciclo infinito...
Nella descrizione, aiutarsi con i numeri di riga indicati.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-4

11.1.11

Temporizzatore

PN0203

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32Kbytes di
ROM, 32 Kbytes di RAM, due porti paralleli di ingresso IN e NUM (indirizzi 40h e 41h) e un porto
parallelo di uscita U (indirizzo 42h).
Si chiede di scrivere, in linguaggio assembly Z80, un programma che emuli il funzionamento di un timer
(temporizzatore) avente le caratteristiche descritte nel seguito.
Il temporizzatore ha un ingresso di comando START, 8 ingressi di dato N7..N0, e una uscita OUT. In
condizioni di riposo, luscita OUT e` a zero, e il dispositivo attende un fronte di discesa sullingresso
START. Allarrivo del fronte di discesa sullingresso START, il dispositivo attiva luscita OUT per una
durata proporzionale al valore letto sugli ingressi N7..N0. Per il temporizzatore, lunita` di tempo e` 250
mS, per cui la durata massima dellimpulso risultera` pari a 63,75 secondi (se il valore impostato sugli
ingressi N7..N0 e` zero, limpulso non e` generato). Durante la generazione dellimpulso, lingresso
START ignorato. Si supponga lingresso START collegato al bit 0 del porto IN, gli ingressi N7..N0 al
porto NUM, luscita OUT al bit 7 del porto U.
Nota: il programma deve andare automaticamente in esecuzione al RESET hardware del sistema.

11.1.12

Funzione aritmetica programmabile (1)

PN0001

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, tre porti paralleli di ingresso DA, DB e OPST (indirizzi 44h, 45h e 50h) e un
porto parallelo di uscita UU (indirizzo 55h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un dispositivo
logico - aritmetico avente le seguenti specifiche:
Ingressi:
A7..0
B7..0
OP1..0
ST

Primo operando A (8 bit);


Secondo operando B (8 bit);
Codice operativo della operazione da eseguire;
Segnale di calcolo, attivo sul fronte di salita;

F7..0

Risultato F della operazione (8 bit).

Uscite:
Al fronte di salita del segnale di calcolo ST, il dispositivo esegue sugli operandi A e B loperazione
specificata dal codice operativo OP, secondo la tabella qui riportata. Il risultato di una operazione e`
mantenuto stabile fino alla successiva.
Lunita` dispone internamente di un flag FLAG, il cui valore, definito dal risultato dellultima operazione
eseguita, viene mantenuto sino alla esecuzione della successiva operazione e, se necessario, da questa
utilizzato.
OP1..0
00

Operazione
F = A Shift Right 1

01
10
11

F = A div 2
F = A + B + FLAG
F = A B FLAG

Descrizione
Loperando A e` scalato a destra di un bit. Il contenuto di FLAG e` inserito nel bit 7.
Il bit in uscita dal bit 0 e` copiato in FLAG.
Il resto della divisione e` registrato in FLAG
Somma aritmetica tra numeri interi senza segno, il riporto e` registrato nel FLAG
Sottrazione tra numeri interi senza segno, il prestito e` registrato nel FLAG

Si supponga di collegare gli ingressi A7..0 e B7..0 rispettivamente ai porti DA e DB, OP1..0 al porto OPST
(bit 1 e 0), ST al porto OPST (bit 2), e luscita F7..0 al porto UU. FLAG non e` visibile dallesterno. Il
programma deve partire al RESET del sistema.

11.1.13

Funzione aritmetica programmabile (2)

PN9906

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, tre porti paralleli di ingresso SET, DX e DY (indirizzi 82h, 83h e 84h) e due
porti paralleli di uscita UH e UL (indirizzi 8Ah e 8Bh).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-5

Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di una unita`
logico - aritmetica combinatoria avente le seguenti specifiche:
Ingressi:
X7..0
Y7..0
S1..0

Primo operando X (8 bit, intero positivo);


Secondo operando Y (8 bit, intero positivo);
Operazione da eseguire;

U15..0

Risultato della operazione (16 bit).

Uscite:
Luscita U15..0 e` funzione degli operandi
impostato su S1..0:
S1..0
00
01
10
11

Operazione
U = X xor Y
U=X+Y
U = X SHL Y
U=Y

X7..0 e Y7..0, e il tipo di operazione dipende dal codice

Commento
Bit a bit, byte alto azzerato
Somma aritmetica
X, esteso a 16 bit, scalato a sinistra di Y bit (0 <= Y <= 8)
Byte alto azzerato

Si supponga di collegare gli ingressi X7..0 e Y7..0 rispettivamente ai porti DX e DY, S1..0 al porto SET (bit
1 e 0), e luscita U15..0 ai porti UH e UL. Il programma deve partire al RESET del sistema.

11.1.14

Funzione aritmetica programmabile (3)

PN9905

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, tre porti paralleli di ingresso OPCODE, DA e DB (indirizzi 30h, 31h e 32h) e un
porto parallelo di uscita FU (indirizzo 40h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di una unita`
logico - aritmetica combinatoria avente le seguenti specifiche:
Ingressi:
A3..0
B3..0
OP1..0

Primo operando A (4 bit);


Secondo operando B (4 bit);
Codice operativo della operazione da eseguire;

F7..0

Risultato della operazione (8 bit).

Uscite:

Luscita F7..0 e` funzione degli operandi A3..0 e B3..0, e il tipo di operazione dipende dal codice impostato
su OP1..0:
OP1..0
00
01
10
11

Operazione
U = not A
U = A nand B
U=A+B
U=A*B

Commento
Bit a bit, impostare a zero i bit alti del risultato
Bit a bit, impostare a zero i bit alti del risultato
Somma aritmetica, operandi e risultato in complemento a due
Moltiplicazione, operandi e risultato intesi come interi positivi

Si supponga di collegare gli ingressi A3..0 e B3..0 rispettivamente ai porti DA e DB (bit 3..0), OP1..0 al
porto OPCODE (bit 1 e 0), e luscita F7..0 al porto FU. I bit non utilizzati dei porti di ingresso sono da
intendersi collegati a zero. Si presti attenzione alla estensione del segno nel passare dalla
rappresentazione a 4 bit a quella a 8. Il programma deve partire al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-6

11.1.15

Funzione aritmetica (calcolo con numeri frazionari)

PN0002

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, due porti paralleli di ingresso PA e PB (indirizzi 14h e 15h) e un porto parallelo
di uscita RIS (indirizzo 20h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli un dispositivo di calcolo avente
le seguenti specifiche:
Ingressi:
A6..0
B3..0
CK

Primo operando A (7 bit, intero positivo);


Secondo operando B (4 bit, intero positivo);
Segnale di sincronizzazione;

U7..0

Risultato U della operazione (8 bit, intero positivo).

Uscite:

Al fronte di salita di CK, il dispositivo esegue, sugli operandi A e B, la seguente operazione:

U = A x 1,625 B
La parte intera del risultato U e` fornita in uscita al fronte di discesa di CK; la parte frazionaria di U e`
ignorata. Suggerimento: 1,625 = 1 + 1/2 + 1/8. Si supponga di collegare gli ingressi: A6..0 al porto PA
(bit6..0), B3..0 al porto PB (bit3..0), CK al porto PB (bit7), e le uscite U7..0 al porto RIS. Il programma deve
partire al RESET del sistema.

11.1.16

Controllo di sensori di temperatura

PN9602

Un sistema basato sul microprocessore DMC8 possiede 8 Kbytes di ROM (indirizzi 0000h..1FFFh) e 8
Kbytes di RAM (indirizzi E000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro:
- 2 porti paralleli di ingresso TL e TH (indirizzi 00h e 01h), collegati a 8 coppie di sensori di
temperatura, poste rispettivamente in 8 forni di un impianto industriale;
- 3 porti paralleli di uscita PLOW, POK e PHIGH (indirizzi 30h, 31h e 32h), collegati a 3 file di 8
spie luminose su di un pannello di controllo.
Ogni sensore fornisce "1" se la temperatura supera una soglia prefissata. Per il forno i, il sensore tarato
sulla temperatura bassa e` collegato al bit i del porto TL, ed il sensore tarato sulla temperatura alta
allo stesso bit del porto TH. Le spie luminose indicano la temperatura degli 8 forni, ed ogni forno ne ha 3
('LOW', 'OK' e 'HIGH').
Si chiede di scrivere, in linguaggio assembly, il programma di monitoraggio della temperatura dei forni.
Tale programma deve essere attivato dal reset del sistema e controllare, ogni 5 minuti primi (circa), lo
stato dei sensori. Per ogni forno devono essere accese le spie: LOW quando la temperatura e` bassa,
OK se la temperatura e` intermedia, HIGH se la temperatura e` alta. Ricordarsi di inizializzare (se
necessario) lo Stack Pointer.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-7

11.1.17

Flip-Flop JK - PET

PN9705

Un sistema basato sul microprocessore DMC8 possiede 16Kbytes di ROM (indirizzi 0000h..3FFFh) e
4Kbytes di RAM (indirizzi F000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro, un
porto parallelo di ingresso INGRESSI (indirizzo 20h), i cui bit 0, 1, 2 sono collegati rispettivamente alle
linee di ingresso CK, J, e K, ed un porto parallelo di uscita USCITE (indirizzo 21h), di cui e` significativo
il bit 7, connesso alla linea Q.

CK

CK
0

CK
J
K

JK e.t. FF

Q
0

CK

CK

1
J

1
K

Si chiede di scrivere, in linguaggio assembly, un programma attivato al reset hardware che emuli il
funzionamento di un flip-flop JK edge-triggered, il cui diagramma ASM e` riportato in figura.
Ricordarsi di definire, se necessario, lo stack (inizializzando lo Stack Pointer) e di collegare
lesecuzione del programma al RESET del sistema.

11.1.18

Vasche con sensori di livello

PN9701

Un sistema basato sul microprocessore DMC8 possiede 16Kbytes di ROM (indirizzi 0000h..3FFFh) e
16Kbytes di RAM (indirizzi C000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro:
- 1 porto parallelo di ingresso DATA (indirizzo F0h), collegato a 8 sensori di livello S0..7 posti in 8
diverse vasche di un impianto industriale per la depurazione delle acque;
- 2 porti paralleli di uscita OUTA e OUTB (indirizzi 30h e 31h), collegati a 2 file separate di 4 coppie
di spie luminose rosse/verdi su di un pannello di controllo.
Ogni sensore fornisce "1" se viene raggiunto dal liquido. Le lampadine servono a visualizzare lo stato del
livello delle vasche (spia rossa: livello insufficiente, spia verde: livello corretto).
Per ogni porto di uscita, le lampadine rosse risultano collegate ai bit 0,1,2 e 3, mentre le verdi ai
rimanenti bit 4,5,6 e 7. I sensori da S0 a S3 devono corrispondere alle spie collegate al porto OUTA, i
sensori da S4 a S7 alle spie del porto OUTB.
Si chiede di scrivere, in linguaggio assembly, un programma di monitoraggio del livello delle vasche.
Tale programma deve essere attivato dal RESET del sistema e controllare, ogni 10 minuti primi
(circa), lo stato dei sensori, attivando di conseguenza le corrispondenti spie luminose.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-8

11.1.19

Registro a scorrimento SISO a 5 bit

PN9804

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM e alcuni porti di ingresso/uscita paralleli.
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un registro a
scorrimento a 5 bit Serial Input Serial Output (SISO), avente le seguenti specifiche:
Ingressi:
CK:
IN:
INIBIT:
PRESET:
Uscita:
OUT:

Clock di scorrimento, attivo sui fronti di salita;


Ingresso seriale;
Inibizione sincrona dello scorrimento (inibisce se = 1);
Preset asincrono. In qualunque momento, se = 1, il contenuto del registro viene forzato
a 01011.
Uscita seriale (il bit meno significativo del registro).

Si supponga di collegare gli ingressi CK, INIBIT, PRESET e IN ad un porto INPUTS (indirizzo 02h,
rispettivamente ai pin 0, 1. 2 e 3); luscita OUT sara` collegata a un porto OUTPUTS (indirizzo 03h). Il
programma deve essere attivato al RESET del sistema.

11.1.20

Registro a scorrimento PISO a 16 bit

PN9803

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM e alcuni porti di ingresso/uscita paralleli.
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un registro a
scorrimento a 16 bit Parallel Input Serial Output (PISO), avente le seguenti specifiche:
Ingressi:
CK:
Clock di caricamento e scorrimento, attivo sui fronti di salita;
IN15..IN0: Ingressi per il caricamento parallelo;
MODE:
Modo di funzionamento. Sul fronte di salita del clock CK, il registro:
- carica il dato parallelo, se MODE= 0;
- fa scorrere i bit (dal bit 15 al bit 0), se MODE =1;
CLEAR: Clear asincrono (se = 1, il registro azzera il suo contenuto, in qualunque momento,
indipendentemente dal clock).
Uscita:
OUTS:
Uscita seriale (corrispondente al bit 0).
Si supponga di collegare gli ingressi CK, MODE e CLEAR ad un porto CONTROLS (indirizzo 42h,
rispettivamente ai pin 0, 1 e 2) e gli ingressi IN15..IN0 a due porti INPUT_H e INPUT_L (indirizzo 41h e
40h rispettivamente); luscita OUTS sara` collegata a un porto OUTPUT (indirizzo 43h). Il programma
deve essere attivato al RESET del sistema.

11.1.21

Registro a scorrimento universale a 16 bit

PN9901

Si dispone di una scheda microcomputer basata sul microprocessore DMC8, cosi configurata: 16
Kbytes di ROM (indirizzi 0000h-3FFFh), 8 Kbytes di RAM (indirizzi E000h-FFFFh), tre porti paralleli di
ingresso CNTL, INH e INL (indirizzi 10h, 11h e 12h) e due porti paralleli di uscita OUTH e OUTL
(indirizzi 20h e 21h).
Si chiede di scrivere, in linguaggio assembly, un programma che permetta alla scheda di simulare il
funzionamento di un registro a 16 bit, descritto dalle seguenti specifiche:
Ingressi:
CK:
IN15..IN0:

Clock, attivo sui fronti di salita (si supponga che la sua frequenza massima sia di due
ordini di grandezza piu` bassa di quella del processore);
Ingressi per il caricamento parallelo;

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-9

S1, S0:

CLEAR:

Controllo del modo di funzionamento. Sul fronte di salita del clock:


a) se S1=0 e S0=0 il registro mantiene il valore precedente;
b) se S1=0 e S0=1 il registro fa ruotare a destra i bit di un passo, nella direzione dal bit
15 al bit 0 (nel bit 15 viene caricato il precedente bit 0);
c) se S1=1 e S0=0 il registro fa ruotare a sinistra i bit di un passo, nella direzione dal bit
0 al bit 15 (nel bit 0 viene caricato il precedente bit 15);
d) se S1=1 e S0=1 il registro carica il dato parallelo presente in quel momento agli
ingressi.
Reset sincrono (se = 1, il registro azzera le sue uscite sul fronte di salita del clock).

Uscite:
OUT15..OUT0:

Uscite parallele e seriali.

Si supponga di collegare gli ingressi CK, S1, S0 e CLEAR al porto CNTL (ai bit 7,6,5 e 4, nellordine) e gli
ingressi IN15..IN0 ai due porti INH e INL; le uscite OUT15..OUT0 ai porti OUTH e OUTL. Il programma
deve essere attivato al RESET hardware del sistema.

11.1.22

Registro a scorrimento SIPO a 24 bit

PN9802

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM e alcuni porti di ingresso/uscita paralleli. Si chiede di scrivere, in linguaggio
assembly, un programma che simuli il funzionamento di un registro a scorrimento a 24 bit Serial Input
Parallel Output (SIPO), avente le seguenti specifiche:
Ingressi:
CK:
Clock di scorrimento, attivo sui fronti di salita;
IN:
Ingresso seriale sincrono;
EN:
Abilitazione allo scorrimento (se = 0, il registro mantiene fisse le sue uscite);
CLEAR: Reset Asincrono (se = 1, il registro azzera le sue uscite, ignorando il clock);
Uscite:
U0..U23: Uscite parallele (nellordine di scorrimento: U0 => U23).
Si supponga di collegare CK, IN, EN e CLEAR ad un porto INPUTS (indirizzo 35h, rispettivamente ai pin
0, 1, 2 e 3) e le uscite U0..U23 a tre porti U_0_7, U_7_15, U_16_23 (indirizzi 40h, 41h e 42h). Il
programma deve essere attivato al RESET del sistema.

11.1.23

Contatore binario sincrono avanti/indietro a 10 bit

PN0204

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, un porto parallelo di ingresso INPUT (indirizzo 88h) e due porti paralleli di
uscita OUTH e OUTL (indirizzi A0h e A1h).
Si chiede di scrivere, in linguaggio assembly Z80, un programma che simuli il funzionamento di un
contatore binario sincrono avanti/indietro a 10 bit (ciclico, modulo 1024), che abbia le seguenti
specifiche:
Ingressi:
CK:
Clock di conteggio, attivo sui fronti di salita;
UP:
Ingresso sincrono per impostare la direzione di conteggio (conta in avanti se a livello alto);
EN:
Ingresso sincrono di abilitazione del conteggio (se basso, al fronte attivo di CK, il contatore
non cambia le sue uscite, se alto, lavora normalmente);
CL:
Ingresso sincrono di azzeramento (se alto, il contatore e` azzerato al fronte attivo del clock).
Uscite:
Q9..0: Uscite di conteggio (10 bit).
Si supponga di collegare gli ingressi CK, UP, EN e CL al porto INPUT (rispettivamente ai pin 0, 1, 2 e 3).
Le uscite Q9..0 saranno collegate ai porti OUTH e OUTL (OUTL0 = Q0; i bit non utilizzati devono essere
azzerati). Il programma deve essere attivato al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-10

11.1.24

Contatore sincrono avanti/indietro presettabile a 16 bit

PN9904

Si consideri disponibile un sistema basato sul microprocessore DMC8, cosi configurato: 32 Kbytes di
ROM, 32 Kbytes di RAM, tre porti paralleli di ingresso CTL, DATAH e DATAL (indirizzi 50h, 51h e 52h)
e due porti paralleli di uscita OUTH e OUTL (indirizzi 80h e 81h).
Si chiede di scrivere, in linguaggio assembly, un programma che simuli il funzionamento di un contatore
sincrono avanti/indietro presettabile a 16 bit (modulo 65536), avente le seguenti specifiche:
Ingressi:
CK:
DIR:
EN:
DATA15..0:
LOAD:

Uscite:
OUT15..0:

Clock di conteggio, attivo sui fronti di salita;


Ingresso sincrono per impostare la direzione di conteggio (conta in avanti se a livello alto);
Ingresso sincrono di abilitazione del conteggio (attivo a livello alto);
Ingresso di dato a 16 bit per il caricamento parallelo;
Ingresso sincrono di caricamento del dato presentato allingresso DATA (sul fronte attivo
del clock, quando LOAD alto, il contatore carica il valore impostato allingresso DATA,
indipendentemente dal valore di EN e DIR).
Uscita di conteggio a 16 bit.

Si supponga di collegare gli ingressi CK, DIR, EN e LOAD al porto CTL (rispettivamente ai pin 0, 1, 2 e
3); le uscite OUT15..0 saranno collegate ai porti OUTH e OUTL; gli ingressi DATA15..0 ai porti DATAH e
DATAL. Il programma deve essere attivato al RESET del sistema.

11.1.25

Contatore sincrono binario avanti/indietro, ciclico, modulo 256

PN9801

Un sistema basato sul microprocessore DMC8 possiede 8Kbytes di ROM (indirizzi 0000h..1FFFh) e
8Kbytes di RAM (indirizzi E000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro, un
porto parallelo di ingresso INPUTS (indirizzo 22h), i cui bit 0, 1, 2, 3 sono collegati rispettivamente alle
linee di ingresso CK, RESET, EN, UP, ed un porto parallelo di uscita OUTPUTS (indirizzo 34h), di cui
sono significative tutte le linee (W7 .. W0).
Si chiede di scrivere, in linguaggio assembly, un programma attivato al reset hardware che simuli il
comportamento di un contatore sincrono avanti/indietro (binario ciclico modulo 256), che possieda le
seguenti caratteristiche:
a) riceve un clock esterno CK (periodo = 100 mS) ed e` controllato dagli ingressi RESET, EN, UP;
b) genera le 8 uscite W7 .. W0, che rappresentano i numeri da 00h a FFh;
c) lingresso di RESET, quando a 1, azzera il contatore, ed e asincrono;
d) lingresso di EN, quando a 1, abilita il conteggio del contatore ed e sincrono rispetto a CK;
e) lingresso di UP, quando a 1, obbliga il conteggio in avanti, quando a 0 quello indietro, ed e
sincrono rispetto a CK;
Ricordarsi di definire lo stack (inizializzando lo Stack Pointer, se serve) e di collegare lesecuzione del
programma al RESET del sistema.

11.1.26

Visualizzazione su 8 lampadine di sequenza numerica

PN9702

Un sistema basato sul microprocessore DMC8 possiede 8Kbytes di ROM (indirizzi 0000h..1FFFh) e
8Kbytes di RAM (indirizzi E000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro:
- 1 porto parallelo di ingresso START (indirizzo 88h), il cui bit 0 e` collegato a un pulsante;
- 2 porti paralleli di ingresso ENABLE (indirizzo AAh) e SET (indirizzo BBh), collegati rispettivamente
a 8 interruttori E0..7 di abilitazione e a 8 interruttori S0..7 di predisposizione;
- 1 porto parallelo di uscita LIGHTS (indirizzo EEh), le cui linee L0..7 attivano 8 lampade in una vetrina.
Nella memoria ROM sono presenti, a partire dall'indirizzo 1000h, 128 byte contenenti le configurazioni di
accensione delle 8 lampade, da visualizzare in sequenza (in ogni byte, il bit 0 corrisponde alla lampada
L0 , il bit 1 alla lampada L1 , ecc.).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-11

Si chiede di scrivere, in linguaggio assembly, un sottoprogramma che svolga le seguenti funzioni:


- Il sottoprogramma ritorna subito al chiamante se la linea di START e` trovata a 0, altrimenti esegue,
una sola volta, la sequenza di accensione delle lampade memorizzata nella ROM.
- Ogni configurazione viene mantenuta sulle lampade per circa mezzo secondo.
- Alla fine della sequenza le lampade sono spente, e il sottoprogramma torna al chiamante (i registri
devono essere restituiti invariati al chiamante).
- Il porto SET definisce, bit per bit, se la sequenza di ogni lampada deve essere generata cosi` come
e`, oppure negata (il bit j, se a 1, impone linversione del bit della lampada Lj ; se a 0 no).
- Il porto ENABLE controlla labilitazione delle 8 lampade (il bit j, se a 0 inibisce laccensione della
lampada Lj ; se a 1 la abilita).

11.1.27

Generatore di segnale digitale

PN9604

Un sistema basato sul microprocessore DMC8 possiede 32Kbytes di ROM (indirizzi 0000h..7FFFh) e
16Kbytes di RAM (indirizzi C000h..FFFFh). Tra i suoi dispositivi di ingresso-uscita troviamo, tra l'altro:
- 1 porto parallelo di ingresso (indirizzo 08h), il cui bit 7 e` collegato ad una linea di controllo ENABLE;
- 1 porto parallelo di uscita WAVE (indirizzo A0h, linee W7..W0).
Nella memoria ROM sono stati memorizzati, a partire dall'indirizzo 5000h, i 4096 campioni ad 8 bit di un
segnale "analogico" che si vuole generare tramite l'uscita WAVE. Tale uscita sara` infatti collegata ad un
dispositivo di conversione digitale / analogica, esterno al sistema e del quale non ci occuperemo.
Si chiede di scrivere, in linguaggio assembly, un sottoprogramma che, quando chiamato, generi la
sequenza dei 4096 campioni sul porto WAVE, azzerandolo alla fine. Tra la generazione di un campione
ed il successivo devono trascorrere 100 S circa. La linea di controllo ENABLE, quando a "1", abilita
l'uscita dei valori sul porto WAVE. Quando a "0", impone a zero le linee del porto WAVE, senza pero`
fermare lalgoritmo di generazione, che deve proseguire con la stessa temporizzazione.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-12

11.2

Esercizi di progetto

(con uso di tecniche di interrupt)

Questo ultimo gruppo di esercizi richiede di scrivere dei programmi in assembly utilizzando
tecniche di interrupt, e riguardano la progettazione di piccoli sistemi di controllo embedded.

11.2.1

Controllore per effetti speciali di luce

PI011127

Si consideri disponibile un sistema di controllo, basato sul microprocessore DMC8, configurato con 32
Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in figura.
Linterfaccia parallela dingresso (allocata agli indirizzi A0h e A1h) permette di ricevere comandi da una
sala di controllo e di leggere lo stato di due interruttori, Light e Enable. Il porto parallelo di uscita
LAMPS (indirizzo A6h) pilota una fila di 8 proiettori L7..L0 facenti parte di un impianto di effetti speciali
per uno studio cinematografico. Il
nostro sistema ha il compito di
accendere un proiettore alla
volta, a rotazione, secondo le
indicazioni ricevute dalla sala di
controllo.
La sala di controllo invia ogni tanto
un byte di comando al nostro
sistema, previo controllo che la
linea Busy sia a zero. Se cosi` e`,
pone il byte di comando sulle line
del dato e genera un impulso sulla
linea Strobe, alto per 100 nS.
Ogni volta che la sala di controllo
invia un byte di comando, come si
pu osservare in figura, la logica
dellinterfaccia attiva una richiesta
di interrupt INT al processore.

Si chiede di scrivere, in linguaggio


assembly, il programma di
gestione del sistema, in base alle
specifiche tecniche qui di seguito
descritte.
Il
sistema,
nel
programma principale, si occupa di
fare ruotare la figura di
accensione delle lampade dei
proiettori. Al RESET del sistema, in
attesa del primo comando, le
lampade sono mantenute spente.
Ogni comando consiste in un byte,
i cui bit hanno, per convenzione, il
significato qui descritto:
Bit 7: se a 1, attiva laccensione delle lampade, se a 0, le spegne (in questo caso, i bit 6..0 sono
privi di significato);
Bit 6: se a 1, ordina la rotazione verso destra, se a 0 quella verso sinistra;
Bit 5..0: numero binario senza segno di 6 bit che definisce il tempo di rotazione (il tempo che passa tra
una configurazione e quella successiva ruotata) in unita` di 100 mS (000000 corrisponde a 100 mS,
111111 a 6,4 S).
Il sistema tiene conto dello stato degli interruttori Light e Enable. Light, quando a 1, abilita il normale
funzionamento delle luci; quando a 0 mantiene spente le lampade (ma il sistema continua a ricevere e
processare i comandi). Se Light riportato a 1, le lampade si devono accendere coerentemente con
le impostazioni date dallultimo comando ricevuto. Enable, quando a 1, abilita la funzione dei
comandi; quando a 0 ne sospende la funzione (il sistema continua a ricevere i comandi, ma non li
attua). Il programma deve essere eseguito al RESET del sistema.
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-13

11.2.2

Contatore di transiti autostradali

PI020627

Si consideri disponibile un sistema di controllo, basato sul microprocessore DMC8, configurato con 32
Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in figura.
Il porto parallelo di ingresso SENS (allindirizzo AAh) permette di leggere sui bit F7 e F0 le uscite di due
sensori di prossimit, posizionati uno allinizio e laltro alla fine di una bretella autostradale a senso
unico. I due porti paralleli di uscita CNTA e CNTB (indirizzi 0Ah e 0Bh) pilotano rispettivamente due file
indipendenti di 8 lampadine,
poste su di un pannello.
Un Timer attiva ogni 50 mS la
linea di richiesta di interrupt INT
del processore: allaccettazione
della interruzione, la risposta del
processore INTA disattiva in
modo automatico la linea INT .
Si chiede di scrivere, in
linguaggio
assembly,
un
programma di controllo del
transito dei veicoli nel tratto
autostradale suddetto, in base
alle specifiche qui riportate.
Il sistema, nel programma
principale,
controlla
continuamente i due sensori.
Ogni volta che un veicolo passa
sopra uno dei sensori, questo si
attiva (attivo alto).
Si supponga di considerare
transitato un veicolo quando il
segnale in uscita dal sensore
passa da zero a uno.
Si faccia lipotesi che sopra il
singolo sensore possa passare
un solo veicolo alla volta (i
veicoli sono cio nettamente
distinguibili tra loro).
Ovviamente, due veicoli possono
trovarsi
contemporaneamente
sopra il sensore di inizio e quello
di fine del tratto autostradale.
Il programma principale si preoccupa di valutare il numero di veicoli presenti sulla tratta (che sono
cio transitati sopra il sensore di inizio, ma non ancora su quello di fine).
Ogni 10 secondi, utilizzando la routine di interrupt, il sistema aggiorner sulle lampadine del porto
CNTA, in binario, il numero di veicoli in quel momento presenti sulla tratta, mentre sulle lampadine
del porto CNTB riporter la differenza tra il numero di veicoli attuali e quelli rilevati 10 secondi prima
(come numero intero con segno, in complemento a due).
Note:

Il programma deve essere eseguito automaticamente al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-14

11.2.3

Contatore di prodotti da forno

PI020906
Si consideri disponibile un
sistema di controllo, basato sul
microprocessore
DMC8,
configurato con 32 Kbytes di
ROM, 32 Kbytes di RAM, e i
dispositivi di I/O rappresentati in
figura.
Il porto parallelo di ingresso
CNT (allindirizzo 88h) permette
di leggere sui bit F7 e F0 le
uscite di due sensori ottici,
posizionati uno allingresso e
laltro alluscita di un forno
continuo per la cottura di
prodotti alimentari.
I due porti paralleli di uscita
NUM e MEDIA (indirizzi 3Ah e
3Bh) pilotano rispettivamente
due file indipendenti di 8
lampadine, poste su di un
pannello.
Un Timer attiva ogni 50 mS la
linea di richiesta di interrupt
INT
del
processore:
allaccettazione
della
interruzione, la risposta del
processore INTA disattiva in
modo automatico la linea INT .
Si chiede di scrivere, in
linguaggio
assembly,
un
programma di controllo del
numero di oggetti in transito
nel forno, in base alle
specifiche qui riportate.

Il sistema, nel programma principale, controlla continuamente i due sensori. Ogni volta che un
oggetto passa davanti ad uno dei sensori, questo attiva la sua uscita. Si supponga di considerare
transitato un oggetto quando il segnale in uscita dal sensore passa da uno a zero. Si tenga presente
che davanti al singolo sensore pu passare un solo oggetto alla volta, e che due diversi oggetti, nello
stesso momento, possono trovarsi uno davanti al sensore di ingresso e laltro davanti a quello di
uscita.
Il programma principale si occupa di valutare il numero di oggetti presenti in un dato momento nel
forno (che sono cio passati davanti al sensore di ingresso, ma non ancora davanti a quello di uscita).
Ogni minuto, utilizzando la routine di interrupt, il sistema aggiorner sulle lampadine del porto NUM, in
binario, il numero di oggetti in quel momento presenti nel forno, mentre sulle lampadine del porto
MEDIA riporter la media delle ultime 4 misure effettuate.
Note:

Come indicazione, si tenga presente che il forno pu contenere al massimo 50 oggetti e che al massimo
entrano ed escono 10 oggetti al minuto.
Il programma deve essere eseguito automaticamente al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-15

11.2.4

Controllore di carrello industriale

PI030204

Un sistema basato sul microprocessore


DMC8 controlla un carrello industriale per la
movimentazione a distanza di manufatti. Il
funzionamento del carrello (semplificato per
ragioni didattiche) pu essere cos descritto:
o Il suo movimento vincolato da un binario
rettilineo e prevede 4 possibili stazioni (A, B,
C e D);
o E controllato in cabina dalloperatore
mediante un solo pannello con 4 pulsanti per
la scelta della stazione di destinazione;
o E provvisto di sensori di posizione lungo il
binario (descritti pi sotto).

Come riportato nella figura qui a lato, la


pulsantiera connessa al porto di ingresso
BUTTONS (indirizzo 80h).
I pulsanti A, B, C e D sono collegati
come in figura ai bit del porto (se premuti,
generano un livello alto).
Il porto di ingresso SENSORS (indirizzo
F2h) collegato, come in figura, ai seguenti
sensori di posizione:
- SD, SC, SB e SA, quando a uno, segnalano
che il carrello si trova presso una delle 4
stazioni, rispettivamente D, C, B e A;
- Tcd, Tbc e Tab, quando a uno, segnalano
che il carrello si trova nella tratta in mezzo
a due stazioni consecutive, rispettivamente
C-D, B-C o A-B.
Per semplicit, si supponga che i sensori siano predisposti in modo che non si possa mai verificare il
caso in cui due sensori contigui risultino attivi contemporaneamente.
ll porto di uscita MOTOR (indirizzo F1h) consente di attivare il motore del carrello, nelle due direzioni: il
dispositivo di potenza che controlla il motore riceve due bit di comando: ToA (bit 0: se a 1, accende il
motore nella direzione verso il capolinea A), e ToD (bit 1: se a 1, accende il motore nella direzione
verso laltro capolinea).
Un Timer attiva ogni 50 mS la linea di richiesta di interrupt INT del processore: allaccettazione della
interruzione, la risposta del processore INTA disattiva in modo automatico la linea INT . Il sistema
inoltre provvisto di 32 Kbytes di ROM e 32 Kbytes di RAM.

Si chiede di scrivere, in linguaggio assembly, il programma di controllo della movimentazione del


carrello, seguendo le specifiche qui riportate:
Il sistema, nel programma di interruzione, legge la pulsantiera a disposizione delloperatore.
Lo stato della pulsantiera viene convalidato da due letture consecutive, distanti tra loro 50 mS, allo
scopo di impedire che i rimbalzi meccanici dei pulsanti possano fornire letture errate. Nellindividuare il
pulsante premuto dalloperatore, si deve tenere conto della possibilit che questi possa premere
erroneamente pi pulsanti nello stesso momento. Al fine di impedire le ambiguit, deve essere
effettuata una codifica a priorit, secondo lordine pi conveniente.
Infine, la routine di interruzione rende disponibile la richiesta al programma principale nella variabile
STATION. Se nessun tasto risulta premuto, la variabile STATION non deve essere aggiornata.
Il programma principale, invece, ha il compito di gestire lattivazione del motore, attuando la richiesta
delloperatore codificata dal programma di interruzione nella variabile STATION. Tenendo conto della
posizione attuale del carrello, questo dovr essere portato alla stazione desiderata.
Il programma deve essere attivato automaticamente al RESET hardware del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-16

11.2.5

Gestione di pulsanti (Up / Down)

PI030409

Si consideri disponibile un sistema di


controllo di impianto, basato sul
microprocessore DMC8, configurato
con 32 Kbytes di ROM, 32 Kbytes di
RAM, e i dispositivi di I/O rappresentati
in figura.
Il porto parallelo di ingresso SW
(allindirizzo A8h) permette di leggere
sui bit F1 e F0 le uscite di due pulsanti
elettromeccanici, posizionati su di un
pannello.
I due porti paralleli di uscita NUMH e
NUML (indirizzi 3Bh e 3Ah) pilotano
complessivamente
16
lampadine,
posizionate in fila, sullo stesso
pannello.
Il numero binario B15..B0 visualizzato
sulle lampadine rappresenta il valore di
una variabile che il sistema trasmette,
mediante le stesse linee, anche
allimpianto.
Un Timer attiva ogni 50 mS la linea di
richiesta
di
interrupt
INT
del
processore:
allaccettazione
della
interruzione, la risposta del processore
INTA disattiva in modo automatico la
linea INT .
Si chiede di scrivere, in linguaggio assembly, un programma di interruzione che gestisca il numero
binario visualizzato sulle lampadine, sulla base delle modalit di azionamento dei due pulsanti (Up e
Down).
Il sistema, nel programma principale, svolge ciclicamente altri compiti di controllo dellimpianto, che
non interagiscono con il controllo delle lampadine e dei pulsanti. Il programma principale deve quindi
essere scritto tenendo conto delle esigenze del nostro problema di controllo, ma deve concludersi con
un salto allindirizzo 5000h, dove si suppone si trovi il programma di gestione della parte rimanente
dellimpianto. Tale programma stato scritto da altri e immaginiamo sia gi presente nella ROM.
Il programma di interruzione deve controllare periodicamente i pulsanti Up e Down. Allo scopo di
impedire che i rimbalzi meccanici dei pulsanti possano fornire letture errate, lo stato dei pulsanti deve
essere convalidato da due letture consecutive degli stessi, a distanza di 50 mS.
Specifiche utente sullazionamento dei pulsanti:

1) Premere per un breve tempo il pulsante Up produce, al suo rilascio, lincremento del
numero visualizzato di una unit;
2) Premere lo stesso pulsante per un secondo produce, al suo rilascio, un incremento di
dieci unit.
3) Analogamente per il pulsante Down, a cui corrispondono, con le stesse modalit, il
decremento di una oppure di dieci unit.
4) Nel caso di pressione contemporanea dei due pulsanti, prioritario lazionamento del
pulsante Down.
Note:

Il programma deve essere eseguito automaticamente al RESET del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-17

11.2.6

Misuratore di velocit di rotazione

PI041112

Si consideri disponibile un sistema di controllo industriale, basato sul microprocessore d-Mc8,


configurato con 32 Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in figura.
Il porto parallelo di ingresso PULSES (indirizzo 20h) permette di leggere, tramite le linee W7 e W0, le
uscite di due ruote tachimetriche. Ogni ruota tachimetrica costituita da un disco forato, solidale con
la rotazione di un asse meccanico, e da un sensore ottico. Il sensore ottico in grado di vedere il
passaggio di 32 fori, posizionati in modo regolare lungo il bordo del disco (la figura indicativa).
Quando il disco ruota, il sensore genera
unalternanza di impulsi: 32 impulsi
indicano, ovviamente, che il disco ha
compiuto una rotazione completa.
Il porto parallelo di uscita SEROUT
(indirizzo 22h) collega il nostro sistema
con il resto dellimpianto industriale,
attraverso la linea seriale asincrona
SER.
Un
dispositivo
hardware
di
temporizzazione (Timer) attiva ogni 10
mS la linea di richiesta di interrupt INT
del processore. La risposta del
processore
sulluscita
INTA ,
allaccettazione
della
interruzione,
disattiva in modo automatico la linea
INT .
Si chiede di scrivere, in linguaggio
assembly, il programma di gestione del
sistema, rispettando le specifiche
riportate qui di seguito.
Il sistema, nel programma principale,
controlla continuamente, in parallelo, i
sensori delle due ruote tachimetriche.
Ogni volta che uno dei sensori presenta
un fronte di salita, incrementa il
corrispondente conteggio degli impulsi.
ll programma di interruzione si occupa, ogni minuto primo, di valutare la media delle velocit delle
due ruote, in termini di rotazioni al minuto. La media delle velocit deve essere calcolata su 8 bit,
arrotondata allunit. Il valore cos calcolato viene poi serializzato bit a bit sulla linea SER del porto
parallelo SEROUT (bit 0).
Il protocollo di trasmissione seriale, di tipo asincrono, prevede una velocit di trasmissione di 100 bit per
secondo (tempo di bit pari a 10 mS). Il pacchetto di trasmissione seriale prevede, nellordine, la
emissione di un bit di start a 1, gli 8 bit del dato (con l MSB trasmesso per primo), e un bit di stop a
0 (vedi figura). La serializzazione dei bit viene temporizzata dal programma dinterruzione senza
limpiego di routine di ritardo.
Note:
o Il programma deve essere eseguito automaticamente al RESET del sistema.
o Come sopra precisato, i sensori vedono 32 impulsi per ogni rotazione completa, ma la media delle velocit,
arrotondata allunit, deve essere data in termini di rotazioni al minuto.
o Si supponga che la velocit di rotazione massima delle ruote corrisponda a circa 120 rotazioni al minuto.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-18

11.2.7

Conteggio di oggetti prodotti (con visualizzazione in binario)

PI050125

Si consideri disponibile un sistema di controllo industriale, basato sul microprocessore d-Mc8,


configurato con 32 Kbytes di ROM, 32 Kbytes di RAM, e i dispositivi di I/O rappresentati in figura.
Il sistema permette di monitorare i pezzi in
uscita da quattro presse meccaniche che
producono bulloni di ferro.
Il porto parallelo di ingresso TRACKS
(allindirizzo 00h) permette di leggere sui bit
S6, S4, S2 e S0 le uscite di quattro sensori
magnetici posizionati sulluscita delle
presse.
I due porti paralleli di uscita HIGH e LOW
(indirizzi
05h
e
06h)
pilotano
complessivamente una fila di 16 lampadine,
poste su di un pannello.
Un dispositivo hardware di temporizzazione
(Timer) attiva ogni 10 mS la linea di
richiesta di interrupt INT del processore. La
risposta del processore sulluscita INTA ,
allaccettazione della interruzione, disattiva
in automatico la linea INT .
Si chiede di scrivere, in linguaggio
assembly, il programma del sistema di
controllo, in base alle specifiche qui
riportate.
Il sistema, nel programma principale,
controlla continuamente i quattro sensori.
Ogni volta che il sistema rivela il passaggio
di un pezzo su di un sensore, incrementa il
conto dei bulloni prodotti dalla pressa
relativa a quel sensore.
Mediante il programma di interruzione, ogni 5 secondi il sistema aggiorna sulle 16 lampadine, in binario,
il numero complessivo di pezzi contati in tale intervallo di tempo. La parte bassa del conteggio
riportata sul porto LOW, quella alta sul porto HIGH.
Per richiamare lattenzione delloperatore, se una delle presse non ha prodotto pezzi nellintervallo di
tempo considerato, le lampadine sono attivate lampeggianti (accese per 250 mS, spente per 250 mS).
Note:

o
o

Il programma deve essere eseguito automaticamente al RESET del sistema.


Si faccia lipotesi che il numero di pezzi prodotti in 5 secondi da ciascuna pressa sia al massimo
di 90. Un pezzo si considera transitato quando viene rivelato un fronte di salita del segnale
uscente dal relativo sensore.

Suggerimento:

Conviene contare il tempo in sotto-intervalli di 250 mS (10 mS x j = 250mS; 250mS x k = 5 S).

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-19

11.2.8

Conteggio di oggetti (con trasmissione seriale a comando)

PI060123

Si consideri disponibile un piccolo sistema


di controllo, basato sul microprocessore dMc8, configurato con 32 Kbytes di ROM, 32
Kbytes di RAM, e i dispositivi di I/O
rappresentati in figura.
Il sistema permette di monitorare i pezzi in
uscita da due torni automatici che
producono aste filettate.
Il porto parallelo di ingresso INPUTS
(allindirizzo 12h) permette di leggere sui bit
S1 e S0 le uscite dei due sensori magnetici
posizionati sulluscita delle unit di
produzione. Il porto suddetto legge anche lo
stato di un pulsante, sulla linea S7.
Il porto parallelo di uscita SEROUT
(indirizzo 32h) collega il nostro sistema con
lunit di gioco, attraverso la linea seriale
asincrona SER (collegata sul bit 7).
Un dispositivo hardware di temporizzazione
(Timer) attiva ogni 30 mS la linea di
interrupt
INT
del
processore.
Laccettazione della interruzione da parte
del processore, segnalata sulluscita INTA ,
disattiva la linea INT .
Si chiede di scrivere, in linguaggio
assembly, il programma di gestione
dellinterfaccia di gioco, rispettando le
specifiche riportate qui di seguito.
Il sistema, nel programma principale, controlla continuamente i due sensori. Ogni volta che il sistema
rivela il passaggio di un pezzo su di un sensore, ne incrementa il relativo conteggio.
Il programma di interruzione si occupa di alcuni compiti:
1) Ogni due minuti salva il valore dei conteggi effettuati dal programma principale sui sensori e li
reinizializza.
2) Esegue la lettura del pulsante, che si suppone esente da rimbalzi meccanici ( gi filtrato da un
dispositivo locale). Ogni volta che il pulsante viene premuto, calcola la somma dei conteggi salvati.
Il valore ottenuto, calcolato su 16 bit, viene poi inviato in modo seriale, bit a bit, sulla linea SER del
porto parallelo SEROUT (bit 7).
Il protocollo di trasmissione seriale, di tipo asincrono, prevede un tempo di bit pari a 30 mS. Il pacchetto
composto da un bit di start a 1, seguito dai 16 bit del dato (con l MSB trasmesso per primo), e
infine un bit di stop a 0 (vedi figura). La serializzazione temporizzata dal programma di interruzione,
senza impiego di routine di ritardo, in modo tale da non interrompere la lettura dei sensori durante la
trasmissione del dato.
Note:

o
o
o
o

Il programma deve essere eseguito automaticamente al RESET del sistema.


Si faccia lipotesi che il numero di pezzi prodotti in un secondo da ciascuna unit sia al massimo
di quattro.
Un pezzo si considera transitato quando viene rivelato un fronte di salita del segnale uscente
dal relativo sensore.
Il pulsante si considera premuto quando la sua uscita presenta un fronte di salita.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-20

11.2.9

Conteggio di oggetti (con trasmissione seriale automatica)

PI070710

Si consideri disponibile un piccolo


sistema di controllo, basato sul
microprocessore DMC8, configurato
con 32 Kbytes di ROM, 32 Kbytes di
RAM, e i dispositivi di I/O rappresentati
in figura. Il sistema esegue controlli
periodici sulle uscite di quattro presse
meccaniche.
Il porto parallelo di ingresso INPUTS
(allindirizzo 80h) permette di leggere
sui bit S7, S6, S5 e S4 le uscite di quattro
sensori A, B, C e D (posizionati
sulluscita delle unit di produzione).
Il porto parallelo di uscita SEROUT
(indirizzo 81h) collega il nostro sistema
con la sala di controllo dell'impianto,
attraverso la linea seriale asincrona
SER (collegata sul bit 7).
Un
dispositivo
hardware
di
temporizzazione (Timer) attiva ogni 10
mS la linea di interrupt INT del
processore.
Laccettazione
della
interruzione da parte del processore,
segnalata sulluscita INTA , disattiva la
linea INT .
Si chiede di scrivere, in linguaggio
assembly, il programma di gestione del
sistema, rispettando le specifiche
riportate qui di seguito.
Il sistema, nel programma principale, controlla continuamente i quattro sensori: ogni volta che il
sistema rivela il passaggio di un pezzo su di un sensore (al fronte di salita del segnale), ne incrementa
il relativo conteggio.
Il programma di interruzione si occupa della trasmissione, alla sala di controllo dell'impianto, ogni 10
secondi, della somma dei 4 conteggi, espressa su 16 bit.
La somma dei conteggi inviata sotto forma di pacchetto composto da un bit di start a 1, dai 16 bit
di informazione e da un bit di stop a '0'. L'MSB del byte trasmesso per primo, ed il tempo di bit
pari a 10 mS. La serializzazione temporizzata dal programma di interruzione stesso, senza impiego di
routine di ritardo, in modo tale da non interrompere la lettura dei sensori durante la trasmissione del
dato.
Note:

o
o
o

Il programma deve essere eseguito automaticamente al RESET del sistema.


Si faccia lipotesi che il numero di pezzi prodotti in 10 secondi da ciascuna unit sia al massimo
di 200.
I conteggi, dopo essere stati rilevati per calcolarne e trasmetterne la somma, sono azzerati.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-21

11.2.10

Telecomando per sintonizzatore radio

PI080613

In figura rappresentato lhardware


di un telecomando per
un
sintonizzatore radio, basato sul
microprocessore DMC8.
Il porto parallelo di ingresso
BUTTONS (indirizzo 00h) permette
di leggere, tramite le linee P7P0, gli
otto
pulsanti
a
disposizione
dell'utente (volume, toni alti, toni
bassi, cambio canale).
Il porto parallelo di uscita TXOUT
(indirizzo 01h) pilota il trasmettitore a
raggi infrarossi (non rappresentato in
fugura), attraverso la linea seriale
asincrona TX, collegata al bit 7.
Il Timer attiva ogni 2 mS la linea di
richiesta di interrupt INT del
processore. L'accettazione INTA
della interruzione, da parte del
processore, disattiva in
modo
automatico la linea INT .
Si chiede di scrivere, in linguaggio assembly, il programma di gestione del sistema, rispettando le
specifiche riportate qui di seguito.
Ai fini del progetto, il programma principale non esegue operazioni significative per la nostra
interfaccia, salvo la necessaria inizializzazione del sistema al RESET hardware. Subito dopo, il
programma principale entra in un ciclo infinito nel quale non fa nulla, delegando il controllo del sistema
al programma di interruzione.
Specifiche del programma di interruzione:
-

Il programma di interruzione esegue la lettura dei pulsanti, effettuando un controllo antirimbalzo


sullo stato degli stessi. I pulsanti sono esaminati ogni 128 mS, e il controllo antirimbalzo consiste
nel verificare che la configurazione letta sul porto sia identica a quella letta la volta prima
(quando questo verificato, lo stato dei pulsanti convalidato).

Se almeno un pulsante premuto, la nuova configurazione, codificata su 6 bit (C5..C0) secondo


la tabella qui riportata, predisposta per essere inviata in formato seriale sulla linea TX (al
trasmettitore a raggi infrarossi). La codifica "a priorit": se l'utente preme per sbaglio pi
pulsanti insieme, ne viene considerato uno solo, come indicato nella tabella seguente:
P7
1
0
0
0
0
0
0
0
0

P6
1
0
0
0
0
0
0
0

P5
1
0
0
0
0
0
0

P4
1
0
0
0
0
0

P3
1
0
0
0
0

P2
1
0
0
0

P1
1
0
0

P0
1
0

C5
0
0
0
0
0
0
0
0
0

C4
1
1
1
1
1
1
1
1
0

C3
0
0
0
0
0
0
0
0
0

C2
1
1
1
1
0
0
0
0
0

C1
1
1
0
0
1
1
0
0
0

C0
1
0
1
0
1
0
1
0
0

Se nessun tasto premuto, il sistema non invia alcun codice. Inoltre, non deve essere controllato
se il tasto attualmente premuto uguale o diverso dal precedente: se un tasto mantenuto
premuto, il suo codice sar continuamente re-inviato.

Il programma di interruzione effettua la trasmissione dei bit sulla linea TX, seguendo un
protocollo di trasmissione seriale asincrono (un bit di start; 6 bit di dato, nellordine C5..C0; un
bit di stop). Si presti attenzione al tempo di bit, pari a 8 mS .

Nota: Il programma principale deve essere eseguito automaticamente al RESET del sistema;
La trasmissione dei bit deve essere effettuata senza limpiego di routine di ritardo.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-22

11.2.11

Ascensore

PI080714
Un sistema basato sul microprocessore d-Mc8
controlla lascensore di un palazzo di 7 piani (oltre al
piano terra). Nella cabina dellascensore montato
un pannello con 8 pulsanti (piano terra, piano 1,
piano 2 piano 7); inoltre, ad ogni piano presente
un pulsante di chiamata.
Come si osserva in figura, la pulsantiera della cabina
connessa al porto di ingresso CAB (indirizzo 16h). I
pulsanti T, 1, 2, 3, 4, 5, 6 e 7 sono collegati
rispettivamente ai bit P0, P1, P2, P3, P4, P5, P6 e P7
del porto.
Gli 8 pulsanti di chiamata dei piani sono collegati al
porto di ingresso CALL (indirizzo 19h), ai bit C0, C1,
C2, C3, C4, C5, C6 e C7. Tutti i pulsanti, se premuti,
generano un livello alto.
Il porto di ingresso FLR (indirizzo 11h) legge un
codificatore di posizione, che consente di sapere
dove si trova lascensore. La codifica a quattro bit
della posizione (F3F2F1F0) riportata nella tabella qui
sotto.
Il porto di uscita MTR (indirizzo 62h) consente di
attivare il motore di elevazione: il dispositivo di
potenza che controlla il motore riceve due bit di
comando: ON (bit 4: se a 1, accende il motore), e
UP (bit 5: se a 1 fa girare il motore in salita, se 0 in
discesa).
Un Timer attiva ogni 40 mS la linea di richiesta di
interrupt INT del processore: allaccettazione della
interruzione, la risposta del processore INTA
disattiva in modo automatico la linea INT .

Si chiede di scrivere, in linguaggio assembly, il


programma di controllo dellascensore, seguendo le
specifiche qui riportate.
Posizione cabina
7 piano (alla porta)
Tra il 6 e il 7 piano
6 piano (alla porta)
Tra il 5 e il 6 piano
5 piano (alla porta)
Tra il 4 e il 5 piano
4 piano (alla porta)
Tra il 3 e il 4 piano
3 piano (alla porta)
Tra il 2 e il 3 piano
2 piano (alla porta)
Tra il 1 e il 2 piano
1 piano (alla porta)
tra Terra e il 1 piano
Terra (alla porta)

F3F2F1F0

1
1
1
1
1
1
1
0
0
0
0
0
0
0
0

Codice di posizione

1
1
1
0
0
0
0
1
1
1
1
0
0
0
0

1
0
0
1
1
0
0
1
1
0
0
1
1
0
0

0
1
0
1
0
1
0
1
0
1
0
1
0
1
0

Il sistema, nel programma di interruzione, acquisisce sia lo


stato della pulsantiera della cabina che dei pulsanti presenti ai
singoli piani. Per evitare il fenomeno dei rimbalzi meccanici
dei pulsanti, il loro stato deve essere convalidato da due
letture consecutive, distanti tra loro 40 mS.
La routine del programma di interruzione si occupa anche di
codificare la richiesta (usando i codici di posizione riportati
nella tabella), e di rendere disponibile questo codice al
programma principale nella variabile FLOOR. Se nessun tasto
risulta premuto, la variabile FLOOR non deve essere
aggiornata. Si tenga conto della possibilit che pi pulsanti
possano essere premuti insieme: si consideri prioritaria la
richiesta relativa al piano pi basso e che la pulsantiera della
cabina prevale sui pulsanti di chiamate esterni.
Il programma principale, invece, ha il compito di gestire
lattivazione e la direzione del motore, attuando la richiesta
codificata dal programma di interruzione nella variabile
FLOOR, portando lascensore al piano voluto.

Nota: il programma deve essere attivato automaticamente al RESET hardware del sistema.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-23

11.2.12

Telecomando per amplificatore audio

PI090115

In figura rappresentato lhardware


di un telecomando per
un
amplificatore stereo, basato sul
microprocessore DMC8.
Il porto parallelo di ingresso
BUTTONS (indirizzo 00h) permette
di leggere, tramite le linee P5P0, i
sei pulsanti a disposizione dell'utente
(volume, toni alti, toni bassi).
Il porto parallelo di uscita TXOUT
(indirizzo 01h) pilota il trasmettitore a
raggi infrarossi (non rappresentato in
fugura), attraverso la linea seriale
asincrona TX, collegata al bit 7.
Il Timer attiva ogni 2 mS la linea di
richiesta di interrupt INT del
processore. L'accettazione INTA
della interruzione, da parte del
processore, disattiva in modo
automatico la linea INT .
Si chiede di scrivere, in linguaggio assembly, il programma di gestione del sistema, rispettando le
specifiche riportate qui di seguito.
Ai fini del progetto, il programma principale non esegue operazioni significative per la nostra
interfaccia, salvo la necessaria inizializzazione del sistema al RESET hardware. Subito dopo, il
programma principale entra in un ciclo infinito nel quale non fa nulla, delegando il controllo del sistema
al programma di interruzione.
Specifiche del programma di interruzione:
-

Il programma di interruzione esegue la lettura dei pulsanti, effettuando un controllo antirimbalzo


sullo stato degli stessi. I pulsanti sono esaminati ogni 32 mS, e il controllo antirimbalzo consiste
nel verificare che la configurazione letta sul porto sia identica a quella letta le due volte
precedenti (32 e 64 mS prima): quando questo verificato, lo stato dei pulsanti convalidato.

Se almeno un pulsante premuto, la nuova configurazione dei pulsanti, senza nessuna


operazione di codifica, predisposta per essere inviata in formato seriale sulla linea TX (al
trasmettitore a raggi infrarossi). Se nessun tasto premuto, il sistema non invia alcun codice.
Inoltre, non deve essere controllato se il tasto attualmente premuto uguale o diverso dal
precedente: se un tasto mantenuto premuto, il suo codice sar re-inviato (ad ogni convalida,
ogni 32 mS).

Il programma di interruzione effettua anche la trasmissione dei bit sulla linea TX, seguendo un
protocollo di trasmissione seriale asincrono (con tempo di bit pari a 4 mS):
-

1 bit di start;
6 bit di dato, nellordine i bit [Vol +], [Vol -], [High +], [High -], [Low +], [Low -];
1 bit di stop).

Nota: Il programma principale deve essere eseguito automaticamente al RESET del sistema;
La trasmissione dei bit deve essere effettuata senza limpiego di routine di ritardo.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11-24

12. Appendice: tabelle delle istruzioni DMC8


12.1

Tabelle delle Istruzioni DMC8


Le tabelle seguenti mostrano le istruzioni del DMC8 e riassumomo schematicamente i dettagli
riguardanti la loro esecuzione. Partendo da sinistra, questo il significato delle colonne:
Il codice mnemonico Assembly dellistruzione;
Loperazione che svolge rappresentata in modo simbolico;
Gli indicatori (flags) interessati dallesecuzione dellistruzione;
Il codice operativo in binario e, subito a destra, in esadecimale (Hex);
Il numero di byte di cui e` composta listruzione;
Il numero di cicli macchina della istruzione;
Il numero di cicli di clock necessari per lesecuzione dellistruzione;
Eventuali commenti.

Mnemonic:
Symbolic Operation:
Flags:
Opcode:
Bytes:
M Cycles:
Clock Cycles:
Comments:

12.1.1 Istruzioni di Caricamento a 8 bit


Mnemonic
LD r, r

Symbolic
Operation
r r

LD r, n

rn

LD r, (HL)

r (HL)

LD r, (IX + d)

r (IX + d)

LD r, (IY + d)

r (IY + d)

LD (HL), r

(HL) r

LD (IX + d), r

(IX + d) r

LD (IY + d), r

(IY + d) r

LD (HL), n

(HL) n

LD (IX + d), n

(IX + d) n

LD (IY + d), n

(IY + d) n

LD A, (BC)

A (BC)

LD A, (DE)

A (DE)

LD A, (nn)

A (nn)

LD (BC), A

(BC) A

LD (DE), A

(DE) A

LD (nn), A

(nn) A

Notes:
Flag Notation:

Flags
H P/V N

Opcode
76 543 210
01 r
r

Hex

00 r 110
n
01 r 110

Bytes
1

M
Cycles
1

Clock
Cycles
4

11 011 101
01 r 110
d
11 111 101
01 r 110
d
01 110 r

DD

19

FD

19

DD

19

FD

19

36

10

DD
36

19

FD
36

19

11 011 101
01 110 r
d
11 111 101
01 110 r
d
00 110 110
n
11 011 101
00 110 110
d
n
11 111 101
00 110 110
d
n
00 001 010

0A

00 011 010

1A

010

010

3A

13

00 111
n
n
00 000

02

00 010 010

12

00 110 010
n
n

32

13

Comments
r, r
000
001
010
011
100
101
111

Reg.
B
C
D
E
H
L
A

r, r means any of the registers A, B, C, D, E, H, L.


= flag is not affected.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.2 Istruzioni di Caricamento a 16 bit


Mnemonic
LD dd, nn

Symbolic
Operation
dd nn

LD IX, nn

IX nn

LD IY, nn

IY nn

LD HL, (nn)

L (nn)
H (nn+1)

LD dd, (nn)

ddL (nn)
ddH (nn+1)

LD IX, (nn)

IXL (nn)
IXH (nn+1)

LD IY, (nn)

IYL (nn)
IYH (nn+1)

LD (nn), HL

(nn) L
(nn+1) H

LD (nn), dd

(nn) ddL
(nn+1) ddH

LD (nn), IX

(nn) IXL
(nn+1) IXH

LD (nn), IY

(nn) IYL
(nn+1) IYH

LD SP, HL

SP HL

LD SP, IX

SP IX

LD SP, IY

SP IY

Notes:
Flag Notation:

Flags
H P/V N

(prima parte)
Opcode
76 543 210
00 dd0 001
n
n
11 011 101
00 100 001
n
n
11 111 101
00 100 001
n
n
00 101 010
n
n
11 101 101
01 dd1 011
n
n
11 011 101
00 101 010
n
n
11 111 101
00 101 010
n
n
00 100 010
n
n
11 101 101
01 dd0 011
n
n
11 011 101
00 100 010
n
n
11 111 101
00 100 010
n
n
11 111 001
11 011 101
11 111 001
11 111 101
11 111 001

Hex

Bytes
3

M
Cycles
3

Clock
Cycles
10

DD
21

14

FD
21

14

2A

16

ED

20

DD
2A

20

FD
2A

20

22

16

DD

20

DD
22

20

FD
22

20

F9

DD
F9
FD
F9

10

10

Comments
dd Pair
00 BC
01 DE
10 HL
11 SP

dd is any of the register pair BC, DE, HL, SP.


qq is any of the register pair BC, DE, HL, AF.
= flag is not affected.

(continua)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.3 Istruzioni di Caricamento a 16 bit


Mnemonic
PUSH qq

PUSH IX

PUSH IY

POP qq

POP IX

POP IY

Notes:
Flag Notation:

Symbolic
Operation
SP SP - 1
(SP) qqH
SP SP - 1
(SP) qqL
SP SP - 1
(SP) IXH
SP SP - 1
(SP) IXL
SP SP - 1
(SP) IYH
SP SP - 1
(SP) IYL
qqL (SP)
SP SP + 1
qqH (SP)
SP SP + 1
IXL (SP)
SP SP + 1
IXH (SP)
SP SP + 1
IYL (SP)
SP SP + 1
IYH (SP)
SP SP + 1

Flags
H P/V N

(seconda parte)
Opcode
76 543 210
11 qq0 101

Hex

Bytes
1

M
Cycles
3

Clock
Cycles
11

11 011 101
11 100 101

DD
E5

15

11 111 101
11 100 101

FD
E5

15

11 qq0 001

10

11 011 101
11 100 001

DD
E1

14

11 111 101
11 100 001

FD
E1

14

Comments
qq Pair
00 BC
01 DE
10 HL
11

AF

dd is any of the register pair BC, DE, HL, SP.


qq is any of the register pair BC, DE, HL, AF.
= flag is not affected.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.4 Istruzioni Aritmetiche e Logiche a 8 bit


Mnemonic

Symbolic
Operation

ADD A, r

AA+r

10 000 r

ADD A, n

AA+n

ADD A, (HL)

A A + (HL)

11 000 110
n
10 000 110

ADD A, (IX + d)

A A + (IX + d)

ADD A, (IY + d)

A A + (IY + d)

ADC A, r

A A + r + CY

ADC A, n

A A + n + CY

ADC A, (HL)

A A + (HL) + CY

ADC A, (IX + d)

A A + (IX + d)+CY

ADC A, (IY + d)

A A + (IY + d)+CY

SUB r

AA-r

SUB n

AA-n

SUB (HL)

A A - (HL)

SUB (IX + d)

A A - (IX + d)

SUB (IY + d)

A A - (IY + d)

SBC A, r

A A - r - CY

SBC A, n

A A - n - CY

SBC A, (HL)

A A - (HL) - CY

SBC A, (IX + d)

A A - (IX + d)-CY

SBC A, (IY + d)

A A - (IY + d)-CY

CP r

A-r

CP n

A-n

CP (HL)

A - (HL)

CP (IX + d)

A - (IX + d)

CP (IY + d)

A - (IY + d)

Notes:

The V symbol in the P/V flag column indicates that the P/V flag contains the overflow of the operation.
Similarly the P symbol indicates parity.
r means any of the registers A, B, C, D, E, H, L.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

Flag Notation:

Flags
H P/V N

(prima parte)

Opcode
76 543 210

11 011 101
10 000 110
d
11 111 101
10 000 110
d
10 001 r

M
Cycles

Clock
Cycles

DD

19

FD

19

DD

19

FD

19

DD

19

FD

19

DD

19

FD

19

DD

19

FD

19

Hex

11 001 110
n
10 001 110
11 011 101
10 001 110
d
11 111 101
10 001 110
d
10 010 r
11 010 110
n
10 010 110
11 011 101
10 010 110
d
11 111 101
10 010 110
d
10 011 r
11 011 110
n
10 011 110
11 011 101
10 011 110
d
11 111 101
10 011 110
d
10 111 r
11 111 110
n
10 111 110
11 011 101
10 111 110
d
11 111 101
10 111 110
d

Byte
s
1

Comments

r
000
001
010
011
100
101
111

Reg..
B
C
D
E
H
L
A

(continua)
Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.5 Istruzioni Aritmetiche e Logiche a 8 bit

Mnemonic

Symbolic
Operation

AND r

A A and r

10 100 r

AND n

A A and n

AND (HL)

A A and (HL)

11 100 110
n
10 100 110

AND (IX + d)

A A and (IX+d)

AND (IY + d)

A A and (IY+d)

OR r

A A or r

OR n

A A or n

OR (HL)

A A or (HL)

OR (IX + d)

A A or (IX+d)

OR (IY + d)

A A or (IY+d)

XOR r

A A xor r

XOR n

A A xor n

XOR (HL)

A A xor (HL)

XOR (IX + d)

A A xor (IX+d)

XOR (IY + d)

A A xor (IY+d)

INC r

rr+1

11 011 101
10 101 110
d
11 111 101
10 101 110
d
00 r 100

INC (HL)

(HL) (HL) + 1

00 110 100

INC (IX + d)

(IX + d) (IX + d) + 1

INC (IY + d)

(IY + d) (IY + d) + 1

DEC r

rr1

11 011 101
00 110 100
d
11 111 101
00 110 100
d
00 r 101

DEC (HL)

(HL) (HL) - 1

00 110 101

DEC (IX + d)

(IX + d) (IX + d) - 1

DEC (IY + d)

(IY + d) (IY + d) - 1

11 011 101
00 110 101
d
11 111 101
00 110 101
d

CPL

_
AA

NEG

_
AA +1

Notes:

Flag Notation:

Flags
H P/V N

(seconda parte)

Opcode
76 543 210

M
Cycles

Clock
Cycles

DD

19

FD

19

DD

19

FD

19

DD

19

FD

19

11

DD

23

FD

23

11

DD

23

FD

23

00 101 111

2F

Ones
complement.

11 101 101
01 000 100

ED
44

Twos
complement.

11 011 101
10 100 110
d
11 111 101
10 100 110
d
10 110 r

Hex

11 110 110
n
10 110 110
11 011 101
10 110 110
d
11 111 101
10 110 110
d
10 101 r
11 101 110
n
10 101 110

Byte
s
1

Comments

r
000
001
010
011
100
101
111

Reg..
B
C
D
E
H
L
A

The V symbol in the P/V flag column indicates that the P/V flag contains the overflow of the operation.
Similarly the P symbol indicates parity.
r means any of the registers A, B, C, D, E, H, L.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.6 Istruzioni Aritmetiche a 16 bit


Mnemonic
ADD HL, ss
ADC HL, ss
SBC HL, ss
ADD IX, pp

Symbolic
Operation
HL HL + ss
HL HL + ss
+ CY
HL HL ss
CY
IX IX + pp

Flags
H P/V N
2
0

ADD IY, rr

IY IY + rr

INC ss

ss ss + 1

INC IX

IX IX + 1

INC IY

IY IY + 1

DEC ss

C
1

Opcode
76 543 210
00 ss1 001

Hex

Bytes
1

M
Cycles
3

Clock
Cycles
11

11 101 101
01 ss1 010
11 101 101
01 ss0 010
11 011 101
00 pp1 001
11 111 101
00 rr1 001
00 ss0 011

ED

15

ED

15

DD

15

FD

15

11 011 101
00 100 011
11 111 101
00 100 011
00 ss1 011

DD
23
FD
23

10

10

11 011 101
00 101 011
11 111 101
00 101 011

DD
2B
FD
2B

10

10

Comments
ss
00
01
10
11

Reg.
BC
DE
HL
SP

pp
00
01
10
11

Reg.
BC
DE
IX
SP

rr
00
01
10
11

Reg.
BC
DE
IY
SP

ss ss - 1

DEC IX

IX IX - 1

DEC IY

IY IY - 1

Notes:

The V symbol in the P/V flag column indicates that the P/V flag contains the overflow of the operation.
Ss means any of the registers BC, DE, HL, SP.
Pp means any of the registers BC, DE, IX, SP.
Rr means any of the registers BC, DE, IY, SP.
16 bit additions are performed by first adding the two low order eight bits, and then the two high order eight bits.
1
Indicates the flag is affected by the 16 bit result of the operation.
2
Indicates the flag is affected by the 8 bit addition of the high order eight bits.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

Flag Notation:

12.1.7 Istruzioni di controllo della CPU

CCF

Symbolic
Operation
__
CY CY

SCF

CY 1

00 110 111

37

NOP

No Operation

00 000 000

00

HALT

CPU halted

01 110 110

76

IFF 0

11 110 011

F3

IFF 1

11 111 011

FB

Mnemonic

DI
EI

Notes:

Flag Notation:

Flags
H P/V N

Opcode
76 543 210

Hex

Bytes

M
Cycles

Clock
Cycles

00 111 111

3F

Comments
Complement
carry flag.

The V symbol in the P/V flag column indicates that the P/V flag contains the overflow of the operation.
Similarly the P symbol indicates parity.
1
No interrupts are issued directly after a DI or EI.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set, X = flag is dont care,
= flag is set according to the result of the operation.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.8 Istruzioni di Salto (Jump)


Mnemonic
JP nn

Symbolic
Operation
PC nn

Flags
H P/V N

Opcode
76 543 210
11 000 011
n
n
11 cc 010
n
n

Hex
C3

Bytes
3

M
Cycles
3

Clock
Cycles
10

10

JP cc, nn

if cc is true,
PC nn

JP ( HL )

PC HL

11 101 001

E9

JP ( IX )

PC IX

PC IY

DD
E9
FD
E9

JP ( IY )

11 011 101
11 101 001
11 111 101
11 101 001

Notes:
Flag Notation:

= flag is not affected.

Comments

cc
Condition
000 NZ non zero
001 Z zero
010 NC non carry
011 C carry
100 PO parity odd
101 PE parity even
110 P sign positive
111 M sign
negative

12.1.9 Istruzioni di Chiamata e Ritorno da sottoprogrammi (Call e Return)


Mnemonic
CALL nn

CALL cc, nn

RET

RET cc

RST p

Notes:
Flag Notation:

Symbolic
Operation
SP SP - 1
(SP) PCH
SP SP - 1
(SP) PCL
PC nn
if cc is true,
SP SP - 1
(SP) PCH
SP SP - 1
(SP) PCL
PC nn

Flags
H P/V N

Opcode
76 543 210
11 001 101
n
n

Bytes
3

M
Cycles
5

Clock
Cycles
17

Comments

11 ccc 100
n
n

3
3

3
5

10
17

if cc is false
if cc is true

PCL (SP)
SP SP + 1
PCH (SP)
SP SP + 1
if cc is true,
PCL (SP)
SP SP + 1
PCH (SP)
SP SP + 1

11 001 001

10

11 ccc 000

1
1

1
3

5
11

if cc is false
if cc is true

SP SP - 1
(SP) PCH
SP SP - 1
(SP) PCL
PC p

11 t 111

11

__t
000
001
010
011
100
101
110
111

Hex
CD

C9

_ p
0000h
0008h
0010h
0018h
0020h
0028h
0030h
0038h

= flag is not affected.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.10

Istruzioni di Rotazione e di Scalamento


S

Flags
H P/V N
0 0

Opcode
76 543 210
00 000 111

Hex
07

Bytes
1

M
Cycles
1

Clock
Cycles
4

RLA

00 010 111

17

RRCA

00 001 111

0F

RRA

00 011 111

1F

RLC r

CB

RLC (HL)

CB

15

RLC (IX + d)

DD
CB

23

RLC (IY + d)

FD
CB

23

RL r

CB

RL (HL)

CB

15

RL (IX + d)

DD
CB

23

RL (IY + d)

FD
CB

23

RRC r

CB

RRC (HL)

CB

15

RRC (IX + d)

DD
CB

23

RRC (IY + d)

FD
CB

23

RR r

CB

RR (HL)

CB

15

RR (IX + d)

DD
CB

23

RR (IY + d)

FD
CB

23

RLD

11 001 011
00 000 r
11 001 011
00 000 110
11 011 101
11 001 011
d
00 000 110
11 111 101
11 001 011
d
00 000 110
11 001 011
00 010 r
11 001 011
00 010 110
11 011 101
11 001 011
d
00 010 110
11 111 101
11 001 011
d
00 010 110
11 001 011
00 001 r
11 001 011
00 001 110
11 011 101
11 001 011
d
00 001 110
11 111 101
11 001 011
d
00 001 110
11 001 011
00 011 r
11 001 011
00 011 110
11 011 101
11 001 011
d
00 011 110
11 111 101
11 001 011
d
00 011 110
11 101 101
01 101 111

ED
6F

18

RRD

11 101 101
01 100 111

ED
67

18

Mnemonic
RLCA

Notes:

Flag Notation:

Symbolic
Operation

(prima parte)
Comments

r
000
001
010
011
100
101
111

Reg.
B
C
D
E
H
L
A

The P symbol in the P/V flag column indicates that the P/V flag contains the parity of the result.
r means any of the registers A, B, C, D, E, H, L.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

(continua)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.11

Istruzioni di Rotazione e di Scalamento


S

Flags
H P/V N
0 P 0

SLA (HL)

SLA (IX + d)

SLA (IY + d)

SRA r

SRA (HL)

SRA (IX + d)

SRA (IY + d)

SRL r

SRL (HL)

SRL (IX + d)

SRL (IY + d)

Mnemonic
SLA r

Notes:

Flag Notation:

Symbolic
Operation

Opcode
76 543 210
11 001 011
00 100 r
11 001 011
00 100 110
11 011 101
11 001 011
d
00 100 110
11 111 101
11 001 011
d
00 100 110
11 001 011
00 101 r
11 001 011
00 101 110
11 011 101
11 001 011
d
00 101 110
11 111 101
11 001 011
d
00 101 110
11 001 011
00 111 r
11 001 011
00 111 110
11 011 101
11 001 011
d
00 111 110
11 111 101
11 001 011
d
00 111 110

(seconda parte)

Hex
CB

Bytes
2

M
Cycles
2

Clock
Cycles
8

CB

15

DD
CB

23

FD
CB

23

CB

CB

15

DD
CB

23

FD
CB

23

CB

CB

15

DD
CB

23

FD
CB

23

Comments
r
Reg.
000 B
001 C
010 D
011 E
100 H
101 L
111 A

The P symbol in the P/V flag column indicates that the P/V flag contains the parity of the result.
r means any of the registers A, B, C, D, E, H, L.
CY means the carry flip-flop.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

12.1.12

Istruzioni di manipolazione del Bit

Mnemonic
BIT b, r
BIT b, (HL)
BIT b, (IX + d)

Symbolic
Operation
_
Z rb
___
Z (HL)b
_____
Z (IX+ d)b

S
X

Flags
H P/V N
1 X 0

Opcode
76 543 210
11 001 011
01 b r
11 001 011
01 b 110
11 011 101
11 001 011
d
01 b 110
11 111 101
11 001 011
d
01 b 110
11 001 011
11 b r
11 001 011
11 b 110
11 011 101
11 001 011
d
11 b 110
11 111 101
11 001 011
d
11 b 110
11 001 011
10 b r
11 001 011
10 b 110
11 011 101
11 001 011
d
10 b 110
11 111 101
11 001 011
d
10 b 110

Hex
CB

Bytes
2

M
Cycles
2

Clock
Cycles
8

CB

12

DD
CB

20

FD
CB

20

CB

CB

15

DD
CB

23

FD
CB

23

CB

CB

15

DD
CB

23

FD
CB

23

BIT b, (IY + d)

_____
Z (IY+ d)b

SET b, r

rb 1

SET b, (HL)

(HL)b 1

SET b, (IX + d)

(IX+ d)b 1

SET b, (IY + d)

(IY+ d)b 1

RES b, r

rb 0

RES b, (HL)

(HL)b 0

RES b, (IX + d)

(IX+ d)b 0

RES b, (IY + d)

(IY+ d)b 0

Notes:

The notation mb indicates bit b (0 to 7) of location m.


BIT instructions are performed by an bitwise AND.
= flag is not affected, 0 = flag is reset, 1 = flag is set, X = flag is dont care,
= flag is set according to the result of the operation.

Flag Notation:

12.1.13

Comments
r
Reg.
000 B
001 C
010 D
011 E
100 H
101 L
111 A

b
000
001
010
011
100
101
110
111

Bit.
0
1
2
3
4
5
6
7

Istruzioni di Ingresso / Uscita (Input / Output)

Mnemonic
IN A, (n)

Symbolic
Operation
A (n)

Flags
H P/V N

IN r, (C)

r (C)

OUT (n), A

(n) A

OUT (C), r

(C) r

Notes:

The V symbol in the P/V flag column indicates that the P/V flag contains the overflow of the operation.
Similarly the P symbol indicates parity.
r means any of the registers A, B, C, D, E, H, L.
= flag is not affected, 0 = flag is reset, 1 = flag is set,
= flag is set according to the result of the operation.

Flag Notation:

Opcode
76 543 210
11 011 011
n
11 101 101
01 r 000
11 010 011
n
11 101 101
01 r 001

Hex
DB

Bytes
2

M
Cycles
3

Clock
Cycles
11

ED

12

D3

11

ED

12

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

Comments
R
Reg.
000 B
001 C
010 D
011 E
100 H
101 L
111 A

10

12.2

Elenco in ordine alfabetico1 delle istruzioni DMC8


8E
DD8E d
FD8E d
8F
88
89
8A
8B
8C
8D
CE n
ED4A
ED5A
ED6A
ED7A
86
DD86 d
FD86 d
87
80
81
82
83
84
85
C6 n
9
19
29
39
DD09
DD19
DD29
DD39
FD09
FD19
FD29
FD39
A6
DDA6 d
FDA6 d
A7
A0
A1
A2
A3
A4
A5
E6 n
CB46
DDCB d 46
FDCB d 46
CB47

ADC A, (HL)
ADC A, (IX + d)
ADC A, (IY + d)
ADC A, A
ADC A, B
ADC A, C
ADC A, D
ADC A, E
ADC A, H
ADC A, L
ADC A, n
ADC HL, BC
ADC HL, DE
ADC HL, HL
ADC HL, SP
ADD A, (HL)
ADD A, (IX + d)
ADD A, (IY + d)
ADD A, A
ADD A, B
ADD A, C
ADD A, D
ADD A, E
ADD A, H
ADD A, L
ADD A, n
ADD HL, BC
ADD HL, DE
ADD HL, HL
ADD HL, SP
ADD IX, BC
ADD IX, DE
ADD IX, IX
ADD IX, SP
ADD IY, BC
ADD IY, DE
ADD IY, IY
ADD IY, SP
AND (HL)
AND (IX + d)
AND (IY + d)
AND A
AND B
AND C
AND D
AND E
AND H
AND L
AND n
BIT 0, (HL)
BIT 0, (IX + d)
BIT 0, (IY + d)
BIT 0, A

CB40
CB41
CB42
CB43
CB44
CB45
CB4E
DDCB d 4E
FDCB d 4E
CB4F
CB48
CB49
CB4A
CB4B
CB4C
CB4D
CB56
DDCB d 56
FDCB d 56
CB57
CB50
CB51
CB52
CB53
CB54
CB55
CB5E
DDCB d 5E
FDCB d 5E
CB5F
CB58
CB59
CB5A
CB5B
CB5C
CB5D
CB66
DDCB d 66
FDCB d 66
CB67
CB60
CB61
CB62
CB63
CB64
CB65
CB6E
DDCB d 6E
FDCB d 6E
CB6F
CB68
CB69
CB6A

BIT 0, B
BIT 0, C
BIT 0, D
BIT 0, E
BIT 0, H
BIT 0, L
BIT 1, (HL)
BIT 1, (IX + d)
BIT 1, (IY + d)
BIT 1, A
BIT 1, B
BIT 1, C
BIT 1, D
BIT 1, E
BIT 1, H
BIT 1, L
BIT 2, (HL)
BIT 2, (IX + d)
BIT 2, (IY + d)
BIT 2, A
BIT 2, B
BIT 2, C
BIT 2, D
BIT 2, E
BIT 2, H
BIT 2, L
BIT 3, (HL)
BIT 3, (IX + d)
BIT 3, (IY + d)
BIT 3, A
BIT 3, B
BIT 3, C
BIT 3, D
BIT 3, E
BIT 3, H
BIT 3, L
BIT 4, (HL)
BIT 4, (IX + d)
BIT 4, (IY + d)
BIT 4, A
BIT 4, B
BIT 4, C
BIT 4, D
BIT 4, E
BIT 4, H
BIT 4, L
BIT 5, (HL)
BIT 5, (IX + d)
BIT 5, (IY + d)
BIT 5, A
BIT 5, B
BIT 5, C
BIT 5, D

CB6B
CB6C
CB6D
CB76
DDCB d 76
FDCB d 76
CB77
CB70
CB71
CB72
CB73
CB74
CB75
CB7E
DDCB d 7E
FDCB d 7E
CB7F
CB78
CB79
CB7A
CB7B
CB7C
CB7D
DC n n
FC n n
D4 n n
CD n n
C4 n n
F4 n n
EC n n
E4 n n
CC n n
3F
BE
DDBE d
FDBE d
BF
B8
B9
BA
BB
BC
BD
FE n
2F
35
DD35 d
FD35 d
3D
5
0B
0D
15

BIT 5, E
BIT 5, H
BIT 5, L
BIT 6, (HL)
BIT 6, (IX + d)
BIT 6, (IY + d)
BIT 6, A
BIT 6, B
BIT 6, C
BIT 6, D
BIT 6, E
BIT 6, H
BIT 6, L
BIT 7, (HL)
BIT 7, (IX + d)
BIT 7, (IY + d)
BIT 7, A
BIT 7, B
BIT 7, C
BIT 7, D
BIT 7, E
BIT 7, H
BIT 7, L
CALL C, nn
CALL M, nn
CALL NC, nn
CALL nn
CALL NZ, nn
CALL P, nn
CALL PE, nn
CALL PO, nn
CALL Z, nn
CCF
CP (HL)
CP (IX + d)
CP (IY + d)
CP A
CP B
CP C
CP D
CP E
CP H
CP L
CP n
CPL
DEC (HL)
DEC (IX + d)
DEC (IY + d)
DEC A
DEC B
DEC BC
DEC C
DEC D

Questo elenco delle istruzioni, ordinato in ordine alfabetico, e` utile, ad esempio, per controllare rapidamente se esiste, oppure no, una
certa istruzione o un certo modo di indirizzamento; le istruzioni, comprese tutte le varianti, sono in totale 659.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

11

1B
1D
25
2B
DD2B
FD2B
2D
3B
F3
FB
76
ED78
DB n
ED40
ED48
ED50
ED58
ED60
ED68
34
DD34 d
FD34 d
3C
4
3
0C
14
13
1C
24
23
DD23
FD23
2C
33
E9
DDE9
FDE9
DA n n
FA n n
D2 n n
C3 n n
C2 n n
F2 n n
EA n n
E2 n n
CA n n
2
12
77
70
71
72
73
74
75
36 n
DD77 d
DD70 d
DD71 d

DEC DE
DEC E
DEC H
DEC HL
DEC IX
DEC IY
DEC L
DEC SP
DI
EI
HALT
IN A, (C)
IN A, (n)
IN B, (C)
IN C, (C)
IN D, (C)
IN E, (C)
IN H, (C)
IN L, (C)
INC (HL)
INC (IX + d)
INC (IY + d)
INC A
INC B
INC BC
INC C
INC D
INC DE
INC E
INC H
INC HL
INC IX
INC IY
INC L
INC SP
JP (HL)
JP (IX)
JP (IY)
JP C, nn
JP M, nn
JP NC, nn
JP nn
JP NZ, nn
JP P, nn
JP PE, nn
JP PO, nn
JP Z, nn
LD (BC), A
LD (DE), A
LD (HL), A
LD (HL), B
LD (HL), C
LD (HL), D
LD (HL), E
LD (HL), H
LD (HL), L
LD (HL), n
LD (IX + d), A
LD (IX + d), B
LD (IX + d), C

DD72 d
DD73 d
DD74 d
DD75 d
DD36 d n
FD77 d
FD70 d
FD71 d
FD72 d
FD73 d
FD74 d
FD75 d
FD36 d n
32 n n
ED43 n n
ED53 n n
22 n n
ED63 n n
DD22 n n
FD22 n n
ED73 n n
0A
1A
7E
DD7E d
FD7E d
3A n n
7F
78
79
7A
7B
7C
7D
3E n
46
DD46 d
FD46 d
47
40
41
42
43
44
45
06 n
ED4B n n
01 n n
4E
DD4E d
FD4E d
4F
48
49
4A
4B
4C
4D
0E n
56

LD (IX + d), D
LD (IX + d), E
LD (IX + d), H
LD (IX + d), L
LD (IX + d), n
LD (IY + d), A
LD (IY + d), B
LD (IY + d), C
LD (IY + d), D
LD (IY + d), E
LD (IY + d), H
LD (IY + d), L
LD (IY + d), n
LD (nn), A
LD (nn), BC
LD (nn), DE
LD (nn), HL
LD (nn), HL
LD (nn), IX
LD (nn), IY
LD (nn), SP
LD A, (BC)
LD A, (DE)
LD A, (HL)
LD A, (IX + d)
LD A, (IY + d)
LD A, (nn)
LD A, A
LD A, B
LD A, C
LD A, D
LD A, E
LD A, H
LD A, L
LD A, n
LD B, (HL)
LD B, (IX + d)
LD B, (IY + d)
LD B, A
LD B, B
LD B, C
LD B, D
LD B, E
LD B, H
LD B, L
LD B, n
LD BC, (nn)
LD BC, nn
LD C, (HL)
LD C, (IX + d)
LD C, (IY + d)
LD C, A
LD C, B
LD C, C
LD C, D
LD C, E
LD C, H
LD C, L
LD C, n
LD D, (HL)

DD56 d
FD56 d
57
50
51
52
53
54
55
16 n
ED5B n n
11 n n
5E
DD5E d
FD5E d
5F
58
59
5A
5B
5C
5D
1E n
66
DD66 d
FD66 d
67
60
61
62
63
64
65
26 n
2A n n
21 n n
DD2A n n
DD21 n n
FD2A n n
FD21 n n
6E
DD6E d
FD6E d
6F
68
69
6A
6B
6C
6D
2E n
ED7B n n
F9
DDF9
FDF9
31 n n
ED44
0
B6
DDB6 d

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

LD D, (IX + d)
LD D, (IY + d)
LD D, A
LD D, B
LD D, C
LD D, D
LD D, E
LD D, H
LD D, L
LD D, n
LD DE, (nn)
LD DE, nn
LD E, (HL)
LD E, (IX + d)
LD E, (IY + d)
LD E, A
LD E, B
LD E, C
LD E, D
LD E, E
LD E, H
LD E, L
LD E, n
LD H, (HL)
LD H, (IX + d)
LD H, (IY + d)
LD H, A
LD H, B
LD H, C
LD H, D
LD H, E
LD H, H
LD H, L
LD H, n
LD HL, (nn)
LD HL, nn
LD IX, (nn)
LD IX, nn
LD IY, (nn)
LD IY, nn
LD L, (HL)
LD L, (IX + d)
LD L, (IY + d)
LD L, A
LD L, B
LD L, C
LD L, D
LD L, E
LD L, H
LD L, L
LD L, n
LD SP, (nn)
LD SP, HL
LD SP, IX
LD SP, IY
LD SP, nn
NEG
NOP
OR (HL)
OR (IX + d)
12

FDB6 d
B7
B0
B1
B2
B3
B4
B5
F6 n
ED79
ED41
ED49
ED51
ED59
ED61
ED69
D3 n
F1
C1
D1
E1
DDE1
FDE1
F5
C5
D5
E5
DDE5
FDE5
CB86
DDCB d 86
FDCB d 86
CB87
CB80
CB81
CB82
CB83
CB84
CB85
CB8E
DDCB d 8E
FDCB d 8E
CB8F
CB88
CB89
CB8A
CB8B
CB8C
CB8D
CB96
DDCB d 96
FDCB d 96
CB97
CB90
CB91
CB92
CB93
CB94
CB95
CB9E

OR (IY + d)
OR A
OR B
OR C
OR D
OR E
OR H
OR L
OR n
OUT (C), A
OUT (C), B
OUT (C), C
OUT (C), D
OUT (C), E
OUT (C), H
OUT (C), L
OUT (n), A
POP AF
POP BC
POP DE
POP HL
POP IX
POP IY
PUSH AF
PUSH BC
PUSH DE
PUSH HL
PUSH IX
PUSH IY
RES 0, (HL)
RES 0, (IX + d)
RES 0, (IY + d)
RES 0, A
RES 0, B
RES 0, C
RES 0, D
RES 0, E
RES 0, H
RES 0, L
RES 1, (HL)
RES 1, (IX + d)
RES 1, (IY + d)
RES 1, A
RES 1, B
RES 1, C
RES 1, D
RES 1, E
RES 1, H
RES 1, L
RES 2, (HL)
RES 2, (IX + d)
RES 2, (IY + d)
RES 2, A
RES 2, B
RES 2, C
RES 2, D
RES 2, E
RES 2, H
RES 2, L
RES 3, (HL)

DDCB d 9E
FDCB d 9E
CB9F
CB98
CB99
CB9A
CB9B
CB9C
CB9D
CBA6
DDCB d A6
FDCB d A6
CBA7
CBA0
CBA1
CBA2
CBA3
CBA4
CBA5
CBAE
DDCB d AE
FDCB d AE
CBAF
CBA8
CBA9
CBAA
CBAB
CBAC
CBAD
CBB6
DDCB d B6
FDCB d B6
CBB7
CBB0
CBB1
CBB2
CBB3
CBB4
CBB5
CBBE
DDCB d BE
FDCB d BE
CBBF
CBB8
CBB9
CBBA
CBBB
CBBC
CBBD
C9
D8
F8
D0
C0
F0
E8
E0
C8
CB16
DDCB d 16

RES 3, (IX + d)
RES 3, (IY + d)
RES 3, A
RES 3, B
RES 3, C
RES 3, D
RES 3, E
RES 3, H
RES 3, L
RES 4, (HL)
RES 4, (IX + d)
RES 4, (IY + d)
RES 4, A
RES 4, B
RES 4, C
RES 4, D
RES 4, E
RES 4, H
RES 4, L
RES 5, (HL)
RES 5, (IX + d)
RES 5, (IY + d)
RES 5, A
RES 5, B
RES 5, C
RES 5, D
RES 5, E
RES 5, H
RES 5, L
RES 6, (HL)
RES 6, (IX + d)
RES 6, (IY + d)
RES 6, A
RES 6, B
RES 6, C
RES 6, D
RES 6, E
RES 6, H
RES 6, L
RES 7, (HL)
RES 7, (IX + d)
RES 7, (IY + d)
RES 7, A
RES 7, B
RES 7, C
RES 7, D
RES 7, E
RES 7, H
RES 7, L
RET
RET C
RET M
RET NC
RET NZ
RET P
RET PE
RET PO
RET Z
RL (HL)
RL (IX + d)

FDCB d 16
CB17
CB10
CB11
CB12
CB13
CB14
CB15
17
CB06
DDCB d 06
FDCB d 06
CB07
CB00
CB01
CB02
CB03
CB04
CB05
7
ED6F
CB1E
DDCB d 1E
FDCB d 1E
CB1F
CB18
CB19
CB1A
CB1B
CB1C
CB1D
1F
CB0E
DDCB d 0E
FDCB d 0E
CB0F
CB08
CB09
CB0A
CB0B
CB0C
CB0D
0F
ED67
C7
CF
D7
DF
E7
EF
F7
FF
9E
DD9E d
FD9E d
9F
98
99
9A
9B

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

RL (IY + d)
RL A
RL B
RL C
RL D
RL E
RL H
RL L
RLA
RLC (HL)
RLC (IX + d)
RLC (IY + d)
RLC A
RLC B
RLC C
RLC D
RLC E
RLC H
RLC L
RLCA
RLD
RR (HL)
RR (IX + d)
RR (IY + d)
RR A
RR B
RR C
RR D
RR E
RR H
RR L
RRA
RRC (HL)
RRC (IX + d)
RRC (IY + d)
RRC A
RRC B
RRC C
RRC D
RRC E
RRC H
RRC L
RRCA
RRD
RST 00h
RST 08h
RST 10h
RST 18h
RST 20h
RST 28h
RST 30h
RST 38h
SBC A, (HL)
SBC A, (IX + d)
SBC A, (IY + d)
SBC A, A
SBC A, B
SBC A, C
SBC A, D
SBC A, E
13

9C
9D
DE n
ED42
ED52
ED62
ED72
37
CBC6
DDCB d C6
FDCB d C6
CBC7
CBC0
CBC1
CBC2
CBC3
CBC4
CBC5
CBCE
DDCB d CE
FDCB d CE
CBCF
CBC8
CBC9
CBCA
CBCB
CBCC
CBCD
CBD6
DDCB d D6
FDCB d D6
CBD7
CBD0
CBD1
CBD2
CBD3
CBD4
CBD5
CBDE
DDCB d DE
FDCB d DE
CBDF
CBD8
CBD9
CBDA
CBDB
CBDC
CBDD
CBE6
DDCB d E6
FDCB d E6
CBE7
CBE0
CBE1
CBE2
CBE3
CBE4
CBE5
CBEE
DDCB d EE

SBC A, H
SBC A, L
SBC A, n
SBC HL, BC
SBC HL, DE
SBC HL, HL
SBC HL, SP
SCF
SET 0, (HL)
SET 0, (IX + d)
SET 0, (IY + d)
SET 0, A
SET 0, B
SET 0, C
SET 0, D
SET 0, E
SET 0, H
SET 0, L
SET 1, (HL)
SET 1, (IX + d)
SET 1, (IY + d)
SET 1, A
SET 1, B
SET 1, C
SET 1, D
SET 1, E
SET 1, H
SET 1, L
SET 2, (HL)
SET 2, (IX + d)
SET 2, (IY + d)
SET 2, A
SET 2, B
SET 2, C
SET 2, D
SET 2, E
SET 2, H
SET 2, L
SET 3, (HL)
SET 3, (IX + d)
SET 3, (IY + d)
SET 3, A
SET 3, B
SET 3, C
SET 3, D
SET 3, E
SET 3, H
SET 3, L
SET 4, (HL)
SET 4, (IX + d)
SET 4, (IY + d)
SET 4, A
SET 4, B
SET 4, C
SET 4, D
SET 4, E
SET 4, H
SET 4, L
SET 5, (HL)
SET 5, (IX + d)

FDCB d EE
CBEF
CBE8
CBE9
CBEA
CBEB
CBEC
CBED
CBF6
DDCB d F6
FDCB d F6
CBF7
CBF0
CBF1
CBF2
CBF3
CBF4
CBF5
CBFE
DDCB d FE
FDCB d FE
CBFF
CBF8
CBF9
CBFA
CBFB
CBFC
CBFD
CB26
DDCB d 26
FDCB d 26
CB27
CB20
CB21
CB22
CB23
CB24
CB25
CB2E
DDCB d 2E
FDCB d 2E
CB2F
CB28
CB29
CB2A
CB2B
CB2C
CB2D
CB3E
DDCB d 3E
FDCB d 3E
CB3F
CB38
CB39
CB3A
CB3B
CB3C
CB3D
96
DD96 d

SET 5, (IY + d)
SET 5, A
SET 5, B
SET 5, C
SET 5, D
SET 5, E
SET 5, H
SET 5, L
SET 6, (HL)
SET 6, (IX + d)
SET 6, (IY + d)
SET 6, A
SET 6, B
SET 6, C
SET 6, D
SET 6, E
SET 6, H
SET 6, L
SET 7, (HL)
SET 7, (IX + d)
SET 7, (IY + d)
SET 7, A
SET 7, B
SET 7, C
SET 7, D
SET 7, E
SET 7, H
SET 7, L
SLA (HL)
SLA (IX + d)
SLA (IY + d)
SLA A
SLA B
SLA C
SLA D
SLA E
SLA H
SLA L
SRA (HL)
SRA (IX + d)
SRA (IY + d)
SRA A
SRA B
SRA C
SRA D
SRA E
SRA H
SRA L
SRL (HL)
SRL (IX + d)
SRL (IY + d)
SRL A
SRL B
SRL C
SRL D
SRL E
SRL H
SRL L
SUB (HL)
SUB (IX + d)

FD96 d
97
90
91
92
93
94
95
D6 n
AE
DDAE d
FDAE d
AF
A8
A9
AA
AB
AC
AD
EE n

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

SUB (IY + d)
SUB A
SUB B
SUB C
SUB D
SUB E
SUB H
SUB L
SUB n
XOR (HL)
XOR (IX + d)
XOR (IY + d)
XOR A
XOR B
XOR C
XOR D
XOR E
XOR H
XOR L
XOR n

14

12.3

Elenco in ordine numerico2 delle istruzioni DMC8


0
01 n n
2
3
4
5
06 n
7
9
0A
0B
0C
0D
0E n
0F
11 n n
12
13
14
15
16 n
17
19
1A
1B
1C
1D
1E n
1F
21 n n
22 n n
23
24
25
26 n
29
2A n n
2B
2C
2D
2E n
2F
31 n n
32 n n
33
34
35
36 n
37
39
3A n n
3B
3C

NOP
LD BC, nn
LD (BC), A
INC BC
INC B
DEC B
LD B, n
RLCA
ADD HL, BC
LD A, (BC)
DEC BC
INC C
DEC C
LD C, n
RRCA
LD DE, nn
LD (DE), A
INC DE
INC D
DEC D
LD D, n
RLA
ADD HL, DE
LD A, (DE)
DEC DE
INC E
DEC E
LD E, n
RRA
LD HL, nn
LD (nn), HL
INC HL
INC H
DEC H
LD H, n
ADD HL, HL
LD HL, (nn)
DEC HL
INC L
DEC L
LD L, n
CPL
LD SP, nn
LD (nn), A
INC SP
INC (HL)
DEC (HL)
LD (HL), n
SCF
ADD HL, SP
LD A, (nn)
DEC SP
INC A

3D
3E n
3F
40
41
42
43
44
45
46
47
48
49
4A
4B
4C
4D
4E
4F
50
51
52
53
54
55
56
57
58
59
5A
5B
5C
5D
5E
5F
60
61
62
63
64
65
66
67
68
69
6A
6B
6C
6D
6E
6F
70
71

DEC A
LD A, n
CCF
LD B, B
LD B, C
LD B, D
LD B, E
LD B, H
LD B, L
LD B, (HL)
LD B, A
LD C, B
LD C, C
LD C, D
LD C, E
LD C, H
LD C, L
LD C, (HL)
LD C, A
LD D, B
LD D, C
LD D, D
LD D, E
LD D, H
LD D, L
LD D, (HL)
LD D, A
LD E, B
LD E, C
LD E, D
LD E, E
LD E, H
LD E, L
LD E, (HL)
LD E, A
LD H, B
LD H, C
LD H, D
LD H, E
LD H, H
LD H, L
LD H, (HL)
LD H, A
LD L, B
LD L, C
LD L, D
LD L, E
LD L, H
LD L, L
LD L, (HL)
LD L, A
LD (HL), B
LD (HL), C

72
73
74
75
76
77
78
79
7A
7B
7C
7D
7E
7F
80
81
82
83
84
85
86
87
88
89
8A
8B
8C
8D
8E
8F
90
91
92
93
94
95
96
97
98
99
9A
9B
9C
9D
9E
9F
A0
A1
A2
A3
A4
A5
A6

LD (HL), D
LD (HL), E
LD (HL), H
LD (HL), L
HALT
LD (HL), A
LD A, B
LD A, C
LD A, D
LD A, E
LD A, H
LD A, L
LD A, (HL)
LD A, A
ADD A, B
ADD A, C
ADD A, D
ADD A, E
ADD A, H
ADD A, L
ADD A, (HL)
ADD A, A
ADC A, B
ADC A, C
ADC A, D
ADC A, E
ADC A, H
ADC A, L
ADC A, (HL)
ADC A, A
SUB B
SUB C
SUB D
SUB E
SUB H
SUB L
SUB (HL)
SUB A
SBC A, B
SBC A, C
SBC A, D
SBC A, E
SBC A, H
SBC A, L
SBC A, (HL)
SBC A, A
AND B
AND C
AND D
AND E
AND H
AND L
AND (HL)

Questo elenco delle istruzioni, ordinato in ordine di codice operativo, e` utile per risalire al codice sorgente a
partire dal codice eseguibile.

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

15

A7
A8
A9
AA
AB
AC
AD
AE
AF
B0
B1
B2
B3
B4
B5
B6
B7
B8
B9
BA
BB
BC
BD
BE
BF
C0
C1
C2 n n
C3 n n
C4 n n
C5
C6 n
C7
C8
C9
CA n n
CB00
CB01
CB02
CB03
CB04
CB05
CB06
CB07
CB08
CB09
CB0A
CB0B
CB0C
CB0D
CB0E
CB0F
CB10
CB11
CB12
CB13
CB14
CB15
CB16
CB17

AND A
XOR B
XOR C
XOR D
XOR E
XOR H
XOR L
XOR (HL)
XOR A
OR B
OR C
OR D
OR E
OR H
OR L
OR (HL)
OR A
CP B
CP C
CP D
CP E
CP H
CP L
CP (HL)
CP A
RET NZ
POP BC
JP NZ, nn
JP nn
CALL NZ, nn
PUSH BC
ADD A, n
RST 0h
RET Z
RET
JP Z, nn
RLC B
RLC C
RLC D
RLC E
RLC H
RLC L
RLC (HL)
RLC A
RRC B
RRC C
RRC D
RRC E
RRC H
RRC L
RRC (HL)
RRC A
RL B
RL C
RL D
RL E
RL H
RL L
RL (HL)
RL A

CB18
CB19
CB1A
CB1B
CB1C
CB1D
CB1E
CB1F
CB20
CB21
CB22
CB23
CB24
CB25
CB26
CB27
CB28
CB29
CB2A
CB2B
CB2C
CB2D
CB2E
CB2F
CB38
CB39
CB3A
CB3B
CB3C
CB3D
CB3E
CB3F
CB40
CB41
CB42
CB43
CB44
CB45
CB46
CB47
CB48
CB49
CB4A
CB4B
CB4C
CB4D
CB4E
CB4F
CB50
CB51
CB52
CB53
CB54
CB55
CB56
CB57
CB58
CB59
CB5A
CB5B

RR B
RR C
RR D
RR E
RR H
RR L
RR (HL)
RR A
SLA B
SLA C
SLA D
SLA E
SLA H
SLA L
SLA (HL)
SLA A
SRA B
SRA C
SRA D
SRA E
SRA H
SRA L
SRA (HL)
SRA A
SRL B
SRL C
SRL D
SRL E
SRL H
SRL L
SRL (HL)
SRL A
BIT 0, B
BIT 0, C
BIT 0, D
BIT 0, E
BIT 0, H
BIT 0, L
BIT 0, (HL)
BIT 0, A
BIT 1, B
BIT 1, C
BIT 1, D
BIT 1, E
BIT 1, H
BIT 1, L
BIT 1, (HL)
BIT 1, A
BIT 2, B
BIT 2, C
BIT 2, D
BIT 2, E
BIT 2, H
BIT 2, L
BIT 2, (HL)
BIT 2, A
BIT 3, B
BIT 3, C
BIT 3, D
BIT 3, E

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

CB5C
CB5D
CB5E
CB5F
CB60
CB61
CB62
CB63
CB64
CB65
CB66
CB67
CB68
CB69
CB6A
CB6B
CB6C
CB6D
CB6E
CB6F
CB70
CB71
CB72
CB73
CB74
CB75
CB76
CB77
CB78
CB79
CB7A
CB7B
CB7C
CB7D
CB7E
CB7F
CB80
CB81
CB82
CB83
CB84
CB85
CB86
CB87
CB88
CB89
CB8A
CB8B
CB8C
CB8D
CB8E
CB8F
CB90
CB91
CB92
CB93
CB94
CB95
CB96
CB97

BIT 3, H
BIT 3, L
BIT 3, (HL)
BIT 3, A
BIT 4, B
BIT 4, C
BIT 4, D
BIT 4, E
BIT 4, H
BIT 4, L
BIT 4, (HL)
BIT 4, A
BIT 5, B
BIT 5, C
BIT 5, D
BIT 5, E
BIT 5, H
BIT 5, L
BIT 5, (HL)
BIT 5, A
BIT 6, B
BIT 6, C
BIT 6, D
BIT 6, E
BIT 6, H
BIT 6, L
BIT 6, (HL)
BIT 6, A
BIT 7, B
BIT 7, C
BIT 7, D
BIT 7, E
BIT 7, H
BIT 7, L
BIT 7, (HL)
BIT 7, A
RES 0, B
RES 0, C
RES 0, D
RES 0, E
RES 0, H
RES 0, L
RES 0, (HL)
RES 0, A
RES 1, B
RES 1, C
RES 1, D
RES 1, E
RES 1, H
RES 1, L
RES 1, (HL)
RES 1, A
RES 2, B
RES 2, C
RES 2, D
RES 2, E
RES 2, H
RES 2, L
RES 2, (HL)
RES 2, A
16

CB98
CB99
CB9A
CB9B
CB9C
CB9D
CB9E
CB9F
CBA0
CBA1
CBA2
CBA3
CBA4
CBA5
CBA6
CBA7
CBA8
CBA9
CBAA
CBAB
CBAC
CBAD
CBAE
CBAF
CBB0
CBB1
CBB2
CBB3
CBB4
CBB5
CBB6
CBB7
CBB8
CBB9
CBBA
CBBB
CBBC
CBBD
CBBE
CBBF
CBC0
CBC1
CBC2
CBC3
CBC4
CBC5
CBC6
CBC7
CBC8
CBC9
CBCA
CBCB
CBCC
CBCD
CBCE
CBCF
CBD0
CBD1
CBD2
CBD3

RES 3, B
RES 3, C
RES 3, D
RES 3, E
RES 3, H
RES 3, L
RES 3, (HL)
RES 3, A
RES 4, B
RES 4, C
RES 4, D
RES 4, E
RES 4, H
RES 4, L
RES 4, (HL)
RES 4, A
RES 5, B
RES 5, C
RES 5, D
RES 5, E
RES 5, H
RES 5, L
RES 5, (HL)
RES 5, A
RES 6, B
RES 6, C
RES 6, D
RES 6, E
RES 6, H
RES 6, L
RES 6, (HL)
RES 6, A
RES 7, B
RES 7, C
RES 7, D
RES 7, E
RES 7, H
RES 7, L
RES 7, (HL)
RES 7, A
SET 0, B
SET 0, C
SET 0, D
SET 0, E
SET 0, H
SET 0, L
SET 0, (HL)
SET 0, A
SET 1, B
SET 1, C
SET 1, D
SET 1, E
SET 1, H
SET 1, L
SET 1, (HL)
SET 1, A
SET 2, B
SET 2, C
SET 2, D
SET 2, E

CBD4
CBD5
CBD6
CBD7
CBD8
CBD9
CBDA
CBDB
CBDC
CBDD
CBDE
CBDF
CBE0
CBE1
CBE2
CBE3
CBE4
CBE5
CBE6
CBE7
CBE8
CBE9
CBEA
CBEB
CBEC
CBED
CBEE
CBEF
CBF0
CBF1
CBF2
CBF3
CBF4
CBF5
CBF6
CBF7
CBF8
CBF9
CBFA
CBFB
CBFC
CBFD
CBFE
CBFF
CC n n
CD n n
CE n
CF
D0
D1
D2 n n
D3 n
D4 n n
D5
D6 n
D7
D8
DA n n
DB n
DC n n

SET 2, H
SET 2, L
SET 2, (HL)
SET 2, A
SET 3, B
SET 3, C
SET 3, D
SET 3, E
SET 3, H
SET 3, L
SET 3, (HL)
SET 3, A
SET 4, B
SET 4, C
SET 4, D
SET 4, E
SET 4, H
SET 4, L
SET 4, (HL)
SET 4, A
SET 5, B
SET 5, C
SET 5, D
SET 5, E
SET 5, H
SET 5, L
SET 5, (HL)
SET 5, A
SET 6, B
SET 6, C
SET 6, D
SET 6, E
SET 6, H
SET 6, L
SET 6, (HL)
SET 6, A
SET 7, B
SET 7, C
SET 7, D
SET 7, E
SET 7, H
SET 7, L
SET 7, (HL)
SET 7, A
CALL Z, nn
CALL nn
ADC A, n
RST 8h
RET NC
POP DE
JP NC, nn
OUT (n), A
CALL NC, nn
PUSH DE
SUB n
RST 10h
RET C
JP C, nn
IN A, (n)
CALL C, nn

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

DD09
DD19
DD21 n n
DD22 n n
DD23
DD29
DD2A n n
DD2B
DD34 d
DD35 d
DD36 d n
DD39
DD46 d
DD4E d
DD56 d
DD5E d
DD66 d
DD6E d
DD70 d
DD71 d
DD72 d
DD73 d
DD74 d
DD75 d
DD77 d
DD7E d
DD86 d
DD8E d
DD96 d
DD9E d
DDA6 d
DDAE d
DDB6 d
DDBE d
DDCB d 06
DDCB d 0E
DDCB d 16
DDCB d 1E
DDCB d 26
DDCB d 2E
DDCB d 3E
DDCB d 46
DDCB d 4E
DDCB d 56
DDCB d 5E
DDCB d 66
DDCB d 6E
DDCB d 76
DDCB d 7E
DDCB d 86
DDCB d 8E
DDCB d 96
DDCB d 9E
DDCB d A6
DDCB d AE
DDCB d B6
DDCB d BE
DDCB d C6
DDCB d CE
DDCB d D6

ADD IX, BC
ADD IX, DE
LD IX, nn
LD (nn), IX
INC IX
ADD IX, IX
LD IX, (nn)
DEC IX
INC (IX + d)
DEC (IX + d)
LD (IX + d), n
ADD IX, SP
LD B, (IX + d)
LD C, (IX + d)
LD D, (IX + d)
LD E, (IX + d)
LD H, (IX + d)
LD L, (IX + d)
LD (IX + d), B
LD (IX + d), C
LD (IX + d), D
LD (IX + d), E
LD (IX + d), H
LD (IX + d), L
LD (IX + d), A
LD A, (IX + d)
ADD A, (IX + d)
ADC A, (IX + d)
SUB (IX + d)
SBC A, (IX + d)
AND (IX + d)
XOR (IX + d)
OR (IX + d)
CP (IX + d)
RLC (IX + d)
RRC (IX + d)
RL (IX + d)
RR (IX + d)
SLA (IX + d)
SRA (IX + d)
SRL (IX + d)
BIT 0, (IX + d)
BIT 1, (IX + d)
BIT 2, (IX + d)
BIT 3, (IX + d)
BIT 4, (IX + d)
BIT 5, (IX + d)
BIT 6, (IX + d)
BIT 7, (IX + d)
RES 0, (IX + d)
RES 1, (IX + d)
RES 2, (IX + d)
RES 3, (IX + d)
RES 4, (IX + d)
RES 5, (IX + d)
RES 6, (IX + d)
RES 7, (IX + d)
SET 0, (IX + d)
SET 1, (IX + d)
SET 2, (IX + d)
17

DDCB d DE
DDCB d E6
DDCB d EE
DDCB d F6
DDCB d FE
DDE1
DDE5
DDE9
DDF9
DE n
DF
E0
E1
E2 n n
E4 n n
E5
E6 n
E7
E8
E9
EA n n
EC n n
ED40
ED41
ED42
ED43 n n
ED44
ED48
ED49
ED4A
ED4B n n
ED50
ED51
ED52
ED53 n n
ED58
ED59
ED5A
ED5B n n
ED60
ED61
ED62
ED63 n n
ED67
ED68
ED69
ED6A
ED6F
ED72
ED73 n n
ED78
ED79
ED7A
ED7B n n
EE n
EF
F0
F1
F2 n n
F3

SET 3, (IX + d)
SET 4, (IX + d)
SET 5, (IX + d)
SET 6, (IX + d)
SET 7, (IX + d)
POP IX
PUSH IX
JP (IX)
LD SP, IX
SBC A, n
RST 18h
RET PO
POP HL
JP PO, nn
CALL PO, nn
PUSH HL
AND n
RST 20h
RET PE
JP (HL)
JP PE, nn
CALL PE, nn
IN B, (C)
OUT (C), B
SBC HL, BC
LD (nn), BC
NEG
IN C, (C)
OUT (C), C
ADC HL, BC
LD BC, (nn)
IN D, (C)
OUT (C), D
SBC HL, DE
LD (nn), DE
IN E, (C)
OUT (C), E
ADC HL, DE
LD DE, (nn)
IN H, (C)
OUT (C), H
SBC HL, HL
LD (nn), HL
RRD
IN L, (C)
OUT (C), L
ADC HL, HL
RLD
SBC HL, SP
LD (nn), SP
IN A, (C)
OUT (C), A
ADC HL, SP
LD SP, (nn)
XOR n
RST 28h
RET P
POP AF
JP P, nn
DI

F4 n n
F5
F6 n
F7
F8
F9
FA n n
FB
FC n n
FD09
FD19
FD21 n n
FD22 n n
FD23
FD29
FD2A n n
FD2B
FD34 d
FD35 d
FD36 d n
FD39
FD46 d
FD4E d
FD56 d
FD5E d
FD66 d
FD6E d
FD70 d
FD71 d
FD72 d
FD73 d
FD74 d
FD75 d
FD77 d
FD7E d
FD86 d
FD8E d
FD96 d
FD9E d
FDA6 d
FDAE d
FDB6 d
FDBE d
FDCB d 06
FDCB d 0E
FDCB d 16
FDCB d 1E
FDCB d 26
FDCB d 2E
FDCB d 3E
FDCB d 46
FDCB d 4E
FDCB d 56
FDCB d 5E
FDCB d 66
FDCB d 6E
FDCB d 76
FDCB d 7E
FDCB d 86
FDCB d 8E

CALL P, nn
PUSH AF
OR n
RST 30h
RET M
LD SP, HL
JP M, nn
EI
CALL M, nn
ADD IY, BC
ADD IY, DE
LD IY, nn
LD (nn), IY
INC IY
ADD IY, IY
LD IY, (nn)
DEC IY
INC (IY + d)
DEC (IY + d)
LD (IY + d), n
ADD IY, SP
LD B, (IY + d)
LD C, (IY + d)
LD D, (IY + d)
LD E, (IY + d)
LD H, (IY + d)
LD L, (IY + d)
LD (IY + d), B
LD (IY + d), C
LD (IY + d), D
LD (IY + d), E
LD (IY + d), H
LD (IY + d), L
LD (IY + d), A
LD A, (IY + d)
ADD A, (IY + d)
ADC A, (IY + d)
SUB (IY + d)
SBC A, (IY + d)
AND (IY + d)
XOR (IY + d)
OR (IY + d)
CP (IY + d)
RLC (IY + d)
RRC (IY + d)
RL (IY + d)
RR (IY + d)
SLA (IY + d)
SRA (IY + d)
SRL (IY + d)
BIT 0, (IY + d)
BIT 1, (IY + d)
BIT 2, (IY + d)
BIT 3, (IY + d)
BIT 4, (IY + d)
BIT 5, (IY + d)
BIT 6, (IY + d)
BIT 7, (IY + d)
RES 0, (IY + d)
RES 1, (IY + d)

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

FDCB d 96
FDCB d 9E
FDCB d A6
FDCB d AE
FDCB d B6
FDCB d BE
FDCB d C6
FDCB d CE
FDCB d D6
FDCB d DE
FDCB d E6
FDCB d EE
FDCB d F6
FDCB d FE
FDE1
FDE5
FDE9
FDF9
FE n
FF

RES 2, (IY + d)
RES 3, (IY + d)
RES 4, (IY + d)
RES 5, (IY + d)
RES 6, (IY + d)
RES 7, (IY + d)
SET 0, (IY + d)
SET 1, (IY + d)
SET 2, (IY + d)
SET 3, (IY + d)
SET 4, (IY + d)
SET 5, (IY + d)
SET 6, (IY + d)
SET 7, (IY + d)
POP IY
PUSH IY
JP (IY)
LD SP, IY
CP n
RST 38h

18

12.4

Codice ASCII (7 bit)

Si riporta qui per comodit la tabella del codice ASCII (American Standard Code for Information Interchange).

12.4.1 Caratteri ASCII Non Stampabili


Char.
NUL
SOH
STX
ETX
EOT
ENQ
ACK
BEL
BS
HT
LF
VT
FF
CR
SO
SI

Dec.
0
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15

Hex.
00
01
02
03
04
05
06
07
08
09
0A
0B
0C
0D
0E
0F

Char.
DLE
XON
DC2
XOFF
DC4
NAK
SYN
ETB
CAN
EM
SUB
ESC
FS
GS
RS
US

Dec.
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31

Hex.
10
11
12
13
14
15
16
17
18
19
1A
1B
1C
1D
1E
1F

Char.

Dec.

Hex

DEL

127

7F

Char.
@
A
B
C
D
E
F
G
H
I
J
K
L
M
N
O
P
Q
R
S
T
U
V
W
X
Y
Z
[
\
]
^
_

Dec.
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95

Hex.
40
41
42
43
44
45
46
47
48
49
4A
4B
4C
4D
4E
4F
50
51
52
53
54
55
56
57
58
59
5A
5B
5C
5D
5E
5F

Char.
`
a
b
c
d
e
f
g
h
i
j
k
l
m
n
o
p
q
r
s
t
u
v
w
x
y
z
{
|
}
~

Dec.
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126

Hex.
60
61
62
63
64
65
66
67
68
69
6A
6B
6C
6D
6E
6F
70
71
72
73
74
75
76
77
78
79
7A
7B
7C
7D
7E

12.4.2 Caratteri ASCII Stampabili


Char.
!
"
#
$
%
&
'
(
)
*
+
,
.
/
0
1
2
3
4
5
6
7
8
9
:
;
<
=
>
?

Dec.
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63

Hex.
20
21
22
23
24
25
26
27
28
29
2A
2B
2C
2D
2E
2F
30
31
32
33
34
35
36
37
38
39
3A
3B
3C
3D
3E
3F

Elettronica dei Sistemi Digitali Sistemi a microprocessore Giuliano Donzellini Ver.06/02/2015

19