# Calcolatori elettronici/Il progetto di circuiti logici

Calcolatori elettronici
Copertina Tutti i moduli · Sviluppo
    CopertinaCalcolatori elettronici/Copertina
* L'evoluzione dei sistemi di elaborazioneCalcolatori elettronici/L'evoluzione dei sistemi di elaborazione
* Il progetto di circuiti logiciCalcolatori elettronici/Il progetto di circuiti logici
* I processoriCalcolatori elettronici/I processori
* Architettura 8086Calcolatori elettronici/Architettura 8086
* Unità di controlloCalcolatori elettronici/Unità di controllo
* Introduzione alle memorieCalcolatori elettronici/Introduzione alle memorie
* Le memorie ad accesso casualeCalcolatori elettronici/Le memorie ad accesso casuale
* Le memorie cacheCalcolatori elettronici/Le memorie cache
* Le memorie ad accesso serialeCalcolatori elettronici/Le memorie ad accesso seriale
* La memoria virtualeCalcolatori elettronici/La memoria virtuale
* La gestione dei dispositivi input/outputCalcolatori elettronici/La gestione dei dispositivi input/output
* Intel 8255Calcolatori elettronici/Intel 8255
* Intel 8259Calcolatori elettronici/Intel 8259
* I busCalcolatori elettronici/I bus
* Le architetture a pipelineCalcolatori elettronici/Le architetture a pipeline
* Assembler 8086
          IntroduzioneCalcolatori elettronici/Introduzione
   * Informazioni generaliCalcolatori elettronici/Informazioni generali
   * Istruzioni di trasferimento datiCalcolatori elettronici/Istruzioni di trasferimento dati
   * Istruzioni aritmeticheCalcolatori elettronici/Istruzioni aritmetiche
   * Istruzioni per il controllo del flussoCalcolatori elettronici/Istruzioni per il controllo del flusso
   * Istruzioni per la manipolazione dei bitCalcolatori elettronici/Istruzioni per la manipolazione dei bit
   * Le procedureCalcolatori elettronici/Le procedure
   * Istruzioni per il controllo del processoreCalcolatori elettronici/Istruzioni per il controllo del processore
   * Formato delle istruzioni macchina, tempi di esecuzioneCalcolatori elettronici/Formato delle istruzioni macchina, tempi di esecuzione
Modifica il sommario
chiudi indice
Per fare un circuito con determinate specifiche (costo, prestazioni...), si scelgono dei componenti, avendo informazioni di base sulla loro funzionalità, e li si assembla (topologia).
I sistemi digitali elaborano input digitali in output digitali (= binari).
Il circuito dispone di una libreria di componenti che rappresenta le porte logiche da interconnettere, rappresentabili con un grafo con:
* vertici = porte logiche
* archi = linee per il trasferimento dei dati tra le porte
Un circuito è definito da:
* struttura: da quali componenti è composto il circuito e come sono connessi questi componenti
* comportamento: ciò che fa
Due circuiti con strutture diverse possono avere lo stesso comportamento; il viceversa è da evitare.

## Progettazione

Dati un comportamento e una struttura, il progettista deve interconnettere i componenti tenendo conto del comportamento e del costo.
Il costo di progetto/sviluppo si paga una sola volta, ma è significativo → deve essere recuperato sul costo di produzione dei componenti (vivo), che deve essere relativamente basso. Il prodotto deve richiedere un costo di manutenzione ragionevole → meno guasti possibile e costi di riparazione bassi.
flusso di progetto: specifiche → sintesi → verifica → realizzazione
Il progettista di un circuito realizza prima un modello, che descrive le porte logiche e le loro interconnessioni che soddisfano le specifiche, quindi verifica tramite simulazione che si comporti come previsto prima di metterlo in produzione.
Il costo di progettazione a volte viene fatto in maniera top-down, partendo dalle specifiche e realizzando un progetto suddividendo il problema in sottoproblemi più semplici, oppure partendo da un modello simile già esistente e modificando alcune parti.

### Livelli di progettazione

