1 Einleitung
Diese Dokumentation behandelt den Aufbau des Super Nintendo Entertainment Systems (SNES). Es soll einen Überblick darüber verschaffen, mit welchen technischen Tricks eine, für damalige Verhältnisse, leistungsstarke und doch recht günstige Konsole für den Homeentertainment-Bereich entwickelt wurde. Dieses Dokumentation gliedert sich dabei grob in vier Teile. Im ersten Teil, dem Kapitel 2, verschaffen wir uns zunächst einen Überblick darüber, gegen welche Systeme der SNES konkurrieren musste. Um dies zu veranschaulichen führen wir auch die technischen Daten der Mitbewerber auf.
Der zweite Teil (Kapitel 3) beschäftigt sich mit dem technischen Aufbau des Systems. Es werden viele der eingebauten Elemente näher erläutert. Auf eine ausführliche Erklärung einiger Elemente wird jedoch verzichtet, da diese Standardkomponenten der Elektronik sind und daher auch nur bekannte Funktionen ausführen.
Im Anschluss an den Aufbau des SNES behandelt der dritte Teil des Dokuments (Kapitel 4 + 5) den Aufbau der Module (engl. Cartridge). Zunächst soll der allgemeine Aufbau und das Pinout dieser Module dargestellt werden. Danach werden einige der Co-Prozessoren, welche in machen Modulen vorhanden waren, ausführlich erklärt.
Im letzten Teil der wird auf den praktischen Teil eingegangen. Es soll der Aufbau eines SNES-Programms erklärt und einige einfache Programmbeispiele dargestellt werden. Zudem wird beschrieben mit welcher Software der Quelltext kompiliert wird und welche Testmöglichkeiten man hat.
2 Computertechnik dieser Zeit
Als der SNES 1990 erstmals auf den Markt kam, musste sich dieser in direktem Konkurrenzkampf mit dem SEGA MegaDrive und handelsüblichen PCs / Amigas begeben. Der Vorteil für die Konsolenhersteller war jedoch, dass das Zusammenspiel der Komponenten aufeinander ausgelegt war und auch viele spezielle Co-Prozessoren vorhanden waren, welche trotz langsamerer Taktfrequenz zum Teil aufwändigere Spiele abarbeiten konnten als der Hauptprozessor eines PCs. Außerdem war ein PC damals nicht als Spielesystem ausgelegt. Für damalige Verhältnisse aufwändige Grafiken mussten alleine von der CPU errechnet werden, wohingegen der SNES 2 PPUs (Picture Processing Units) zur Grafikdarstellung besaß. Diese Arbeitsweise ist erst Mitte der 90er mit dem Erscheinen der ersten 3D-Grafikkarten in die PC-Welt übernommen worden. Auch waren Soundkarten im PC eher eine Ausnahme, da selbst die günstigen Modelle noch über 150 DM kosteten. Jedoch besaß der PC andere Vorzüge gegenüber dem SNES. Er konnte nicht nur für Spiele sondern auch für Büroanwendungen verwendet werden. Auch war er fast beliebig erweiterbar, auch wenn aufgrund von fehlender Standards noch vieles inkompatibel zueinander war (Beispiel: CD-ROM Schnittstellen). Was wohl auch für den PC sprach, war die Möglichkeit, Software einfach kopieren zu können. Diese Möglichkeit zum Kopieren der Module gab es später zwar auch für Konsolen, war aber noch recht teuer und umständlich.
Im Vergleich zum PC war der Amiga, auch wenn Hersteller Commodore es anders sah, ein reiner Spielecomputer und somit das Bindeglied zwischen dem PC und den Konsolen. Im Gegenteil zum PC war dieser nicht beliebig erweiterbar, bot aber bereits eine vorinstallierte Soundeinheit. Somit war er als Spielecomputer recht beliebt. Auch die Softwarepiraterie erlebte mit dem Amiga einen drastischen Anstieg, da Spiele, wie beim PC auch, auf Diskette und ohne Kopierschutz-mechanismen vertrieben wurde.
Im Konsolenlager lieferten sich lange Zeit Nintendos SNES und Segas MegaDrive einen erbitterten Kampf. Der MegaDrive war zur Zeit der Veröffentlichung des SNES bereits zwei Jahre auf den Markt. Da Japan jedoch eine Hochburg von Nintendo war und auch die USA von Nintendo mehr angetan waren, konnte Sega mit dem MegaDrive hier keine großen Erfolge erzielen. Lediglich in Europa konnte sich der MegaDrive etablieren, da diese 16 Bit Konsole hier zwei Jahre vor dem 16Bit SNES auf den Markt kam. 1993 bzw. 1994 endete die Ära der 16Bit Konsolen, nachdem 3DO in Amerika eine, überteuerte und daher wenig verkaufte, Konsole mit CD-ROM-Laufwerk anbot. 1994 veröffentlichte Sony dann die PlayStation, welche den SNES weitestgehend ablöste.
3 Das System
Dieses Kapitel behandelt den Aufbau des Super Nintendo Entertainment Systems. Es werden hier die einzelnen Bauelemente und Zusammenhänge erklärt, welche zur Erzeugung der Video- und Audiosignale verwendet werden. Es wird jedoch darauf verzichtet, darauf einzugehen, wie Daten genau verarbeitet werden und wie diese schließlich auf PAL bzw. NTSC umgewandelt werden. Nachdem bereits im vorangegangenen Kapitel ein kleiner Überblick über das Gesamtsystem gegeben wurde, steigen wir nun in die Arbeitsweise des Gerätes ein. Hierzu wird im folgenden Unterkapitel zunächst ein Einblick in die Konsole gegeben. Die darauf folgenden Unterkapitel beschreiben anschließend die Funktionsweise der einzelnen Bauelemente.
3.1 Das Gesamtsystem
Das Blockschaltbild des Systems sieht wie folgt aus:
Bevor wir zu den einzelnen Komponenten des Systems kommen, möchten wir auf das Zusammenspiel der Komponenten eingehen.
Der CIC-Chip ist der Kopierschutz des Systems (siehe Kapitel 3.5). Er verfügt über eine Reset-Leitung, mittels der er die zweite Grafikeinheit abschalten kann. Diese gibt das Reset-Signal dann weiter an die erste Grafikeinheit, die Soundeinheiten, dem RAM und die SNES-CPU.
Die SNES-CPU ist an zwei Adressbus-Systeme angeschlossen. Zum einen der 24 Bit breite A-Bus und zum anderen der 8 Bit breite B-Bus. Mittels des A-Busses ist es der CPU möglich, den gesamten RAM sowie den gesamten ROM-Speicher des Moduls zu adressieren. Der B-Bus hingegen dient zur Kommunikation mit den anderen Bauteilen. So haben die Sound- & Grafikeinheiten nur Zugriff auf einen kleinen Teil des RAMs. Allen Einheiten gemein ist der 8 Bit breite Datenbus.
Die beiden PPUs haben zudem einen eigenen Speicher (32KB pro Einheit). Die Besonderheit bei der Verdrahtung ist jedoch dass nur die erste Einheit in der Lage ist, den Speicher zu adressieren. Somit ist die zweite PPU auf das Anlegen der richtigen Adresse auf dem Adressbus auf die erste PPU angewiesen.
Die Soundeinheiten des Systems können nur über die Sound CPU mit dem Rest des Systems kommunizieren. Auf welche Art die Soundeinheiten untereinander kommunizieren, wird im entsprechenden Kapitel behandelt.
3.2 Hauptprozessor
Der Hauptprozessor des Systems ist eine Spezialanfertigung für Nintendo welche mit dem Western Design Center 65816 bzw. 65C816 kompatibel ist. Der von Nintendo verwendete Name dieses Prozessors ist „5A22“. Technisch gesehen entspricht dieser Chip einer Weiterentwicklung des Prozessors welcher auch im NES verbaut war (MOS Technologies 6502). Prinzipiell kann der SNES somit den Programmcode des NES verarbeiten, jedoch scheitert die Umsetzung an den PPUs welche nicht kompatibel zum NES-Pendant sind.
Im Gegensatz zum 6502 besitzt dieser Prozessor auf 16Bit erweiterte Alu, X & Y, Index-Register und Stack-Pointer. Über einen Softwareschalter lässt sich die CPU jedoch in einen 8Bit Modus umschalten. Wie bereits zuvor angesprochen verfügt die CPU über einen Anschluss an den 24Bit Adressbus.
Kommen wir nun zum internen Aufbau der Einheit. Zur Verständnis stellen wir nachfolgend das Blockschaltbild des Prozessors, welches aus der offiziellen Dokumentation stammt, dar.
Der Hauptprozessor verfügt über drei 8-Bit-Schnittstellen, über die er mit den anderen Bauteilen auf dem Chip kommunizieren kann. Dies sind zwei reine Adress-Schnittstellen, die die Datenleitungen A0 bis A15 bereitstellen, sowie eine Schnittstelle, die wahlweise für Adressen oder Daten genutzt werden kann und bei Adressen die Leitungen A16 bis A23 bereitstellt. Somit kann parallel eine 24-Bit-Adresse ausgegeben werden, oder eine 16-Bit-Adresse und gleichzeitig 8 Bit Daten.
Die Datenleitungen werden in den Prozessor weitergeleitet, im Gegensatz zu den Adsressleitungen. Bei Befehlsbytes geschieht dies über die Data Latch/Predecode-Einheit, bei Datenbytes über das Databank-Register. Adressen werden über den Internal Adress Bus ein- und ausgelesen. Über die Data Latch/Predecode-Einheit werden Befehle in das Instruction-Register geschrieben. Das Databank-Register gibt Daten weiter auf den Internal Data Bus, von dem sie weitergegeben werden können an Program Counter, Accumulator, ALU oder Direct-Register (welches bei bestimmten Adressierungsarten benötigt wird). In die Register X und Y können die Daten nur über einen weiteren Schritt über den Internal Special Bus geladen werden, auf den sonst nur Accumulator, ALU und Stack-Pointer sowie die Transfer Switches Zugriff haben.
Neben den drei 8-Bit-Schnittstellen verfügt der Hauptprozessor noch über eine Reihe von Steuerleitungen, die die System Control, Timing Control und Interrupt Logic-Einheiten sowie den Clock Generator steuern bzw. entsprechende Befehle und Signale weitergeben.
3.3 Grafikprozessoren (Nintendo 5C77 & Nintendo 5C78)
Der SNES kann Auflösungen von 256*224 bis 512*478 Pixeln darstellen, wobei die Darstellung jeweils unterschiedlich abläuft. Bilder mit Auflösungen von 256*224 bis 512*239 werden progressive aufgebaut, also Zeile für Zeile von oben nach unten. Bilder mit Auflösungen von 512*448 oder 512*478 werden interlaced aufgebaut, also erst die ungeraden Zeilen, dann die geraden. Dies geschieht, damit das Auge keine halben Bilder wahrnimmt, weil der Aufbau des ganzen Bildes zuviel Zeit in Anspruch nimmt.
Die beiden Grafikprozessoren arbeiten als eine Einheit, können also auch als solche wahrgenommen werden. Der erste Grafikchip ist für den Zugriff auf den internen Grafikspeicher zuständig und mit diesem über einen Adressbus verbunden. Der zweite Chip sendet die Farbinformationen an die RGB-Einheit, die diese Daten weitergibt. Der interne RAM umfasst 64 KB Speicher für Daten, 544 Byte für Objekte (Sprites im Weiteren) und 512 Byte für Farbdaten. Die Farben setzen sich aus den RGB-Farbwerten (15 Bit Farben) zusammen, was eine Bandbreite von 32.768 Farben ermöglicht. Allerdings werden im Farbdaten-RAM nur Paletten von 4 bis 256 Farben pro Palette gespeichert, aus denen die jeweiligen Elemente auf dem Bildschirm wählen können. 256 Farben ist gleichzeitig die Speichergrenze des Farbdaten-RAM (Eine Farbe braucht 2 Byte Speicher), wodurch die 256-Farben-Palette auch als „full palette“ bezeichnet wird. Jede Palette enthält die Farbe „durchsichtig“, wodurch dahinter liegende Objekte gezeigt werden.
Der SNES kann in 8 Modi Grafiken darstellen, die sich jeweils grundsätzlich unterscheiden. Allen Modi gemeinsam ist, dass sie Layer verwenden, wobei die Anzahl der Layer je nach Modus variiert. Jeder Layer ist aufgebaut aus Tiles, „Kacheln“, die eine Größe zwischen 32*32 und 128*128 Pixeln haben können. Die Daten für die Tiles sind im internen Daten-RAM hinterlegt und können auch mehrfach verwendet werden. Die möglichen Farben für die Tiles sind wiederum vom Modus abhängig. Die Tiles können in zwei Planes, „Ebenen“, angeordnet werden, die Vordergrund und Hintergrund des Layers darstellen. Alle Layer können unabhängig voneinander auf dem Bildschirm horizontal und vertikal verschoben werden.
Auf jede Plane jedes Layers können sich Sprites, „Objekte“, befinden. Diese Sprites können die Größe von 8*8 bis 64*64 Pixeln haben, sind für sich bewegbar sowie horziontal und vertikal drehbar. Die Daten der Sprites werden im Objekt-RAM gespeichert, wobei maximal 32 Sprites gleichzeitig dargestellt werden können. Auch
Sprites werden aus Tiles geformt, wobei diese für Sprites immer 8*8 Pixel groß sind und über eine 16-Farben-Palette verfügen.
Die Modi im Einzelnen:
Modus 0: 4 Layer stehen zur Verfügung, jeder Layer verfügt nur über eine 4-Farben-Palette.
Modus 1: 3 Layer, zwei mit jeweils 16-Farben-Paletten, einer mit einer 4-Farben-Palette.
Modus 2: 2 Layer, jeder mit einer 16-Farben-Palette. Jedes Tile kann einzeln verschoben werden.
Modus 3: 2 Layer, einer mit der „full palette“, 256 Farben, einer mit einer 16-Farben-Palette. Zusätzlich kann der Layer mit der full palette auch Farben aus einem 11-Bit-Farbraum (RGB 443) direkt definieren.
Modus 4: 2 Layer, einer mit der „full palette“, einer mit einer 4-Farben-Palette. Zusätzlich kann der Layer mit der full palette auch Farben aus dem 15-Bit-Farbraum direkt definieren. Jedes Tile kann einzeln verschoben werden.
Modus 5: 2 Layer, einer mit einer 16-Farben-Palette, einer mit einer 4-Farben-Palette. Veränderte Codierung der Tiles, um interlaced-Darstellung zu erleichtern.
Modus 6: 1 Layer, der eine 16-Bit-Palette verwendet. Ebenfalls veränderte Tile-Codierung zur Erleichterung von interlaced-Darstellungen, zusätzlich kann jedes Tile einzeln verschoben werden.
Modus 7: Dieser Modus bildet eine große Besonderheit des SNES. Es wird nur ein Layer verwendet, der entweder nur über eine Plane mit full palette verfügt, oder über zwei Planes mit jeweils 128 Farben. Besonderheit ist, dass der Layer unter Benutzung von Matrix-Transformationen gedreht, gekippt und kleiner oder größer skaliert werden kann. Dies soll Dreidimensionalität simulieren und perspektivische Darstellung ermöglichen.
Weitere Möglichkeiten der Farbgestaltung ergaben sich aus gröberer Pixelung der Layer oder Farbaddition bzw. –subtraktion der Farben von Layer und Sprite, was eine wiederum größere Farbvielfalt ermöglicht, als eigentlich vorgesehen.
3.4 Soundsystem
Das Soundsystem des SNES besteht aus einem Sony 8 Bit Prozessor (SPC700) und einem Sony DSP (WWW210R6X) gefolgt von einigen Filtern und D/A-Wandlern. Eingehen wollen wir in diesem Kapitel nur auf den Prozessor, da dieser maßgeblich für die Leistung der Soundausgabe ist.
Der Sony SPC700 CMOS 8 Bit Prozessor ist die Verwaltungseinheit des Soundsystems.
Aufgabe dieses Chips ist es, die zur Tonerzeugung benötigten Daten anzufordern und in den 64KB großen Sound-RAM zu übertragen.
Zudem wird der SPC700 zur Steuerung des DSPs verwendet. Dieser arbeitet die Anweisungen der Sound CPU zu entsprechender Zeit mit den Daten aus dem Sound-RAM ab und gibt die erzeugten digitalen Daten an die D/A-Wandler & Filter weiter.
Nun soll die Funktionsweise des SPC700 genauer erläutert werden.
3.4.1 Speicher
Da der SPC700 maximal 64KB Adressieren kann und dies bereits mit der Größe des RAMs ausgereizt ist, besteht ein Konflikt mit dem 64Byte großen IPL ROM, welcher den initialen Zustand der Soundeinheit nach dem Starten der Konsole enthält. Als Lösung wurden vom Adressbereich des RAMs 64Byte an den ROM abgetreten.
Der verbleibende Adressbereich ist jedoch nicht vollständig für beliebige Daten verfügbar. So sind weitere 128Byte für die Special Function Register (kurz: SFR) reserviert.
Alle noch verfügbaren Adressbereiche stehen für Sounddaten zur Verfügung. Zu beachten ist nur, dass der Bereich von 0200H – 7FFH der Bereich ist, welcher für Datentransfers benötigt wird. So sollten Daten, die öfter benötigt werden, aus diesem Bereich verschoben werden, um der Gefahr zu entgehen, dass diese bei einem weiteren Datentransfer überschrieben werden.
3.4.2 Kommunikation mit der SNES-CPU
Die zuvor angesprochenen Datentransfers des SPC700 laufen alle über den Datenbus, den B-Bus und der SNES-CPU ab. Hierzu stehen der SPC700 vier Ports zur Verfügung. Von jedem der vier Ports stehen zwei Versionen zur Verfügung: jeweils ein Read- und ein Write-Register. Die Read-Register können von der SNES-CPU beschrieben und von der Sound-CPU nur gelesen werden. Anders herum ist es bei den Write-Registern, welche nur vom SPC700 beschrieben werden können. Aufgrund der Tatsache, dass sich die Speicherstellen im Work-RAM (kurz: WRAM) des SNES befinden greifen, die SNES-CPU und die Sound-CPU mit unterschiedlichen Speicheradressen auf diesen zu. Der Sound-CPU steht nur der 8 Bit breite B-Bus zur Verfügung, die SNES-CPU kann hingegen den 24 Bit breiten A-Bus verwenden.
3.4.3 Timer / Counter
Die 8 Bit Timer der Sound-CPU sind in Sets zusammen mit den 4Bit Countern geschaltet (je ein Timer und ein Counter). Zwei der drei Sets werden mit 8KHz angesteuert, das dritte Set hingegen mit 64KHz. Die vor den Countern befindlichen Timer können dabei wie üblich mit einem max. Wert vorbelegt werden. Sobald der Timer in Betrieb ist und den Vorgabewert erreicht, wird ein Signal an den entsprechenden Counter im Set gesendet. Dieser wird dann um 1 inkrementiert.
Auf die Vorgehensweise wie aus den Binärdaten ein Audiosignal erzeugt wird, möchten wir hier nicht näher eingehen. Ziehen Sie bitte hierzu Kapitel 3-2-1 aus dem 1. Entwicklerhandbuch zu Rate.
3.5 Der Kopierschutz
Über den Kopierschutzchip ist wenig in Erfahrung zu bringen. Nintendo hält sich verständlicherweise auch sehr bedeckt bei dem Thema. Die Funktionsweise des Kopierschutzes hingegen ist bekannt.
Beim Einschalten der Konsole beginnt der Chip mit einem baugleichen Chip auf dem Modul zu kommunizieren. Stellt sich dabei heraus, dass kein Chip oder auch ein falscher Chip (die NTSC-Version unterscheidet sich von der PAL-Version) auf dem Modul vorhanden ist, setzt der CIC-Chip im SNES das RESET-Signal und stoppt somit alle im SNES vorhandenen Einheiten. Welche Daten zwischen den beiden Einheiten ausgetauscht werden, ist nicht bekannt. Es ist auch nicht bekannt, ob es sich bei jedem Startvorgang um die gleichen Daten handelt, die übermittelt werden; es ist aber davon auszugehen, dass der CIC-Chip im SNES ein zufälliges Signal generiert, auf welches der Chip im Modul entsprechend antwortet.
Um auf eine Frage aus unserem Vortrag zurückzukommen, möchten wir an dieser Stelle noch einmal erläutern, warum es nicht immer möglich ist, einfach die RESET-Leitung zu durchtrennen um den Kopierschutz unwirksam zu machen. Bei unseren Recherchen sind wir auf genau diese Vorgehensweise gestoßen. Und dieses Vorgehen funktionierte auch bei den ersten verfügbaren Modulen. Bei den neueren hingegen wird dieses Vorgehen vom Modul erkannt und verweigert daraufhin den Datentransfer. Auf welche Art dies vom Modul ermittelt wird ist uns aufgrund der unbekannten genauen Funktionsweise des Chips unbekannt. Wir vermuten jedoch, dass der CIC-Chip im SNES beim Setzten des RESET-Signals auch alle Übertragungen zum Pendant im Modul abbricht. Dieser könnte diesen Abbruch der Kommunikation als Indiz für das Setzten des Resets im SNES nehmen und somit den Datenaustausch zwischen ROM und SNES unterbinden.
3.6 Diverse Komponenten
Abschließend werden wir noch einen kleinen Überblick über alle nicht angesprochenen Elemente geben. Dies sind u.A. die I/O-Schnittstellen und die ausgebenden Bausteine.
4 Das Modul
Die Spiele für den Super Nintendo wurden in den meisten Fällen auf Modulen sog. Cartridges ausgeliefert (nur ein Bruchteil wurde über ein nur in Japan und Groß-Britannien erhältliches Satellitenmodem veröffentlicht). Die Cartridges beinhalten immer einen ROM und einen CIC Chip. Außerdem können diese einen SRAM und eine Batterie, einen MAD-1 und / oder einen Co-Prozessor enthalten. Diese Komponenten sollen nachfolgend kurz erklärt werden:
Die Verdrahtung dieser Komponenten soll hier nicht weiter behandelt werden, da diese je nach Ausstattung des Moduls unterschiedlich ist.
Lediglich das Pinout soll hier noch behandelt werden. Dieses können Sie der nachfolgenden Abbildung und Tabelle entnehmen.
Die Angaben stammen von zwei Internetseiten, bei denen die Autoren ausdrücklich darauf hinweisen, dass die Angaben aus Dokumentationen übernommen wurden und nicht auf Richtigkeit geprüft wurden. Dennoch gehen wir davon aus, dass zumindest die Pins 5-27 & 36-58 korrekt sind, da diese auf allen von uns gefundenen Quellen identisch waren. Bei den eben nicht genannten Pins (1-4, 28-35 & 59-62) haben wir jedoch nur eine Quelle gefunden, die diese beschreibt. Daher sind diese mit Vorsicht zu betrachten. Die genannten Pins gehören zu den Co-Prozessoren (welche weiter unten behandelt werden) und sind daher nicht in jedem Modul vorhanden (Siehe Abbildung 1 & Abbildung 2).
Abbildung 1: SNES-Cartridge ohne Co-Prozessor (Spiel: "Super R-Type")
Abbildung 2: SNES-Cartridge mit Co-Prozessor (Spiel: "Starwing")
Nun soll noch eine Erklärung zu den Pins 5-27 und 36-58 folgen. Die Pins A0-24 sind die Adressleitungen. Der Super NES kann hier über seinen Bus A die gewünschte Adresse anlegen, um den Inhalt einer Speicherstelle im ROM oder im RAM auszulesen bzw. zu schreiben. Welche Datenquelle bzw. welches Datenziel die CPU auswählt, legt diese mit den Leitungen /RAM Enable bzw. /ROM Enable fest. Über die Pins /READ bzw. /WRITE wird angegeben, in welche Richtung die Daten über die Datenleitungen D0-7 übertragen werden sollen.
Der Pin /IRQ wird zum Senden bzw. Empfangen eines Interrupts verwendet. Die vier CIC-Pins übertragen Daten zum Überprüfen des Kopierschutzes. VCC und GND ist die Spannungsversorgung für das Modul.
Die 24 Adressleitungen unterteilen sich in zwei Bereiche. Über die Leitungen A0-15 wird der Offset und über die Leitungen A16-23 wird die Speicherbank ausgewählt. Auffallend ist, dass über 24 Adressleitungen ein Speicher von max. 128MB bzw. 1024Mbit Byteadressierbar ist. Laut Nintendo ist jedoch die Modulgröße auf max. 8MB bzw. 64Mbit beschränkt. Weshalb es zu einer solchen Einschränkung kommt, ist uns nicht bekannt, soll jedoch hier auch nicht behandelt werden, da dieses Kapitel nur einen kurzen Einblick in das Modul geben sollte.
5 Externe Co-Prozessoren
Da die CPU des SNES mit den max. 3,6MHz recht schwach ist, muss diese für manche Spiele unterstützt werden. Für die ersten Spiele wie „Super Mario World“ reichte die Rechenleistung noch aus. Bei Spielen wie „Starwing“ oder „Super Mario World 2“ welche für damalige Verhältnisse aufwendige Grafiken besaßen, wurden Spezialchips als Co-Prozessoren benötigt. Jedoch waren Grafikberechnungen nicht der einzige Aufgabenbereich solcher Spezialchips. So wurde auch die Berechnung der KI, die Dekompression von Daten aus dem ROM oder auch die Systememulation (Game Boy) auf solche Spezialchips ausgelagert. Ein Teil der möglichen SNES Co-Prozessoren wurde von Nintendo selbst oder von einer von Nintendo beauftragten Firma entwickelt. Meist sind dies universell einsetzbare Co-Prozessoren. Der andere Teil sind herstellerspezifische Eigenentwicklungen. Hierbei handelt es sich meist um Prozessoren, die nur für eine bestimmte Aufgabe entwickelt wurden.
Nachfolgend werden die bekannten von Nintendo entwickelten Spezialchips mit deren Funktion aufgeführt:
Separat von den „offiziellen“ Chips werden nun die herstellerspezifischen Spezialeinheiten aufgeführt:
Diese speziellen Einheiten ersetzen trotz ihrer hohen Leistung nicht die Haupteinheit des SNES, sondern unterstützen diese. Somit wird durch das Einsetzen eines Spielmoduls mit einem solchen Chip das SNES zu einer Multiprozessoreinheit.
5.1 Der SA-1
Der SA-1 Chip ist der leistungsstärkste Spezialchip des SNES. Als Kern dieser Einheit dient die gleiche CPU wie im SNES (WDC65816). Dies macht es leicht, vorhandenen Programmcode auf diesen Prozessor auszulagern. Zudem besitzt der SA-1 noch einige weitere hardwaregestützte Funktionen, welche an entsprechender Stelle in diesem Kapitel behandelt werden.
Die Taktfrequenz dieser Einheit ist um den Faktor 4 höher als die der SNES-CPU im Standard Modus (SNES: 2,68MHz; SA-1: 10,74MHz). Somit ist unter Verwendung dieses Prozessors eine bis zu fünffach höhere Performance des Gesamtsystems möglich.
5.1.1 Speicheranbindung
Gegenüber einem Modul ohne Co-Prozessor bei dem die Adress- und Datenleitungen direkt am RAM und ROM anliegen, werden in diesem Fall die Adressen und Daten an den SA-1 übergeben. Dieser übernimmt dann die Ansteuerung des Speichers. Nachfolgendes Bild soll diesen Aufbau veranschaulichen.
In dieser Darstellung ist nicht erkennbar, dass die SNES CPU auf fast den gesamten Speicher des Moduls zugreifen kann. Lediglich die internen Register des im SA-1 enthaltenen WDC65816 sind der SNES-CPU nicht zugänglich. Der SA-1 hingegen hat selbstverständlich Zugriff auf diese Register, jedoch besitzt diese Einheit keine Möglichkeit Daten, direkt aus dem WRAM des SNES zu beziehen.
Verallgemeinert kann man sagen, dass die SA-1 Einheit auf den gesamten auf dem Modul befindlichen Speicher zugreifen kann, jedoch keinen Zugriff auf den im SNES implementierten Speicher bekommt. Dies ist auch sinnvoll, da die SNES-CPU die Steuereinheit des Gesamtsystems ist und eine Umsetzung eines gemeinsamen Speichers recht aufwändig ist. Als Beispiel hierfür kann man die Multiprozessor-Server-Systeme nennen.
5.1.2 Interner Aufbau
Der interne Aufbau des SA-1 entspricht dem des nachfolgenden Blockschaltbildes. Die einzelnen dort dargestellten Elemente werden nachfolgend erläutert.
Auf die CPU soll hier nicht eingegangen werden, da diese bis auf wenige Unterschiede (Siehe Entwicklerhandbuch 2 Kapitel 1-5-5) die gleiche wie im SNES ist. Informationen zur Arbeitsweise der Einheit entnehmen Sie bitte Kapitel 3.2. Auch beim 2KB bzw. 16Kb großen RAM wird auf eine Erklärung verzichtet, da davon ausgegangen wird, dass die Funktionsweise von RAM bekannt ist. Die „Super NES CPU I/O“ (siehe Abbildung oben) ist an sich keine Einheit sondern lediglich das Pinout, mittels welches der SNES mit dem Modul verbunden ist.
Allen einzelnen Einheiten gemein ist die Konfigurationsart. Sowohl das Einstellen der Einheiten als auch die Kommunikation wird über SFR (Special Function Register) gesteuert. Hierzu stehen eine Vielzahl an Registern zur Verfügung, die aufgrund des Umfangs nicht alle erläutert werden sollen. Eine ausführliche Beschreibung ist dem Entwicklerhandbuch von Nintendo zu entnehmen.
5.1.2.1 Super MMC:
Die Super MMC ist ein Speichercontroller welcher die Ansteuerung des GamePak-Roms übernimmt. Diese Einheit ermöglicht dem SNES ein ROM mit über 32Mb Speicher zu adressieren. Hierzu wird der sog. Map Mode 22 verwendet. Um diesen zu veranschaulichen, sollte zunächst ein Blick auf die Memory-Map des SA-1 geworfen werden (Abbildung unten)
Im linken Bereich der Abbildung befinden sich vier separate Bereiche, welche mit „Game Pak Rom Select“ gekennzeichnet sind (0000H – FFFFH in den Bänken C0H – FFH). Jedes dieser Elemente hat einen Adressbereich, der zum Adressieren von 8Mbit nötig ist. Über spezielle Register, welche anschließend noch genauer beschrieben werden, kann nun angegeben werden, welcher Adressteil des GamePak-Roms mit diesen Bänken dargestellt werden soll. Diese Konfigurationsregister ermöglichen zudem die Zuweisung bestimmter ROM-Adressbereiche in die virtuellen Adressbereiche 00:8000H – 1F:FFFFH, 20:8000H – 3F:FFFFH, 80:8000H – 9F:FFFFH, A0:8000H – BF:FFFFH. Dabei besteht eine spezielle Verknüpfung der Bänke Cx, Dx, Ex, Fx mit den zuvor genannten Adressbereichen. Bank Cx ist dem Bereich 00:8000H – 1F:FFFFH zugewiesen, wohingegen Bank Dx mit dem Bereich 20:8000H – 3F:FFFFH verknüpft ist. Diese Art der Verbindung besteht auch für die übrigen beiden Bänke Ex und Fx.
Welche Adressbereiche des ROMs in diesen Adressraum gelegt werden können, hängt somit vom in der zugehörigen Bank ausgewählten Speicherbereich ab. Entweder es wird der Adressbereich der Bank in den Speicherbereich kopiert oder es wird der Block des ROMs abgelegt, welcher dieselbe Nummer hat wie der Adressbereich (siehe hierzu Abbildung unten). Eine genauere Erklärung folgt weiter unten in diesem Kapitel.
Sowohl der SA-1 als auch die SuperNES CPU können über die in diesen Bereichen dargestellten Speicherbereiche auf den Speicher des ROMs zugreifen.
Wie bereits erwähnt, wird über SFR ausgewählt, welche GamePak-ROM-Bereiche an welcher Stelle in der Memory Map vertreten sind. Ein solches Register ist wie folgt aufgebaut:
Dieses Register gibt an, welche Adressen des Roms in der Bank Cx und im Bereich 00:8000H – 1F:FFFFH dargestellt werden. Die Register für die anderen Bänke besitzen den gleichen Aufbau wie das oben dargestellte.
Die Bits CB0-CB2 geben an, welche 8Mb des ROMs mittels der Bank Cx in der Memory Map angesprochen werden soll. Sollte z.B. der Speicherbereich 40:0000H – 4F:FFFFH in Bank Cx abgelegt werden, so entspricht dies dem fünften Element des ROMs und somit der Bitfolge 100. Nun gibt es noch das Bit, welches mit „CBM“ gekennzeichnet ist. Dieses gibt an, welches Element in den ersten Game Pak ROM Image-Bereich geladen wird (für Bank Dx wäre es das zweite Game Pak ROM Image, beim Ex das Dritte und bei Fx das Vierte). Setzt man das CBM Bit, so ist im entsprechenden Game Pak ROM Image Bereich der gleiche ROM-Bereich abgebildet wie in Bank Cx. Ist das Bit nicht gesetzt, so wird der erste Bereich des ROMs in den ersten Game Pak ROM Image-Bereich gelegt (bei Bank Dx der zweite Teil in den zweiten Bereich und so fort)
Auf die Speicherbänke 40H – 6FH und die BW-RAM Image Bereiche gehen wir nicht näher ein. Lediglich der Verwendungszweck soll hier kurz erklärt werden. Die Bänke 40H-6FH dienen zum Adressieren des Backup-RAMs. Dieser Speicherbereich kann in Blöcke à 64Kb unterteilt werden. Einer dieser Blöcke kann in die BW-RAM Image-Bereiche projiziert werden. Hierbei ist zu beachten, dass der BW-RAM-Image-Bereich in den Bänken 00H – 3FH den identischen Inhalt hat wie der in den Bänken 80H - BFH.
Die weiteren noch nicht besprochenen Bereiche sind nicht im Zusammenhang mit dem Super MMC zu sehen, da dieser nur die Speicherverwaltung zum externen ROM und RAM übernimmt.
5.1.2.2 Arithmetic Circuit
Diese Einheit dient zum schnellen Abarbeiten von arithmetischen Funktionen. Es wird die Multiplikation, die Division und die kumulative Summe unterstützt. Alle Operanten, mit Ausnahme des Divisors, können dabei „signed“ sein.
Gesteuert wird die Einheit durch das Register 2250H, in welchem die Bits ACM und M/D die durchzuführende Operation angeben. Wie diese gesetzt werden können und wie viele Takte (bei einer Taktfrequenz von 10,74MHz) für die Verarbeitung notwendig sind, entnehmen Sie der nachfolgenden Tabelle.
Werte, die diese Einheit verarbeiten soll, müssen dazu in speziellen Registern gesichert werden. Welcher Operand in welches Register eingetragen werden muss, entnehmen Sie bitte dem 2. Entwicklerhandbuch Kapitel 1-7-2 folgende.
5.1.2.3 Character Conversion Circuit
Die CCC dient zum Umwandeln der im BW-RAM oder I-RAM abgelegten Bitmap-Daten in ein PPU-konformes Format. Aufgrund des Aufbaus von Bitmap-Daten können mit diesem Format z.B. Rotationen und Größenanpassungen schneller durchgeführt werden. Jedoch ist die PPU nicht in der Lage, Bitmap-Daten zu verarbeiten. Wie diese Umwandlung durchgeführt wird, entnehmen Sie bitte Kapitel 1-6-1 des 2. Entwicklerhandbuchs.
5.1.2.4 Variable Length Bit Processing Unit
Diese Einheit ist in der Lage, unterschiedlich lange Datensätze aus dem GamePak ROM zu lesen. Aus Sicht dieser Einheit besteht der gesamte ROM-Speicher aus einem Datenstring welcher an beliebiger Stelle gelesen werden kann. So muss nicht mehr Byteweise aus dem Speicher gelesen werden, was zu einem Geschwindigkeitsschub führt. Umgesetzt wird diese Funktion mittels eines Barrel-Shifts.
Die Arbeitsweise dieser Einheit ist in Kapitel 1-8-1 im 2. Entwicklerhandbuch beschrieben.
5.1.2.5 Timer & DMA Circuit
Aufgrund der Tatsache, dass die Funktionsweise dieser Einheiten bekannt sein sollte, verzichten wir an dieser Stelle auf eine Beschreibung. Sollten dennoch Informationen zu diesen Einheiten erwünscht sein, so ziehen sie bitte Kapitel 1-9-1 des zweiten Entwicklerhandbuchs für den DMA-Circuit zu Rate. Das Kapitel der Timer ist leider nicht in dieser Version des Dokuments vorhanden.
5.1.3 Kommunikation mit dem SNES
Der SA-1 ist nicht in der Lage, der SNES-CPU Befehle aufzuzwingen, da das SA-1 System den Slave darstellt. Dennoch muss natürlich eine Kommunikation zwischen beiden Einheiten stattfinden. Dies geschieht über spezielle Register, welche Interrupts auslösen. Hierzu stehen zwei Arten von Interrupts zur Verfügung. Zum einen der normale IRQ sowie der NMI (Not Maskable Interrupt). Letzerer ist nur in eine Richtung möglich. Dem SA-1 ist es nicht möglich, einen NMI an die Konsole zu senden.
Nach dem Empfang eines IRQs versucht der Empfänger anhand eines Registers festzustellen, von welcher Einheit der Request gesendet wurde. Anschließend wird der Request vom Empfänger zurückgesetzt.
Neben den eigentlichen IRQ kann noch eine zusätzliche 4Bit große Nachricht übertragen werden, welche dem Empfänger ermöglicht, auf spezielle Weise auf den Interrupt zu reagieren. Da dies jedoch nicht immer ausreichend ist, können zusätzliche Informationen über dem von beiden Prozessoren erreichbaren I-Ram ausgetauscht werden. Auch der BW-RAM könnte hierfür verwendet werden, jedoch ist dieser während einer Character Conversation nicht zugänglich.
In diesem Zusammenhang soll auch der „Internal Controller“ etwas näher erläutert werden. Aufgabe dieses Elementes ist es, Kollisionen bei Datentransfers zu vermeiden. Dies gilt sowohl für die im SA-1 verbauten Einheiten als auch für die Transfers nach Extern. Sollte die SNES-CPU und ein Element des SA-1 simultan auf den RAM zugreifen wollen, so wird der SNES-CPU Vorrang gewährt.
5.1.4 Operating Modes
Die SA-1 Erweiterung kann in verschiedenen Modi zusammen mit der SNES-CPU arbeiten. Diese Modi werden nicht durch SFR eingestellt, sondern dynamisch von der SNES-CPU gewählt. Allen Modi gemein ist, dass die SA-1 keinen Einfluss auf die Wahl hat. Dieser ist im Master-Slave-System der Slave und führt daher nur die Operationen aus, die diesem zugewiesen wurden.
Folgende 3 Modi stehen zur Wahl:
5.1.4.1 Accelerator Mode
Dieser Modus ist aus Programmierer-Sicht der am einfachsten umzusetzende. Hierbei dient der SNES-CPU nur zum Hochladen der auszuführenden Routinen zum SA-1. Dieser verarbeitet dann die ihm zugeschickten Daten. Während der Verarbeitung im SA-1 wartet der SNES-CPU im Idle-Zustand. Erst sobald die SA-1 per Interrupt an die SNES-CPU signalisiert, dass die Programmroutinen verarbeitet wurden, beginnt die CPU weitere Routinen an den SA-1 zu senden.
Die gesamte Abarbeitung des Programmcodes wird also durch die SA-1-Einheit durchgeführt. Dass die SNES-CPU dabei Untätig ist, macht diesen Modus zum langsamsten von allen.
Nachfolgend ist diese Verarbeitungsmethode dargestellt:
5.1.4.2 Parallel Processing Mode
Bei diesem Modus werden zuvor sequenziell abgearbeitete Programmteile parallel auf den beiden CPUs abgearbeitet. Dieser Modus ist somit schneller als der Accelerator Mode, da auch die SNES-CPU an der Abarbeitung des Programmcodes beteiligt ist. Es können jedoch auch hier Idle-States entstehen, wenn Programmteile auf Ergebnisse von Routinen im anderen Prozessor warten müssen.
6 Programmierung des Systems
6.1 Allgemeiner Aufbau der Instruktionen
Der SNES wird mit einer Variante des Assembler-Befehlscodes programmiert. Diese Variante verfügt über eine große Bandbreite von Befehlen und kann verwendet werden, um alle Bauteile des SNES zu programmieren. Auch die allermeisten SNES-Emulatoren verwenden diesen Befehlscode, allerdings gibt es auch eine Abwandlung von C, die zur Programmierung verwendet werden kann. Wir haben nur die Assembler-Variante verwendet.
Die große Bandbreite von Befehlen von unterschiedlicher Länge lässt vermuten, das es sich um einen CISC-Befehlssatz handelt, sicher lässt sich dies aber für den SNES nicht sagen, da das Produkt des Compilers nicht bekannt ist, sondern nur der geschriebene Code, und wir ausserdem nicht alle Befehle kennen. Der Assembler-Befehlscode verfügt über drei genutzte Register (Akkumulator, X, Y), für die jeweils Lade- und Speicher-Befehle existieren. Weiterhin gibt es Befehle, um Daten von einem ins andere Register zu verschieben. Ein eigener Speicherbefehl speichert den Wert null in einer Speicherzelle. Auch gibt es einer Reihe von Sprungbefehlen, vom einfachen Sprung bis zu Varianten wie ‚bpl „Wert“’ (Branch on Plus, Springe, wenn der Wert „Wert“ positiv ist). Daneben gibt es noch eine ganze Reihe weiterer Befehle, deren Beschreibung hier den Rahmen sprengen würde. Zumal es nicht sicher ist, dass uns alle Befehle bekannt sind, da es nicht möglich war, einen vollständigen Befehlssatz zu finden.
Jeder Befehl kann maximal einen angegebenen Parameter haben, der zweite Parameter ist grundsätzlich durch den Befehl vorgegeben, so überhaupt ein zweiter Parameter nötig ist. Als Beispiel soll hier der Befehl ‚lda’ dienen, der einen Wert in den Akkumulator lädt. Lda lässt sich verschiedentlich laden, so kann man einen Wert direkt angeben, der in den Akku geladen werden soll (lda #$00 , lade den Wert(#) 00 Hex($) in den Akku), oder eine Speicherstelle angeben, deren Wert in den Akku geladen werden soll (lda $2214 , lade den Wert der Speicherstelle 2214 Hex($) in den Akku). Auch kann Registerindirekt adressiert werden (lda $2214,x , lade den Wert in den Akku, der sich in der Speicherstelle befindet, die durch 2214 Hex($) plus den Inhalt des X-Registers(x) adressiert wird). Statt einer 16 Bit-Adresse kann auch eine 24 Bit-Adresse angegeben werden, oder es kann über das Direct-Register adressiert werden.
6.2 Initialisierungsparameter
Um einen SNES emulieren zu können, muss sich ein Emulator auch wie ein solcher verhalten. Daher muss er auch den Initialisierungsalgorithmus abbilden, der im SNES zum Zeitpunkt des Anschaltens abläuft. Hierzu gibt es im Netz zwei Init-Routinen, die einfach in jedes Emulator-Programm eingebunden werden können, und den Emulator auf den Stand setzen, dass er das eigentliche Programm genau so abarbeitet, wie ein echter SNES es tun würde. Die Routinen sind in den Anhängen A und B zu finden, die Inhalte seien hier noch mal kurz erläutert:
header.inc
In der header.inc werden allgemeine Dinge definiert, die teilweise beim echten SNES durch die Hardware schon vorgegeben sind, teilweise von SNES zu SNES variieren können. Allen gemeinsam ist aber, dass sie bei einem SNES immer gleich sind. Am wichtigsten sind hier die Definitionen der ROM-Bänke und der ROM-Startadressen, so dass klar ist, über wie viel Speicher der simulierte ROM verfügt und wo dieser adressiert wird. Als Zusatz lässt sich hier der Name des zu schreibenden Programms definieren.
Snes_Init.asm
Die Snes_Init.asm ist, entgegen der header.inc, keine Header-Datei, sondern beinhaltet ein Makro, welches ein Unterprogramm aufruft. Somit könnte sie auch im eigentlichen Programmcode stehen. Dass sie dennoch ausgegliedert ist, liegt einfach daran, dass der Code sich immer wieder verwenden lässt, und als eigene Datei einfacher einzubinden ist. Der SNES verfügt über nur wenige Register in der CPU, sondern lässt viele wichtige Werte im RAM an eigens dafür vorgesehenen Stellen ablegen. Die Snes_Init.asm schreibt an diese Stellen die benötigten Werte, so dass das Programm mit einem Minimum an Änderungen auskommt, ohne irgendwo undefinierte Werte stehen zu haben. Das wiederum heisst in den meisten Fällen, dass die entsprechenden Speicherstellen mit null initialisiert werden (stz = Store Zero), an einigen Stellen werden aber auch andere Werte geschrieben, so wird der Bildschirm mit „Ausgeschaltet, volle Helligkeit“ initialisiert, damit im Programm hier eine Ausgabe definiert werden kann, und er dann angeschaltet werden kann.
6.3 Entwickeltes Testprogramm
Die Programme wurden in mehreren Zyklen entwickelt, mit dem festen Ziel, am Ende etwas „zum Zeigen“ zu haben. So wurde mit der Informationssuche begonnen, und als erstes ein einfaches Programm entwickelt, welches den Bildschirm einfärbt. Diese Funktion ist auch noch im Soundtest-Programm zu finden. Zu diesem Zeitpunkt lagen die beiden Init-Dateien schon vor, wodurch dieser Schritt sich recht einfach gestaltete. Das Programm tut nicht mehr, als den Bildschirm abzuschalten, die Farbe durch Ändern der entsprechenden Parameter zu wechseln, und den Bildschirm wieder einzuschalten.
Da über den Soundchip und dessen Programmierung am meisten Informationen vorlagen, war das der logische nächste Schritt. Dies gestaltete sich etwas schwieriger, da mit einem anderen Chip, dem Soundchip, kommuniziert werden musste. Da aber der größte Teil der SNES-Programmierung auf diesem Wege abläuft, war das unumgänglich. Der Ablauf war aus en Inormationen ersichtlich: Daten zuerst auf dem ROM, dies sollte im Initialisierungsteil geschehen, da auf dem SNES die Daten auch schon von Anfang an auf dem ROM sind. Dann müssen die Daten auf den RAM der CPU und von da weiter in den RAM des Soundchips. Weiterhin müssen die Header-Informationen vom ROM auf den RAM, und dort in ein kleines Programm verpackt werden, welches das Abspielen der Datei startet. Dieses Programm muss ebenfalls an den Soundchip gesendet werden und dort gestartet werden. Mit entsprechender Initialisierung wird die Musik dann als Endlosschleife abgespielt. Der Quellcode ist in Anhang C zu finden.
Der dritte Schritt war dann die Entwicklung eines kleinen Grafik-Programms. Hierzu lag ein rudimentäres Beispielprogramm vor, welches entsprechend modifiziert werden musste. Die Quelle des Beispielprogramms liegt uns leider nicht mehr vor. Ein Datensatz zum Anzeigen von Buchstaben war ebenfalls gefunden worden. Das Programm wurde in vier einzelnen schritten entwickelt: Anzeigen eines Buchstaben, eines Textes, eines fliessenden Textes, und als letztes, eines in einer Sinuskurve schwingenden Textes, als optisches „Highlight“. Der Aufbau ist immer ähnlich. Zunächst wird der SNES initialisiert, wobei hier noch zusätzliche unterprogramme hinzukommen, die den Grafik-RAM leeren und den Buchstaben-Datensatz hineinkopieren. Dann wird der anzuzeigende Text identifiziert und Zeilenweise angezeigt. Zuletzt wird noch der Bildschirm wieder angeschaltet, und je nach Programm das ganze auf dem Stand angehalten oder immer wieder neu gestartet. Bei einem einzelnen Buchstaben gestaltet sich das recht einfach: Der Buchstabe wird identifiziert und alle Pixel desselben angezeigt. Bei der Zeile ist das schon schwieriger, da jeder Buchstabe einzeln angezeigt werden muss. Bei dem Fliesstext wird nur ein Teil des Textes angezeigt, wobei der angezeigte Teil jeweils nach der Anzeige geändert wird, beim schwingenden Text muss die Anzeige noch mit der Sinuskurve verrechnet werden. Der Quelltext der letzten Variante, des schwingenden Textes, ist in Anhang D zu finden.
6.4 Kompilierung und Test
Geschrieben werden die Programme, aufgrund ihrer Assembler-ähnlichen Programmiersprache, mit jedem denkbaren Texteditor. Es mag spezielle Programme geben, die das Schreiben eines SNES-Programmes erleichtern, doch zumindest waren solche für uns nicht auffindbar. Ein einmal geschriebenes Programm wird dann, sobald fertig und fehlerfrei, in eine Objektdatei kompiliert. Wir haben dazu das WLA DX Macro Assembler Package verwendet, welches neben Compiler und Linker noch eine Textausgabe der gefundenen Fehler anzeigt. Dies ist zum debuggen sehr hilfreich. Wenn die Objektdatei existiert, muss eine Link-Datei erstellt werden, in der alle Objektdateien des aktuellen ROM aufgeführt sind. Diese Datei ist, zumindest bei dem von uns genutzten Linker, notwendig, auch wenn nur eine Objektdatei existiert. Die Objektdatei und die Linkdatei werden dann dem Linker übergeben, der daraus eine smc-Datei macht, die von jedem üblichen SNES-Emulator gelesen werden kann. Wir haben hier den ZSNES-Emulator verwendet. Im Emulator lässt sich jetzt das entsprechende simulierte ROM auswählen und starten. Über die Ausgabe erhält man eine weitere Möglichkeit, den Code zu testen.