Die Abteilung, die mit den größten Schwierigkeiten aufwartet, ist wohl der Kassetten-Manager. Der Grund ist, dass man hier praktisch drei Versionen alleine Amstrad-intern unterscheiden muss:
• Die Abteilungen des Betriebssystems: Der Cassette Manager Der Cassette Manager: Der Cassette Managerder CASSETTE MANAGER Garbage Collection: ... beim CPC 464beim CPC 464,
• Die Abteilungen des Betriebssystems: Der Cassette Manager Der Cassette Manager: Der Cassette Managerder CASSETTE MANAGER bei CPC 664 und CPC 6128 und
• Die Abteilungen des Betriebssystems: AmsdosAmsdos (Amstrad Disc Operating System),
von Disketten-Interfaces anderer Anbieter, wie etwa VDOS von Vortex, ganz zu schweigen.
Kommt noch hinzu, dass auch Einleitung: BASIC Anhang: BasicBasic seine ganz speziellen Probleme mit den Massenspeichern hat.
Sowohl die Disketten- als auch Kassetten-Routinen benötigen für eine Ein- oder Ausgabe-Datei jeweils einen 2 kByte großen Puffer. Den richtet Einleitung: BASIC Anhang: BasicBasic immer über Die Aufteilung des RAM durch den Basic-Interpreter: Chaos über HIMEMHIMEM ein. Weil hier der Speicherplatz aber auch dynamisch an veränderliche Zeichenmatrizen und Maschinencode-Routinen zugeteilt wird, kann es passieren, dass man plötzlich den Anteil der redefinierbaren Zeichenmatrizen nicht mehr verändern kann.
Unangenehmer ist jedoch (zumindest Garbage Collection: ... beim CPC 464beim CPC 464), dass Einleitung: BASIC Anhang: BasicBasic den Puffer nur bei Bedarf einrichtet, und dafür jedesmal eine Strings: Garbage CollectionGarbage Collection im String-Bereich durchführen muss.
Das folgende Programm umgeht das Problem:
100 SYMBOL AFTER 256
110 |TAPE:OPENOUT"
120 MEMORY HIMEM-1
130 CLOSEOUT:|DISC
Hiernach wird der Puffer nicht mehr freigegeben, und auch die Anzahl der Symbol-Matrizen kann wieder frei verändert werden. Wenn Garbage Collection: ... beim CPC 464beim CPC 464 kein Disketten-Kontroller angeschlossen ist, dürfen die beiden RSX-Kommandos |TAPE und |DISC natürlich nicht mit eingegeben werden.
Sehr unpraktisch ist, dass man Garbage Collection: ... beim CPC 464beim CPC 464 das Breaken von Kassetten- und Disketten-Operationen nicht unterbinden kann. Das folgende Programm zeigt, wie man Garbage Collection: ... beim CPC 664 und 6128beim CPC 664 und 6128 jeden Disketten- oder Kassettenfehler und Breaks des Anwenders abfangen kann. Garbage Collection: ... beim CPC 464Beim CPC 464 ist das allerdings vergebene Liebesmüh':
5 |TAPE ' falls gewünscht
10 ON BREAK GOSUB 200 ' Break abfangen
15 ON ERROR GOTO 100 ' Fehlerbedingung abfangen
20 SAVE" ' <---- Bitte mit [ESC] unterbrechen o. AE.
25 PRINT "zeile 25"
30 GOTO 20
99 '
100 PRINT "Der Linien-Algorithmus: Fehler 3Fehler: ";ERR;DERR;" in Zeile ";ERL : RESUME NEXT
199 '
200 PRINT "Break erkannt." : RETURN
Leider hören die Probleme auf der Assembler-Ebene nicht auf. Die Fehlernummern in DERR sind nämlich nicht nur in Einleitung: BASIC Anhang: BasicBasic eingeführt Datenbreite: Wordsworden, sondern auch direkt beim MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCASSETTE MANAGER des CPC 664/6128. Die Abteilungen des Betriebssystems: AmsdosAmsdos kannte sie sowieso schon.
Dadurch sind jetzt Die Abteilungen des Betriebssystems: AmsdosAmsdos und Die Abteilungen des Betriebssystems: Der Cassette Manager Der Cassette Manager: Der Cassette Managerder CASSETTE MANAGER Garbage Collection: ... beim CPC 464beim CPC 664/6128 einander noch ähnlicher, als das schon Garbage Collection: ... beim CPC 464beim CPC 464 der Fall war. Dafür gibt es jetzt zwischen Die Abteilungen des Betriebssystems: Der Cassette Manager Der Cassette Manager: Der Cassette Managerdem CASSETTE MANAGER des CPC 464 und dem der 6er-Typen Kompatibilitäts-Probleme.
Der Fehler-Status von Grundlagen: UnterprogrammeUnterprogrammen wird beim Schneider CPC gewöhnlich im Carry-Flag zurückgemeldet, wobei ein gesetztes CY-Flag bedeutet, dass die Die Fließkomma-Routinen: OperationenOperation erfolgreich abgeschlossen wurde. So ist es auch bei den Kassetten- und Disketten-Routinen. Eine Ausnahme bildet nur der Katalog-Vektor.
Tritt aber ein Der Linien-Algorithmus: Fehler 3Fehler auf, so fangen die Probleme an:
Die Top-Level-Routinen können, bis auf CASSETTE MANAGER: BC92: CAS OUT ABANDONCAS OUT ABANDON und CASSETTE MANAGER: BC7D: CAS IN ABANDONCAS IN ABANDON, einen Der Linien-Algorithmus: Fehler 3Fehler zurückmelden. Dabei gibt es zum Teil erhebliche Unterschiede zwischen CAS-464, CAS-664/6128 und Die Abteilungen des Betriebssystems: AmsdosAmsdos.
Die Kassetten-Operationen können gebreakt werden. Das wird Garbage Collection: ... beim CPC 464beim CPC 464 laut Firmware-Manual mit CY=0 und Z=1 vermerkt, bei CPC 664 und 6128 mit dem Fehlercode 0 im A-Register. Trotzdem scheinen beide glücklicherweise gleich zu arbeiten:
CAS-464, CAS-664/6128: CY=0 und Z=1 und Operationen: BD5B / 349A / 349A: FLO SUBA=0 --> Break
Disketten-Operationen können nicht unterbrochen werden.
Alle andern Der Linien-Algorithmus: Fehler 3Fehler werden bei den Kassetten-Routinen immer mit CY=0 und Z=0 angemerkt. Der CPC 664/6128 gibt in Operationen: BD5B / 349A / 349A: FLO SUBA zusätzlich aber immer noch einen Fehler-Code aus.
Die Abteilungen des Betriebssystems: AmsdosAmsdos kennt noch mehr Der Linien-Algorithmus: Fehler 3Fehler, die auch mit CY=0 gemeldet werden. Die Fehlerbedingungen "EOF", "Datei nicht eröffnet" bzw. "Bereits eine Datei eröffnet" werden wie bei den Kassetten-Routinen mit Z=0 gemeldet, die anderen aber mit Z=1, was beim Kassettenbetrieb der Break-Meldung entspricht.
Die folgende Tabelle enthält eine Aufstellung der möglichen Fehler-Kodierungen, wie sie ganz allgemein bei MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS 464, MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS 664/6128 und Die Abteilungen des Betriebssystems: AmsdosAmsdos auftreten können:
Zero- | Fehlernummer | Bedeutung (Operationen: BD5B / 349A / 349A: FLO SUBA=Die Abteilungen des Betriebssystems: AmsdosAmsdos, 4=MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS 464, 6=CAS664/6128)
Die Z80: Wirkung der Z80-Befehle auf die FlagsFlag | im Akku |
------+--------------+-----+----------------------------------------------------
Z=1 | 0 | 4 6 | Break
Z=0 | 1...5 | 4 | End of File oder Datei nicht eröffnet
| | | oder bereits eine Datei eröffnet.
Z=0 | 14 | Operationen: BD5B / 349A / 349A: FLO SUBA 6 | Datei nicht eröffnet bzw.
| | | bereits eine Datei eröffnet.
Z=0 | 15 | Operationen: BD5B / 349A / 349A: FLO SUBA 6 | End of File (hard end).
Z=0 | 26 | Operationen: BD5B / 349A / 349A: FLO SUBA | End of File (soft end).
| | |
Z=1 | 32 | Operationen: BD5B / 349A / 349A: FLO SUBA | unbekannter Befehl, Die Z80: Illegalsillegaler Dateiname.
Z=1 | 33 | Operationen: BD5B / 349A / 349A: FLO SUBA | Datei existiert bereits.
Z=1 | 34 | Operationen: BD5B / 349A / 349A: FLO SUBA | Datei existiert nicht.
Z=1 | 35 | Operationen: BD5B / 349A / 349A: FLO SUBA | Inhaltsverzeichnis ist voll.
Z=1 | 36 | Operationen: BD5B / 349A / 349A: FLO SUBA | Diskette ist voll.
Z=1 | 37 | Operationen: BD5B / 349A / 349A: FLO SUBA | Diskette wurde bei offener Datei gewechselt.
Z=1 | 38 | Operationen: BD5B / 349A / 349A: FLO SUBA | Datei ist schreibgeschützt.
Z=1 |Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 6 gesetzt:| Operationen: BD5B / 349A / 349A: FLO SUBA | Amsdos-Fehlercodes: FDC-Fehler:FDC-Fehler.
Z=1 |Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 7 gesetzt:| Operationen: BD5B / 349A / 349A: FLO SUBA | Der Linien-Algorithmus: Fehler 3Fehler wurde dem Anwender bereits mitgeteilt.
------+--------------+-----+----------------------------------------------------
Amsdos-Fehlercodes: FDC-Fehler:FDC-Fehler: Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 6 (&40) ist gesetzt. Die folgenden Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bits bedeuten: --------------------------------------------------------------------------------
&01 1 - ID- oder Data-Adress-Marke fehlt (Diskette ist nicht formatiert)
&02 2 - Diskette ist schreibgeschützt (Schreibschutzkerbe ist geöffnet)
&04 4 - Sektor nicht auffindbar (falsches Disketten-Format eingeloggt)
&08 8 - Laufwerk ist nicht bereit (Diskette nicht/nicht richtig drin)
&10 16 - Puffer-Überlauf (dürfte nie vorkommen)
&20 32 - Kontrollsummen-Fehler (Diskette möglicherweise beschädigt) --------------------------------------------------------------------------------
Die Fehler-Rückmeldung bei MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT weicht stark von diesem allgemeinen Muster ab.
Der Der Cassette Manager: KatalogKatalog von Kassette muss gebreakt werden, weil er sonst bis zum Sankt-Nimmerleinstag andauert. Trotzdem wird das nicht als Der Linien-Algorithmus: Fehler 3Fehler mit CY=0 angemerkt. Im Gegensatz dazu muss ein Der Cassette Manager: KatalogKatalog von Diskette nicht gebreakt werden. Dafür merkt aber jetzt Die Abteilungen des Betriebssystems: AmsdosAmsdos einen Der Linien-Algorithmus: Fehler 3Fehler an! Möglicherweise wollte man damit zum Kassetten-Katalog kompatibel sein und nahm für dessen Return-Bedingung (fälschlicherweise) das Standard-Verhalten "Break = Der Linien-Algorithmus: Fehler 3Fehler <--> CY = 0" an.
MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT 464: CY=1
MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT 664/6128: CY=1
DISC CAT o.k.: CY=0 und Z=0
MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT 464: CY=0, Z=0, Operationen: BD5B / 349A / 349A: FLO SUBA=1 (1...5)
MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT 664/6128: CY=0, Z=0, Operationen: BD5B / 349A / 349A: FLO SUBA=14 = Fehlercode
DISC CAT: geht! Der Strom wird vorher geschlossen.
MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCAS CAT: Lesefehler werden im Der Cassette Manager: KatalogKatalog vermerkt und führen nicht zum Abbruch.
DISC CAT: CY=0, Z=1, Operationen: BD5B / 349A / 349A: FLO SUBA=Fehlercode
Die Abteilungen des Betriebssystems: AmsdosAmsdos ist so aufgebaut, dass von der Amsdos: Datei-VerwaltungDatei-Verwaltung her kaum ein Unterschied zum Kassetten-Manager festzustellen ist. Das ist zwar einerseits ein Vorteil, weil so die Kompatibilität erhalten blieb, leider aber ein Nachteil für all diejenigen, die ihrer Einleitung: MassenspeicherFloppy etwas dichter auf die Scheibe rücken wollen. So ist von Einleitung: BASIC Anhang: BasicBasic aus kein direkter Zugriff auf einzelne Sektoren möglich und auch Adressierungsarten der Z80: Relativrelative Dateien mit direktem Schreib/Lese-Zugriff auf einzelne Datensätze wurden nicht implementiert.
Zur gleichen Zeit kann nur eine Datei für Eingabe (Lesen) und eine für Ausgabe (Schreiben) geöffnet werden. Für jede Datei wird ein Puffer von 2 kByte im RAM benötigt.
Das 'Handling' ist dabei weitgehend unabhängig davon, ob man eine Ein- oder Ausgabe-Datei vor sich hat, auf Kassette oder Diskette arbeitet oder in Einleitung: BASIC Anhang: BasicBasic oder Assembler programmiert:
• Zunächst muss die Datei eröffnet werden, wofür man den Puffer einrichten
und den Datei-Namen übergeben muss.
• Dann kann in der Datei gearbeitet werden: Entweder liest (oder schreibt) man
zeichenweise (das ist in Einleitung: BASIC Anhang: BasicBasic bei OPENIN, OPENOUT und SAVE "basicprog",Operationen: BD5B / 349A / 349A: FLO SUBa der
Fall), oder 'en Die Speicherkonfiguration im Schneider CPC: Blockblock', also die ganze Datei auf einmal. Das geht natürlich
schneller. Mischen der beiden Möglichkeiten ist aber nicht erlaubt.
• Zum Schluss muss die Datei wieder geschlossen werden.
Bei der Bearbeitung von Disketten-Dateien von Maschinencode aus muss man zusätzlich noch selbst darauf achten, dass die Diskette eingeloggt ist. Die Abteilungen des Betriebssystems: AmsdosAmsdos legt in seinem System-RAM nämlich einen 'Low Level Disc Driving: &82 Drive ParameterDrive Parameter Die Speicherkonfiguration im Schneider CPC: BlockBlock' an, in dem die wichtigsten Formatierungs-Parameter gespeichert sind. Bezieht sich diese Tabelle beispielsweise noch auf eine Diskette im Daten-Format, wenn eine CP/M-Disk eingelegt wird, so kann Die Abteilungen des Betriebssystems: AmsdosAmsdos diese Diskette nicht beschreiben oder lesen!
Am einfachsten geschieht dies durch Aufruf des RSX-Kommandos |Operationen: BD5B / 349A / 349A: FLO SUBA oder |LOW KERNEL JUMPBLOCK: 000B: LOW KL LOW PCHL LOW KERNEL JUMPBLOCK: 001B: LOW KL FAR PCHL LOW KERNEL JUMPBLOCK: 003B: LOW EXT INTERRUPTB.
Nicht nur Garbage Collection: ... beim CPC 464beim CPC 464, auch bei den 6er-Typen sind die Kassetten-Routinen vollständig im Erläuterung zu den Anschlüssen 40 bis 45: 42 - ROMEN (0)ROM des Betriebsytems enthalten. Ist auch Die Abteilungen des Betriebssystems: AmsdosAmsdos present, so muss man Die Abteilungen des Betriebssystems: AmsdosAmsdos nur mit |TAPE, |TAPE.IN oder |TAPE.OUT ausblenden.
Die Kassetten-Routinen geben bei Bedarf Dialog-Texte aus. So zum Beispiel, wenn eine Datei eröffnet wird, um den Kassetten-Rekorder zu starten. Diese Meldungen können aber auch unterdrückt werden. Dazu muss man den Vektor CASSETTE MANAGER: BC6B: CAS NOISYCAS NOISY aufrufen, und im A-Register ein entsprechendes Die Z80: Wirkung der Z80-Befehle auf die FlagsFlag übergeben. Einleitung: BASIC Anhang: BasicBasic schaltet normalerweise diese System-Meldungen ein. Wenn man aber einen Dateinamen übergibt, der mit einem Ausrufe-Zeichen "!" anfängt, so werden die Meldungen von Einleitung: BASIC Anhang: BasicBasic ausgeschaltet.
Nicht von dieser Regelung betroffen sind die Fehler-Meldungen:
"Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: RD und WR - read und write Erklärung zu den Anschluss-Bezeichnungen: RD - ReadRead error Operationen: BD5B / 349A / 349A: FLO SUBa" - Lesefehler (unmöglich lange Periode gelesen).
"Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: RD und WR - read und write Erklärung zu den Anschluss-Bezeichnungen: RD - ReadRead error LOW KERNEL JUMPBLOCK: 000B: LOW KL LOW PCHL LOW KERNEL JUMPBLOCK: 001B: LOW KL FAR PCHL LOW KERNEL JUMPBLOCK: 003B: LOW EXT INTERRUPTb" - Checksummen-Fehler.
"Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: RD und WR - read und write Erklärung zu den Anschluss-Bezeichnungen: RD - ReadRead error c" - Verify-Fehler.
"Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: RD und WR - read und write Erklärung zu den Anschluss-Bezeichnungen: RD - ReadRead error d" - Die Speicherkonfiguration im Schneider CPC: BlockBlock länger als 2kBytes.
"Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: RD und WR - read und write Erklärung zu den Anschluss-Bezeichnungen: WR - WriteWrite error Operationen: BD5B / 349A / 349A: FLO SUBa" - geforderte Der Sound Manager: PeriodenlängePeriodenlänge ist zusammen mit der angegebenen
Precompensation zu kurz.
und die Aufforderung, einen Ladeversuch zu wiederholen:
"Rewind tape"
Es ist möglich, gleichzeitig eine Ein- und eine Ausgabe-Datei eröffnet zu haben. Da dann mit zwei verschiedenen Kassetten gearbeitet werden muss, die, jenachdem, ob gerade wieder ein Die Speicherkonfiguration im Schneider CPC: BlockBlock geladen oder gespeichert werden soll, vom Anwender ausgetauscht werden müssen, sollte man hier immer mit eingeschalteten Meldungen arbeiten.
Jede Datei, die vom MAIN FIRMWARE JUMPBLOCK: CASSETTE MANAGER Die Firmware des Schneider CPC: CASSETTE MANAGERCASSETTE MANAGER auf Kassette geschrieben wird, wird von ihm in jeweils höchstens 2 kByte lange Bloecke unterteilt.
Jeder Die Speicherkonfiguration im Schneider CPC: BlockBlock setzt sich dabei aus zwei 'Datenspeicherung und Datenstrukturen: RecordsRecords' zusammen: Ein 'Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecord' und ein 'Data Datenspeicherung und Datenstrukturen: RecordsRecord'.
Der Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecord enthält 64 Datentypen: Bytes Datenbreite: BytesBytes Informationen über den folgenden Data Datenspeicherung und Datenstrukturen: RecordsRecord, der 1 bis 2048 Datentypen: Bytes Datenbreite: BytesBytes lang sein kann, und die Daten dieses Die Speicherkonfiguration im Schneider CPC: BlockBlocks enthält.
Datentypen: Bytes Datenbreite: BytesByte 00 bis 15: File-Name.
Datentypen: Bytes Datenbreite: BytesByte 16: Block-Nummer (von 1 bis ...).
Datentypen: Bytes Datenbreite: BytesByte 17: Die Z80: Wirkung der Z80-Befehle auf die FlagsFlag für den letzten Die Speicherkonfiguration im Schneider CPC: BlockBlock einer Datei ( <>0 -> letzter Die Speicherkonfiguration im Schneider CPC: BlockBlock).
Datentypen: Bytes Datenbreite: BytesByte 18: Header und Data Record: Datei-Typ:Datei-Typ (siehe unten).
Datentypen: Bytes Datenbreite: BytesByte 19 und 20: Länge des Data Datenspeicherung und Datenstrukturen: RecordsRecords in Datentypen: Bytes Datenbreite: BytesBytes.
Datentypen: Bytes Datenbreite: BytesByte 21 und 22: Quell-Adresse des Data Datenspeicherung und Datenstrukturen: RecordsRecords
Datentypen: Bytes Datenbreite: BytesByte 23: Die Z80: Wirkung der Z80-Befehle auf die FlagsFlag für den ersten Die Speicherkonfiguration im Schneider CPC: BlockBlock einer Datei ( <>0 -> erster Die Speicherkonfiguration im Schneider CPC: BlockBlock).
Datentypen: Bytes Datenbreite: BytesByte 24 und 25: Gesamt-Länge der Datei.
Datentypen: Bytes Datenbreite: BytesByte 26 und 27: Startadresse (für Maschinencode-Routinen).
Datentypen: Bytes Datenbreite: BytesByte 28 bis 63: Unbenutzt.
Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 0: Die Z80: Wirkung der Z80-Befehle auf die FlagsFlag für geschützte Dateien ( <>0 -> geschützt).
Port C - Output: &F6xx: Bits 0 bis 3:Bit 1 bis 3: Header und Data Record: Datei-Typ:Datei-Typ: 0 - Basic-Programm in der internen Darstellung.
1 - Speicherabzug (Maschinencode o. AE.)
2 - Bildschirm-Abzug.
3 - ASCII-Datei.
4 bis 7: nicht definiert.
Port C - Output: &F6xx: Bits 0 bis 3:Bit 4 bis 7: 'Version': Normalerweise immer 0. Nur ASCII-Dateien 1.
Wird eine Datei für Ausgabe eröffnet, so gibt der Vektor CASSETTE MANAGER: BC8C: CAS OUT OPENCAS OUT OPEN die Adresse des Header-Puffers zurück. Man kann dann den File-Typ, Gesamtlänge und Startadresse beschreiben. Der Typ wird aber schon vorab auf ASCII eingestellt. Soll also eine ASCII-Datei eröffnet werden, muss man in der Regel nichts mehr in den Amsdos: HeaderHeader eintragen (Die Länge ist wahrscheinlich noch unbekannt und eine Startadresse gibt es auch nicht).
In die unbenutzten Datentypen: Bytes Datenbreite: BytesBytes von 28 bis 63 kann das Programm eintragen, was ihm Spass macht. Dieser Bereich wird nur jedesmal, wenn eine neue Output-Datei eröffnet wird, standardmäßig mit Real: NullNullen beschrieben.
Wird eine Eingabe-Datei eröffnet, so wird normalerweise so lange von der Kassette gelesen, bis der erste Die Speicherkonfiguration im Schneider CPC: BlockBlock der Datei mit dem angegebenen Namen gefunden wird. Dann steht der Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecord des ersten Die Speicherkonfiguration im Schneider CPC: BlockBlocks dem Hauptprogramm sofort zur Verfügung. Gibt man jedoch einen Namen an, der entweder Real: Nullnull Zeichen lang ist, oder mit einem Nullbyte anfängt, so eröffnet Die Abteilungen des Betriebssystems: Der Cassette Manager Der Cassette Manager: Der Cassette Managerder CASSETTE MANAGER die erste Datei, die er finden kann.
Bei diesem normalen File-Handling handelt es sich um die oberste Ebene des CASSETTE MANAGERs. Man kann aber auch eine Ebene tiefer zugreifen:
Die Vektoren CASSETTE MANAGER: BC9E: CAS WRITECAS WRITE, CASSETTE MANAGER: BCA1: CAS READCAS READ und CASSETTE MANAGER: BCA4: CAS CHECKCAS CHECK können benutzt werden, um Dateien in einem eigenen Amsdos: FormateFormat auf der Kassette abzuspeichern. Dabei steht neben den 'normalen' Die Fließkomma-Routinen: FunktionenFunktionen 'Speichern' und 'Laden' noch eine dritte bereit, mit der man Daten auf der Kassette mit dem Inhalt des Speichers im Computer vergleichen kann. Damit kann man gerade abgespeicherte Dateien auf Der Linien-Algorithmus: Fehler 3Fehler überprüfen.
Diese Vektoren speichern immer einen 'Datenspeicherung und Datenstrukturen: RecordsRecord'. Die High Level-Routinen rufen jeweils zum Lesen (Speichern) des Amsdos: HeaderHeader- und des Data Datenspeicherung und Datenstrukturen: RecordsRecords zwei mal die entsprechende Low Level Routine auf. Die Länge eines Datenspeicherung und Datenstrukturen: RecordsRecords ist dabei nicht festgelegt, sondern kann jeden beliebigen Betrag von einem Datentypen: Bytes Datenbreite: BytesByte bis zu 65536 Stück annehmen.
Jeder Datenspeicherung und Datenstrukturen: RecordsRecord erhält beim Speichern auf Kassette eine Kennung, ein Der Cassette Manager: Synchronisations-ZeichenSynchronisations-Zeichen. Soll ein Datenspeicherung und Datenstrukturen: RecordsRecord wieder gelesen werden, so muss man dieses Zeichen angeben. Nur Datenspeicherung und Datenstrukturen: RecordsRecords mit diesem Zeichen werden erkannt und eingeladen.
Die High Level Routinen benutzen das, um den Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecord vom Data Datenspeicherung und Datenstrukturen: RecordsRecord zu unterscheiden:
Synchron-Zeichen: Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecord: &2C
Data Datenspeicherung und Datenstrukturen: RecordsRecord: &16
Jeder Datenspeicherung und Datenstrukturen: RecordsRecord wird auf der Kassette als ein Bit-Strom aufgezeichnet. Das heißt, auf der Kassette gibt es keine physikalische Trennung der einzelnen Datentypen: Bytes Datenbreite: BytesBytes, Checksummen, Der Cassette Manager: Synchronisations-ZeichenSynchronisations-Zeichen o. AE..
Jedes Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit wird als eine Periode eines Rechteck-Signals gespeichert. Ein Rechteck-Signal deshalb, weil die Ausgabe nicht analog sondern digital über ein Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit der Die ICs im Überblick: Die PIO 8255 Das Innenleben der CPC-Rechner: Die PIO 8255 Speicher und Peripherie: Die PIO 8255 Die Anschlussbelegungen der wichtigsten ICs im CPC: Die PIO 8255PIO erfolgt. Für jedes Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit wird also eine bestimmte Zeit der Datenausgang mit Real: NullNull und dann mit Eins programmiert.
Dabei ist die Länge des Real: NullNull- und Eins-Pegels (normalerweise) identisch. Ein Real: NullNull- und ein Eins-Bit unterscheiden sich in der Länge ihrer Periode: Eins-Bits werden mit der doppelten Der Sound Manager: PeriodenlängePeriodenlänge abgespeichert. Das 'Timing' wird dabei mit Hilfe des Refresh-Registers der Die ICs im Überblick: Die CPU Z80 Das Innenleben der CPC-Rechner: Die CPU Z80 Die Anschlussbelegungen der wichtigsten ICs im CPC: Die CPU Z80Z80 realisiert. Bei jedem Befehlshol-Zyklus wird dieses Die Tonausgabe: Das Kontrollregister (Reg. 7) Die Tonausgabe: Die möglichen Hüllkurvenformen (Reg. 13)Register erhöht, so dass man hiermit die Anzahl der Befehle zählen kann, die zwischen zwei Flanken des Rechteck-Signals abgearbeitet wurden.
Daraus ergibt sich auch, dass die Angaben über die Speichergeschwindigkeit, die 'Baud-Rate', nur ein Mittelwert sein kann und nur für Dateien zutrifft, die gleich viele Real: NullNull- und Eins-Bits enthalten. Man kann also die Speicherung von Daten auf Kassette beschleunigen, indem man Dateien, die besonders viele Eins-Bits enthalten, einfach 'invertiert' abspeichert.
Pegel^ +-------+ +---+ +---+
| | | | | | |
| | | | | | | |
| +-------+ +---+ +---+
----+------------------------------------------------->
| <---- Eins ----><-Null-><-Null-> zeit
Die analoge Verstärker-Elektronik eines Kassetten-Rekorders neigt dazu, hohe Frequenzen zu unterdrücken. Ein ideales Rechteck-Signal hat aber Oberwellen praktisch beliebig hoher Frequenz. Es kommt deshalb zu einer Verrundung des gespeicherten Signals.
Am schlimmsten sind davon die Übergänge von einer kurzen zu einer langen Periode und umgekehrt betroffen, wie es immer bei aufeinanderfolgenden Einsen und Real: NullNullen auftritt. Das führt dazu, dass sich der Übergang vom High- zum Low-Pegel so verschiebt, dass der Unterschied zwischen der langen und der kurzen Periode geringer wird. Einsen und Real: NullNullen werden schlechter unterscheidbar.
Die Speicher-Software arbeitet deshalb mit einer Vor-Kompensation, die bei Eins-Null-Übergängen die kurze Periode noch ein wenig kürzer und die lange ein wenig länger macht, so dass sie dann beim Einladen möglichst die korrekte Länge haben.
Bei der Programmierung der Speicher-Geschwindigkeit mit dem Vektor CASSETTE MANAGER: BC68: CAS SET SPEEDCAS SET SPEED muss man deshalb nicht nur die Länge einer halben Null-Periode sondern auch die Länge dieser Vor-Kompensation angeben.
Ein weiteres Phaenomen tritt bevorzugt dann auf, wenn man einen externen Kassetten-Rekorder anschließt: Es kann passieren, dass das Eingangs-Signal invertiert ist. Das heißt, wo ein Eins-Pegel gespeichert wurde, wird ein Null-Pegel eingelesen, und umgekehrt.
Das muss auf jeden Fall erkannt werden, damit auch immer zwei Perioden-Hälften, die zum selben Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit gehören, gemessen werden. Würde die Inversion nicht erkannt, so würde immer ein eine Halb-Periode des vorhergehenden Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bits mit einer Halbperiode des folgenden zusammen genommen, wodurch die gemessenen Zeiten prima gemittelt werden. Leider lassen sie sich dann nicht mehr unterscheiden:
gespeichert: <---- Eins ----><-Null-><-Null->
Pegel ^ +-------+ +---+ +---+ +-------+
| | | | | | | | |
| | | | | | | | |
| +---+ +-------+ +---+ +---+
------+------------------------------------------------------------>
gelesen: <----??----><----??----><-Null-><----??----> Zeit
Gegliedert ist ein Datenspeicherung und Datenstrukturen: RecordsRecord in mehrere Abschnitte: Zunächst einmal kommen &800 = 2048 Eins-Bits, die zur Synchronisation dienen. Normalerweise braucht man dafür aber weit weniger Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bits. Beim Schneider CPC bestimmt die Lade-Routine aber nach 256 gelesenen Perioden, mit welcher Geschwindigkeit dieser Datenspeicherung und Datenstrukturen: RecordsRecord gespeichert wurde, und stellt sich automatisch darauf ein.
Danach kommt ein einzelnes Null-Bit, das das Ende des Synchronisations-Vorspanns anzeigt. Daran, dass dieses Null-Bit mit einer kurzen Periode auf Null-Pegel oder Eins-Pegel anfing, kann man erkennen, ob das Signal invertiert ist oder nicht.
Das erste Datentypen: Bytes Datenbreite: BytesByte danach ist das Der Cassette Manager: Synchronisations-ZeichenSynchronisations-Zeichen, das beim Speichern und Laden immer angegeben werden muss. Alle Datentypen: Bytes Datenbreite: BytesBytes werden mit Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 7 zuerst abgespeichert. Die Lade-Routine überprüft, ob das Sync-Byte übereinstimmt, und setzt nur dann den Lade-Versuch fort. Stimmt das Zeichen nicht, so hat die Routine entweder versucht, sich auf eine zufällige Serie aus lauter Einsbits zu synchronisieren, oder es handelt sich um einen Datenspeicherung und Datenstrukturen: RecordsRecord vom falschen Typ (Beispielsweise ein Data Datenspeicherung und Datenstrukturen: RecordsRecord, statt eines zu suchenden Amsdos: HeaderHeader Datenspeicherung und Datenstrukturen: RecordsRecords).
Erst danach kommen die eigentlichen Daten, oder auch Header-Informationen, oder wie sie auch immer interpretiert werden. Diese sind, unabhängig von der gespeicherten Anzahl Datentypen: Bytes Datenbreite: BytesBytes, immer in 256-Byte-Abschnitte gegliedert. Nach jedem Abschnitt folgen zwei Datentypen: Bytes Datenbreite: BytesBytes mit einer Prüfsumme, die nach dem CRC-Verfahren gebildet wird.
Sollen beispielsweise 600 Datentypen: Bytes Datenbreite: BytesBytes aus dem RAM gespeichert werden, so ist der Datenteil 3 Abschnitte lang. Der letzte wird mit 3*256-600 = 168 Nullbytes aufgefüllt. Nach dem letzten Abschnitt folgt noch ein Schwanz aus 32 Eins-Bits, die vor allem dazu dienen, dass die letzten Datenbytes ohne Verzerrungen abgespeichert werden.
Zur praktischen Anwendung dieser Routinen ist die Kenntnis, wie die einzelnen Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bits nun zu Papier (bzw. Magnetband) gebracht werden, natürlich vollkommen uninteressant. Wer aber vielleicht selbst einmal solche Routinen schreiben will, als Kopierschutz, oder weil ihm diese zu langsam sind, der sieht hieran immerhin, wie es prinzipiell funktionieren muss.
Auch unter Einleitung: BASIC Anhang: BasicBasic kann es sehr interessant sein, auf die Kassetten-Routinen der untersten Ebene zuzugreifen, weil man hier beliebig lange Datenspeicherung und Datenstrukturen: RecordsRecords abspeichern kann. Damit kann man die Speicher- und Ladezeit verkürzen, ohne mit höheren (und damit unsichereren) Baudraten arbeiten zu müssen.
Das folgende Assembler-Programm bindet einige RSX-Befehle ein, mit denen man beliebige Speicherbereiche speichern, laden und auch überprüfen kann. Außerdem kann man mit |SET.SPEED jede (mögliche) Speichergeschwindigkeit einstellen, und die Praecompensation dem eigenen Einleitung: MassenspeicherKassettenrekorder anpassen.
Die Fehlernummern, die die Kassetten-Routinen zurückmelden können, werden zwischengespeichert, und lassen sich anschließend mit |ERROR,@f% abfragen. Dabei dient der Wert &FF als Kennung für eine ordnungsgemaesse Ausführung.
Ein zusätzlicher Fehlercode ist &Der Zeichensatz des Schneider CPC: &A0 = 160A0 (=&80 + 32), der Amsdos-kompatibel gewählt wurde: Code 32 heißt "unbekannter Befehl", was in diesem Zusammenhang auf eine falsche Parameter-Anzahl hindeuten soll. Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 7 ist gesetzt, weil der Der Linien-Algorithmus: Fehler 3Fehler dem Anwender bereits mitgeteilt wurde. Zum Beispiel so:
USE: |ERROR,@Die Z80: Wirkung der Z80-Befehle auf die Flagsflag%
; Low Level-Routinen via Maschinencode über HIMEM: RSXRSX Erklärung zu den Anschlüssen: Vcc und Vss Erklärung zu den Anschluss-Bezeichnungen: Vcc und Vssvs.26.5.86 (c) G.Woigk
; -------------------------- ---------- -----------
;
ORG 40000
;
; Deklarationen
;
MOTON: EQU #BC6E ; CASSETTE MANAGER: BC6E: CAS START MOTORCAS START MOTOR
MOTOFF: EQU #BC71 ; CASSETTE MANAGER: BC71: CAS STOP MOTORCAS STOP MOTOR
LOAD: EQU #BCA1 ; CASSETTE MANAGER: BCA1: CAS READCAS READ
SAVE: EQU #BC9E ; CASSETTE MANAGER: BC9E: CAS WRITECAS WRITE
VERIFY: EQU #BCA4 ; CASSETTE MANAGER: BCA4: CAS CHECKCAS CHECK
SPEED: EQU #BC68 ; CASSETTE MANAGER: BC68: CAS SET SPEEDCAS SET SPEED
PCBC: EQU #000E ; LOW MAIN FIRMWARE JUMPBLOCK: KERNEL Die Firmware des Schneider CPC: KERNELKL JP(BC) INSTRUCTION
INTRO: EQU #BCD1 ; KERNEL: BCD1: KL LOG EXTKL LOG EXT
PRINT: EQU #BB5A ; TEXT VDU: BB5A: TXT OUTPUTTXT OUTPUT
;
; Initialisieren
;
INIT: LD HL,SPACE ; Zeiger auf 4 Datentypen: Bytes Datenbreite: BytesByte Platz für verkettete Trees: ListenListe.
LD BC,TABEL ; Zeiger auf Tabelle externer Kommandos.
JP INTRO ; RSX-Paket in's Betriebsystem einbinden.
;
SPACE: DEFS 4 ; Platz für Hangelpointer
;
TABEL: DEFW BCD1: KL LOG EXT: 2. Namenstabelle (NAMTAB)NAMTAB ; Zeiger --> Namenstabelle
JP BSPEED ; |SET.SPEED
JP BLOAD ; |LOAD
JP BSAVE ; |SAVE
JP BVERI ; |VERIFY
JP BERROR ; |ERROR
;
BCD1: KL LOG EXT: 2. Namenstabelle (NAMTAB)NAMTAB: DEFB "S","LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE","T",".","S","P","LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE","LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE","D"+#80
DEFB "L","O","Operationen: BD5B / 349A / 349A: FLO SUBA","D"+#80
DEFB "S","Operationen: BD5B / 349A / 349A: FLO SUBA","V","LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE"+#80
DEFB "V","LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE","R","I","F","Y"+#80
DEFB "LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE","R","R","O","R"+#80
DEFB 0
;
; Fehlermeldungen:
;
MSPEED: DEFM "SET.SPEED, periode, praecomp"
DEFB 0
MLOAD: DEFM "LOAD"
DEFB 0
MSAVE: DEFM "SAVE"
DEFB 0
MVERI: DEFM "VERIFY"
DEFB 0
MERROR: DEFM "ERROR, @Die Z80: Wirkung der Z80-Befehle auf die Flagsflag%"
DEFB 0
MLSV: DEFM ", sync, adresse, länge"
DEFB 0
;
Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: M1 - Machine Cycle OneM1: DEFB 13,18,10 ; Zeile löschen und eine Zeile tiefer.
DEFM " USE: |" ; Start der Fehlermeldung: "USE:" & RSX-Strich.
DEFB 0
;
M2: DEFB 18,13,10,18,0 ; Zeile löschen, Zeile tiefer, Zeile löschen.
;
; Gebe Fehlermeldung aus:
;
ERROR: EX DE,HL ; Zeiger in HL nach DE retten
LD HL,Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: M1 - Machine Cycle OneM1
Maschinencode über HIMEM: CALLCALL PR$ ; Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: M1 - Machine Cycle OneM1 ausdrucken
EX DE,HL ; DE zeigt jetzt auf M2
ER1: Maschinencode über HIMEM: CALLCALL PR$ ; nun Fehlertext ausdrucken
EX DE,HL ; M2 ausdrucken
;
LD Operationen: BD5B / 349A / 349A: FLO SUBA,#80+32 ; vorher noch schnell Fehlerflag setzen:
LD (FFLAG),Operationen: BD5B / 349A / 349A: FLO SUBA ; Datenbreite: Bits Port B - Input: &F5xx: Bit 0: Port B - Input: &F5xx: Bit 4: Port B - Input: &F5xx: Bit 5: Port B - Input: &F5xx: Bit 6: Port B - Input: &F5xx: Bit 7: Port C - Output: &F6xx: Bit 4: Port C - Output: &F6xx: Bit 5:Bit 7=1 --> Der Linien-Algorithmus: Fehler 3Fehler bereits mitgeteilt
; Der Linien-Algorithmus: Fehler 3Fehler = 32 --> unbekanntes Kommando
; (Hier: falsche Parameterzahl)
;
PR$: LD Operationen: BD5B / 349A / 349A: FLO SUBA,(HL) ; Zeichen holen,
INC HL ; Zeiger weiterstellen.
AND Operationen: BD5B / 349A / 349A: FLO SUBA ; Zeichen = &00 ?
RET Z ; Dann Endmarke --> zurück.
Maschinencode über HIMEM: CALLCALL PRINT ; Zeichen drucken (oder Ctrlcode befolgen)
JR PR$ ; und nächstes Zeichen.
;
; Fehlermeldung bei LOAD, SAVE UND VERIFY
;
ERROR2: EX DE,HL ; Zeiger nach DE retten
LD HL,Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: M1 - Machine Cycle OneM1
Maschinencode über HIMEM: CALLCALL PR$ ; Alle noch folgenden Anschlüsse fallen unter die Rubrik STEUER- oder auch CONTROLBUS:: M1 - Machine Cycle OneM1 audrucken
EX DE,HL
Maschinencode über HIMEM: CALLCALL PR$ ; Fehlertext ausdrucken
LD HL,MLSV ; Zeiger auf gemeinsamen Text für Argumente
JR ER1 ; so weiter machen, als sei dies der Fehlertext
; gewesen.
; |SET.SPEED,periode,compens
;
; periode = Länge eines halben Nullbits in Mikrosek.: 130...480
; compens = Precompensation in Mikrosekunden: 0...255
;
BSPEED: LD HL,MSPEED ; Zeiger auf Fehlertext nach HL laden.
CP 2 ; 2 Argumente ?
JR NZ,ERROR ; Nein, dann Der Linien-Algorithmus: Fehler 3Fehler.
;
LD Operationen: BD5B / 349A / 349A: FLO SUBA,(IX+0) ; Operationen: BD5B / 349A / 349A: FLO SUBA = 1. Basic und Maschinencode: ParameterParameter = Praecompensation
LD L,(IX+2)
LD H,(IX+3) ; HL = 2. Basic und Maschinencode: ParameterParameter = Länge 1/2 Nullbit.
JP SPEED ; CASSETTE MANAGER: BC68: CAS SET SPEEDCAS SET SPEED
;
; |SAVE, sync, start, länge
;
BSAVE: LD HL,MSAVE ; Zeiger auf Fehlertext.
LD BC,SAVE ; Adresse von CASSETTE MANAGER: BC9E: CAS WRITECAS WRITE
JR SLV ; und weiter.
;
; |LOAD, sync, start ,länge
;
BLOAD: LD HL,MLOAD ; Zeiger auf Fehlertext.
LD BC,LOAD ; Adresse von CASSETTE MANAGER: BCA1: CAS READCAS READ
JR SLV ; und weiter.
;
; |VERIFY, sync, start, länge
;
BVERI: LD HL,MVERI ; Zeiger auf Fehlertext.
LD BC,VERIFY ; Adresse von CASSETTE MANAGER: BCA4: CAS CHECKCAS CHECK
SLV: CP 3 ; 3 Argumente?
JR NZ,ERROR2 ; Nein, dann Der Linien-Algorithmus: Fehler 3Fehler.
;
Maschinencode über HIMEM: CALLCALL MOTON ; CASSETTE MANAGER: BC6E: CAS START MOTORCAS START MOTOR
LD Operationen: BD5B / 349A / 349A: FLO SUBA,(IX+4) ; Operationen: BD5B / 349A / 349A: FLO SUBA = 1. Basic und Maschinencode: ParameterParameter = Der Cassette Manager: Synchronisations-ZeichenSynchronisations-Zeichen
LD LOW KERNEL JUMPBLOCK: 000E: LOW PCBC INSTRUCTION LOW KERNEL JUMPBLOCK: 001E: LOW PCHL INSTRUCTIONE,(IX+0)
LD D,(IX+1) ; DE = 3. Basic und Maschinencode: ParameterParameter = Datei-Länge
LD L,(IX+2)
LD H,(IX+3) ; HL = 2. Basic und Maschinencode: ParameterParameter = Start-Adresse
;
Maschinencode über HIMEM: CALLCALL PCBC ; Routine (Adresse in BC) aufrufen.
;
LD HL,FFLAG ; Fehlercode aus Operationen: BD5B / 349A / 349A: FLO SUBA im Fehlerflag speichern.
LD (HL),Operationen: BD5B / 349A / 349A: FLO SUBA ; Aber Der Linien-Algorithmus: Fehler 3Fehler auf &FF setzen für 'alles o.k.',
JR NC,P1 ; falls CY-Flag gesetzt ist.
LD (HL),#FF
;
P1: JP MOTOFF ; CASSETTE MANAGER: BC71: CAS STOP MOTORCAS STOP MOTOR
;
; |ERROR, @Die Z80: Wirkung der Z80-Befehle auf die Flagsflag%
;
BERROR: LD HL,MERROR ; Zeiger auf Fehlertext
DEC Operationen: BD5B / 349A / 349A: FLO SUBA ; ein Basic und Maschinencode: ParameterParameter ?
JP NZ,ERROR
;
LD L,(IX+0) ; HL = @Die Z80: Wirkung der Z80-Befehle auf die Flagsflag%
LD H,(IX+1)
LD Operationen: BD5B / 349A / 349A: FLO SUBA,(FFLAG) ; Fehlerflag holen
LD (HL),Operationen: BD5B / 349A / 349A: FLO SUBA ; und in der Integervariablen abspeichern.
INC HL
LD (HL),0 ; MSB der Unterprogramme: VariablenVariablen Real: Nullnullen.
RET
;
FFLAG: DEFB 0 ; Speicher für den Fehlerstatus der Routinen.
;
END
|