Affichage d'une variable en assembleur [Résolu/Fermé]

Signaler
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
-
nicocorico
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
-
Bonjour, je suis un débutant en assembleur, je programme avec le TASM 5.0

Je voudrais bien savoir comment afficher une variable entière ..
j'ai essayé avec la fonction 09h, mais ceci n'a pas marché, rien est affiché lors de l'exécution ..
Merci d'avance



10 réponses

Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Peux-tu mettre ton code, pour être sûr que tout est bien paramétré ?
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
Wé, apparement, ce n'e'st point un problème de code, mais de conversion
On m'a dit qu'il faut convertir le nombre de l Héxa en ASCII ..??
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Ha oui bien sûr, les fonctions dos n'affiche que des chaines de caractères ! Donc il faut que tu réserve une chaine et que tu la remplisse...
Pour ce faire, il te suffit de diviser successivement la valeur par 10, puis d'ajouter 48, le code ascii pour '0', au reste de la division contenu dans EDX. Tu obtiendras ainsi les caractères de droite à gauche...
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
exusez moi, mais je suis super nul pour l assembleur, voici mon code source :

; segment des variable et données
data segment

a dw 11h
b dw 18h
c dw ?
tab dw 2 dup (?)


data ends




code segment


assume cs : code, ds : data

begin:

mov ax,data
mov ds, ax

; additioner A et B, le mettre dans le AX, ensuite le transmettre dans C
mov dx, a
add dx, b
mov c, dx

; affichage du résultat stocké dans la variable C
mov si,0

boucle1:
sub dx, 10
INC si
cmp dx, 10
JL suite
JMP boucle1

suite:
mov tab[1], si
mov tab[0], dx

mov dx, offset tab[0]
mov ah, 09h
int 21

mov dx, offset tab[1]
mov ah, 09h
int 21

; interruption du programme DOS
mov ah, 4ch
int 21

code ends
end begin
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Pas la peine de t'excuser : je te renvoie à ma devise !
Alors voici l'idée générale, avec divisions multiples pour extraire les caractères en base 10. Je ne sais pas si ça va fonctionner directement dans ton assembleur et je ne peux pas tester, alors il y aura peut-être quelques corrections à apporter...
Hésite pas si tu as des questions !
data segment     
  a dw 11h     
  b dw 18h     
  c dw ?     
  tab db 06 dup (?)     

data ends     
code segment     
assume cs : code, ds : data     

begin:     

  mov   ax,data     
  mov   ds, ax     

  mov   AX, a     
  add   AX, b  ; je préfère AX ici car il est le divisé     
  mov   c, AX  ; et DX sert aussi dans la division     

  Mov   SI,offset tab[05]     
  Mov   Byte ptr [SI],'$'     
  Mov   CX,10;     

@Bcl:     
  Dec   SI   // On commence par décrémenter car on a déjà mis '$' 
  Xor   DX,DX    // Xor plutôt que 'Mov DX,0' car plus compact     
  Div   CX       // Divise AX par 10, DX contient le reste     
  Add   DL,48    // Ajoute '0' en ascii     
  Mov   [SI],DL  // Ajoute le caractère     
  And   AX,AX    // Teste si AX vaut 0     
  Jnz   @Bcl    

  // En sortie de boucle, SI pointe sur le 1er caractère du nombre     

  Mov   DX,SI     
  Mov   AH,09h     
  Int   21     

  ; interruption du programme DOS     
  mov   ah, 4ch     
  int   21     

code ends     
end begin

Le chêne aussi était un gland, avant d'être un chêne
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
Merci pour cette réponse, mais est ce que tu peux m'expliquer quelques trucs ...


PS : j'ai remarqué que dans ton programme, tu utilise la syntaxe du C pour les commentaire =p

voilà le code
data segment
a dw 11h
b dw 18h
c dw ?
tab db 06 dup (?)

data ends

code segment

assume cs : code, ds : data

begin:

mov ax,data
mov ds, ax

mov AX, a
add AX, b ; je préfère AX ici car il est le divisé
mov c, AX ; et DX sert aussi dans la division

Mov SI,offset tab[05]
Mov Byte ptr [SI],'$'
Mov CX,10;
;********************************************************
;en fait,ça fait quoi au just, est ce que ça a une relation avec tab que j'ai ;déclaré, et qui n'est pas utilisé (à directement à mon petit savoir)
;********************************************************
@Bcl:
Dec SI ; On commence par décrémenter car on a déjà mis '$'
Xor DX,DX ; Xor plutôt que 'Mov DX,0' car plus compact
Div CX ; Divise AX par 10, DX contient le reste
Add DL,48 ; Ajoute '0' en ascii
Mov [SI],DL ;Ajoute le caractère
And AX,AX ; Teste si AX vaut 0
Jnz @Bcl

; En sortie de boucle, SI pointe sur le 1er caractère du nombre

Mov DX,SI
Mov AH,09h
Int 21
;*********************************************************
;est ce que c'est vraiment le tableau qui va étre affiché là? oubien SI ???
;********************************************************

; interruption du programme DOS
mov ah, 4ch
int 21

