Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
105 changes: 46 additions & 59 deletions CPU_emu/Class_CPU.cs → CPU_emu/CPU/CPU.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,11 @@ namespace CPU_emulator;

public partial class CPU
{

public uint PC { get; set; } = 0xFFFC; // ProgramCounter
public bool SlowDown { get; set; } = false;
public int SlowDownTime { get; set; } = 750; //

public ushort SP; // StackPointer
public byte A, X, Y; // registers
private ushort ResetVector = 0xFFFC;
Expand All @@ -29,16 +29,16 @@ public partial class CPU
private bool _ExitRequested;
private bool _SteppingMode;
internal ulong _CpuCycle;
private const uint MAX_MEM = 1024 * 64;
private byte[] Data = new byte[MAX_MEM];
//private const uint MAX_MEM = 1024 * 64;
//private byte[] Data = new byte[MAX_MEM];

MemoryBus _memoryBus;
MappedBus _memoryBus;

private byte
NegativeFlagBit = 0b10000000,
OverflowFlagBit = 0b01000000,
BreakFlagBit = 0b000010000,
UnusedFlagBit = 0b000100000,
BreakFlagBit = 0b000010000,
UnusedFlagBit = 0b000100000,
InterruptDisableFlagBit = 0b000000100,
ZeroBit = 0b00000001;

Expand All @@ -51,31 +51,33 @@ public byte[] Memory
{
get
{
return Data;
return _memoryBus.Dump(0, _memoryBus.RamSize);
}

set
{
Data = value;
//Data = value;
_memoryBus.Load(0, value);
OnMemoryUpdate?.Invoke(this, new CPUEventArgs(this));
}
}

//public uint PC { get => pC; set => pC = value; }
//public uint InitialPC { get => _initialPC; set => _initialPC = value; }

public event EventHandler<CPUEventArgs> OnFlagsUpdate;
public event EventHandler<CPUEventArgs> OnMemoryUpdate;
public event EventHandler<CPUEventArgs> OnRegisterUpdate;
public event EventHandler<CPUEventArgs> OnCpuCycleIncrement;
public event EventHandler<CPUEventArgs> OnProgramCounterUpdate;
public event EventHandler<CPUEventArgs> OnStackPointerUpdate;
public event EventHandler<CPUEventArgs> OnPCoverflow;
public event EventHandler<CPUEventArgs> OnBreak;
public CPU()
public event EventHandler<CPUEventArgs>? OnFlagsUpdate;
public event EventHandler<CPUEventArgs>? OnMemoryUpdate;
public event EventHandler<CPUEventArgs>? OnRegisterUpdate;
public event EventHandler<CPUEventArgs>? OnCpuCycleIncrement;
public event EventHandler<CPUEventArgs>? OnProgramCounterUpdate;
public event EventHandler<CPUEventArgs>? OnStackPointerUpdate;
public event EventHandler<CPUEventArgs>? OnPCoverflow;
public event EventHandler<CPUEventArgs>? OnBreak;

public CPU(MappedBus memoryBus)
{
_memoryBus = new MemoryBus(ref Data);
//_memoryBus = new MemoryBus(ref Data);
_memoryBus = memoryBus;
SetVectors();
}

Expand All @@ -97,7 +99,7 @@ public void Reset()
SetRegister("A", 0);
SetRegister("X", 0);
SetRegister("Y", 0);

ExitRequested = false;

// set all status flags to false
Expand All @@ -111,24 +113,24 @@ public void Reset()

}



public void Start()
{
ExitRequested = false;

var CpuRunner = new BackgroundWorker();
CpuRunner.DoWork += CpuRunner_DoWork;
CpuRunner.RunWorkerAsync();
}


