From 8bdf8f2a5529fd79234f6c982b0aafcf21fe8406 Mon Sep 17 00:00:00 2001 From: Tim Allen Date: Mon, 8 Aug 2016 20:12:03 +1000 Subject: [PATCH] Update to v101r01 release. byuu says: Changelog: - added eight more 68K instructions - split ADD(direction) into two separate ADD functions I now have 54 out of 88 instructions implemented (thus, 34 remaining.) The map is missing 25,182 entries out of 65,536. Down from 32,680 for v101.00 Aside: this version number feels really silly. r10 and r11 surely will as well ... --- higan/emulator/emulator.hpp | 2 +- higan/emulator/thread.hpp | 5 +- higan/processor/m68k/disassembler.cpp | 52 ++++++-- higan/processor/m68k/instruction.cpp | 174 ++++++++++++++++++++++++-- higan/processor/m68k/instructions.cpp | 140 ++++++++++++++++++--- higan/processor/m68k/m68k.hpp | 29 ++++- higan/sfc/smp/timing.cpp | 4 +- 7 files changed, 362 insertions(+), 44 deletions(-) diff --git a/higan/emulator/emulator.hpp b/higan/emulator/emulator.hpp index 1e2ce5a8..c4f9891c 100644 --- a/higan/emulator/emulator.hpp +++ b/higan/emulator/emulator.hpp @@ -11,7 +11,7 @@ using namespace nall; namespace Emulator { static const string Name = "higan"; - static const string Version = "101"; + static const string Version = "101.01"; static const string Author = "byuu"; static const string License = "GPLv3"; static const string Website = "http://byuu.org/"; diff --git a/higan/emulator/thread.hpp b/higan/emulator/thread.hpp index 640cdc6b..d1358fea 100644 --- a/higan/emulator/thread.hpp +++ b/higan/emulator/thread.hpp @@ -3,6 +3,8 @@ namespace Emulator { struct Thread { + enum : uintmax { Second = (uintmax)1 << (8 * sizeof(uintmax) - 1) }; + virtual ~Thread() { if(_handle) co_delete(_handle); } @@ -15,7 +17,7 @@ struct Thread { auto setFrequency(double frequency) -> void { _frequency = frequency + 0.5; - _scalar = ((uintmax)1 << (8 * sizeof(uintmax) - 1)) / _frequency; + _scalar = Second / _frequency; } auto setScalar(uintmax scalar) -> void { @@ -30,6 +32,7 @@ struct Thread { if(_handle) co_delete(_handle); _handle = co_create(64 * 1024 * sizeof(void*), entrypoint); setFrequency(frequency); + setClock(0); } inline auto step(uint clocks) -> void { diff --git a/higan/processor/m68k/disassembler.cpp b/higan/processor/m68k/disassembler.cpp index 42e708db..64917c68 100644 --- a/higan/processor/m68k/disassembler.cpp +++ b/higan/processor/m68k/disassembler.cpp @@ -90,14 +90,12 @@ auto M68K::disassembleRegisters() -> string { // -template auto M68K::disassembleADD(DataRegister dr, uint1 direction, EffectiveAddress ea) -> string { - string op{"add", _suffix(), " "}; +template auto M68K::disassembleADD(EffectiveAddress from, DataRegister with) -> string { + return {"add", _suffix(), " ", _effectiveAddress(from), ",", _dataRegister(with)}; +} - if(direction == 0) { - return {op, _effectiveAddress(ea), ",", _dataRegister(dr)}; - } else { - return {op, "", _dataRegister(dr), ",", _effectiveAddress(ea)}; - } +template auto M68K::disassembleADD(DataRegister from, EffectiveAddress with) -> string { + return {"add", _suffix(), " ", _dataRegister(from), ",", _effectiveAddress(with)}; } template auto M68K::disassembleADDA(AddressRegister ar, EffectiveAddress ea) -> string { @@ -116,6 +114,14 @@ template auto M68K::disassembleADDX(EffectiveAddress target, Effectiv return {"addx", _suffix(), " ", _effectiveAddress(target), ",", _effectiveAddress(source)}; } +template auto M68K::disassembleAND(EffectiveAddress from, DataRegister with) -> string { + return {"and", _suffix(), " ", _effectiveAddress(from), ",", _dataRegister(with)}; +} + +template auto M68K::disassembleAND(DataRegister from, EffectiveAddress with) -> string { + return {"and", _suffix(), " ", _dataRegister(from), ",", _effectiveAddress(with)}; +} + template auto M68K::disassembleANDI(EffectiveAddress ea) -> string { return {"andi", _suffix(), " ", _immediate(), ",", _effectiveAddress(ea)}; } @@ -193,6 +199,14 @@ auto M68K::disassembleDBCC(uint4 condition, DataRegister dr) -> string { return {"db", _condition(condition), " ", _dataRegister(dr), ",$", hex(base + displacement, 6L)}; } +template auto M68K::disassembleEOR(DataRegister from, EffectiveAddress with) -> string { + return {"eor", _suffix(), " ", _dataRegister(from), ",", _effectiveAddress(with)}; +} + +template auto M68K::disassembleEORI(EffectiveAddress with) -> string { + return {"eori", _suffix(), " ", _immediate(), ",", _effectiveAddress(with)}; +} + auto M68K::disassembleEORI_TO_CCR() -> string { return {"eori ", _immediate(), ",ccr"}; } @@ -287,6 +301,18 @@ auto M68K::disassembleNOP() -> string { return {"nop "}; } +template auto M68K::disassembleOR(EffectiveAddress from, DataRegister with) -> string { + return {"eor", _suffix(), " ", _effectiveAddress(from), ",", _dataRegister(with)}; +} + +template auto M68K::disassembleOR(DataRegister from, EffectiveAddress with) -> string { + return {"eor", _suffix(), " ", _dataRegister(from), ",", _effectiveAddress(with)}; +} + +template auto M68K::disassembleORI(EffectiveAddress with) -> string { + return {"ori", _suffix(), " ", _immediate(), ",", _effectiveAddress(with)}; +} + auto M68K::disassembleORI_TO_CCR() -> string { return {"ori ", _immediate(), ",ccr"}; } @@ -355,10 +381,22 @@ template auto M68K::disassembleSUB(DataRegister source, EffectiveAddr return {"sub", _suffix(), " ", _dataRegister(source), ",", _effectiveAddress(target)}; } +template auto M68K::disassembleSUBA(AddressRegister to, EffectiveAddress from) -> string { + return {"suba", _suffix(), " ", _addressRegister(to), ",", _effectiveAddress(from)}; +} + +template auto M68K::disassembleSUBI(EffectiveAddress with) -> string { + return {"subi", _suffix(), " ", _immediate(), ",", _effectiveAddress(with)}; +} + template auto M68K::disassembleSUBQ(uint4 immediate, EffectiveAddress ea) -> string { return {"subq", _suffix(), " #", immediate, _effectiveAddress(ea)}; } +template auto M68K::disassembleSUBX(EffectiveAddress with, EffectiveAddress from) -> string { + return {"subx", _suffix(), " ", _effectiveAddress(with), ",", _effectiveAddress(from)}; +} + template auto M68K::disassembleTST(EffectiveAddress ea) -> string { return {"tst", _suffix(), " ", _effectiveAddress(ea)}; } diff --git a/higan/processor/m68k/instruction.cpp b/higan/processor/m68k/instruction.cpp index 77393d14..45690f79 100644 --- a/higan/processor/m68k/instruction.cpp +++ b/higan/processor/m68k/instruction.cpp @@ -37,20 +37,33 @@ M68K::M68K() { std::integral_constant::value //ADD - for(uint3 dreg : range(8)) - for(uint1 direction : range(2)) - for(uint3 mode : range(8)) - for(uint3 reg : range(8)) { - auto opcode = pattern("1101 ---- ++-- ----") | dreg << 9 | direction << 8 | mode << 3 | reg << 0; - if(direction == 1 && (mode == 0 || mode == 1 || (mode == 7 && reg >= 2))) continue; + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1101 ---0 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode == 7 && reg >= 5) continue; - DataRegister dr{dreg}; - EffectiveAddress ea{mode, reg}; - bind(opcode | 0 << 6, ADD, dr, direction, ea); - bind(opcode | 1 << 6, ADD, dr, direction, ea); - bind(opcode | 2 << 6, ADD, dr, direction, ea); + EffectiveAddress from{mode, reg}; + DataRegister with{dreg}; + bind(opcode | 0 << 6, ADD, from, with); + bind(opcode | 1 << 6, ADD, from, with); + bind(opcode | 2 << 6, ADD, from, with); - if(direction == 0 && mode == 1) unbind(opcode | 0 << 6); + if(mode == 1) unbind(opcode | 0 << 6); + } + + //ADD + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1101 ---1 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode <= 1 || (mode == 7 && reg >= 2)) continue; + + DataRegister from{dreg}; + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, ADD, from, with); + bind(opcode | 1 << 6, ADD, from, with); + bind(opcode | 2 << 6, ADD, from, with); } //ADDA @@ -112,6 +125,34 @@ M68K::M68K() { bind(opcode | 2 << 6 | 1 << 3, ADDX, addressTarget, addressSource); } + //AND + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1100 ---0 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 5)) continue; + + EffectiveAddress from{mode, reg}; + DataRegister with{dreg}; + bind(opcode | 0 << 6, AND, from, with); + bind(opcode | 1 << 6, AND, from, with); + bind(opcode | 2 << 6, AND, from, with); + } + + //AND + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1100 ---1 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode <= 1 || (mode == 7 && reg >= 2)) continue; + + DataRegister from{dreg}; + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, AND, from, with); + bind(opcode | 1 << 6, AND, from, with); + bind(opcode | 2 << 6, AND, from, with); + } + //ANDI for(uint3 mode : range(8)) for(uint3 reg : range(8)) { @@ -309,6 +350,32 @@ M68K::M68K() { bind(opcode, DBCC, condition, dr); } + //EOR + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1011 ---1 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 2)) continue; + + DataRegister from{dreg}; + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, EOR, from, with); + bind(opcode | 1 << 6, EOR, from, with); + bind(opcode | 2 << 6, EOR, from, with); + } + + //EORI + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("0000 1010 ++-- ----") | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 2)) continue; + + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, EORI, with); + bind(opcode | 1 << 6, EORI, with); + bind(opcode | 2 << 6, EORI, with); + } + //EORI_TO_CCR { auto opcode = pattern("0000 1010 0011 1100"); @@ -509,6 +576,46 @@ M68K::M68K() { bind(opcode, NOP); } + //OR + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1000 ---0 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 5)) continue; + + EffectiveAddress from{mode, reg}; + DataRegister with{dreg}; + bind(opcode | 0 << 6, OR, from, with); + bind(opcode | 1 << 6, OR, from, with); + bind(opcode | 2 << 6, OR, from, with); + } + + //OR + for(uint3 dreg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1000 ---1 ++-- ----") | dreg << 9 | mode << 3 | reg << 0; + if(mode <= 1 || (mode == 7 && reg >= 2)) continue; + + DataRegister from{dreg}; + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, OR, from, with); + bind(opcode | 1 << 6, OR, from, with); + bind(opcode | 2 << 6, OR, from, with); + } + + //ORI + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("0000 0000 ++-- ----") | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 2)) continue; + + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, ORI, with); + bind(opcode | 1 << 6, ORI, with); + bind(opcode | 2 << 6, ORI, with); + } + //ORI_TO_CCR { auto opcode = pattern("0000 0000 0011 1100"); @@ -693,6 +800,31 @@ M68K::M68K() { bind(opcode | 2 << 6, SUB, source, target); } + //SUBA + for(uint3 areg : range(8)) + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("1001 ---+ 11-- ----") | areg << 9 | mode << 3 | reg << 0; + if(mode == 7 && reg >= 5) continue; + + AddressRegister to{areg}; + EffectiveAddress from{mode, reg}; + bind(opcode | 0 << 8, SUBA, to, from); + bind(opcode | 1 << 8, SUBA, to, from); + } + + //SUBI + for(uint3 mode : range(8)) + for(uint3 reg : range(8)) { + auto opcode = pattern("0000 0100 ++-- ----") | mode << 3 | reg << 0; + if(mode == 1 || (mode == 7 && reg >= 2)) continue; + + EffectiveAddress with{mode, reg}; + bind(opcode | 0 << 6, SUBI, with); + bind(opcode | 1 << 6, SUBI, with); + bind(opcode | 2 << 6, SUBI, with); + } + //SUBQ for(uint3 data : range(8)) for(uint3 mode : range(8)) @@ -709,6 +841,24 @@ M68K::M68K() { if(mode == 1) unbind(opcode | 0 << 6); } + //SUBX + for(uint3 treg : range(8)) + for(uint3 sreg : range(8)) { + auto opcode = pattern("1001 ---1 ++00 ----") | treg << 9 | sreg << 0; + + EffectiveAddress dataTarget{DataRegisterDirect, treg}; + EffectiveAddress dataSource{DataRegisterDirect, sreg}; + bind(opcode | 0 << 6 | 0 << 3, SUBX, dataTarget, dataSource); + bind(opcode | 1 << 6 | 0 << 3, SUBX, dataTarget, dataSource); + bind(opcode | 2 << 6 | 0 << 3, SUBX, dataTarget, dataSource); + + EffectiveAddress addressTarget{AddressRegisterIndirectWithPreDecrement, treg}; + EffectiveAddress addressSource{AddressRegisterIndirectWithPreDecrement, sreg}; + bind(opcode | 0 << 6 | 1 << 3, SUBX, addressTarget, addressSource); + bind(opcode | 1 << 6 | 1 << 3, SUBX, addressTarget, addressSource); + bind(opcode | 2 << 6 | 1 << 3, SUBX, addressTarget, addressSource); + } + //TST for(uint3 mode : range(8)) for(uint3 reg : range(8)) { diff --git a/higan/processor/m68k/instructions.cpp b/higan/processor/m68k/instructions.cpp index 2bf984f8..b170fc8b 100644 --- a/higan/processor/m68k/instructions.cpp +++ b/higan/processor/m68k/instructions.cpp @@ -72,18 +72,24 @@ template auto M68K::ADD(uint32 source, uint32 target) -> return clip(result); } -template auto M68K::instructionADD(DataRegister dr, uint1 direction, EffectiveAddress ea) -> void { - if(direction == 0) { - auto source = read(ea); - auto target = read(dr); - auto result = ADD(source, target); - write(dr, result); - } else { - auto source = read(dr); - auto target = read(ea); - auto result = ADD(source, target); - write(ea, result); - } +template auto M68K::instructionADD(EffectiveAddress from, DataRegister with) -> void { + auto source = read(from); + auto target = read(with); + auto result = ADD(source, target); + write(with, result); +} + +template auto M68K::instructionADD(DataRegister from, EffectiveAddress with) -> void { + auto source = read(from); + auto target = read(with); + auto result = ADD(source, target); + write(with, result); +} + +template auto M68K::instructionADDA(AddressRegister ar, EffectiveAddress ea) -> void { + auto source = read(ea); + auto target = read(ar); + write(ar, source + target); } template auto M68K::instructionADDI(EffectiveAddress modify) -> void { @@ -93,12 +99,6 @@ template auto M68K::instructionADDI(EffectiveAddress modify) -> void write(modify, result); } -template auto M68K::instructionADDA(AddressRegister ar, EffectiveAddress ea) -> void { - auto source = read(ea); - auto target = read(ar); - write(ar, source + target); -} - template auto M68K::instructionADDQ(uint4 immediate, EffectiveAddress modify) -> void { auto source = read(modify); auto target = immediate; @@ -113,10 +113,35 @@ template auto M68K::instructionADDX(EffectiveAddress target_, Effecti write(target, result); } +template auto M68K::AND(uint32 source, uint32 target) -> uint32 { + uint32 result = target & source; + + r.c = 0; + r.v = 0; + r.z = clip(result) == 0; + r.n = sign(result) < 0; + + return clip(result); +} + +template auto M68K::instructionAND(EffectiveAddress from, DataRegister with) -> void { + auto source = read(from); + auto target = read(with); + auto result = AND(source, target); + write(with, result); +} + +template auto M68K::instructionAND(DataRegister from, EffectiveAddress with) -> void { + auto source = read(from); + auto target = read(with); + auto result = AND(source, target); + write(with, result); +} + template auto M68K::instructionANDI(EffectiveAddress ea) -> void { auto source = readPC(); auto target = read(ea); - auto result = target & source; + auto result = AND(source, target); write(ea, result); r.c = 0; @@ -288,6 +313,31 @@ auto M68K::instructionDBCC(uint4 condition, DataRegister dr) -> void { } } +template auto M68K::EOR(uint32 source, uint32 target) -> uint32 { + uint32 result = target ^ source; + + r.c = 0; + r.v = 0; + r.z = clip(result) == 0; + r.n = sign(result) < 0; + + return clip(result); +} + +template auto M68K::instructionEOR(DataRegister from, EffectiveAddress with) -> void { + auto source = read(from); + auto target = read(with); + auto result = EOR(source, target); + write(with, result); +} + +template auto M68K::instructionEORI(EffectiveAddress with) -> void { + auto source = readPC(); + auto target = read(with); + auto result = EOR(source, target); + write(with, result); +} + auto M68K::instructionEORI_TO_CCR() -> void { auto data = readPC(); writeCCR(readCCR() ^ data); @@ -454,6 +504,38 @@ auto M68K::instructionMOVE_USP(uint1 direction, AddressRegister ar) -> void { auto M68K::instructionNOP() -> void { } +template auto M68K::OR(uint32 source, uint32 target) -> uint32 { + auto result = target | source; + + r.c = 0; + r.v = 0; + r.z = clip(result) == 0; + r.n = sign(result) < 0; + + return clip(result); +} + +template auto M68K::instructionOR(EffectiveAddress from, DataRegister with) -> void { + auto source = read(from); + auto target = read(with); + auto result = OR(source, target); + write(with, result); +} + +template auto M68K::instructionOR(DataRegister from, EffectiveAddress with) -> void { + auto source = read(from); + auto target = read(with); + auto result = OR(source, target); + write(with, result); +} + +template auto M68K::instructionORI(EffectiveAddress with) -> void { + auto source = readPC(); + auto target = read(with); + auto result = OR(source, target); + write(with, result); +} + auto M68K::instructionORI_TO_CCR() -> void { auto data = readPC(); writeCCR(readCCR() | data); @@ -628,6 +710,19 @@ template auto M68K::instructionSUB(DataRegister source_, EffectiveAdd write(target_, result); } +template auto M68K::instructionSUBA(AddressRegister to, EffectiveAddress from) -> void { + auto source = read(from); + auto target = read(to); + write(to, target - source); +} + +template auto M68K::instructionSUBI(EffectiveAddress with) -> void { + auto source = readPC(); + auto target = read(with); + auto result = SUB(source, target); + write(with, result); +} + template auto M68K::instructionSUBQ(uint4 immediate, EffectiveAddress ea) -> void { auto source = immediate; auto target = read(ea); @@ -635,6 +730,13 @@ template auto M68K::instructionSUBQ(uint4 immediate, EffectiveAddress write(ea, result); } +template auto M68K::instructionSUBX(EffectiveAddress with, EffectiveAddress from) -> void { + auto source = read(from); + auto target = read(with); + auto result = SUB(source, target); + write(with, result); +} + template auto M68K::instructionTST(EffectiveAddress ea) -> void { auto data = read(ea); diff --git a/higan/processor/m68k/m68k.hpp b/higan/processor/m68k/m68k.hpp index e242a1eb..1b4013d5 100644 --- a/higan/processor/m68k/m68k.hpp +++ b/higan/processor/m68k/m68k.hpp @@ -98,11 +98,15 @@ struct M68K { template auto negative(uint32 result) -> bool; template auto ADD(uint32 source, uint32 target) -> uint32; - template auto instructionADD(DataRegister dr, uint1 direction, EffectiveAddress ea) -> void; + template auto instructionADD(EffectiveAddress from, DataRegister with) -> void; + template auto instructionADD(DataRegister from, EffectiveAddress with) -> void; template auto instructionADDA(AddressRegister ar, EffectiveAddress ea) -> void; template auto instructionADDI(EffectiveAddress modify) -> void; template auto instructionADDQ(uint4 immediate, EffectiveAddress modify) -> void; template auto instructionADDX(EffectiveAddress target, EffectiveAddress source) -> void; + template auto AND(uint32 source, uint32 target) -> uint32; + template auto instructionAND(EffectiveAddress from, DataRegister with) -> void; + template auto instructionAND(DataRegister from, EffectiveAddress with) -> void; template auto instructionANDI(EffectiveAddress ea) -> void; auto instructionANDI_TO_CCR() -> void; auto instructionANDI_TO_SR() -> void; @@ -124,6 +128,9 @@ struct M68K { template auto instructionCMPI(EffectiveAddress ea) -> void; template auto instructionCMPM(EffectiveAddress ax, EffectiveAddress ay) -> void; auto instructionDBCC(uint4 condition, DataRegister dr) -> void; + template auto EOR(uint32 source, uint32 target) -> uint32; + template auto instructionEOR(DataRegister from, EffectiveAddress with) -> void; + template auto instructionEORI(EffectiveAddress with) -> void; auto instructionEORI_TO_CCR() -> void; auto instructionEORI_TO_SR() -> void; auto instructionJSR(EffectiveAddress target) -> void; @@ -145,6 +152,10 @@ struct M68K { auto instructionMOVE_TO_SR(EffectiveAddress ea) -> void; auto instructionMOVE_USP(uint1 direction, AddressRegister ar) -> void; auto instructionNOP() -> void; + template auto OR(uint32 source, uint32 target) -> uint32; + template auto instructionOR(EffectiveAddress from, DataRegister with) -> void; + template auto instructionOR(DataRegister from, EffectiveAddress with) -> void; + template auto instructionORI(EffectiveAddress with) -> void; auto instructionORI_TO_CCR() -> void; auto instructionORI_TO_SR() -> void; template auto ROL(uint32 result, uint shift) -> uint32; @@ -167,7 +178,10 @@ struct M68K { template auto SUB(uint32 source, uint32 target) -> uint32; template auto instructionSUB(EffectiveAddress source, DataRegister target) -> void; template auto instructionSUB(DataRegister source, EffectiveAddress target) -> void; + template auto instructionSUBA(AddressRegister to, EffectiveAddress from) -> void; + template auto instructionSUBI(EffectiveAddress with) -> void; template auto instructionSUBQ(uint4 immediate, EffectiveAddress ea) -> void; + template auto instructionSUBX(EffectiveAddress with, EffectiveAddress from) -> void; template auto instructionTST(EffectiveAddress ea) -> void; //disassembler.cpp @@ -197,11 +211,14 @@ struct M68K { private: //disassembler.cpp - template auto disassembleADD(DataRegister dr, uint1 direction, EffectiveAddress ea) -> string; + template auto disassembleADD(EffectiveAddress from, DataRegister with) -> string; + template auto disassembleADD(DataRegister from, EffectiveAddress with) -> string; template auto disassembleADDA(AddressRegister ar, EffectiveAddress ea) -> string; template auto disassembleADDI(EffectiveAddress modify) -> string; template auto disassembleADDQ(uint4 immediate, EffectiveAddress modify) -> string; template auto disassembleADDX(EffectiveAddress target, EffectiveAddress source) -> string; + template auto disassembleAND(EffectiveAddress from, DataRegister with) -> string; + template auto disassembleAND(DataRegister from, EffectiveAddress with) -> string; template auto disassembleANDI(EffectiveAddress ea) -> string; auto disassembleANDI_TO_CCR() -> string; auto disassembleANDI_TO_SR() -> string; @@ -220,6 +237,8 @@ private: template auto disassembleCMPI(EffectiveAddress ea) -> string; template auto disassembleCMPM(EffectiveAddress ax, EffectiveAddress ay) -> string; auto disassembleDBCC(uint4 condition, DataRegister dr) -> string; + template auto disassembleEOR(DataRegister from, EffectiveAddress with) -> string; + template auto disassembleEORI(EffectiveAddress with) -> string; auto disassembleEORI_TO_CCR() -> string; auto disassembleEORI_TO_SR() -> string; auto disassembleJSR(EffectiveAddress target) -> string; @@ -239,6 +258,9 @@ private: auto disassembleMOVE_TO_SR(EffectiveAddress ea) -> string; auto disassembleMOVE_USP(uint1 direction, AddressRegister ar) -> string; auto disassembleNOP() -> string; + template auto disassembleOR(EffectiveAddress from, DataRegister with) -> string; + template auto disassembleOR(DataRegister from, EffectiveAddress with) -> string; + template auto disassembleORI(EffectiveAddress with) -> string; auto disassembleORI_TO_CCR() -> string; auto disassembleORI_TO_SR() -> string; template auto disassembleROL(uint4 shift, DataRegister modify) -> string; @@ -256,7 +278,10 @@ private: auto disassembleRTS() -> string; template auto disassembleSUB(EffectiveAddress source, DataRegister target) -> string; template auto disassembleSUB(DataRegister source, EffectiveAddress target) -> string; + template auto disassembleSUBA(AddressRegister to, EffectiveAddress from) -> string; + template auto disassembleSUBI(EffectiveAddress with) -> string; template auto disassembleSUBQ(uint4 immediate, EffectiveAddress ea) -> string; + template auto disassembleSUBX(EffectiveAddress with, EffectiveAddress from) -> string; template auto disassembleTST(EffectiveAddress ea) -> string; template auto _read(uint32 addr) -> uint32; diff --git a/higan/sfc/smp/timing.cpp b/higan/sfc/smp/timing.cpp index 95407cb5..42edb8d4 100644 --- a/higan/sfc/smp/timing.cpp +++ b/higan/sfc/smp/timing.cpp @@ -6,8 +6,8 @@ auto SMP::step(uint clocks) -> void { synchronize(cpu); #else //forcefully sync S-SMP to S-CPU in case chips are not communicating - //sync if S-SMP is more than 24 samples ahead of S-CPU - if(clock() - cpu.clock() > frequency() * scalar() / (768 / 24)) synchronize(cpu); + //sync if S-SMP is more than 1ms ahead of S-CPU + if(clock() - cpu.clock() > Thread::Second / 1'000) synchronize(cpu); #endif }