Assembler 8086

IL DEBUG

Il DEBUG è un'utility di uso frequente dell'MS-DOS e serve per la ricerca e l’ eliminazione degli errori nei programmi; Esso ci consente di visualizzare passo-passo tutte le istruzioni che vengono eseguite tramite il comando T; ci permette di scrivere dei programmi in assembler ed eseguirli; inoltre si possono leggere i registri e vedere i valori delle celle di memoria.

Per iniziare a scrivere con il DEBUG andare sul sistema operativo MS-DOS.

Al prompt dell'MS-DOS scrivere

DEBUG  (senza estensione) 

c:>DEBUG (invio)

-

(Nota: Il debug risponde con un trattino il quale indica che ora non bisogna inserire comandi del DOS ma comandi conosciuti dal DEBUG ; in altre parole indica che sta aspettando un comando dall'utente)

Se dopo il trattino inseriamo il simbolo ? cioè

- ? (invio)

il sistema ci permette di vedere tutti i comandi del DEBUG

PROMPT DEI COMANDI DEL DEBUG

Dopo essere entrati in debug inserire -?  per visualizzare i comandi del debug e la loro sintassi:

-? (invio)

Comandi del Debug del microprocessore 8086

Comandi del debug:

Assembla A [indirizzo]

Confronta C intervallo indirizzo

Dump D [intervallo]

Immetti E indirizzo [elenco]

Riempi F intervallo elenco

Vai G [=indirizzo] [indirizzi]

Esadecimale H valore1 valore2

Input I porta

Carica L [indirizzo] [unità] [primosettore] [numero]

Muovi M intervallo indirizzo

Nomina N [nomepercorso] [elencoargomenti]

Output O porta byte

Procedi P [=indirizzo] [numero]

Esci Q Registro

R [registro]

Cerca S intervallo elenco

Traccia T [=indirizzo] [valore]

Disassembla U [intervallo]

Scrivi W [indirizzo] [unità] [primosettore] [numero]

Assegna memoria espansa XA [n.pagine]

Rilascia memoria espansa XD [handle]

Mapping pagine di memoria espansa XM [pagLog] [pagFis] [handle]

Visualizza stato memoria espansa XS -

Visualizzazione dei registri

Visualizzazione dei registri e sua modifica.

IL COMANDO R:

Dopo essere entrati nel debug se dopo il trattino inseriamo il simbolo R cioè

-R (invio)

il sistema ci permette di vedere i registri con i loro contenuti. I registri sono piccole aree di memoria; si trovano nella CPU, ma non devono essere confusi con la memoria. Infatti i registri, come la memoria, servono a memorizzare un'informazione, ma sono anche, a differenza della memoria, piccole aree di lavoro privilegiate sulle quali è possibile effettuare operazioni di tipo specifico. Infatti tra tutte le istruzioni che ogni microprocessore è in grado di fare sul contenuto dei registri, non di tutte le istruzioni ne esiste la corrispondente sulla memoria. Da questo segue che per poter eseguire tali istruzioni è necessario prima effettuare il trasferimento dei dati dalla memoria ai registri. Da tutto questo discorso si evince che le operazioni sui registri sono più veloci di quelle sulla memoria. Infatti lavorando con i registri le informazioni non devono essere più indirizzate in nessun posto e non devono arrivare all'Unità Centrale attraverso il BUS DATI. A differenza della memoria, in ogni microprocessore il numero dei registri è fisso.

Nel caso dell'8086/8088 i registri sono 14 ed ognuno ha la lunghezza di una parola cioè di 16 bit. Nel DEBUG si usa solo il sistema ESADECIMALE, non c'è quindi la necessità di inserire la lettera H finale, ma se si vuole mettere è indifferente. 

Il comando R del DEBUG non si limita a visualizzare i registri, ma se aggiungiamo il nome del registro, il comando indicherà al DEBUG che desideriamo visualizzare il registro e poi modificarlo.

ESEMPIO:

-R CX (invio) permette di vedere i contenuti del registro CX; mentre

-R AX (invio)

AX 0000 (risposta del DEBUG)

: 3A7 (invio)

 se dopo i due punti scriviamo 3A7 vuol dire che vogliamo modificare AX e che al posto del valore che prima aveva cioè 0000 vogliamo inserire 3A7. A questo punto per vedere se il DEBUG ha effettuato il cambiamento che noi volevamo, basta digitare di nuovo il comando che ci permette di vedere i registri, cioè R

-R (invio)

avremo

AX 03A7

BX=.................... eccetera.

Il comando D

Il comando D

- D (invio)

permette di leggere un blocco di memoria; compaiono 8 righe organizzate in tre colonne. Nella colonna di sinistra vi sono due numeri esadecimali separati da : che non è un segno di divisione; E' un modo contorto per scrivere gli indirizzi di memoria, le cui motivazioni sono ormai prevalentemente storiche ma che è di uso universale e quindi intoccabile.

L'indirizzo si calcola così: si prende il primo numero, lo si moltiplica per 16 decimale (oppure per 10H in esadecimale, cioè si aggiunge uno zero in fondo a destra: è esadecimale (shift a sinistra)) e si somma il secondo.

ADDR=segment*10H+OFFSET

Esempio:

0E23:0100

significa

E230+100=E330

Questo è l'indirizzo della prima posizione di RAM considerata.

Nella colonna centrale appaiono, su ogni riga, 16 coppie di cifre esadecimali. Ciascuna coppia corrisponde a un byte e descrive l'attuale contenuto di un particolare byte in memoria. Quello più a sinistra è il contenuto del byte il cui indirizzo è dato, nel modo indicato nella colonna di sinistra; quello successivo è il contenuto del byte successivo (quindi nell'esempio fatto, di indirizzo E331), e così via fino all'ultimo, corrispondente all'indirizzo E33F.

