diff --git a/InstructionSets/x86/Instruction.cpp b/InstructionSets/x86/Instruction.cpp index d7a8f5fac..060ac2c22 100644 --- a/InstructionSets/x86/Instruction.cpp +++ b/InstructionSets/x86/Instruction.cpp @@ -10,6 +10,117 @@ using namespace InstructionSet::x86; +std::string InstructionSet::x86::to_string(Operation operation, DataSize size) { + switch(operation) { + case Operation::AAA: return "aaa"; + case Operation::AAD: return "aad"; + case Operation::AAM: return "aam"; + case Operation::AAS: return "aas"; + case Operation::DAA: return "daa"; + case Operation::DAS: return "das"; + + case Operation::CBW: return "cbw"; + case Operation::CWD: return "cwd"; + case Operation::ESC: return "esc"; + + case Operation::HLT: return "hlt"; + case Operation::WAIT: return "wait"; + + case Operation::ADC: return "adc"; + case Operation::ADD: return "add"; + case Operation::SBB: return "sbb"; + case Operation::SUB: return "sub"; + case Operation::MUL: return "mul"; + case Operation::IMUL_1: return "imul"; + case Operation::DIV: return "div"; + case Operation::IDIV: return "idiv"; + + case Operation::INC: return "inc"; + case Operation::DEC: return "dec"; + + case Operation::IN: return "in"; + case Operation::OUT: return "out"; + + case Operation::JO: return "jo"; + case Operation::JNO: return "jno"; + case Operation::JB: return "jb"; + case Operation::JNB: return "jnb"; + case Operation::JE: return "jo"; + case Operation::JNE: return "jne"; + case Operation::JBE: return "jbe"; + case Operation::JNBE: return "jnbe"; + case Operation::JS: return "js"; + case Operation::JNS: return "jns"; + case Operation::JP: return "jp"; + case Operation::JNP: return "jnp"; + case Operation::JL: return "jl"; + case Operation::JNL: return "jnl"; + case Operation::JLE: return "jle"; + case Operation::JNLE: return "jnle"; + + case Operation::IRET: return "iret"; + case Operation::JMPabs: return "jmp word"; + case Operation::JPCX: return "jpcx"; + case Operation::INT: return "int"; + case Operation::INTO: return "into"; + + case Operation::LAHF: return "lahf"; + case Operation::SAHF: return "sahf"; + case Operation::LDS: return "lds"; + case Operation::LES: return "les"; + case Operation::LEA: return "lea"; + + case Operation::CMPS: { + constexpr char sizes[][6] = { "cmpsb", "cmpsw", "cmpsd", "?" }; + return sizes[static_cast(size)]; + } + case Operation::LODS: return "lods"; + case Operation::MOVS: return "movs"; + case Operation::SCAS: return "scas"; + case Operation::STOS: return "stos"; + + case Operation::LOOP: return "loop"; + case Operation::LOOPE: return "loope"; + case Operation::LOOPNE: return "loopne"; + + case Operation::MOV: return "mov"; + case Operation::NEG: return "neg"; + case Operation::NOT: return "not"; + case Operation::AND: return "and"; + case Operation::OR: return "or"; + case Operation::XOR: return "xor"; + case Operation::NOP: return "nop"; + case Operation::POP: return "pop"; + case Operation::POPF: return "popf"; + case Operation::PUSH: return "push"; + case Operation::PUSHF: return "pushf"; + case Operation::RCL: return "rcl"; + case Operation::RCR: return "rcr"; + case Operation::ROL: return "rol"; + case Operation::ROR: return "ror"; + case Operation::SAL: return "sal"; + case Operation::SAR: return "sar"; + case Operation::SHR: return "shr"; + + case Operation::CLC: return "clc"; + case Operation::CLD: return "cld"; + case Operation::CLI: return "cli"; + case Operation::STC: return "stc"; + case Operation::STD: return "std"; + case Operation::STI: return "sti"; + case Operation::CMC: return "cmc"; + + case Operation::CMP: return "cmp"; + case Operation::TEST: return "test"; + + case Operation::XCHG: return "xchg"; + case Operation::XLAT: return "xlat"; + + default: + assert(false); + } +} + std::string InstructionSet::x86::to_string(Source source, DataSize size) { switch(source) { case Source::eAX: { diff --git a/InstructionSets/x86/Instruction.hpp b/InstructionSets/x86/Instruction.hpp index a95cd44a6..c28893c14 100644 --- a/InstructionSets/x86/Instruction.hpp +++ b/InstructionSets/x86/Instruction.hpp @@ -340,6 +340,12 @@ enum class Operation: uint8_t { MOVtoTr, MOVfromTr, }; +constexpr int num_operands(Operation operation) { + switch(operation) { + default: return 2; + } +} + enum class DataSize: uint8_t { Byte = 0, Word = 1, @@ -354,6 +360,7 @@ constexpr int byte_size(DataSize size) { constexpr int bit_size(DataSize size) { return (8 << int(size)) & 0x3f; } +std::string to_string(Operation, DataSize); enum class AddressSize: uint8_t { b16 = 0, diff --git a/OSBindings/Mac/Clock SignalTests/8088Tests.mm b/OSBindings/Mac/Clock SignalTests/8088Tests.mm index dfe02df23..4b1bed3c9 100644 --- a/OSBindings/Mac/Clock SignalTests/8088Tests.mm +++ b/OSBindings/Mac/Clock SignalTests/8088Tests.mm @@ -23,7 +23,7 @@ namespace { // The tests themselves are not duplicated in this repository; // provide their real path here. -constexpr char TestSuiteHome[] = "/Users/thomasharte/Projects/ProcessorTests/8088/v1"; +constexpr char TestSuiteHome[] = "/Users/tharte/Projects/ProcessorTests/8088/v1"; } @@ -37,7 +37,7 @@ constexpr char TestSuiteHome[] = "/Users/thomasharte/Projects/ProcessorTests/808 NSSet *allowList = nil; // [[NSSet alloc] initWithArray:@[ // @"00.json.gz", -// ]]; +// ]];∂ NSArray *files = [[NSFileManager defaultManager] contentsOfDirectoryAtPath:path error:nil]; files = [files filteredArrayUsingPredicate:[NSPredicate predicateWithBlock:^BOOL(NSString* evaluatedObject, NSDictionary *) { @@ -88,14 +88,12 @@ constexpr char TestSuiteHome[] = "/Users/thomasharte/Projects/ProcessorTests/808 log_hex(); // Repeat the decoding, for ease of debugging. - Decoder straw_man; - straw_man.decode(data.data(), data.size()); + Decoder().decode(data.data(), data.size()); return false; } // Form string version, compare. std::string operation; - const bool is_byte_operation = decoded.second.operation_size() == InstructionSet::x86::DataSize::Byte; using Repetition = InstructionSet::x86::Repetition; switch(decoded.second.repetition()) { @@ -104,18 +102,9 @@ constexpr char TestSuiteHome[] = "/Users/thomasharte/Projects/ProcessorTests/808 case Repetition::RepNE: operation += "repne "; break; } - int operands = 0; - using Operation = InstructionSet::x86::Operation; - switch(decoded.second.operation) { - case Operation::SUB: operation += "sub"; operands = 2; break; - case Operation::CMP: operation += "cmp"; operands = 2; break; - case Operation::CMPS: - operation += is_byte_operation? "cmpsb" : "cmpsw"; - break; - default: break; - } + operation += to_string(decoded.second.operation, decoded.second.operation_size()); - auto to_string = [is_byte_operation] (InstructionSet::x86::DataPointer pointer, const auto &instruction) -> std::string { + auto to_string = [] (InstructionSet::x86::DataPointer pointer, const auto &instruction) -> std::string { std::string operand; using Source = InstructionSet::x86::Source; @@ -140,6 +129,7 @@ constexpr char TestSuiteHome[] = "/Users/thomasharte/Projects/ProcessorTests/808 return operand; }; + const int operands = num_operands(decoded.second.operation); if(operands > 1) { operation += " "; operation += to_string(decoded.second.destination(), decoded.second);