--- nono/vm/fdc.cpp 2026/04/29 17:05:18 1.1.1.11 +++ nono/vm/fdc.cpp 2026/04/29 17:05:25 1.1.1.12 @@ -169,62 +169,79 @@ FDCDevice::Init() void FDCDevice::ResetHard(bool poweron) { - // uPD765 マニュアルによると、リセット信号によるリセットでは - // SRT, HUT, HLT は影響を受けない。 - - // シリンダ位置 pcn はとりあえずわからないので放置。 - if (poweron) { // READY ポーリングはリセットの影響を受けないはず initialized = false; scheduler->StopEvent(motor_event); } + // uPD765 マニュアルによると、リセット信号によるリセットでは + // SRT, HUT, HLT は影響を受けない。 + + // シリンダ位置 pcn はとりあえずわからないので放置。 + + // US0,US1 を low (FDD0) に。 + us = 0; + // 割り込み (と DRQ) をネゲート。 + msr.ndm = false; + st0.ic = ST0_IC_IC; + st0.se = false; + st0.ec = false; + st0.nr = false; + st0.hd = false; + st0.us = 0; + ChangeInterrupt(); + scheduler->StopEvent(phase_event); scheduler->StopEvent(poll_event); CommandPhase(); } -uint64 +busdata FDCDevice::Read(uint32 offset) { - mpu->AddCycle(19); // InsideOut p.135 + busdata data; switch (offset) { case 0: - { if (dack) { // DACK が立っているときは A0 によらずデータレジスタをアクセス - return ReadData(); + data = ReadData(); + } else { + data = GetMSR(); + putlog(4, "STAT -> $%02x", data.Data()); } - - uint8 stat = GetMSR(); - putlog(4, "STAT -> $%02x", stat); - return stat; - } + break; case 1: - return ReadData(); + data = ReadData(); + break; case 2: - return ReadDriveStatus(); + data = ReadDriveStatus(); + break; case 3: - return 0xff; + data = 0xff; + break; default: VMPANIC("corrupted offset=%d", offset); } + + // InsideOut p.135 + const busdata wait = busdata::Wait(19 * 40_nsec); + data |= wait; + + return data; } -uint64 +busdata FDCDevice::Write(uint32 offset, uint32 data) { - mpu->AddCycle(19); // InsideOut p.135 - switch (offset) { case 0: if (dack) { // DACK が立っているときは A0 によらずデータレジスタをアクセス WriteDataReg(data); - return 0; + break; } // ここはフェーズに関わらず 0x34, 0x35, 0x36 のコマンドだけを @@ -245,11 +262,11 @@ FDCDevice::Write(uint32 offset, uint32 d data); break; } - return 0; + break; case 1: WriteCmd(data); - return 0; + break; case 2: { @@ -267,7 +284,7 @@ FDCDevice::Write(uint32 offset, uint32 d bit <<= 1; } drivectrl = data; - return 0; + break; } case 3: @@ -319,14 +336,19 @@ FDCDevice::Write(uint32 offset, uint32 d f->SetDriveSelect(accdrive, is2DD); } } - return 0; + break; } default: VMPANIC("corrupted offset=%d", offset); } + + // InsideOut p.135 + const busdata wait = busdata::Wait(19 * 40_nsec); + + return wait; } -uint64 +busdata FDCDevice::Peek(uint32 offset) { switch (offset) {