--- nono/vm/bt454.cpp 2026/04/29 17:04:49 1.1.1.4 +++ nono/vm/bt454.cpp 2026/04/29 17:05:10 1.1.1.7 @@ -4,9 +4,9 @@ // Licensed under nono-license.txt // -#include "bt454.h" -#include "bitmap.h" -#include "renderer.h" +// +// BT454 +// // 仕様書には $c100_0000 と書いてあるが、PROM も NetBSD カーネルも // $c110_0000 にアクセスしている。実際には 4バイトごとにミラーが見えて @@ -14,33 +14,49 @@ // LUNA88K でも1バイトずつ連続配置されている(BusIO_B)、LUNA88K の他の多くの // デバイスのような BusIO_BFFF 配置でないので注意。 +#include "bt454.h" +#include "planevram.h" +#include "renderer.h" +#include "uimessage.h" + // 下位ニブルは 0x0f が読めるようだ #define LOW_NIBBLE (0x0f) -std::unique_ptr gBT454; +// グローバル参照用 +BT454Device *gBT454; +// コンストラクタ BT454Device::BT454Device() + : inherited("BT454") { - logname = "bt454"; - devname = "BT454"; devaddr = 0xc1000000; } +// デストラクタ BT454Device::~BT454Device() { + gBT454 = NULL; } bool BT454Device::Init() { - nplane = gBitmap->GetPlaneCount(); + nplane = gPlaneVRAM->GetPlaneCount(); + assert(nplane >= 0); return true; } +// リセット void -BT454Device::ResetHard() +BT454Device::ResetHard(bool poweron) { reg.idx = 0; + + // XXX BT454 のレジスタの初期値は不明なのでとりあえず全部黒にしておく + memset(reg.color, 0, countof(reg.color)); + for (int i = 0; i < countof(reg.color); i++) { + MakeHostColor(i); + } } /* static */ const char @@ -192,15 +208,30 @@ BT454Device::MakeHostColor(int idx) if (nplane == 1) { // 1bpp なら R,G,B のうち G の値だけを使用 if (ab == 1) { - reg.hostcolor[col * 4 + 0] = reg.color[col * 3 + 1]; - reg.hostcolor[col * 4 + 1] = reg.color[col * 3 + 1]; - reg.hostcolor[col * 4 + 2] = reg.color[col * 3 + 1]; + reg.hostcolor[col].r = reg.color[col * 3 + 1]; + reg.hostcolor[col].g = reg.color[col * 3 + 1]; + reg.hostcolor[col].b = reg.color[col * 3 + 1]; } } else { // 4bpp なら代入するだけ - reg.hostcolor[col * 4 + idx] = reg.color[col * 3 + idx]; + switch (ab) { + case 0: + reg.hostcolor[col].r = reg.color[col * 3 + ab]; + break; + case 1: + reg.hostcolor[col].g = reg.color[col * 3 + ab]; + break; + case 2: + reg.hostcolor[col].b = reg.color[col * 3 + ab]; + break; + default: + __unreachable(); + } } // パレット変更が起きたことをレンダラに通知 - gRenderer->Invalidate(); + gRenderer->Invalidate2(); + + // UI にも通知 + UIMessage::Post(UIMessage::PALETTE); }