ゲームボーイのCPUについて、誤った技術情報が検索トップの方に表示されるので、私が把握する限りでZ80との仕様差を書いておきます。
ゲームボーイのCPUとは?
☓ 8080
☓ Z80
○ 8080カスタム or Z80カスタム(正確にはSHARPのLR35902)
Z80との仕様差:
- 1マシンサイクルが全て4Hz(なので全ての命令のTサイクルは4で割り切れる)
- 一部フラグ(S, P/V, X, Y)が存在しない(※X, Yはundocumented)
- レジスタ IX, IY が存在しない
- プレフィクスDD(IX命令)、FD(IY命令)が存在しない
- 裏レジスタが存在しない(ので、EX/EXX命令も存在しない)
- IN/OUT命令が存在しない(I/Oは$FF00〜$FFFFにメモリマップド)
- プレフィクスED命令(結構便利な命令群)が存在しない
- $ED $4D (RETI命令) については $D9 (EXX命令) へ移動
- Rレジスタに実質アクセスできない(Rレジスタ=DRAMへ通電するためのレジスタで命令実行毎に0〜127の範囲でインクリメントされ続けるもの。この特徴を利用してゲームでは乱数ジェネレータとして利用されることがあるが、ED命令削除の影響でゲームボーイでは利用できないので、乱数を使いたい場合は自前の乱数テーブル等を作る必要がある)
- プレフィクスCBのSLL命令(undocumented)がSWAP命令に置き換わっている(SWAPはレジスタ上位4bitと下位4bitを入れ替えるLR35902固有機能)
- DJNZ命令がSTOP命令に置き換わっている(STOPはHALTよりも省電力な割込待機機能)
- LDI/LDD命令をシンプル化(Bレジスタのデクリメントを行わず、HLのインクリメント・デクリメントのみ行う)
- LDIR/LDDR(OTIR/OTDR)相当の命令が無いのでBレジスタのデクリメントが要らない(これらの命令は結構便利だが、継続条件時に5Hzの無駄クロックが発生する関係で、性能が求められる箇所では使用せずにOUTI, OUTI, OUTI...などといった形でRじゃない方の命令を並べて書くのが普通...つまり、ゲーム用CPUなら無くても良いよね という判断だと思います)
- LDH命令を追加($FF00〜$FFFFへのアクセス命令のサイクル数を少なくしたもの=I/O命令の代替用)
- スタックポインタを便利に使えるようにする命令群(LD (addr),SP / ADD SP,d / LDHL SP,d)を追加(※LDHLはADD SP,dの結果をHLに代入する命令)
- LD (addr),A と LD A,(addr) の命令コードを変更
- LD HL, (addr) と LD (addr), HL を廃止
私の認識はだいたいこんな感じ。
これで本当に正しいか少し自信がないので、自前Z80エミュレータにLR35902コンパチモードを追加して検証してみようと思っているところです。
https://github.com/suzukiplan/z80/pull/17
(以下、余談)
ゲームボーイのCPUが8080派生なのかZ80派生なのかという議論を目にしますが、機能的には8080とZ80のどちらにも近いと思います。レジスタセットは8080に近いし、豊富なシフト命令(CB prefix instruction set)はZ80に近い。また、IN/OUT命令をメモリマップで代用しているから6502っぽさも感じられます。(Z80をよりゲーム用に洗練させた感じなので、GBZ80という通称が一番しっくりくる)
敢えて、8080派生 or Z80派生のどちらが正しいかを「CPUの設計過程でどちらをベースCPUにしていたか」という観点で推測すると、
Z80派生が正しいと思います。というのも8080をLR35902化するのと、Z80をLR35902化するのなら後者の方が設計コストが圧倒的に低いので。
(8080派生だとするとCBプレフィクス命令の追加設計が物量的に重そうだし、bit/set/res命令辺りは普通にand/orで代用できてand/or比で性能的なメリットも無いから、ゲーム用の機能としてわざわざ新設する意味がないような気がするので)