mirror of
https://github.com/TomHarte/CLK.git
synced 2024-12-24 12:30:17 +00:00
Added a couple of timing tests, both of which seem to pass for now.
This commit is contained in:
parent
e8f70398c1
commit
503d684af0
@ -56,6 +56,5 @@ class KlausDormannTests: XCTestCase {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -13,7 +13,9 @@ typedef NS_ENUM(NSInteger, CSTestMachineRegister) {
|
||||
CSTestMachineRegisterProgramCounter,
|
||||
CSTestMachineRegisterStackPointer,
|
||||
CSTestMachineRegisterFlags,
|
||||
CSTestMachineRegisterA
|
||||
CSTestMachineRegisterA,
|
||||
CSTestMachineRegisterX,
|
||||
CSTestMachineRegisterY,
|
||||
};
|
||||
|
||||
extern const uint8_t CSTestMachineJamOpcode;
|
||||
|
@ -51,6 +51,8 @@ class MachineJamHandler: public CPU6502::AllRAMProcessor::JamHandler {
|
||||
case CSTestMachineRegisterLastOperationAddress: return CPU6502::Register::LastOperationAddress;
|
||||
case CSTestMachineRegisterFlags: return CPU6502::Register::Flags;
|
||||
case CSTestMachineRegisterA: return CPU6502::Register::A;
|
||||
case CSTestMachineRegisterX: return CPU6502::Register::X;
|
||||
case CSTestMachineRegisterY: return CPU6502::Register::Y;
|
||||
case CSTestMachineRegisterStackPointer: return CPU6502::Register::S;
|
||||
default: break;
|
||||
}
|
||||
|
@ -18,6 +18,50 @@ class TimingTests: XCTestCase, CSTestMachineJamHandler {
|
||||
self.runTest(code, expectedRunLength: 2)
|
||||
}
|
||||
|
||||
func testLDA() {
|
||||
let code: [UInt8] = [
|
||||
0xa9, 0x00, // [2] LDA #$00
|
||||
0xa5, 0x00, // [3] LDA $00
|
||||
0xb5, 0x00, // [4] LDA $00,X
|
||||
0xad, 0x00, 0x00, // [4] LDA $0000
|
||||
0xbd, 0x00, 0x00, // [4] LDA $0000, x (no wrap)
|
||||
0xbd, 0x02, 0x00, // [5] LDA $0002, x (wrap)
|
||||
0xb9, 0x00, 0x00, // [4] LDA $0000, y (no wrap)
|
||||
0xb9, 0x10, 0x00, // [5] LDA $0010, y (wrap)
|
||||
0xa1, 0x44, // [6] LDA ($44, x)
|
||||
0xb1, 0x00, // [5] LDA ($00), y (no wrap)
|
||||
0xb1, 0x02, // [6] LDA ($01), y (wrap)
|
||||
CSTestMachineJamOpcode]
|
||||
self.runTest(code, expectedRunLength: 48)
|
||||
}
|
||||
|
||||
func testBCS() {
|
||||
let code: [UInt8] = [
|
||||
0x18, // [2] CLC
|
||||
0xb0, 0xff, // [2] BCS -1 (not taken)
|
||||
0x90, 0x7f, // [3] BCC +7f (taken)
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x90, 0x00, // [3] BCC 0 (taken)
|
||||
0x90, 0x7f, // [4] BCC +6f (taken, page wrap)
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
|
||||
CSTestMachineJamOpcode]
|
||||
self.runTest(code, expectedRunLength: 14)
|
||||
}
|
||||
|
||||
func runTest(code: [UInt8], expectedRunLength: UInt32) {
|
||||
let machine = CSTestMachine()
|
||||
|
||||
@ -25,7 +69,13 @@ class TimingTests: XCTestCase, CSTestMachineJamHandler {
|
||||
|
||||
let immediateCode = NSData(bytes: code, length: code.count)
|
||||
machine.setData(immediateCode, atAddress: 0x200)
|
||||
machine.setValue(0x00, forAddress: 0x0000)
|
||||
machine.setValue(0x00, forAddress: 0x0001)
|
||||
machine.setValue(0xff, forAddress: 0x0002)
|
||||
machine.setValue(0x00, forAddress: 0x0003)
|
||||
machine.setValue(0x200, forRegister: CSTestMachineRegister.ProgramCounter)
|
||||
machine.setValue(0xff, forRegister: CSTestMachineRegister.X)
|
||||
machine.setValue(0xfe, forRegister: CSTestMachineRegister.Y)
|
||||
|
||||
self.endTime = 0
|
||||
while self.endTime == 0 {
|
||||
@ -37,7 +87,7 @@ class TimingTests: XCTestCase, CSTestMachineJamHandler {
|
||||
|
||||
func testMachine(machine: CSTestMachine!, didJamAtAddress address: UInt16) {
|
||||
if self.endTime == 0 {
|
||||
self.endTime = machine.timestamp - 3
|
||||
self.endTime = machine.timestamp - 7
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -20,6 +20,8 @@ enum class Register {
|
||||
StackPointer,
|
||||
Flags,
|
||||
A,
|
||||
X,
|
||||
Y,
|
||||
S
|
||||
};
|
||||
|
||||
@ -61,7 +63,7 @@ template <class T> class Processor {
|
||||
CycleReadAndIncrementPC, CycleIncrementPCAndReadStack, CycleIncrementPCReadPCHLoadPCL, CycleReadPCHLoadPCL,
|
||||
CycleReadAddressHLoadAddressL, CycleReadPCLFromAddress, CycleReadPCHFromAddress, CycleLoadAddressAbsolute,
|
||||
OperationLoadAddressZeroPage, CycleLoadAddessZeroX, CycleLoadAddessZeroY, CycleAddXToAddressLow,
|
||||
CycleAddYToAddressLow, CycleCorrectAddressHigh, OperationMoveToNextProgram, OperationIncrementPC,
|
||||
CycleAddYToAddressLow, OperationCorrectAddressHigh, OperationMoveToNextProgram, OperationIncrementPC,
|
||||
CycleFetchOperandFromAddress, CycleWriteOperandToAddress, OperationCopyOperandFromA, OperationCopyOperandToA,
|
||||
CycleIncrementPCFetchAddressLowFromOperand, CycleAddXToOperandFetchAddressLow, CycleIncrementOperandFetchAddressHigh, OperationDecrementOperand,
|
||||
OperationIncrementOperand, OperationORA, OperationAND, OperationEOR,
|
||||
@ -135,13 +137,13 @@ template <class T> class Processor {
|
||||
#define Program(...) {__VA_ARGS__, OperationMoveToNextProgram}
|
||||
|
||||
#define Absolute CycleLoadAddressAbsolute
|
||||
#define AbsoluteX CycleLoadAddressAbsolute, CycleAddXToAddressLow, CycleCorrectAddressHigh
|
||||
#define AbsoluteY CycleLoadAddressAbsolute, CycleAddYToAddressLow, CycleCorrectAddressHigh
|
||||
#define AbsoluteX CycleLoadAddressAbsolute, CycleAddXToAddressLow, OperationCorrectAddressHigh
|
||||
#define AbsoluteY CycleLoadAddressAbsolute, CycleAddYToAddressLow, OperationCorrectAddressHigh
|
||||
#define Zero OperationLoadAddressZeroPage
|
||||
#define ZeroX CycleLoadAddessZeroX
|
||||
#define ZeroY CycleLoadAddessZeroY
|
||||
#define IndexedIndirect CycleIncrementPCFetchAddressLowFromOperand, CycleAddXToOperandFetchAddressLow, CycleIncrementOperandFetchAddressHigh
|
||||
#define IndirectIndexed CycleIncrementPCFetchAddressLowFromOperand, CycleIncrementOperandFetchAddressHigh, CycleAddYToAddressLow, CycleCorrectAddressHigh
|
||||
#define IndirectIndexed CycleIncrementPCFetchAddressLowFromOperand, CycleIncrementOperandFetchAddressHigh, CycleAddYToAddressLow, OperationCorrectAddressHigh
|
||||
|
||||
#define Read(op) CycleFetchOperandFromAddress, op
|
||||
#define Write(op) op, CycleWriteOperandToAddress
|
||||
@ -750,7 +752,7 @@ template <class T> class Processor {
|
||||
throwaway_read(_address.full);
|
||||
}
|
||||
break;
|
||||
case CycleCorrectAddressHigh:
|
||||
case OperationCorrectAddressHigh:
|
||||
_address.full = _nextAddress.full;
|
||||
break;
|
||||
case CycleIncrementPCFetchAddressLowFromOperand:
|
||||
@ -888,6 +890,8 @@ template <class T> class Processor {
|
||||
case Register::StackPointer: return _s;
|
||||
case Register::Flags: return get_flags();
|
||||
case Register::A: return _a;
|
||||
case Register::X: return _x;
|
||||
case Register::Y: return _y;
|
||||
case Register::S: return _s;
|
||||
default: break;
|
||||
}
|
||||
@ -900,6 +904,8 @@ template <class T> class Processor {
|
||||
case Register::StackPointer: _s = value; break;
|
||||
case Register::Flags: set_flags(value); break;
|
||||
case Register::A: _a = value; break;
|
||||
case Register::X: _x = value; break;
|
||||
case Register::Y: _y = value; break;
|
||||
case Register::S: _s = value; break;
|
||||
default: break;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user