Il progetto può avvenire a diversi livelli. Un approccio top-down prevede la discesa nei seguenti livelli:
* sistema: opera su blocchi di dati codificati in un certo modo (es. output allo schermo), e utilizza dei componenti già noti;
* registri: non opera su 0 e 1, ma sulle variabili (ad es. si progetta il circuito per il nuovo standard USB partendo da blocchi logici elementari e assemblandoli);
* porte logiche: gli elementi assemblati dal progettista sono le porte logiche, in grado di produrre dei segnali di uscita su ciascuna porta logica che dipendono dai segnali in ingresso e che sono determinati da funzioni booleane implementate in hardware;
* transistor: livello molto basso, ma sempre su grandezze digitali;
* elettrico: il circuito è descritto dal progettista a livello elettrico, cioè in termini di connessioni di componenti quali condensatori, induttori, ecc. → si riduce allo studio di un sistema di equazioni differenziali in cui compaiono correnti e tensioni.
Più si scende di livello, più il dettaglio di tempo è importante, e più piccoli e semplici devono essere i circuiti per poter essere studiati.

## Livello di porte logiche

Il progetto di un sistema sequenziale sincrono si compone delle seguenti fasi:
* si costruiscono il diagramma degli stati e la tavola degli stati;
* minimizzazione degli stati: un algoritmo cerca di minimizzare il diagramma degli stati, ovvero di ricondurlo a un diagramma equivalente riunendo più stati in uno;
* assegnazione degli stati: data una serie di stati con nomi simbolici, si assegna a ciascuno stato una codifica binaria e si calcola il numero di flip-flop necessari per memorizzarli:
    $\sup\{\log _{2}{({\text{numero degli stati}})}\}$
* costruzione della tavola di verità della rete combinatoria: per ogni combinazione di ingressi e di stati correnti, si elencano le uscite e gli stati futuri;
* sintesi della rete combinatoria: tramite le tavole di Karnaugh, si esprimono le funzioni $f$ e $h$ (ciascun bit è dato da una funzione booleana);
* si disegna il circuito.

### Circuiti combinatori

I circuiti combinatori implementano funzioni combinatorie. Una funzione combinatoria è una trasformazione:
    $z:B^{n}\to B$
dove $B=\{0,1\}$.
In un sistema combinatorio, i valori di uscita dipendono esclusivamente dai valori applicati ai suoi ingressi in quell'istante.

#### Rappresentazione

Il sistema deve trasformare un certo numero di bit in ingresso in un certo numero di bit in uscita. Il comportamento di un sistema combinatorio può essere descritto da:
* funzione booleana: es. $f(a,b)=a\cdot b$ con $\cdot$ = porta AND;
* tavola di verità: la tabella indica l'output per ogni combinazione in ingresso.

##### Esempio

Il codificatore prioritario indica l'indice del primo bit in ingresso di valore 1. Si può descrivere con funzioni booleane o più semplicemente con una tavola di verità.

#### Terminologia

Porte logiche :
| AND | OR | XOR | NOT ${\overline {x}}$ |
| $x_{1}\cdot x_{2}$ | $x_{1}+x_{2}$ | $x_{1}\oplus x_{2}$ | NOT ${\overline {x}}$ |
| NAND | NOR | XNOR | NOT ${\overline {x}}$ |
| ${\overline {x_{1}\cdot x_{2}}}$ | ${\overline {x_{1}+x_{2}}}$ | ${\overline {x_{1}\oplus x_{2}}}$ | NOT ${\overline {x}}$ |
fan-in = numero di ingressi di una porta | fan-out = numero di altre porte pilotate dall'uscita di una porta
Due porte logiche sono in connessione wired-or se le loro uscite vanno agli ingressi di una porta OR, che si può anche omettere.
| letterale | minterm | maxterm | cubo |
| ${\dot {x_{i}}}$ | ${\dot {x_{1}}}\cdot {\dot {x_{2}}}\cdot \cdots \cdot {\dot {x_{n}}}$ | ${\dot {x_{1}}}+{\dot {x_{2}}}+\cdots +{\dot {x_{n}}}$ | ${\dot {x_{i}}}\cdot \cdots \cdot {\dot {x_{j}}}\cdot \cdots \cdot {\dot {x_{k}}}$ |

#### Circuiti combinatori ben formati

