Polyasm
Polyasm
Polyasm
1 Introduction
1.1 Architecture d'un ordinateur
Un ordinateur de type PC est constitue d'elements assurant des fonctions pre-
cises : le calcul, la memoire, la circulation des informations(programmes et donnees),
le contr^ole des dierents organes.
Bus d’adresse
Mémoire RAM
1
{ Le mnemonique ou assembleur. Programmer en code machine est peut pra-
tique, et on prefere decrire des operations a realiser a l'aide de mots-cles qui
rappelent la signication de cette operation. Un programme special ( pour
nous TURBO-ASSEMBLEUR) compile ce langage. La compilation est une
operation en 2 phases : apres verication de la validite du programme decrit
en assembleur, ce dernier est traduit en code machine pr^et a ^etre execute. ( a
une operation pres qu'on appele l'edition de liens).
Par exemple, incrementer de 1 le registre AL s'ecrit en assembleur 8086: INC
AL
{ les langages evolues : PASCAL, C, ADA, COBOL, .. .En PASCAL, par exemple,
l'operation precedente pourrait s'ecrire : i:= i + 1 ;
1.3 Numeration
1.3.1 Representation des nombres
L'atome d'information s'appele le bit et vaut 0 ou 1. Avec un bit, on peut coder
2 informations dierentes, deux etats : m^ale ou femelle, noir ou blanc, .. .
Avec 2 bits, on peut coder 4 (22 ) etats ou congurations dierentes : 00, 01, 10
et 11. soient les 4 saisons, 4 chires, 4 situations particulieres .. .
On a convenu tres t^ot de grouper les bits par 8 pour constituer un octet, ce qui
permet de coder 28 nombres ou etats. Un octet permet de coder 256 valeurs die-
rentes, ce qui est susant, en occident, pour representer l'ensemble des caracteres
d'un clavier de machine a ecrire. A chaque valeur sur 8 bits correspond un symbole
alphanumerique. Plusieurs codes existent, mais le plus utilise en informatique, en
tout cas sur un PC est le code ASCII. Dans ce code, le caractere A est code 65, a
est code 97, le chire 0 est code 48.
Enn, on regroupe frequemment les octets par 2, 4 ou plus, pour constituer des
mots, doubles-mots, . . .
On convient que le bit de poids le plus faible d'un nombre sera denomme \bit
0" et que le bit de poids le plus fort sera denomme \ bit 7" ou \bit 15", selon la
longueur de la representation.
1.3.2 Conversion binaire-decimal
Nous travaillons en numeration de position, ce qui signie que, dans n'importe
quelle base de representation, un nombre s'ecrit toujours :
n =
X,
d 1
i
Pi b
k=0
ou d est le nombre de chires, i un poids et b la base. Par exemple, en base 10,
p
Un nombre binaire est une suite de 0 et de 1 de poids respectifs : 20, 21, 22 , etc
.. .
Ainsi 1101 a pour valeur en decimal: 1 23 + 1 22 + 0 21 + 1 20 a partir des
: : : :
2
De plus, ce sont toujours des chires, car le nombre 13 par exemple, dans une base
b donnee, signie 3 unites et 1 fois la base a la puissance 1. En base 16, on ne peut
plus trouver de chires pour representer les valeurs comprises entre 10 et 15. 10 a
la signication: 0 unites et une seizaine. On utilise donc les lettres A, B,.. .F; A
correspond au 10 decimal, B au 11 decimal, . .. et F au 15 decimal.
Ainsi 2C hexa vaut 2*16+13, soit 4510.
A l'inverse, la division par 16 fournit les poids de la representation hexa d'une
valeur decimale.
1.3.4 hexadecimal-binaire
A un \chire " hexadecimal correspondent 4 bits, car F = 1111. La correspon-
dance est ainsi tres facile.
Partant d'un nombre binaire, il sut de grouper ses bits par 4 a partir des poids
faibles, puis de donner la correspondance hexadecimale de chacun des groupes. Par
exemple:
11 1101 0110 1110 vaut 3D6E
Un programmeur en assembleur doit savoir jongler avec l'ensemble de ces repre-
sentations et codages ( auquels il doit bien souvent ajouter loctal). Ainsi la lettre
`A' dont le code decimal en ASCII est 65 a pour representation binaire 01000001b
et 41h en hexadecimal.
1.3.5 Notation des nombres en ASM86
An de permettre a l'assembleur de distinguer les dierentes bases de represen-
tation, les valeurs binaires sont accompagnees d'un b minuscule, les valeurs octales
d'un o minuscules et les valeurs hexa d'un h minuscule. Pour eviter de plus les confu-
sions avec les identicateurs ou mots-cles du langage, les valeurs hexadecimales dont
le premier \chire " est une lettre sont precedees d'un 0.
Exemples :
mov al, 01110100b
mov ah, 75h
mov ax, 0BAD4h
2 Le 8086
2.1 La famille IAPx86
Il s'agit d'une famille de processeurs a compatibilite ascendante, c.a.d. que le
code des plus anciens est toujours compris et correctement execute par les plus
recents.
{ le 8086 dispose d'un bus de 16 bits pour les donnees. sa capacite d'adressage
est de 1Mo et il est cadence a 4.77 ou 8 Mhz.
{ le 8088 est la version 8 bits du 8086. il a les m^emes caracteristiques, mais un
assembleur plus reduit.
{ le 80286 est une machine 16 bits, pouvant adresser 8Mo de code et de donnees,
cadence a 6,8,10,12 ou 16 Mhz. Il introduit 2 modes d'adressage ( reel ou
protege).
{ le 80386 est un faux 32 bits, adressant 4Go et cadence a 16, 20 ou 25 Mhz.
3
{ le 80486 est un vrai 32 bits dote d'une memoire cache integree et d'une unite
de calcul en virgule
ottante.
{ le 80586, appele pentium pour des raisons de protection commerciale, dispose
d'un bus de donnees de 64 bits et est muni d'un dispositif de prevision des
branchements. Il est constitue de 2 processeurs en pipe-line paralleles lui per-
mettant d'executer deux instructions en m^eme temps. Son cadencement est
envisage (en 1994) jusqu'a 150 MHZ.
{ le \P6", successeur du pentium, est annonce. Il sera constitue de 6 millions
de transistors ( contre 275 000 pour le 386 , 1 million pour le 486 et 3 pour
le pentium) et la dimension des traits de ses transistors sera de 0.6 microns
(contre 11.5 pour le 386). Il pourra traiter 250 millions d'instructions par
seconde.
Dans la suite, nous ne nous interresserons qu'au 8086.
2.2 Les memoires du 8086
Le 8086 dipose de plusieurs memoires. La plus importante est la memoire de tra-
vail ou RAM (Random Access Memory). C'est elle qui contient la partie active du
systeme, les programmes et les donnees. Il existe une memoire morte (ininscriptible),
la ROM, qui contient le code binaire des instructions assembleur et les sequences
correspondant aux dierentes interruptions.L'ordinateur dispose enn d'une troi-
sieme memoire physiquement distincte de la RAM, la memoire d'Entrees/Sorties,
permettant les echanges avec l'exterieur.
La RAM est un bloc de 1 Mo d'adresses qui est decoupe de la maniere suivante:
La partie basse des adresses est reservee pour le systeme. Au dessus du systeme, on
trouve une zone qui est physiquement limite a 640Ko, dans la quelle on range les
programmes en execution et les donnees actives : le tas. Au dessus du tas se trouve
une pile, destinee a gerer les apels de procedures et les interruptions. Au dessus de
la limite des 640Ko se situe la memoire graphique qui est physiquement situee sur
la carte video.
1 Mo
MEMOIRE
VIDEO
640 Ko
Pile
disponible
pour la pile
ou le tas.
Tas
SYSTEME
4
2.2.1 Mecanisme d'adressage du 8086
Le 8086 peut adresser 1 Mo, soient des adresses allant de 0 a 0FFFFFh. Ceci
pose un pobleme. On a vu que :
{ Un octet peut coder 256 valeurs ( de 0 a 255)
{ Un mot (16 bits) peut en coder 65536 ( de 0 a 65535)
{ Un double-mot (32 bits) peut coder 4 Mo.
Comment a-t-on pu proceder pour qu'une une machine 16 bits puisse adresser da-
vantage que 64 Ko?
En realite, les adresses sont comptees par paquets de 64 Ko. Chacun de ces blocs
d'adresse constitue un SEGMENT. La memoire est donc decoupee en un certain
nombre de segments.
Une adresse logique est constituee de 2 valeurs : un numero de segment et la
valeur de l'oset=deplacemet par rapport au debut du segment.
L'adresse physique du 8086 est representee sur 20 bits (veritable dimension de
son bus d'adresses) soit:
Valeur du segment (16 bits)
* 16 (= d
ecal
ee 4 fois a
gauche)
+ Valeur de l'Offset ( 16 bits)
--------------------------------
= adresse m
emoire sur 20 bits, soit de 0
a 1Mo.
On remarquera que la m^eme adresse absolue peut ^etre obtenue a partir de plu-
sieurs adresses logiques dierentes.
2.3 Les ports d'E/S
En plus de l'espace de 1Mo existe une memoire specialisee de 64 Ko destinee aux
echanges avec l'exterieur (Reseau, imprimantes, ecrans, .. .) Cet echange se fait par
l'intermediaire du port d'Entrees/Sorties (E/S en abrege).
En pratique, on n'utilise qu'un petit nombre d'adresses au sein de cette me-
moire. Les dierents organes connectes a l'ordinateur connaissent la ou les adresses
au niveaux desquelles se font les echanges qui les concernent. Il n'est donc pas
recommande d'ecrire n'importe ou sans precaution.
L'acces a cette memoire se fait a l'aide des instructions IN et OUT.
2.3.1 La memoire Video
Les images video sont implantees en memoire RAM au dela des fatidiques 640 Ko
qui constituent la limite de la memoire centrale ( A l'epoque, vers 1980, il semblait
impossible que l'on ait jamais besoin d'atteindre une limite aussi Kolossale !)
En fait, l'introduction de standards graphiques VGA, VGA etendus, ... a conduit
les architectes a implanter la memoire graphique sur les cartes video elles-m^emes.
Les constructeurs ne s'etant jamais entendu sur un standard, chaque carte a son
propre mode de programmation. Une technique generale existe cependant, assez
lourde, et qui oblige a passer par l'intermediaire d'une zone de la memoire d'E/S et
de registres specialises de la carte graphique.
5
2.3.2 La pile
La programmation d'un ordinateur necessite l'usage (d'au moins) une pile. Une
pile est une structure lineaire dont on ne peut manipuler que le sommet, a l'image
d'une pile d'assiettes : vouloir retirer une assiette du milieu conduit a la catastrophe.
La seule methode d'acces consiste a empiler ou depiler des assiettes a partir du
sommet de la pile. Une telle structure permet de conserver en memoire l'ordre selon
lequel on y a stocke des informations. En les depilant, l'ordinateur se retrouve dans
l'etat ou il etait avant les operations qui ont conduit a des empilements successifs.
L'assembleur vous fera manipuler une pile qui est stockee \en fond de panier",
c.a.d dans les adresses les plus hautes de la memoire. (correspondant aux 640 Ko).
Une petite particularite : La base de la pile se trouve a l'adresse maximale, et elle
s'accroit vers les adresses basses. A l'inverse, les programmes se developpent sur le
\tas", en bas de memoire, juste au dessus de la zone reservee pour le systeme. Pile
et Tas croissent donc a l'inverse l'un de l'autre.
2.4 Les registres
Ce sont des mots de memoire de 16 bits c^ables de facon particuliere, qui per-
mettent de retenir des informations au cours de leur manipulation par le programme.
2.4.1 Registres a usage general
4 registres peuvent se decomposer en 2 registres de 8 bits chacun.
{ AX (A pour accumulateur) joue le r^ole d'operande implicite dans de nom-
breuses operations : MUL, DIV, INC, . .. La partie de poids forts se nomme
AH et celle de poids faibles AL ( H pour high et L pour low)
15 8 7 0
AH AL
Registre AX
6
{ DI (Destination Index) permet comme SI de pointer sur des adresses memoire.
Il est aussi tres utilise pour les traitements de cha^ne (avec STOS)
{ BP (Base Pointer) sert de pointeur sur l'adresse memoire correspondant a
la base de la pile, et permet en fait d'atteindre n'importe quel element de
celle-ci : MOV AX, [BP+4]
{ SP (Stack Pointer) pointe sur le sommet de la pile. Son contenu est automati-
quement gere par les instructions PUSH et POP d'empilage et de desempilage.
2.4.2 Registres speciaux
{ IP (Instruction Pointer) contient l'adresse de l'instruction qui suit celle qui
est en cours d'execution, c'est-a-dire la prochaine a devoir ^etre executee en
dehors des cas de branchement.
{ DS (Data Segment) pointe sur l'adresse de debut du segment qui contient les
donnees. Un segment est une suite de 65536 adresses. Implicitement, BX et
SI, lorsqu'ils servent de pointeur, sont prexes par DS. Une adresse est donc
completement denie par un couple : DS:BX ou DS:SI
Le nom du segment de donnees standard est DATA. Pour charger DS, il faut
obligatoirement utiliser AX ainsi:
MOV AX, @DATA
MOV DS, AX
{ CS (Code Segment) pointe sur le segment contenant le code du programme.
{ ES (Extra Segment) permet de pointer sur un segment supplementaire deni
par le programmeur. Il se charge par l'intermediaire de AX comme DS.
{ SS (Stack Segment) segment contenant la pile.
2.4.3 Le registre indicateur (Flag Register)
Il est utilise pour stocker des etats particulier du microprocesseur en cours de
fonctionnement (le signe de la derniere operation eectuee, l'existence d'une retenue
en cours de propagation, .. .) Quelques bits seulement de ce registre ont une signi-
cation et sont nommes: CF est l'indicateur de retenue (Carry Flag), OF l'indicateur
de debordement (Over
ow Flag), ...
O D I T S Z A P C
Overflow Carry
Direction Parity
Interrupt Auxiliary carry
Trap Sign Zero
Ce registre est contr^ole par des instructions particulieres, par exemple:
CLC : mise
a z
ero de CF (Clear C).
STI : mise
a 1 de IF ( Set I)
CLD : mise
a 0 de DF
STD : mise
a 1 de DF
7
Ce registre est modie par les instructions arithmetiques et logiques, ainsi que
par les comparaisons.
2.5 Les interruptions
APPLICATION Les actions sur l’infrastructure
matérielle se font par interruptions.
infrastructure matérielle
Une interruption est generee par l'instruction INT suivie du numero d'un ser-
vice. Le principal service du DOS est 21h. Le BIOS dispose de nombreux services
correspondant aux dispositifs qu'il commande ( ecran, contr^oleur de disque).
A chaque interruption est associe un ensemble de fonctions du systeme. Le nu-
mero de la fonction se charge toujours dans AH. Selon la fonction, d'autres registres
peuvent aussi ^etre utilises. Exemples de fonctions :
{ Pour desactiver un programme et revenir au DOS : Fonction 4Ch
{ Attente d'un caractere : Fonction 1 du DOS (service 21h). le caractere recu
est dans AL.
{ Achage d'un octet : Fonction 2 du service 21h. le caractere a acher est
dans DL.
{ Positionner le curseur : Fonction 2 du BIOS ( service 10h); le numero de ligne
est place dans DH, le numero de colonne dans DL et le numero de page d'ecran
dans BH.
8
3 Analyse de programmes en assembleur
3.1 Exemples
3.1.1 Fichier: ADDITION.ASM
; Ce programme realise l'addition de deux nombres rentr
es au
; clavier chiffre apres chiffre et affiche le r
esultat.
; Les chiffres lus sont des caracteres. Il faut restituer
; la valeur decimale de chacun d'eux, stocker les nombres obtenus
; sur 4 octets maximum et additionner les octets correspondants
; de chaque nombre en propageant la retenue.
DOSSEG
.MODEL small
.STACK 100h
.DATA
num1 DB 4 dup(0) ; premier nombre
num2 DB 4 dup(0) ; second nombre
num3 DB 4 dup(0) ; r
esultat
chaine1 DB 'TAPEZ LE PREMIER NOMBRE : ','$'
chaine2 DB 13,10, 'TAPEZ LE SECOND NOMBRE : ','$'
chaine3 DB 13,10,' RESULTAT : ','$'
.CODE
;*********************************************************************
; Procedure de lecture de nombres cod
es sur 4 octets. *
; Les operandes sont lues dans l'ordre des poids d
ecroissants. *
; La pile permet de les utiliser selon les poids croissants. *
;*********************************************************************
lect PROC
mov ah,01 ; code fonction de lecture d'un caractere.
mov cx,0 ; mise
a 0 du compteur.
boucle_lecture:
int 21h ; lecture
cmp al,0Dh ; a-t-on lu un retour-charriot ?
je rangement ; OUI => on range les valeurs lues.
push ax ; sinon on empile le caractere dans un mot.
inc cx ; on compte un ASCII de plus
jmp boucle_lecture
rangement: ; rangement du nombre lu.
add di,3 ; on se place en fin de zone de stockage.
boucle_rangement:
pop ax ; d
epiler un code ASCII
sub al,30h ; conversion en valeur d
ecimale
mov bl,al ; stockage dans BL
dec cx ; on d
ecr
emente CX pour comper l'octet d
epil
e
cmp cx,0 ; si CX =0 ...
je suite ; ... c'est fini
pop ax ; sinon on d
epile l'ASCII suivant.
sub al,30h ; conversion en valeur d
ecimale
push cx ; sauvegarde de CX (compteur d'ASCII lus )
mov cl,4 ; on compte 4 d
ecalages pour le ranger ...
shl ax,cl ; ... dans la partie droite de AL.
pop cx ; restitution de CX
9
or bl,al ; on accole le chiffre au pr
ec
edent
suite:
mov [di],bl ; sauvegarde en m
emoire par position d
ecroisante
cmp cx,0
je fin_lect
dec di ; on pointe sur la position pr
ec
edente
loop boucle_rangement ; jusqu'
a ce que CX soit nul
fin_lect:
ret
lect ENDP
DebutProgramme:
mov ax,@data
mov ds,ax
mov ah,9 ;la fonction de lecture n 9 exige
; des cha^
nes termin
ees par un '$'
mov dx, OFFSET chaine1 ; affichage du 1 message
int 21h
mov di,OFFSET num1
call lect
mov ah,9
mov dx, OFFSET chaine2 ; affichage du 2 message
int 21h
mov di,OFFSET num2
call lect
mov ah,9
mov dx, OFFSET chaine3 ; affichage du 3 message
int 21h
call Addition
mov ah,4Ch ; retour au DOS et ...
int 21h ; ... FIN DU PROGRAMME
Addition PROC
mov si,OFFSET num1 ; SI et DI pointent sur les 2 op
erandes
mov di,OFFSET num2
add si,4 ; on se place en queue des op
erandes
add di,4
mov cx,4
mov bx,OFFSET num3 ; BX pointe sur le r
esultat
add bx,4 ; et on se place sur l'octet de poids faible
clc ; mise
a z
ero du bit de retenue (CF)
boucle_addition:
dec si
dec di
dec bx
mov al,[di]
adc al,[si] ; addition avec prise en compte de la retenue
daa ; ajustement en codage BCD
mov [bx],al ; stockage de l'octet du r
esultat
loop boucle_addition
mov di,OFFSET num3 ; on pointe sur le r
esultat pour l'afficher
mov cx,4 ; le r
esultat est sur 4 octets
mov ah,02 ; code fonction d'
ecriture d'un caract
ere
affich: ; boucle d'affichage
10
mov dl,[di]
mov bl,dl
push cx ; sauvegarde du compteur d'octets affich
es
mov cl,4
shr dl,cl ; le demi-octet de gauche (poids forts) est
; decale
a droite
add dl,30h ; transformation du chiffre en son code ASCII
int 21h ; impression sur l'
ecran
mov dl,bl ; on r
ecup
ere l'octet initial
and dl,0Fh ; on masque le demi-octet de gauche d
ej
a trait
e
add dl,30h ; transformation num
erique -> ASCII
int 21h ; affichage
ecran
inc di
pop cx ; r
ecup
eration du nombre de tours de boucle
loop affich
FIN:
ret
Addition ENDP
END DebutProgramme
11
mov ax,dx ; DX doit contenir le num
ero de la ligne du pixel
mov dh,32 ; on multiplie par 32/20 ...
mul dh ; ... pour tenir compte du caract
ere rectangulaire ...
mov dx,0 ; ... de l'espace d'affichage
mov bx,20
div bx
mov cx,ax ; CX doit contenir le num
ero de la colonne du pixel
pop dx
pop ax
int 10h ; appel au BIOS pour allumer le point
a l'
ecran
pop cx ; r
ecup
eration du nombre de points restant a tracer
loop diag
attente:
mov ah,1
int 21h
fin:
mov ah,0 ; Retour au mode TEXTE
mov al,3
int 10h
mov ah,4Ch ; retour au DOS
int 21h
END
12
int 21h ; Affiche la chaine
a l'
ecran.
mov ah,4Ch
int 21h ; Retour au DOS.
END
;****************************************************************
;* Module dans un fichier s
epare *
;* ConcateneChaine *
;* Concat
ene deux cha^nes et range le *
;* r
esultat dans la variable globale *
;* ChaineFinale. *
;* ENTREES : DS:AX = pointeur vers la premiere cha^
ne *
;* DS:BX = pointeur vers la seconde cha^ne *
;* SORTIES : n
eant *
;* REGISTRES MODIFIES : AL, SI, DI, ES *
;****************************************************************
DOSSEG
.MODEL small
.DATA
GLOBAL ChaineFinale : BYTE
.CODE
GLOBAL ConcateneChaine
ConcateneChaine PROC
cld ; on fixe le sens de parcours
; des chaines
mov di,SEG ChaineFinale
mov es,di
mov di,OFFSET ChaineFinale ; ES:DI pointe sur le r
esultat
13
3.2 Structure d'une ligne
[Label:] [Instruction|Directive] [Op
erandes] [; commentaire]
14
{ SHORT force une expression a ^etre un pointeur de type proche.
{ on a de plus les operateurs arithmetiques: +, -, *, /
Exemples :
MOV val, 1234h
MOV AH, HIGH val
MOV AL, LOW val
mov AX, OFFSET var+((4*2)-3)
MOV BYTE PTR [BX],1
MOV AL, SIZE var
4 Les directives
Il y a 2 familles de directives selon le mode de segmentation (standard ou sim-
plie)
{ standard : pour de programmes de grande taille, developpes completement en
assembleur.( ca a existe : Systemes, CAO, SGBD)
{ simplie : Pour de petits modules independants, eventuellement associes a un
programme en langage evolue.
C'est ce dernier mode que nous utiliserons et que nous allons exposer.
{ DOSSEG : ordonne les segments selon la convention MICROSOFT et permet
la compatibilite avec MASM. Il faut l'utiliser quand on interface ASM avec
ADA ALSYS.
{ .MODEL selectionne le modele de memoire. Il y a 6 modeles dierents :
{ TINY : Code et donnees sont sur un m^eme segment de 64Ko. Les sauts
se font au sein de ce segment.
{ SMALL : code et donnees sont sur un segment chacun.
{ MEDIUM : Le code est sur plusieurs segments. les donnees sur un seul
segment.
{ COMPACT : Le code est sur 64Ko, les donnees sur plusieurs segments.
{ LARGE: Code et donnees sont multisegment, mais une structure de
donnee ( tableau par exemple) doit tenir sur un seul segment.
{ HUGE : Id. mais les structures de donnees sont multi-segment.
Nous travaillerons toujours en modele SMALL.
{ .STACK permet de dimensionner la pile. Cette pile est indispensable, et sauf cas
exceptionnel, elle doit toujours ^etre presente et susamment dimensionnee.
{ .DATA permet de denir les donnees simples ou complexes de l'application.
{ .CODE precede les instructions du programme qui se termine par la directive
.END
15
5 Declaration des donnees
5.1 Donnees initialisees
5.1.1 Donnees simples
DB (Data Byte) denit une donnee sur 1 octet, DW (Data Word) sur 1 mot ( 2
octets), DD (Data Double) un double mot, DQ pour 8 octets, DT pour 10 octets.
V1 DB 'A'
V2 DW 380
V3 DD 4BFCh
5.1.2 Tableaux
TAB DW 0,1,2,3,4
MATRICE DD 0,1,2
DD 3,4,5
DD 6,7,8
T DW 256 DUP(0)
ChaineVide DB 10 DUP(' ')
Les declarations de CH1 et CH2 ont le m^eme resultat. les valeurs 0Dh=13, 0Ah=10
correspondent aux codes ASCII commandant le saut a la ligne ( Carriage return et
Line Feed). Le $ est utilise pour acher a l'ecran la cha^ne a l'aide de la fonction 9
du DOS :
MOV AH,9
MOV DX, OFFSET CH4
INT 21h
REM :
BUF DW 10 DUP(0)
PTB DW BUF
initialise la variable PTB utilisee ici comme pointeur avec la valeur de BUF, qui est
l'adresse de BUF(0).
MOV AX, OFFSET BUF
MOV AX,[PTB]
16
5.2 Donnees non initialisees
La reservation de place en memoire se fait tres simplement sur le modele suivant:
BUF DB 10 DUP(?) r eserve 10 octets pour BUF.
5.3 Directive EQU
Elle permet d'aecter une valeur a un label ( qui ne pourra plus ^etre modiee)
reponse EQU 'O'
LongueurMax EQU 1000
Il faut s'obliger a utiliser le plus possible des labels lorsqu'on programme en as-
sembleur. Il est en eet plus facile de lire par exemple: CMP AL, REPONSE que:
CMP AL, 'O'
Des constantes peuvent ainsi en denir d'autres :
zone EQU 10
debut EQU (zone +2)
fin EQU (zone + 50
Cette directive est aussi tres utile pour declarer des messages a acher:
message EQU 'Donnez votre r
eponse (O/N) : '
Enn, cette directive permet de rendre plus lisible des manipulations par adres-
sage indirect:
.DATA
temp EQU [BP+2]
i EQU [BP+4]
j EQU [BP+6]
k EQU [BP+8]
.CODE
Somme3 PROC
PUSH BP
MOV BP,SP ; BP pointe sur le sommet de pile
SUB SP,2 ; SP pointe sur le mot pr
ec
edant
MOV AX,i
ADD AX,j
MOV temp,AX
MOV AX,k
ADD AX,temp
MOV SP,BP
POP BP
RET
Somme3 ENDP
Ce programme est certainement plus lisible que s'il presentait explicitement les
manipulations de la pile.
La directive = est identique a EQU, a ceci pres qu'elle permet de modier la
valeur d'initialisation en cours d'execution.
17
5.3.1 Calcul de la longueur d'un vecteur ou d'une cha^ne
Il est dicile et maladroit de compter le nombre de valeurs pour prexer l'opera-
teur DUP. Il est preferable d'utiliser un label. Tout identicateur, en informatique,
represente en general l'adresse de la valeur qu'il represente. Ainsi, un label corres-
pond a la valeur de l'adresse au sein du segment de la position qu'il occupe dans
le programme. Le m^eme r^ole est tenu par la variable $, qui represente l'adresse
courante dans le segment en cours d'assemblage. Dans l'exemple qui suit, $ repere
l'adresse du dernier mot de TABLE :
table DW 50 DUP(0)
FinTable Label Word
Longueur DW (FinTable-Table)
ou encore
table DW 50 DUP(0)
longueur EQU ($-table)
Toutes les 3 chargent le caractere 'E' dans AL. (le caractere d'adresse 0 est 'A').
Mais,
MOV AL, var
MOV AL, [VAR]
ont le m^eme eet, car le nom d'une variable repere l'adresse de sa valeur.
6.2 Adressage direct
Une position memoire est reperee par le nom d'une variable ou une combinaison
nom-constante.
Ce mode n'est pas tres souple, car l'adresse evaluee reste xe.
MOV AX,[100+12]
MOV BX,DS:[50]
18
6.3 Adressage indirect
On utilise a cet eet un registre contenant l'adresse de base, a laquelle on ajoute
un deplacement. Reprenons l'exemple precedent :
MOV BX, OFFSET var + 4
MOV AL, [BX]
cette fois-ci, nous balayons une variable chaine, terminee par le code ASCII nul, et
en sortant, nous placons le dernier caractere non nul dans AL.
Pour l'adressage indirect, on peut utiliser exclusivement les registres : BX, BP,
SI et DI.
Il existe 16 facons d'utiliser le mode indirect. La forme generale est :
[registre de base +/- registre index +/- deplacement]
[depl] [BX+DI] [SI + depl] [BP + DI + depl]
[BX] [BP + SI] [DI + depl]
[SI] [BP + DI] [BX + SI + depl]
[DI] [BP + depl] [BX + DI + depl]
[BX+SI] [BX+depl] [BP + SI + depl]
Les expressions utilisant BX pointent sur la RAM (c-a-d sur le segment courant de
celle-ci, correspondant generalement a la valeur de DS), celles utilisant BP pointent
sur la pile.
ici BX et [BX] ont des signications dierentes; BX correspond au contenu du
registre (qui peut ^etre une adresse), alors que [BX] est la valeur dont l'adresse est
dans BX.
Les expressions qui suivent sont equivalentes :
.DATA
chaine DB 'ABCDEF'
.CODE
MOV AX,@DATA
MOV DS,AX
19
.....
MOV SI,OFFSET chaine+4
MOV AL,[SI]
.......
MOV SI,4
MOV AL, [chaine + SI]
.......
MOV BX, OFFSET chaine
MOV AL,[BX + 4]
.......
MOV SI,4
MOV BX,OFFSET chaine
MOV AL,[BX + SI]
Cette aectation est sans ambigute non plus, car le nombre d'octets que permet
d'adresser [var] a ete specie a la declaration par la directive DB.
Il susbsite cependant des ambigutes , comme par exemple:
MOV [BX],1 : on ne peut decider ici si l'on range la valeur 1 dans un octet
ou dans un mot. Une telle instruction generera un message d'erreur de la part du
compilateur.
7.2 mecanismes de conversion
On leve les ambigutes a l'aide des operateurs BYTE PTR et WORD PTR
Ces operateurs permettent de traiter une variable selon un format dierent de celui
correspondant a sa declaration :
var DD ?
......
MOV WORD PTR [var], AX
MOV WORD PTR [var+2], DX
La variable var declaree comme double-mot est traitee ici comme si l'on avait en
fait deux mots independants.
7.3 Donnees signees et non signees
C'est au programmeur de faire la distinction, car il ne s'agit que d'une convention
et d'un codage particulier. Ainsi, 0FFFFh peut-il representer aussi bien 65 535 que
-1 !
20
La representation binaire des nombres entiers contenus dans un registre fournit
un nombre continu de valeurs : on passe de 65 535 a 0 en ajoutant 1, en represen-
tation non signee. Et, en representation signee, (dans laquelle le bit de poids fort
designe le signe , positif s'il est nul), 0FFFEh corespond a la valeur decimale -2.
Certaines instructions assembleur ne fonctionne pas de la m^eme maniere selon que
le bit de poids fort est considere comme un bit de signe ou un poids numerique.
7.3.1 Conversion d'un octet non signe en un mot
On force l'octet de poids fort a 0 :
MOV CL, 12
MOV AL, CL
MOV AH, 0 ; le mot de valeur 12 est dans AX
8 Instructions arithmetiques
8.1 ADD et SUB
Les additions et soustractions se font sur 8 ou 16 bits selon les operandes. Les
operations 32 bits ou plus doivent ^etre ecrites par le programmeur en eectuant le
transfert des retenues avec ADC (ADd with Cary) et SBB (SuB with Borrow).
ADD AX, BX
21
ADC DX, CX ; r
ealise DX:AX := DX:AX + CX:BX
de m^eme:
SUB AX,BX
SBB DX,CX ; r
ealise DX:AX := DX:AX - CX:BX
8.2 Incrementation/decrementation
Par INC et DEC.
ADD AX, 1 occupe 3 octets; INC AX n'en occupe qu'un et est plus rapide. De
m^eme, il vaut mieux ecrire deux fois de suite INC AX que ADD AX, 2.
8.3 Multiplication/division
La multiplication est une instruction dans laquelle l'accumulateur est un ope-
rande implicite.
MUL var : si var est une variable 8 bits, AL est operande implicite, et les 16 bits
du resultat sont ranges dans AX.
si var est une variable 16 bits, AX est operande implicite et les 32 bits du resultat
sont ranges dans le couple DX:AX
MOV AL, 25 ; AL operande implicite
MOV DH, 40 ; AX r
esultat implicite
MUL DH ; AX contient 1000
.......
MOV AX, 1000
MUL AX ; calcul de AX au carr
e. r
esultat dans DX:AX
22
Pour les donnees signees, il faut utiliser IDIV:
MOV AX, -545
CWD ; place -545 dans DX:AX
IDIV 100 ; quotient -5 dans AX, reste -45 dans DX
8.4 Negation
On utilise l'instruction NEG registre g
en
eral ou m
emoire
9 Operations logiques
L'instruction AND permet de masquer des valeurs :
MOV AL, var
AND AL, 0Fh ; ne retient que les 4 bits de poids faible de AL
l'instruction XOR permet d'inverser les bits d'un registre ou de les mettre plus
rapidement a zero que ne le fait un MOV :
XOR AX, AX ; remise
a 0 repide de AX
.....
MOV BL, 1011 0001b
NOT BL ; BL = 0100 1110
XOR BL, 0FFh ; BL reprend sa valeur initiale
10 Decalages et rotations
10.1 Logiques
SHL (Shift Left) eectue un decalage a gauche des bits. Le bit de poids fort se
retrouve dans CF et un 0 est introduit en bit de poids faible.
SHL AL, 1 Aucun autre op erande que 1 n'est accepte ! si l'on veut faire plu-
sieurs decalages successifs, il faut ecrire autant de fois SHL registre,1
Une facon plus elegante d'operer consiste a utiliser CL dans son r^ole de compteur:
MOV CL,4
SHL AX,CL ; effectue 4 d
ecalages de AX
Le decalage a gauche revient a faire une multiplication par 2 d'une valeur non signee.
SHR (Shift Right) opere de facon analogue a droite. Le resultat est la division
par 2 d'une valeur non signee.
23
10.2 Arithmetiques
SAR(Shift Arithmetic Right): le bit de poids fort est recopie. le bit 0 transfere
dans CF. Cette operation, qui preserve le bit de signe, permet de faire une division
par 2 de valeurs signees. La m^eme operation est realisee a gauche par SAL.
ROR(ROtation Right) eectue une permutation vers la droite. le bit de poids
faible se retrouve dans CF. Cette operation permet de recadrer des bits dans un
mot ou un octet. A gauche, l'instruction est ROL.
RCR(Rotation with Carry Right) permet une permutation avec prise en compte
de la retenue, utile par exemple dans le cas de decalages d'operandes etendus sur
plusieurs mots. L'operation symetrique est RCL.
15 0
SHL CF 0
15 0
SAR CF
15 0
ROR CF
15 0
CF
RCR
Toutes ces instructions n'operent que sur un bit a la fois, ou sur le nombre de
positions speciees par CL.
11 Sauts
11.1 Inconditionnels
JMP(jump) est l'equivalent d'un GOTO. Cette instruction permet de sauter a
une adresse representee sur 16 bits, au sein du segment de code donc. L'adresse
de saut est reperee par une etiquette. Dans les cas ou l'on cherche a economiser
du code, on peut utiliser JMP SHORT etiquette qui correspond a un saut de 127
octets. Hors contrainte de ce type, TASM optimise l'adresse selon le cas.
11.2 Conditionnels
Ils s'eectuent apres une comparaison CMP. CMP est identique a SUB, mais ne
produit pas de resultat; il possitionne seulement les
ags. Les sauts sont toujours
courts (127 octets), et il faut prendre garde que l'etiquette puisse eectivement
^etre atteinte.
24
INSTRUCTION Conditions de saut Indicateurs
pour valeurs non signees
JB/JNAE below/ not above or equal CF = 1
JAE/JNB above or equal/not below CF=0
JBE/JNA below or equal CF=1 et ZF=1
JA/JNBE above/not below or equal
JE/JZ equal/zero ZF=1
JNE/JNZ not equal/not zero ZF=0
pour valeurs signees
JL/JNGE less than/not greater than SF=NOT OF
JGE/JNL greater or equal/not less than SF=OF
JLE/JNG less or equal/not greater than ZF=1 ou SF=NOT OF
JG/JNLE greater than/not less or equal ZF=0 ou SF=OF
JP/JPE Parity even (paire) PF=1
JNP/JNPO Parity odd (impaire) PF=0
JS signe SF=1
JNS non signe SF=0
JC retenue CF=1
JNC pas de retenue CF=0
JO over
ow OF=1
JNO pas d'over
ow OF=0
Exemples :
MOV AH, 1
INT 21h ; lecture d'un octet rang
e dans AL
CMP AL, 'A'
JE suite ; Si l'octet lu est un 'A' on va
a suite, sinon ...
..... ; on poursuit en s
equence
suite:
.....
Dans l'exemple qui suit, on interprete de 2 facons dierentes l'octet de valeur 130.
En representation non signe, il correspond au code ASCII de 'e'. En representation
signee, il vaut -2. Dans les deux cas, le saut n'a lieu que parce que la valeur dans
AL est bien superieure (au sens de chaque convention de signe) a la constante 127
sur laquelle porte la comparaison:
MOV AL,130 MOV AL,130
CMP AL, 127 CMP AL,127
JA LettreAccentuee JG ValeurNegative
... ...
12 Boucles
12.1 Boucle POUR
On utilise l'instruction LOOP qui necessite l'emploi de CX comme compteur. A
chaque tour de boucle, CX est automatiquement decremente. Si, apres decremen-
tation, CX est nul, on sort de la boucle.
ATTENTION : si CX est nul au premier tour, il est decremente. sa valeur devient
65535, et on peut attendre un bon moment la sortie de boucle !
MOV CX, NbDeTours
25
BouclePour:
... ; corps de boucle
LOOP BouclePour
26
LODSW transfere un mot de DS:SI vers AX
CLD
MOV SI,OFFSET chaine
LODSB SI est incr
ement
e
...
STD
MOV SI, OFFSET cahine + LongueurChaine
LODSW SI est d
ecr
ement
e
27
si CX vaut 0 au depart, l'instruction n'est pas executee ( et c'est heureux !). REP
peut ^etre utilise avec l'ensemble des instructions de traitement de cha^ne, ainsi
qu'avec SCAS et CMPS.
REPE et REPNE sont aussi disponibles avec les signications respectives : re-
peter tant que egalite ou tant que pas egalite.
SI et DI sont modies apres l'acces en memoire, ce qui fait qu'en n d'echange,
on pointe sur une adresse posterieure (si on a fait CLD) au dernier element de
la cha^ne. Si on a tranfere des mots, on pointe sur une adresse posterieure de 2
positions, les adresses etant toujours comptees en octet.
13.2 Analyse de cha^ne
13.2.1 SCAS
eectue un balayage de la memoire pour chercher la presence ou l'absence d'un
octet ou la valeur d'un mot.
SCASB compare la valeur de l'octet dans AL avec celui situe en ES:DI; DI
est modie selon la valeur de DF. Avec SCASW , c'est le contenu de AX qui est
recherche.
Exemple: recherche du caractere 'a' dans un texte termine par l'ASCII nul
.DATA
texte DB 'texte d''essai',0
dim EQU ($-texte)
.CODE
MOV AX, @DATA
MOV DS, AX
MOV ES, AX
MOV DI, OFFSET texte ; DI pointe sur le d
ebut du texte
MOV AL, 'a'
MOV CX, dim ; CX contient le nombre de caracteres
a balayer.
CLD ; balayage dans l'ordre direct.
REPNE SCASB
JE trouve
JMP PasTrouve
trouve :
DEC DI ; on pointe maintenant sur 'a'
13.2.2 CMPS
Permet de comparer directement 2 cha^nes. CMPSB compare l'octet en DS:SI
avec celui en ES:DI et modie SI et DI simultanement selon DF. CMPSW agit de
m^eme au niveau de mots.
MOV SI, OFFSET tab1
MOV AX, SEG tab1
MOV DS, AX
28
JNE different
....
different:
DEC SI
DEC SI
DEC DI
DEC DI ; on pointe sur les 2
el
ements diff
erents.
14 Sous-programmes
14.1 principe
L'appel d'un sous-programme se fait par CALL label de sous-programme. Soit
un programme implante a l'adresse 1000 et une procedure a l'adresse 1100.
1000 MOV AL,1 ---> 1100 SHL AL, 1
1002 MOV BL,3 | 1102 ADD AL,BL
1004 CALL SP ------------ 1104 AND AL,7
1007 MOV AL,2 <------------- 1106 ADD AL,'0'
1009 INT 21h |-----1108 RET
29
14.2.2 par la pile
On utilise a cet eet une structure, c'est a dire l'equivalent d'un enregistrement
(RECORD). La syntaxe de declaration en est :
nom STRUC
champ1 type valeur
champ2 type valeur
...
nom ENDS
Avant l'appel, les parametres sont empiles par une succession de PUSH. Lors du CALL,
l'adresse de retour est rangee dans la pile. Elle est composee des deux registres CS
et IP.
On trouve donc dans la pile :
IP <- SP
CS
par4
par3
par2
par1 <- BP
L'acces a la pile se fait a partir de SP. Il vaut mieux ne pas modier la structure
de la pile en cours d'execution du sous-programme, aussi on ne la depile pas. Mais
on accede et on modie les valeurs qu'elle contient en utilisant des indirections avec
BP.
Il faut se souvenir ici que la pile est logee en haut de la memoire et que ses
adresses croissent a l'inverse des adresses de la memoire. L'adresse du sommet est
inferieure a celle de sa base ! Pour la manipuler comme on en a l'habitude et la
\voir" conformement au schema ci-dessus, on a l'habitude d'intervertir les reperes
que sont BP et SP avec la sequence :
PUSH BP pour sauvegarder la valeur du registre
MOV BP,SP BP contient la valeur de SP (adresses basses), ce qui nous permet
par la suite d' ecrire des expressions avec [BP+depl] ...
On doit egalement se souvenir que les adresses sont comptees en octet, alors que
la pile stocke des mots. Les adresses vont donc de 2 en 2.
L'adresse de par1 devient [BP+2], en adressage indirect, celle de par2 devient
[BP+4], etc ...
L'instruction RET depile en n d'execution l'adresse de retour. L'instruction
RET n permet de d epiler, outre l'adresse de retour les n/2 parametres qui la precede.
L'exemple suivant illustre ce qui vient d'^etre dit:
TOTO PROC NEAR
parametres STRUC
par1 DW ?
par2 DB ?
par3 DB ? ; ces deux parametres tiennent sur le meme mot dans la pile
par4 DW ?
parametres ENDS
30
...
mov AX, params.par1
mov BL, params.par2
mul BL
...
POP bp
ADD SP,2
RET 6 ; les parametres occupent 3 mots sur la pile
TOTO ENDP
dans cet exemple, les parametres ont ete depiles avant retour. Pour recuperer des
resultats, il convient de sauver leur valeur dans des registres au prealable.
15 Programmes multi-modules
Il est possible de faire de la compilation separee en assembleur. Le principal
probleme qui se pose est le partage des donnees et du code entre plusieurs modules.
Un exemple de realisation, propose en 3.1.3, illustre ce qui suit.
On distingue le probleme du partage des donnees separement de celui du code.
15.1 Partage des donnees
Les donnees, que ce soit en import ou en export, sont declarees avec la directive
GLOBAL et associees a leur type, dans tous les modules ou on les utilise. Cette
declaration regle uniquement le probleme de l'import-export. La declaration de
reservation de place en memoire se fait ensuite dans le module a qui l'on attribue
le r^ole de createur de cette donnee.
;Module du programme principal
...
.DATA
GLOBAL var1:WORD, var2:BYTE ; var1 est d
efini pour l'usage d'un autre module
var1 DW ? ; son implantation est d
ecidee ici
.CODE
GLOBAL P1 : NEAR, P2 : FAR ; La proc
edure P1, d
eclaree "proche", n
ecessite
; un d
eplacement au sein du segment
; Pour P2, on a besoin de CS:IP pour acc eder
; a
un autre segment
...
MOV [var1],BX
MOV AL,[var2]
...
CALL P1
CALL P2
END
-------------------------------------
; Module de P1
.DATA
GLOBAL var2:BYTE ; var2 est d
eclar
ee ici et sera utilisee dans
var2 DB ? ; le programme principal
.CODE
GLOBAL P1 ; cette declaration premet l'export de P1
P1 PROC NEAR ; D
eclaration de P1 dans le segment de code courant
...
31
RET
P1 ENDP
END
16 Commandes de TASM
16.1 compilation
la commande de compilation est : TASM [options] NomDeFichier
Si on utilise * comme nom de chiers, tous les chiers d'extension .ASM sont
compiles. L'option /zi permet de prendre en compte les donnees qui seront utilisees
par TURBO-DEBUGEUR.
16.2 edition des liens
On utilise la commande LINK. L'option /v permet l'utulisation de TURBO-
DEBUGEUR. La commande s'applique a l'ensemble des chiers objets (d'extension
.OBJ) qui compose le logiciel. On a deux solutions pour pr esenter ces arguments sur
la ligne de commande
{ LINK /v a+b+c permet de lier les modules-objet contenus dans les chiers
a.obj, b.obj et c.obj (un m^eme chier peut contenir plusieurs modules-objet).
{ LINK /v @f permet de lier les modules-objet contenus dans le chier f. Ce
dernier est un chier de texte qui contient une liste de type : a + b + . . . +
z. On utilise un tel chier en indirection des lors que le nombre de chiers
composant est eleve.
17 Problemes courants
Les erreurs les plus frequemment rencontrees sont :
{ l'oubli de revenir au DOS
{ l'oubli du RET dans une procedure. Le code continue de se derouler.
{ le fait que les operandes soient stockes a l'envers en memoire.
la valeur 4BA7h stockee en memoire correspond a la valeur A74Bh d'une
variable.
{ l'abscence du dimensionnement de la pile.
{ l'eacement de registres vitaux par une procedure.
32
{ des erreurs de sens de sauts conditionnels.
JA, JB, JAE et JBE traitent des donnees non signees.
JG,JL, JGE et JLE traitent des donnees signees.
le E traite l'egalite; ne pas confondre JA et JAE.
Bien dierencier aussi JC et JNC (problemes de logique)
{ boucles : valeur de CX; veiller a ne pas avoir CX nul en debut de boucle.
{ oubli de retour en arriere sur les cha^nes avec REP.
{ indicateur de direction inverse
{ oubli de preparer les segments de cha^ne (ES)
{ operations arithmetiques avec retenue. Penser a eacer CF avec CLC.
{ attention a la dierence entre compte d'octets et compte de mots.
{ confusion valeur/adresse
supposons que la variable var de valeur 1234h soit implantee a l'adresse 1000h.
MOV BX, OFFSET var charge 1000h dans BX
MOV AX, [BX] charge 1234h dans AX
MOV AX, [var] charge aussi 1234h dans AX
MOV [var], 5678h
MOV AX, var charge 5678h dans AX
33
S.I.O. Travaux pratiques page 34 Documentation de travaux pratiques
INSTRUCTIONS DU 8086 Lorsque la taille des arguments n’est pas indiquée, c’est que l’instruction ac-
cepte des arguments sur 8 ou 16 bits, à condition qu’ils soient de la même
taille.
Lorsqu’un des arguments peut être de plusieurs types, ces différents formats
sont regroupés entre accolades. Exemple: {r+m} signifie registre ou mémoire.
Instructions du 8086
S.I.O. Travaux pratiques page 35 Documentation de travaux pratiques
AAA AAS
Ajustement ASCII après addition: corrige le contenu de AL après une ad- Ajustement ASCII de AL après soustraction: corrige le contenu de AL
dition de deux nombres en BCD non compacté, pour le mettre au format BCD non après une addition de deux nombres exprimés en BCD non compacté, pour le
compacté. mettre au format BCD non compacté.
O D I T S Z A P C O D I T S Z A P C
? ? ? * ? * ? ? ? * ? *
ADC
AAD
Addition avec retenue: les deux opérandes et la retenue sont additionnés, et
Ajustement ASCII avant division: prépare le dividende ou le diviseur pour le résultat est placé dans le premier opérande.
effectuer une division entre deux nombres exprimés en BCD non compacté. Format:
• ADC r,*
O D I T S Z A P C • ADC m,{i+r}
? * * ? * ?
O D I T S Z A P C
* * * * * *
AAM
Instructions du 8086
S.I.O. Travaux pratiques page 36 Documentation de travaux pratiques
AND CLI
ET logique: Un ET logique est appliqué à chaque bit des opérandes, le résultat Mise à zéro de l’indicateur d’interruption.
est placé dans le premier opérande.
Format: CMC
• AND r,*
• AND m,r Inverse l’indicateur de retenue.
O D I T S Z A P C CMP
0 * * ? * 0
Compare les deux opérandes en soustrayant le deuxième opérande au pre-
mier. Celui-ci n’est pas modifié, mais les indicateurs peuvent être modifiés
Format:
CALL • CMP {r+m},*
• CMP m,{i+r}
Appel de procédure.
Les indicateurs ne sont pas modifiés. O D I T S Z A P C
Format: * * * * * *
• CALL label
• CALL m16
• CALL r16 CMPS,CMPSB,CMPSW
Instructions du 8086
S.I.O. Travaux pratiques page 37 Documentation de travaux pratiques
DAA DIV
Ajustement décimal de AL après addition: s’utilise après ADD pour reca- Division non signée: effectue la division du contenu de l’accumulateur par la
drer le résultat de l’addition de deux nombres BCD au format BCD compact valeur de l’argument.Si l’argument est sur 8 bits, AL est le dividende, le quo-
(un octet contient deux chiffres décimaux, chacun codé sur quatre bits). tient est placé dans AL et le reste dans AH, si l’argument est sur 16 bits, AX
est le dividende, le quotient est placé dans AX et le reste dans DX.
O D I T S Z A P C Format:
? * * * * * • DIV {m+r}
O D I T S Z A P C
? ? ? ? ? ?
DAS
O D I T S Z A P C HLT
? * * * * * Suspend l’exécution du programme et place le processeur dans l’état balte. Le
processeur ne repartira que par reset ou prise en compte d’une interruption.-
Dans ce dernier cas, on retrouve les contenus de CS et IP.
DEC
O D I T S Z A P C O D I T S Z A P C
* * * * * * ? ? ? ? ? ?
Instructions du 8086
S.I.O. Travaux pratiques page 38 Documentation de travaux pratiques
IMUL INT,INTO
Multiplication signée: multiplie le contenu de l’accumulateur par celui de Appel d’interruption: INTO est un appel conditionnel qui ne sera effectif
l’opérande.Si celui-ci est sur 8 bits, AL est multiplié et le résultat est placé que si l’indicateur O vaut 1.
dans AX, s’il est sur 16 bits, AX est multiplié et le résultat se trouve dans Les indicateurs T et S sont mis à zéro.
DX:AX (Poids forts dans DX). Format:
Format: • INT[O] i8
• IMUL {m+r}
IRET
O D I T S Z A P C
* ? ? ? ? * Retour d’interruption.
Dépile le registre des indicateurs.
IN Jcondition
Lecture de données sur un périphérique: transfère un octet ou un mot de- Saut si la condition est vérifiée.
puis le périphérique repéré par le deuxième opérande dans l’accumulateur. Les conditions valides sont composées des lettres suivantes:
Format: • A: above (au dessus)
• IN {AL,AX},i8 • B: below (en dessous)
• IN {AL,AX},DX • C: carry (retenue)
• E: equal (égal, pair)
O D I T S Z A P C • G: greater (plus grand)
* ? ? ? ? * • L: lesser (plus petit)
• N: not (non)
• O: overflow (dépassement de capacité, impair)
• P: parity (parité)
• S: signed (signé)
INC • Z: zero
Les conditions acceptées sont les suivantes:
Incrémente l’argument de un (voir DEC). JA,JAE,JB,JBE,JC,JE,JG,JGE,JL,JLE,JNA,JNAE,JNB,JNBE,JNC,JNE,JNG
,JNGE,JNL,JNLE,JO,JP,JPE,JS,JZ,JNO,JNP,JPO,JNS,JNZ.
O D I T S Z A P C Il existe encore une autre condition : JCXZ qui effectue le branchement si CX
* * * * * vaut 0.
L et G sont utilisés pour comparer des entiers signés, A et B pour des valeurs
non signées.
Les indicateurs ne sont pas modifiés.
Instructions du 8086
S.I.O. Travaux pratiques page 39 Documentation de travaux pratiques
Format: LOCK
• Jcondition r128.r128 est une étiquette ou une valeur correspondant à un dé-
placement dans le segment de code courant d’au plus 128 octets en amont Valide le préfixe de signal de verrouillage.
ou 127 octets en aval.Il est possible d’augmenter la longueur du saut en Les indicateurs ne sont pas modifiés.
plaçant la directive JUMPS (annulée par NOJUMPS) dans le texte source
avant l’instruction de saut. LODS,LODSB,LODSW
JMP Charge un caractère dans l’accumulateur: charge dans AL (donnée sur 8
bits) ou AX (donnée sur 16 bits) la valeur pointée par DS:SI.
Saut inconditionnel. LODS peut être préfixée par REP, ce qui a peu d’intérêt.
Les indicateurs ne sont pas modifiés. Les indicateurs ne sont pas modifiés.
Format: Format:
• JMP r128 • LODSB et LODSW n’ont pas d’arguments.
• JMP r • LODS m
• JMP m
• JMP ptr 16:16 LOOP, LOOPcondition
LAHF Boucle: décrémente CX; si le résultat est différent de zéro, opère un branche-
ment à l’adresse spécifiée en argument (voir Jcondition pour les formats).
Charge les indicateurs dans AH. LOOPcondition effectue le branchement tant que la condition est vérifiée et
Les indicateurs ne sont pas modifiés. que CX est différent de zéro. Les seules conditions valides sont LOOPE (ou
LOOPZ), vrai quand l’indicateur Z est à un, et sa négation LOOPNE
LEA (ou LOOPNZ).
Les indicateurs ne sont pas modifiés.
Charge une valeur de déplacement d’adresse: calcul l’adresse (offset) du
second opérande et la place dans le premier. MOV
Les indicateurs ne sont pas modifiés.
Copie de données: recopie dans le premier opérande la valeur représentée par
LDS,LES le deuxième opérande.
Les indicateurs ne sont pas modifiés.
Charge un pointeur: Le premier mot (OFFSET) adressé par le deuxième Format:
opérande est placé dans le premier opérande, le second (SEGMENT) est placé • MOV r,*
dans DS (LDS) ou ES (LES). • MOV m,{r+i}
Les indicateurs ne sont pas modifiés. • MOV segreg,{r+m}
• MOV {r+m},segreg
Instructions du 8086
S.I.O. Travaux pratiques page 40 Documentation de travaux pratiques
MOVS,MOVSB,MOVSW NOT
Copie de données entre chaînes: copie l’octet(MOVSB) ou le mot (MO- Négation logique: l’opérande est remplacé par son complément à un.
VSW) repéré par DS:SI dans ES:DI puis incrémente (CLD) ou décrémente Les indicateurs ne sont pas modifiés.
(STD) SI et DI. Format:
Cette instruction peut être préfixée par REP. • NOT {r+m}
Les indicateurs ne sont pas modifiés.
Format: OR
• MOVSB et MOVSW n’ont pas de paramètres.
• MOVS: m,m Ou logique: effectue un ou logique sur chaque bit des opérandes et place le
résultat dans le premier opérande.
MUL Format:
• OR {r+m},{imm+r}
Multiplication non signée: voir IMUL. • OR r,m
O D I T S Z A P C O D I T S Z A P C
* ? ? ? ? * 0 * * ? * 0
NEG OUT
Négation par complément à deux: l’opérande est remplacé par son complé- Ecriture sur un périphérique: transfère une donnée depuis le premier opé-
ment à deux. L’indicateur de retenue est mis à un, sauf si l’opérande vaut 0, rande vers le périphérique repéré par le deuxième opérande.
auquel cas l’indicateur de retenue est mis à 0. Les indicateurs ne sont pas modifiés.
Format: Format:
• NEG {r+m} • OUT {imm+DX},{AL+AX}
O D I T S Z A P C
* * * * * * POP
Instructions du 8086
S.I.O. Travaux pratiques page 41 Documentation de travaux pratiques
POPF REP,REPE,REPZ,REPNE,REPNZ
Dépile le registre d’indicateurs: prend la valeur située en sommet de pile et Répétition d’opérations de manipulations de chaînes.
la place dans le registre d’indicateurs. Ces instructions sont des préfixes permettant la répétition des instructions de
Tous les indicateurs sont susceptibles d’être modifiés. chaînes.
REP décrémente CX puis répète l’instruction si CX est différent de zéro.
PUSH REPE (=REPZ) et REPNE (=REPNZ) ne préfixent que les instructions des fa-
milles SCAS et CMPS; REPE (répéter tant que égal) arrête l’itération si l’in-
Empile l’opérande: décrémente SP de 2, puis place la valeur en sommet de dicateur Z vaut 0 (détection d’une inégalité), REPNE (répéter tant que non
pile. égal) est la condition opposée.
Les indicateurs ne sont pas modifiés. L’indicateur Z peut être modifié.
Format:
• PUSH {r+m}
PUSHF RET
Empile le registre des indicateurs, qui ne sont pas modifiés. Retour d’une procédure: IP et CS (retour long) sont dépilés.
Si RET est suivi d’une valeur sur 16 bits, elle représente le nombre d’octets à
RCL,RCR,ROL,ROR enlever de la pile avant d’effectuer le retour de procédure (paramètres d’entrée
de la procédure).
Rotation d’un octet ou d’un mot d’une ou CL positions. Les indicateurs ne sont pas modifiés.
RCL: rotation vers la gauche en tenant compte de la retenue. A chaque étape
de la rotation, la retenue est placée dans le bit de poids faible du premier opé-
rande, le bit de poids fort de cet opérande est placé dans la retenue.
ROL: rotation vers la gauche sans tenir compte de la retenue. A chaque étape
de la rotation, la retenue prend la valeur du bit de poids fort du premier opé- SAHF
rande avant la rotation.
RCR et ROR sont les rotations vers la droite correspondantes. Sauvegarde AH dans le registre des indicateurs (seulement les indicateurs
C et O peuvent être modifiés. S,Z,A,P,C).
Format: AH doit contenir SZ*A*P*C dans cet ordre.
• {RCL+RCR+ROL+ROR} {r+m},{1+CL}
Instructions du 8086
S.I.O. Travaux pratiques page 42 Documentation de travaux pratiques
SAL,SAR,SHL,SHR SCAS,SCASB,SCASW
STD
Instructions du 8086
S.I.O. Travaux pratiques page 43 Documentation de travaux pratiques
SUB XLAT,XLATB
Soustraction: soustrait le deuxième opérande au premier et place le résultat Table de correspondance: avant d’appeler XLAT, AL doit contenir un indice
dans le premier. de tableau, BX l’adresse de base du tableau. Au retour, AL contient la valeur
Format: voir ADC. de la case correspondante du tableau.
Les indicateurs ne sont pas modifiés.
O D I T S Z A P C
Format:
* * * * * * • XLAT m8
• XLATB
XOR
TEST
Ou exclusif.
Comparaison: même action que AND, mais le résultat n’est pas gardé. Format: voir OR.
Format: voir AND.
A O D I T S Z A P C
O D I T S Z P C
0 * * ? * 0 0 * * ? * 0
WAIT
Arrêt du processeur jusqu’à ce que la broche BUSY# soit inactive. Cette bro-
che est gérée par le coprocesseur.
Les indicateurs ne sont pas modifiés.
XCHG
Instructions du 8086
S.I.O. Travaux pratiques Documentation de travaux pratiques
Sortie: Aucune.
Interruption 10h, fonction 0Bh, service 01h Interruption 10h, fonction 0Fh
Sélection de la palette de couleurs. Lecture du mode vidéo.
Entrée: AH=0Bh Entrée: AH=0Fh
BH=1
BL=Numéro de la palette. Sortie: AL=Mode vidéo (voir fonction 0 de l’interruption 10h).
AH=Nombre de caractères par ligne.
Sortie: Aucune. BH=Numéro de la page écran.
Sortie: AL=Couleur.
Remarque: La chaîne doit être terminée par un $. Sortie: AL=FFh, date erronée.
Sortie: AL=Version.
AH=Sous-version. Interruption 21h, fonction 3Bh
Changer de répertoire.
Interruption 21h, fonction 31h Entrée: AH=3Bh
DS:DX=Adresse du nom du sous-répertoire(ASCIIZ).
Terminer le programme mais laisser résident.
Entrée: AH=31h Sortie: CF=0 changement réussi.
AL=Code de fin. CF=1, alors AX=3 (chemin non trouvé).
DX=Nombre de paragraphes à réserver (1 paragraphe=16 octets).
Sortie: Aucune.
Sortie: CF=0 création réussie; AX=Handle du fichier. Interruption 21h, fonction 3Fh
CF=1 problème:
AX=3 Chemin non trouvé. Lire fichier.
AX=4 Trop de fichiers ouverts. Entrée: AH=3Fh
AX=5 Accès refusé. BX=Handle du fichier (Handle du clavier=0).
CX=Nombre d’octets à lire.
DS:DX=Adresse du buffer.
Interruption 21h, fonction 3Dh Sortie: CF=0 tout va bien, AX=nombre d’octets lus.
CF=1
Ouvrir fichier. AX=5 accès interdit.
Entrée: AH=3Dh AX=6 handle non autorisé ou fichier non ouvert.
AL=Mode d’accès.Principalement:
Bits 0-2:
000=Lecture seulement. Interruption 21h, fonction 40h
001=Ecriture seulement.
010=Lecture/écriture. Ecrire dans un fichier.
DS:DX=Adresse du nom du fichier. Entrée: AH=40h
BX=Handle du fichier (Handle de l’écran=1).
Sortie: CF=0 ouverture réussie; AX=Handle du fichier. CX=Nombre d’octets à écrire.
CF=1 problème. DS:DX=Adresse du buffer.
AX=2 fichier non trouvé.
AX=3 chemin non trouvé. Sortie: CF=0 tout s’est bien passé, AX=nombre d’octets écrits.
AX=4 trop de fichiers ouverts. CF=1
AX=5 accès refusé. AX=5 accès refusé.
AX=6 handle non autorisé ou fichier non ouvert.
Sortie: CF=0 tout s’est bien passé, DS:SI contient la spécification du chemin. Sortie: CF=0 tout s’est bien passé.
CF=1 erreur, AX=15 (périphérique inconnu). CF=1 erreur:
AX=7 bloc de contrôle de la mémoire détruit.
AX=8 pas assez de mémoire.
BX=Nombre de paragraphes encore disponibles.
Interruption 21h, fonction 48h
Réserver mémoire RAM.
Entrée: AH=48h Interruption 21h, fonction 4Ch
BX=Nombre de paragraphes.
Terminer un programme.
Sortie: CF=0 réservation réussie, AX:0=adresse de la zone. Entrée: AH=4Ch
CF=1 alors: AL=Code de fin.
AX=7 bloc de contrôle de la mémoire détruit.
AX=8 pas assez de mémoire. Sortie: Aucune.
BX=Nombre de paragraphes encore disponibles.
Sortie: CF=0 tout s’est bien passé, la DTA a été mise à jour.
CF=1 erreur:
AX=2 chemin non trouvé.
AX=18 pas de fichier correspondant au schéma.
Sortie: CF=0 tout s’est bien passé, la DTA a été mise à jour.
CF=1 erreur AX=18 (pas de fichier correspondant au schéma).