現在地

μPD78C10ボード(ソフトウェア編)


ボードが出来たら当然次はソフトウェアを何とかしなくてはなりません。

いつものようにUniversal Monitorを移植することにします。

こういうのってCなどの高級言語か擬似コードを元にアセンブリ言語に変換していくのが一般的なのかもしれませんが、私の場合は似たプロセッサ向けのアセンブリ言語のソースを見ながら直接アセンブリ言語で書き下ろしています。

元にしたソースのバグを発見したり、最適化を思いついたりすることもありますね。ある意味コードレビューしているようなものですから。

今回は8080用を元にしていて、現時点でD(ump), S(et), G(o), L(oad), P(unch)の各コマンドが動いています。ここまでで感じたことをあげてみます。

  1. ニーモニックは8080にそっくりなものが多い。SHLD, LXIなど
  2. レジスタも8080とほぼ同じ。裏レジスタがある点はZ80に近いとも言えるが、IXなどは無い。PSW(フラグレジスタ)には裏レジスタは無いので要注意。
  3. 条件分岐命令は無く、条件スキップと無条件分岐命令の組み合わせを使用する。分岐命令以外もスキップできるので条件付加算とか条件付ストアなどもできる。
  4. 条件スキップは比較命令がほとんど。例外はあるが結果を残す演算命令では条件スキップしない。
    結果としてEQI A,0(Aが0だったらスキップ)といった命令を多用することになる。
    2021年11月4日 訂正:
    SK, SKNというフラグの状態でスキップする命令がありました。
  5. 2項演算命令はディスティネーションがアキュムレータに固定されているプロセッサが多い中、C←C+AとかL←L+immなどが可能。
    HEXファイルのチェックサム計算には便利でした。
  6. レジスタ間の転送に制限(MOV L,Eなどはできない)がある。
  7. 8ビットのINR, DCRでキャリー・ボローが発生すると次の命令をスキップする。これは次のようなループに便利でした。
         149/     1ED : 6A 0F               	MVI	B,16-1
         150/     1EF :                     DPL0:
         151/     1EF : 40 16 02            	CALL	DPB
         152/     1F2 : 52                  	DCR	B
         153/     1F3 : FB                  	JR	DPL0

    だが16ビットのINX, DCXにはこの動作は無いので注意。

  8. MVI, LXI命令で特定のレジスタの場合にだけ"stacking effect"と呼ばれる動作がある。
         395/     373 : 67 31               	NEI	A,'1'
         396/     375 : C5                  	JR	LHS00
         397/     376 : 67 39               	NEI	A,'9'
         398/     378 : C4                  	JR	LHS01
         399/     379 : 4F 95               	JRE	LH3		; Unsupported record type
         400/     37B :                     LHS00:
         401/     37B : 69 00               	MVI	A,0
         402/     37D :                     LHS01:
         403/     37D : 69 01               	MVI	A,1
         404/     37F : 70 79 DA 0F         	MOV	RECTYP,A

    これAが"1"で400行目から実行すると、401行でAに0を入れても403行で1が入って、402行から実行したのと同じになってしまうように見えますね。実はMVI A,byteが連続すると先頭以外は実行されない(これが"stacking effect")のです。飛び越すためのJR命令が不要になります。
    他にMVI L,byte, LXI H,wordも同様です。

今回はμPD78C10ですがμPD7800も持っているので両対応にしたいところ。以前書いたようにRET命令といった基本的な命令のコードが変更されているので同一バイナリは諦めていますが、ソースはできれば共通にしたいのでEAレジスタなどは避けて書いています。

最後にCPUコア以外で気になった点をいくつか。

  • MMレジスタを設定しないと内蔵RAMが使えません。
  • 内蔵シリアルI/Oはステータスレジスタがありません。割り込み要因レジスタをSKIT, SKNIT命令で判定するしかありませんが、これは破壊読出しになるので要注意。CONSTルーチンの実装にてこずりました。
  • 内蔵タイマをボーレートジェネレータに使う場合は意外に自由度が低いです。深く考えずに12MHzにしたら2400bpsまでしか出ませんでした。もちろん半端な値でよければもっと上げられますが。

コメントを追加

Plain text

  • HTMLタグは利用できません。
  • ウェブページアドレスとメールアドレスは、自動的にハイパーリンクに変換されます。
  • 行と段落は自動的に折り返されます。
※ コメントは原則公開です。個別のご相談などは「ご意見・ご要望」からお願いします。