Le

Les bases en x86-64 Assembly

1 exercice

À propos de Les bases

Commentaires

Le parcours x86-64 d'Exercism utilise NASM (The Netwide Assembler) comme assembleur. Dans NASM, les commentaires sont précédés d'un point-virgule (;).

Les commentaires peuvent être placés n'importe où dans le programme et tout ce qui suit un ; est ignoré par l'assembleur.

Constantes

Une constante définie au moment de l'assemblage peut être déclarée dans NASM avec equ. Par exemple, ceci définit une constante nommée UNIVERSE avec la valeur 42 :

UNIVERSE equ 42

Les constantes sont évaluées une seule fois, au moment de leur définition, et ne peuvent pas être redéfinies par la suite.

Registres généraux (GPR)

En assembleur, au lieu de variables, on utilise généralement des registres pour stocker des valeurs. Un registre du processeur est une petite zone de mémoire rapide à l'intérieur du processeur d'un ordinateur. La plupart des calculs sont effectués dans les registres du processeur.

Certains de ces registres servent à divers calculs et sont appelés registres généraux (GPR). D'autres ont des usages spéciaux ou dédiés.

En x86-64, il y a 16 registres généraux (GPR) de 64 bits, auxquels on peut aussi accéder en 32 bits, 16 bits ou 8 bits. Les GPR sont décrits ci-dessous, où n dans rn va de 8 à 15 : r8, r9, r10, r11, r12, r13, r14 et r15.

64 bits 32 bits 16 bits 8 bits
rax eax ax ah/al
rbx ebx bx bh/bl
rcx ecx cx ch/cl
rdx edx dx dh/dl
rsi esi si sil
rdi edi di dil
rbp ebp bp bpl
rsp esp sp spl
rn rnd rnw rnb

Lorsqu'on utilise moins de 64 bits, les bits auxquels on accède proviennent généralement de la partie inférieure du registre. L'exception à cette règle concerne ah, bh, ch et dh, qui accèdent aux 8 bits supérieurs de la partie 16 bits du registre.

Illustration de la manière dont on accède aux bits du registre rax :

+--------+---------------------------------------+
| 64-bit |                  rax                  |
+--------+-------------------+-------------------+
| 32-bit |                   |        eax        |
+--------+-------------------+---------+---------+
| 16-bit |                             |    ax   |
+--------+-----------------------------+----+----+
| 8-bit  |                             | ah | al |
+--------+-----------------------------+----+----+

Certains de ces registres doivent être préservés lors des appels de fonction : rbp, rsp, rbx, r12, r13, r14 et r15. Ne pas les préserver peut entraîner une erreur ou un comportement indéfini.

Les autres ne sont pas préservés et peuvent être utilisés librement : rax, rcx, rdx, rdi, rsi, r8, r9, r10 et r11.

Note

Les registres sont généralement préservés sur la pile à l'aide d'une instruction push. Ils sont ensuite restaurés avant la fin de la fonction à l'aide d'une instruction pop.

Instructions

Les instructions sont des éléments de calcul qu'un processeur peut effectuer. Elles ont généralement la forme suivante :

name destination, source

Ainsi, le nom de l'instruction est placé en premier, puis au moins un espace, suivi de l'opérande de destination, d'une virgule (,) et enfin d'un opérande source. L'opérande source n'est généralement pas modifié par une instruction, contrairement à l'opérande de destination.

Les deux opérandes doivent avoir la même taille, sauf indication contraire. Par exemple, l'opérande de destination doit aussi faire 16 bits si l'opérande source fait 16 bits.

Par exemple, pour stocker une valeur dans un registre, on peut utiliser l'instruction mov :

mov rax, rdx  ; rax = rdx
              ; mov is the name, rax is the destination operand and rdx is the source operand

L'extrait ci-dessus copie le contenu des 64 bits de rdx, l'opérande source, vers les 64 bits de rax, qui est l'opérande de destination de l'instruction.

Il est possible d'utiliser des nombres entiers constants comme opérandes source (mais pas comme opérandes de destination) dans la plupart des instructions :

mov rcx, 42 ; rcx = 42
            ; rcx is the destination operand and 42 is the source operand

À noter qu'écrire dans un registre 32 bits efface aussi les bits supérieurs, donc mov eax, 42 est identique à mov rax, 42. Ce n'est pas le cas pour les registres 16 bits et 8 bits.

Pour les opérations arithmétiques d'addition, de soustraction et de multiplication, on peut utiliser les instructions add, sub et imul :

add rax, rsi ; rax = rax + rsi
imul rax, rdi ; rax = rax * rdi
sub rax, r8 ; rax = rax - r8

Fonctions

Les instructions sont organisées en fonctions. Toutes les fonctions sont placées dans la section .text du fichier source.

La déclaration d'une fonction comprend :

  1. Une étiquette portant le nom de la fonction, suivie d'un :.
  2. Les instructions qui définissent la fonction.
  3. L'instruction de retour, ret.

Il existe des conventions spécifiques pour la façon dont les arguments sont passés et renvoyés par une fonction. Les deux principales conventions d'appel sont System V AMD64 ABI et Microsoft x64.

Ce parcours utilise la convention d'appel System V AMD64 ABI et les six premiers arguments entiers sont passés à une fonction dans des registres. Ils sont passés dans l'ordre suivant : rdi, rsi, rdx, rcx, r8 et r9.

Une valeur entière est renvoyée par la fonction dans le registre rax.

Pour appeler une fonction, on utilise l'instruction call. Une fonction peut être appelée n'importe où dans le même fichier source. Pour rendre une fonction visible aux autres fichiers source, il faut utiliser la directive global.

Par exemple, ceci déclare une fonction sum :

section .text ; functions are placed here

global sum ; sum is visible to other source files

sum:
    ; first argument is passed in rdi
    ; second argument is passed in rsi
    ; return value is placed in rax

    mov rax, rdi ; rax is now equal to rdi
    add rax, rsi ; rax = rax + rsi

    ret ; function return

Et ceci appelle notre fonction sum avec les arguments 3 et 5 :

mov rdi, 3  ; First argument in rdi
mov rsi, 5  ; Second argument in rsi
call sum

; The rax register now contains the value 8 (3 + 5), after sum returns
Modifie via GitHub Le lien s'ouvre dans une nouvelle fenêtre ou un nouvel onglet

Apprends Les bases