mirror of
https://github.com/AppleWin/AppleWin.git
synced 2024-06-03 13:29:40 +00:00
Flux track working with test ProDOS image
This commit is contained in:
parent
9478739a15
commit
28b9e23ebc
176
source/Disk.cpp
176
source/Disk.cpp
|
@ -352,7 +352,7 @@ void Disk2InterfaceCard::ReadTrack(const int drive, ULONG uExecutedCycles)
|
|||
{
|
||||
pFloppy->m_byte = 0;
|
||||
}
|
||||
else
|
||||
else if (!pFloppy->m_isFluxTrack)
|
||||
{
|
||||
// NB. This function is only called for a new track when there's a latch read, ie. only for *even* DEVICE SELECT I/O accesses.
|
||||
// . So when seeking across tracks (ie. sequencing through the magnet phases), then not all (quarter) tracks will need reading.
|
||||
|
@ -384,6 +384,13 @@ void Disk2InterfaceCard::ReadTrack(const int drive, ULONG uExecutedCycles)
|
|||
|
||||
FindTrackSeamWOZ(*pFloppy, pDrive->m_phasePrecise/2);
|
||||
}
|
||||
else // WOZ && Flux track
|
||||
{
|
||||
pFloppy->m_byte = 0; // For flux tracks: cross-track sync is hard! (So ignore for now)
|
||||
//pFloppy->m_tickCount = 0;
|
||||
NextFluxData(*pFloppy);
|
||||
memset(&pDrive->m_headWindowFlux, 0, sizeof(pDrive->m_headWindowFlux));
|
||||
}
|
||||
|
||||
pFloppy->m_trackimagedata = (pFloppy->m_nibbles != 0);
|
||||
|
||||
|
@ -1340,6 +1347,29 @@ void __stdcall Disk2InterfaceCard::DataLatchReadWriteWOZ(WORD pc, WORD addr, BYT
|
|||
if (!drive.m_spinning) // GH#599
|
||||
return;
|
||||
|
||||
if (floppy.m_isFluxTrack)
|
||||
{
|
||||
if (!bWrite)
|
||||
{
|
||||
if (m_seqFunc.function != readSequencing)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
uint64_t cycleDelta = g_nCumulativeCycles - m_diskLastCycle;
|
||||
const UINT MAX_TRACK_CYCLE_SIZE = 0x1C00 * 8 * 4; // max nibbles * 8 (bits) * 4 (usec/bit)
|
||||
if (cycleDelta > MAX_TRACK_CYCLE_SIZE)
|
||||
cycleDelta = MAX_TRACK_CYCLE_SIZE;
|
||||
|
||||
m_diskLastCycle = g_nCumulativeCycles;
|
||||
|
||||
UINT ticks = ((UINT)cycleDelta) * 8; // 125ns units
|
||||
DataLatchReadWOZFlux(pc, addr, ticks);
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// Skipping forward a large amount of bitcells means the bitstream will very likely be out-of-sync.
|
||||
// The first 1-bit will produce a latch nibble, and this 1-bit is unlikely to be the nibble's high bit.
|
||||
// So we need to ensure we run enough bits through the sequencer to re-sync.
|
||||
|
@ -1485,6 +1515,150 @@ void Disk2InterfaceCard::DataLatchReadWOZ(WORD pc, WORD addr, UINT bitCellRemain
|
|||
#endif
|
||||
}
|
||||
|
||||
void Disk2InterfaceCard::NextFluxData(FloppyDisk& floppy)
|
||||
{
|
||||
floppy.m_zeroTickCount = 0;
|
||||
do
|
||||
{
|
||||
BYTE data = floppy.m_trackimage[floppy.m_byte++];
|
||||
if (floppy.m_byte == floppy.m_nibbles)
|
||||
floppy.m_byte = 0;
|
||||
floppy.m_zeroTickCount += data;
|
||||
if (data != 255)
|
||||
break;
|
||||
} while (1);
|
||||
|
||||
floppy.m_bitCellCount = (floppy.m_zeroTickCount + 0x0f) / 0x20;
|
||||
floppy.m_tickCountdown = (floppy.m_bitCellCount > 1) ? 0x20 : floppy.m_zeroTickCount; // last one may be eg. 0x1E,0x20,0x22
|
||||
|
||||
// floppy.m_zeroTickCount += 0x0f;
|
||||
// floppy.m_zeroTickCount &= ~0x1f;
|
||||
// _ASSERT(floppy.m_zeroTickCount);
|
||||
}
|
||||
|
||||
void Disk2InterfaceCard::DataLatchReadWOZFlux(WORD pc, WORD addr, UINT ticks)
|
||||
{
|
||||
static int dbg = 0;
|
||||
#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 < ticks; i++)
|
||||
{
|
||||
#if 0
|
||||
uint32_t bit0 = floppy.m_zeroTickCount ? 0 : 1;
|
||||
|
||||
// m_headWindowFlux[3,..,0] <<= 1
|
||||
for (int j = 0; j < 4; j++)
|
||||
{
|
||||
uint32_t highBit = drive.m_headWindowFlux[j] & 0x80000000 ? 1 : 0;
|
||||
drive.m_headWindowFlux[j] = (drive.m_headWindowFlux[j] << 1) | bit0;
|
||||
bit0 = highBit;
|
||||
}
|
||||
|
||||
if (floppy.m_zeroTickCount == 0)
|
||||
NextFluxData(floppy);
|
||||
else
|
||||
floppy.m_zeroTickCount--;
|
||||
|
||||
floppy.m_tickCount++;
|
||||
floppy.m_tickCount &= 0x1f;
|
||||
if (floppy.m_tickCount)
|
||||
continue;
|
||||
|
||||
//
|
||||
|
||||
// BYTE outputBit = (drive.m_headWindow & 0xf) ? (drive.m_headWindow >> 1) & 1
|
||||
// : (rand() < RAND_THRESHOLD(3, 10)) ? 1 : 0; // ~30% chance of a 1 bit (Ref: WOZ-2.0)
|
||||
|
||||
BYTE outputBit = drive.m_headWindowFlux[1] ? 1 : 0;
|
||||
|
||||
if (dbg)
|
||||
{
|
||||
LogOutput("%d : %08X\n", outputBit, drive.m_headWindowFlux[1]);
|
||||
}
|
||||
#endif
|
||||
|
||||
floppy.m_zeroTickCount--;
|
||||
|
||||
floppy.m_tickCountdown--;
|
||||
if (floppy.m_tickCountdown)
|
||||
continue;
|
||||
|
||||
floppy.m_bitCellCount--;
|
||||
|
||||
BYTE outputBit = floppy.m_bitCellCount ? 0 : 1; // TODO: MC3470 random chance of a 1 bit
|
||||
|
||||
if (outputBit == 0)
|
||||
{
|
||||
if (floppy.m_bitCellCount > 1)
|
||||
floppy.m_tickCountdown = 0x20;
|
||||
else if (floppy.m_bitCellCount == 1)
|
||||
floppy.m_tickCountdown = floppy.m_zeroTickCount; // last one may be eg. 0x1E,0x20,0x22
|
||||
}
|
||||
else
|
||||
{
|
||||
NextFluxData(floppy);
|
||||
}
|
||||
|
||||
//
|
||||
|
||||
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++;
|
||||
#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)
|
||||
{
|
||||
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
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void Disk2InterfaceCard::DataLoadWriteWOZ(WORD pc, WORD addr, UINT bitCellRemainder)
|
||||
{
|
||||
_ASSERT(m_seqFunc.function == dataLoadWrite);
|
||||
|
|
|
@ -70,6 +70,10 @@ public:
|
|||
m_trackimagedata = false;
|
||||
m_trackimagedirty = false;
|
||||
m_isFluxTrack = false;
|
||||
m_zeroTickCount = 0;
|
||||
m_bitCellCount = 0;
|
||||
// m_tickCount = 0;
|
||||
m_tickCountdown = 0;
|
||||
m_longestSyncFFRunLength = 0;
|
||||
m_longestSyncFFBitOffsetStart = -1;
|
||||
m_initialBitOffset = 0;
|
||||
|
@ -92,6 +96,10 @@ public:
|
|||
bool m_trackimagedata;
|
||||
bool m_trackimagedirty;
|
||||
bool m_isFluxTrack;
|
||||
UINT m_zeroTickCount; // Flux data: # of ticks (zeros) until next flux transition (one)
|
||||
UINT m_bitCellCount;
|
||||
// UINT m_tickCount;
|
||||
UINT m_tickCountdown;
|
||||
UINT m_longestSyncFFRunLength;
|
||||
int m_longestSyncFFBitOffsetStart;
|
||||
UINT m_initialBitOffset; // debug
|
||||
|
@ -116,6 +124,7 @@ public:
|
|||
m_lastStepperCycle = 0;
|
||||
m_motorOnCycle = 0;
|
||||
m_headWindow = 0;
|
||||
memset(&m_headWindowFlux, 0, sizeof(m_headWindowFlux));
|
||||
m_spinning = 0;
|
||||
m_writelight = 0;
|
||||
m_disk.clear();
|
||||
|
@ -128,6 +137,7 @@ public:
|
|||
unsigned __int64 m_lastStepperCycle;
|
||||
unsigned __int64 m_motorOnCycle;
|
||||
BYTE m_headWindow;
|
||||
uint32_t m_headWindowFlux[4]; // 32 bits / 4us (0.125ms x 8 x 4 = 4us)
|
||||
DWORD m_spinning;
|
||||
DWORD m_writelight;
|
||||
FloppyDisk m_disk;
|
||||
|
@ -214,7 +224,9 @@ private:
|
|||
void UpdateBitStreamPosition(FloppyDisk& floppy, const ULONG bitCellDelta);
|
||||
void UpdateBitStreamOffsets(FloppyDisk& floppy);
|
||||
__forceinline void IncBitStream(FloppyDisk& floppy);
|
||||
void NextFluxData(FloppyDisk& floppy);
|
||||
void DataLatchReadWOZ(WORD pc, WORD addr, UINT bitCellRemainder);
|
||||
void DataLatchReadWOZFlux(WORD pc, WORD addr, UINT ticks);
|
||||
void DataLoadWriteWOZ(WORD pc, WORD addr, UINT bitCellRemainder);
|
||||
void DataShiftWriteWOZ(WORD pc, WORD addr, ULONG uExecutedCycles);
|
||||
void SetSequencerFunction(WORD addr, ULONG executedCycles);
|
||||
|
|
Loading…
Reference in New Issue
Block a user