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

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



[第48回]


●DIVIDE,SUBDE,CHKSGN,CHGSGN,CKHLDE

今回はPRTNUMについて書くつもりだったのですがプログラムを確認していて、DIVIDEなどの計算サブルーチンをCALLしていることに気が付きました。
PRTNUMは10進数を表示するサブルーチンです。
TINY BASICでは数値は16進数で管理しているのですが、それをPRINT文で表示するときには10進数に変換して表示します。
16進数から10進数への変換の過程では割り算が必要になります。
ということで、今回は予定を変更してDIVIDEなどの計算サブルーチンについて説明をすることにします。
今回説明するサブルーチンの中にはPRTNUMでは使わないものも含まれていますが、オリジナルのTINY BASICではそれらも含めてまとめて扱っていますので、ことのついでということで今回はそれらも一緒に説明してしまうことにします。



DIVIDEは16進数2バイトの割り算です。
HL/DEを計算します。
商はBCに入れられます。
余りはHLに入れられます。
割り算ですけれど実際の計算は引き算を繰り返すことで結果を求めています。
計算の効率を上げるため最初にH/DEの計算を行なってその結果をBに入れ、、次にその余りをHに残したうえでHL/DEの計算を行い結果をCに入れます。
私達が10進数の割り算を筆算で行なうときと同じ計算方法です。

SUBDEはHL−DEを計算します。
8080には16ビットの減算命令はありませんから最初にL−Eの計算を行い次にその結果のキャリーを含めてH−Dの計算を行ないます。

なおDIVIDEの計算は正の整数に対して行ないます。
負数はあらかじめCHGSGNによって正数に直してから計算します。

CHKSGNはHLの正負を判定して負数のときはそれを正数に変換するサブルーチンです。
正数のときはそのままリターンします。
負数のときは次のCHGSGN:を実行します。
CHGSGNの実行によって負数が正数に変換されます(正数のときは負数に変換されます)。

CHGSGN:では2の補数を求めることで負数から正数へ、正数から負数への変換を行います。
たとえば2進数(16進数)のFFFFは10進数の−1です。
2の補数は元の数の全ビットを反転してその結果に1を加えて算出します。
1)FFFFのビットを反転する→0000になる
2)その結果に1を加える→0001になる
逆の計算をしてみます。
1)0001のビットを反転する→FFFEになる
2)その結果に1を加える→FFFFになる
アドレス0486から048Dでその計算をしています。

ところがこの計算ができない数があります。
8000H(−32768)です。
上の例と同じ計算をしてみます。
1)8000のビットを反転する→7FFFになる
2)その結果に1を加える→8000になる
8000Hは符号付数では−32768ですが、正の数としての32768も同じ8000Hになってしまうため、負数から正数への変換が正しく行なわれません。
16ビットの数を符号付数として考えた場合、最上位ビット(ビット15)が1のときには負数、0の時には正数として扱うからです。
アドレス0487のPUSH PSWと048E POP PSW〜0490 JP QHOWはそのための処理です。
PUSH PSWでAレジスタに入れた変換前のHが保存されます。
POP PSW以後で変換前のHと変換後のHのXORを実行します。
CHGSGNの変換前のHLと変換後のHLは正負が逆になります。
それはHだけに注目しても同じです。
その両者のXORを計算するとHの最上位ビットは1になります(結果は負数になるのでサインフラグが立つ)。
ところが変換前にHL=8000だったときだけ変換後もH=80なので両者のXORを計算した結果は00になりサインフラグは立ちません。
そこでその場合にはJP QHOWが実行されます。
QHOWはHOW?を表示するルーチンです。
JPはZ80ニーモニックでは無条件ジャンプ命令なのでまぎらわしいのですが、8080アセンブラではJump if Positive(結果が正のときジャンプする)です。

アドレス0493〜0496でBレジスタのビット7を反転させています。
BレジスタはCHKSGNでもCHGSGNでも使われていませんから、その外で値が定義されています。
Bレジスタがどう使われているのかは今のところ確かめていません。
おそらく数式の計算の過程で正負を管理するために使われているのではと推測しています。
いずれ数式の計算について説明をしていく過程でわかってくると思います。

最後のCKHLDEはどこで使われているのか今のところ調べていません。
おそらく数式の計算の過程で使われるのだと思います。
CKHLDEではHLとDEの符号を判定します。
同符号なら何もしないでCK1:にジャンプします。
異符号ならHLとDEの値を交換します。
いずれの場合にもCK1:でRST 4を実行します。
RST 4は[第12回]で説明しました。
HLとDEの比較を行ないます。
一致しているときはZフラグが立ちます。
HL<DEのときはキャリーフラグが立ちます。

復活!TINY BASIC[第48回]
2020.7.26upload

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