|
Tutorial
|
Dettaglio Istruzioni |
|
|
 |
Istruzioni
della Cpu 80x86 |
SCHEDA n° 07 [I/
167
di 198] |
 |
|
SCAS - Confronta
i dati di un'area di memoria con l'accumulatore, modificando le flags |
|
 | Questa istruzione confronta
il contenuto dell'accumulatore con quello di una locazione di memoria
puntata da ES:DI
e
modifica le flag in funzione del risultato. |
 | In pratica simula
la sottrazione dell'operando destinazione dall'accumulatore
senza però alterare
il contenuto dell'accumulatore (come farebbe invece l'effettiva
sottrazione, SUB); questo basta per
modificare le flag coinvolte dal risultato e a favorire gli eventuali salti
condizionati (Jxx) conseguenti. |
 | Per funzionare correttamente è necessario
specificare un operando destinazione, di solito l'etichetta
del primo dei dati da confrontare con l'accumulatore; in questo
modo l'assemblatore è in grado di stabilire la dimensione del dato
da assumere dalla memoria; se l'operando non viene aggiunto l'assemblatore segnala errore. |
 | In questo modo è chiara anche la dimensione
del registro (accumulatore) di destinazione, cioè AL
se il dato letto è un byte, AX
se word e EAX
se doubleword (con processori 80386/486). |
 | L'istruzione è particolarmente utile per trovare
un determinato byte o carattere in una stringa
o in una tabella; per confrontare
2 stringhe o tabelle è disponibile la CMPS,
che si basa sul medesimo principio di funzionamento. |
 | Nonostante la necessità di dichiarare
l'operando sorgente (solo per motivi di corretta compilazione) i dati sono
comunque assunti
dalla locazione puntata da ES:DI, per
cui l'uso di questa istruzione ha senso solo se, in precedenza, il registro DI è stato inizializzato con l'etichetta usata come operando,
per esempio anticipando la SCAS
ES:Testo01 con LEA
DI,Testo01, vedi esempio successivo). |
 | Le sue caratteristiche sono riassunte nella
seguente tabella (leggi le istruzioni
): |
SCAS
SCAS
ES:[DI] |
Cambia
le Flag simulando {Accumulatore
- ES:[DI]} |
|
|
Esempio
di Applicazione |
Cicli
di Clock |
Mem
Acces |
N°
Bytes |
Flag
influenzate |
| Mnemonico |
Operandi |
86 |
268 |
386 |
486 |
O |
D |
I |
T |
S |
Z |
A |
P |
C |
SCAS
|
[Depo01]
|
15 |
7 |
7 |
6 |
1 |
1 |
# |
|
|
|
# |
# |
# |
# |
# |
SCAS
|
[Depo02]
|
19 |
 | La tabella evidenzia che l'istruzione
modifica alcune flag. La figura seguente mostra le risorse
richieste da questa istruzione in funzione degli operandi
coinvolti (leggi le
istruzioni)
e sottolinea l'assoluta indipendenza del
codice generato dall'etichetta
della zona di memoria coinvolta, necessaria solo per evitare segnalazioni
d'errore da parte dell'assemblatore: |
|
Addr |
|
Codifica
Masm |
|
Istruzione |
|
0100
0101
0103 |
|
55
55AA
55AA1188 |
|
.386p
Depo01
DB 55H
Depo02 DB
55AAH
Depo04 DD 55AA1188H |
| ---- |
|
---------------- |
|
------ |
--------------------------- |
0107
0108
0109
010B
010C
010D
010F
0110
0111 |
|
AE
AF
66 AF
AE
AF
66 AF
AE
AF
66 AF |
|
|
SCAS Byte
Ptr ES:[DI]
SCAS Word Ptr ES:[DI]
SCAS Dword Ptr ES:[DI]
SCAS ES:Depo01
SCAS ES:Depo02
SCAS ES:Depo04
SCAS ES:[Depo01]
SCAS ES:[Depo02]
SCAS ES:[Depo04] |
|
 | Riassumendo, in dettaglio l'istruzione si
comporta in questo modo:
 | Il dato prelevato dalla locazione di
memoria ha la dimensione di un byte,
di una word o di
una doubleword. |
 | il segmento
dell'area Dati è
per default, ES e l'offset è per
default DI;
per questo è assolutamente necessario inizializzare i registri (insieme alla flag DF)
prima di utilizzarle; non è possibile
forzare un altro registro di segmento, con l'override. |
 | dopo aver confrontato il dato con l'accumulatore
