Mémento architecture et assembleur MIPS
Adapté de : https://minnie.tuhs.org/CompArch/Resources/mips_quick_tutorial.html
Types de données et Constantes littérales
Types de données
- Les instructions sont toutes sur 4 octets.
- Les données sont accessibles sous 3 formes : byte (1 octet), halfword (2 octets), word (4 octets).
- Un caractère utilise 1 octet de mémoire.
- Un entier utilise 4 octets de mémoire.
Constantes littérales
- Les nombres sont utilisés tel que, c.-à-d. 42, ou aussi 0xbabe.
- Les caractères sont entourés par des simples quote, c.-à-d. 'b'.
- Les chaînes de caractères sont entourées par des doubles quotes, c.-à-d. "Une chaîne".
- Les noms de label sont liés au charset de l'environnement JAVA et peuvent donc être en UTF8 ou autre, c.-à-d. Матрёшка ou Matriochka.
Structure d'un programme
Commentaires et Indentations
Les commentaires peuvent apparaître dans toutes les parties d'un fichier MIPS.
Un commentaire commence par le caractère « # » et s'étend jusqu'à la fin de la ligne.
L'indentation est libre pour le confort de lecture.
Labels
Les labels sont utilisés par l'assembleur pour identifier des adresses mémoires statiques :
- un label est identifié par un nom suivi du caractère « : »,
- dans les déclarations de données, les labels sont des adresses mémoire de variables,
- dans le code du programme, les labels sont des adresses de saut dans le code,
- dans tous les cas, les valeurs de ces adresses sont calculées automatiquement par le programme d'assemblage.
Déclarations de données
Une section de déclaration déclare des noms de variables, initialise leur valeur, et réalise leur allocation mémoire dans la zone des données statiques.
La section est identifiée par la directive :
Le format d'une déclaration de variable est :
Par l'exemple :
Avec .word et .half, les adresses sont automatiquement alignées sur des mots de 4 octets ou 2 octets. Dans tous les cas, on peut forcer l'alignement d'une variable sur une frontière de 2n octets avec la directive .align n avant la déclaration de variable :
Code du programme
Le code du programme est identifiée par la directive :
Le code contient des instructions et des labels pour les sauts.
Le point d'entrée pour l'exécution est donnée par le label « main: ».
La terminaison de l'exécution est réalisée en fin de fichier ou utilise l'appel système exit (cf. plus loin).
Exemple de fichier MIPS
Registres
On dispose de 32 registres pour l'usage général (+ 32 registres pour les instructions flottantes).
Dans l'assembleur, les noms de registre commencent par $ avec deux formes au choix :
- utilisant le numéro du registre, c.-à-d. de $0 à $31,
- utilisant un nom conventionnel, p.ex. $sp ou $t1,
Deux registres spéciaux, nommément Lo et Hi, sont utilisés pour les résultats de multiplications ou de divisions. Ils ne sont accessibles qu'avec les instructions spéciales mfhi (Move From Hi) et mflo (Move From Lo).
La pile à la « tête en bas » : l'adresse de sommet de pile décroît quand la pile grandit.
Voici les registres dont on dispose :
Numéro | Nom | Sous-titre | Description |
---|---|---|---|
0 | zero | zéro | toujours la valeur 0 |
1 | at | Assembler Temporary |
réservé par l'assembleur pour les pseudo-instructions |
2-3 | v0-v1 | Values | Résultats de fonctions ou évaluations d'expressions |
4-7 | a0-a3 | Arguments | Les 4 premiers arguments d'une fonction
Valeur non préservée par un appel de fonction |
8-15 24-25 |
t0-t7 t8-t9 |
Temporaries | Registre de travail
Valeur non préservée par un appel de fonction |
16-23 | s0-s7 | Saved values | Registres de travail
Valeur préservée par un appel de fonction |
26-27 | k0-k1 | Kernel | Réservé pour interruptions et trap handler |
28 | gp | Global Pointer | Adresse de base pour les données statiques |
29 | sp | Stack Pointer | Adresse du sommet de pile |
30 | fp | Frame Pointer | Adresse de base du cadre d'appel d'une fonction
Valeur préservée par un appel de fonction |
31 | ra | Return Address | Adresse de retour de fonction
Valeur préservée par un appel de fonction |
Dans le tableau, on remarque que la valeur de certains registres est dite « préservée » ou « non préservée » pendant un appel de fonction :
- valeur d'un registre préservée par l'appel : la fonction appelée est responsable de ne pas écraser ce registre ou doit faire un backup/restore autour de la fonction si elle veut utiliser ce registre ;
- valeur d'un registre non préservée par l'appel : l'appelé fait ce qu'il veut de ce registre ; l'appelant fait un backup/restore autour des appels de fonction s'il veut utiliser ce registre.
Instructions
Format des instructions
Les instructions MIPS sont toutes codées sur 32 bits et se déclinent synthétiquement suivant 3 formes :
6 bits | 5 bits | 5 bits | 5 bits | 5 bits | 6 bits | |
---|---|---|---|---|---|---|
format R | Op Code | Reg 2 | Reg 3 | Reg 1 | Shift | SubCode |
format I | Op Code | Reg 2 | Reg 1 | Immediate 16 bits | ||
format J | Op Code | Adresse 26 bits |
Instructions d'accès mémoire et chargement de registre
Ces instructions sont les instructions qui permettent le transfert entre la mémoire (RAM) et les registres. Les autres instructions MIPS (calcul, saut, etc.) travaillent uniquement avec les registres du processeur.
On inclut aussi dans cette section les instructions réalisant la copie entre registres ou le chargement de registres avec des valeurs constantes ou des labels (adresses statiques).
Dans le tableau qui suit, la formulation « pseudo-instruction suivant 16 ou 32 bits, signé ou non » signifie que la pseudo-instruction génère une séquence d'instructions basiques différentes selon que la constante est codée sur 16 ou 32 bits, et selon que la constante est signée ou non (signe négatif). Cf. l'exemple dans le cours avec la pseudo-instruction li.
Les voici :
Référence indirecte et indexée à la mémoire (RAM)
Dans les instructions Load/Store, la référence à la mémoire utilise un format général RAM = value($R1), où $R1 est un registre contenant une adresse mémoire de base et value est une constante entière signée utilisée comme décalage (offset) par rapport à l'adresse de base. Par exemple, l'adresse notée -12($t1) a pour valeur RAM[$t1-12].
N.B. La notation 0($R1) peut être abrégée par ($R1).
Exemple
Instructions de calcul
Les opérandes (souvent 3) sont des registres ou éventuellement des constantes (immediate).
Instructions de saut
Branchements Conditionnels :
Appels Systèmes
Les appels systèmes de MIPS réalisent les interactions entre l'exécutable et le système d'exploitation : entrées/sorties, allocation mémoires, exit, heure, etc., MIDI, etc. L'appel est réalisé par l'instruction syscall ; le type d'appel est préalablement stocké dans le registre $v0, et les éventuels arguments dans les registres $a0—$a4 (à sauvegarder si besoin !). En sortie, le résultat éventuel de l'appel utilise les registres $v0 et $v1.
Les principaux appels systèmes sont :
Service | code dans $v0 | Arguments en entrée | Résultat en sortie |
---|---|---|---|
Print Integer | 1 | $a0=entier à imprimer | |
Print String | 4 |
$a0=adresse de la chaîne à imprimer, la chaîne est terminé par \0 |
|
Read Integer | 5 | $v0=entier lu | |
Read String (fgets) | 8 |
$a0=adresse du buffer
d'entrée $a1=taille du buffer |
chaîne à l'adresse $a0, la chaîne est terminée par \0 |
Sbrk (malloc) Allocate heap memory |
9 | $a0=nombre d'octets à allouer |
$v0=adresse mémoire allouée et non initialisée |
Exit | 10 | ||
Print Character | 11 | $a0=caractère à imprimer | |
Read Character | 12 | $v0=caractère lu | |
Exit with status | 17 | $a0=valeur de retour de l'exécution | exit status du processus |
Voici quatre exemples :
Appels Systèmes (Bonus)
Pour terminer, voici deux appels systèmes spécifiques à l'outil Mars :
Service | code dans $v0 | Arguments en entrée | Résultat en sortie |
---|---|---|---|
MIDI out Asynchronous | 31 |
$a0=note 0-127
$a1=durée (ms) $a2=instrument 0-127 $a3=volume 0-127 |
Joue la note et retour immédiat |
MIDI out Synchronous | 33 |
$a0=note 0-127
$a1=durée (ms) $a2=instrument 0-127 $a3=volume 0-127 |
Joue la note et retour après la durée |
- Note de 0 à 127. Note 57 = 440Hz = la3 (A4). Douze notes par octave.
-
Instruments de 0 à 127, 16 familles de 8 instruments :
- Piano(0-7), Percussions chromatiques(8-15), Orgues(16-23), Guitares(24-31)
- Basses(32-39), Cordes(40-47), Orchestre(48-55), Cuivres(56-63)
- Anches(64-71), Flutes(72-79), Synthétiseur solo(80-87), Nappes de synthétiseur(88-95)
- Effets de synthétiseur(96-103), Instruments ethniques(104-111), Percussions(112-119), Effets sonores (120-127)
- cf. Liste détaillée
Un exemple "Apéro==Canon de MIDI": midiCanon.mips.
CSC4251_4252, Télécom SudParis, Pascal Hennequin, Denis Conan, Paul Gibson Last modified: November 2024