Breve guida AL LINGUAGGIO ASSEMBLY (emulatore

Transcript

Breve guida AL LINGUAGGIO ASSEMBLY (emulatore
LABORATORIO DI SISTEMI – ASSEMBLY 8086
PROF. CARMELO CALARCO
Breve guida
AL LINGUAGGIO
ASSEMBLY
(emulatore EMU8086)
1
LABORATORIO DI SISTEMI – ASSEMBLY 8086
IL LINGUAGGIO ASSEMBLY
Il linguaggio assembly è un linguaggio di programmazione a
basso livello. Per linguaggi di basso livello si intendono il
sottogruppo linguaggi di programmazione orientanti alla
macchina, al contrario del linguaggio di programmazione ad alto
livello che è orientato all'utente.
Un esempio di linguaggio a basso livello è l'assembly.
Per programmare in assembly è necessario conoscere la struttura
di base di un PC. La struttura più semplice di un computer può
essere così schematizzata:
Il SYSTEM BUS (parte colorata in giallo) connette le varie
componenti del computer.
La CPU è il cuore di un computer, esegue tutte le
operazioni di calcolo e rappresenta quindi il parametro
principale per valutare le prestazioni di un computer. È
composta da un’unità con funzioni aritmetiche e logiche
chiamata ALU (Arithmetic/Logic Unit), da un’unità di
controllo e temporizzazione chiamata CTU (Control/Timing
Unit) e dai registri, piccole memorie che contengono i dati
2
LABORATORIO DI SISTEMI – ASSEMBLY 8086
da utilizzare nelle operazioni matematico/logiche o di
controllo.
La RAM è l’area di memoria in cui i programmi sono
caricati per poi essere mandati in esecuzione.
Il processore 8086 ha una serie di registri (14) a 16 bit, è possibile distinguere
tra:
registri accumulatori, utilizzabili indifferentemente come registri a 16 bit
(word) o 8 bit:




AX – registro accumulatore (diviso in AH / AL).
BX – registro base, contiene l’indirizzo di base di una tabella o di un
vettore (diviso in BH / BL).
CX – registro contatore usato nelle operazioni fra stringhe e nelle
iterazioni come registro contatore a sedici bit (diviso in CH / CL).
DX – registro dati (diviso in DH / DL).
Questi registri sono usati normalmente per i seguenti scopi:
- operazioni aritmetiche ad otto e a sedici bit;
- operazioni logiche;
- trasferimento dei dati.
Registri indice, contengono l’indirizzo per raggiungere le locazioni di memoria
all’interno del segmento dati, sono due:


SI - registro indice sorgente.
DI – registro indice destinazione.
3
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Registri puntatore, (o Index o Offset) sono generalmente utilizzati come
puntatori a dati in memoria (contengono cioè gli indirizzi di memoria). Si
possono dividere in:



BP – registro puntatore alla base dello stack (Base Pointer).
SP – registro puntatore alla fine dello stack (Stack Pointer).
IP – registro puntatore delle istruzioni: lavora in parallelo al segmento
CS e punta all’ istruzione che è in esecuzione.
Lo stack è un’area di memoria della CPU in cui i dati vengono estratti col
metodo FIFO (First In First Out)
Registri di segmento
La memoria della CPU è suddivisa in paragrafi, costituiti da 16 byte contigui e
da segmenti costituiti ciascuno da 64k byte. Ogni segmento inizia in
corrispondenza di un paragrafo, ossia ad un indirizzo multiplo di 16.




CS – segmento del codice: punta all’indirizzo di testa del segmento
contenente il codice del programma.
DS – segmento dei dati: punta all’indirizzo di testa del segmento
contenente i dati usati dal programma.
ES – segmento extra, ovvero segmento dati aggiuntivo.
SS – segmento dello stack: punta al segmento contenente lo stack.
Registro dei flag o di stato
Si tratta di un registro a 16 bit, chiamato anche registro di stato, contenente 9
bit utilizzati per indicare differenti condizioni durante l’esecuzione del
programma.
15
14
13
12
11
OF
10
DF
09
IF
08
TF
07
SF
06
ZF
05
04
AF
03
02
PF
01
00
CF
I bit 0,2,4,6,7,11, contengono flag di stato, che indicano risultati di
operazioni di programma.
I bit 8,9,10, contengono flag di controllo. Gli altri non vengono utilizzati.
4
LABORATORIO DI SISTEMI – ASSEMBLY 8086
SINTASSI LINGUAGGIO ASSEMBLY
Il processore 8086 è un processore a due indirizzi, la sintassi generale è la seguente:
ISTRUZIONE
DESTINAZIONE, SORGENTE
dove:
 istruzione è un codice operativo;
 destinazione è l’operando che riceve il risultato;
 sorgente è l’operando che fornisce un valore al microprocessore.
La destinazione può essere un registro o una variabile.
La sorgente può essere un registro, una variabile, una costante.
Vediamo alcuni esempi possibili:
MOV ax,bx
MOV bx,ax
MOV variabile,ax
ed alcuni esempi errati:
ADD al,bx (dimensioni diverse)
ADD var1,var2 (due variabili)
ADD 5,ax (la dest. non può essere una costante)
5
LABORATORIO DI SISTEMI – ASSEMBLY 8086
INDIRIZZAMENTO DEI DATI DEL PROCESSORE
8086
Gli indirizzamenti possibili sono:
1) indirizzamento immediato, il sorgente è una costante:
MOV AL,8
(cifra decimale)
MOV AL,0FH
(cifra esadecimale, seguita dal suffisso H e prec. dallo 0 se
inizia con una lettera)[B:binario/O:ottale]
2) indirizzamento con registro, gli operandi sono dei registri:
MOV AX,BX
ADD DL,AL
CMP AX,DX
MOV CX,BH (non valida - dimensioni diverse)
3) indirizzamento diretto, uno dei due operandi è una variabile:
MOV AX,PIPPO
MOV PLUTO,AL
MOV TIZIO,5
MOV 5,TIZIO (non valida – costante come destinazione)
MOV CAIO,TIZIO (non valida – due variabili)
6
LABORATORIO DI SISTEMI – ASSEMBLY 8086
MODELLO DI UN PROGRAMMA IN ASSEMBLY CON L’EMULATORE EMU8086
LABORATORIO DI SISTEMI – ASSEMBLY 8086