Alla riga successiva, all'estremità sinistra, troviamo l'indirizzo E33F. Alla riga successiva, all'estremità sinistra, troviamo l'indirizzo E340, e il discorso ricomincia.

Il comando D ci permette quindi di esaminare il contenuto di

8*16=128 byte per volta.

La colonna di destra contiene in ciascuna 16 caratteri alfanumerici, che costituiscono una rappresentazione figurativa dei corrispondenti byte della colonna centrale, secondo la codifica, detta ASCII, di uso pressoché universale. Se i byte in memoria rappresentano un testo scritto questa codifica ci permette di "leggere" facilmente il testo; se rappresenta un programma o dati numerici codificati in altra forma, essa non serve assolutamente a nulla. Avendo dato soltanto il comando D il programma DEBUG ha scelto di sua iniziativa un'area di RAM disponibile per scrivere nuovi programmi, ma è possibile fargli visualizzare qualunque area della memoria compresa entro i primi 1048576 byte facendo seguire il D dall'indirizzo iniziale (scritto sempre nel solito modo contorto che gli piace tanto).

Provate ad esempio a dare il comando

-D FFFF:0

così facendo leggete un pezzo di ROM. Il suo contenuto è generalmente incomprensibile (è scritto in linguaggio macchina), tuttavia nella prima riga, colonna di destra leggete una data: essa è la data in cui è stata scritta la ROM, che serve per identificazione e che è leggibile in codice ASCII. Diamo adesso il comando

-D 0100 (invio)

permette di leggere un blocco di memoria a partire dall'indirizzo 0100 indicato. 

Il comando A

Il comando A

- A (invio)

converte le istruzioni in codice macchina (A=assembla)

-A 0100 (invio)

assembla il programma dall'indirizzo 0100

A questo punto si può iniziare a scrivere un programmma :

- A 0100 (invio)

MOV AL,10 (invio)

......................

 altre istruzioni

INT 3

 questa istruzione indica che il programma è terminato;

L'istruzione INT 3 , è un'interruzione di tipo tre e ci permette di tornare al DOS. Alla fine di ogni programma scritto in assembler bisogna mettere tale interruzione. 

Il comando U

Il comando U

- U (invio) 

Il comando U disassembla le istruzioni, ci permette di vedere l'ultimo indirizzo e possiamo quindi stabilire il numero di celle occupate dal programma. Nell'esempio precedente supponiamo di avere: 110 INT 3

allora per vedere quanto è lungo il nostro programma dobbiamo fare la differenza tra l'ultima cella occupata dall'istruzione INT 3 e la prima cella del nostro programma che nel nostro esempio iniziava con 0100 cioè (0110-0100)+1 sono le celle occupate dal nostro programma

l comando Q

Per uscire dal DEBUG si utilizza il comando

-Q (invio)

Questa istruzione vuol dire  quit cioè comando per uscire dal DEBUG

Nota :

dati= byte sui quali facciamo le operazioni

indirizzo= numero che identifica la cella contenente un byte, che rappresentano dei dati.

Struttura di un programma in Debug

 Quando si scrive un programma con il DEBUG si può iniziare con il comando

-A 0100

……….

istruzioni

-int 3

Il comando int 3 (cioè interruzione di tipo 3) deve essere inserito alla fine del nostro programma e consente di ritornare al sistema operativo.

Per disassemblare il programma si utilizza

-U (invio)

che disassembla le istruzioni e ci permette di vedere l'ultimo indirizzzo. Per stabilire il numero di celle occupate dal nostro programma bisogna vedere l'indirizzo in cui abbiamo inserito il valore di int 3.

Ad esempio se il programma è arrivato all'indirizzo 110 int 3 vuol dire che le celle occupate sono (110-100)+1=11 ove 100 è l'indirizzo di inizio, 110 è l'indirizzo finale, +1 perché è quello attuale. 

Salvataggio di un file

Per salvare il programma da noi scritto in un floppy-disk si usa la seguente procedura:

-N a:\nome.com (invio)

comando per salvare il file nome.com in assembler

-R BX (invio)                registro da cui si inizia a salvare il file

0 (invio)                       comando per azzerare il contenuto di BX

-R CX (invio)                registro in cui si termina il salvataggio

-11 (invio)                     numero di celle occupate dal programma nell' esempio 11

-w (invio)                     significa write e consente di salvare il programma

Riapertura di un file

Per recuperare il programma sul disco: uscire dal debug con il comando:

-Q (invio)

Il computer si posiziona in C: digitare

c:\DEBUG a:\nome.com (invio)

-u 100 (invio)       per visualizzare il programma salvato dalla posizione 100

-r (invio)              per vedere la prima riga del comando

-t (invio)               per vedere passo-passo il programma