WOZ: #672
. Even disk i/o read accesses will update the data latch . All disk i/o write accesses will update the data latch
This commit is contained in:
parent
7987883847
commit
b770306496
2 changed files with 130 additions and 96 deletions
222
source/Disk.cpp
222
source/Disk.cpp
|
@ -1046,7 +1046,7 @@ void Disk2InterfaceCard::UpdateBitStreamOffsets(FloppyDisk& floppy)
|
|||
floppy.m_bitMask = 1 << remainder;
|
||||
}
|
||||
|
||||
void __stdcall Disk2InterfaceCard::ReadWriteWOZ(WORD pc, WORD addr, BYTE bWrite, BYTE d, ULONG uExecutedCycles)
|
||||
UINT Disk2InterfaceCard::DataLatchReadWriteCommonWOZ(ULONG uExecutedCycles)
|
||||
{
|
||||
/* m_floppyLoadMode = 0; */
|
||||
FloppyDrive& drive = m_floppyDrive[m_currDrive];
|
||||
|
@ -1059,7 +1059,7 @@ void __stdcall Disk2InterfaceCard::ReadWriteWOZ(WORD pc, WORD addr, BYTE bWrite,
|
|||
{
|
||||
_ASSERT(0); // Can't happen for WOZ - ReadTrack() should return an empty track
|
||||
m_floppyLatch = 0xFF;
|
||||
return;
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Don't change latch if drive off after 1 second drive-off delay (UTAIIe page 9-13)
|
||||
|
@ -1067,7 +1067,7 @@ void __stdcall Disk2InterfaceCard::ReadWriteWOZ(WORD pc, WORD addr, BYTE bWrite,
|
|||
// Note: Sherwood Forest sets shift mode and reads with the drive off.
|
||||
// TODO: And same for a write?
|
||||
if (!drive.m_spinning) // GH#599
|
||||
return;
|
||||
return 0;
|
||||
|
||||
CpuCalcCycles(uExecutedCycles);
|
||||
|
||||
|
@ -1095,118 +1095,145 @@ void __stdcall Disk2InterfaceCard::ReadWriteWOZ(WORD pc, WORD addr, BYTE bWrite,
|
|||
|
||||
m_diskLastCycle = g_nCumulativeCycles;
|
||||
|
||||
//
|
||||
return bitCellRemainder;
|
||||
}
|
||||
|
||||
if (!m_floppyWriteMode)
|
||||
void __stdcall Disk2InterfaceCard::DataLatchReadWOZ(WORD pc, WORD addr, BYTE d, ULONG uExecutedCycles)
|
||||
{
|
||||
_ASSERT(!m_floppyWriteMode);
|
||||
|
||||
const UINT bitCellRemainder = DataLatchReadWriteCommonWOZ(uExecutedCycles);
|
||||
if (!bitCellRemainder)
|
||||
return;
|
||||
|
||||
// m_diskLastReadLatchCycle = g_nCumulativeCycles; // Not used by WOZ (only by NIB)
|
||||
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
bool newLatchData = false;
|
||||
#endif
|
||||
|
||||
FloppyDrive& drive = m_floppyDrive[m_currDrive];
|
||||
FloppyDisk& floppy = drive.m_disk;
|
||||
|
||||
for (UINT i = 0; i < bitCellRemainder; i++)
|
||||
{
|
||||
// m_diskLastReadLatchCycle = g_nCumulativeCycles; // Not used by WOZ (only by NIB)
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
bool newLatchData = false;
|
||||
#endif
|
||||
BYTE n = floppy.m_trackimage[floppy.m_byte];
|
||||
|
||||
for (UINT i = 0; i < bitCellRemainder; i++)
|
||||
drive.m_headWindow <<= 1;
|
||||
drive.m_headWindow |= (n & floppy.m_bitMask) ? 1 : 0;
|
||||
BYTE outputBit = (drive.m_headWindow & 0xf) ? (drive.m_headWindow >> 1) & 1
|
||||
: rand() & 1;
|
||||
|
||||
floppy.m_bitMask >>= 1;
|
||||
if (!floppy.m_bitMask)
|
||||
{
|
||||
BYTE n = floppy.m_trackimage[floppy.m_byte];
|
||||
floppy.m_bitMask = 1 << 7;
|
||||
floppy.m_byte++;
|
||||
}
|
||||
|
||||
drive.m_headWindow <<= 1;
|
||||
drive.m_headWindow |= (n & floppy.m_bitMask) ? 1 : 0;
|
||||
BYTE outputBit = (drive.m_headWindow & 0xf) ? (drive.m_headWindow >> 1) & 1
|
||||
: rand() & 1;
|
||||
floppy.m_bitOffset++;
|
||||
if (floppy.m_bitOffset == floppy.m_bitCount)
|
||||
{
|
||||
floppy.m_bitMask = 1 << 7;
|
||||
floppy.m_bitOffset = 0;
|
||||
floppy.m_byte = 0;
|
||||
}
|
||||
|
||||
floppy.m_bitMask >>= 1;
|
||||
if (!floppy.m_bitMask)
|
||||
if (m_resetSequencer)
|
||||
{
|
||||
m_resetSequencer = false; // LSS takes some cycles to reset (ref?)
|
||||
continue;
|
||||
}
|
||||
|
||||
//
|
||||
|
||||
m_shiftReg <<= 1;
|
||||
m_shiftReg |= outputBit;
|
||||
|
||||
if (m_latchDelay)
|
||||
{
|
||||
m_latchDelay -= 4;
|
||||
if (m_latchDelay < 0)
|
||||
m_latchDelay = 0;
|
||||
|
||||
if (m_shiftReg)
|
||||
{
|
||||
floppy.m_bitMask = 1 << 7;
|
||||
floppy.m_byte++;
|
||||
m_dbgLatchDelayedCnt = 0;
|
||||
}
|
||||
|
||||
floppy.m_bitOffset++;
|
||||
if (floppy.m_bitOffset == floppy.m_bitCount)
|
||||
else // m_shiftReg==0
|
||||
{
|
||||
floppy.m_bitMask = 1 << 7;
|
||||
floppy.m_bitOffset = 0;
|
||||
floppy.m_byte = 0;
|
||||
}
|
||||
m_latchDelay += 4; // extend by 4us (so 7us again) - GH#662
|
||||
|
||||
if (m_resetSequencer)
|
||||
{
|
||||
m_resetSequencer = false; // LSS takes some cycles to reset (ref?)
|
||||
continue;
|
||||
}
|
||||
|
||||
//
|
||||
|
||||
m_shiftReg <<= 1;
|
||||
m_shiftReg |= outputBit;
|
||||
|
||||
if (m_latchDelay)
|
||||
{
|
||||
m_latchDelay -= 4;
|
||||
if (m_latchDelay < 0)
|
||||
m_latchDelay = 0;
|
||||
|
||||
if (m_shiftReg)
|
||||
{
|
||||
m_dbgLatchDelayedCnt = 0;
|
||||
}
|
||||
else // m_shiftReg==0
|
||||
{
|
||||
m_latchDelay += 4; // extend by 4us (so 7us again) - GH#662
|
||||
|
||||
m_dbgLatchDelayedCnt++;
|
||||
m_dbgLatchDelayedCnt++;
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
if (m_dbgLatchDelayedCnt >= 3)
|
||||
{
|
||||
LOG_DISK("read: latch held due to 0: PC=%04X, cnt=%02X\r\n", regs.pc, m_dbgLatchDelayedCnt);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
if (!m_latchDelay)
|
||||
{
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
if (newLatchData)
|
||||
if (m_dbgLatchDelayedCnt >= 3)
|
||||
{
|
||||
LOG_DISK("read skipped latch data: %04X = %02X\r\n", floppy.m_byte, m_floppyLatch);
|
||||
newLatchData = false;
|
||||
LOG_DISK("read: latch held due to 0: PC=%04X, cnt=%02X\r\n", regs.pc, m_dbgLatchDelayedCnt);
|
||||
}
|
||||
#endif
|
||||
m_floppyLatch = m_shiftReg;
|
||||
|
||||
if (m_shiftReg & 0x80)
|
||||
{
|
||||
m_latchDelay = 7;
|
||||
m_shiftReg = 0;
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
// May not actually be read by 6502 (eg. Prologue's CHKSUM 4&4 nibble pair), but still pass to the log's nibble reader
|
||||
m_formatTrack.DecodeLatchNibbleRead(m_floppyLatch);
|
||||
newLatchData = true;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
if (m_floppyLatch & 0x80)
|
||||
if (!m_latchDelay)
|
||||
{
|
||||
#if LOG_DISK_NIBBLES_USE_RUNTIME_VAR
|
||||
if (m_bLogDisk_NibblesRW)
|
||||
#endif
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
if (newLatchData)
|
||||
{
|
||||
LOG_DISK("read %04X = %02X\r\n", floppy.m_byte, m_floppyLatch);
|
||||
LOG_DISK("read skipped latch data: %04X = %02X\r\n", floppy.m_byte, m_floppyLatch);
|
||||
newLatchData = false;
|
||||
}
|
||||
#endif
|
||||
m_floppyLatch = m_shiftReg;
|
||||
|
||||
if (m_shiftReg & 0x80)
|
||||
{
|
||||
m_latchDelay = 7;
|
||||
m_shiftReg = 0;
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
// May not actually be read by 6502 (eg. Prologue's CHKSUM 4&4 nibble pair), but still pass to the log's nibble reader
|
||||
m_formatTrack.DecodeLatchNibbleRead(m_floppyLatch);
|
||||
newLatchData = true;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
#endif
|
||||
}
|
||||
else if (!floppy.m_bWriteProtected) // && m_floppyWriteMode
|
||||
|
||||
#if LOG_DISK_NIBBLES_READ
|
||||
if (m_floppyLatch & 0x80)
|
||||
{
|
||||
#if LOG_DISK_NIBBLES_USE_RUNTIME_VAR
|
||||
if (m_bLogDisk_NibblesRW)
|
||||
#endif
|
||||
{
|
||||
LOG_DISK("read %04X = %02X\r\n", floppy.m_byte, m_floppyLatch);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
// Show track status (GH#201) - NB. Prevent flooding of forcing UI to redraw!!!
|
||||
if ((floppy.m_byte & 0xFF) == 0)
|
||||
FrameDrawDiskStatus((HDC)0);
|
||||
}
|
||||
|
||||
void __stdcall Disk2InterfaceCard::DataLatchWriteWOZ(WORD pc, WORD addr, BYTE d, ULONG uExecutedCycles)
|
||||
{
|
||||
_ASSERT(m_floppyWriteMode);
|
||||
|
||||
const UINT bitCellRemainder = DataLatchReadWriteCommonWOZ(uExecutedCycles);
|
||||
if (!bitCellRemainder)
|
||||
return;
|
||||
|
||||
FloppyDrive& drive = m_floppyDrive[m_currDrive];
|
||||
FloppyDisk& floppy = drive.m_disk;
|
||||
|
||||
if (!floppy.m_bWriteProtected)
|
||||
{
|
||||
//TODO
|
||||
}
|
||||
|
||||
// Show track status (GH#201) - NB. Prevent flooding of forcing UI to redraw!!!
|
||||
if ((floppy.m_byte & 0xFF) == 0)
|
||||
FrameDrawDiskStatus( (HDC)0 );
|
||||
FrameDrawDiskStatus((HDC)0);
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
|
@ -1516,9 +1543,7 @@ BYTE __stdcall Disk2InterfaceCard::IORead(WORD pc, WORD addr, BYTE bWrite, BYTE
|
|||
case 0x9: pCard->ControlMotor(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xA: pCard->Enable(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xB: pCard->Enable(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xC: if (!isWOZ) pCard->ReadWrite(pc, addr, bWrite, d, nExecutedCycles);
|
||||
else pCard->ReadWriteWOZ(pc, addr, bWrite, d, nExecutedCycles);
|
||||
break;
|
||||
case 0xC: if (!isWOZ) pCard->ReadWrite(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xD: pCard->LoadWriteProtect(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xE: pCard->SetReadMode(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xF: pCard->SetWriteMode(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
|
@ -1526,9 +1551,14 @@ BYTE __stdcall Disk2InterfaceCard::IORead(WORD pc, WORD addr, BYTE bWrite, BYTE
|
|||
|
||||
// only even addresses return the latch (UTAIIe Table 9.1)
|
||||
if (!(addr & 1))
|
||||
{
|
||||
if (isWOZ)
|
||||
pCard->DataLatchReadWOZ(pc, addr, d, nExecutedCycles);
|
||||
|
||||
return pCard->m_floppyLatch;
|
||||
else
|
||||
return MemReadFloatingBus(nExecutedCycles);
|
||||
}
|
||||
|
||||
return MemReadFloatingBus(nExecutedCycles);
|
||||
}
|
||||
|
||||
BYTE __stdcall Disk2InterfaceCard::IOWrite(WORD pc, WORD addr, BYTE bWrite, BYTE d, ULONG nExecutedCycles)
|
||||
|
@ -1553,9 +1583,7 @@ BYTE __stdcall Disk2InterfaceCard::IOWrite(WORD pc, WORD addr, BYTE bWrite, BYTE
|
|||
case 0x9: pCard->ControlMotor(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xA: pCard->Enable(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xB: pCard->Enable(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xC: if (!isWOZ) pCard->ReadWrite(pc, addr, bWrite, d, nExecutedCycles);
|
||||
else pCard->ReadWriteWOZ(pc, addr, bWrite, d, nExecutedCycles);
|
||||
break;
|
||||
case 0xC: if (!isWOZ) pCard->ReadWrite(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xD: pCard->LoadWriteProtect(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xE: pCard->SetReadMode(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
case 0xF: pCard->SetWriteMode(pc, addr, bWrite, d, nExecutedCycles); break;
|
||||
|
@ -1565,7 +1593,11 @@ BYTE __stdcall Disk2InterfaceCard::IOWrite(WORD pc, WORD addr, BYTE bWrite, BYTE
|
|||
if (pCard->m_floppyWriteMode /* && m_floppyLoadMode */)
|
||||
{
|
||||
pCard->m_floppyLatch = d;
|
||||
|
||||
if (isWOZ)
|
||||
pCard->DataLatchWriteWOZ(pc, addr, d, nExecutedCycles);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -188,6 +188,7 @@ private:
|
|||
UINT GetBitCellDelta(const BYTE optimalBitTiming);
|
||||
void UpdateBitStreamPosition(FloppyDisk& floppy, const ULONG bitCellDelta);
|
||||
void UpdateBitStreamOffsets(FloppyDisk& floppy);
|
||||
UINT DataLatchReadWriteCommonWOZ(ULONG uExecutedCycles);
|
||||
void SaveSnapshotFloppy(YamlSaveHelper& yamlSaveHelper, UINT unit);
|
||||
void SaveSnapshotDriveUnit(YamlSaveHelper& yamlSaveHelper, UINT unit);
|
||||
bool LoadSnapshotFloppy(YamlLoadHelper& yamlLoadHelper, UINT unit, UINT version, std::vector<BYTE>& track);
|
||||
|
@ -199,7 +200,8 @@ private:
|
|||
void __stdcall ControlMotor(WORD, WORD address, BYTE, BYTE, ULONG uExecutedCycles);
|
||||
void __stdcall Enable(WORD, WORD address, BYTE, BYTE, ULONG uExecutedCycles);
|
||||
void __stdcall ReadWrite(WORD pc, WORD addr, BYTE bWrite, BYTE d, ULONG uExecutedCycles);
|
||||
void __stdcall ReadWriteWOZ(WORD pc, WORD addr, BYTE bWrite, BYTE d, ULONG uExecutedCycles);
|
||||
void __stdcall DataLatchReadWOZ(WORD pc, WORD addr, BYTE d, ULONG uExecutedCycles);
|
||||
void __stdcall DataLatchWriteWOZ(WORD pc, WORD addr, BYTE d, ULONG uExecutedCycles);
|
||||
void __stdcall LoadWriteProtect(WORD, WORD, BYTE write, BYTE value, ULONG);
|
||||
void __stdcall SetReadMode(WORD, WORD, BYTE, BYTE, ULONG);
|
||||
void __stdcall SetWriteMode(WORD, WORD, BYTE, BYTE, ULONG uExecutedCycles);
|
||||
|
|
Loading…
Add table
Reference in a new issue