alcuni modelli di memoria processore 8086:
TYNY: unico seg per i dati e per il codice;
SMALL: un seg per il codice ed uno per i dati;
COMPACT: un seg per il codice e più seg per i dati;
MEDIUM: un seg per i dati e più seg per il codice;
LARGE: più segmenti per i dati e per la memoria;

Definizione di Costanti
• Le costanti sono nomi dati a valori
• non compaiono nel codice oggetto ed eseguibile
– Il valore di una costante non può essere modificato
• Durante la traduzione, l’assemblatore sostituisce ogni occorrenza
del nome di una costante con il valore corrispondente
– Esempi:
MAX EQU 10h
VAT EQU ‘@’
MOV AH,MAX ;diventa MOV AH,10h
MOV AL,VAT ;diventa MOV AL,40h (cod. ASCII di @) ***

Definizione di variabili
• Sintassi:
<nome> <tipo> <val_iniziale>
dove:
<nome> è un identificatore
<tipo> indica la dimensione e può essere
– DB: Byte (8 bit)
– DW: Word (16 bit)
– DD: Double Word (32 bit) (non usato nell’8086)
<val_iniziale> è il valore di inizializzazione e può essere
– un valore numerico (es.: VAR1 DB 10)
– una stringa di caratteri (es.: VAR1 DB ”casa: $”)
– il carattere ? (indica nessun valore, es.: VAR1 DB ?)
8
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 Dichiarazione di una stringa di caratteri:
.data
MESSAGGIO1 DB "Inserisci un carattere $"
 Codice per l’output di una stringa di caratteri:
MOV DX,OFFSET MESSAGGIO1
MOV AH,09H
INT 21H
 Codice che sposta a capo il cursore:
.data
CAPORIGA DB 13,10,"$"
 Input di un carattere inserito dalla tastiera:
(il carattere digitato viene inserito nel registro AL)
.data
CARAT DB ?
…
MOV AH, 01H
INT 21H
=> viene caricato in AL
MOV CARAT, AL
 Output di un carattere inserito dalla tastiera:
MOV DL, CARAT
MOV AH, 02H
INT 21H
9
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 Dichiarazione di una variabile stringa:
.data
STRINGA DB N,?,N DUP (?)
 i cicli:
MOV CX,VALORE
OBIETTIVO:
…
…
LOOP OBIETTIVO
 Salto incondizionato:
etichetta:
…
…
JMP etichetta
JMP etichetta1
…
…
etichetta1:
 Confronto:
CMP DEST, SORG
Esempi di confronto:
cmp registro,variabile
cmp registro,registro
cmp variabile,costante
cmp registro,costante
es.:
– cmp ax,var1
– cmp ax,bx
– cmp var,5
– cmp al,0dh
cmp var1,0dh (13)
je etichetta
10
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 Salti condizionati senza segno:
(in funzione del risultato della CMP)
JE/JNE: salta se DEST=/≠SORG
(sintassi JE/JNE <etichetta>)
JB/JBE: salta se DEST</<=SORG
(sintassi JB/JBE <etichetta>)
JA/JAE: salta se DEST>/>=SORG
(sintassi JA/JAE <etichetta>)
 Salti condizionati con segno:
