まごころせいじつ堂

浜町庄金 研究開発  マイコンで遊んでばっかりで

8080A

8080Aの割り込み応答の謎

 きっかけはNEC μPD8080Aのカタログにあったこの記述。

The μPD8080A has the capability to accept a multiple byte instruction upon an interrupt. This means that a CALL instruction can be inserted so that any address in the memory can be the starting Iocation for an interrupt program. This can be accom- plished without auxilliary circuit because INTA is active for all three bytes of the CALL instruction.

 わざわざ3バイト命令のCALLを受け付けるよ書いてあるのはなんでだろうか。8080Aはもともとできたのでは?ということで調べてみた。その前に8080Aの割り込み動作について。

 8080Aは割り込み許可の状態でINT入力がHになると割り込み動作にはいる。割り込み復帰のための現プログラムカウンタの保存はしない代わりに1命令分をデータバスから読み込んで(fetch)実行する。ここで特定の命令、RST7(FFH)を読み込むと現在のPCを保存して38Hにジャンプする。この1命令実行時はPCを更新しないので、38Hからの割り込み処理からリターンする時に元通りの番地に戻ることができる。RSTn命令はRST0〜RST7まで存在し、n × 8番地がエントリポイントとなる。
 スタックにPCを保存してジャンプする命令ならCALL命令でもよく、これは3バイト長である。任意のアドレスをエントリポイントにできるが、割り込み時の回路が複雑になる。

 さて割り込み時は8080Aのデータバスに出力されるステータスをデコードすることにより得られる*INTA信号がアクティブになる。ここを観測することにより割り込み時にどんな長さのコードを取り込んでいるのかがわかるはず。命令実行時にはSYNC信号が立つので、*INTAの立ち下がりをトリガにして同時にSYNC信号をオシロで観測することにした。

 実験に使用するのはSBC8080ボードとPALO ALTO BASICを元に機能を追加してあるSBC8080システムROMを使用した。これは割り込みを許可し8251UARTを初期化し端末の文字入力でINTを上げてくれるのでそのまま割り込みの観測に使える。

 *INTA信号は8228システムコントローラが8080Aのデータバスからデコードし出力する。ただし+12Vにプルアップした状態では何も変化しなかった。+12Vプルアップしていると割り込み発生時に内部で自動的にRST7(FFH)を生成し、*INTA信号は外に出さないようだ。

 8228の*INTAの+12Vプルアップを外し、観測する。端末から1文字入力すると*INTAが発生した。ただし*INTAの数はまちまちである。これは割り込みサイクルで命令取り込み時にバスがフローティング状態のため、バラバラなデータを読み込んでいるせいだと思われる。以下はたまたま1バイト命令のRST7がはいった様子(キー入力が続けてできたので38H番地に飛んでいると思われる)。
2019INTA1


 データバスを弱くプルアップ/プルダウンして任意の命令フォーマットを与えることにする。10KΩプルアップ/プルダウンでCALL命令に相当するCDHに設定した。CALL CDCDHとなるはず。
2019INTA

 観測結果は以下の通り*INTAが3発。
2019INTA3

 さて割り込みで使うRST7とCALL xxxxは観測できたが、ひょっとしてこの*INTA信号は任意の命令のデコード後にわかる命令のバイト数分出るのではなかろうか。ということで配線を変えてADC imm(CEH CEH)にしてみた。結果は予想どおり*INTA 2発。

2019INTA2

 8080Aは割り込み時に1命令を読み込んで実行し、RSTnやCALL xxxxでスタックにPCを保存することを期待している。が、これは任意の命令でよく、命令をフェッチ/デコードして得られた命令のバイト数分*INTAを発生して1命令を実行する。
 Intel 8080Aとそのクローン、NEC μPD8080Aも同じ結果であり、NECのカタログに書いてあった割り込み時に3バイト命令も受け付けるよという記述はわざわざ書くまでのことでもなかったということになる。

 あとクローン8080Aについては解析済で以下からverilogソースが見られます。




NEC 8bit 2MHz MPU i8080互換 UPD8080AFC
B0773MVDKN
5つ星のうち5.0
¥ 1,200

NEC uPD8080AのDAA命令調査 ADD編

 前回の SBC8080システムROMでBASICから機械語を呼び出す で実チップのテスト環境が整ったので以前から気になっていたIntel 8080とNEC μPD8080Aの非互換部分についての調査を行った。

 NEC μPD8080AはIntel 8080のクローンではなく独自に改良し、DAA命令(十進補正命令)の減算対応、実行クロック数の改善がなされた。が、せっかく改善したのに非互換部分が嫌われ完全互換のμPD8080AFに切り替わった。
MCS-80(IC Collection)

 まずDAA命令の動作について。DAA十進補正命令はハーフキャリーを参照する。

Auxiliary Carry: If the instruction caused a carry out of bit 3 and into bit 4 of the resulting value, the auxiliary carry is set; otherwise it is reset. This flag is affected by single precision additions, subtractions, increments, decrements, comparisons, and logical operations, but is principally used with additions and increments preceding a DAA (Decimal Adjust Accumulator) instruction
FLAGレジスタのbit4はACフラグ(またはHフラグ ハーフキャリー)で加算時のbit3からbit4への桁上げで立つ。このフラグは加減算/INC/DEC/比較/論理演算で変化するが主に加算とINCの後のDAA命令で使う、とある。

 DAA命令の記述。
スクリーンショット 2019-01-13 21.30.20

 DAA命令は直前のADD命令について、BCD表現の数値を加算したものとして補正を行う。例えば04H+06Hは0AHだけどこれを10Hに修正する。その手順は以下のとおり:
