%,{c H},{BGCOLOR:dddddd|BOLD|CENTER}
第1版第15刷 P.275-282
2章 カセット・インターフェイス
カセットテープレコーダは、MSXの最も安価な外部記憶装置です。このカセットテープ上の情報をマシン語中で取り扱うためには、カセット・インターフェイスの使用法を知らなくてはなりません。本章では、このために必要となる情報を説明します。
2.1 ボーレート
MSXのカセット・インターフェイスは以下の2種類のボーレートを使用できます(表5.2)。なお、BASICのスタート時にはデフォルトで1200ボーが設定されています。
ボーレート | 特徴 |
---|---|
1200bps | 低スピード/高信頼性 |
2400bps | 高スピード/低信頼性 |
表5.2 MSXのボーレート
ボーレートの指定は、SCREEN命令の第4パラメータまたはCSAVE命令の第2パラメータで行います。一度指定すると以後そのボーレートが引き続いて使用されます。
SCREEN ,,,<ボーレート> CSAVE "ファイル名",<ボーレート> (<ボーレート>は両者とも、1で1200ボー、2で2400ボー)
2.2 1ビットの構成
入出力の基本となる1ビットのデータは図5.11のように記録されます。パルスの幅はCPUのT-STATEをカウントして決められるため、カセット・インターフェイス作動中はすべての割り込みが禁止されています。
なお、カセットから入力されるビットデータは、汎用入出力インターフェイスのポートB(PSGのレジスタ#14)の第7ビットを通して読み取ることが可能です。第5部1章リスト5.2のプログラム例の中で、この機能を使用していますので、参照してください。
図5.11 1ビットの構成
2.3 1バイトの構成
1バイトのデータは図5.12のようなビット列で記録されます。スタートビットとして“0”のビットがひとつ、次にデータ本体が最下位ビットから最上位ビットの順で8ビット、最後にストップビットとして“1”のビットが2つ続き、合計11ビットを使用します。
図5.12 1バイトの構成
2.4 ヘッダの構成
ヘッダとはセーブまたはロード時に、カセットテープが動き出してから回転が安定するまでの時間待ちや、ファイル間に区切りをつけるために、ある特定の周波数の信号を一定時間テープに記録させた部分のことです。ロングヘッダとショートヘッダの2種類があり、ロングヘッダはモータの回転が安定するまでの時間待ちに使用されます。また、テープリード時のボーレートは、ロングヘッダを読んで決定されます。ショートヘッダはファイルボディ間の区切りに使用されます。
表5.3 ヘッダの構成
2.5 ファイルのフォーマット
MSXのBASICは次の3タイプのカセットフォーマットのファイルをサポートしています。
(1)BASICテキストファイル
CSAVE命令でバイナリセーブしたBASICプログラムは、このフォーマットにしたがって記録されます。なお、ファイルは前半のファイルヘッダと後半のファイルボディに分けられます。
図5.13 バイナリファイルのフォーマット
ファイルヘッダは、ロングヘッダの後にOD3Hという値が10バイト続き、その後に6バイトのファイル名が置かれます。ファイルボディはショートヘッダの後にプログラム本体が続き、7バイトの00Hでファイルエンドを示します。
(2)ASCIIテキストファイル
SAVE命令でアスキーセーブされたBASICプログラム、およびOPEN命令によって作られたデータファイルは、このフォーマットにしたがって記録されます。
ファイルヘッダは、ロングヘッダの後に0EAHという値が10バイト続き、その後に6バイトのファイル名が置かれます。
データ本体は256バイトごとのブロックに分けられ、それぞれのブロックの前にはショートヘッダが置かれます。ファイルエンドはCtrl-Z(1AH)で示されます。このため、1AHという値を含むデータファイルを作ることはできません。
図5.14 アスキーファイルのフォーマット
(3)マシン語ファイル
BSAVE命令でセーブされたマシン語ファイルは、このフォーマットにしたがって記録されます。ファイルヘッダは、ロングヘッダの後に0D0Hという値が10バイト続き、その後ろに6バイトのファイル名が置かれます。
ファイルボディは、ショートヘッダの後に、先頭アドレス、最終アドレス、実行開始アドレスの順に3つのアドレスが記録され、その次にマシン語本体が続きます。データの量は先頭アドレスと最終アドレスから計算できますから、特別なファイルエンドマークはありません。実行開始アドレスとは、BLOAD命令のRオプション使用時に、プログラムが実行されるアドレスです。
図5.15 マシン語ファイルのフォーマット
2.6 カセットファイルのアクセス
カセットファイルをアクセスするために、以下のBIOSルーチンが用意されています。
● TAPION (OOE1H/MAIN)……………読み込みOPEN
入力:---
出力:異常終了時CYフラグ=ON
機能:テープレコーダのモータを起動し、ロングヘッダまたはショートヘッダを読み込む。同時にそのファイルが記録されたボーレートを判別し、ワークエリアをそれに合わせて設定する。なお、割り込みは禁止される。
● TAPIN (00E4H/MAIN)……………1バイトの読み込み
入力:---
出力:A←読み込んだデータ
異常終了時CYフラグ=ON
機能:テープからデータを1バイト読み込み、Aレジスタに格納する。
● TAPIOF (00E7H/MAIN)……………読み込みCLOSE
入力:---
出力:---
機能:テープからの読み込み動作を終了する。同時に割り込みは再開される。
● TAPOON (00EAH/MAIN)……………書き出しOPEN
入力:A←ヘッダの種類(0=ショートヘッダ, 0以外=ロングヘッダ)
出力:異常終了時CYフラグ=ON
機能:デープレコーダのモータを起動し、Aレジスタで指定された種類のヘッダをテープに書き出す。なお、割り込みは禁止される。
● TAPOUT (00EDH/MAIN)……………1バイトの書き出し
入力:A←書き込みデータ
出力:異常終了時CYフラグ=ON
機能:Aレジスタの内容をテープに書き込む。
● TAPOOF (00F0H/MAIN)……………書き込みCLOSE
入力:---
出力:---
機能:テープへの書き込み動作を終了する。同時に割り込みは再開される。
● STMOTR (00F3H/MAIN)……………モータの動作指定
入力:A←動作の指定(0=停止, 1=起動, 255=現在と反対の状態にする)
出力:---
機能:Aレジスタで指定した値にしたがって、モータの動作状態を設定する。
これらのBIOSを使用してカセットファイルのREAD/WRITEルーチンを作成する際に、なるべく無駄な動作をせずに、ただひたすらREADまたはWRITEのみに専念するようにしてください。たとえば、テープからデータを読み込みながらそのデータをCRTに表示させたりすると、READエラーを生じることがあります。
リスト5.4にBIOSルーチンを使用したサンプルプログラムを示します。
リスト5.3 カセットにセーブされたファイル名の表示
;============================================================ ; ; List 5.3 Cassette files ; ; Set cassette tape into recorder and run this program. ; Then the all names and atributes of the programs ; in that tape are listed out. ; ;============================================================ ; CHPUT EQU 00A2H TAPION EQU 00E1H TAPIN EQU 00E4H TAPIOF EQU 00E7H ORG 0C000H ;----- program start ----- カセットテープ内のプログラム名一覧を表示する START: CALL TAPION ;motor on and read header LD B,16 LD HL,WORK ;work area address LBL01: PUSH HL PUSH BC CALL TAPIN ;read a byte of data from tape POP BC POP HL JR C,ERROR ;set carry flag if read error LD (HL),A INC HL DJNZ LBL01 LD HL,FILNAM ;write file name CALL PUTSTR LD HL,WORK+10 CALL PUTSTR CALL CRLF LD A,(WORK) ;check file attributes LD HL,BINFIL CP 0D3H ;check binary file JR Z,LBL03 LD HL,ASCFIL CP 0EAH ;check ascii file JR Z,LBL03 LD HL,MACFIL CP 0D0H ;check machine code file JR Z,LBL03 ERROR: LD HL,ERRSTR LBL03: CALL PUTSTR CALL TAPIOF RET ;----- put CRLF ----- CRLF: LD HL,STCRLF CALL PUTSTR RET ;----- put string ----- PUTSTR: LD A,(HL) ;get a character from strings CP '$' ;check end of strings RET Z CALL CHPUT ;write a character to CRT INC HL JR PUTSTR ;----- strings data ----- FILNAM: DB 'FILE NAME :$' ASCFIL: DB 'ASCII FILE',0DH,0AH,'$' BINFIL: DB 'BINARY FILE',0DH,0AH,'$' MACFIL: DB 'BSAVE FILE',0DH,0AH,'$' ERRSTR: DB 'TAPE READ ERROR',0DH,0AH,'$' STCRLF DB ODH,0AH,'$' ;----- WORK AREA ----- WORK: DS 16,0 DB '$' ;end of strings END