private void CpuRunner_DoWork(object sender, DoWorkEventArgs e)
{

Type thisType = this.GetType();


while (CpuIsRunning)
{
byte instruction = FetchByte();
Expand All @@ -143,7 +145,7 @@ private void CpuRunner_DoWork(object sender, DoWorkEventArgs e)
{
break;
}
if (PC >= MAX_MEM)
if (PC >= _memoryBus.RamSize)
{
OnPCoverflow?.Invoke(this, new CPUEventArgs(this));
break;
Expand Down Expand Up @@ -184,11 +186,6 @@ private void CallInstruction(Type thisType, byte instruction)
}
}

private uint AddrAbsolute()
{
return FetchWord(ref _CpuCycle);
}

private byte PullByteFromStack(ref ulong CpuCycle)
{
IncrementSP();
Expand All @@ -198,13 +195,13 @@ private byte PullByteFromStack(ref ulong CpuCycle)
return b;
}

private void PushByteToStack(byte b,ref ulong CpuCycle)
private void PushByteToStack(byte b, ref ulong CpuCycle)
{
WriteByteToMemory(b, SP);
IncrementCpuCycle(1);
DecrementSP();
IncrementCpuCycle(1);

}

public void Stop()
Expand All @@ -222,48 +219,41 @@ private void SetZeroAndNegativeFlags(byte register)

private byte FetchByte()
{
//byte data = Data[PC];
byte data = _memoryBus.Read((ushort)PC);
IncrementPC();
IncrementCpuCycle(1);
return data;
}

private ushort FetchWord(ref ulong CpuCycle)
private ushort FetchWord()
{
ushort LoByte = ReadByteFromMemory((ushort)PC);
PC++;
IncrementPC();
ushort HiByte = (ushort)(ReadByteFromMemory((ushort)PC) << 8);
IncrementPC();

IncrementCpuCycle(2);

return LoByte |= HiByte;
}

public void WriteByteToMemory(byte b,ushort address)
public void WriteByteToMemory(byte b, ushort address)
{
//Data[address] = b;
_memoryBus.Write(address, b);
OnMemoryUpdate?.Invoke(this, new CPUEventArgs(this));
}

private byte ReadByteFromMemory(ushort address)
{
//return Data[address];
return _memoryBus.Read(address);
}

private ushort ReadWordFromMemory(ushort address)
{
//ushort tmpPC = ReadByteFromMemory(ResetVector);
//ResetVector++;
//tmpPC |= (ushort)(ReadByteFromMemory(ResetVector) << 8);


ushort LoByte = ReadByteFromMemory(address);
address++;
ushort HiByte = (ushort)(ReadByteFromMemory(address) <<8);
ushort HiByte = (ushort)(ReadByteFromMemory(address) << 8);

return LoByte |= HiByte;
}

Expand Down Expand Up @@ -293,7 +283,7 @@ private void IncrementCpuCycle(ulong count)

private void ResetCpuCycle()
{
_CpuCycle =0;
_CpuCycle = 0;
OnCpuCycleIncrement?.Invoke(this, new CPUEventArgs(this));
}

Expand All @@ -314,8 +304,8 @@ public void DecrementPC()
PC--;
OnProgramCounterUpdate?.Invoke(this, new CPUEventArgs(this));
}
//UT


public void SetRegister(string regname, byte value)
{
switch (regname)
Expand All @@ -334,28 +324,25 @@ public void SetRegister(string regname, byte value)
}
OnRegisterUpdate?.Invoke(this, new CPUEventArgs(this));
}
//UT

public void ResetMemory()
{
for (int i = 0; i < MAX_MEM; i++)
{
Data[i] = 0x00;
}
_memoryBus.EraseRam();

SetVectors();

OnMemoryUpdate?.Invoke(this, new CPUEventArgs(this));
}
public byte[] ReadMemory()
{
return Data;
return _memoryBus.DumpRam();
}

internal void UpdateMemoryRange(byte[] data, int startAddress)
{
for (int i = 0; i < data.Length; i++)
{
Memory[startAddress + i] = data[i];
_memoryBus.Write((ushort)(startAddress + i), data[i]);
}

OnMemoryUpdate?.Invoke(this, new CPUEventArgs(this));
Expand All @@ -364,7 +351,7 @@ internal void UpdateMemoryRange(byte[] data, int startAddress)

public class CPUEventArgs : EventArgs
{
CPU cpu = new CPU();
CPU cpu;

public string Message { get; set; }
public byte[] Memory { get; set; }
Expand Down Expand Up @@ -395,5 +382,5 @@ private void SetProperties()
Cycles = cpu._CpuCycle;
}


}
81 changes: 70 additions & 11 deletions CPU_emu/CPU_emu.CMD_Methods.cs → CPU_emu/CPU/CPU_CMD_Methods.cs
Original file line number Diff line number Diff line change
Expand Up @@ -15,29 +15,85 @@ public void Cmd_00()
#endregion

#region LDA
// Load Accumulator immidiate A9

[Opcode(2)]
public void Cmd_A9()
public void Cmd_A9() // Load Accumulator immidiate A9
{
SetRegister("A", FetchByte());
byte value = AddrImmediate();
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// Load Accumulator zeropage A5
public void Cmd_A5()
// LDA $zz
[Opcode(2)]
public void Cmd_A5() // Load Accumulator zeropage A5
{
SetRegister("A", ReadByteFromMemory(FetchByte()));
ushort addr = AddrZeroPage();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// Load Accumulator zeropage X B5
public void Cmd_B5()
// LDA $zz,X
[Opcode(4)]
public void Cmd_B5() // Load Accumulator zeropage X B5
{
byte b_tmp = FetchByte();
b_tmp += X; // add regX to address
SetRegister("A", ReadByteFromMemory(b_tmp));
ushort addr = AddrZeroPageX();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// LDA $nnnn (absolute)
[Opcode(4)]
public void Cmd_AD() // Load Accumulator absolute AD
{
ushort addr = AddrAbsolute();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// LDA $nnnn,X
[Opcode(4)]
public void Cmd_BD() // Load Accumulator absolute X BD
{
ushort addr = AddrAbsoluteX();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// LDA $nnnn,Y
[Opcode(4)]
public void Cmd_B9()
{
ushort addr = AddrAbsoluteY();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// LDA ($zz,X) – Indirect,X
[Opcode(6)]
public void Cmd_A1()
{
ushort addr = AddrIndirectX();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

// LDA ($zz),Y – Indirect,Y
[Opcode(5)]
public void Cmd_B1()
{
ushort addr = AddrIndirectY();
byte value = ReadByteFromMemory(addr);
SetRegister("A", value);
SetZeroAndNegativeFlags(A);
}

#endregion

#region LDX
Expand Down Expand Up @@ -105,4 +161,7 @@ public void Cmd_48()
}

#endregion



}
Loading