/// <summary> /// Perform an instruction (a command and an optional parameter) on the stack /// </summary> /// <param name="instruction">The instruction to execute</param> public void ExecuteInstruction(CliffordInstruction instruction) { switch (instruction.Command) { case Command.Push: { if (!instruction.Parameter.HasValue) { throw new InvalidOperationException(); } Push((int)instruction.Parameter); break; } case Command.Pop: { Pop(); break; } case Command.Add: { int[] operands = GetOperands(2); Push(operands[0] + operands[1]); break; } case Command.Subtract: { int[] operands = GetOperands(2); Push(operands[0] - operands[1]); break; } case Command.Multiply: { int[] operands = GetOperands(2); Push(operands[0] * operands[1]); break; } case Command.Divide: { int[] operands = GetOperands(2); Push(operands[0] / operands[1]); break; } default: throw new InvalidOperationException(); } }
/// <summary> /// Clifford Engine entry point /// </summary> /// <param name="args">Unused</param> static void Main(string[] args) { CliffordProgramCodeCollection codes = new CliffordProgramCodeCollection(); CliffordInstructionQueue instructions = new CliffordInstructionQueue(); CliffordStack stack = new CliffordStack(); // Get codes as a whitespace-separated string string input = Console.ReadLine(); // Tokenise on whitespace string[] commandsString = input.Split(new char[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); foreach (string command in commandsString) { if (!codes.Add(command)) { Console.WriteLine("Warning. Failed to parse command: " + command); } } // Generate Instructions instructions = codes.GenerateInstructions(); if (instructions == null) { Console.WriteLine("Error generating instructions. Check input."); return; } // Execute Instructions while (!instructions.IsEmpty()) { #if DEBUG DisplayEngineState(stack, instructions); #endif CliffordInstruction instruction = instructions.FetchInstruction(); if (instruction != null) { stack.ExecuteInstruction(instruction); } } // Display resultant stack DisplayEngineState(stack); // Stay alive! Console.ReadLine(); }
/// <summary> /// Adds a new instruction to the instruction queue /// </summary> /// <param name="instruction">The instruction to add</param> public void AddInstruction(CliffordInstruction instruction) { instructions.Enqueue(instruction); }