JR-300エミュレータの開発その4

JR-300エミュレータの開発話、第4弾!(^-^)

 

開発時に書いていた記録から引っ張ってきているので、どうしても中身が日記っぽくなってしまっている!読んでて気持ち悪くないかな…心配(^^;;

生暖かく見てくださると助かります~!

 

なんでも良いけど……

いろんな人から「セミリタイアいいですね!」とかDM来るんですけど…汗

ちゃんと仕事してるよ!(ToT)
空いた時間でエミュレータ作ってるよ!(^^;;

信じて~~!(泣)

 

2022/11/18(金)
次はLINE命令に取り掛かる。
簡単なテストをしてみたところ、グラフィックコントローラに渡るパラメータは想像よりも少ない。
この結果から、な~んとなくだけど直線補間ハードが載っているらしいと思ってる!

律儀に1ドットずつ描いてたCIRCLEとは違うぜ!(^-^)

 

I/OアクセスはLINE命令1つにつき60回出てくる。

そのうち先頭の6回はコマンドモードの初期化っぽいアクセスで、残りの54回でLINEを引いてるっぽい。

54回の内訳はRGBで各18回ずつとなっていて、それぞれよく似たパラメータが出ている。
つまり18個のパラメータを解析する事が出来れば、画面にLINEが引かれる…という事だ!(^o^)

 

先にPSETをテストしていたおかげで、なんとなくデータの並びが理解できる。

LINE(50,0)-(0,75),3 とすると、以下のようなデータがI/Oアクセスする。

 

1E  FF FF
CC
92  60 00 04
52  20 20
32  F0 D2 00 98 00 73 FF 26 00
36
CC
92  60 02 04
52  20 20
32  F0 D2 00 98 00 73 FF 26 00
36
4C
92  60 01 04
52  20 20
32  F0 D2 00 98 00 73 FF 26 00
36

 

最初の1バイトがコマンドコード、続くのがオプションという感じ。
この並びはPSETと共通なところもあり、先に解析しておいた情報が役立つ。
例えばコマンド0x92はVRAMアドレスを指している。

60 00 04というデータの先頭2バイトがVRAMアドレス。

0x0060は1バイトごとにビットを反転させて0x0006。

…みたいな感じで、1つずつ意味を解読していく必要がある。

 

コマンド0x32が長くて、これは何だ???となった。
何度もLINE命令のパラメータを変更してはチェックしてみたところ、どうやら最初の0xF0というのはサブコマンドコードらしい。


LINEの角度によって8種類のコードがある事がわかった。
角度によって変わるとなれば、これはもうDDA補間(ブレゼンハムの線分発生アルゴリズム等)で描画するためのパラメータだろうとピンと来る。
ただ…確か計算に必要な数値は3つだった気がするけど、4つ(4word)あるね…。

 

その後、0xF0の次にある2バイトは、ループ回数だと判明する。
0x00D2のビットを反転させると0x004B、10進数で75、なるほど(^^)

こうやって1つ1つのパラメータを丁寧に解析していく。

 

残りの3つがDDA補間に必要なパラメータ(e,dx,dy)だろうと予想して数値を見ていくけど……なんか違う。
それっぽい数字なんだけど、誤差が多くて長いLINEを引くとドットが目的の位置に到達しない。
うーん…これは???

 

手を変え品を変え、いろんな直線補間アルゴリズムにアテてみるけど、どれも計算結果と合わない。
困ったぞ、LINEがちゃんと機能しなければPAINT漏れとかあるし、そもそもデモンストレーションが動かないかも。
これは是が非でも合わせるぞと頑張ってみる!!

 

……頑張ってみたが、結局どれも計算式が合わない!
グラフィックコントローラの中で行っている直線補間アルゴリズムが分からない以上、どうにかして辻褄を合わせるしか無い。

 

仕方ないので、3つ出ているパラメータのうち、2つが誤差多くて使えないため、1つの情報を元に、他の2つのパラメータを計算する事にした!
つまり2つのパラメータは使わない判断をした(^^;;
これでいいんだっけ?(@_@;;

ま、いっかw ← さっき丁寧に…って書いた人と同一人物

 

ここまでやったところで、ようやく画面に正しそうなLINEが描画出来た!
ひー!LINEはかなり大変だった!!(T_T)

 

2022/11/19(土)
次はPAINT命令に取り組む!
最終的にデモンストレーションを動かすためには、おそらく避けては通れないと見ているため、頑張って動かしたい。

 

PAINTは最初っから大変であろう事が、なんとなくだけど見えている。
PAINTという処理は、境界線の情報をVRAMから拾ってくる必要がある。
つまりグラフィックコントローラから何かしらの情報を返さねばならない。

今まではグラフィックコントローラに出力するばかりだったので、データを返す方法も含めて経験値がゼロだ!

 

PAINTのアルゴリズムとして想像出来るのは、指定されたポイントから左右にRayを伸ばしていき、境界色に突き当たったらその範囲を塗る…というのを繰り返すモノだろう。塗るという動作はLINE命令としてI/Oに出てくるんだと思う。


問題は、どんな情報が与えられて、どんな情報を返したら良いのかがさっぱり分からない事だ。
これはもう逆アセンブラリストを追いかけるしかないが、PAINT命令のような複雑なものを逆アセンブラで追いかけるのは(出来れば)避けたい(-_-;;

 

PAINT命令を動かしてみると、RGBごとに3回x2のI/Oリクエストが来ているので、おそらく左右のサーチをプレーンごとにしていそう。
各プレーンごとなので、ドットがあるところまでの距離…とかじゃないだろうか??

 

……と思ってみていたけれども、PAINTする座標によってグラフィックコントローラから返すデータが1バイトの時と2バイトの時があるようだ。
しかもコマンドが0x40と0x60の時がある…これはなんだ???(@_@;

 

PAINTの起点座標をアドレス変換したデータをコントローラに出力しつつ、何かの返事を期待している。
PAINT処理だと考えれば、右をみるか左をみるという処理が必ず入るはず…それが0x40と0x60??
うーん、全く仮説が立たない。これは厳しいぞ(T-T)

 

別の業務作業をしている時、ハタと気がついた。
そうか、PAINTを開始する座標を見て、すでにその場所が境界色になってるかどうかを判定しているのではないかと…。
グラフィックコントローラから返すデータを適当にしていたが、これを境界色ではない色を返すように変えてみた。

 

そしたら!!!
2度めのアクセスがあって40回 x 3のデータロードが発生した!!!
ををををを??(@_@;;
ちょっと待て。
そうなの?そういう事?

 

……つまりこういう事だ。
PAINTしようとする起点のデータを得て、Z80側でPAINTの必要があるかを判定し、必要があるとなったらその1ライン(320 or 640ドット x 3プレーン)すべてをZ80側に転送して、PAINT範囲をチェックした後、LINE命令で線を引くという流れ。

 

いや…いやいやいや……汗

グラフィックコントローラってそういうモノなの??(T-T)
せめて左右のビットが立ってるところまでの距離を返すとか、そういう機能なのかと思ってた(^^;

せっかくLINE描画が速くても、これでは相殺どころかマイナスになるのでは…orz

 

メインCPU側の動作を見て大雑把なプログラム方針が決まったので、さっそく実装してみる。
いろいろと試行錯誤はあったけれど、無事にPAINTが動くようになった!
これは嬉しいなー!(^^)
もっと時間がかかると思っていたので、ワリとあっさり動いたのは感動です♪

 

よし、せっかくなのでCLS 2の方も対応させてみよう。
これで今までの解析実績があったので、割と簡単に対応完了。

 

ただ…気になったことがあって、マシンの初期化時にグラフィックコントローラの0xA000から16KBをクリアするコードが出てる。
VRAM領域自体は0x0000~0xBFFFまでの48KBあるのでメモリオーバーにはなっていないのだけど、なぜ0xA000をクリア???
こういう些細な事が気になってくる(^^;;

 

2022/11/20(日)
画面解像度(320 or 640)を変更する方法を探す。

 

PRINT SCREEN(1,1) とすると、テキスト画面の座標(1,1)のアスキーコードを返す。
そういえばFMシリーズを使ってる時、カッコを付けると関数として動くけど、つけなければコマンドとして動く命令があることを思い出し、
なにげに SCREEN 0 とかしてみた!
するとエラーにならずテキスト画面がクリアされた!

 

詳しく調べてみたところ、以下のような状況だった。

SCREEN 0,0 ... 不明(テキストのみクリア)
SCREEN 0,1 ... 不明(テキストのみクリア)
SCREEN 1,0 ... 320x200
SCREEN 1,1 ... 320x200
SCREEN 2,0 ... 640x200
SCREEN 2,1 ... 640x200

第2オプションは全くの不明。

アセンブルしてみないと分からないかも。

 

カタログスペックには640x400ドットのモノクロモードがあるように読み取れるのだけど、プログラムコードを読む限り縦方向は200にハードコーディングされている。
プログラム自体がRAMに置かれているので自己書き換えの可能性は否定しないが、今のところは無いのではないか…と思いたい。

ちなみにMicrosoftのGW-BASICでは自己書き換えあったぞ…(ぼそっ

 

次にグラフィックに関係しそうな命令は…と思ってみてみると、SYMBOL命令があった。
過去にFM-11を使っていた時の記憶では、グラフィック画面に拡大された文字を表示する機能だった。

 

同じかどうかは分からないが、試しに実行してみたところ、サブCPU側へコマンドが発行された。
あれ???サブCPUなの??
サブCPU = テキスト画面側だと思うんだけど、そっちに発行する??
んー……しばしSYMBOL命令の構造を考えてみる……
あ、違う、多分コレはフォントデータをサブCPU側に問い合わせしてるんだ!

 

試しに&H3021とかやると”亜”の漢字データへのアクセスが発生しないかと思いやってみたが、Type mismatchになってしまう。

残念ながら漢字はサポートしてないみたいだ(^^;

 

うーむ、SYMBOL命令が全く解析できない。
FM-7のBASIC資料を見ると、以下のような文法なんだけど…
SYMBOL(X座標,Y座標),"文字列",横倍率、縦倍率、カラー

JR-300ではどうやら、
SYMBOL(X座標,Y座標),"文字列",不明、カラー、不明
となっているみたいなのだ。

 

しかもサブCPUにフォントデータを取得しに行くのは理解できるのだけど、その結果としてグラフィックコントローラに出力されるデータが少なすぎる。
高性能ではないであろうコントローラにこんな短いコマンド??
これが全く理解できない(T-T)
SYMBOL命令の解析実装は一旦中止だ(TT)

 

グラフィック周りはまだまだ続くよー!(^-^;;

 

ではまた次回!(^-^)ノ