mirror of
https://github.com/MoleskiCoder/EightBitNet.git
synced 2024-12-23 17:31:33 +00:00
Follow most of the guideline suggestions from VS2019 preview. Pretty good suggestions!
Signed-off-by: Adrian Conlon <Adrian.conlon@gmail.com>
This commit is contained in:
parent
28b7a88f0f
commit
03caba99dc
@ -54,7 +54,7 @@ namespace EightBit
|
||||
|
||||
public static int CountBits(int value)
|
||||
{
|
||||
int count = 0;
|
||||
var count = 0;
|
||||
while (value != 0)
|
||||
{
|
||||
++count;
|
||||
|
@ -18,7 +18,7 @@ namespace EightBit
|
||||
|
||||
public void Tick(int extra)
|
||||
{
|
||||
for (int i = 0; i < extra; ++i)
|
||||
for (var i = 0; i < extra; ++i)
|
||||
{
|
||||
this.Tick();
|
||||
}
|
||||
|
@ -18,7 +18,7 @@ namespace EightBit
|
||||
protected IntelProcessor(Bus bus)
|
||||
: base(bus)
|
||||
{
|
||||
for (int i = 0; i < 0x100; ++i)
|
||||
for (var i = 0; i < 0x100; ++i)
|
||||
{
|
||||
this.decodedOpCodes[i] = new IntelOpCodeDecoded((byte)i);
|
||||
}
|
||||
@ -87,10 +87,7 @@ namespace EightBit
|
||||
this.OnLoweredHALT();
|
||||
}
|
||||
|
||||
protected static int BuildHalfCarryIndex(byte before, byte value, int calculation)
|
||||
{
|
||||
return ((before & 0x88) >> 1) | ((value & 0x88) >> 2) | ((calculation & 0x88) >> 3);
|
||||
}
|
||||
protected static int BuildHalfCarryIndex(byte before, byte value, int calculation) => ((before & 0x88) >> 1) | ((value & 0x88) >> 2) | ((calculation & 0x88) >> 3);
|
||||
|
||||
protected static int CalculateHalfCarryAdd(byte before, byte value, int calculation)
|
||||
{
|
||||
|
@ -48,7 +48,7 @@ namespace EightBit
|
||||
|
||||
public int Run(int limit)
|
||||
{
|
||||
int current = 0;
|
||||
var current = 0;
|
||||
while (this.Powered && (current < limit))
|
||||
{
|
||||
current += this.Step();
|
||||
|
@ -45,10 +45,7 @@ namespace EightBit
|
||||
|
||||
public ushort Word
|
||||
{
|
||||
get
|
||||
{
|
||||
return (ushort)(this.Low | Chip.PromoteByte(this.High));
|
||||
}
|
||||
get => (ushort)(this.Low | Chip.PromoteByte(this.High));
|
||||
|
||||
set
|
||||
{
|
||||
@ -84,12 +81,7 @@ namespace EightBit
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
var rhs = obj as Register16;
|
||||
if (rhs == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return rhs.Low == this.Low && rhs.High == this.High;
|
||||
return rhs == null ? false : rhs.Low == this.Low && rhs.High == this.High;
|
||||
}
|
||||
|
||||
public override int GetHashCode() => this.Word;
|
||||
|
@ -34,15 +34,9 @@ namespace EightBit
|
||||
return returned.ToString();
|
||||
}
|
||||
|
||||
public static string Dump_ByteValue(byte value)
|
||||
{
|
||||
return value.ToString("X2");
|
||||
}
|
||||
public static string Dump_ByteValue(byte value) => value.ToString("X2");
|
||||
|
||||
public static string Dump_WordValue(ushort value)
|
||||
{
|
||||
return value.ToString("X4");
|
||||
}
|
||||
public static string Dump_WordValue(ushort value) => value.ToString("X4");
|
||||
|
||||
public string Disassemble(ushort current)
|
||||
{
|
||||
@ -503,215 +497,81 @@ namespace EightBit
|
||||
return output.ToString();
|
||||
}
|
||||
|
||||
private string ConvertAddress(ushort absolute)
|
||||
{
|
||||
if (this.symbols.Labels.TryGetValue(absolute, out string label))
|
||||
{
|
||||
return label;
|
||||
}
|
||||
private string ConvertAddress(ushort absolute) => this.symbols.Labels.TryGetValue(absolute, out var label) ? label : "$" + Dump_WordValue(absolute);
|
||||
|
||||
return "$" + Dump_WordValue(absolute);
|
||||
}
|
||||
private string ConvertAddress(byte absolute) => this.symbols.Labels.TryGetValue(absolute, out var label) ? label : "$" + Dump_ByteValue(absolute);
|
||||
|
||||
private string ConvertAddress(byte absolute)
|
||||
{
|
||||
if (this.symbols.Labels.TryGetValue(absolute, out string label))
|
||||
{
|
||||
return label;
|
||||
}
|
||||
private string ConvertConstant(ushort constant) => this.symbols.Constants.TryGetValue(constant, out var label) ? label : this.Dump_DByte(constant);
|
||||
|
||||
return "$" + Dump_ByteValue(absolute);
|
||||
}
|
||||
private string ConvertConstant(byte constant) => this.symbols.Constants.TryGetValue(constant, out var label) ? label : Dump_ByteValue(constant);
|
||||
|
||||
private string ConvertConstant(ushort constant)
|
||||
{
|
||||
if (this.symbols.Constants.TryGetValue(constant, out string label))
|
||||
{
|
||||
return label;
|
||||
}
|
||||
private byte GetByte(ushort absolute) => this.bus.Peek(absolute);
|
||||
|
||||
return this.Dump_DByte(constant);
|
||||
}
|
||||
private ushort GetWord(ushort absolute) => this.processor.PeekWord(absolute).Word;
|
||||
|
||||
private string ConvertConstant(byte constant)
|
||||
{
|
||||
if (this.symbols.Constants.TryGetValue(constant, out string label))
|
||||
{
|
||||
return label;
|
||||
}
|
||||
private string Dump_Byte(ushort absolute) => Disassembler.Dump_ByteValue(this.GetByte(absolute));
|
||||
|
||||
return Dump_ByteValue(constant);
|
||||
}
|
||||
private string Dump_DByte(ushort absolute) => this.Dump_Byte(absolute) + " " + this.Dump_Byte(++absolute);
|
||||
|
||||
private byte GetByte(ushort absolute)
|
||||
{
|
||||
return this.bus.Peek(absolute);
|
||||
}
|
||||
private string Dump_Word(ushort absolute) => Disassembler.Dump_WordValue(this.GetWord(absolute));
|
||||
|
||||
private ushort GetWord(ushort absolute)
|
||||
{
|
||||
return this.processor.PeekWord(absolute).Word;
|
||||
}
|
||||
private string Disassemble_Implied(string instruction) => "\t" + instruction;
|
||||
|
||||
private string Dump_Byte(ushort absolute)
|
||||
{
|
||||
return Disassembler.Dump_ByteValue(this.GetByte(absolute));
|
||||
}
|
||||
private string Disassemble_Absolute(string instruction) => this.AM_Absolute_dump() + "\t" + instruction + " " + this.AM_Absolute();
|
||||
|
||||
private string Dump_DByte(ushort absolute)
|
||||
{
|
||||
return this.Dump_Byte(absolute) + " " + this.Dump_Byte(++absolute);
|
||||
}
|
||||
private string Disassemble_Indirect(string instruction) => this.AM_Absolute_dump() + "\t" + instruction + " (" + this.AM_Absolute() + ")";
|
||||
|
||||
private string Dump_Word(ushort absolute)
|
||||
{
|
||||
return Disassembler.Dump_WordValue(this.GetWord(absolute));
|
||||
}
|
||||
private string Disassemble_Relative(string instruction, ushort absolute) => this.AM_Immediate_dump() + "\t" + instruction + " $" + Disassembler.Dump_WordValue(absolute);
|
||||
|
||||
private string Disassemble_Implied(string instruction)
|
||||
{
|
||||
return "\t" + instruction;
|
||||
}
|
||||
private string Disassemble_Immediate(string instruction) => this.AM_Immediate_dump() + "\t" + instruction + " " + this.AM_Immediate();
|
||||
|
||||
private string Disassemble_Absolute(string instruction)
|
||||
{
|
||||
return this.AM_Absolute_dump() + "\t" + instruction + " " + this.AM_Absolute();
|
||||
}
|
||||
private string Disassemble_AM_00(int bbb, string instruction) => this.AM_00_dump(bbb) + "\t" + instruction + " " + this.AM_00(bbb);
|
||||
|
||||
private string Disassemble_Indirect(string instruction)
|
||||
{
|
||||
return this.AM_Absolute_dump() + "\t" + instruction + " (" + this.AM_Absolute() + ")";
|
||||
}
|
||||
private string Disassemble_AM_01(int bbb, string instruction) => this.AM_01_dump(bbb) + "\t" + instruction + " " + this.AM_01(bbb);
|
||||
|
||||
private string Disassemble_Relative(string instruction, ushort absolute)
|
||||
{
|
||||
return this.AM_Immediate_dump() + "\t" + instruction + " $" + Disassembler.Dump_WordValue(absolute);
|
||||
}
|
||||
private string Disassemble_AM_10(int bbb, string instruction) => this.AM_10_dump(bbb) + "\t" + instruction + " " + this.AM_10(bbb);
|
||||
|
||||
private string Disassemble_Immediate(string instruction)
|
||||
{
|
||||
return this.AM_Immediate_dump() + "\t" + instruction + " " + this.AM_Immediate();
|
||||
}
|
||||
private string Disassemble_AM_10_x(int bbb, string instruction) => this.AM_10_x_dump(bbb) + "\t" + instruction + " " + this.AM_10_x(bbb);
|
||||
|
||||
private string Disassemble_AM_00(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_00_dump(bbb) + "\t" + instruction + " " + this.AM_00(bbb);
|
||||
}
|
||||
private string Disassemble_AM_11(int bbb, string instruction) => this.AM_11_dump(bbb) + "\t" + instruction + " " + this.AM_11(bbb);
|
||||
|
||||
private string Disassemble_AM_01(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_01_dump(bbb) + "\t" + instruction + " " + this.AM_01(bbb);
|
||||
}
|
||||
private string Disassemble_AM_11_x(int bbb, string instruction) => this.AM_11_x_dump(bbb) + "\t" + instruction + " " + this.AM_11_x(bbb);
|
||||
|
||||
private string Disassemble_AM_10(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_10_dump(bbb) + "\t" + instruction + " " + this.AM_10(bbb);
|
||||
}
|
||||
private string AM_Immediate_dump() => this.Dump_Byte((ushort)(this.address + 1));
|
||||
|
||||
private string Disassemble_AM_10_x(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_10_x_dump(bbb) + "\t" + instruction + " " + this.AM_10_x(bbb);
|
||||
}
|
||||
private string AM_Immediate() => "#$" + this.AM_Immediate_dump();
|
||||
|
||||
private string Disassemble_AM_11(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_11_dump(bbb) + "\t" + instruction + " " + this.AM_11(bbb);
|
||||
}
|
||||
private string AM_Absolute_dump() => this.Dump_DByte((ushort)(this.address + 1));
|
||||
|
||||
private string Disassemble_AM_11_x(int bbb, string instruction)
|
||||
{
|
||||
return this.AM_11_x_dump(bbb) + "\t" + instruction + " " + this.AM_11_x(bbb);
|
||||
}
|
||||
private string AM_Absolute() => "$" + this.Dump_Word((ushort)(this.address + 1));
|
||||
|
||||
private string AM_Immediate_dump()
|
||||
{
|
||||
return this.Dump_Byte((ushort)(this.address + 1));
|
||||
}
|
||||
private string AM_ZeroPage_dump() => this.Dump_Byte((ushort)(this.address + 1));
|
||||
|
||||
private string AM_Immediate()
|
||||
{
|
||||
return "#$" + this.AM_Immediate_dump();
|
||||
}
|
||||
private string AM_ZeroPage() => "$" + this.Dump_Byte((ushort)(this.address + 1));
|
||||
|
||||
private string AM_Absolute_dump()
|
||||
{
|
||||
return this.Dump_DByte((ushort)(this.address + 1));
|
||||
}
|
||||
private string AM_ZeroPageX_dump() => this.AM_ZeroPage_dump();
|
||||
|
||||
private string AM_Absolute()
|
||||
{
|
||||
return "$" + this.Dump_Word((ushort)(this.address + 1));
|
||||
}
|
||||
private string AM_ZeroPageX() => this.AM_ZeroPage() + ",X";
|
||||
|
||||
private string AM_ZeroPage_dump()
|
||||
{
|
||||
return this.Dump_Byte((ushort)(this.address + 1));
|
||||
}
|
||||
private string AM_ZeroPageY_dump() => this.AM_ZeroPage_dump();
|
||||
|
||||
private string AM_ZeroPage()
|
||||
{
|
||||
return "$" + this.Dump_Byte((ushort)(this.address + 1));
|
||||
}
|
||||
private string AM_ZeroPageY() => this.AM_ZeroPage() + ",Y";
|
||||
|
||||
private string AM_ZeroPageX_dump()
|
||||
{
|
||||
return this.AM_ZeroPage_dump();
|
||||
}
|
||||
private string AM_AbsoluteX_dump() => this.AM_Absolute_dump();
|
||||
|
||||
private string AM_ZeroPageX()
|
||||
{
|
||||
return this.AM_ZeroPage() + ",X";
|
||||
}
|
||||
private string AM_AbsoluteX() => this.AM_Absolute() + ",X";
|
||||
|
||||
private string AM_ZeroPageY_dump()
|
||||
{
|
||||
return this.AM_ZeroPage_dump();
|
||||
}
|
||||
private string AM_AbsoluteY_dump() => this.AM_Absolute_dump();
|
||||
|
||||
private string AM_ZeroPageY()
|
||||
{
|
||||
return this.AM_ZeroPage() + ",Y";
|
||||
}
|
||||
private string AM_AbsoluteY() => this.AM_Absolute() + ",Y";
|
||||
|
||||
private string AM_AbsoluteX_dump()
|
||||
{
|
||||
return this.AM_Absolute_dump();
|
||||
}
|
||||
private string AM_IndexedIndirectX_dump() => this.AM_ZeroPage_dump();
|
||||
|
||||
private string AM_AbsoluteX()
|
||||
{
|
||||
return this.AM_Absolute() + ",X";
|
||||
}
|
||||
private string AM_IndexedIndirectX() => "($" + this.Dump_Byte((ushort)(this.address + 1)) + ",X)";
|
||||
|
||||
private string AM_AbsoluteY_dump()
|
||||
{
|
||||
return this.AM_Absolute_dump();
|
||||
}
|
||||
private string AM_IndirectIndexedY_dump() => this.AM_ZeroPage_dump();
|
||||
|
||||
private string AM_AbsoluteY()
|
||||
{
|
||||
return this.AM_Absolute() + ",Y";
|
||||
}
|
||||
|
||||
private string AM_IndexedIndirectX_dump()
|
||||
{
|
||||
return this.AM_ZeroPage_dump();
|
||||
}
|
||||
|
||||
private string AM_IndexedIndirectX()
|
||||
{
|
||||
return "($" + this.Dump_Byte((ushort)(this.address + 1)) + ",X)";
|
||||
}
|
||||
|
||||
private string AM_IndirectIndexedY_dump()
|
||||
{
|
||||
return this.AM_ZeroPage_dump();
|
||||
}
|
||||
|
||||
private string AM_IndirectIndexedY()
|
||||
{
|
||||
return "($" + this.Dump_Byte((ushort)(this.address + 1)) + "),Y";
|
||||
}
|
||||
private string AM_IndirectIndexedY() => "($" + this.Dump_Byte((ushort)(this.address + 1)) + "),Y";
|
||||
|
||||
private string AM_00_dump(int bbb)
|
||||
{
|
||||
|
@ -50,7 +50,6 @@ namespace M6502.Test
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
var programFilename = this.configuration.Program;
|
||||
var programPath = this.configuration.RomDirectory + "/" + this.configuration.Program;
|
||||
var loadAddress = this.configuration.LoadAddress;
|
||||
this.ram.Load(programPath, loadAddress.Word);
|
||||
@ -88,7 +87,6 @@ namespace M6502.Test
|
||||
private void CPU_ExecutingInstruction(object sender, System.EventArgs e)
|
||||
{
|
||||
var address = this.CPU.PC.Word;
|
||||
var cell = this.Peek(address);
|
||||
|
||||
var output = new StringBuilder();
|
||||
|
||||
|
@ -8,28 +8,18 @@ namespace M6502.Test
|
||||
|
||||
internal class Configuration
|
||||
{
|
||||
private readonly Register16 loadAddress = new Register16(0x400);
|
||||
private readonly Register16 startAddress = new Register16(0x400);
|
||||
private readonly string romDirectory = "roms";
|
||||
private readonly string program = "6502_functional_test.bin";
|
||||
private bool debugMode = false;
|
||||
|
||||
public Configuration()
|
||||
{
|
||||
}
|
||||
|
||||
public bool DebugMode
|
||||
{
|
||||
get => this.debugMode;
|
||||
set => this.debugMode = value;
|
||||
}
|
||||
public bool DebugMode { get; set; } = false;
|
||||
|
||||
public Register16 LoadAddress { get => this.loadAddress; }
|
||||
public Register16 LoadAddress { get; } = new Register16(0x400);
|
||||
|
||||
public Register16 StartAddress { get => this.startAddress; }
|
||||
public Register16 StartAddress { get; } = new Register16(0x400);
|
||||
|
||||
public string RomDirectory { get => this.romDirectory; }
|
||||
public string RomDirectory { get; } = "roms";
|
||||
|
||||
public string Program { get => this.program; }
|
||||
public string Program { get; } = "6502_functional_test.bin";
|
||||
}
|
||||
}
|
@ -12,14 +12,10 @@ namespace M6502.Test
|
||||
private readonly Stopwatch timer = new Stopwatch();
|
||||
private readonly Board board;
|
||||
private long totalCycles = 0;
|
||||
private long instructions = 0;
|
||||
|
||||
private bool disposed = false;
|
||||
|
||||
public TestHarness(Configuration configuration)
|
||||
{
|
||||
this.board = new Board(configuration);
|
||||
}
|
||||
public TestHarness(Configuration configuration) => this.board = new Board(configuration);
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
@ -38,7 +34,6 @@ namespace M6502.Test
|
||||
while (cpu.Powered)
|
||||
{
|
||||
this.totalCycles += cpu.Step();
|
||||
++this.instructions;
|
||||
}
|
||||
|
||||
this.timer.Stop();
|
||||
|
@ -555,8 +555,6 @@ namespace EightBit
|
||||
|
||||
private static byte ClearFlag(byte f, StatusBits flag, int condition) => ClearFlag(f, (byte)flag, condition);
|
||||
|
||||
private static byte ClearFlag(byte f, StatusBits flag, bool condition) => ClearFlag(f, (byte)flag, condition);
|
||||
|
||||
private void HandleNMI()
|
||||
{
|
||||
this.RaiseNMI();
|
||||
@ -769,10 +767,7 @@ namespace EightBit
|
||||
return returned;
|
||||
}
|
||||
|
||||
private byte SUB(byte operand, byte data, int borrow = 0)
|
||||
{
|
||||
return this.Decimal != 0 ? this.SUB_d(operand, data, borrow) : this.SUB_b(operand, data, borrow);
|
||||
}
|
||||
private byte SUB(byte operand, byte data, int borrow = 0) => this.Decimal != 0 ? this.SUB_d(operand, data, borrow) : this.SUB_b(operand, data, borrow);
|
||||
|
||||
private byte SUB_b(byte operand, byte data, int borrow)
|
||||
{
|
||||
@ -808,10 +803,7 @@ namespace EightBit
|
||||
return returned;
|
||||
}
|
||||
|
||||
private byte ADD(byte operand, byte data, int carry = 0)
|
||||
{
|
||||
return this.Decimal != 0 ? this.ADD_d(operand, data, carry) : this.ADD_b(operand, data, carry);
|
||||
}
|
||||
private byte ADD(byte operand, byte data, int carry = 0) => this.Decimal != 0 ? this.ADD_d(operand, data, carry) : this.ADD_b(operand, data, carry);
|
||||
|
||||
private byte ADD_b(byte operand, byte data, int carry)
|
||||
{
|
||||
|
@ -4,29 +4,21 @@
|
||||
|
||||
namespace EightBit
|
||||
{
|
||||
using System.Text;
|
||||
|
||||
public class Disassembler
|
||||
{
|
||||
private readonly Bus bus;
|
||||
|
||||
private bool prefixCB = false;
|
||||
private bool prefixDD = false;
|
||||
private bool prefixED = false;
|
||||
private bool prefixFD = false;
|
||||
|
||||
public Disassembler(Bus bus)
|
||||
{
|
||||
this.bus = bus;
|
||||
}
|
||||
public Disassembler(Bus bus) => this.Bus = bus;
|
||||
|
||||
public Bus Bus => this.bus;
|
||||
public Bus Bus { get; }
|
||||
|
||||
public static string AsFlag(byte value, StatusBits flag, string represents) => (value & (byte)flag) != 0 ? represents : "-";
|
||||
|
||||
public static string AsFlags(byte value)
|
||||
{
|
||||
return $"{AsFlag(value, StatusBits.SF, "S")}"
|
||||
public static string AsFlags(byte value) =>
|
||||
$"{AsFlag(value, StatusBits.SF, "S")}"
|
||||
+ $"{AsFlag(value, StatusBits.ZF, "Z")}"
|
||||
+ $"{AsFlag(value, StatusBits.YF, "Y")}"
|
||||
+ $"{AsFlag(value, StatusBits.HC, "H")}"
|
||||
@ -34,7 +26,6 @@ namespace EightBit
|
||||
+ $"{AsFlag(value, StatusBits.PF, "P")}"
|
||||
+ $"{AsFlag(value, StatusBits.NF, "N")}"
|
||||
+ $"{AsFlag(value, StatusBits.CF, "C")}";
|
||||
}
|
||||
|
||||
public static string State(Z80 cpu)
|
||||
{
|
||||
@ -147,10 +138,10 @@ namespace EightBit
|
||||
|
||||
var output = $"{opCode:x2}";
|
||||
|
||||
string specification = string.Empty;
|
||||
var specification = string.Empty;
|
||||
if (this.prefixCB)
|
||||
{
|
||||
output += this.DisassembleCB(cpu, pc, ref specification, ref dumpCount, x, y, z, p, q);
|
||||
output += this.DisassembleCB(ref specification, x, y, z);
|
||||
}
|
||||
else if (this.prefixED)
|
||||
{
|
||||
@ -161,7 +152,7 @@ namespace EightBit
|
||||
output += this.DisassembleOther(cpu, pc, ref specification, ref dumpCount, x, y, z, p, q);
|
||||
}
|
||||
|
||||
for (int i = 0; i < dumpCount; ++i)
|
||||
for (var i = 0; i < dumpCount; ++i)
|
||||
{
|
||||
output += $"{this.Bus.Peek((ushort)(pc + i + 1)):x2}";
|
||||
}
|
||||
@ -184,9 +175,9 @@ namespace EightBit
|
||||
return output;
|
||||
}
|
||||
|
||||
private string DisassembleCB(Z80 cpu, ushort pc, ref string specification, ref int dumpCount, int x, int y, int z, int p, int q)
|
||||
private string DisassembleCB(ref string specification, int x, int y, int z)
|
||||
{
|
||||
string output = string.Empty;
|
||||
var output = string.Empty;
|
||||
switch (x)
|
||||
{
|
||||
case 0: // rot[y] r[z]
|
||||
|
@ -15,15 +15,9 @@ namespace EightBit
|
||||
this.variable = (byte)(value & (byte)Mask.Mask7);
|
||||
}
|
||||
|
||||
public static implicit operator byte(RefreshRegister input)
|
||||
{
|
||||
return ToByte(input);
|
||||
}
|
||||
public static implicit operator byte(RefreshRegister input) => ToByte(input);
|
||||
|
||||
public static implicit operator RefreshRegister(byte input)
|
||||
{
|
||||
return FromByte(input);
|
||||
}
|
||||
public static implicit operator RefreshRegister(byte input) => FromByte(input);
|
||||
|
||||
public static RefreshRegister operator ++(RefreshRegister value) => Increment(value);
|
||||
|
||||
@ -31,10 +25,7 @@ namespace EightBit
|
||||
|
||||
public static bool operator !=(RefreshRegister left, RefreshRegister right) => !(left == right);
|
||||
|
||||
public static byte ToByte(RefreshRegister input)
|
||||
{
|
||||
return (byte)((input.high << 7) | (input.variable & (byte)Mask.Mask7));
|
||||
}
|
||||
public static byte ToByte(RefreshRegister input) => (byte)((input.high << 7) | (input.variable & (byte)Mask.Mask7));
|
||||
|
||||
public static RefreshRegister Increment(RefreshRegister value)
|
||||
{
|
||||
@ -42,15 +33,9 @@ namespace EightBit
|
||||
return value;
|
||||
}
|
||||
|
||||
public static RefreshRegister FromByte(byte input)
|
||||
{
|
||||
return new RefreshRegister(input);
|
||||
}
|
||||
public static RefreshRegister FromByte(byte input) => new RefreshRegister(input);
|
||||
|
||||
public byte ToByte()
|
||||
{
|
||||
return ToByte(this);
|
||||
}
|
||||
public byte ToByte() => ToByte(this);
|
||||
|
||||
public override bool Equals(object obj)
|
||||
{
|
||||
|
@ -46,7 +46,6 @@ namespace Z80.Test
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
var programFilename = this.configuration.Program;
|
||||
var programPath = this.configuration.RomDirectory + "/" + this.configuration.Program;
|
||||
var loadAddress = this.configuration.LoadAddress;
|
||||
this.ram.Load(programPath, loadAddress.Word);
|
||||
@ -68,15 +67,15 @@ namespace Z80.Test
|
||||
|
||||
private void BDOS()
|
||||
{
|
||||
switch (CPU.C)
|
||||
switch (this.CPU.C)
|
||||
{
|
||||
case 0x2:
|
||||
System.Console.Out.Write(CPU.E.ToString());
|
||||
System.Console.Out.Write(this.CPU.E.ToString());
|
||||
break;
|
||||
case 0x9:
|
||||
for (ushort i = CPU.DE.Word; Peek(i) != '$'; ++i)
|
||||
for (var i = this.CPU.DE.Word; this.Peek(i) != '$'; ++i)
|
||||
{
|
||||
System.Console.Out.Write((char)Peek(i));
|
||||
System.Console.Out.Write((char)this.Peek(i));
|
||||
}
|
||||
|
||||
break;
|
||||
@ -95,21 +94,15 @@ namespace Z80.Test
|
||||
|
||||
break;
|
||||
case 0x5: // BDOS
|
||||
BDOS();
|
||||
this.BDOS();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private void CPU_LoweredHALT(object sender, System.EventArgs e)
|
||||
{
|
||||
this.LowerPOWER();
|
||||
}
|
||||
private void CPU_LoweredHALT(object sender, System.EventArgs e) => this.LowerPOWER();
|
||||
|
||||
private void CPU_ExecutingInstruction_Debug(object sender, System.EventArgs e)
|
||||
{
|
||||
System.Console.Error.WriteLine($"{EightBit.Disassembler.State(this.CPU)}\t{this.disassembler.Disassemble(this.CPU)}");
|
||||
}
|
||||
private void CPU_ExecutingInstruction_Debug(object sender, System.EventArgs e) => System.Console.Error.WriteLine($"{EightBit.Disassembler.State(this.CPU)}\t{this.disassembler.Disassemble(this.CPU)}");
|
||||
}
|
||||
}
|
||||
|
@ -13,7 +13,6 @@ namespace Z80.Test
|
||||
#if DEBUG
|
||||
configuration.DebugMode = true;
|
||||
#endif
|
||||
// configuration.DebugMode = true;
|
||||
|
||||
using (var harness = new TestHarness(configuration))
|
||||
{
|
||||
|
@ -12,14 +12,10 @@ namespace Z80.Test
|
||||
private readonly Stopwatch timer = new Stopwatch();
|
||||
private readonly Board board;
|
||||
private long totalCycles = 0;
|
||||
private long instructions = 0;
|
||||
|
||||
private bool disposed = false;
|
||||
|
||||
public TestHarness(Configuration configuration)
|
||||
{
|
||||
this.board = new Board(configuration);
|
||||
}
|
||||
public TestHarness(Configuration configuration) => this.board = new Board(configuration);
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
@ -38,7 +34,6 @@ namespace Z80.Test
|
||||
while (cpu.Powered)
|
||||
{
|
||||
this.totalCycles += cpu.Step();
|
||||
++this.instructions;
|
||||
}
|
||||
|
||||
this.timer.Stop();
|
||||
|
83
Z80/Z80.cs
83
Z80/Z80.cs
@ -28,7 +28,6 @@ namespace EightBit
|
||||
private bool prefixCB = false;
|
||||
private bool prefixDD = false;
|
||||
private bool prefixED = false;
|
||||
private bool prefixFD = false;
|
||||
|
||||
private PinLevel nmiLine = PinLevel.Low;
|
||||
private PinLevel m1Line = PinLevel.Low;
|
||||
@ -40,10 +39,7 @@ namespace EightBit
|
||||
private bool displaced = false;
|
||||
|
||||
public Z80(Bus bus, InputOutput ports)
|
||||
: base(bus)
|
||||
{
|
||||
this.ports = ports;
|
||||
}
|
||||
: base(bus) => this.ports = ports;
|
||||
|
||||
public event EventHandler<EventArgs> ExecutingInstruction;
|
||||
|
||||
@ -130,7 +126,7 @@ namespace EightBit
|
||||
this.Exx();
|
||||
this.IX.Word = this.IY.Word = this.BC.Word = this.DE.Word = this.HL.Word = (ushort)Mask.Mask16;
|
||||
|
||||
this.prefixCB = this.prefixDD = this.prefixED = this.prefixFD = false;
|
||||
this.prefixCB = this.prefixDD = this.prefixED = false;
|
||||
}
|
||||
|
||||
public virtual void RaiseNMI()
|
||||
@ -204,7 +200,7 @@ namespace EightBit
|
||||
this.OnExecutingInstruction();
|
||||
if (this.Powered)
|
||||
{
|
||||
this.displaced = this.prefixCB = this.prefixDD = this.prefixED = this.prefixFD = false;
|
||||
this.displaced = this.prefixCB = this.prefixDD = this.prefixED = false;
|
||||
this.LowerM1();
|
||||
if (this.RESET().Lowered())
|
||||
{
|
||||
@ -295,22 +291,11 @@ namespace EightBit
|
||||
|
||||
private static byte ClearFlag(byte f, StatusBits flag, int condition) => ClearFlag(f, (byte)flag, condition);
|
||||
|
||||
private static byte ClearFlag(byte f, StatusBits flag, bool condition) => ClearFlag(f, (byte)flag, condition);
|
||||
private static byte AdjustSign(byte input, byte value) => SetFlag(input, StatusBits.SF, value & (byte)StatusBits.SF);
|
||||
|
||||
private static byte AdjustSign(byte input, byte value)
|
||||
{
|
||||
return SetFlag(input, StatusBits.SF, value & (byte)StatusBits.SF);
|
||||
}
|
||||
private static byte AdjustZero(byte input, byte value) => ClearFlag(input, StatusBits.ZF, value);
|
||||
|
||||
private static byte AdjustZero(byte input, byte value)
|
||||
{
|
||||
return ClearFlag(input, StatusBits.ZF, value);
|
||||
}
|
||||
|
||||
private static byte AdjustParity(byte input, byte value)
|
||||
{
|
||||
return SetFlag(input, StatusBits.PF, EvenParity(value));
|
||||
}
|
||||
private static byte AdjustParity(byte input, byte value) => SetFlag(input, StatusBits.PF, EvenParity(value));
|
||||
|
||||
private static byte AdjustSZ(byte input, byte value)
|
||||
{
|
||||
@ -342,15 +327,9 @@ namespace EightBit
|
||||
return AdjustXY(input, value);
|
||||
}
|
||||
|
||||
private static byte AdjustHalfCarryAdd(byte input, byte before, byte value, int calculation)
|
||||
{
|
||||
return SetFlag(input, StatusBits.HC, CalculateHalfCarryAdd(before, value, calculation));
|
||||
}
|
||||
private static byte AdjustHalfCarryAdd(byte input, byte before, byte value, int calculation) => SetFlag(input, StatusBits.HC, CalculateHalfCarryAdd(before, value, calculation));
|
||||
|
||||
private static byte AdjustHalfCarrySub(byte input, byte before, byte value, int calculation)
|
||||
{
|
||||
return SetFlag(input, StatusBits.HC, CalculateHalfCarrySub(before, value, calculation));
|
||||
}
|
||||
private static byte AdjustHalfCarrySub(byte input, byte before, byte value, int calculation) => SetFlag(input, StatusBits.HC, CalculateHalfCarrySub(before, value, calculation));
|
||||
|
||||
private static byte AdjustOverflowAdd(byte input, int beforeNegative, int valueNegative, int afterNegative)
|
||||
{
|
||||
@ -358,10 +337,7 @@ namespace EightBit
|
||||
return SetFlag(input, StatusBits.VF, overflow);
|
||||
}
|
||||
|
||||
private static byte AdjustOverflowAdd(byte input, byte before, byte value, byte calculation)
|
||||
{
|
||||
return AdjustOverflowAdd(input, before & (byte)StatusBits.SF, value & (byte)StatusBits.SF, calculation & (byte)StatusBits.SF);
|
||||
}
|
||||
private static byte AdjustOverflowAdd(byte input, byte before, byte value, byte calculation) => AdjustOverflowAdd(input, before & (byte)StatusBits.SF, value & (byte)StatusBits.SF, calculation & (byte)StatusBits.SF);
|
||||
|
||||
private static byte AdjustOverflowSub(byte input, int beforeNegative, int valueNegative, int afterNegative)
|
||||
{
|
||||
@ -369,20 +345,11 @@ namespace EightBit
|
||||
return SetFlag(input, StatusBits.VF, overflow);
|
||||
}
|
||||
|
||||
private static byte AdjustOverflowSub(byte input, byte before, byte value, byte calculation)
|
||||
{
|
||||
return AdjustOverflowSub(input, before & (byte)StatusBits.SF, value & (byte)StatusBits.SF, calculation & (byte)StatusBits.SF);
|
||||
}
|
||||
private static byte AdjustOverflowSub(byte input, byte before, byte value, byte calculation) => AdjustOverflowSub(input, before & (byte)StatusBits.SF, value & (byte)StatusBits.SF, calculation & (byte)StatusBits.SF);
|
||||
|
||||
private static byte RES(int n, byte operand)
|
||||
{
|
||||
return (byte)(operand & ~(1 << n));
|
||||
}
|
||||
private static byte RES(int n, byte operand) => (byte)(operand & ~(1 << n));
|
||||
|
||||
private static byte SET(int n, byte operand)
|
||||
{
|
||||
return (byte)(operand | (1 << n));
|
||||
}
|
||||
private static byte SET(int n, byte operand) => (byte)(operand | (1 << n));
|
||||
|
||||
private void DisableInterrupts() => this.IFF1 = this.IFF2 = false;
|
||||
|
||||
@ -531,7 +498,6 @@ namespace EightBit
|
||||
|
||||
private void ExecuteCB(int x, int y, int z)
|
||||
{
|
||||
var memoryY = y == 6;
|
||||
var memoryZ = z == 6;
|
||||
var indirect = (!this.displaced && memoryZ) || this.displaced;
|
||||
var direct = !indirect;
|
||||
@ -620,8 +586,6 @@ namespace EightBit
|
||||
|
||||
private void ExecuteED(int x, int y, int z, int p, int q)
|
||||
{
|
||||
var memoryY = y == 6;
|
||||
var memoryZ = z == 6;
|
||||
switch (x)
|
||||
{
|
||||
case 0:
|
||||
@ -647,14 +611,7 @@ namespace EightBit
|
||||
case 1: // Output to port with 16-bit address
|
||||
this.MEMPTR.Word = this.Bus.Address.Word = this.BC.Word;
|
||||
this.MEMPTR.Word++;
|
||||
if (y != 6)
|
||||
{
|
||||
this.Bus.Data = this.R(y); // OUT (C),r[y]
|
||||
}
|
||||
else
|
||||
{
|
||||
this.Bus.Data = 0; // OUT (C),0
|
||||
}
|
||||
this.Bus.Data = y != 6 ? this.R(y) : (byte)0;
|
||||
|
||||
this.WritePort();
|
||||
this.Tick(12);
|
||||
@ -1132,7 +1089,7 @@ namespace EightBit
|
||||
case 1: // 8-bit loading
|
||||
if (!(memoryZ && memoryY))
|
||||
{
|
||||
bool normal = true;
|
||||
var normal = true;
|
||||
if (this.displaced)
|
||||
{
|
||||
if (memoryZ || memoryY)
|
||||
@ -1365,7 +1322,7 @@ namespace EightBit
|
||||
this.Execute(this.FetchByte());
|
||||
break;
|
||||
case 3: // FD prefix
|
||||
this.displaced = this.prefixFD = true;
|
||||
this.displaced = true;
|
||||
this.LowerM1();
|
||||
this.Execute(this.FetchByte());
|
||||
break;
|
||||
@ -2038,10 +1995,7 @@ namespace EightBit
|
||||
++this.MEMPTR.Low;
|
||||
}
|
||||
|
||||
private void WritePort()
|
||||
{
|
||||
this.ports.Write(this.Bus.Address.Low, this.Bus.Data);
|
||||
}
|
||||
private void WritePort() => this.ports.Write(this.Bus.Address.Low, this.Bus.Data);
|
||||
|
||||
private byte ReadPort(byte port)
|
||||
{
|
||||
@ -2050,9 +2004,6 @@ namespace EightBit
|
||||
return this.ReadPort();
|
||||
}
|
||||
|
||||
private byte ReadPort()
|
||||
{
|
||||
return this.Bus.Data = this.ports.Read(this.Bus.Address.Low);
|
||||
}
|
||||
private byte ReadPort() => this.Bus.Data = this.ports.Read(this.Bus.Address.Low);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user