(1) 下の桁がA-Fになっている、またはハーフキャリーが立っていれば6Hを加算する。
(2) (1)の後、上の桁がA-Fになっていればキャリーフラグを立て60Hを加算する。

もっと詳しい実装の解説はこちら:

 ではデータを採取して比較を行う。コードは前回を参照。テスト結果は1バイトの十進数で

数値A 数値B A+Bの結果 加算後フラグ DAA補正後の結果 補正後フラグ

このデータが256×256パターンで65536行。このデータを適当なunix環境に持っていってawkで処理。Excelでもなんでもいいです。

 まずは16進に変換。数値Aと数値Bは連結してインデックスとして使えるようにする。フラグは2進数表示。こんな感じになる。

0000 00 01000110 00 01000110
0001 01 00000010 01 00000010
0002 02 00000010 02 00000010
0003 03 00000110 03 00000110
...

あとは任意のフィールドを切り出して比較していくだけ。

対象となるCPUは以下:
(1) INTEL MD8080 A/B インテル純正の安心感。すべての比較元とします
2019-MD8080

(2) CCCP KP580BM80 (USSR KR580VM80) ソ連製8080クローン
2019-USSR1

(3) CCCP KP580BM80A (USSR KR580VM80A) ソ連製8080Aクローン
2019-USSR2

(4) NEC μPD8080A 今回の主な調査対象
2019-D8080A

(5) NEC μPD8080A-T -Tサフィックスはなんだろう?
2019-D8080AT

(6) NEC μPD8080AFC Intel 8080A完全互換にしたもの
2019-D8080AFC

テスト結果:(HフラグはACフラグと読み替えて)
a. 加減算後のDAAについて
(1) (2) (3) (6) はまったく同じ。DAA動作は完全互換
(4) (5) はまったく同じ。NEC μPD8080AとμPD8080A-Tは同じもの

b.加算後のDAAについて(1)と(4)を比較
・演算結果の数値は一致
・フラグが異なる
・NEC μPD8080Aは未定義フラグbit3が常に"1"。INTEL 8080Aは常に"0"
・NEC μPD8080AはDAA命令の前後でHフラグの状態は変わらない
・INTEL 8080AのDAA命令前後でのHフラグの動作:
 DAA前にHフラグが立っているとDAA後にHフラグは落ちる
 DAA前にHフラグが落ちているとDAA後に補正前の演算結果の下1桁がA~Fだった場合に立つ

 DAA補正後のHフラグに関しては定義されていないのでこれらは未定義動作として済ませるんですが、続きがあります。

 Dr.Dobb's Journal 1976/11/12 によると"IMSAI INCOMPATIBILITY"というのでNEC製8080Aの挙動についてメーカーに質問が出ている。本来 XRA Aの後にDAAはやらないんだけどやってみたら結果が0のはずが6になっている。これって十進補正をやっているように見えますね。

確認コードはこちら:

 ここでIntelのユーザーズマニュアルでXRA命令を確認してみる。
スクリーンショット 2019-01-13 21.29.56

 XRA命令実行後にAC(ハーフキャリー)はクリアされると書いてあるが、NEC μPD8080Aではクリアされずにセットされたままになっている。この部分は未定義ではないのでIntel 8080とNEC 8080Aの非互換部分と言える。これはXRA命令の実装でACフラグを操作するパスがなさそうに見える。さらに想像するとNEC 8080AではANA以外の論理演算命令ではACフラグは変化しないのかもしれない。

※追記 XRAをANA/ORA命令に替えて実験
ANA命令 Intel 8080でACフラグクリア 仕様書の誤記?
ORA命令 Intel 8080でACフラグクリア
NEC 8080AではANA/ORAともACはクリアされずそのまま


 SUB後のDAA命令編に続く


Ex: El
Posted with Amakuri at 2019.1.13
808 State
Salvo

SBC8080ボード

 記事を書いてたつもりが抜けていたのでメモとして。


 8080Aは周辺チップが必要なことと+12V/-5Vの回路のせいでSBCシリーズとしては部品密度高めです。確実な組み立て方としては

(1) NJM2360A周辺を実装し、5V供給で+12Vが生成されることを確認
2018SBC8080-1

(2) 8224周辺と-5V生成回路を実装し、-5Vが生成されることを確認
2018SBC8080-2


(3)残りの部品を実装
2018SBC8080-3


の順でやればよいでしょう。

 ROM/RAM/UARTについては秋月B基板サイズに収まらないためSBC8080SUBボードに実装されます。作例では40Pフラットケーブルで接続されていますが、私はピンヘッダとピンソケットで重ねられるようにしました。このうちピンヘッダはSBC8080SUBボード側の部品面に、ROMなどソケット部品が干渉しないよう背の高い連結ピンヘッダを半分にカットして使用、SBC8080ボード側ははんだ面にピンソケットを実装。

ボードの間隔は17mmになります。この高さのスペーサがなかなか見つからないのですが、使用すると接続後しっかり固定できます。
2018SBC8080-4

 動作確認はSBC8080システムROMで行った。以下は手持ちの石の組み合わせ。

NEC uPB8224C / NEC uPB8228C / NEC D8080A


次回予告:寒い国から来たCPU


インテル8080伝説
Posted with Amakuri at 2018.12.31
鈴木哲哉
ラトルズ



記事検索
プロフィール

hardyboy

カテゴリ別アーカイブ
月別アーカイブ
QRコード
QRコード
  • ライブドアブログ