From 3c20e1f03734af55cf5f5d9765a48f11a3e19772 Mon Sep 17 00:00:00 2001 From: Thomas Harte Date: Fri, 15 Jan 2021 21:30:30 -0500 Subject: [PATCH] Adds files for the M50740 and corrects namespace errors elsewhere. --- InstructionSets/M50740/Decoder.cpp | 17 +++ InstructionSets/M50740/Decoder.hpp | 34 +++++ InstructionSets/M50740/Instruction.hpp | 120 ++++++++++++++++++ InstructionSets/PowerPC/Decoder.cpp | 2 +- InstructionSets/PowerPC/Decoder.hpp | 4 +- InstructionSets/PowerPC/Instruction.hpp | 4 +- InstructionSets/x86/Decoder.cpp | 4 +- InstructionSets/x86/Decoder.hpp | 6 +- InstructionSets/x86/Instruction.hpp | 4 +- .../Clock Signal.xcodeproj/project.pbxproj | 20 +++ .../Clock SignalTests/PowerPCDecoderTests.mm | 6 +- .../Mac/Clock SignalTests/x86DecoderTests.mm | 24 ++-- 12 files changed, 213 insertions(+), 32 deletions(-) create mode 100644 InstructionSets/M50740/Decoder.cpp create mode 100644 InstructionSets/M50740/Decoder.hpp create mode 100644 InstructionSets/M50740/Instruction.hpp diff --git a/InstructionSets/M50740/Decoder.cpp b/InstructionSets/M50740/Decoder.cpp new file mode 100644 index 000000000..033f084f9 --- /dev/null +++ b/InstructionSets/M50740/Decoder.cpp @@ -0,0 +1,17 @@ +// +// Decoder.cpp +// Clock Signal +// +// Created by Thomas Harte on 1/15/21. +// Copyright © 2021 Thomas Harte. All rights reserved. +// + +#include "Decoder.hpp" + +namespace InstructionSet { +namespace M50740 { + + + +} +} diff --git a/InstructionSets/M50740/Decoder.hpp b/InstructionSets/M50740/Decoder.hpp new file mode 100644 index 000000000..f31ba3838 --- /dev/null +++ b/InstructionSets/M50740/Decoder.hpp @@ -0,0 +1,34 @@ +// +// Decoder.hpp +// Clock Signal +// +// Created by Thomas Harte on 1/15/21. +// Copyright © 2021 Thomas Harte. All rights reserved. +// + +#ifndef InstructionSets_M50740_Decoder_hpp +#define InstructionSets_M50740_Decoder_hpp + +#include "Instruction.hpp" + +#include + +namespace InstructionSet { +namespace M50740 { + +class Decoder { + public: + std::pair decode(const uint8_t *source, size_t length); + + private: + enum class Phase { + Instruction, + AwaitingOperand + }; + int operand_size_; +}; + +} +} + +#endif /* InstructionSets_M50740_Decoder_hpp */ diff --git a/InstructionSets/M50740/Instruction.hpp b/InstructionSets/M50740/Instruction.hpp new file mode 100644 index 000000000..aef5ff873 --- /dev/null +++ b/InstructionSets/M50740/Instruction.hpp @@ -0,0 +1,120 @@ +// +// Instruction.hpp +// Clock Signal +// +// Created by Thomas Harte on 1/15/21. +// Copyright © 2021 Thomas Harte. All rights reserved. +// + +#ifndef InstructionSets_M50740_Instruction_h +#define InstructionSets_M50740_Instruction_h + +#include + +namespace InstructionSet { +namespace M50740 { + +enum class AddressingMode { + Implied, + Accumulator, + Immediate, + Absolute, + AbsoluteX, + AbsoluteY, + ZeroPage, + ZeroPageX, + ZeroPageY, + XIndirect, + IndirectY, + Relative, + AbsoluteIndirect, + ZeroPageIndirect, + SpecialPage, + BitAccumulator, + BitZeroPage +}; + +enum class Operation: uint8_t { + ADC, + AND, + ASL, + BBC, + BBS, + BCC, + BCS, + BEQ, + BIT, + BMI, + BNE, + BPL, + BRA, + BRK, + BVC, + BVS, + CLB, + CLC, + CLD, + CLI, + CLT, + CLV, + CMP, + COM, + CPX, + CPY, + DEC, + DEX, + DEY, + EOR, + FST, + INC, + INX, + INY, + JMP, + JSR, + LDA, + LDM, + LDX, + LDY, + LSR, + NOP, + ORA, + PHA, + PHP, + PLA, + PLP, + ROL, + ROR, + RRF, + RTI, + RTS, + SBC, + SEB, + SEC, + SED, + SEI, + SET, + SLW, + STA, + STP, + STX, + STY, + TAX, + TAY, + TST, + TSX, + TXS, + TYA +}; + +struct Instruction { + Operation operation; + AddressingMode addressing_mode; + + Instruction(Operation operation, AddressingMode addressing_mode) : operation(operation), addressing_mode(addressing_mode) {} +}; + +} +} + + +#endif /* InstructionSets_M50740_Instruction_h */ diff --git a/InstructionSets/PowerPC/Decoder.cpp b/InstructionSets/PowerPC/Decoder.cpp index efa550070..e4dfe0b86 100644 --- a/InstructionSets/PowerPC/Decoder.cpp +++ b/InstructionSets/PowerPC/Decoder.cpp @@ -8,7 +8,7 @@ #include "Decoder.hpp" -using namespace CPU::Decoder::PowerPC; +using namespace InstructionSet::PowerPC; Decoder::Decoder(Model model) : model_(model) {} diff --git a/InstructionSets/PowerPC/Decoder.hpp b/InstructionSets/PowerPC/Decoder.hpp index 4b252c892..edb1029be 100644 --- a/InstructionSets/PowerPC/Decoder.hpp +++ b/InstructionSets/PowerPC/Decoder.hpp @@ -11,8 +11,7 @@ #include "Instruction.hpp" -namespace CPU { -namespace Decoder { +namespace InstructionSet { namespace PowerPC { enum class Model { @@ -51,7 +50,6 @@ struct Decoder { } }; -} } } diff --git a/InstructionSets/PowerPC/Instruction.hpp b/InstructionSets/PowerPC/Instruction.hpp index a1d1237ca..dfdc03daa 100644 --- a/InstructionSets/PowerPC/Instruction.hpp +++ b/InstructionSets/PowerPC/Instruction.hpp @@ -11,8 +11,7 @@ #include -namespace CPU { -namespace Decoder { +namespace InstructionSet { namespace PowerPC { enum class Operation: uint8_t { @@ -185,7 +184,6 @@ struct Instruction { // Sanity check on Instruction size. static_assert(sizeof(Instruction) <= 8); -} } } diff --git a/InstructionSets/x86/Decoder.cpp b/InstructionSets/x86/Decoder.cpp index 2634ec9e3..b4e74d686 100644 --- a/InstructionSets/x86/Decoder.cpp +++ b/InstructionSets/x86/Decoder.cpp @@ -12,12 +12,12 @@ #include #include -using namespace CPU::Decoder::x86; +using namespace InstructionSet::x86; // Only 8086 is suppoted for now. Decoder::Decoder(Model) {} -std::pair Decoder::decode(const uint8_t *source, size_t length) { +std::pair Decoder::decode(const uint8_t *source, size_t length) { const uint8_t *const end = source + length; // MARK: - Prefixes (if present) and the opcode. diff --git a/InstructionSets/x86/Decoder.hpp b/InstructionSets/x86/Decoder.hpp index b5235a0aa..f09dd7fc0 100644 --- a/InstructionSets/x86/Decoder.hpp +++ b/InstructionSets/x86/Decoder.hpp @@ -13,8 +13,7 @@ #include -namespace CPU { -namespace Decoder { +namespace InstructionSet { namespace x86 { enum class Model { @@ -26,7 +25,7 @@ enum class Model { This is an experimental implementation; it has not yet undergone significant testing. */ -struct Decoder { +class Decoder { public: Decoder(Model model); @@ -149,7 +148,6 @@ struct Decoder { } }; -} } } diff --git a/InstructionSets/x86/Instruction.hpp b/InstructionSets/x86/Instruction.hpp index 334b01658..544823042 100644 --- a/InstructionSets/x86/Instruction.hpp +++ b/InstructionSets/x86/Instruction.hpp @@ -11,8 +11,7 @@ #include -namespace CPU { -namespace Decoder { +namespace InstructionSet { namespace x86 { /* @@ -298,7 +297,6 @@ class Instruction { static_assert(sizeof(Instruction) <= 8); -} } } diff --git a/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj b/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj index db5bc1983..ff7297575 100644 --- a/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj +++ b/OSBindings/Mac/Clock Signal.xcodeproj/project.pbxproj @@ -928,6 +928,9 @@ 4BEDA3BF25B25563000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA3B925B25563000C2DBD /* Decoder.cpp */; }; 4BEDA3C025B25563000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA3B925B25563000C2DBD /* Decoder.cpp */; }; 4BEDA3C125B25563000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA3B925B25563000C2DBD /* Decoder.cpp */; }; + 4BEDA40C25B2844B000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA40B25B2844B000C2DBD /* Decoder.cpp */; }; + 4BEDA40D25B2844B000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA40B25B2844B000C2DBD /* Decoder.cpp */; }; + 4BEDA40E25B2844B000C2DBD /* Decoder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEDA40B25B2844B000C2DBD /* Decoder.cpp */; }; 4BEE0A6F1D72496600532C7B /* Cartridge.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEE0A6A1D72496600532C7B /* Cartridge.cpp */; }; 4BEE0A701D72496600532C7B /* PRG.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEE0A6D1D72496600532C7B /* PRG.cpp */; }; 4BEE149A227FC0EA00133682 /* IWM.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 4BEE1498227FC0EA00133682 /* IWM.cpp */; }; @@ -1934,6 +1937,9 @@ 4BEDA3B925B25563000C2DBD /* Decoder.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Decoder.cpp; sourceTree = ""; }; 4BEDA3D225B257F2000C2DBD /* Instruction.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Instruction.hpp; sourceTree = ""; }; 4BEDA3DB25B2588F000C2DBD /* Instruction.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Instruction.hpp; sourceTree = ""; }; + 4BEDA40A25B2844B000C2DBD /* Decoder.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Decoder.hpp; sourceTree = ""; }; + 4BEDA40B25B2844B000C2DBD /* Decoder.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Decoder.cpp; sourceTree = ""; }; + 4BEDA41725B2845D000C2DBD /* Instruction.hpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.h; path = Instruction.hpp; sourceTree = ""; }; 4BEE0A6A1D72496600532C7B /* Cartridge.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Cartridge.cpp; sourceTree = ""; }; 4BEE0A6B1D72496600532C7B /* Cartridge.hpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.h; path = Cartridge.hpp; sourceTree = ""; }; 4BEE0A6D1D72496600532C7B /* PRG.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = PRG.cpp; sourceTree = ""; }; @@ -4353,6 +4359,7 @@ isa = PBXGroup; children = ( 4BEDA3B625B25563000C2DBD /* README.md */, + 4BEDA40925B2844B000C2DBD /* M50740 */, 4BEDA3B325B25563000C2DBD /* PowerPC */, 4BEDA3B725B25563000C2DBD /* x86 */, ); @@ -4380,6 +4387,16 @@ path = x86; sourceTree = ""; }; + 4BEDA40925B2844B000C2DBD /* M50740 */ = { + isa = PBXGroup; + children = ( + 4BEDA40B25B2844B000C2DBD /* Decoder.cpp */, + 4BEDA40A25B2844B000C2DBD /* Decoder.hpp */, + 4BEDA41725B2845D000C2DBD /* Instruction.hpp */, + ); + path = M50740; + sourceTree = ""; + }; 4BEE0A691D72496600532C7B /* Cartridge */ = { isa = PBXGroup; children = ( @@ -5127,6 +5144,7 @@ 4B055A941FAE85B50060FFFF /* CommodoreROM.cpp in Sources */, 4BBB70A5202011C2002FE009 /* MultiMediaTarget.cpp in Sources */, 4B8318BC22D3E588006DB630 /* DisplayMetrics.cpp in Sources */, + 4BEDA40E25B2844B000C2DBD /* Decoder.cpp in Sources */, 4B1B88BD202E3D3D00B67DFF /* MultiMachine.cpp in Sources */, 4BE0A3EF237BB170002AB46F /* ST.cpp in Sources */, 4B055A971FAE85BB0060FFFF /* ZX8081.cpp in Sources */, @@ -5231,6 +5249,7 @@ 4B2BF19623E10F0100C3AD60 /* CSHighPrecisionTimer.m in Sources */, 4BE211FF253FC80900435408 /* StaticAnalyser.cpp in Sources */, 4B8334951F5E25B60097E338 /* C1540.cpp in Sources */, + 4BEDA40C25B2844B000C2DBD /* Decoder.cpp in Sources */, 4B89453C201967B4007DE474 /* StaticAnalyser.cpp in Sources */, 4B595FAD2086DFBA0083CAA8 /* AudioToggle.cpp in Sources */, 4B1497921EE4B5A800CE2596 /* ZX8081.cpp in Sources */, @@ -5557,6 +5576,7 @@ 4B778F2B23A5EF0F0000D260 /* Commodore.cpp in Sources */, 4B778F3F23A5F1890000D260 /* MacintoshDoubleDensityDrive.cpp in Sources */, 4B778F1623A5ECA00000D260 /* Z80AllRAM.cpp in Sources */, + 4BEDA40D25B2844B000C2DBD /* Decoder.cpp in Sources */, 4B778EF723A5EB670000D260 /* SSD.cpp in Sources */, 4B778F5723A5F2BB0000D260 /* ZX8081.cpp in Sources */, 4B778F2F23A5F0B10000D260 /* ScanTarget.cpp in Sources */, diff --git a/OSBindings/Mac/Clock SignalTests/PowerPCDecoderTests.mm b/OSBindings/Mac/Clock SignalTests/PowerPCDecoderTests.mm index 2ec9be6d2..37ab84a3e 100644 --- a/OSBindings/Mac/Clock SignalTests/PowerPCDecoderTests.mm +++ b/OSBindings/Mac/Clock SignalTests/PowerPCDecoderTests.mm @@ -11,8 +11,8 @@ #include "../../../InstructionSets/PowerPC/Decoder.hpp" namespace { - using Operation = CPU::Decoder::PowerPC::Operation; - using Instruction = CPU::Decoder::PowerPC::Instruction; + using Operation = InstructionSet::PowerPC::Operation; + using Instruction = InstructionSet::PowerPC::Instruction; } @interface PowerPCDecoderTests : XCTestCase @@ -119,7 +119,7 @@ namespace { // MARK: - Decoder - (void)decode:(const uint32_t *)stream { - CPU::Decoder::PowerPC::Decoder decoder(CPU::Decoder::PowerPC::Model::MPC601); + InstructionSet::PowerPC::Decoder decoder(InstructionSet::Model::MPC601); for(int c = 0; c < 32; c++) { instructions[c] = decoder.decode(stream[c]); } diff --git a/OSBindings/Mac/Clock SignalTests/x86DecoderTests.mm b/OSBindings/Mac/Clock SignalTests/x86DecoderTests.mm index 20b5f8731..197cd0418 100644 --- a/OSBindings/Mac/Clock SignalTests/x86DecoderTests.mm +++ b/OSBindings/Mac/Clock SignalTests/x86DecoderTests.mm @@ -13,10 +13,10 @@ #include "../../../InstructionSets/x86/Decoder.hpp" namespace { - using Operation = CPU::Decoder::x86::Operation; - using Instruction = CPU::Decoder::x86::Instruction; - using Source = CPU::Decoder::x86::Source; - using Size = CPU::Decoder::x86::Size; + using Operation = InstructionSet::x86::Operation; + using Instruction = InstructionSet::x86::Instruction; + using Source = InstructionSet::x86::Source; + using Size = InstructionSet::x86::Size; } @interface x86DecoderTests : XCTestCase @@ -39,12 +39,12 @@ namespace { - (void)assert:(Instruction &)instruction operation:(Operation)operation size:(int)size { XCTAssertEqual(instruction.operation, operation); - XCTAssertEqual(instruction.operation_size(), CPU::Decoder::x86::Size(size)); + XCTAssertEqual(instruction.operation_size(), InstructionSet::x86::Size(size)); } - (void)assert:(Instruction &)instruction operation:(Operation)operation size:(int)size source:(Source)source destination:(Source)destination displacement:(int16_t)displacement { XCTAssertEqual(instruction.operation, operation); - XCTAssertEqual(instruction.operation_size(), CPU::Decoder::x86::Size(size)); + XCTAssertEqual(instruction.operation_size(), InstructionSet::x86::Size(size)); XCTAssertEqual(instruction.source(), source); XCTAssertEqual(instruction.destination(), destination); XCTAssertEqual(instruction.displacement(), displacement); @@ -65,19 +65,17 @@ namespace { - (void)assert:(Instruction &)instruction operation:(Operation)operation size:(int)size source:(Source)source { XCTAssertEqual(instruction.operation, operation); - XCTAssertEqual(instruction.operation_size(), CPU::Decoder::x86::Size(size)); + XCTAssertEqual(instruction.operation_size(), InstructionSet::x86::Size(size)); XCTAssertEqual(instruction.source(), source); } - (void)assert:(Instruction &)instruction operation:(Operation)operation size:(int)size destination:(Source)destination { - XCTAssertEqual(instruction.operation, operation); - XCTAssertEqual(instruction.operation_size(), CPU::Decoder::x86::Size(size)); + [self assert:instruction operation:operation size:size]; XCTAssertEqual(instruction.destination(), destination); } - (void)assert:(Instruction &)instruction operation:(Operation)operation size:(int)size operand:(uint16_t)operand destination:(Source)destination { - XCTAssertEqual(instruction.operation, operation); - XCTAssertEqual(instruction.operation_size(), CPU::Decoder::x86::Size(size)); + [self assert:instruction operation:operation size:size]; XCTAssertEqual(instruction.destination(), destination); XCTAssertEqual(instruction.source(), Source::Immediate); XCTAssertEqual(instruction.operand(), operand); @@ -105,7 +103,7 @@ namespace { - (void)decode:(const std::initializer_list &)stream { // Decode by offering up all data at once. - CPU::Decoder::x86::Decoder decoder(CPU::Decoder::x86::Model::i8086); + InstructionSet::x86::Decoder decoder(InstructionSet::x86::Model::i8086); instructions.clear(); const uint8_t *byte = stream.begin(); while(byte != stream.end()) { @@ -117,7 +115,7 @@ namespace { // Grab a byte-at-a-time decoding and check that it matches the previous. { - CPU::Decoder::x86::Decoder decoder(CPU::Decoder::x86::Model::i8086); + InstructionSet::x86::Decoder decoder(InstructionSet::x86::Model::i8086); auto previous_instruction = instructions.begin(); for(auto item: stream) {