CATEGORII DOCUMENTE |
SETUL DE INSTRUCTIUNI ALE MICROPROCESOARELOR INTEL 80x86 IN MODUL REAL SAU VIRTUAL 8086.
A 1.1 Notatii, conventii
Notatiile folosite in continuare sunt urmatoarele:
Operanzi:
- dst: operandul destinatie (al carui loc va fi ocupat de rezultatul instructiunii)
- src: operandul sursa (care va ramane neschimbat in urma instructiunii)
Date numerice (imediate):
- de 8 biti - n: 0..0FFh.Notatie echivalenta: imm8;
- de 16 biti - nn: 0..0FFFFh.Notatie echivalenta: imm16;
- de 32 biti - nnnn:0..0FFFFFFFFh. Notatie echivalenta: imm32;
-pentru salturi relative se folosesc notatiile: rel8,rel16,rel32
Registre:
- de 8 biti - r8:
- de 16 biti - r16: AX, BX, CX, DX, SI, DI, SP, BP,F;
- de 32 biti -r32: EAX,EBX,ECX,EDX,ESI,EDI,ESP,EBP,EF;
- registre de segment - rs: DS, ES, SS, CS.
Memoria:
- m8: Continutul unei locatii de memorie adresabila prin adresa efectiva ;
- m16: Continutul a doua locatii consecutive de memorie, formand un operand de 16 biti (2 octeti).Adresa efectiva indica octetul mai putin semnificativ al operandului, iar adresa efectiva +1 indica octetul mai semnificativ;
- m32: Continutul a patru locatii consecutive de memorie, formand un operand de 32 biti (4 octeti) Adresa efectiva indica octetul mai putin semnificativ al operandului, iar adresa efectiva +3 indica octetul mai semnificativ.
Observatie: Operanzii de 32 de biti exista numai pentru procesoare incepand cu Intel 80386. Daca sunt folositi in programul sursa astfel de operanzi, este obligatorie directiva .386 in preambulul programului.
A1.2. Instructiuni de transfer
A1.2.1. Transferuri cu memoria si registrele:
MOV - copierea datelor
Mnemonic: MOV dst, src
Actiune: 'dst' ia valoarea 'src'.
dst ← src.
Operanzi: dst: r8, r 16, rs, m8, m 16;
src: r8, r16, rs, m8, m16, n, nn;
Restrictii: nu sunt posibile transferuri de tip:
- MOV rs, rs
- MOV rs, nn
- MOV cs,*
- MOV m, m.
MOVSX - transfera cu extensia de semn intr-un format mai mare
Mnemonic: MOVSX dst,src.
Actiune dst← src.
Operandul sursa este transferat intr-un registru cu dimensiune mai mare, pastrand semnul prin transferul bitului de semn in pozitia cea mai semnificativa a operandului destinatie.
Operanzi: src: m8,r8 => dst:r16,r32;
src: m16,r16 => dst:r32.
MOVSZ - transfera cu completare cu zerouri intr-un format mai mare
Mnemonic: MOVSZ dst,src.
Actiune dst← src.
Operandul sursa este transferat intr-un registru cu dimensiune mai mare, completand cu zerouri bitii suplimentari din operandului destinatie.
Operanzi: src: m8,r8 => dst:r16,r32;
src: m16,r16 => dst:r32.
XCHG - interschimbare intre registre sau intre un registru si memorie
Mnemonic: XCHG dst, src.
Actiune: Se interschimba continuturile dst si src.
dst ← src;
src ← dst.
Operanzi: dst: r8, r16,r32;
src: r8, r16, m8, m16,m32.
Restrictii: Nu exista instructiuni de tip:
- XCHG rs, rs
- XCHG cs, *.
Varianta:
XCHG dst - interschimb cu acumulatorul implicit
XLAT
- translatare in
Actiune:
In
registrul
Adresa de segment este data de DS.
LEA - calculul si incarcarea adresei efective a unei variabile intr-un registru general
Actiune: r ← AE(mem).
Mnemonic: LEA r, mem.
Operanzi: r: r16, r32;
mem: m16,m32.
Daca marimile operanzilor sunt diferite, se fac automat trunchieri la marimea operandului cel mai mic.
LGS/LSS/LDS/LES/LFS - Incarca un pointer (ca o adresa logica de 32 de biti) din memorie, de la adresa nn, intr-o pereche formata dintr-un registru de segment si un registru de 16 biti.
Mnemonic: LDS r16,RS:nn;
etc.
Actiune:
LDS r16, nn: R16L←[RS:nn],R16H←[RS:nn+1],DSL←[RS:nn+2],DSH ← [RS:nn+3]
LSS r16, nn: R16L←[RS:nn],R16H←[RS:nn+1],SSL←[RS:nn+2], SSH ← [RS:nn+3]
LES r16, nn: R16L←[RS:nn],R16H←[RS:nn+1],ESL←[RS:nn+2],DEH ← [RS:nn+3]
LFS r16, nn: R16L←[RS:nn],R16H←[RS:nn+1],FSL←[RS:nn+2], FSH ← [RS:nn+3]
LGS r16, nn: R16L←[RS:nn],R16H←[RS:nn+1],GSL←[RS:nn+2],GSH← [RS:nn+3]
unde r16 este un registru de 16 biti de uz general, RS este un registru de segment (DS,SS,ES,FS sau GS) iar nn este un numar de 16 biti.
Observatie: Instructiunile LSS, LGS, LFS nu apar la procesoare anterioare lui 80386 (nici nu existau registrele de segment FS si GS), de aceea, in cazul folosirii lor, in partea initiala a programului trebuie introdusa directiva .386.
LAHF - citirea indicatorilor de conditii (octetul inferior al registrului F) in AH
Actiune: AH ← F
AH7=SF (flagul de semn, 1 daca este minus, 0 daca este plus);
AH6=ZF (flagul de zero, 1 daca este 0, 0 daca nu este 0);
AH5=0 ;
AH4=AF (flagul de transport auxiliar de la cei 4 biti inferiori ai unui rezultat);
AH3=0 ;
AH2=PF (flagul de paritate, 1 daca este par, 0 daca este impar);
AH1=IF (flagul de intreruperi, 1 daca daca intreruperile sunt activate, 0 daca nu);
AH0=CF (flagul de transport 1 daca exista transport de la rezultat);
Structura octetului inferior al registrului indicatorilor de conditii F este:
S |
Z |
x |
A |
x |
P |
x |
C |
SAHF - Salvare AH in registrul de flaguri.
Actiune: F ← AH
SF=AH7 (flagul de semn, 1 daca este minus, 0 daca este plus);
ZF=AH6 (flagul de zero, 1 daca este 0, 0 daca nu este 0);
AF= AH4 (flagul de transport auxiliar de la cei 4 biti inferiori ai unui rezultat);
PF=AH2 (flagul de paritate, 1 daca este par, 0 daca este impar);
IF= AH1 (flagul de intreruperi, 1 daca daca intreruperile sunt activate, 0 daca nu);
CF=AH0 (flagul de transport 1 daca exista transport de la rezultat);
Bitii AH5 si AH3 trebuie sa fie 0.
A1.2.2. Transferuri cu stiva
PUSH - salvarea datelor in stiva
Mnemonic: PUSH src.
Operand r16, r32, m16, m32.
Actiune:
Pentru operand de 16 biti:
SP ← SP-2;
[SP] ← src1 (octetul inferior al sursei);
[SP+ 1] ← src (octetul superior al sursei);
Pentru operand de 32 biti:
SP ← SP-4;
[SP] ← src1 (octetul inferior al sursei);
[SP+ 1] ← src2;
[SP+2] ← src3;
[SP+ 3] ← src4 (octetul superior al sursei).
Descriere: Indicatorul de stiva este decrementat cu un numar egal cu numarul de octeti ai operandului, dupa care operandul este salvat in stiva incepand de la adresa continuta acum in indicatorul de stiva.
Observatie: Este permisa si salvarea din memorie (2 sau 4 locatii consecutive, adresate cu unul din modurile de adresare ).
POP - aducerea datelor din stiva
Mnemonic: POP dst.
Actiune:
Pentru operand de 16 biti:
dst [SP];
dsth ← [SP+ 1];
SP ← SP+2.
Pentru operand de 32 biti:
SP ← SP-4;
dst1← [SP] (octetul inferior al sursei);
dst2 ← [SP+ 1];
dst3 ← [SP+2];
dst4 ← [SP+3] (octetul superior al sursei).
Operand: r16 (cu exceptia lui CS),r32, m16,m32
Descriere: Registrul sau locatiile de memorie specificate de operand se incarca cu continutul locatiilor de stiva a caror adresa de start se afla in indicatorul de stiva. Apoi indicatorul de stiva este incrementat cu un numar egal cu numarul de octeti ai operandului.
Observatie: Este permisa si aducerea din stiva in locatii de memorie (2 sau 4 locatii consecutive, adresate cu unul din modurile de adresare).
PUSHF,PUSHFD - salvarea registrului indicatorilor de conditii in stiva, respectiv a registrului extins al indicatorilor de conditii
Mnemonic : PUSHF
Actiune: SP ← SP-2
[SP] ← F (octetul inferior al registrului F);
[SP+1] ← F2 (octetul superior al registrului F).
Mnemonic: PUSHFD
Actiune: SP ← SP-4;
[SP] ← EF (octetul inferior al registrului EF);
[SP+1] ← EF
[SP+2] ← EF
[SP+3] ← EF (octetul superior al registrului EF).
POPF, POPFD - aducerea indicatorilor de conditii din stiva , respectiv a registrului extins al indicatorilor de conditii.
Mnemonic : POPF
Actiune: F ← [SP] (octetul inferior al registrului F);
Fh ← [SP+1] (octetul superior al registrului F);
SP ← SP+2.
Mnemonic : POPFD
Actiune: F ← [SP] (octetul inferior al registrului EF);
F ← [SP+1] ;
F ← [SP+2] ;
F ← [SP+3] (octetul superior al registrului EF);
SP ← SP+4.
PUSHA,PUSHAD- salvarea tuturor registrelor in stiva
Mnemonic : PUSHA
Actiune: SP ← SP-16;
[SP] ← AX,CX,DX,BX,SP(valoarea initiala),BP,SI,DI.
Mnemonic : PUSHAD
Actiune: SP ← SP-32;
[SP] ← EAX,ECX,EDX,EBX,ESP(valoarea initiala),EBP,ESI,EDI.
POPA,POPAD- readucerea tuturor registrelor din stiva
Mnemonic : POPA
Actiune: [SP] ← AX,CX,DX,BX,SP(nu se modifica),BP,SI,DI;
SP ← SP+16.
Mnemonic : POPAD
Actiune: [SP] ← EAX,ECX,EDX,EBX,ESP(nu se modifica), EBP,ESI,EDI;
SP ← SP+32.
A1.2.3. Transferuri cu porturile
IN - citire din portul n sau a carui adresa este in DX
Mnemonic: IN dst, src.
Actiune:
AX ← [port]16 sau
EAX ← [port]32 .
AX ← port[DX]16 sau
EAX ← port[DX]32 .
Operanzi: port: n,[DX].
Observatii: Se poate face citire pe 8 biti (in AL, dintr-un port de 8 biti), pe 16 biti (in AX, dintr-un port de 16 biti) sau pe 32 biti (in EAX, dintr-un port de 32 biti).
In cazul in care adresa portului este continutul lui DX, aceasta are 16 biti, deci sunt posibile 65536 porturi. Daca adresa este un numar n, aceasta are numai 8 biti, deci sunt posibile 256 de porturi.
OUT - scriere in portul n sau a carui adresa este in DX
Mnemonic: OUT dst, src
Actiune: [port]8
←
[port]16 ← AX sau
[port]32 ← EAX
port[DX]8 ←
port[DX]16 ← AX sau
port[DX]32 ← EAX
Operanzi: port: n,[DX]
Observatii: Se poate face citire pe 8 biti (in AL, dintr-un port de 8 biti), pe 16 biti (in AX, dintr-un port de 16 biti) sau pe 32 biti (in EAX, dintr-un port de 32 biti).
In cazul in care adresa portului este continutul lui DX, aceasta are 16 biti, deci sunt posibile 65536 porturi. Daca adresa este un numar n, aceasta are numai 8 biti, deci sunt posibile 256 de porturi.
A1.2.4. Instructiuni de transfer de siruri
LODSB, LODSW, LODSD,STOSB, STOSW,STOSD
Mnemonic: LODSB - Incarca un octet de la DS:SI in
Actiune: AL← [SI];
SI← SI +1 daca DF=0, SI← SI-1 daca DF=1.
Mnemonic: LODSW - Incarca un cuvant de la DS:SI in AX
Actiune: AL← [SI];
AH← [SI+1];
SI← SI +2 daca DF=0, SI← SI-2 daca DF=1.
Mnemonic: LODSD - Incarca un dublucuvant de la DS:SI in EAX
Actiune: EAX0← [SI] (octetul inferior al EAX);
EAX1← [SI+1];
EAX1← [SI+2];
EAX1← [SI+3] (octetul superior al EAX);
SI← SI +4 daca DF=0, SI← SI-4 daca DF=1.
Mnemonic: STOSB - Incarca AL la ES:DI
Actiune: [DI]←
DI← DI +1 daca DF=0, DI← DI-1 daca DF=1
Mnemonic: STOSW - Incarca AL la ES:DI
Actiune: [DI]←
[DI+1]← AH;
DI← DI +2 daca DF=0, DI← DI-2 daca DF=1.
Mnemonic: STOSD - Incarca un dublucuvant din EAX la ES:DI
Actiune: [DI]← EAX0 (octetul inferior al EAX);
[DI+1]← EAX1 ;
[DI+2]← EAX2 ;
[DI+3] ← EAX3 (octetul superior al EAX);
DI← DI +4 daca DF=0, DI← DI-4 daca DF=1.
Mnemonic: LODS dst,src - Muta un octet, doi octeti sau 4 octeti de la adresa la adresa DS:SI in AL, AX sau EAX. Aceasta instructiune este echivalenta cu LODSB,LODSW si LODSD care nu au insa operanzi expliciti.
Mnemonic: STOS dst,src - Muta continutul lui AL, AX sau EAX in memorie la adresa ES:DI. Aceasta instructiune este echivalenta cu STOSB,STOSW si STOSD care nu au insa operanzi expliciti.
Pentru instructiunile de transfer LODSB, LODSW si LODSW, sursa este locatia de memorie cu adresa efectiva data de registrul index sursa SI si adresa de segment data de DS.
Pentru instructiunile de transfer STOSB, STOSW si STOSD destinatia este locatia de memorie cu adresa efectiva data de registrul index destinatie DI si adresa de segment data de ES.
In urma efectuarii unei astfel de instructiuni, registrul index SI respectiv DI se modifica in functie de starea flagului DF (de directie). Daca DF este 0, registrul index va fi incrementat cu 1 la LODSB si STOSB, cu 2 la LODSW si STOSW si cu 4 la LODSD si STOSD . Daca DF este 1, registrul index va fi decrementat cu 1, 2, respectiv cu 4.
Registrul general implicit este AL la transferul de un octet, AX la transferul de doi octeti si EAX la transferul pe 4 octeti.
MOVS,MOVSB, MOVSW,MOVSD
Aceste instructiuni combina instructiunile LODSB si STOSB, respectiv LODSW si STOSW, fara a afecta AL sau AX. Segmentul destinatie este intotdeauna ES. Segmentul sursa implicit este DS, dar poate fi si altul specificat in adresa sursa.
Mnemonic: MOVSB - Muta un octet de la adresa DS:SI la adresa ES:DI
Actiune: [DS]← [SI];
SI← SI +1 daca DF=0, SI← SI-1 daca DF=1;
DI← DI +1 daca DF=0, DI← DI-1 daca DF=1.
Mnemonic: MOVSW - Muta un cuvant de la adresa DS:SI la adresa ES:DI
Actiune: [DI]← [SI];
[DI+1]← [SI+1];
SI← SI +2 daca DF=0, SI← SI-2 daca DF=1;
DI← DI +2 daca DF=0, DI← DI-2 daca DF=1.
Mnemonic: MOVSD - Muta un dublu-cuvant (32 de biti) de la adresa DS:SI la adresa ES:DI
Actiune: [DI]← [SI];
[DI+1]← [SI+1];
[DI+2]← [SI+2];
[DI+3]← [SI+3];
SI← SI +4 daca DF=0, SI← SI-4 daca DF=1;
DI← DI +4 daca DF=0, DI← DI-4 daca DF=1.
Mnemonic: MOVS dst,src - Muta un octet, doi octeti sau 4 octeti de la adresa SI la adresa ES:DI. Operanzii sunt simboluri de o anumita lungime, declarati anterior in program. Aceasta instructiune este echivalenta cu MOVSB, MOVSW si MOVSD care nu au insa operanzi expliciti.
INS, INSB, INSW, INSD
Mnemonic: INSB - Incarca in memorie la ES:DI continutul portului de 8 biti a carui adresa este in DX
Actiune: [DI]←port[DX];
DI← DI +1 daca DF=0, DI← DI-1 daca DF=1.
Mnemonic: INSW - Incarca in memorie la ES:DI continutul portului de 16 biti a carui adresa este in DX
Actiune:[DI] ← port[DX]0 (octetul inferior al portului a carui adresa e in DX);
[DI+1]← port[DX]1(octetul superior al portului a carui adresa e in DX);
DI← DI +2 daca DF=0, DI← DI-2 daca DF=1.
Mnemonic: INSD - Incarca in memorie la ES:DI continutul portului de 32 biti a carui adresa este in DX
Actiune: [DI]← port[DX]0 (octetul inferior al portului a carui adresa e in DX);
[DI+1]←port[DX]1;
[DI+2]←port[DX]2;
[DI+3]← port[DX]3 (octetul superior al portului a carui adresa e in DX);
DI← DI +4 daca DF=0, DI← DI-4 daca DF=1.
Mnemonic: INS dst,src - Muta un octet, doi octeti sau 4 octeti din portul a carui adresa este continuta in DX, intr-un registru sau in memorie la adresa ES:DI.Aceasta instructiune este echivalenta cu instructiunile INSB, INSW si INSD care nu au insa operanzi expliciti.
OUTS, OUTSB, OUTSW, OUTSD
Mnemonic: OUTSB - Incarca din memorie de la DS:SI in portul de 8 biti a carui adresa este in DX
Actiune: port[DX]← [SI];
SI← SI +1 daca DF=0, SI← SI-1 daca DF=1.
Mnemonic: OUTSW - Incarca din memorie de la DS:SI in portul de 16 biti a carui adresa este in DX.
Actiune: port[DX]0← [SI] (octetul inferior al portului a carui adresa e in DX);
port[DX]1← [SI+1] (octetul superior al portului a carui adresa e in DX);
SI← SI +2 daca DF=0, SI← SI-2 daca DF=1.
Mnemonic: INSD - Incarca din memorie de la DS:SI in portul de 32 biti a carui adresa este in DX
Actiune: port[DX]0← [SI] (octetul inferior al portului a carui adresa e in DX);
port[DX]1← [SI+1] ;
port[DX]2← [SI+2] ;
port[DX]3← [SI+3] (octetul superior al portului a carui adresa e in DX);
SI← SI +4 daca DF=0, SI← SI-4 daca DF=1.
Mnemonic: OUTS dst,src - Muta un octet, doi octeti sau 4 octeti in portul a carui adresa este continuta in DX, dintr-un registru sau din memorie de la adresa DS:SI. Aceasta instructiune este echivalenta cu instructiunile OUTSB, OUTSW si OUTSD care nu au insa operanzi expliciti.
Prefixul REP
Instructiunile de transfer de siruri LODS, LODSx, STOS, STOSx, MOVS, MOVSx, INS, INSx, OUTS, OUTSx (unde x este B,W sau D) pot fi precedate de prefixul REP, care cere procesorului sa repete instructiunea pe care o precede pana cand CX devine 0 (prin decrementare automata). In cazul instructiunilor LODSx se foloseste insa de regula prefixul LOOP, deoarece cu REP s-ar rescrie in mod inutil registrul AL, AX sau EAX de CX ori.
A1.3. Instructiuni de calcul
Exista urmatoarele tipuri de operatii efectuate de ALU:
- aritmetice;
- aritmetice speciale;
- logice;
- deplasari;
- rotatii.
Toate acestea afecteaza corespunzator unul sau mai multi din urmatorii indicatori de conditii:
- CF (Carry Flag) - indicator de transport - reflecta transportul in exterior al bitului cel mai semnificativ al rezultatului operatiilor aritmetice. Acest indicator poate fi folosit in cazul adunarii sau scaderii numerelor pe mai multi octeti, semnificand in primul caz transport la adunare si in al doilea caz imprumut la scadere. Indicatorul CF nu este modificat de instructiuni de incrementare si decrementare.
- PF (Parity Flag) - indicator de paritate - este pozitionat pe 1 daca rezultatul are un numar par de biti 1.
- AF (Auxiliary Carry Flag) - indicator de transport auxiliar - este pozitionat in 1 daca a fost transport de la nivelul inferior la nivelul superior al semioctetului rezultatului (de la bitul 3 la bitul 4). Acest indicator se foloseste in programele de calcule in aritmetica zecimala.
- ZF (Zero Flag) - indicatorul de zero - este pozitionat in 1 daca rezultatul
operatiei a fost zero.
- SF (Sign Flag) indicatorul de semn - este pozitionat in 1 daca cel mai semnificativ bit al rezultatului (MSB) este 1, adica in reprezentarea numerelor in C2 (complement fata de 2) rezultatul este negativ.
- OF (Overflow Flag) - indicator de depasire aritmetica (a gamei de valori posibil de reprezentat) - este pozitionat in 1 daca dimensiunea rezultatului depaseste capacitatea
locatiei de destinatie si a fost pierdut un bit (la valorile cu semn se altereaza semnul).
A1.3.1. Instructiuni aritmetice si logice
Observatii genera1e:
- Operanzi: dst: r8, r16, r32, m8, m16, m32
src: r8, r16, r32, m8, m16, m32, n, nn, nnnn
- Operatiile sunt posibile pe 8, 16 sau 32 biti (sursa si destinatia avand marimi compatibile)
- Sursa si destinatia nu pot fi concomitent locatii de memorie
- Adresarea imediata (specificarea valorii numerice a operandului) este posibila numai pentru sursa.
- Sunt posibile adunari, scaderi si inmultiri cu semn avand operandul destinatie registru sau memorie pe 16 sau 32 de biti, si operandul sursa o valoare imediata de 8 biti. In acest caz, operandul de 8 biti este extins la 16 sau 32 de biti cu pastrarea semnului (bitul cel mai semnificativ, cel de semn, este copiat din pozitia a 8-a in toti bitii pana la pozitia 16, respectiv 32). Aceasta posibilitate exista si pentru operatiile logice, cu exceptia instructiunii TEST.
ADC dst,src - Adunare cu carry (transport)
Actiune: dst ← dst + src + CF;
ADD dst,src - Adunare
Actiune: dst ← dst + src;
SUB dst,src - Scadere
Actiune: dst ← dst - src;
SBB dst,src - Scadere cu 'borrow' (imprumut)
Actiune: dst ← dst - src - CF;
INC dst - Incrementare
Actiune: dst ← dst + 1; Nu este afectat CF.
DEC dst - Decrementare
Actiune: dst ← dst - 1; Nu este afectat CF.
NEG dst - Negare aritmetica
Actiune: dst ← - dst (complementare fata de doi)
Descriere: Se obtine operandul cu semn schimbat in complement fata de 2.
CF este setat automat, cu exceptia cazului cand operandul este 0.
NOT dst - Complementare fata de 1
Actiune: dst ← 0FFh - dst ; pentru operand de 8 biti
dst ← 0FFFFh - dst ; pentru operand de 16 biti
dst ← 0FFFFFFFFh - dst ; pentru operand de 32 biti
Descriere: Instructiunea NOT inverseaza operandul; orice 1 devine 0 si viceversa.
Nu sunt afectati indicatorii de conditii.
MUL src - Inmultirea fara semn lui AL, AX sau EAX cu un numar.
Actiunea depinde de marimea operandului src, luand urmatoarele forme:
- src de 8 biti: AX ← AL * src8; src: r8,m8;
Daca AH = 0 atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
-src de 16 biti: DX: AX ← AX * src16; src: r16,m16;
Daca DX = 0 atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
- src de 32 biti: EDX: EAX ← EAX * src32; src: r32,m32;
Daca EDX = 0 atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
IMUL (dst,) src - Inmultirea cu semn a lui AL,AX , EAX sau a altui registru cu un numar.
Actiunea depinde de operandul destinatie si de marimea operandului src.
In cazul in care destinatia este acumulatorul AL,AX sau EAX se obtine rezultatul complet, chiar daca apare flagul Overflow, deoarece rezultatul va fi memorat cu precizie dubla fata de a operanzilor:
- src de 8 biti: AX ← AL * src8; src: r8,m8;
Daca AH = 0 sau AH = FF atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
- src de 16 biti: DX: AX ← AX * src16; src: r16,m16;
Daca DX = 0 sau AH = FF atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
- src de 32 biti: EDX: EAX ← EAX * src32; src: r32,m32;
Daca EDX = 0 sau AH = FF atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
Spre deosebire de inmultirea numerelor fara semn cu instructiunea MUL, in cazul instructiunii IMUL este posibil ca deinmultitul sa fie si alt registru in afara de acumulator, iar sursa sa fie o valoare numerica imediata. In acest caz insa, daca rezultatul are mai multi biti decat registrul care contine deinmultitul, se pierd bitii care depasesc largimea acestuia.
Actiunea este urmatoarea:
- cu dst de 16 biti:
IMUL dst,src
dst ← dst * src; (dst= r16; src=r16/m16 /imm8/imm16);
Daca DX = 0 sau AH = FF atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
Daca src este de tip imm8, acesta se extinde cu semn pana la lungimea dst.
- cu dst de 32 biti:
IMUL dst,src
dst ← dst * src; (dst= r32; src=r32/m32 /imm8/imm32);
Daca DX = 0 sau AH = FF atunci CF ← 0; In celelalte cazuri CF ← 1 si OF ← CF.
Daca src este de tip imm8, acesta se extinde cu semn pana la lungimea dst.
DIV src - Impartirea fara semn a acumulatorului cu un registru sau locatie de memorie.
Actiune: - daca src este de 8 biti:
AL ← AX/src8 (catul impartirii);
AL ← AX % src8 (restul impartirii);
src: r8,m8.
- daca src este de 16 biti:
AX ← DX : AX/srcl6 (catul impartirii);
DX DX : AX % srcl6 (restul impartirii);
src: r16,m16.
- daca src este de 32 biti:
EAX ← EDX : EAX/srcl6 (catul impartirii);
EDX EDX : EAX % srcl6 (restul impartirii);
src: r32,m32.
Observatii: Daca rezultatul (catul) nu incape in registrul destinatie AL, AX respectiv EAX, sau impartitorul este 0, se genereaza Intrerupere 0 (DE - Divide Error) si se sare automat din program. De aceea trebuie facuta o evaluare prealabila a domeniului de valori ale rezultatului si trebuie folosit un registru destinatie corespunzator.
Daca catul este subunitar, el este ajustat la 0.
Indicatorii de conditii sunt nedefiniti.
IDIV src - Impartirea cu semn a acumulatorului cu un registru sau locatie de memorie.
Actiune: - daca src este de 8 biti:
AL ← AX/src8 (catul impartirii);
AL ← AX % src8 (restul impartirii);
src: r8,m8.
- daca src este de 16 biti:
AX ← DX : AX/srcl6 (catul impartirii);
DX DX : AX % srcl6 (restul impartirii);
src: r16,m16.
- daca src este de 32 biti:
EAX ← EDX : EAX/srcl6 (catul impartirii);
EDX EDX : EAX % srcl6 (restul impartirii);
src: r32,m32.
Observatie: Daca rezultatul (catul) nu incape in registrul destinatie AL, AX respectiv EAX, sau impartitorul este 0, se genereaza intrerupere 0 (DE - Divide Error) si se sare automat din program. De aceea trebuie facuta o evaluare prealabila a domeniului de valori ale rezultatului si trebuie folosit un registru destinatie corespunzator.
Daca catul este subunitar, el este ajustat la 0.
Semnul restului este acelasi cu al impartitorului.
Indicatorii de conditii sunt nedefiniti.
CBW - Conversie de la Byte (8 biti) din AL la Word (16 biti) in AX, cu pastrare semn.
Actiune: AL = 0 => AH ← 0;
AL = 1 => AH ← 0FFh.
Bitul cel mai semnificativ al lui AL este copiat in toti bitii registrului AH.
Indicatorii de conditii nu sunt afectati.
CWD - Conversie de la Word (16 biti) din AX la Dword (32 biti) in DX:AX, cu pastrare semn.
Actiune: AX = 0 => DX ← 0;
AL = 1 => DX ← 0FFFFh.
Bitul cel mai semnificativ al lui AX este copiat in toti bitii registrului DX.
Indicatorii de conditii nu sunt afectati.
CWDE - Conversie de la Word (16 biti) la Dword (32 biti) in EAX, cu pastrare semn.
Actiune:
EAX = 0 => EAX ..EAX31= 1 ;
EAX = 1 => EAX ..EAX31= 1 .
Bitul cel mai semnificativ al lui AX este copiat in toti bitii jumatatii superioare a lui EAX.
Indicatorii de conditii nu sunt afectati.
CDQ - Conversie de la Dword (32 biti) in EAX la Qword (64 biti) in EDX:EAX, cu pastrare semn.
Actiune:
EAX = 0 => EDX ← 0;
AL = 1 => EDX ← 0FFFFFFFFh.
Bitul cel mai semnificativ al lui EAX este copiat in toti bitii registrului EDX.
Indicatorii de conditii nu sunt afectati.
AND dst,src - SI logic pe bit
Actiune: bn(dst) ← bn(dst) AND bn(src) ;
dst: r8,r16,r32,m8,m16,m32;
src: r8,r16,r32,m8,m16,m32,imm8,imm16,imm32.
Descriere: Fiecare bit al rezultatului instructiunii AND este un 1 daca ambii biti corespunzatori ai operanzilor sunt 1; altminteri, devine un 0.
Sursa si destinatia trebuie sa fie de dimensiuni egale. Este posibil ca sursa sa fie o valoare imediata de 1 octet iar destinatia sa fie de 2 sau 4 octeti, caz in care numarul sursa va fi extins cu semn pana la valoarea destinatiei.
Nu se admite ca ambii operanzi sa fie locatii de memorie.
OR dst,src - SAU logic pe bit
Actiune: bn(dst) ← bn(dst) OR bn(src) ;
dst: r8,r16,r32,m8,m16,m32;
src: r8,r16,r32,m8,m16,m32,imm8,imm16,imm32;
Descriere: Instructiunea OR calculeaza SAU al celor doi operanzi si rezultatul este plasat in primul operand. Fiecare bit al rezultatului este 0 daca ambii biti corespunzatori ai operanzilor sunt 0; altminteri, fiecare bit este 1.
Sursa si destinatia trebuie sa fie de dimensiuni egale. Este posibil ca sursa sa fie o valoare imediata de 1 octet iar destinatia sa fie de 2 sau 4 octeti, caz in care numarul sursa va fi extins cu semn pana la valoarea destinatiei.
Nu se admite ca ambii operanzi sa fie locatii de memorie.
XOR dst,src - SAU EXCLUSIV logic pe bit
Actiune: bn(dst) ← bn(dst) XOR bn(src) ;
dst: r8,r16,r32,m8,m16,m32;
src: r8,r16,r32,m8,m16,m32,imm8,imm16,imm32.
Descriere: Instructiunea XOR calculeaza SAU EXCLUSIV al celor doi operanzi. Fiecare bit al rezultatului este 1 daca bitii corespunzatori ai operanzilor sunt diferiti; fiecare bit este 0 daca bitii corespunzatori sunt identici. Rezultatul inlocuieste primul operand.
Sursa si destinatia trebuie sa fie de dimensiuni egale. Este posibil ca sursa sa fie o valoare imediata de 1 octet iar destinatia sa fie de 2 sau 4 octeti, caz in care numarul sursa va fi extins cu semn pana la valoarea destinatiei.
Nu se admite ca ambii operanzi sa fie locatii de memorie.
CMP dst,src - Comparatie aritmetica (prin scadere)
Actiune: dst-src;
dst: r8,r16,r32,m8,m16,m32;
src: r8,r16,r32,m8,m16,m32,imm8,imm16,imm32.
Decriere: Se face diferenta intre dst si src, fara generare rezultat - se modifica doar indicatorii de conditii.
Sursa si destinatia trebuie sa fie de dimensiuni egale. Este posibil ca sursa sa fie o valoare imediata de 1 octet iar destinatia sa fie de 2 sau 4 octeti, caz in care numarul sursa va fi extins cu semn pana la valoarea destinatiei.
Nu se admite ca ambii operanzi sa fie locatii de memorie.
TEST dst,src - testare (SI fara generare de rezultat)
dst: r8,r16,r32,m8,m16,m32;
src: r8,r16,r32,m8,m16,m32,imm8,imm16,imm32.
Descriere: Instructiunea TEST calculeaza 'SI logic pe bit' de cei doi operanzi. Fiecare bit al rezultatului este 1, daca ambii biti corespunzatori ai operanzilor sunt l; altminteri, fiecare bit este 0. Rezultatul operatiei este sters si doar f1agurile sunt modificate.
Sursa si destinatia trebuie sa fie de dimensiuni egale.
Nu se admite ca ambii operanzi sa fie locatii de memorie.
SCAS,SCASB,SCASW,SCASD - Compara acumulatorul cu un sir
Mnemonic: SCAS dst
Descriere - Compara continutul registrului (E)AX cu continutul locatiilor de memorie (una, doua sau patru) care incep la adresa ES:[DI] si pozitioneaza corespunzator flagurile
dst: m8,m16,m32
Actiune: AL - ES:[DI];
DI← DI+n daca DF=0, DI← DI-n daca DF=1 unde n=1/2/4 in functie de dimensiunea operandului.
Mnemonic: SCASB - Compara continutul registrului AL cu continutul locatiei ES:DI si pozitioneaza corespunzator flagurile
Actiune: AL - ES:[DI];
DI← DI+1 daca DF=0, DI← DI-1 daca DF=1.
Mnemonic: SCASW - Compara continutul registrului AX cu continutul locatiilor ES:[DI] si ES:[DI+1] si pozitioneaza corespunzator flagurile
Actiune: AL - ES:[DI];
AH - ES:[DI+1];
DI← DI+2 daca DF=0, DI← DI-2 daca DF=1.
Mnemonic: SCASD - Compara continutul registrului EAX cu continutul locatiilor ES:[DI], ES:[DI+1], ES:[DI+2] si ES:[DI+3] si pozitioneaza corespunzator flagurile.
Actiune: EAX1 - ES:[DI] - octetul cel mai putin semnificativ al lui EAX;
EAX2 - ES:[DI+1] ;
EAX3 - ES:[DI+2] ;
EAX4 - ES:[DI+3] - octetul cel mai semnificativ al lui EAX;
DI← DI+4 daca DF=0, DI← DI-4 daca DF=1.
La aceste instructiuni operandul este intotdeauna in segmentul ES, si nu este posibila schimbarea acestui segment.
Instructiunea SCASB compara octetul din locatia de memorie cu adresa ES:DI cu continutul lui AL si pozitioneaza indicatorii de conditii in functie de rezultatul compararii. Registrul DI va fi incrementat cu 1 daca DF=0 si decrementat cu 1 daca DF=1.
Instructiunea SCASW compara cuvantul punctat de locatia de memorie cu adresa ES:DI (octetul inferior fiind la aceasta adresa, iar cel superior la cea urmatoare), cu continutul lui AX si pozitioneaza indicatorii de conditii in functie de rezultatul compararii. Registrul DI va fi incrementat cu 2 daca DF=0 si decrementat cu 2 daca DF=1.
Instructiunea SCASD compara cuvantul punctat de locatia de memorie cu adresa ES:DI (octetul inferior fiind la aceasta adresa, iar cel superior la cea de a treia din cele care urmeaza), cu continutul lui EAX si pozitioneaza indicatorii de conditii in functie de rezultatul compararii. Registrul DI va fi incrementat cu 4 daca DF=0 si decrementat cu 4 daca DF=1.
In conformitate cu regulile aritmeticii in complement fata de 2 (numerele negative au bitul cel mai semnificativ 1 iar scaderea cu rezultat negativ da un imprumut) , daca numarul din memorie este mai mic decat cel din registru, indicatorii C (transport la adunare si imprumut la scadere) si S (semn) se pozitioneaza in 1 . Daca numarul din memorie este mai mare decat cel din cu cel din registru, indicatorii C si S se pozitioneaza in 0. Daca numarul din memorie este egal cu cel din registru, se pozitioneaza in 1 indicatorul Z.
CMPS, CMPSB, CMPSW, CMPSD -compara doua seturi de locatii de memorie
Mnemonic: CMPS dst,src - Compara continutul locatiilor (una, doua sau patru) care incep la adresa DS:[SI] cu continutul aceluiasi numar de locatii care incep la adresa ES:[DI] si pozitioneaza corespunzator flagurile.
dst,src: m8,m16,m32.
Actiune: DS:[SI] - ES:[DI];
SI←SI +n daca DF=0, SI←SI-n daca DF=1;
DI←DI +n daca DF=0, DI←DI-n daca DF=1 unde n=1/2/4 in functie de dimensiunea operanzilor.
Mnemonic: CMPSB - Compara continutul locatiei DS:[SI] cu continutul locatiei ES:[DI] si pozitioneaza corespunzator flagurile
Actiune: DS:[SI] - ES:[DI];
SI←SI +1 daca DF=0, SI←SI-1 daca DF=1;
DI←DI +1 daca DF=0, DI←DI-1 daca DF=1.
Mnemonic: CMPSW - Compara continutul locatiilor DS:[SI] si DS:[SI+1] cu continutul locatiilor ES:[DI] si ES:[DI+1] si pozitioneaza corespunzator flagurile
Actiune: DS:[SI] - ES:[DI];
DS:[SI+1] - ES:[DI+1];
SI←SI +2 daca DF=0, SI←SI-2 daca DF=1;
DI←DI +2 daca DF=0, DI←DI-2 daca DF=1.
Mnemonic: CMPSD - Compara continutul a patru locatii care incep la adresa DS:[SI] cu continutul a patru locatii care incep la adresa ES:[DI] si pozitioneaza corespunzator flagurile
Actiune: DS:[SI] - ES:[DI];
DS:[SI+1] - ES:[DI+1];
DS:[SI+2] - ES:[DI+2];
DS:[SI+3] - ES:[DI+3];
SI←SI +2 daca DF=0, SI←SI-2 daca DF=1;
DI←DI +2 daca DF=0, DI←DI-2 daca DF=1.
La aceste instructiuni operandul al doilea este intotdeauna in segmentul ES, si nu este posibila schimbarea acestui segment. Primul operand este implicit in segmentul DS, dar se acest segment poate fi schimbat ( prin 'segment override byte').
Pentru instructiunea de comparatie CMPSB primul operand este locatia de memorie cu adresa efectiva data de registrul index sursa SI si adresa de segment data de DS iar al doilea operand este locatia de memorie cu adresa efectiva data de registrul index destinatie DI si adresa de segment data de ES.
Pentru instructiunea de comparatie CMPSW primul operand este dat de locatiile de memorie cu adresele DS:[SI] (octetul inferior) si DS:[SI+1] (octetul superior) iar al doilea operand este dat de locatiile de memorie cu adresele ES:[DI] (octetul inferior) si ES:[DI+1] (octetul superior).
Pentru instructiunea de comparatie CMPSD primul operand este dat de patru locatii de memorie care incep la adresa DS:[SI] (octetul inferior) si se termina la DS:[SI+1] (octetul superior), iar al doilea operand este dat de patru locatii de memorie care incep la adresa ES:[DI] (octetul inferior) si se termina la ES:[DI+1] (octetul superior).
Pentru instructiunea de comparatie CMPS primul operand este dat de una doua sau patru locatii de memorie care incep la adresa DS:[SI] (octetul inferior) si se termina iar al doilea operand este dat de patru locatii de memorie care incep la adresa ES:[DI] (octetul inferior) si se termina la ES:[DI+1] (octetul superior).
In urma efectuarii unei astfel de instructiuni, registrele index SI respectiv DI se modifica in functie de starea flagului DF (de directie). Daca DF este 0, registrele index vor fi incrementate cu 1 la CMPSB si cu 2 la CMPSW. Daca DF este 1, registrele index vor fi decrementate cu 1, respectiv cu 2.
A1.3.2. Ajustari zecimale pentru operatii cu numere BCD
AAA - Ajustare in cod BCD despachetat a lui AL dupa adunare
Actiune:
IF (AL AND OFH) > 9) OR (AF=1)
THEN
AL ← (AL + 6) AND OFH;
AH ← AH + 1;
AF ← 1;
CF ← 1;
ELSE
CF ← 0;
AF ← 0.
FI.
Descriere: Executia instructiunii AAA se face numai dupa instructiunea ADD (sau ADC), care lasa rezultatul in registrul AL. Semioctetii inferiori ai operanzilor instructiunii de adunare trebuie sa fie in intervalul 09. In acest caz, instructiunea AAA ajusteaza registrul AX pentru a contine rezultatul zecimal corect in format BCD despachetat. Daca adunarea a dus la un transport zecimal, registrul AH este incrementat iar flagurile CF si AF sunt setate. Daca nu a fost transport zecimal, flagurile CF si AF sunt sterse iar AH ramane neschimbat. In ambele cazuri, registrul AL ramane cu jumatatea superioara in 0 (BCD despachetat).
De exemplu, daca AH=0 si daca AL=0Ah atunci AX devine 0100, daca AL=0Bh atunci AX devine 0101, daca AL=0Ch atunci AX devine 0102, s.a.m.d.).
Dupa instructiunea AAA se poate obtine in AL rezultatul in cod ASCII executand o instructiune OR AL,30h
AAS - Ajustare in cod BCD despachetat a lui AL dupa scadere
Actiune:
IF (AL AND OFH) > 9) OR (AF=1)
THEN
AL ← AL - 6) AND OFH;
AH ← AH - 1;
AF ← 1;
CY ← 1;
ELSE
CF ← 0;
AF ← 0
FI.
Descriere: Executia instructiunii AAS se face numai dupa instructiunea SUB (sau SBB), care lasa rezultatul in registrul AL. Semioctetii inferiori ai operanzilor instructiunii de scadere trebuie sa fie in intervalul 09. In acest caz, instructiunea AAS ajusteaza registrul AX pentru a contine rezultatul zecimal corect in format BCD despachetat Daca scaderea a dus la un transport zecimal, registrul AH este decrementat iar flagurile CF si AF sunt setate. Daca nu a fost transport zecimal, flagurile CF si AF sunt sterse iar AH ramane neschimbat. In ambele cazuri, registrul AL ramane cu jumatatea superioara in 0 (BCD despachetat).
Dupa instructiunea AAA se poate obtine in AL rezultatul in cod ASCII executand o instructiune OR AL,30h
DAA - Ajustare AL dupa adunare (BCD impachetat)
Actiune:
IF (AL AND OFH) > 9) OR (AF=1)
THEN
AL ← AL + 6;
AF ← 1;
ELSE
AF ← 0;
FI
IF (AL> 9FH) OR (CF=1)
THEN
AL ← AL +60H;
CF ← 1;
ELSE
CF ← 0;
FI.
Descriere: Executia instructiunii DAA se face numai dupa instructiunea ADD (sau ADC), care lasa un rezultat de doi digiti BCD impachetat in registrul AL. Cei doi operanzi ai instructiunii de adunare trebuiau sa fi fost de asemenea in format BCD impachetat pe cate doi digiti. In acest caz, instructiunea DAA ajusteaza registrul AL pentru a contine cele doua cifre BCD impachetat corecte ale rezultatului.
DAS - Ajustare AL dupa scadere (BCD impachetat)
Actiune:
IF (AL AND OFH) > 9) OR (AF=1)
THEN
AL ← AL - 6;
AF ← 1;
ELSE
AF ← 0;
FI
IF (AL> 9FH) OR (CF=1)
THEN
AL ← AL -60H;
CF ← 1;
ELSE
CF ← 0;
FI.
Descriere: Executia instructiunii DAA se face numai dupa instructiunea SUB (sau SBB), care lasa un rezultat de doi digiti BCD impachetat in registrul AL. Cei doi operanzi ai instructiunii de scadere trebuiau sa fi fost de asemenea in format BCD impachetat pe cate doi digiti. In acest caz, instructiunea DAS ajusteaza registrul AL pentru a contine cele doua cifre BCD impachetat corecte ale rezultatului.
AAM - Ajustare AL dupa inmultire
Actiune: AH ← AL/10;
AL ← AL modulo 10.
Descriere: Executia instructiunii AAM se face numai dupa instructiunea MUL intre doua cifre BCD despachetate (fiecare ocupa cate un octet), care lasa rezultatul in registrul AX. Deoarece rezultatul este mai mic de 100, el este continut integral in registrul AL. Instructiunea AAM despacheteaza rezultatul din AL prin impartire cu 10, lasand catul (cifra cea mai semnificativa) in AH, si restul (cifra mai putin semnificativa) in registrul AL.
AAD - Ajustare AL inainte de impartire;
Actiune:
AL ← AH * 10 + AL;
AH ← 0.
Instructiunea AAD este folosita pentru a pregati doua cifre in format BCD despachetat (cifra mai putin semnificativa in AL si cea mai semnificativa in AH) pentru o impartire care va genera un rezultat in format BCD despachetat. Aceasta se realizeaza dand lui AL valoarea AL+(10*AH) si lui AH valoarea 0. AX va deveni egal deci cu echivalentul binar al numarului initial de doua cifre BCD despachetat.
A1.3.3. Deplasari si rotatii
SHL src,[nr] -Deplasare logica spre stanga cu nr pozitii (numere fara semn)
Actiune:
C MSB LSB
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Operandul src este inmultit cu 2 de [nr] ori.
SHR src,[nr] -Deplasare logica spre dreapta cu nr pozitii (numere fara semn)
Actiune:
MSB LSB C
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Operandul src este impartit cu 2 de [nr] ori.
SAL src,[nr] -Deplasare aritmetica spre stanga cu nr pozitii (numere cu semn)
Actiune:
C MSB LSB
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Operandul src cu semn este inmultit cu 2 de [nr] ori. Instructiunea este echivalenta cu instructiunea SHL
SAR src,[nr] -Deplasare aritmetica spre dreapta cu nr pozitii (numere cu semn)
Actiune:
MSB LSB C
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Operandul src cu semn este impartit cu 2 de [nr] ori.
ROL src,[nr]-Rotatie prin carry spre stanga cu [nr] pozitii
Actiune:
C MSB LSB
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
ROR src,[nr]-Rotatie prin carry spre dreapta cu [nr] pozitii
Actiune:
MSB LSB C
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
RCL src,[nr]-Rotatie cu carry spre stanga cu [nr] pozitii
Actiune:
C MSB LSB
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
RCR src,[nr]-Rotatie cu carry spre dreapta cu [nr] pozitii
Actiune:
MSB LSB C
Operanzi: -src:r8,r16,r32,m8,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Fiecare instructiune de rotatie ROL si ROR deplaseaza bitii operandului src (registru sau locatie de memorie). Instructiunile de rotatie spre stanga deplaseaza toti bitii catre pozitia cea mai semnificativa (catre MSB), exceptand bitul din pozitia cea mai semnificativa, care este mutat in pozitia cea mai putin semnificativa (LSB). Instructiunile de rotatie spre dreapta actioneaza invers: bitii sunt deplasati catre pozitia cea mai putin semnificativa iar bitul din pozitia cea mai putin semnificativa ajunge in pozitia cea mai semnificativa.
Pentru instructiunile RCL si RCR, flagul CF este o parte a cantitatii rotite. Instructiunea RCL deplaseaza flagul CF in bitul cel mai putin semnificativ si cel mai semnificativ bit in flagul CF; instructiune a RCR deplaseaza flagul CF in bitul cel mai semnificativ si bitul cel mai semnificativ in flagul CF. La instructiunile ROL si ROR, valoarea flagului CF nu este parte a rezultatului, dar flagul CF receptioneaza o copie a bitului care a fost deplasat de la un capat la altul.
Rotatia este repetata de un numar de ori indicat de al doilea operand, care este 1, o valoare imediata de 8 biti, sau continutul registrului CL.
Numarul de deplasari maxim admis este de 31; daca se specifica [n] mai mare, se trunchiaza automat la cei mai putin semnificativi 5 biti.
Flagul OF este definit numai pentru forme cu o singura rotatie ale instructiunilor (al doilea operand este un 1). Este nedefinit in toate celelalte cazuri. Pentru deplasari/rotiri spre stanga, bitul CF de dupa deplasare este 'sau-exclusivat' cu bitul rezultat de cel mai inalt ordin, spre a rezulta flagul OF. Pentru deplasari/rotiri spre dreapta, cei doi biti cu cel mai inalt ordin ai rezultatului sunt 'sau-exclusivati' spre a rezulta flagul OF.
SHLD dst,src,[n] - deplasare stanga cu dubla precizie
C MSB dst LSB MSB src LSB
Operanzi: -src:r16,r32,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Continutul dst (registru sau locatie de memorie) este deplasat spre stanga de [n] ori impreuna cu registrul src, ai carui biti patrund in dst. Registrul src ramane neschimbat. Bitul CF ia valoarea ultimului bit care a fost deplasat din MSB al dst.
Deoarece bitii care vor intra prin deplasare in dst sunt proveniti de la un alt registru, aceasta instructiune este utila pentru deplasari cu dubla precizie (pe 64 de biti)
SHRD dst,src,[n]- deplasare dreapta cu dubla precizie
MSB src LSB MSB dst LSB C
Operanzi: -src:r16,r32,m16,m32;
-[nr]: 1, CL,imm8.
Descriere: Continutul dst (registru sau locatie de memorie) este deplasat spre dreapta de [n] ori impreuna cu registrul src, ai carui biti patrund in dst. Registrul src ramane neschimbat. Bitul CF ia valoarea ultimului bit care a fost deplasat din MSB al dst.
Deoarece bitii care vor intra prin deplasare in dst sunt proveniti de la un alt registru, aceasta instructiune este utila pentru deplasari cu dubla precizie (pe 64 de biti).
A1.4 Instructiuni de lucru pe bit
CLC - stergere flag transport (CF = 0)
STC - setare flag transport (CF = 1)
CMC - complementarea transport (CF = NOT CF)
CLD - stabilire directie crescatoare (DF = 0)
Dupa aceasta instructiune, la operatiile cu siruri registrele index vor fi incrementate.
STD - stabilire diretie descrescatoare (DF 1)
Dupa aceasta instructiune, la operatiile cu siruri registrele index vor fi decrementate.
STI - activare intreruperi (IF = 1)
CLI - dezactivare intreruperi (IF = 0)
BT - Testare bit (Copiere bit in CF)
Mnemonic: BT dst,src
dst: r16,r32,m16,m32;
src: r16,r32,imm8.
Actiune: CF← Bit( Baza, index).
Descriere: Primul operand specifica baza iar al doilea indexul. Bitul cu indexul dat de ala doilea operand din registrul sau locatia de memorie specificata de primul operand este copiat in CF. Daca baza este un registru, indexul este ajustat automat modulo 16 sau modulo 32 in functie de marimea registrului. Daca baza este o locatie de memorie, ea reprezinta adresa locatiei de memorie care contine bitul cu index 0. Sunt posibile valori ale indexului intre -231 si 231-1 daca al doilea operand este un registru sau intre 0 si 31 daca al doilea operand este o valoare imediata.
BTR - Testare bit si resetare (Copiere bit in CF si resetare)
Mnemonic: BT dst,src
dst: r16,r32,m16,m32;
src: r16,r32,imm8.
Actiune: CF← Bit( Baza, index)
Bit( Baza, index)← 0.
Descriere: Primul operand specifica baza iar al doilea indexul. Bitul cu indexul dat de al doilea operand din registrul sau locatia de memorie specificata de primul operand este copiat in CF, dupa care este resetat (adus la 0). Daca baza este un registru, indexul este ajustat automat modulo 16 sau modulo 32 in functie de marimea registrului. Daca baza este o locatie de memorie, ea reprezinta adresa locatiei de memorie care contine bitul cu index 0. Sunt posibile valori ale indexului intre -231 si 231-1 daca al doilea operand este un registru sau intre 0 si 31 daca al doilea operand este o valoare imediata.
BTS - Testare bit si setare (Copiere bit in CF si setare)
Mnemonic: BT dst,src
dst: r16,r32,m16,m32;
src: r16,r32,imm8.
Actiune: CF← Bit( Baza, index)
Bit( Baza, index)← 1.
Descriere: Primul operand specifica baza iar al doilea indexul. Bitul cu indexul dat de ala doilea operand din registrul sau locatia de memorie specificata de primul operand este copiat in CF, dupa care este setat (adus la 1). Daca baza este un registru, indexul este ajustat automat modulo 16 sau modulo 32 in functie de marimea registrului. Daca baza este o locatie de memorie, ea reprezinta adresa locatiei de memorie care contine bitul cu index 0. Sunt posibile valori ale indexului intre -231 si 231-1 daca al doilea operand este un registru sau intre 0 si 31 daca al doilea operand este o valoare imediata.
BTC - Testare bit si complementare (Copiere bit in CF si complementare)
Mnemonic: BT dst,src
dst: r16,r32,m16,m32;
src: r16,r32,imm8.
Actiune: CF← Bit( Baza, index);
Bit( Baza, index)← NOT Bit( Baza, index).
Descriere: Primul operand specifica baza iar al doilea indexul. Bitul cu indexul dat de ala doilea operand din registrul sau locatia de memorie specificata de primul operand este copiat in CF, dupa care este complementat (ia valoarea opusa). Daca baza este un registru, indexul este ajustat automat modulo 16 sau modulo 32 in functie de marimea registrului. Daca baza este o locatie de memorie, ea reprezinta adresa locatiei de memorie care contine bitul cu index 0. Sunt posibile valori ale indexului intre -231 si 231-1 daca al doilea operand este un registru sau intre 0 si 31 daca al doilea operand este o valoare imediata.
BSF - Scanare inainte a bitilor
Mnemonic: BSF dst,src
dst: r16,r32;
src: r16,r32,m16,m32.
Actiune: dst←index(src,0).
Descriere: Bitii din src sunt testati pe rand incepand cu cel mai putin semnificativ, si daca toti sunt 0 este sters flagul ZF. Daca vreunul este gasit in 1, indexul sau incepand de la 0 este scris in dst.
BSF - Scanare inapoi a bitilor
Mnemonic: BSR dst,src
dst: r16,r32;
src: r16,r32,m16,m32.
Actiune: dst←index(src,0).
Descriere: Bitii din src sunt testati pe rand incepand cu cel mai semnificativ, si daca toti sunt 0 este sters flagul ZF. Daca vreunul este gasit in 1, indexul sau incepand de la 0 este scris in dst.
SETcc - Seteaza octet daca conditia cc este indeplinita
Instructiunea are una din urmatoarele forme:
SETA r/m8 Seteaza octetul daca este peste (CF=0 and ZF=0)
SETAE r/m8 Seteaza octetul daca este peste sau egal (CF=0)
SETB r/m8 Seteaza octetul daca este sub (CF=1)
SETBE r/m8 Seteaza octetul daca este sub sau egal (CF=1 or (ZF=1)
SETC r/m8 Seteaza octetul daca este transport (CF=1)
SETE r/m8 Seteaza octetul daca este egal (ZF=1)
SETG r/m8 Seteaza octetul daca este mai mare (ZF=0 or SF=OF)
SETGE r/m8 Seteaza octetul daca este mai mare sau egal (SF=OF)
SETL r/m8 Seteaza octetul daca este mai mic (SF←>OF)
SETLE r/m8 Seteaza octetul daca este mai mic sau egal (ZF=1 si SF←>OF)
SETNA r/m8 Seteaza octetul daca nu este peste (CF=1)
SETNAE r/m8 Seteaza octetul daca nu este peste sau egal (CF=1)
SETNB r/m8 Seteaza octetul daca nu este sub (CF=0)
SETNBE r/m8 Seteaza octetul daca nu este sub sau egal (CF=0 si ZF=0)
SETNC r/m8 Seteaza octetul daca nu este transport (CF=0)
SETNE r/m8 Seteaza octetul daca nu este (ZF=0)
SETNG r/m8 Seteaza octetul daca nu este mai mare (ZF=1 or SF←>OF)
SETNGE r/m8 Seteaza octetul daca nu este mai mare sau egal (SF←>OF)
SETNL r/m8 Seteaza octetul daca nu este mai mic (SF=OF)
SETNLE r/m8 Seteaza octetul daca nu este mai mic sau egal (ZF=1 si SF←>OF)
SETNO r/m8 Seteaza octetul daca nu este overflow (OF=0)
SETNP r/m8 Seteaza octetul daca nu este paritate (PF=0)
SETNS r/m8 Seteaza octetul daca semnul este 0 (SF=0)
SETNZ r/m8 Seteaza octetul daca nu este zero (ZF=0)
SETO r/m8 Seteaza octetul daca este overflow (OF=1)
SETP r/m8 Seteaza octetul daca este paritate (PF=1)
SETPE r/m8 Seteaza octetul daca este paritate para (PF=1)
SETPO r/m8 Seteaza octetul daca este paritate impara (PF=0)
SETS r/m8 Seteaza octetul daca semnul este 1 (SF=1)
SETZ r/m8 Seteaza octetul daca este zero (ZF=1)
Descriere: Daca conditia este indeplinita, atunci operandul (registru de 8 biti sau locatie de memorie) devine 1. Daca nu, acesta devine 0.
A1.5. Instructiuni de ramificare in program
JMP adr - salt neconditionat
adr: r16,r32,m16,m32,rel8,rel16,rel32,ptr16:16,ptr16:32,m16:16,m16:32.
Descriere: Instructiunea JMP transfera controlul catre un alt punct in lantul de instructiuni fara a se memora adresa de revenire. Operandul adr (tinta) specifica adresa instructiunii la care se sare. Acest operand poate fi o valoare imediata, un registru de uz general sau o locatie de memorie.
Aceasta instructiune poate executa patru tipuri diferite de salturi:
Salt apropiat (near) - Un salt catre o instructiune din segmentul de cod curent, segment indicat de continutul curent al registrului CS), numit si salt intrasegment.
Task switch - Un salt catre o instructiune aflata intr-un alt task (posibil numai in modul virtual protejat - v. [2] )
Salturile apropiate si scurte. Cand se executa un salt apropiat, procesorul sare la adresa (din segmentul de cod curent) care este specificata de operandul tinta. Acesta specifica fie un deplasament absolut (fata de baza segmentului de cod) fie un deplasament relativ (o valoare cu semn fata de valoarea curenta a numaratorului de program).Registrul CS nu se modifica la astfel de salturi.
Un deplasamet absolut este specificat indirect printr-un registru general sau o locatie de memorie (operandul este r16/m16 sau r32/m32).Un deplasament absolut se incarca direct in EIP. Marimea operandului determina si continutul EIP; daca acesta este de 16 biti, cei 16 biti superiori din EIP sunt pusi in 0, rezultand un deplasament care nu depaseste 16 biti.
Un deplasament relativ este in general specificat in limbaj de asamblare printr-o eticheta, dar la nivel de cod masina acesta este decodificat ca o valoare imediata cu semn, de 8, 16 sau 32 de biti. Aceasta valoare este adunata la valoarea din EIP, adica la adresa instructiunii imediat urmatoare celei de salt.
Salturi indepartate in modul Real sau Virtual 8086. Cand se executa un salt indepartat in modul Real sau Virtual 8086, procesorul sare la un segment de cod si un deplasament specificat de operandul instructiunii. Acesta specifica o adresa absoluta departata, fie direct printr-un pointer (ptr16:16 sau ptr16:32) fie indirect printr-o locatie de memorie (m16:16 sau m16:32).
In varianta cu pointer, segmentul si deplasamentul adresei la care se sare sunt specificate de instructiune printr-o valoare imediata de 4 octeti (operand de 16 biti) sau de 6 octeti (operand de 32 de biti).
In varianta indirecta, operandul specifica o locatie de memorie care contine 4 octeti (operand de 16 biti) sau 6 octeti (operand de 32 de biti).
Adresa indepartata este incarcata direct in registrele CS (primii doi octeti) si EIP (uramatorii 2 sau 4 octeti). Daca operandul este de 16 biti, cei 16 biti superiori din EIP sunt pusi in 0, rezultand un deplasament care nu depaseste 16 biti.
Jcc adr - Salt conditionat
adr: rel8,rel16,rel32.
Descriere: Instructiunea Jcc transfera controlul catre un alt punct in lantul de instructiuni fara a se memora adresa de revenire, numai daca este indeplinita conditia cc. Daca aceasta conditie nu este indeplinita, se continua cu instructiunea imediat urmatoare. Operandul adr (tinta) specifica adresa instructiunii la care se sare. Acest operand este un deplasament relativ. In general, in limbaj de asamblare, deplasamentul relativ este specificat printr-o eticheta, dar la nivel de cod masina acesta este decodificat ca o valoare imediata cu semn, de 8, 16 sau 32 de biti. Aceasta valoare este adunata la valoarea din EIP, adica la adresa instructiunii imediat urmatoare celei de salt.
Aceasta instructiune poate executa doua tipuri diferite de salturi:
Salt apropiat (near) - Un salt catre o instructiune din segmentul de cod curent, segment indicat de continutul curent al registrului CS), numit si salt intrasegment.
In functie de rezultatul operatiei aritmetice sau logice precedente (care modifica anumiti indicatori de conditii) pot exista urmatoarele forme de instructiuni de salt conditionat:
JP adr (JPE adr) - salt conditionat de paritate para. (PF=1)
JNP adr (JPO adr) - salt conditionat de paritate impara (PF=0)
JO adr - salt conditionat de OF = 1 - a fost depasire.
JNO adr - salt conditionat de OF = 0 - nu a fost depasire.
JS adr - salt conditionat de SF = 1 - rezultatul a fost negativ.
JNS adr - salt conditionat de SF = 0 - rezultatul a fost pozitiv.
JE adr (JZ adr) - salt conditionat de ZF = 1 - egalitate la comparatia anterioara.
JNE adr (JNZ adr) - salt conditionat de ZF = 0 - inegalitate la comparatia anterioara.
Salturi conditionate de comparatii ale unor numere cu semn:
JL adr (JNGE adr) - salt conditionat de SF ≠ OF (SF xor OF = 1) - mai mic la comparatia anterioara a unor valori cu semn.
JLE adr (JNG adr) - salt conditionat de ZF = 1 sau SF ≠ OF - mai mic sau egal la comparati a anterioara a unor valori cu semn.
JG adr (JNLE adr) - sat conditionat de ZF = 0 si SF = OF - mai mare la comparatia anterioara a unor valori cu semn.
JGE adr (JNL adr) - salt conditionat de SF = OF - mai mare sau egal la comparatia anterioara a unor valori cu semn.
Salturi conditionate de comparatii ale unor numere fara semn:
JB adr (JNAE adr, JC adr) - salt conditionat de CF = 1 - mai mic la comparatia anterioara a unor valori cu fara semn sau transport la operatia anterioara.
JBE adr (JNA adr) - salt conditionat de CF = 1 sau ZF = 1 - mai mic sau egal la comparatia anterioara a unor valori fara semn.
JA adr (JNBE adr) - salt conditionat de CF = ZF = 0 - mai mare la comparatia anterioara a unor valori fara semn.
JAE adr (JNB adr, JNC adr) - salt conditionat de CF = 0 - mai mare sau egal la comparatia anterioara a unor valori fara semn sau nu exista transport la operatia anterioara.
JCXZ - salt conditionat de continutul lui CX = 0.Deplasament numai pe 8 biti.
JECXZ - salt conditionat de continutul lui ECX = 0.Deplasament numai pe 8 biti.
LOOP, LOOPE,(LOOPZ),LOOPNE(LOOPNZ)
Mnemonic: LOOP, LOOPE,(LOOPZ),LOOPNE(LOOPNZ)
Descriere: Instructiunea LOOP decrementeaza contorul CX sau ECX fara sa schimbe flagurile. Apoi sunt testate conditiile specificate de forma LOOP folosita. Daca conditia este indeplinita, se face un salt scurt (domeniul -128 pana la +127) la eticheta data de operandul instructiunii LOOP. Acest lucru se repeta pana cand contorul ajunge la 0 sau pana cand conditia nu mai este indeplinita. Daca atributul de lungime al operandului este 16 biti contorul va fi CX, iar daca este de 32 de biti contorul va fi ECX .
Instructiunea LOOP permite controlul iteratiilor prin combinarea decrementarii automate a indexului cu saltul conditionat. Se foloseste introducand in registrul contor (CX sau ECX) numarul fara semn al iteratiilor si punand instructiunea LOOP la sfarsitul seriei de instructiuni care vor fi repetate. Operandul instructiunii LOOP este eticheta de la inceputul secventei care se va repeta.
LOOP - Repetare de CX ori a secventei
Mnemonic : LOOP rel8.
Operand: n: numar cu semn pe 8 biti.
Actiune: CX ← CX - 1;
daca CX ≠ 0 atunci IP ← IP + n.
Se repeta secventa de instructiuni de lungime n octeti, marcata cu un capat de instructiunea LOOP pana cand CX = 0. Lungimea fiind data de un numar cu semn, poate fi cuprinsa intre -128 si +128 octeti.
LOOPZ (sau LOOPE) - Repetare de CX ori a secventei, conditionata de ZF = 1
Mnemonic: LOOPZ rel8.
Operand: n: numar cu semn pe 8 biti.
Actiune: CX ← CX - 1;
daca ZF =1 si CX ≠ 0 atunci IP ← IP + n.
Se repeta secventa de instructiuni de lungime n octeti, marcata cu un capat de instructiunea LOOP pana cand CX = 0, dar numai cat timp ZF =1. Orice resetare a fanionului ZF duce la iesirea fortata din ciclu. Lungimea fiind data de un numar cu semn, poate fi cuprinsa intre -128 si +128 octeti.
LOOPNZ (sau LOOPNE -Repetare de CX ori a secventei, conditionata de ZF = 0.
Mnemonic: LOOPNZ rel8
Operand: n: numar cu semn pe 8 biti.
Actiune: CX ← CX -1;
daca ZF = 0 si CX ≠ 0 atunci IP ← IP + n.
Se repeta secventa de instructiuni de lungime n octeti, marcata cu un capat de instructiunea LOOP pana cand CX = 0, dar numai cat timp ZF = 0. Orice resetare a fanionului ZF duce la iesirea fortata din ciclu. Lungimea fiind data de un numar cu semn, poate fi cuprinsa intre -128 si +128 octeti.
CALL adr - apel de subrutina
Descriere: Instructiunea CALL conduce la executia subrutinei (procedurii) al carei nume este specificat de operand. Cand aceasta procedura s-a terminat (apare o instructiune RET de reintoarcere), executia programului continua cu instructiunea imediat urmatoare instructiunii CALL.
Actiune: Exista doua variante ale acestei instructiuni, a caror Actiune este urmatoarea:
CALL apropiat (near). Sunt acele apeluri de proceduri care au operandul de tip r16, m16, r232, m32, rel16 si rel32, care se executa in interiorul aceluiasi segment. Prin urmare, schimbarea si salvarea registrului de segment de cod nu este necesara.
Formele CALL rel16 si CALL rel32 aduna un deplasament cu semn la continutul lui EIP (adresa instructiunii care urmeaza lui CALL), pentru a determina destinatia. Marimea operandului determina si continutul EIP; daca acesta este de numai 16 biti, cei 16 biti superiori din EIP sunt pusi in 0, rezultand un deplasament care nu depaseste 16 biti.
Formele CALL r16/m16 si CALL r32/m32 specifica un registru sau o adresa de memorie de unde se extrage deplasamentul absolut fata de baza segmentului (adresa efectiva). Marimea operandului determina si marimea deplasamentului extras.
Valoarea curenta a lui EIP (adresa instructiunii imediat urmatoare lui CALL) este salvata in stiva inainte de incarcarea EIP cu noua adresa efectiva (deplasament fata de baza segmentului). Aceasta va fi readusa in EIP de instructiunea RET cu care se termina subrutina.
CALL indepartat (far). Formele CALL ptr16:16 si CALL ptr 16:32 folosesc un pointer de 4 sau 6 octeti catre subrutina chemata. Formele CALL m16:16 si CALL m16:32 extrag pointerul respectiv din locatia de memorie specificata. In modul Real sau Virtual 8086, pointerul da 16 biti pentru registrul CS si restul de 16 sau 32 de biti pentru registrul EIP. Instructiunile CALL indepartat salveaza in stiva si registrul CS si registrul IP (sau EIP).
RET - reantoarcere din subrutina
Mnemonic: RET
RET n
Descriere: Instructiunea RET produce reintoarcerea dintr-o subrutina prin transferarea controlului la instructiunea a carei adresa se afla in stiva. Acesta adresa este in mod normal plasata in stiva de o instructiune CALL, iar reintoarcerea se face la instructiunea imediat urmatoare acesteia.
Parametrul numeric optional al instructiunii RET da numarul de octeti din stiva (daca operandul e pe 16 biti) sau de cuvinte (daca operandul e pe 32 de biti) care sa fie eliberati dupa ce este extrasa adresa de reintoarcere.
Pentru o reintoarcere intrasegment (apropiata), adresa extrasa din stiva este un deplasament fata de baza segmentului (adresa efectiva) care va fi incarca in IP. Registrul CS ramane neschimbat.
Pentru o reintoarcere intersegment (indepartata), adresa extrasa din stiva este un pointer. Mai intai este extras deplasamentul si incarcat in IP iar apoi adresa de segment si incarcata in CS.
INT - apelare intrerupere software
Mnemonic: INT n
INTO
Descriere: Instructiunea INT genereaza o chemare prin software a unei subrutine de tratare a unei intreruperi. Operandul imediat, cuprins intre 0 si 255 da indexul in tabela de intreruperi al subrutinei care este chemata. In modul Real, aceasta tabela cuprinde pointeri de cate 4 octeti
Intreruperea conditionata INTO este identica cu INT, dar operandul implicit este 4, si poate apare numai daca flagul Overflow este setat.
Primele 32 de intreruperi sunt rezervate de Intel pentru utilizari speciale. Unele dintre ele sunt folosite de exceptiile generate intern de procesor.
INT se comporta in principiu ca un CALL (far) dar inainte de a se salva in stiva adresa de reintoarcere, se salveaza si registrul de flaguri. Subrutinele de tratare a intreruperilor se incheie cu instructiunea IRET care aduce din stiva si adresa de reintoarcere si continutul registrului de flaguri
Instructiunea INT este folosita frecvent pentru apelarea unor subrutine standard din BIOS sau din sistemul de operare (vezi anexele 2 si 3), care pot realiza foarte eficient o serie de actiuni de larga raspandire.
IRET - reintoarcere din intrerupere
Descriere: In modul Real, instructiunea IRET extrage din stiva adresa de reintoarcere din subrutina de tratare a unei intreruperi, precum si registrul de flaguri. Aceasta are ca efect revenirea in program la instructiunea imediat urmatoare celei care a precedat intreruperea, cu reactivarea intreruperilor (acceptarea unei cerei de intrerupere sterge flagul de intreruperi). Ca alternativa, daca s-ar folosi la sfarsitul rutinei de intrerupere o instructiune de tip RET, aceasta ar trebui precedata de o instructiune STI pentru reactivarea intreruperilor.
A1.6. Instructiuni speciale
HLT - oprirea oricarei activitati a procesorului. Se poate iesi numai cu RESET sau intrerupere hard. Daca se iese din aceasta stare cu o intrerupere (inclusiv NMI), programul continua cu instructiunea imediat urmatoare instructiunii HLT.
NOP - Instructiune fara operatie.
Politica de confidentialitate | Termeni si conditii de utilizare |
Vizualizari: 1825
Importanta:
Termeni si conditii de utilizare | Contact
© SCRIGROUP 2024 . All rights reserved