aggiorna il valore del registro di offset (DI o
DSI),
in funzione del valore della flag di direzione DF
(che va quindi predisposta con certezza
prima di iniziare il
confronto):
 | se DF=0
(direzione in avanti) al puntatore viene sommato 1 (cioè viene
incrementato, se l'operando è un byte), 2 (se è una
word) o 4
(se ha dimensione doubleword). |
 | se DF=1
(direzione indietro) al puntatore viene sottratto 1
(cioè viene decrementato, se l'operando è un byte), 2 (se è una
word) o 4 (se ha dimensione doubleword). |
|
 | la presenza dell'operando è richiesta dalla sintassi
per consentire all'assemblatore di capire la dimensione
dei dati da trattare; esso deve dunque essere dichiarato con la specifica della
dimensione dei dati a cui fanno riferimento (Byte o
Word o Dword Ptr).
|
 | l'assemblatore compila comunque questa istruzione con il medesimo unico byte di
codice operativo con cui tratta le istruzioni da essa derivate, tutte
prive di operando, cioè SCASB,
se i dati manipolati sono bytes, SCASW
se sono word, o SCASD se doubleword.
|
|
 | Questa potente istruzione esegue con un solo
codice operativo il compito di 2 istruzioni, cioè equivale all'esecuzione del seguente codice: |
 | Prima di concludere è opportuno sottolineare che questa
istruzione può fruire dell'operatore di autoripetizione REPE
o REPNE: anteponendolo al suo mnemonico il processo di confronto
viene ripetuto automaticamente CX volte su tutta l'area sotto test, a meno
che non venga trovato un valore uguale (E) o diverso (NE) dall'accumulatore; per il
corretto uso dei questo prefisso è dunque necessario caricare
preventivamente CX con il numero di
confronti da eseguire. |
 | Data l'utilità di questa tecnica viene proposto un
esercizio d'esempio: |
|
Addr |
|
Codifica
Masm |
|
Istruzione |
|
|
0100 |
|
20 45
73 65 6D 70
69 6F 20 64 69 20
54 65 73 74 6F 20 |
|
Testo01
DB " Esempio di Testo " |
| ---- |
|
---------------- |
|
------------------ |
--------------------------- |
0112
0113
0117
0119
011C
011E
----
0122
0123
----
0125
0126 |
|
FC
8D 3E 0100
B0 54
B9 0012
F2 AE
0F 84 0125
----------------
90
EB 01
----------------
4F
90 |
|
;-----------------
tutte_diverse:
;-----------------
trovata_lettera_T:
continua: |
CLD
LEA DI,Testo01
MOV AL,'T'
MOV CX,18
REPNE SCAS
ES:Testo01
JE trovata_lettera_T
---------------------------
;
servizio non trovata "T"
NOP
JMP SHORT continua
;--------------------------
DEC DI
;servizio prima "T" trovata
;--------------------------
NOP |
|
 | L'analisi del codice suggerisce queste considerazioni:
 | la presenza dell'istruzione CLD
impone la lettura della memoria in avanti. |
 | per inizializzare l'offset DI
del puntatore si è fatto uso l'uso dell'istruzione LEA. |
 | il segment di default è ES e
non può essere cambiato con l'override
ES. |
 | il contatore CX è stato caricato con la dimensione
della stringa, cioè il numero dei suoi caratteri e il prefisso REPNE provvederà a
ripetere automaticamente il confronto se il dato assunto dalla locazione
è diverso da "T", valore predisposto il AL, fino all'esaurimento di tutti gli
elementi. |
 | se i caratteri sono tutte
diversi da "T" il processo ha termine regolarmente e, essendo
NE la condizione d'uscita, l'istruzione JE
non verrà eseguita e il programma
proseguirà subito sotto, nella zona di programma indicata
dall'etichetta tutte_diverse. |
 | se viene rilevata almeno una
"T" il processo verrà
immediatamente interrotto prima della fine e, essendo ora E
la condizione d'uscita, l'istruzione JE
verrà eseguita e il programma
proseguirà più in basso, nella zona di programma indicata
dall'etichetta trovata_lettera_T: la
prima istruzione da eseguire è, in questo caso, il decremento del
puntatore DI,
così da favorire la localizzazione della "T" nella stringa
sotto test. |
|
©
2001-2010 - Studio Tecnico
ing. Giorgio OBER
Tutti i diritti sono riservati
|