Qual è lo scopo e l'uso effettivo dei registri EDI e ESI in assembler?
So che sono usati per le operazioni sulle stringhe per una cosa.
Qualcuno può fare anche un esempio?
Qual è lo scopo e l'uso effettivo dei registri EDI e ESI in assembler?
So che sono usati per le operazioni sulle stringhe per una cosa.
Qualcuno può fare anche un esempio?
Risposte:
Ci sono alcune operazioni che puoi fare solo con DI / SI (o le loro controparti estese, se non hai imparato ASM nel 1985). Tra questi ci sono
REP STOSB
REP MOVSB
REP SCASB
Che sono, rispettivamente, operazioni di memorizzazione, caricamento e scansione ripetute (= massa). Quello che fai è impostare SI e / o DI in modo che puntino a uno o entrambi gli operandi, magari mettere un conteggio in CX e poi lasciarlo strappare. Queste sono operazioni che funzionano su un mucchio di byte alla volta, e in un certo senso mettono la CPU in automatico. Poiché non stai codificando in modo esplicito i loop, fanno le loro cose in modo più efficiente (di solito) di un loop codificato a mano.
Nel caso ve lo stiate chiedendo: a seconda di come impostate l'operazione, la memorizzazione ripetuta può essere qualcosa di semplice come inserire il valore 0 in un grande blocco di memoria contiguo; MOVSB è usato, penso, per copiare dati da un buffer (beh, qualsiasi gruppo di byte) a un altro; e SCASB viene utilizzato per cercare un byte che corrisponda a un criterio di ricerca (non sono sicuro che stia solo cercando l'uguaglianza o cosa - puoi cercarlo :))
È la maggior parte di ciò a cui servono quei reg.
SI
= Indice di origine
DI
= Indice di destinazione
Come altri hanno indicato, hanno usi speciali con le istruzioni di stringa. Per la programmazione in modalità reale, il ES
registro di segmento deve essere utilizzato con DI
e DS
con SI
come in
movsb es:di, ds:si
SI e DI possono essere utilizzati anche come registri di indice per scopi generali. Ad esempio, il C
codice sorgente
srcp [srcidx++] = argv [j];
si compila in
8B550C mov edx,[ebp+0C]
8B0C9A mov ecx,[edx+4*ebx]
894CBDAC mov [ebp+4*edi-54],ecx
47 inc edi
dove ebp+12
contiene argv
, ebx
è j
e edi
ha srcidx
. Notare che la terza istruzione usa edi
moltiplicato per 4 e aggiunge ebp
offset per 0x54 (la posizione di srcp
); le parentesi intorno all'indirizzo indicano un riferimento indiretto.
AX
= accumulatore
DX
= doppia parola accumulatore
CX
= contatore
BX
= registro di base
Sembrano registri di uso generale, ma ci sono un certo numero di istruzioni che (inaspettatamente?) Usano uno di essi - ma quale? - implicitamente.
Codici operativi come MOVSB e MOVSW che copiano in modo efficiente i dati dalla memoria puntata da ESI alla memoria puntata da EDI. Così,
mov esi, source_address
mov edi, destination_address
mov ecx, byte_count
cld
rep movsb ; fast!
Oltre alle operazioni sulle stringhe (MOVS / INS / STOS / CMPS / SCASB / W / D / Q ecc.) Menzionate nelle altre risposte, volevo aggiungere che ci sono anche istruzioni di assemblaggio x86 più "moderne" che implicitamente usano in EDI / RDI minimo:
L'istruzione SSE2 MASKMOVDQU
(e l'imminente AVX VMASKMOVDQU
) scrive selettivamente i byte da un registro XMM alla memoria puntata da EDI / RDI.
Oltre ai registri utilizzati per le operazioni di massa, sono utili per la loro proprietà di essere preservati attraverso una chiamata di funzione (chiamata preservata) nella convenzione di chiamata a 32 bit. ESI, EDI, EBX, EBP, ESP vengono conservati in chiamata mentre EAX, ECX ed EDX non vengono conservati in chiamata. I registri preservati dalle chiamate vengono rispettati dalla funzione di libreria C ei loro valori persistono attraverso le chiamate della funzione di libreria C.
Jeff Duntemann nel suo libro in linguaggio assembly ha un codice assembly di esempio per la stampa degli argomenti della riga di comando. Il codice utilizza esi ed edi per memorizzare i contatori poiché non verranno modificati dalla funzione di libreria C printf. Per altri registri come eax, ecx, edx, non vi è alcuna garanzia che non vengano utilizzati dalle funzioni della libreria C.
https://www.amazon.com/Assembly-Language-Step-Step-Programming/dp/0470497025
Vedere la sezione 12.8 Come C vede gli argomenti della riga di comando.
Si noti che le convenzioni di chiamata a 64 bit sono diverse dalle convenzioni di chiamata a 32 bit e non sono sicuro che questi registri siano conservati o meno.