Skip to content

Commit

Permalink
Separated Instructions to separate classes
Browse files Browse the repository at this point in the history
Added instruction list for managing instructions instead of big switch
statements
  • Loading branch information
jnosek committed Jul 26, 2014
1 parent 3a24f25 commit 3679d72
Show file tree
Hide file tree
Showing 8 changed files with 220 additions and 55 deletions.
6 changes: 6 additions & 0 deletions AGC/AGC.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,12 @@
<Compile Include="Base\MemoryAddress.cs" />
<Compile Include="Base\Register.cs" />
<Compile Include="Base\Computer.cs" />
<Compile Include="InstructionSet.cs" />
<Compile Include="Instructions\Add.cs" />
<Compile Include="Instructions\AddToStorage.cs" />
<Compile Include="Base\IInstruction.cs" />
<Compile Include="Base\InstructionList.cs" />
<Compile Include="Instructions\QuarterCode.cs" />
<Compile Include="MemoryMap.cs" />
<Compile Include="Processor.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
Expand Down
16 changes: 16 additions & 0 deletions AGC/Base/IInstruction.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC.Base
{
interface IInstruction
{
ushort Code { get; }

Processor CPU { get; set; }

void Execute(ushort K);
}
}
55 changes: 55 additions & 0 deletions AGC/Base/InstructionList.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC.Base
{
class InstructionList
{
private IInstruction[] array;

public InstructionList(int count)
{
array = new IInstruction[0];
}

public InstructionList()
: this(0)
{
}

public void Add(IInstruction instruction)
{
this[instruction.Code] = instruction;
}

public IInstruction this[ushort code]
{
get
{
if (code > array.Length - 1)
throw new IndexOutOfRangeException();

return array[code];
}
set
{
if(code > array.Length - 1)
Array.Resize(ref array, code + 1);

array[code] = value;
}
}

public void Clear()
{
array = new IInstruction[0];
}

public int Count
{
get { return array.Length; }
}
}
}
32 changes: 32 additions & 0 deletions AGC/InstructionSet.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
using Apollo.Virtual.AGC.Base;
using Apollo.Virtual.AGC.Instructions;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC
{
class InstructionSet
{
private Processor CPU;
private InstructionList instructions;

public InstructionSet(Processor cpu)
{
CPU = cpu;
instructions = new InstructionList(7);

instructions.Add(new QuarterCode { CPU = CPU });
instructions.Add(new Add { CPU = CPU });
}

public IInstruction this[ushort code]
{
get
{
return instructions[code];
}
}
}
}
29 changes: 29 additions & 0 deletions AGC/Instructions/Add.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
using Apollo.Virtual.AGC.Base;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC.Instructions
{
/// <summary>
/// AD - 0110
///
/// Adds the value located in K to the accumulator
/// </summary>
class Add : IInstruction
{
public Processor CPU { get; set; }

public ushort Code { get { return 0x06; } }

public void Execute(ushort K)
{
var value = CPU.Memory[K];
CPU.A.Add(CPU.Memory[K]);

// value in K is re-written
CPU.Memory[K] = value;
}
}
}
32 changes: 32 additions & 0 deletions AGC/Instructions/AddToStorage.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
using Apollo.Virtual.AGC.Base;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC.Instructions
{
/// <summary>
/// ADS - 0010 11
/// QuaterCode Instruction
///
/// Adds the accumulator to an eraseable memory location and vice versa
/// </summary>
class AddToStorage : IInstruction
{
public ushort Code
{
get { return 0x02; }
}

public Processor CPU { get; set; }

public void Execute(ushort K)
{
var value = CPU.Memory[K];
CPU.A.Add(value);

CPU.Memory[K] = CPU.A.Read();
}
}
}
40 changes: 40 additions & 0 deletions AGC/Instructions/QuarterCode.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
using Apollo.Virtual.AGC.Base;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Apollo.Virtual.AGC.Instructions
{
/// <summary>
/// QC - 0010
///
/// Operation on 10-bit address space operand restricted to eraseable memory
/// Followed by 2-bit quarter code for instruction
/// </summary>
class QuarterCode : IInstruction
{
private InstructionList instuctions;

public QuarterCode()
{
instuctions = new InstructionList(3);
instuctions.Add(new AddToStorage { CPU = this.CPU });
}

public ushort Code
{
get { return 0x02; }
}

public Processor CPU { get; set; }

public void Execute(ushort K)
{
var quarterCode = (ushort)(K >> 10);
K = (ushort)(K & 0x3FF);

instuctions[quarterCode].Execute(K);
}
}
}
65 changes: 10 additions & 55 deletions AGC/Processor.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ namespace Apollo.Virtual.AGC

public class Processor
{
private MemoryMap memory;
internal MemoryMap Memory;

private InstructionSet instructions;

#region Register Definitions

Expand Down Expand Up @@ -209,7 +211,8 @@ public class Processor

public Processor(MemoryMap memory)
{
this.memory = memory;
this.Memory = memory;
instructions = new InstructionSet(this);

// configure registers

Expand Down Expand Up @@ -262,67 +265,19 @@ public Processor(MemoryMap memory)

}

// try some instructions

/// <summary>
/// AD - 0110
///
/// Adds the value located in K to the accumulator
/// </summary>
public void Add(ushort K)
{
var value = memory[K];
A.Add(memory[K]);

// value in K is re-written
memory[K] = value;
}

/// <summary>
/// ADS - 0010 11
/// Adds the accumulator to an eraseable memory location and vice versa
/// </summary>
/// <param name="K"></param>
public void AddToStorage(ushort K)
{
var value = memory[K];
A.Add(value);

memory[K] = A.Read();
}

public void Execute()
{
// get address of instruction to run
var address = memory.GetAddress(Z.Read());
var address = Memory.GetAddress(Z.Read());

// update Z
Z.Write((ushort)(Z.Read() + 1));

var code = address.Read() >> 12;
var operand = (ushort)(address.Read() & 0xFFF);

switch (code)
{
// Add
case 0x06:
this.Add(operand);
break;

// Quarter Codes
case 0x02:
var quarterCode = operand >> 10;
operand = (ushort)(operand & 0x3FF);

switch (quarterCode)
{
case 0x02:
this.AddToStorage(operand);
break;
}

break;
}
var code = (ushort)(address.Read() >> 12);
var K = (ushort)(address.Read() & 0xFFF);

instructions[code].Execute(K);
}
}
}
Expand Down

0 comments on commit 3679d72

Please sign in to comment.