(in funzione del risultato della CMP)
JE/JNE: salta se DEST=/≠SORG
(sintassi JE/JNE <etichetta>)
JL/JLE: salta se DEST</<=SORG
(sintassi JL/JLE <etichetta>)
JG/JGE: salta se DEST>/>=SORG
(sintassi JG/JGE <etichetta>)
11
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 incremento:
INC VAR1
INC BX
 decremento:
DEC VAR1
DEC BX
 sottrazione:
(sintassi SUB DEST, SORG)
esempi:
SUB AX,10
SUB AX,AX
SUB VAR1,10
SUB AX,BX
SUB BX,VAR1
 addizione:
(sintassi ADD DEST,SORG)
esempi:
ADD AX,10
ADD VAR1,10
ADD AX,BX
ADD BX,VAR1
12
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 divisione:
• Senza segno: DIV (DIVision, unsigned)
Sintassi: DIV <source>
SUB AX,AX ; azzeramento del registro
• Divisione di un byte per un altro byte
MOV AL,VAR1 ; dividendo a 8 bit
DIV VAR2 ; quoziente in AL e resto in AH
• Divisione di una word per un byte
MOV AX,VAR1 ; dividendo a 16 bit
DIV VAR2 ; quoziente in AL e resto in AH
• Con segno: IDIV (Integer DIVision)
– Stessa sintassi di DIV
 moltiplicazione:
• Senza segno: MUL (MULtiply, unsigned)
Sintassi: MUL <source>
MOV AL,NUMERO1 ; operando a 8 bit
MUL NUMERO2 ; risultato in AL (8 bit)
MOVE AX,NUMERO1 ; operando a 16 bit
MUL NUMERO2 ; risultato in AX (16 bit)
• Con segno: IMUL (Integer MULtiply)
– Stessa sintassi di MUL
13
LABORATORIO DI SISTEMI – ASSEMBLY 8086

Le variabili (array)
• Gli array sono sequenze di dati di tipo omogeneo
– Es.: vettori numerici (1,2,5,3)
– Es.: stringhe di caratteri (“prova”)
• Le variabili array si dichiarano come segue:
a DB 1, 4, 6, 16, 3, 0 ; array di 6 byte
b DB ‘H’,’e’,’l’,’l’,’o’ ; array di caratteri
c DB 5 DUP(9) ; come c DB 9,9,9,9,9
d DW 10 DUP(?) ; array di 10 word non inizializzate

Uso delle variabili array
• Per leggere/scrivere il contenuto di un elemento:
– MOV <Registro>, <Variabile>[indice]
– MOV <Variabile>[indice], <Registro>
• Esempio:
MOV AL, a[3]
;copia in AL l’elemento dell’array a di indice 3
• E’ possibile usare i registri BX, SI, DI, BP per
contenere l’indice:
MOV SI, 3
MOV AL, a[SI]
; copia in AL l’elemento dell’array a di indice 3
14
LABORATORIO DI SISTEMI – ASSEMBLY 8086
 vettori di caratteri non definito:
dimensionamento:
DIM EQU 10 (inizio del progr.)
dichiarazione:
VET DB DIM DUP (?)
definizione nel programma:
VET[SI] >SI indice del vettore
15
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Esempi di codice:
 Trasformazione di un carattere in un numero
SUB NUM, 30h
(sottrae al valore corrispondente del codice ASCII del
carattere il valore 30h[48d], il risultato è un valore
che va da 0 a 9 [per es. se il carattere inserito da
tastiera num = 2, il corrispondente codice ASCII è 50,
sottraendo 48, avremo 2 come valore numerico] )
 Trasformazione di un numero ad una cifra in
un carattere
ADD NUM, 30h
(somma al valore corrispondente del codice ASCII del
carattere il valore 30h[48d], il risultato è un valore
che va da 48 a 57 [per es. se il valore di num = 2, il
corrispondente codice ASCII è 50, sommando 48,
avremo 50] )
16
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Input numero a due cifre:
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Visualizzazione numero a due cifre:
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Input/output vettore di un carattere:
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Input di un vettore numerico con elementi a 2 cifre:
n EQU 10
…….
LABORATORIO DI SISTEMI – ASSEMBLY 8086
Output di un vettore numerico con elementi a 2 cifre: