Architettura dei calcolatori elettronici
Linguaggio macchina Parte 2
Per definire il linguaggio macchina di un processore bisogna elencare le istruzioni macchina.
Sintassi e semantica di ogni istruzione
Facciamo uso delle seguenti abbreviazioni o convenzioni:
ACC indica il registro accumulatore
IND " l' indirizzo di una cella di memoria
( x ) " il contenuto di x
<---- " il trasferimento (copia)
UL " ( indirizzo dell' ) unità di lettura ( INPUT )
US " ( indirizzo dell' ) unità di scrittura ( OUTPUT )
Una espressione valida può essere (IND) <---- (UL) che esegue l'operazione di lettura. E' sbagliato scrivere ( IND ) <---- UL , mentre è corretto scrivere:
(IND) <---- 12 che copia il valore 12 nella cella.
La prima istruzione che consideriamo e l'istruzione somma che consente di sommare il contenuto del registro accumulatore ACC con il contenuto della locazione di memoria di indirizzo IND e di copiare il risultato ottenuto nel registro accumulatore che così perde il precedente valore. La semantica sarà:
( ACC ) <----- ( ACC ) + ( IND ) ;
l'istruzione somma ha codice operativo 1 per cui la sintassi sarà:
Tabella 4.1
1 | IND |
Es. se ho una cosa del genere :
Tabella 4.2
1 | 21 |
nota: nella lezione 3 avevamo visto che il codice operativo della somma era 0100 cioe' 4, ma cio' non influenza il discorso didattico che stiamo perseguendo.
e nella memoria all'indirizzo 21 ho come contenuto della cella il valore 113 e nell'ACC ho come contenuto il valore 20, avremo che l'effetto della seguente espressione :
( ACC ) <----- ( ACC ) + ( IND ) sarà quello di avere nell'accumulatore il valore 133. Infatti devo sommare 20 + 113 e trasferire il risultato della somma nell'ACC. Nella realtà si lavora con numeri binari per cui codice operativo ed operando saranno:
Tabella 4.3
001 |
00010101 |
OC OA
La CPU che noi consideriamo ha il seguente linguaggio macchina costituito soltanto da 6 istruzioni, questo implica che per scrivere programmi eseguibili noi dovremo limitarci soltanto a quelle istruzioni in linguaggio macchina! :
Tabella 4.4
Sintassi | Semantica | ||
codice operativo |
operando |
operazionale |
discorsiva |
1 | IND | ( ACC ) <--- ( ACC ) + ( IND ) |
Somma |
2 | IND | ( ACC ) <--- ( ACC ) - ( IND ) |
Sottrazione |
3 | IND | ( ACC ) <--- ( IND ) |
Loading |
4 | IND | ( IND ) <--- ( ACC ) |
Memorizz. |
5 | IND | ( IND ) <--- ( UL ) |
Lettura |
6 | IND | ( US ) <--- ( IND ) |
Scrittura |
Esempio di programma exe:
Tabella 4.5
0101 | 000000000111 |
che corrisponde alla seguente : il primo numero è il 5 in binario quindi è una operazione di lettura ,
il secondo numero è il 7 in binario per cui avremo:
( 7 ) <----- ( UL )
il dato letto da input viene trasferito nella cella di memoria di indirizzo 7
Tabella 4.6
0011 | 000000000111 |
codice operativo 3 operando 7 per cui avremo:
( ACC ) <---- ( 7 ) significato carica il contenuto della cella di indirizzo 7 nel registro accumulatore.
Tabella 4.7
0001 | 000000000010 |
codice operativo 1 operando 2 per cui avremo un' istruzione di
somma: (ACC ) <---- ( ACC ) + ( 2 )
__________________________________________
ESEMPIO
Supponiamo di volere scrivere un programma che , dati due numeri in Input, ne esegui la somma e stampi il risultato in Output.
Analisi
Dovremo leggere due numeri dall' unità di input ( cioè introdurre due dati in memoria ), facendo due operazioni di Input ( read), farne la somma e fare una operazione di output con il risultato ottenuto dalla somma.
Dati
Primo numero, secondo numero, risultato ( somma ).
Sintesi Algoritmo
L'analisi è già un algoritmo " raffiniamolo" tentando di usare tipi di operazioni ( istruzioni ) che la nostra CPU è capace di eseguire.
1) Leggi i 2 numeri e mettili in 2 celle di MC, ma sapendo che il calcolatore non è capace di fare una doppia lettura ho la necessità di un primo " raffinamento" cioè eseguo due read e metto i numeri ad esempio nella cella a e nella cella b
2) Somma i contenuti delle celle di memoria in cui sono stati inseriti i numeri letti e metti il risultato in una cella ad es. c , ma il calcolatore non è capace di fare direttamente la somma fra due celle e mettere il risultato in una terza.
3) Stampare il contenuto della cella c, questo il calcolatore lo può fare.
Raffinamenti
1)
1.1) leggi da input un numero e mettilo nella cella di indirizzo 0
1.2) leggi da input un numero e mettilo nella cella di indirizzo 1
2)
2.1) carica il primo numero
nell'accumulatore (ACC ) <--- ( IND )
2.2) somma tra ( ACC ) ed il secondo numero e metti il risultato in ACC.
2.3) memorizza il ( ACC ) nella cella di indirizzo 2
3) scrittura ( US ) <----- ( 2 )
Tabella 4.8 MEMORIA
0 | 10 |
1 | 38 |
2 | 48 |
CONTENUTO dell'ACCUMULATORE NELLE VARIE FASI:
Tabella 4.9
FASE x | es. 144 |
" 2.1) | 10 |
" 2.2) | 48 |
PROGRAMMAZIONE
Semantica
1.1) ( 0 ) <----- ( UL )
1.2) ( 1 ) <---- ( UL )
2.1) ( ACC ) <---- ( 0 )
2.2) ( ACC ) <---- ( ACC ) + 1
2.3) ( 2 ) <---- ( ACC )
3) ( US ) <---- ( 2 )
Questo programma è scritto in linguaggio macchina simbolico ma non in formato binario o decimale. Sono 6 istruzioni, che usando la sintassi su menzionata possiamo scrivere anche :
Tabella 4.10
5 | 0 | lettura primo numero |
5 | 1 | lettura secondo numero |
3 | 0 | caricamento |
1 | 1 | somma |
4 | 2 | memorizzazione |
6 | 2 | stampa |
Esplicitiamo la terza riga 3 0 il tre rappresenta l'operazione di loading " caricamento" lo zero rappresenta l'indirizzo della cella di memoria, per cui corrisponde tale riga alla ( ACC) <--- ( 0 ), cioè carica il dato contenuto nella cella di memoria zero nel contenuto del registro accumulatore avente indirizzo ACC . Affinché il programma possa essere eseguito deve essere memorizzato in MC per cui avremo delle celle che contengono i DATI, ad es. le celle 0, 1, 2, ..... e le celle che contengono il programma; supponendo che la prima istruzione sia contenuta nella cella di indirizzo 100 avremo una cosa del genere: Rappresentazione decimale di istruzioni e indirizzi.
Tabella 4.11
indirizzi | istruzioni | |
0 | (numero1) | |
1 | (numero2) | |
2 | (risultato) | |
. | . | . |
. | . | . |
99 | . | . |
100 | 5 | 0 |
101 | 5 | 1 |
102 | 3 | 0 |
103 | 1 | 1 |
104 | 4 | 2 |
105 | 6 | 2 |
106 |
Un utile esercizio può essere quello di: tradurre la Tabella 4.11 in formato binario così come è effettivamente rappresentata nella memoria del calcolatore.
Vediamo adesso la Esecuzione simulata
Avendo come dati di input il numero 12 ed il numero 16, ed ipotizzando che il programma sia caricato in MC a partire dalla cella di indirizzo 100. Per cui:
------------------------------------------------------------------
( PC ) <---- 100
FETCH : * ( IR ) <----- ( (PC) ) cioè nel contenuto di IR va il (100) ossia l'istruzione nella cella 100.
* ( PC ) <----- ( PC ) + 1 dentro PC avrò 101;
EXECUTE: lettura
Tabella 4.13
0 |
12 |
------------------------------------------------------------------
FETCH : ( IR ) <------ ( 101 ) ; ( PC ) <----- 102;
EXECUTE: lettura
Tabella 4.14
0 | 12 |
1 | 16 |
-----------------------------------------------------------
FETCH : ( IR ) <----- ( 102 ) ; ( PC ) <----- 103
EXECUTE : caricamento ( ACC ) <----- ( 0 ) cioè il numero 12
-----------------------------------------------------------
FETCH : ( IR ) <----- ( 103 ) ; ( PC ) <----- 104
EXECUTE : somma ( ACC ) <----- ( ACC ) + ( 1 )
-----------------------------------------------------------------
FETCH : ( IR ) <------ ( 104 ); ( PC ) <----- 105
EXECUTE : memorizzazione ( 2 ) <------ ( ACC )
Tabella 4.15
0 | 12 |
1 | 16 |
2 | 28 |
------------------------------------------------------------------
FETCH : ( IR ) <------ ( 105 ) ; ( PC ) <----- 106
EXECUTE : stampa il 28 ( US ) <------ ( 2 )
------------------------------------------------------------------
STOP "lo diciamo noi " ma il calcolatore continuerebbe.
Abbiamo usato 0, 1, 2 come celle per i dati e queste informazioni sono incise nel programma. Se volessimo usare altre celle invece di queste? es. il primo numero nella cella 10 il secondo numero nella cella 11 il risultato della somma nella cella 12 ( è abbastanza logico inserirli in sequenza) il programma cambia un pò ma fà la stessa cosa.
Tabella 4.16
5 |
10 |
5 |
11 |
3 |
10 |
1 |
11 |
4 |
12 |
6 |
12 |