Le simulateur microPIUP
Le simulateur microPIUP permet d'illustrer graphiquement le fonctionnement d'un processeur d'un point de vue fonctionnel et à des fins pédagogiques. Ce processeur est une machine hypothétique dont l'architecture est décrite ici.
L'interface graphique visualise
l'état du processeur (registres généraux, compteur ordinal, registre d'état) et de son contrôleur d'exceptions,
l'espace d'adressage principal,
l'espace d'adressage d'entrée/sortie,
l'état d'un périphérique de sortie.
À chaque pas de la simulation un tableau visualise les caractéristiques de la dernière instruction exécutée :
découpage de l'instruction en champs,
nom de l'instruction,
mode d'adressage et adresse effective s'il y a lieu.
Le simulateur offre bien entendu les principales fonctionnalités d'un débogueur :
le chargement d'un fichier contenant un programme,
l'exécution "enchaînée" des instructions ou en "pas à pas",
la gestion de points d'arrêt,
la modification des contenus des registres généraux, du compteur ordinal (PC), des indicateurs et de la mémoire.
Il permet le déclenchement d'interruptions matérielles et la réinitialisation du processeur (reset).
Le simulateur peut fonctionner en deux modes :
un mode réaliste qui correspond exactement à l'implantation logicielle (par programme) de l'architecture de microPIUP telle qu'elle est décrite dans les spécifications,
un mode assisté qui correspond à une implantation logicielle de microPIUP et d'un système d'exploitation rudimentaire permettant de terminer un programme et de simuler simplement une lecture ou une écriture sur un périphérique.
Le choix du mode de fonctionnement se fait en utilisant la case à cocher « Avec primitives système ».
Ces deux modes de fonctionnement ne diffèrent que par le traitement des trappes logicielles.
En mode assisté, le déclenchement d'une trappe logicielle (instruction TRP) provoquera :
la fin d'exécution du programme exécuté par le processeur pour la trappe n° 64 (primitive de "retour" au système),
la lecture d'une chaîne de caractères sur un objet représentant le périphérique d'entrée pour la trappe n° 65 (primitive système de lecture), le contenu du registre R0 est interprété par cette primitive comme l'adresse mémoire où doivent être copiés les (codes ASCII des) caractères lus,
l'écriture d'une chaîne de caractères sur un objet représentant le périphérique de sortie pour la trappe n° 66 (primitive système d'écriture), le contenu du registre R0 est interprété par cette primitive comme l'adresse mémoire de la chaîne de caractères à afficher,
l'affichage d'un libellé comportant le numéro de trappe sur un objet représentant un périphérique de sortie pour les autres numéros (67 à 255).
Les chaînes de caractères sont codées en ASCII dans la mémoire du simulateur à raison d'un octet par caractère, le dernier caractère effectif de la chaîne étant suivi d'un octet de fin de chaîne dont tous les bits sont à 01 (caractère ASCII NUL).
Le périphérique d'entrée est représenté par une boîte de dialogue, le périphérique de sortie est représenté par une zone de texte.
En mode réaliste, lors de l'exécution d'une instruction TRP l'état du processeur est modifié conformément aux spécifications du processeur.
Quel que soit le mode de fonctionnement du simulateur, il est possible de simuler, à n'importe quel moment de l'exécution, l'arrivée d'une interruption de numéro n et la réinitialisation du processeur (signal RESET).
N.B. L'indicateur IF étant à 0 à l'initialisation (reset) il est possible d'écrire des programmes ne mettant pas en oeuvre le mécanisme d'exceptions non programmées. Ces exceptions sont alors ignorées et l'exécution se poursuit « normalement ».
La fenêtre principale comporte une barre de menu ainsi qu'une barre d'outils offrant un accès rapide aux commandes les plus utilisées et est divisée en différentes zones visualisant l'état du simulateur, du processeur et de la mémoire associée, et permettant d'agir sur le processeur (déclenchement d'interruptions, reset) ou sur le simulateur (mode de fonctionnement).
Elle comporte quatre items :
L'item Fichier
permet :
le chargement d'un exécutable choisi dans un sélecteur de fichier :
la remise à zéro de l'espace d'adressage normal et de la liste des points d'arrêt,
la remise à zéro de l'espace d'adressage d'entrée/sortie,
de quitter l'application.
L'item Execution
permet :
d'exécuter l'instruction suivante si la case "Exécution au pas à pas" du panneau "Modes de fonctionnement" est cochée, les instructions suivantes jusqu'au prochain point d'arrêt ou jusquà la fin du programme (trappe logicielle n° 64 en mode assisté) dans le cas contraire,
de stopper l'exécution (l'item stop n'est activé lorsque que simulateur exécute une séquence d'instructions, la plupart des autres choix sont alors désactivés),
d'ajouter un point d'arrêt (l'adresse du point d'arrêt à ajouter est proposée dans une boîte de dialogue initialisée avec l'adresse du mot sélectionné dans l'onglet "Espace d'adressage normal")
de supprimer le point d'arrêt sélectionné dans la liste affichée en haut à droite de la fenêtre,
de remettre à zéro les registres du processeur,
de charger le compteur ordinal (PC) avec l'adresse du mot sélectionné dans l'onglet "Espace d'adressage normal").
L'item Aide
permet :
d'afficher une boîte d'information sur le simulateur,
d'afficher une fenêtre contenant la présente documentation.
Enfin l'item Fenetres
permet d'ouvrir une fenêtre visualisant le contenu du fichier actuellement chargé en mémoire :
Une marque dans la marge gauche signale la prochaine instruction à exécuter (la position de la marque n'est significative que lorsque l'exécution du programme est stoppée).
L'utilisation de ce même item permet de fermer la fenêtre visualisant le code.
Elle comporte 7 boutons :
offrant des fonctions identiques à celles figurant dans le menu, soit de gauche à droite :
Fichier -> Quitter
Fichier -> Lire fichier programme
Execution -> Executer
Execution -> Stop
Execution -> Remise à zéro des registres
Execution -> Ajouter un point d'arrêt
Execution -> Retirer un point d'arrêt
Comme dans le menu Execution le bouton Stop n'est activé que lorsque le processeur exécute une séquence d'instructions.
Ce panneau permet de sélectionner le mode de fonctionnement du simulateur (assisté/réaliste) et le mode d'exécution (pas à pas/continu). A l'initialisation le simulateur est en mode assisté et en mode d'exécution continu.
Ce panneau visualise l'état du processeur :
La partie supérieure montre le contenu du compteur ordinal (PC) et du registre d'état (SR). Le premier est affiché en hexadécimal, le second en binaire. Ces composants d'affichage sont aussi des champs de saisie qui permettent la modification des registres correspondants du processeur. Il suffit d'amener le pointeur de la souris dans la cellule, d'entrer les caractères de la nouvelle valeur et de valider la saisie en appuyant sur la touche Entrée (Enter, Return).
La partie inférieure affiche en hexadécimal les contenus des 16 registres généraux. Là encore il est possible de modifier les registres en saisissant la nouvelle valeur dans le champ correspondant puis en appuyant sur Entrée (Enter, Return).
Ce panneau visualise les caractéristiques de la dernière instruction exécutée par le processeur.
Lors du démarrage de l'application l'information affichée n'est pas significative :
Une fois un programme chargé et une instruction exécutée, le panneau visualise l'ensemble des informations concernant la dernière instruction exécutée :
le code en hexadécimal du premier mot d'instruction,
le découpage en champs binaires de ce même mot,
le nom symbolique de l'instruction,
le contenu (en hexadécimal) de l'eventuel mot d'extension,
le mode d'adressage utilisé (s'il y a lieu),
et l'adresse effective correspondante.
Le premier de ces deux panneaux permet de simuler l'envoi d'une interruption matérielle au processeur. Le curseur permet de sélectionner le niveau d'interruption souhaité. Celui-ci s'affiche alors sur le bouton de droite derrière le libellé IRQ. Un clic sur ce bouton permet de déclencher l'interruption.
Le deuxième panneau comporte un seul bouton permettant de simuler une réinitialisation du processeur (reset).
Il est impératif d'utiliser ce bouton lorsque l'indicateur W du registre d'état et à 1 (processeur en attente) en même temps que l'indicateur I de ce même registre est à 0 (interruptions inhibées). En effet dans cet état (état d'abandon) le processeur boucle indéfiniment sans exécuter aucune instruction, même si l'utilisateur du simulateur utilise le bouton Exécuter.
Ce panneau visualise la pile, c'est-à-dire la partie de la mémoire allant du sommet de pile (contenu du registre R15) à la base de la pile.
La base de la pile est soit définie au moment du chargement d'un fichier exécutable en utilisant la troisième ligne du fichier, soit définie par défaut avec pour valeur 0x1000, soit définie par l'utilisateur en sélectionnant un mot dans l'onglet "Espace d'adressage normal" puis en cliquant sur le bouton "Adresse de base".
Ce panneau visualise la liste des points d'arrêts actifs.
Les points d'arrêts s'ajoutent et se retirents en utilisant les items de menu Execution->Ajouter un point d'arret et Execution -> Retirer un point d'arret ou les boutons correspondant de la barre d'outils.
Cet onglet visualise l'espace d'adressage normal (la mémoire "principale") dans une grille.
Les mots (de 16 bits) sont représentés à raison de huit par ligne et le mot situé à l'adresse contenu dans le compteur ordinal (la prochaine instruction à exécuter) est affiché en rouge. Les contenus sont affichés en hexadécimal.
La première colonne contient les adresses (écrites en hexadécimal) des premiers mots de chaque ligne. Les titres des colonnes à partir de la deuxième contiennent la quantité (exprimée en hexadécimal) à ajouter à l'adresse située en début de ligne pour obtenir l'adresse du mot situé à l'intersection de la ligne et de la colonne. Ainsi, dans la capture d'écran ci-dessus le mot affiché en rouge est situé à l'adresse 0410 + 0a = 041a.
Une cellule représentant à un mot peut être utilisée pour modifier le contenu du mot mémoire correspondant. Il suffit d'amener le curseur de la souris dans la cellule, de saisir le nouveau contenu (en hexadécimal) puis de valider la saisie en appuyant sur Entrée (Enter, Return).
Cet onglet visualise de façon comparable au précédent l'espace d'adressage d'entrée/sortie.
Il s'agit cette fois de mots de 8 bits.
Cet onglet visualise le périphérique de sortie utilisé en mode assisté par la trappe n° 66.
La zone de texte centrale sert à l'affichage des textes, le bouton "Nouvelle ligne" provoque un saut de ligne. La capture d'écran ci-dessus montre la trace d'exécution d'un programme bouclant indéfiniment sur l'impression d'un point et d'un saut de ligne tous les seize points.
Cet onglet visualise l'état du contrôleur d'exceptions plus précisément l'état du registre ERF (Exception Request Flags) de ce contrôleur.
Chaque cellule représente un indicateur de ce registre. Lorsqu'elle est vide le bit correspondant est à 0, lorsqu'elle contient un signe + le bit est à 1.
La capture d'écran ci-dessus montre l'état du contrôleur après le déclenchement de trois interruptions de niveau 0, 1 et 2 alors que les interruptions étaient inhibées (indicateur I du registre d'état à 0).
Cet onglet permet de surveiller les modifications apportées à des mots sélectionnés dans l'espace d'adressage normal. A chaque accès en écriture à l'un des mots sélectionnés, le simulateur stoppe l'exécution.
C'est un mécanisme de point d'arrêt sur modification (fonction "watchdog" ou "monitoring" des debogueurs).
Pour ajouter une adresse à la liste des mots à surveiller, il suffit de sélectionner le mot dans l'onglet Espace d'adressage normal, puis de sélectionner l'onglet Surveillance et de cliquer sur le bouton Ajouter.
Pour supprimer une adresse de la liste, il suffit de la sélectionner dans la liste (la ligne est alors colorée en rouge) puis de cliquer sur le bouton Retirer.
Il est possible d'utiliser le simulateur en mode "batch" pour exécuter un programme en utilisant la commande :
java -jar microPIUP.jar -batch exécutable [valeur_hexa ...]
L'argument exécutable est le nom du fichier à charger et à exécuter, les arguments suivants, optionnels, sont les valeurs initiales, en hexadécimal, des registres R1, R2, ...
Il est impossible d'interagir avec le simulateur lorsqu'il lancé de cette manière. En particulier il n'est pas possible de déclencher d'interruption matérielle ni d'interrompre l'exécution. Si le programme chargé "boucle" il faut "tuer" le processus.
La version batch ne fonctionne qu'en mode assisté. La trappe n° 65 provoque une lecture sur l'entrée standard et la trappe n° 66 provoque une écriture sur la sortie standard.
Le simulateur permet le chargement en mémoire d'un code conservé dans un fichier "exécutable". Selon le cas, seuls les 4 ou 5 premiers caractères de chaque ligne d'un tel fichier sont interprétés par le chargeur. Le reste de la ligne constitue un commentaire (il est donc ignoré).
Les 4 premiers caractères de la première ligne d'un fichier exécutable sont des chiffres hexadécimaux ('0' à '9', 'A' à 'F 'ou 'a' à 'f') qui représentent l'adresse de chargement du programme en mémoire.
Les 4 premiers caractères de la deuxième ligne sont des chiffres hexadécimaux qui représentent l'adresse de la première instruction à exécuter c'est-à-dire la valeur initiale du compteur ordinal.
Si le premier caractère de la troisième ligne est un S, les 4 caractères suivants sont des chiffres hexadécimaux qui représentent l'adresse de base de la pile, c'est-à-dire la valeur initiale du registre SP, sinon les 4 premiers caractères de la troisième ligne sont des chiffres hexadécimaux qui représentent le premier mot à charger en mémoire.
Les 4 premiers chiffres hexadécimaux des lignes suivantes représentent les mots qui doivent être rangés consécutivement en mémoire.
1C'est une façon classique de représenter les chaînes de caractères. Il est possible d'avoir des chaînes vides ; leur représentation en mémoire se réduit au caractère NUL.