From a877f2a33e6b4b0903518ebb991debf0c53ebd43 Mon Sep 17 00:00:00 2001 From: Ran-j Date: Mon, 14 Apr 2025 00:22:53 -0300 Subject: [PATCH] feat: convert translated instructions from variable in static array --- ps2xRecomp/src/code_generator.cpp | 348 +++++++++++++++--------------- 1 file changed, 173 insertions(+), 175 deletions(-) diff --git a/ps2xRecomp/src/code_generator.cpp b/ps2xRecomp/src/code_generator.cpp index 8d4f153..5a119bc 100644 --- a/ps2xRecomp/src/code_generator.cpp +++ b/ps2xRecomp/src/code_generator.cpp @@ -21,7 +21,7 @@ namespace ps2recomp if (branchInst.opcode == OPCODE_JAL) { // For JAL, set the return address - ss << " ctx->r31 = 0x" << std::hex << (branchInst.address + 8) << ";\n" + ss << " ctx->r[31] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; } @@ -49,7 +49,7 @@ namespace ps2recomp if (branchInst.function == SPECIAL_JALR) { // For JALR, set the return address - ss << " ctx->r" << branchInst.rd << " = 0x" << std::hex << (branchInst.address + 8) << ";\n" + ss << " ctx->r[" << branchInst.rd << "] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; } @@ -64,7 +64,7 @@ namespace ps2recomp } else { - ss << " LOOKUP_FUNC(ctx->r" << branchInst.rs << ")(rdram, ctx);\n"; + ss << " LOOKUP_FUNC(ctx->r[" << branchInst.rs << "])(rdram, ctx);\n"; ss << " return;\n"; } } @@ -76,77 +76,77 @@ namespace ps2recomp switch (branchInst.opcode) { case OPCODE_BEQ: - conditionStr = fmt::format("ctx->r{} == ctx->r{}", branchInst.rs, branchInst.rt); + conditionStr = fmt::format("ctx->r[{}] == ctx->r[{}]", branchInst.rs, branchInst.rt); break; case OPCODE_BNE: - conditionStr = fmt::format("ctx->r{} != ctx->r{}", branchInst.rs, branchInst.rt); + conditionStr = fmt::format("ctx->r[{}] != ctx->r[{}]", branchInst.rs, branchInst.rt); break; case OPCODE_BLEZ: - conditionStr = fmt::format("(int32_t)ctx->r{} <= 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] <= 0", branchInst.rs); break; case OPCODE_BGTZ: - conditionStr = fmt::format("(int32_t)ctx->r{} > 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] > 0", branchInst.rs); break; case OPCODE_BEQL: - conditionStr = fmt::format("ctx->r{} == ctx->r{}", branchInst.rs, branchInst.rt); + conditionStr = fmt::format("ctx->r[{}] == ctx->r[{}]", branchInst.rs, branchInst.rt); break; case OPCODE_BNEL: - conditionStr = fmt::format("ctx->r{} != ctx->r{}", branchInst.rs, branchInst.rt); + conditionStr = fmt::format("ctx->r[{}] != ctx->r[{}]", branchInst.rs, branchInst.rt); break; case OPCODE_BLEZL: - conditionStr = fmt::format("(int32_t)ctx->r{} <= 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] <= 0", branchInst.rs); break; case OPCODE_BGTZL: - conditionStr = fmt::format("(int32_t)ctx->r{} > 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] > 0", branchInst.rs); break; case OPCODE_REGIMM: switch (branchInst.rt) { case REGIMM_BLTZ: - conditionStr = fmt::format("(int32_t)ctx->r{} < 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] < 0", branchInst.rs); break; case REGIMM_BGEZ: - conditionStr = fmt::format("(int32_t)ctx->r{} >= 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] >= 0", branchInst.rs); break; case REGIMM_BLTZL: - conditionStr = fmt::format("(int32_t)ctx->r{} < 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] < 0", branchInst.rs); break; case REGIMM_BGEZL: - conditionStr = fmt::format("(int32_t)ctx->r{} >= 0", branchInst.rs); + conditionStr = fmt::format("(int32_t)ctx->r[{}] >= 0", branchInst.rs); break; case REGIMM_BLTZAL: - conditionStr = fmt::format("(int32_t)ctx->r{} < 0", branchInst.rs); - ss << " ctx->r31 = 0x" << std::hex << (branchInst.address + 8) << ";\n" + conditionStr = fmt::format("(int32_t)ctx->r[{}] < 0", branchInst.rs); + ss << " ctx->r[31] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; break; case REGIMM_BGEZAL: - conditionStr = fmt::format("(int32_t)ctx->r{} >= 0", branchInst.rs); - ss << " ctx->r31 = 0x" << std::hex << (branchInst.address + 8) << ";\n" + conditionStr = fmt::format("(int32_t)ctx->r[{}] >= 0", branchInst.rs); + ss << " ctx->r[31] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; break; case REGIMM_BLTZALL: - conditionStr = fmt::format("(int32_t)ctx->r{} < 0", branchInst.rs); - ss << " ctx->r31 = 0x" << std::hex << (branchInst.address + 8) << ";\n" + conditionStr = fmt::format("(int32_t)ctx->r[{}] < 0", branchInst.rs); + ss << " ctx->r[31] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; break; case REGIMM_BGEZALL: - conditionStr = fmt::format("(int32_t)ctx->r{} >= 0", branchInst.rs); - ss << " ctx->r31 = 0x" << std::hex << (branchInst.address + 8) << ";\n" + conditionStr = fmt::format("(int32_t)ctx->r[{}] >= 0", branchInst.rs); + ss << " ctx->r[31] = 0x" << std::hex << (branchInst.address + 8) << ";\n" << std::dec; break; @@ -453,98 +453,98 @@ namespace ps2recomp { return "// NOP"; } - return fmt::format("ctx->r{} = SLL32(ctx->r{}, {});", + return fmt::format("ctx->r[{}] = SLL32(ctx->r[{}], {});", inst.rd, inst.rt, inst.sa); case SPECIAL_SRL: - return fmt::format("ctx->r{} = SRL32(ctx->r{}, {});", + return fmt::format("ctx->r[{}] = SRL32(ctx->r[{}], {});", inst.rd, inst.rt, inst.sa); case SPECIAL_SRA: - return fmt::format("ctx->r{} = SRA32(ctx->r{}, {});", + return fmt::format("ctx->r[{}] = SRA32(ctx->r[{}], {});", inst.rd, inst.rt, inst.sa); case SPECIAL_SLLV: - return fmt::format("ctx->r{} = SLL32(ctx->r{}, ctx->r{} & 0x1F);", + return fmt::format("ctx->r[{}] = SLL32(ctx->r[{}], ctx->r[{}] & 0x1F);", inst.rd, inst.rt, inst.rs); case SPECIAL_SRLV: - return fmt::format("ctx->r{} = SRL32(ctx->r{}, ctx->r{} & 0x1F);", + return fmt::format("ctx->r[{}] = SRL32(ctx->r[{}], ctx->r[{}] & 0x1F);", inst.rd, inst.rt, inst.rs); case SPECIAL_SRAV: - return fmt::format("ctx->r{} = SRA32(ctx->r{}, ctx->r{} & 0x1F);", + return fmt::format("ctx->r[{}] = SRA32(ctx->r[{}], ctx->r[{}] & 0x1F);", inst.rd, inst.rt, inst.rs); case SPECIAL_MFHI: - return fmt::format("ctx->r{} = ctx->hi;", inst.rd); + return fmt::format("ctx->r[{}] = ctx->hi;", inst.rd); case SPECIAL_MTHI: - return fmt::format("ctx->hi = ctx->r{};", inst.rs); + return fmt::format("ctx->hi = ctx->r[{}];", inst.rs); case SPECIAL_MFLO: - return fmt::format("ctx->r{} = ctx->lo;", inst.rd); + return fmt::format("ctx->r[{}] = ctx->lo;", inst.rd); case SPECIAL_MTLO: - return fmt::format("ctx->lo = ctx->r{};", inst.rs); + return fmt::format("ctx->lo = ctx->r[{}];", inst.rs); case SPECIAL_MULT: - return fmt::format("{{ int64_t result = (int64_t)(int32_t)ctx->r{} * (int64_t)(int32_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ int64_t result = (int64_t)(int32_t)ctx->r[{}] * (int64_t)(int32_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case SPECIAL_MULTU: - return fmt::format("{{ uint64_t result = (uint64_t)ctx->r{} * (uint64_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ uint64_t result = (uint64_t)ctx->r[{}] * (uint64_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case SPECIAL_DIV: - return fmt::format("{{ if (ctx->r{} != 0) {{ ctx->lo = (uint32_t)((int32_t)ctx->r{} / (int32_t)ctx->r{}); ctx->hi = (uint32_t)((int32_t)ctx->r{} % (int32_t)ctx->r{}); }} }}", + return fmt::format("{{ if (ctx->r[{}] != 0) {{ ctx->lo = (uint32_t)((int32_t)ctx->r[{}] / (int32_t)ctx->r[{}]); ctx->hi = (uint32_t)((int32_t)ctx->r[{}] % (int32_t)ctx->r[{}]); }} }}", inst.rt, inst.rs, inst.rt, inst.rs, inst.rt); case SPECIAL_DIVU: - return fmt::format("{{ if (ctx->r{} != 0) {{ ctx->lo = ctx->r{} / ctx->r{}; ctx->hi = ctx->r{} % ctx->r{}; }} }}", + return fmt::format("{{ if (ctx->r[{}] != 0) {{ ctx->lo = ctx->r[{}] / ctx->r[{}]; ctx->hi = ctx->r[{}] % ctx->r[{}]; }} }}", inst.rt, inst.rs, inst.rt, inst.rs, inst.rt); case SPECIAL_ADD: case SPECIAL_ADDU: - return fmt::format("ctx->r{} = ADD32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = ADD32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_SUB: case SPECIAL_SUBU: - return fmt::format("ctx->r{} = SUB32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = SUB32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_AND: - return fmt::format("ctx->r{} = AND32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = AND32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_OR: - return fmt::format("ctx->r{} = OR32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = OR32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_XOR: - return fmt::format("ctx->r{} = XOR32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = XOR32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_NOR: - return fmt::format("ctx->r{} = NOR32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = NOR32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_SLT: - return fmt::format("ctx->r{} = SLT32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = SLT32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case SPECIAL_SLTU: - return fmt::format("ctx->r{} = SLTU32(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = SLTU32(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); // PS2-specific instructions case SPECIAL_MOVZ: - return fmt::format("if (ctx->r{} == 0) ctx->r{} = ctx->r{};", + return fmt::format("if (ctx->r[{}] == 0) ctx->r[{}] = ctx->r[{}];", inst.rt, inst.rd, inst.rs); case SPECIAL_MOVN: - return fmt::format("if (ctx->r{} != 0) ctx->r{} = ctx->r{};", + return fmt::format("if (ctx->r[{}] != 0) ctx->r[{}] = ctx->r[{}];", inst.rt, inst.rd, inst.rs); default: @@ -558,72 +558,72 @@ namespace ps2recomp { return "// NOP (addiu $zero, ...)"; } - return fmt::format("ctx->r{} = ADD32(ctx->r{}, 0x{:X});", + return fmt::format("ctx->r[{}] = ADD32(ctx->r[{}], 0x{:X});", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_SLTI: - return fmt::format("ctx->r{} = (int32_t)ctx->r{} < (int32_t)0x{:X} ? 1 : 0;", + return fmt::format("ctx->r[{}] = (int32_t)ctx->r[{}] < (int32_t)0x{:X} ? 1 : 0;", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_SLTIU: - return fmt::format("ctx->r{} = ctx->r{} < (uint32_t)0x{:X} ? 1 : 0;", + return fmt::format("ctx->r[{}] = ctx->r[{}] < (uint32_t)0x{:X} ? 1 : 0;", inst.rt, inst.rs, (uint32_t)(int16_t)inst.immediate); case OPCODE_ANDI: - return fmt::format("ctx->r{} = AND32(ctx->r{}, 0x{:X});", + return fmt::format("ctx->r[{}] = AND32(ctx->r[{}], 0x{:X});", inst.rt, inst.rs, inst.immediate); case OPCODE_ORI: - return fmt::format("ctx->r{} = OR32(ctx->r{}, 0x{:X});", + return fmt::format("ctx->r[{}] = OR32(ctx->r[{}], 0x{:X});", inst.rt, inst.rs, inst.immediate); case OPCODE_XORI: - return fmt::format("ctx->r{} = XOR32(ctx->r{}, 0x{:X});", + return fmt::format("ctx->r[{}] = XOR32(ctx->r[{}], 0x{:X});", inst.rt, inst.rs, inst.immediate); case OPCODE_LUI: - return fmt::format("ctx->r{} = 0x{:X} << 16;", + return fmt::format("ctx->r[{}] = 0x{:X} << 16;", inst.rt, inst.immediate); case OPCODE_LB: - return fmt::format("ctx->r{} = (int32_t)(int8_t)READ8(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = (int32_t)(int8_t)READ8(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_LH: - return fmt::format("ctx->r{} = (int32_t)(int16_t)READ16(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = (int32_t)(int16_t)READ16(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_LW: - return fmt::format("ctx->r{} = READ32(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = READ32(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_LBU: - return fmt::format("ctx->r{} = (uint32_t)READ8(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = (uint32_t)READ8(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_LHU: - return fmt::format("ctx->r{} = (uint32_t)READ16(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = (uint32_t)READ16(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_SB: - return fmt::format("WRITE8(ADD32(ctx->r{}, 0x{:X}), (uint8_t)ctx->r{});", + return fmt::format("WRITE8(ADD32(ctx->r[{}], 0x{:X}), (uint8_t)ctx->r[{}]);", inst.rs, (int16_t)inst.immediate, inst.rt); case OPCODE_SH: - return fmt::format("WRITE16(ADD32(ctx->r{}, 0x{:X}), (uint16_t)ctx->r{});", + return fmt::format("WRITE16(ADD32(ctx->r[{}], 0x{:X}), (uint16_t)ctx->r[{}]);", inst.rs, (int16_t)inst.immediate, inst.rt); case OPCODE_SW: - return fmt::format("WRITE32(ADD32(ctx->r{}, 0x{:X}), ctx->r{});", + return fmt::format("WRITE32(ADD32(ctx->r[{}], 0x{:X}), ctx->r[{}]);", inst.rs, (int16_t)inst.immediate, inst.rt); // PS2-specific 128-bit load/store case OPCODE_LQ: - return fmt::format("ctx->r{} = (__m128i)READ128(ADD32(ctx->r{}, 0x{:X}));", + return fmt::format("ctx->r[{}] = (__m128i)READ128(ADD32(ctx->r[{}], 0x{:X}));", inst.rt, inst.rs, (int16_t)inst.immediate); case OPCODE_SQ: - return fmt::format("WRITE128(ADD32(ctx->r{}, 0x{:X}), (__m128i)ctx->r{});", + return fmt::format("WRITE128(ADD32(ctx->r[{}], 0x{:X}), (__m128i)ctx->r[{}]);", inst.rs, (int16_t)inst.immediate, inst.rt); // Special case for R5900 @@ -651,51 +651,51 @@ namespace ps2recomp switch (function) { case MMI_MADD: - return fmt::format("{{ int64_t result = (int64_t)(((int64_t)ctx->hi << 32) | ctx->lo) + (int64_t)(int32_t)ctx->r{} * (int64_t)(int32_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ int64_t result = (int64_t)(((int64_t)ctx->hi << 32) | ctx->lo) + (int64_t)(int32_t)ctx->r[{}] * (int64_t)(int32_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case MMI_MADDU: - return fmt::format("{{ uint64_t result = (uint64_t)(((uint64_t)ctx->hi << 32) | ctx->lo) + (uint64_t)ctx->r{} * (uint64_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ uint64_t result = (uint64_t)(((uint64_t)ctx->hi << 32) | ctx->lo) + (uint64_t)ctx->r[{}] * (uint64_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case MMI_PLZCW: - return fmt::format("ctx->r{} = __builtin_clz(ctx->r{});", + return fmt::format("ctx->r[{}] = __builtin_clz(ctx->r[{}]);", inst.rd, inst.rs); case MMI_MFHI1: - return fmt::format("ctx->r{} = ctx->hi;", inst.rd); + return fmt::format("ctx->r[{}] = ctx->hi;", inst.rd); case MMI_MTHI1: - return fmt::format("ctx->hi = ctx->r{};", inst.rs); + return fmt::format("ctx->hi = ctx->r[{}];", inst.rs); case MMI_MFLO1: - return fmt::format("ctx->r{} = ctx->lo;", inst.rd); + return fmt::format("ctx->r[{}] = ctx->lo;", inst.rd); case MMI_MTLO1: - return fmt::format("ctx->lo = ctx->r{};", inst.rs); + return fmt::format("ctx->lo = ctx->r[{}];", inst.rs); case MMI_MULT1: - return fmt::format("{{ int64_t result = (int64_t)(int32_t)ctx->r{} * (int64_t)(int32_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ int64_t result = (int64_t)(int32_t)ctx->r[{}] * (int64_t)(int32_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case MMI_MULTU1: - return fmt::format("{{ uint64_t result = (uint64_t)ctx->r{} * (uint64_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ uint64_t result = (uint64_t)ctx->r[{}] * (uint64_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case MMI_DIV1: - return fmt::format("{{ if (ctx->r{} != 0) {{ ctx->lo = (uint32_t)((int32_t)ctx->r{} / (int32_t)ctx->r{}); ctx->hi = (uint32_t)((int32_t)ctx->r{} % (int32_t)ctx->r{}); }} }}", + return fmt::format("{{ if (ctx->r[{}] != 0) {{ ctx->lo = (uint32_t)((int32_t)ctx->r[{}] / (int32_t)ctx->r[{}]); ctx->hi = (uint32_t)((int32_t)ctx->r[{}] % (int32_t)ctx->r[{}]); }} }}", inst.rt, inst.rs, inst.rt, inst.rs, inst.rt); case MMI_DIVU1: - return fmt::format("{{ if (ctx->r{} != 0) {{ ctx->lo = ctx->r{} / ctx->r{}; ctx->hi = ctx->r{} % ctx->r{}; }} }}", + return fmt::format("{{ if (ctx->r[{}] != 0) {{ ctx->lo = ctx->r[{}] / ctx->r[{}]; ctx->hi = ctx->r[{}] % ctx->r[{}]; }} }}", inst.rt, inst.rs, inst.rt, inst.rs, inst.rt); case MMI_MADD1: - return fmt::format("{{ int64_t result = (int64_t)(((int64_t)ctx->hi << 32) | ctx->lo) + (int64_t)(int32_t)ctx->r{} * (int64_t)(int32_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ int64_t result = (int64_t)(((int64_t)ctx->hi << 32) | ctx->lo) + (int64_t)(int32_t)ctx->r[{}] * (int64_t)(int32_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); case MMI_MADDU1: - return fmt::format("{{ uint64_t result = (uint64_t)(((uint64_t)ctx->hi << 32) | ctx->lo) + (uint64_t)ctx->r{} * (uint64_t)ctx->r{}; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", + return fmt::format("{{ uint64_t result = (uint64_t)(((uint64_t)ctx->hi << 32) | ctx->lo) + (uint64_t)ctx->r[{}] * (uint64_t)ctx->r[{}]; ctx->lo = (uint32_t)result; ctx->hi = (uint32_t)(result >> 32); }}", inst.rs, inst.rt); // MMI0 functions (PADDW, PSUBW, etc.) @@ -703,67 +703,67 @@ namespace ps2recomp switch (inst.sa) { case MMI0_PADDW: - return fmt::format("ctx->r{} = PS2_PADDW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PSUBW: - return fmt::format("ctx->r{} = PS2_PSUBW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PCGTW: - return fmt::format("ctx->r{} = PS2_PCGTW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCGTW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PMAXW: - return fmt::format("ctx->r{} = PS2_PMAXW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PMAXW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PADDH: - return fmt::format("ctx->r{} = PS2_PADDH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PSUBH: - return fmt::format("ctx->r{} = PS2_PSUBH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PCGTH: - return fmt::format("ctx->r{} = PS2_PCGTH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCGTH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PMAXH: - return fmt::format("ctx->r{} = PS2_PMAXH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PMAXH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PADDB: - return fmt::format("ctx->r{} = PS2_PADDB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PSUBB: - return fmt::format("ctx->r{} = PS2_PSUBB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PCGTB: - return fmt::format("ctx->r{} = PS2_PCGTB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCGTB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PEXTLW: - return fmt::format("ctx->r{} = PS2_PEXTLW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTLW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PPACW: - return fmt::format("ctx->r{} = PS2_PPACW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PPACW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PEXTLH: - return fmt::format("ctx->r{} = PS2_PEXTLH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTLH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PPACH: - return fmt::format("ctx->r{} = PS2_PPACH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PPACH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PEXTLB: - return fmt::format("ctx->r{} = PS2_PEXTLB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTLB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI0_PPACB: @@ -779,66 +779,66 @@ namespace ps2recomp switch (inst.sa) { case MMI1_PADDUW: - return fmt::format("ctx->r{} = PS2_PADDW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PSUBUW: - return fmt::format("ctx->r{} = PS2_PSUBW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PEXTUW: - return fmt::format("ctx->r{} = PS2_PEXTUW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTUW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PADDUH: - return fmt::format("ctx->r{} = PS2_PADDH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PSUBUH: - return fmt::format("ctx->r{} = PS2_PSUBH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PEXTUH: - return fmt::format("ctx->r{} = PS2_PEXTUH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTUH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PABSW: - return fmt::format("ctx->r{} = PS2_PABSW(ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PABSW(ctx->r[{}]);", inst.rd, inst.rs); case MMI1_PABSH: - return fmt::format("ctx->r{} = PS2_PABSH(ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PABSH(ctx->r[{}]);", inst.rd, inst.rs); case MMI1_PCEQW: - return fmt::format("ctx->r{} = PS2_PCEQW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCEQW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PCEQH: - return fmt::format("ctx->r{} = PS2_PCEQH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCEQH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PCEQB: - return fmt::format("ctx->r{} = PS2_PCEQB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PCEQB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PMINW: - return fmt::format("ctx->r{} = PS2_PMINW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PMINW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PMINH: - return fmt::format("ctx->r{} = PS2_PMINH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PMINH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PADDUB: - return fmt::format("ctx->r{} = PS2_PADDB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PADDB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PSUBUB: - return fmt::format("ctx->r{} = PS2_PSUBB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSUBB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_PEXTUB: - return fmt::format("ctx->r{} = PS2_PEXTUB(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PEXTUB(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI1_QFSRV: @@ -854,27 +854,27 @@ namespace ps2recomp switch (inst.sa) { case MMI2_PMADDW: - return fmt::format("ctx->r{} = PS2_PMADDW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PMADDW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PSLLVW: - return fmt::format("ctx->r{} = PS2_PSLLVW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSLLVW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PSRLVW: - return fmt::format("ctx->r{} = PS2_PSRLVW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSRLVW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PINTH: - return fmt::format("ctx->r{} = PS2_PINTH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PINTH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PAND: - return fmt::format("ctx->r{} = PS2_PAND(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PAND(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PXOR: - return fmt::format("ctx->r{} = PS2_PXOR(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PXOR(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI2_PMULTW: @@ -920,22 +920,22 @@ namespace ps2recomp switch (inst.sa) { case MMI3_POR: - return fmt::format("ctx->r{} = PS2_POR(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_POR(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI3_PNOR: - return fmt::format("ctx->r{} = PS2_PNOR(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PNOR(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI3_PMADDUW: return fmt::format("// PS2_PMADDUW - Packed Multiply-Add Unsigned Word"); case MMI3_PSRAVW: - return fmt::format("ctx->r{} = PS2_PSRAVW(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PSRAVW(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI3_PINTEH: - return fmt::format("ctx->r{} = PS2_PINTEH(ctx->r{}, ctx->r{});", + return fmt::format("ctx->r[{}] = PS2_PINTEH(ctx->r[{}], ctx->r[{}]);", inst.rd, inst.rs, inst.rt); case MMI3_PMULTUW: @@ -966,23 +966,23 @@ namespace ps2recomp switch (inst.pmfhlVariation) { case PMFHL_LW: - return fmt::format("ctx->r{} = PS2_PMFHL_LW(ctx->hi, ctx->lo);", + return fmt::format("ctx->r[{}] = PS2_PMFHL_LW(ctx->hi, ctx->lo);", inst.rd); case PMFHL_UW: - return fmt::format("ctx->r{} = PS2_PMFHL_UW(ctx->hi, ctx->lo);", + return fmt::format("ctx->r[{}] = PS2_PMFHL_UW(ctx->hi, ctx->lo);", inst.rd); case PMFHL_SLW: - return fmt::format("ctx->r{} = PS2_PMFHL_SLW(ctx->hi, ctx->lo);", + return fmt::format("ctx->r[{}] = PS2_PMFHL_SLW(ctx->hi, ctx->lo);", inst.rd); case PMFHL_LH: - return fmt::format("ctx->r{} = PS2_PMFHL_LH(ctx->hi, ctx->lo);", + return fmt::format("ctx->r[{}] = PS2_PMFHL_LH(ctx->hi, ctx->lo);", inst.rd); case PMFHL_SH: - return fmt::format("ctx->r{} = PS2_PMFHL_SH(ctx->hi, ctx->lo);", + return fmt::format("ctx->r[{}] = PS2_PMFHL_SH(ctx->hi, ctx->lo);", inst.rd); default: @@ -1002,13 +1002,13 @@ namespace ps2recomp switch (rs) { case COP2_QMFC2: - return fmt::format("ctx->r{} = (__m128i)ctx->vu0_vf{};", + return fmt::format("ctx->r[{}] = (__m128i)ctx->vu0_vf[{}];", inst.rt, inst.rd); case COP2_CFC2: if (inst.rd == 0) { - return fmt::format("ctx->r{} = ctx->vu0_status;", inst.rt); + return fmt::format("ctx->r[{}] = ctx->vu0_status;", inst.rt); } else { @@ -1016,13 +1016,13 @@ namespace ps2recomp } case COP2_QMTC2: - return fmt::format("ctx->vu0_vf{} = (__m128)ctx->r{};", + return fmt::format("ctx->vu0_vf[{}] = (__m128)ctx->r[{}];", inst.rd, inst.rt); case COP2_CTC2: if (inst.rd == 0) { - return fmt::format("ctx->vu0_status = ctx->r{} & 0xFFFF;", inst.rt); + return fmt::format("ctx->vu0_status = ctx->r[{}] & 0xFFFF;", inst.rt); } else { @@ -1037,23 +1037,23 @@ namespace ps2recomp switch (inst.function) { case VU0_VADD: - return fmt::format("ctx->vu0_vf{} = PS2_VADD(ctx->vu0_vf{}, ctx->vu0_vf{});", + return fmt::format("ctx->vu0_vf[{}] = PS2_VADD(ctx->vu0_vf[{}], ctx->vu0_vf[{}]);", inst.rd, inst.rs, inst.rt); case VU0_VSUB: - return fmt::format("ctx->vu0_vf{} = PS2_VSUB(ctx->vu0_vf{}, ctx->vu0_vf{});", + return fmt::format("ctx->vu0_vf[{}] = PS2_VSUB(ctx->vu0_vf[{}], ctx->vu0_vf[{}]);", inst.rd, inst.rs, inst.rt); case VU0_VMUL: - return fmt::format("ctx->vu0_vf{} = PS2_VMUL(ctx->vu0_vf{}, ctx->vu0_vf{});", + return fmt::format("ctx->vu0_vf[{}] = PS2_VMUL(ctx->vu0_vf[{}], ctx->vu0_vf[{}]);", inst.rd, inst.rs, inst.rt); case VU0_VDIV: - return fmt::format("ctx->vu0_vf{} = PS2_VDIV(ctx->vu0_vf{}, ctx->vu0_vf{});", + return fmt::format("ctx->vu0_vf[{}] = PS2_VDIV(ctx->vu0_vf[{}], ctx->vu0_vf[{}]);", inst.rd, inst.rs, inst.rt); case VU0_VMULQ: - return fmt::format("ctx->vu0_vf{} = PS2_VMULQ(ctx->vu0_vf{}, ctx->vu0_q);", + return fmt::format("ctx->vu0_vf[{}] = PS2_VMULQ(ctx->vu0_vf[{}], ctx->vu0_q);", inst.rd, inst.rs); default: @@ -1077,12 +1077,12 @@ namespace ps2recomp // For MFC1/MTC1/CFC1/CTC1, the GPR is in rt and the FPR is in rd(fs) if (rs == COP1_MF) { - return fmt::format("ctx->r{} = *(uint32_t*)&ctx->f{};", + return fmt::format("ctx->r[{}] = *(uint32_t*)&ctx->f[{}];", ft, fs); } else if (rs == COP1_MT) { - return fmt::format("*(uint32_t*)&ctx->f{} = ctx->r{};", + return fmt::format("*(uint32_t*)&ctx->f[{}] = ctx->r[{}];", fs, ft); } else if (rs == COP1_CF) @@ -1090,15 +1090,15 @@ namespace ps2recomp // CFC1 - Move Control From FPU if (fs == 31) // FCR31 contains status/control { - return fmt::format("ctx->r{} = ctx->fcr31;", ft); + return fmt::format("ctx->r[{}] = ctx->fcr31;", ft); } else if (fs == 0) // FCR0 is the FPU implementation register { - return fmt::format("ctx->r{} = 0x00000000; // Emulated FPU implementation", ft); + return fmt::format("ctx->r[{}] = 0x00000000; // Emulated FPU implementation", ft); } else { - return fmt::format("ctx->r{} = 0; // Unimplemented FCR{}", ft, fs); + return fmt::format("ctx->r[{}] = 0; // Unimplemented FCR{}", ft, fs); } } else if (rs == COP1_CT) @@ -1106,7 +1106,7 @@ namespace ps2recomp // CTC1 - Move Control To FPU if (fs == 31) // FCR31 contains status/control { - return fmt::format("ctx->fcr31 = ctx->r{} & 0x0183FFFF;", ft); // Apply bit mask for valid bits + return fmt::format("ctx->fcr31 = ctx->r[{}] & 0x0183FFFF;", ft); // Apply bit mask for valid bits } else { @@ -1124,80 +1124,78 @@ namespace ps2recomp switch (function) { case 0x00: // ADD.S - return fmt::format("ctx->f{} = FPU_ADD_S(ctx->f{}, ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_ADD_S(ctx->f[{}], ctx->f[{}]);", fd, fs, ft); case 0x01: // SUB.S - return fmt::format("ctx->f{} = FPU_SUB_S(ctx->f{}, ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_SUB_S(ctx->f[{}], ctx->f[{}]);", fd, fs, ft); case 0x02: // MUL.S - return fmt::format("ctx->f{} = FPU_MUL_S(ctx->f{}, ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_MUL_S(ctx->f[{}], ctx->f[{}]);", fd, fs, ft); case 0x03: // DIV.S - return fmt::format("ctx->f{} = FPU_DIV_S(ctx->f{}, ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_DIV_S(ctx->f[{}], ctx->f[{}]);", fd, fs, ft); case 0x04: // SQRT.S - return fmt::format("ctx->f{} = FPU_SQRT_S(ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_SQRT_S(ctx->f[{}]);", fd, fs); case 0x05: // ABS.S - return fmt::format("ctx->f{} = FPU_ABS_S(ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_ABS_S(ctx->f[{}]);", fd, fs); case 0x06: // MOV.S - return fmt::format("ctx->f{} = FPU_MOV_S(ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_MOV_S(ctx->f[{}]);", fd, fs); case 0x07: // NEG.S - return fmt::format("ctx->f{} = FPU_NEG_S(ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_NEG_S(ctx->f[{}]);", fd, fs); case 0x08: // ROUND.L.S - return fmt::format("*(int64_t*)&ctx->f{} = FPU_ROUND_L_S(ctx->f{});", + return fmt::format("*(int64_t*)&ctx->f[{}] = FPU_ROUND_L_S(ctx->f[{}]);", fd, fs); case 0x09: // TRUNC.L.S - return fmt::format("*(int64_t*)&ctx->f{} = FPU_TRUNC_L_S(ctx->f{});", + return fmt::format("*(int64_t*)&ctx->f[{}] = FPU_TRUNC_L_S(ctx->f[{}]);", fd, fs); case 0x0A: // CEIL.L.S - return fmt::format("*(int64_t*)&ctx->f{} = FPU_CEIL_L_S(ctx->f{});", + return fmt::format("*(int64_t*)&ctx->f[{}] = FPU_CEIL_L_S(ctx->f[{}]);", fd, fs); case 0x0B: // FLOOR.L.S - return fmt::format("*(int64_t*)&ctx->f{} = FPU_FLOOR_L_S(ctx->f{});", + return fmt::format("*(int64_t*)&ctx->f[{}] = FPU_FLOOR_L_S(ctx->f[{}]);", fd, fs); case 0x0C: // ROUND.W.S - return fmt::format("*(int32_t*)&ctx->f{} = FPU_ROUND_W_S(ctx->f{});", + return fmt::format("*(int32_t*)&ctx->f[{}] = FPU_ROUND_W_S(ctx->f[{}]);", fd, fs); case 0x0D: // TRUNC.W.S - return fmt::format("*(int32_t*)&ctx->f{} = FPU_TRUNC_W_S(ctx->f{});", + return fmt::format("*(int32_t*)&ctx->f[{}] = FPU_TRUNC_W_S(ctx->f[{}]);", fd, fs); case 0x0E: // CEIL.W.S - return fmt::format("*(int32_t*)&ctx->f{} = FPU_CEIL_W_S(ctx->f{});", + return fmt::format("*(int32_t*)&ctx->f[{}] = FPU_CEIL_W_S(ctx->f[{}]);", fd, fs); case 0x0F: // FLOOR.W.S - return fmt::format("*(int32_t*)&ctx->f{} = FPU_FLOOR_W_S(ctx->f{});", + return fmt::format("*(int32_t*)&ctx->f[{}] = FPU_FLOOR_W_S(ctx->f[{}]);", fd, fs); - // Continuing the COP1_S switch case from the previous code: - case 0x21: // CVT.D.S - Convert Single to Double (not commonly used on PS2) return fmt::format("// CVT.D.S not implemented (PS2 rarely uses double precision)"); case 0x24: // CVT.W.S - Convert Single to Word - return fmt::format("*(int32_t*)&ctx->f{} = FPU_CVT_W_S(ctx->f{});", + return fmt::format("*(int32_t*)&ctx->f[{}] = FPU_CVT_W_S(ctx->f[{}]);", fd, fs); case 0x25: // CVT.L.S - Convert Single to Long - return fmt::format("*(int64_t*)&ctx->f{} = FPU_CVT_L_S(ctx->f{});", + return fmt::format("*(int64_t*)&ctx->f[{}] = FPU_CVT_L_S(ctx->f[{}]);", fd, fs); case 0x30: // C.F.S - Compare False @@ -1205,31 +1203,31 @@ namespace ps2recomp fs, ft); case 0x31: // C.UN.S - Compare Unordered - return fmt::format("ctx->fcr31 = (FPU_C_UN_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_UN_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x32: // C.EQ.S - Compare Equal - return fmt::format("ctx->fcr31 = (FPU_C_EQ_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_EQ_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x33: // C.UEQ.S - Compare Unordered or Equal - return fmt::format("ctx->fcr31 = (FPU_C_UEQ_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_UEQ_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x34: // C.OLT.S - Compare Ordered Less Than - return fmt::format("ctx->fcr31 = (FPU_C_OLT_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_OLT_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x35: // C.ULT.S - Compare Unordered or Less Than - return fmt::format("ctx->fcr31 = (FPU_C_ULT_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_ULT_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x36: // C.OLE.S - Compare Ordered Less Than or Equal - return fmt::format("ctx->fcr31 = (FPU_C_OLE_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_OLE_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); case 0x37: // C.ULE.S - Compare Unordered or Less Than or Equal - return fmt::format("ctx->fcr31 = (FPU_C_ULE_S(ctx->f{}, ctx->f{})) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", + return fmt::format("ctx->fcr31 = (FPU_C_ULE_S(ctx->f[{}], ctx->f[{}])) ? (ctx->fcr31 | 0x800000) : (ctx->fcr31 & ~0x800000);", fs, ft); default: @@ -1242,7 +1240,7 @@ namespace ps2recomp switch (function) { case 0x20: // CVT.S.W - Convert Word to Single - return fmt::format("ctx->f{} = FPU_CVT_S_W(*(int32_t*)&ctx->f{});", + return fmt::format("ctx->f[{}] = FPU_CVT_S_W(*(int32_t*)&ctx->f[{}]);", fd, fs); default: @@ -1265,16 +1263,16 @@ namespace ps2recomp switch (rd) { case 12: // Status register - return fmt::format("ctx->r{} = ctx->cop0_status;", rt); + return fmt::format("ctx->r[{}] = ctx->cop0_status;", rt); case 13: // Cause register - return fmt::format("ctx->r{} = ctx->cop0_cause;", rt); + return fmt::format("ctx->r[{}] = ctx->cop0_cause;", rt); case 14: // EPC register - return fmt::format("ctx->r{} = ctx->cop0_epc;", rt); + return fmt::format("ctx->r[{}] = ctx->cop0_epc;", rt); default: - return fmt::format("ctx->r{} = 0; // Unimplemented COP0 register {}", rt, rd); + return fmt::format("ctx->r[{}] = 0; // Unimplemented COP0 register {}", rt, rd); } } else if (rs == COP0_MT) @@ -1283,13 +1281,13 @@ namespace ps2recomp switch (rd) { case 12: // Status register - return fmt::format("ctx->cop0_status = ctx->r{};", rt); + return fmt::format("ctx->cop0_status = ctx->r[{}];", rt); case 13: // Cause register - return fmt::format("ctx->cop0_cause = ctx->r{};", rt); + return fmt::format("ctx->cop0_cause = ctx->r[{}];", rt); case 14: // EPC register - return fmt::format("ctx->cop0_epc = ctx->r{};", rt); + return fmt::format("ctx->cop0_epc = ctx->r[{}];", rt); default: return fmt::format("// MTC0 to register {} ignored", rd); @@ -1338,7 +1336,7 @@ namespace ps2recomp uint32_t indexReg = inst.rs; - ss << "switch (ctx->r" << indexReg << ") {\n"; + ss << "switch (ctx->r[" << indexReg << "]) {\n"; for (const auto &entry : entries) {