Forth sur 6502, épisode 7

En route pour l'affichage

Afficher du texte à l'écran

L'étape d'aujourd'hui va permettre de se diriger vers l'affichage d'un texte à l'écran depuis la boucle Forth. Pour cela, il faut revenir un peu sur le fonctionnement de la Famicom.

Le processeur qui s'occupe de l'affichage est le PPU (Picture Processing Unit). Ce processeur a son espace d'adressage mémoire propre de 16 ko dont le routage est configuré par la cartouche insérée. Dans la console, 2 ko de RAM sont dédiés au PPU, assez pour stocker les informations de deux écrans (index de caractères et attributs). La cartouche doit apporter a minima les informations de caractères (en ROM généralement, mais peut aussi offrir un espace RAM pour les construire) ; elle peut aussi étendre le nombre d'écrans (jusqu'à 4) ou ajouter un système de banking de pages.

De manière générale, tout le mapping de la mémoire du PPU est contrôlé par …

Lire la suite →

Forth sur 6502, épisode 6

Des mots complets

Depuis le début de l'implémentation de ce Forth sur 6502, j'ai parlé de « pseudo mots ». Ces mots ont un CFA (Code Field Address) et un PFA (Parameter Field Address), mais pas d'entête de mot ni de principe de dictionnaire.

Or pour qu'un mot soit complet en Forth, il faut ces deux autres concepts. Dans cette implémentation je vais utiliser deux autres sections : le NFA (Name Field Address) et le LFA (Link Field Address).

Ce qui donne la structure complète suivante :

  • NFA : entête du mot, dont le premier octet est la longueur du nom du mot, suivi du nom lui-même. Seuls les 5 bits de poids faible sont utilisés pour la longueur (ce qui limite la longueur des noms à 31 caractères). Le bit de poids fort est toujours à 1, les deux autres bits seront vus plus tard. De plus, le dernier octet du nom a …
Lire la suite →

Forth sur 6502, épisode 5

La boucle, pour de vrai !

Jusqu'à présent, la boucle principale du programme en Forth était basée sur un hack. Ce hack consistait à réinitialiser l'IP (Instruction Pointer) à la fin du traitement. C'est un peu comme si à chaque fois qu'on avait fini le traitement, on relançait le programme depuis le début.

Il est temps d'implémenter un nouveau mot Forth : BRANCH. Ce mot, suivi dans le PFA par un offset, opère un saut inconditionnel en additionnant cet offset à l'IP courant. En choisissant un offset négatif, l'exécution va revenir en arrière et donc créer une boucle infinie.

Le pseudo code est le suivant :

    (IP) -> X       lit l'offset pointé par l'Instruction Pointer
                    L'IP ayant été positionné sur l'emplacement après le mot BRANCH
                    par NEXT.
    IP + X -> IP    ajoute l'offset à l'IP
    NEXT            appelle NEXT pour continuer l'exécution

Du fait du traitement de …

Lire la suite →

Forth sur 6502, épisode 4

NEXT

Nous y voilà ! Après avoir mis en place un framework de tests dans l'article précédent, il est temps d'implémenter le mot NEXT.

Un petit rappel du premier article de Moving Forth : NEXT est le mot qui permet de faire avancer l'exécution d'une séquence de pointeurs vers des mots Forth. Son pseudo-code (en modèle Indirect Threaded Code) est le suivant :

    (IP) -> W   récupère la mémoire pointée par IP dans le registre "W"
                -> W contient maintenant l'adresse du Code Field
    IP+2 -> IP  avance IP, le compteur de programme
    (W) ->  X   récupère la mémoire pointée par W dans le registre "X"
                -> X contient maintenant l'adresse du code d'exécution
    JP (X)      saute à l'adresse présente dans le registre X

Implémentation

En 6502, le code est un peu long, car l'adressage indirect nécessite de passer par des registres en page zéro. Et les manipuler demande plusieurs instructions. Je …

Lire la suite →

Forth sur 6502, épisode 3

Des tests

Depuis le dernier article, je me suis surtout concentré sur la mise en place d'un framework de tests, ainsi que sur une réflexion de « comment commencer » ?

La lecture de l'article 2 de Moving Forth m'a donné une liste de mots à implémenter en priorité : NEXT, DOCOL et ;S. Cela afin d’arriver rapidement sur une boucle écrite en Forth. J'y reviendrai plus loin dans l'article.

Côté tests, ça a été une aventure en plusieurs étapes. Dans l'idée d'augmenter le nombre de tests, je voulais m'appuyer sur un framework de tests LUA tout fait. J'en ai trouvé un, luaunit qui m'a semblé tout à fait répondre à mes attentes. Pour l'utiliser, je dois utiliser un require("luaunit") dans mon script de tests. Et là ont commencé les ennuis. Tout d'abord, require() n'est pas permis par défaut dans Mesen2, il faut aller permettre les fonction E/S dans les …

Lire la suite →