code ends
end begin
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Ha oui, la syntaxe des commentaires c'est une erreur de ma part, c'est aussi une syntaxe delphi en fait, l'habitude tenace est revenue au galop !

Quand au fonctionnement avec SI, il faut comprendre que toute portion mémoire est accédée en fonction de son adresse, donc quand tu écris
'Mov Tab[0], dx' il sera transformé en 'Mov [adresse de Tab[0]], DX'...
Donc si tu charge l'adresse dans un registre, SI en l'occurence, tu peux accéder à Tab de la même manière avec 'Mov [SI],DX'.
Dans l'instruction 'Mov SI, Offset Tab[05]' on charge l'adresse du dernier emplacement du tableau 'Tab' dans 'SI';
Ensuite on place le caractère de fin de chaine avec 'Mov byte ptr [SI] ,'$'' puis, en décrémentant, les caractères constituants le nombre.
Cette opération se fait dans le sens inverse car le reste de la division donne le caractère le plus faible, ça évite donc de devoir les inverser ensuite...

Puis pour l'affichage on met la valeur de 'SI' dans DX, c'est à dire l'offset du début de la chaine. ça revient au même que 'Mov DX, offset Tab[0] ' à ceci près qu'on ne sais pas combien il y a de caractères pour représenter le nombre, donc on utilise 'SI' car il pointe sur le dernier caractère sorti, donc le 1er caractère à afficher...
L'int21-09h attend bien l'adresse de la chaine dans 'DX', et non une valeur à afficher.

Tab fait 6 octets car en 16 bits on aura au maximum 5 caractères (65535 max) plus le caractère terminal '$'.
Ultime précision, avant toute division il faut mettre 'DX' à zéro, car il est censé être le reste d'une potentielle division précédente, et si sa valeur dépasse celle du diviseur, le processeur génèrera une erreur au même titre qu'une division par zéro.

Le chêne aussi était un gland, avant d'être un chêne
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
Bon, just une question, on m'a parlé d'une fonction qui marche avec l'int 21h, c'est la fonction 02h qui affiche la valeur d'une variable en ASCII, i.e sans conversion ... j'ai pas su l'utiliser, est ce qu'elle existe vraiment? si c'est le cas, ce n'est pas la peine d'utiliser un tableau, j'ai pensé à faire la procedure suivante:

mov si, 0
boucle:
sub ax, 10
inc si
cmp ax, 10
jl suite
jmp boucle

suite:
.
.
.



et ensuite, il s'agit d'afficher les deux : ax, qui contient le reste de la division sur 10; et si, le quotient !
nicocorico
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Oui, la fonction 02h existe bien, mais elle ne permet d'afficher qu'un seul caractère, statut quo donc...
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
voivi ce que j'ai pu faire, et ça a marché lors de l'execution
data segment 

a db 15 
b db 16 
chaine  db 3 dup ('$') 

data ends 

code segment 

assume cs: code, ds: data 

begin: 

mov ax, data 
mov ds, ax 

mov ah, a 
add ah, b 

mov al, 0 

boucle: 
sub ah, 10 
inc al 
cmp ah, 10 
jl suite 
jmp boucle 

suite: 
add al, 48 
add ah, 48 
mov chaine[0], al 
mov chaine[1], ah 

mov dx, offset chaine 
mov ah, 09h 
int 21h 

mov ah, 4ch 
int 21h 

code ends 
end begin


Pourrais tu me donner ton avis ?
To really understand what's Death, we should live it
par ce que c'est pas tous les jours qu'on a le droit à un nouveau départ
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Hé bien ton programme doit sans doute fonctionner, mais à mon sens il souffre d'un défault de conception, dans le fait de 'compter le nombre de fois que AH contient 10' plutôt que diviser par 10 pour le calculer directement...
J'ai l'impression que la division te rebutes un peu ! c'est normal, à mes débuts je la trouvais également un peu compliquée !
Mais dans ce cas précis, elle remplaçerait avantageusement la boucle tout en étant beaucoup plus rapide...
Sinon, et puisque tu as l'air de te contenter de 2 chiffres, tu peux aussi employer une instruction moins courante, nommée 'AAM';
Cette instruction divise le contenu de AL par 10 en mettant le chiffre de poids fort dans AH et le faible dans AL :
  Mov  AL, a
  Add  AL, b
  AAM           ; AH contient la dizaine et AL le reste
  Add  AX,3030h ; Ajoute 48 (30h) sur les 2 en même temps
  mov chaine[0], al
  mov chaine[1], ah
nicocorico
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Erreur de ma part, il faut inverser AL et AH :
  mov chaine[0], AH
  mov chaine[1], AL
chiti_
Messages postés
1045
Date d'inscription
jeudi 16 août 2007
Statut
Membre
Dernière intervention
23 novembre 2014
129
Merci infiniment ! j'ai beaucoup appris sur ce sujet, merci encore et bon courage :)
nicocorico
Messages postés
815
Date d'inscription
dimanche 19 juin 2011
Statut
Membre
Dernière intervention
3 juillet 2018
123
Plaisir partagé ! Bonne continuation...