2020.9.4
前へ
次へ
ホームページトップへ戻る

[新連載]復活!TINY BASIC
〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜
すべてはここからはじまりました。
中日電工も。
40年前を振り返りつつ新連載です。
〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜〜



[第81回]


●ENDCHKとERROR処理

前回からの続きです。
INPERRへのジャンプ命令はERROR処理ルーチンの中にあります。
以下はERROR処理ルーチンとその前段にあるENDCHKルーチンの解説文です。



ENDCHKは命令がCRコードで終っているかどうかを確認します。
CRコードで終っていない(余計な文字がある)ときはERROR表示ルーチンが実行されます。
ENDCHKをCALLしている命令を下記に示します。
NEW、STOP、RUN、GOTO、LIST、RETURN

ERROR表示ルーチンでは最初にエラーを示す文字列(WHAT?、HOW?、SORRY)が表示されます。
その後でエラーが発生した行(CURRNTで示される)が表示されます。
行の途中のエラーが発生した位置アドレスには”?”が挿入されて表示されます。
その表示位置アドレスはスタックトップに置かれていなければなりません。
エラー表示後はTINY BASICの実行は中止され、スタート前の入力待ち状態になります。
ただし例外があります。
CURRNTで示されるアドレスには行番号が置かれていますが、その行番号が0の場合にはダイレクトモードであることを示しています。
ダイレクトモードの場合にはエラーメッセージは表示されますが、命令行の表示は行なわれません。
エラー表示後はスタート前の入力待ち状態になります。
また行番号がマイナスの場合にはINPUT命令であることを示しています。
INPUT命令の場合にもエラーメッセージは表示されますが、命令行の表示は行なわれません。
エラー表示後もTINY BASICの実行は中止されず、INPERR:にジャンプします。

エラー表示処理ルーチンには次のものがあります。
QWHAT
エラー発生位置のテキストアドレス(DEレジスタ)をスタックに保存したあとWHAT?を表示します(その後ERROR:にジャンプします)。
AWHAT
WHAT?を表示した後ERROR:にジャンプします。
QSORRY
エラー発生位置のテキストアドレス(DEレジスタ)をスタックに保存したあとSORRYを表示します(その後ERROR:にジャンプします)。
ASORRY
SORRYを表示した後ERROR:にジャンプします。
QHOWとAHOWは下のERRORルーチンの中にはありません。
そのプログラムリストは[第15回]にあります。
QHOW
エラー発生位置のテキストアドレス(DEレジスタ)をスタックに保存したあとHOW?を表示します(その後ERROR:にジャンプします)。
AHOW
HOW?を表示した後ERROR:にジャンプします。

下はENDCHKとERROR処理ルーチンのプログラムリストです。



ENDCHKではRST 5を実行します。
RST 5は[第12回]で説明しました。
RST 5はDEレジスタで示されるメモリの値をチェックして最初に出現するブランク(スペース)ではない文字コードをAレジスタに入れるサブルーチンです。
その文字コードがCR(0D)のときはメインルーチンにリターンします。
それ以外のコードのときは下のQWHAT:が実行されます。

QWHAT:はDEレジスタにある現在のテキスト行の位置アドレスをスタックに保存したあと、下のAWHAT:を実行します。
AWHAT:はDEレジスタにWHAT文字列の先頭アドレスを入れて、その下のERROR:を実行します。
WHAT文字列はこのプログラムリストにはありません。
[第15回]でお見せしたプログラムリストのアドレス00AEにあります。

ERROR:プログラムの説明です。
Aレジスタを0にしてPRTSTGをCALLします。
SUB AはAレジスタを0にするために使われています。
PRTSTGは[第46回][第47回]で説明しました。
DEで指定するアドレスから始まる文字列を終わりの0Dコードまで表示します。
またはAレジスタの値と一致する文字コードがみつかるまで表示します。

その後のアドレス04CEからはエラー行を表示するための処理を行ないます。
04CE POP D
04CF LDAX D
04D0 PUSH PSW
04D1 SUB A
04D2 STAX D
はエラーが発生したテキストの現在位置アドレス(スタックトップに置かれている)の文字をスタックに保存して、代わりにその位置に0を書き込みます。
テキスト行のこの位置までの文字列を表示するための前準備です。

04D3 LHLD CURRNT
04D6 PUSH H
04D7 MOV A,M
04D8 INX H
04D9 ORA M
04DA POP D
04DB JZ RSTART
はCURRNTの値(現在行の先頭アドレス)をHLに入れたあと後の処理のためにスタックに保存します。
行の先頭アドレスとその次のアドレスには行番号を示す16進数2バイトの値があります。
その値をチェックします。
値が0のときはダイレクトモードなので処理を中止してRSTARTにジャンプします。
RSTARTは[第27回]で説明をしました。
この場合
04DA POP D
は実際にはなくてもよい命令です。
しかしこのあとの処理でDEには
04D6 PUSH H
でスタックに保存したCURRNTの値を入れなくてはなりませんから、ここでそれを行なっています。
ダイレクトモードへの分岐もRSTARTのプログラムで行なっています。
RSTARTの始まりのところでCURRNTに初期値として値が”0000”であるメモリアドレスがセットされています。
それが上のプログラムのダイレクトモードの判定で使われています。

04DE MOV A,M
04DF ORA A
04E0 JM INPERR
はINPUT文で入力エラーがあったときの処理です。
ここで[第76回]で書いた意味不明なプログラムの意味がはっきりします。
CURRNTの値で示すアドレスとその次のアドレスにある2バイトの値は通常は行番号を示します。
しかし上で書きましたようにダイレクトモードではその値は0000になっています。
またINPUT命令ではその値はマイナス(最上位ビットが1)になっています。
ダイレクトモードの判定のために、アドレス00C7でLXI H,ST2+1が裏技的に使われています([第27回]参照)。
またINPUT文の判定のために
02F1 LXI H,IP1
02F4 SHLD CURRNT
がやはり裏技的に使われています([第76回参照])。
そしてここで前回説明しましたINPERRへのジャンプ命令が実行されます。

行番号が0でもマイナスでもない場合には通常のテキスト行でのエラー処理が行なわれます。
アドレス04E3からの処理です。

残りはあともう少しですが、今回は説明が長くなってしまいましたので、この続きは次回にすることにいたします。

復活!TINY BASIC[第81回]
2020.9.4upload

前へ
次へ
ホームページトップへ戻る