Back | << | Index | >> |
Description du Programme :
Nous allons illustrer le fonctionnement d’un processeur élémentaire avec un programme simple mettant en jeu une boucle de calcul, à savoir la somme de 5 éléments présents dans un tableau.
Le résultat du calcul doit être placé en mémoire dans la variable ‘résultat’.
En langage C
|
Organigramme
Représentation des données en mémoire
La mémoire est indexée par octet ( si j’augmente l’adresse de 1, je passe à la case suivante, chaque case contenant 8 bits).
Dans une architecture 32 bits, un entier int est codé sur 32 bits ( 4 cases de 8 bits ).
Fonctionnement de la Machine d’Etats
Le Cycle Fetch/Decode/Execute simplifié :
FETCH ( Chargement ) :
On prend l’adresse présente dans PC, et on va chercher dans la mémoire programme
le code de l’instruction à exécuter, que l’on enregistre dans le registre IR.
A l’issue du FETCH, on incrémente la valeur de PC afin de pointer sur l’instruction suivante.
DECODE AND EXECUTE :
En consultant le registre IR, la machine d’état connait l’opération à exécuter.
Elle met alors tout en oeuvre pour contrôler l’UAL et les registres R1,R2,R3 et R4 afin d’exécuter l’instruction.
Codage d’une Instruction :
Toutes les instructions respectent la syntaxe suivante :
Opcode REG_DEST, REG_OP1, REG_OP2, #imm : REG_DEST <– opcode(REG_OP1, REG_OP2+#imm)
Chaque instruction est codée sur 32 bits, selon le format suivant :
J’ai donc 32 bits pour :
MOV R1, R2 // R1<–R2
MOV R2,#5 // R2 <– 5
ADD R3,R2,R1 // R3 <– R2+R1
ADD R1,R2,#1 // R1 <– R2+1
SUB R3,R2,R1 // R3 <– R2-R1
Dans une architecture RISC, seules les instruction de type LOAD et STORE permettent d’accéder à la mémoire.
LDR : permet de charger dans un registre une donnée se trouvant en mémoire de données.
Il faut donc spécifier le registre destination recevant la donnée, et l’adresse de la donnée.
LDR R1,[R0] : je vais chercher en mémoire la donnée dont l’adresse se trouve dans R0, je place la valeur de cette donnée dans R1.
Les instructions sont codées sur 32 bits
Je ne peux donc pas indiquer dans une même instruction le nom de l’instruction,
un numéro de registre et une __adresse mémoire de 32 bit__s.
Pour placer dans R0 l’adresse d’une variable, j’utilise l’instruction suivante :
LDR R0,[PC+offset] : R1 reçoit une valeur correspondant à une adresse d’une variable en mémoire ; le compilateur a placé lors de la compilation cette valeur d’adresse à l’adresse PC+offset.
STR : permet d’écrire en mémoire le contenu d’un registre, en spécifiant dans un autre registre la case mémoire souhaitée.
Ex: STR R1,[R0] : je vais écrire dans la case mémoire pointée par R0 ce qui se trouve dans le registre R1.
Il faut bien entendu au préalable placer dans R0 l’adresse qui va bien avec une instruction LDR.
Une condition if then else ou une boucle for/while en C se traduit par un saut conditionnel en assembleur.
La condition se trouve dans le registre SR.
BNE : Branch if not Equal to Zero : si le résultat de mon opération précédente ( par exemple une soustraction ) est non nul ( autrement dit mon bit d’état Z=0 ), alors j’effectue un saut.
Cela consiste à forcer la valeur de PC avec une adresse indiquée avec l’instruction BNE.
Si ma condition n’est pas respectée, autrement dit j’ai obtenu un résultat nul ( Z=1 ) précédemment, dans ce cas je ne fais pas le saut et passe donc à l’instruction suivant bne.
Programme en Assembleur ARM
R1 = compteur
R2 = i
R3 = acc
REMARQUE : R2 pointe sur les éléments du tableau. Comme chaque valeur fait 32 bits, soit 4 cases de 8 bits, il faut bien incrémenter R2 de 4 à chaque tour de boucle.
La description VHDL du processeur mu0-risc est disponible ici :
Back | << | Index | >> |