I circuiti combinatori ben formati (ccbf) sono caratterizzati da una delle seguenti composizioni:
* una singola linea;
* una singola porta;
* due ccbf giustapposti (cioè uno accanto all'altro);
* due ccbf tali che le uscite di uno sono gli ingressi dell'altro;
* due ccbf tali che uno degli ingressi di uno è anche uno degli ingressi dell'altro.
Sono vietati i circuiti dotati di cicli.

##### Circuiti a due livelli

* somma di prodotti: le uscite di diverse porte and sono pilotate da un'unica porta or;
* prodotto di somme: le uscite di diverse porte or sono pilotate da un'unica porta and.

#### Minimizzazione

Data una tavola di verità, ci possono essere più circuiti equivalenti/funzioni che la implementano.
È possibile costruire lo schema di un circuito dalla sua tavola di verità posizionando una porta OR avente per ingressi le uscite delle porte AND che danno 1, ma il circuito risultante non è quello minimo.

##### Circuiti minimi

Con l'algebra booleana si può semplificare una funzione booleana in un circuito minimo (operazione di minimizzazione).
Il problema di trovare un circuito minimo è di tipo NP-completo. Un circuito minimo è composto dal minimo numero possibile di porte logiche (al più 2 livelli). Implementa una somma di prodotti tale che il numero di prodotti è minimo (cubo), e nessun letterale può essere cancellato da un prodotto.
Dato un numero di variabili in ingresso ragionevole, il circuito minimo è ricavato dalle tavole di Karnaugh, che esprimono il comportamento di un circuito nella maniera più compatta possibile, cercando la copertura degli uni con il minimo numero di cubi.

##### Valori don't care

I valori don't care sono quelli che non sono forniti dalla specifica nella tavola di verità, perché le relative combinazioni in ingresso non si verificano mai.
Nella codifica BCD, si assegnano 4 bit (4 ingressi) a ciascuna delle cifre decimali → siccome le cifre vanno da 1 a 9, avanzano dei bit che sono i valori don't care.

#### Ritardi

Una porta logica è composta da transistor, rappresentabili come degli interruttori che si chiudono quando la tensione applicata al segnale di controllo è alta (1 = cortocircuito) e viceversa (0 = circuito aperto). Una opportuna combinazione di transistor può far commutare la tensione di uscita V$_{out}$ nei valori:
* 1: V$_{out}$ viene lasciata essere uguale alla tensione di alimentazione V$_{cc}$, a cui è collegata attraverso la resistenza pull-up;
* 0: V$_{out}$ risulta collegata alla massa.
Ogni transistor ha un suo tempo di commutazione → il cambiamento di un valore in ingresso si riflette con un certo ritardo nel valore di uscita → il valore in ingresso non viene modificato prima che sia passato il tempo t$_0$ + k per la commutazione del valore in uscita.
Il cammino critico è il cammino di lunghezza massima che va da un ingresso a un'uscita, e si può trovare assegnando un livello a ciascuna porta. Come requisito per il circuito minimo si può stabilire una profondità massima. La profondità massima di un circuito è la lunghezza del cammino critico, ovvero il numero di porte logiche che costituiscono il cammino critico.
La profondità è legata alla velocità del circuito, cioè al numero massimo di configurazioni che è in grado di gestire nell'unità di tempo. Il ritardo massimo è un numero di unità di tempo pari alla profondità massima.

### Sistemi sequenziali

In un sistema sequenziale, il valore di uscita dipende anche da ciò che è successo negli istanti precedenti.
Il numero di storie precedenti non può essere infinito, perché il numero di bit utilizzabili per memorizzare la storia precedente è finito. Una variabile interna Y detta variabile di stato, codificata in un certo numero di bit, memorizza un valore numerico che corrisponde a una determinata storia. L'output viene determinato in base agli ingressi correnti X e alla variabile di stato Y.

#### Esempio

Un sistema campiona l'ingresso I con una certa frequenza di tempo. L'uscita O assume il valore 1 se durante i 3 istanti di campionamento precedenti l'ingresso I ha assunto i valori 101, e assume il valore 0 diversamente.

#### Rappresentazione
##### Diagramma degli stati

Il diagramma degli stati si basa su una scala dei tempi discretizzata in punti ben definiti:
* stato corrente: la variabile di stato può assumere i valori rappresentati come lettere cerchiate;
* ingresso: ogni arco rappresenta il cambio di stato, in base al valore in ingresso corrente;
* uscita: si può scegliere di rappresentare i valori di output in due modi:
** a pedice dello stato (come in figura): questo valore è un unico bit, quindi può dipendere solo dallo stato corrente e non dagli ingressi correnti;
** direttamente sugli archi, racchiusi in un rettangolo: facilita la rappresentazione di valori di uscita composti da più bit.
Il numero totale degli archi è uguale a: numero degli stati × numero delle combinazioni di ingresso.

##### Tavola degli stati

La tavola degli stati elenca tutte le combinazioni possibili di stati correnti e valori in ingresso. Il numero delle righe si calcola: numero degli stati × 2$^{numerodibitiningresso}$ → diventa troppo lunga in caso di alti numeri di stati e di bit in ingresso.

##### Funzioni di transizione e d'uscita degli stati

La funzione di transizione e la funzione di uscita sono delle funzioni booleane che, dati i valori assunti dagli ingressi correnti e dalla variabile di stato corrente, restituiscono rispettivamente il valore futuro della variabile di stato e il valore di uscita.

#### Implementazione

Il flip-flop è un elemento di memoria in grado di memorizzare un singolo bit.

##### Flip-flop asincroni

Il flip-flop SR asincrono è un elemento di memoria di tipo sequenziale in cui si può forzare o mantenere un certo valore binario a seconda della scelta dei due ingressi S e R:
| ingresso S | ingresso R | uscite Y$_1$ e Y$_2$ = NOT Y$_1$ |
| 1 | 0 | Vengono forzati i valori 1 sull'uscita Y$_1$ e 0 sull'uscita Y$_2$. |
| 0 | 1 | Vengono forzati i valori 0 sull'uscita Y$_1$ e 1 sull'uscita Y$_2$. |
| 0 | 0 | I valori in uscita non vengono commutati ma si mantengono costanti. |
| 1 | 1 | È una configurazione vietata perché la transizione dallo stato S = R = 1 allo stato S = R = 0 produce un risultato logicamente non definito: l'uscita Y$_1$ può assumere 0 o 1 a seconda dei ritardi di commutazione Δ$_1$ e Δ$_2$ delle due porte logiche, i quali dipendono da fattori non prevedibili (per es. temperatura, umidità...): l'uscita Y$_1$ rimane al valore 0 se Δ$_1$ < Δ$_2$, cioè la porta 2 commuta prima che la porta 1 abbia finito di commutare; l'uscita Y$_1$ commuta al valore 1 se Δ$_1$ > Δ$_2$, cioè la porta 1 riesce a finire di commutare prima che la porta 2 ha commutato. |

##### Flip-flop sincroni

Il clock è un segnale di temporizzazione a onda quadra. In un flip-flop SR sincrono, il segnale di clock si duplica in due segnali posti agli ingressi di due porte AND in coppia con entrambi gli ingressi S e R:
* clock = 1: il flip-flop è sensibile alle variazioni degli ingressi S e R;
* clock = 0: il flip-flop mantiene il suo valore senza vedere gli ingressi S e R, lasciando così il tempo al nuovo valore di propagarsi.
Due ulteriori segnali P (preset) e C (clear) servono per forzare in modo asincrono il flip-flop rispettivamente a 1 o a 0.
Nel flip-flop di tipo D, S e R sono uniti, attraverso una porta NOT, in un unico ingresso D che permette di forzare una coppia di valori S ≠ R, che rimarrà costante fino al successivo colpo di clock. I flip-flop di tipo D sono i più utilizzati perché sono semplici e poco costosi, e non presentano configurazioni vietate.
Un flip-flop di tipo T è un flip-flop di tipo D senza ingressi: il segnale di clock fa invertire il valore memorizzato (l'uscita ritorna all'ingresso tramite una porta NOT).
Un sistema sequenziale si dice sincrono se tutti i flip-flop sono collegati allo stesso segnale di clock.

##### Modello di Huffman

Il modello di Huffman è un circuito costituito da una rete combinatoria e da una serie di flip-flop sincroni.
Tramite il modello di Huffman si può implementare un sistema sequenziale. La variabile di stato si può memorizzare in una serie di flip-flop. Gli altri blocchi combinatori ricevono in ingresso la variabile di stato e gli altri valori in ingresso.

###### Casi particolari

* modello di Mealy: tutte le uscite z$_i$ della rete combinatoria dipendono sia dagli ingressi x$_i$ sia dalle variabili di stato y$_i$;
* modello di Moore: almeno un'uscita z$_i$ dipende solo dalle variabili di stato y$_i$ → tali uscite rimarranno costanti fino al successivo colpo di clock.

## Livello dei registri

Non si lavora a livello di singoli bit ma a livello di parole (= vettori di bit). Il parallelismo di una parola è il suo numero di bit.

### Componenti generici
#### Porta logica operante su parole

La porta logica operante su parole è uno scatolotto contenente una batteria di porte logiche elementari, avente ingresso e uscita con eguale parallelismo di m bit e con eguale numero di parole.

#### Multiplexer

Il multiplexer, pilotato dall'ingresso p, detto segnale di controllo, seleziona una delle k parole in ingresso portandola in uscita.
Connettendo più multiplexer semplici in cascata si può avere un maggior numero di parole in ingresso.
L'uso di un multiplexer è un modo veloce (ma non efficiente) per implementare il comportamento di una generica funzione booleana data: basta porre agli ingressi con parallelismo di m = 1 bit tutti i possibili 2$^n$ valori restituiti dalla funzione, e ai segnali di controllo gli n ingressi valutati dalla funzione.

#### Decodificatore

Il decodificatore è un modulo avente 2$^n$ linee in uscita e n linee in ingresso. Il valore in ingresso attiva una sola linea di uscita, cioè quella avente per indice lo stesso valore in ingresso.
Accanto ai normali valori in ingresso, vi è il valore di enable e che assume 1 o 0:
* e = 1: alla linea di uscita è consentito essere attivata dalla linea in ingresso corrente;
* e = 0: nessuna uscita può essere attivata, e in uscita vi è un valore predefinito indipendente dalla linea in ingresso.
Anche i decodificatori si possono connettere in cascata: si assegna la discriminazione dei bit più significativi ai decodificatori dei primi livelli e quella dei bit meno significativi ai decodificatori dei livelli sottostanti, e si forniscono come valori di enable le uscite dei decodificatori a livello superiore. Con la connessione in cascata bisogna però tenere in conto dei ritardi di commutazione dei decodificatori (durante il tempo di commutazione Δt i segnali in uscita sono casuali nel tempo).

#### Codificatore

Il codificatore ha un comportamento opposto a quello del decodificatore: riceve una sola delle 2$^k$ linee in ingresso e restituisce fino a k linee in uscita, la cui parola corrisponde all'indice della linea in ingresso corrente.
Sono però vietate le combinazioni in ingresso con più di un bit 1 → non è molto utilizzato.

#### Codificatore prioritario

Nel codificatore prioritario, a ogni linea in ingresso è associata oltre all'indice una priorità. L'uscita è l'indice della linea in ingresso con priorità massima tra quelle attive.
In questo modo viene ottimizzato l'impiego dei bit in ingresso.
Siccome le priorità partono da 0, bisogna distinguere il caso in cui la linea a priorità 0 è quella attiva e il caso in cui nessuna linea è attiva → si aggiunge il bit Input Active (IA) in uscita:
* IA = 1: almeno una linea in ingresso è attiva;
* IA = 0: nessuna linea in ingresso è attiva.

### Moduli aritmetici
#### Sommatore combinatorio

Il sommatore combinatorio è un modulo aritmetico che riceve in ingresso 2 parole di m bit e ne restituisce in uscita la somma in m+1 bit → non è molto utilizzato per il suo costo di progetto: anche se richiede il minimo tempo, è da progettare per ogni numero m.

#### Sommatore combinatorio modulare con ripple carry adder

Il sommatore combinatorio modulare si compone di una successione (= ripple carry adder) di full-adder, che sono dei sommatori combinatori in grado di gestire il riporto. Ogni full-adder riceve solo 2 bit in ingresso (m = 1) e il bit di riporto/carry c proveniente dal full-adder precedente → maggiore flessibilità → minore costo di progetto.
Costruendo la tavola di verità, si sintetizzano le seguenti funzioni:
    ${\begin{cases}z_{i}=x_{i}\oplus y_{i}\oplus c_{i}\\c_{i+1}=x_{i}y_{i}+x_{i}c_{i}+y_{i}c_{i}\end{cases}}$
I full-adder sono implementati con circuiti combinatori a k livelli → il ritardo temporale Δ di ciascun livello si riflette in un ritardo temporale δ = k Δ di ciascun full-adder.
Nel ripple carry adder, il riporto viene propagato nella catena → i ritardi crescono al crescere del parallelismo.

#### Sommatore combinatorio modulare con carry-lookahead

Dalla funzione del sommatore combinatorio modulare relativa al riporto c$_i$:
    ${\begin{cases}c_{i}=x_{i}y_{i}+(x_{i}+y_{i})c_{i-1}=g_{i}+p_{i}c_{i-1}\\c_{i-1}=x_{i}y_{i}+(x_{i}+y_{i})c_{i-2}=g_{i}+p_{i}c_{i-2}\end{cases}}\Rightarrow c_{i}=g_{i}+p_{i}g_{i-1}+p_{i}p_{i-1}c_{i-2}$
con: ${\begin{cases}g_{i}=x_{i}\cdot y_{i}\\p_{i}=x_{i}+y_{i}\end{cases}}$, si può ricavare la seguente formula in termini solo di x e y:
    $c_{k}=g_{k}+(p_{k}g_{k-1}+p_{k}p_{k-1}g_{k-2}+\cdots +p_{k}p_{k-1}\cdots p_{2}p_{1}g_{0})+p_{k}p_{k-1}\cdots p_{2}p_{1}p_{0}c_{in}$
in modo che il full-adder non debba aspettare il carry del precedente. Il carry-lookahead invia a ciascun full-adder il corrispondente c.

#### Sommatore seriale

Il sommatore seriale contiene un singolo full-adder che tratta a ogni colpo di clock una coppia di bit alla volta; il carry corrente viene salvato in un flip-flop interno.

##### Vantaggi

    minimo hardware e minimo costo

##### Svantaggio

    i tempi di esecuzione sono più lunghi a causa dei colpi di clock

#### ALU

La ALU è una componente combinatoria che implementa tutte le principali funzioni aritmetiche (su numeri decimali) e logiche (bit a bit). In ingresso non ha il segnale di clock, ma un segnale di controllo che specifica il tipo di operazione da effettuare. Il ritardo è dovuto solo alle porte logiche interne. Un ulteriore ingresso di carry C$_{in}$ (con corrispettiva uscita C$_{out}$) permette di collegare ALU in cascata per operazioni più complesse.

### Comparatore a 4 bit

Il comparatore a 4 bit permette di confrontare due numeri interi senza segno su 4 bit. Un valore di enable stabilisce se le linee sono attivabili.
Connettendo più comparatori in cascata è possibile confrontare interi composti da un numero maggiore di bit: si va dalla quaterna di bit più significativa a quella meno significativa. Il segnale di enable in ingresso a ogni comparatore è pilotato dal comparatore precedente nella catena, in modo che venga attivato solo se quest'ultimo ha verificato la condizione di uguaglianza.

### Registri
#### Registro a n bit

Il registro a n bit serve per memorizzare un ingresso su n bit ogniqualvolta viene attivato il segnale di load; il valore memorizzato viene riportato nell'uscita z e viene mantenuto costante fino al successivo segnale di load → è possibile stabilizzare un segnale molto variabile. Se presente, il segnale di clear permette di resettare a 0 tutti i bit memorizzati.
Internamente, il registro a n bit contiene una serie di n flip-flop di tipo D, ciascuno dei quali memorizza uno degli n bit della parola in ingresso.

#### Registro a scalamento

Il registro a scalamento (o shift-register) memorizza le parole non parallelamente ma un bit alla volta, perché l'ingresso x e l'uscita z hanno parallelismo 1.
Il segnale di shift enable pilota il clock di ogni flip-flop: al segnale di shift enable, il contenuto corrente viene scalato di una posizione: il flip-flop i-esimo passa il bit memorizzato al flip-flop i+1-esimo, quindi riceve il nuovo bit dal flip-flop i−1-esimo, facendo entrare all'estrema sinistra il nuovo bit in ingresso e facendo uscire all'estrema destra l'ultimo bit in eccesso.
I registri a scalamento universali (più costosi) permettono lo scalamento in entrambi i sensi, e ne esistono diverse implementazioni:
* ci possono essere due segnali di shift enable, uno a destra e uno a sinistra;
* ci può essere un unico segnale di shift enable insieme a uno di left shift select, che specifica se effettuare lo scalamento a destra o a sinistra.
Vi può anche essere un segnale di load che permette di caricare parallelamente n bit in ingresso (come nel registro a n bit).

##### Applicazioni

* convertire dati seriali in ingresso (un bit per volta) in dati paralleli in uscita (byte), e viceversa;
* moltiplicare/dividere numeri per potenze di 2 (basta scalare di un bit);
* memorizzare dati seriali in una coda FIFO (il primo valore scala fino in fondo ed esce per primo).

### Contatori

In un contatore, il valore memorizzato all'interno viene incrementato/decrementato a ogni segnale di count enable. Un contatore può avere, a seconda dell'occasione, anche degli altri segnali specifici:
* up/down: indica se il valore va incrementato o decrementato;
* step: specifica di quanto deve essere incrementato il valore;
* terminal count: fornisce 1 quando il contatore raggiunge il suo valore massimo (11...).
Viene anche detto contatore modulo-2$^k$ (dove k è il numero di bit) perché al 2$^k$-esimo impulso (11...) ritorna al valore iniziale 0.

#### Contatore asincrono

Il contatore asincrono è costituito da una serie di flip-flop di tipo T: il segnale di count enable di ogni flip-flop è pilotato dal flip-flop precedente, così un flip-flop quando commuta da 0 a 1 iniziando il fronte di salita dell'uscita fa commutare anche il flip-flop successivo → il contatore è asincrono perché i flip-flop non sono pilotati dallo stesso segnale di clock. La successione di bit ottenuta è discendente.

##### Vantaggi

    hardware economico e facilità di progettazione

##### Svantaggio

    siccome ogni flip-flop ha un ritardo Δ, il ritardo complessivo è proporzionale al parallelismo del contatore (numero di flip-flop)

#### Contatore sincrono

Il contatore sincrono prevede un unico segnale di count enable. La logica combinatoria è costituita da un sommatore/sottrattore che carica parallelamente tutti i bit, li elabora e restituisce direttamente tutti i nuovi bit da scrivere nei flip-flop.

##### Svantaggi

    hardware più complesso e costoso

##### Vantaggio

    il ritardo è indipendente dal numero di flip-flop, e dipende solo dai ritardi della logica combinatoria e del singolo flip-flop

### Interfacce al bus

Un insieme di moduli è detto in connessione a bus se i segnali vengono trasferiti da un modulo all'altro attraverso una struttura di interconnessione/comunicazione detta bus, da cui i moduli in lettura caricano il valore corrente a ogni segnale di load. Per i moduli in scrittura invece vale la seguente regola: in ogni istante il bus può essere pilotato da uno solo dei moduli collegati in scrittura → ogni modulo deve essere collegato al bus attraverso un'interfaccia.
L'interfaccia è un dispositivo, posto tra il modulo e il bus, che prima di passare al bus il nuovo valore da scrivere verifica che nessun altro modulo stia scrivendo sul bus.
Il buffer tri-state è un'interfaccia che agisce a seconda dei valori di enable, pilotati da un decoder:
* e = 1: il modulo è collegato al bus, e l'interfaccia lascia passare l'uscita del modulo verso il bus;
* e = 0: il modulo è in alta impedenza (l'uscita è Z), cioè è elettricamente scollegato dal bus e la scrittura è inibita.
Il transceiver è un'interfaccia generica che permette la bidirezionalità del segnale (sia in lettura sia in scrittura).

### Memorie

Le memorie sono dei moduli/dispositivi in grado di memorizzare m parole di parallelismo n e di mantenerle nel tempo. A differenza dei registri, le memorie possono leggere o scrivere da/su una sola parola per volta. Il segnale di indirizzo su log$_2$m bit fornisce l'indice della parola; i segnali di read e di write specificano se la parola è da leggere o scrivere. Manca il segnale di clock → le specifiche devono indicare i parametri temporali della memoria, come il tempo minimo di attesa tra un'operazione e l'altra e il tempo di lettura della parola in ingresso, in base ai ritardi interni della memoria.
Un segnale di enable serve per accecare la memoria ai segnali di ingresso e per eventualmente mettere l'uscita a un bus in alta impedenza.

#### Memoria RAM

Le memorie RAM sono delle memorie cosiddette volatili perché il contenuto viene cancellato quando si scollega l'alimentazione. Le memorie RAM si possono inserire internamente in un circuito oppure su piastre.

##### Operazione di scrittura

Un decoder riceve in ingresso il segnale di indirizzo e seleziona una parola attivando uno degli m segnali di load, il quale, per mezzo di una porta AND che lo affianca al segnale di write, attiva la scrittura nella parola di indice corrispondente.

##### Operazione di lettura

Il multiplexer, ricevendo il segnale di indirizzo (sempre accoppiato in AND con il segnale di read), seleziona una parola e ne riporta l'uscita.

#### Memoria ROM

A differenza delle RAM, le memorie ROM sono in sola lettura. Il contenuto viene determinato all'atto della fabbricazione e non può più essere modificato successivamente. La memoria ROM è un modulo combinatorio perché l'uscita dipende solo dall'ingresso dell'indice di parola corrente.

#### Banchi di memoria

Se la lunghezza delle parole è maggiore del parallelismo di un modulo, si possono affiancare più moduli su cui suddividere le parole, a cui fornire le opportune porzioni di bit e parallelamente il segnale di indirizzo comune.
Se invece la suddivisione è fatta sullo spazio di indirizzamento, i dati vengono forniti parallelamente a tutti i moduli tramite un bus. Come segnali di enable si devono usare direttamente i bit più significativi degli indirizzi di memoria, che possono essere elaborati da un decoder o più semplicemente, nel caso di 2 moduli, inviati in via diretta a un modulo e attraverso un inverter all'altro.

### Moduli programmabili
#### PLA

Le PLA aiutano a costruire un circuito di tipo combinatorio in modo più semplice ed economico: il costruttore può infatti programmare una PLA, cioè può collegare le singole porte logiche non direttamente a mano ma attraverso dei segnali elettrici, in modo da personalizzarla in base alla funzione booleana che vuole implementare. La programmazione di una PLA è irreversibile perché si può fare una volta sola.
Un esempio di applicazione è la codifica di un numero in una visualizzazione a trattini sul display del supermercato.

#### FPGA

L'FPGA aggiunge alla PLA una componente sequenziale e la possibilità di riprogrammare più di una volta il circuito. Rappresenta una soluzione intermedia tra il costo di progettazione e l'efficienza della soluzione HW e la flessibilità della soluzione SW.
L'FPGA viene utilizzata spesso per i prototipi: il programmatore può sperimentare il suo codice sull'FPGA prototipo mentre aspetta che venga sviluppato il più ottimizzato circuito integrato ASIC (= soluzione HW).

## Cenni sul consumo

Il consumo nel tempo di corrente da parte di un circuito è definito in termini di:
* energia totale (potenza effettiva)
* dissipazione del calore

### Parametri

* consumo statico: (trascurabile) è fisso perché si deve solo al fatto di essere alimentato, anche se i transistor non commutano;
* consumo dinamico: dovuto ai transistor che commutano un numero di volte proporzionale alla frequenza di clock → si deve ridurre il più possibile, facendo attenzione alle prestazioni.

## Note

* ↑ Due diagrammi di stato si dicono equivalenti se a parità di sequenze di ingresso, il comportamento non cambia.
* ↑ Il puntino su una variabile indica che la variabile può comparire affermata o negata.
* ↑ I valori assunti dalla variabile di stato sono rappresentati in formato binario anziché in lettere.
* ↑ Solitamente il numero di parole m è una potenza di 2.