mirror of
https://github.com/dolphin-emu/dolphin.git
synced 2025-02-12 12:40:36 +00:00
UnitTests: Avoid ppcState global.
This commit is contained in:
parent
2d1f661118
commit
62de9c593b
@ -74,20 +74,20 @@ private:
|
|||||||
std::string m_profile_path;
|
std::string m_profile_path;
|
||||||
};
|
};
|
||||||
|
|
||||||
static void AdvanceAndCheck(u32 idx, int downcount, int expected_lateness = 0,
|
static void AdvanceAndCheck(Core::System& system, u32 idx, int downcount, int expected_lateness = 0,
|
||||||
int cpu_downcount = 0)
|
int cpu_downcount = 0)
|
||||||
{
|
{
|
||||||
s_callbacks_ran_flags = 0;
|
s_callbacks_ran_flags = 0;
|
||||||
s_expected_callback = CB_IDS[idx];
|
s_expected_callback = CB_IDS[idx];
|
||||||
s_lateness = expected_lateness;
|
s_lateness = expected_lateness;
|
||||||
|
|
||||||
PowerPC::ppcState.downcount = cpu_downcount; // Pretend we executed X cycles of instructions.
|
auto& ppc_state = system.GetPPCState();
|
||||||
auto& system = Core::System::GetInstance();
|
ppc_state.downcount = cpu_downcount; // Pretend we executed X cycles of instructions.
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
core_timing.Advance();
|
core_timing.Advance();
|
||||||
|
|
||||||
EXPECT_EQ(decltype(s_callbacks_ran_flags)().set(idx), s_callbacks_ran_flags);
|
EXPECT_EQ(decltype(s_callbacks_ran_flags)().set(idx), s_callbacks_ran_flags);
|
||||||
EXPECT_EQ(downcount, PowerPC::ppcState.downcount);
|
EXPECT_EQ(downcount, ppc_state.downcount);
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST(CoreTiming, BasicOrder)
|
TEST(CoreTiming, BasicOrder)
|
||||||
@ -97,6 +97,7 @@ TEST(CoreTiming, BasicOrder)
|
|||||||
|
|
||||||
auto& system = Core::System::GetInstance();
|
auto& system = Core::System::GetInstance();
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
||||||
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
||||||
@ -109,21 +110,21 @@ TEST(CoreTiming, BasicOrder)
|
|||||||
|
|
||||||
// D -> B -> C -> A -> E
|
// D -> B -> C -> A -> E
|
||||||
core_timing.ScheduleEvent(1000, cb_a, CB_IDS[0]);
|
core_timing.ScheduleEvent(1000, cb_a, CB_IDS[0]);
|
||||||
EXPECT_EQ(1000, PowerPC::ppcState.downcount);
|
EXPECT_EQ(1000, ppc_state.downcount);
|
||||||
core_timing.ScheduleEvent(500, cb_b, CB_IDS[1]);
|
core_timing.ScheduleEvent(500, cb_b, CB_IDS[1]);
|
||||||
EXPECT_EQ(500, PowerPC::ppcState.downcount);
|
EXPECT_EQ(500, ppc_state.downcount);
|
||||||
core_timing.ScheduleEvent(800, cb_c, CB_IDS[2]);
|
core_timing.ScheduleEvent(800, cb_c, CB_IDS[2]);
|
||||||
EXPECT_EQ(500, PowerPC::ppcState.downcount);
|
EXPECT_EQ(500, ppc_state.downcount);
|
||||||
core_timing.ScheduleEvent(100, cb_d, CB_IDS[3]);
|
core_timing.ScheduleEvent(100, cb_d, CB_IDS[3]);
|
||||||
EXPECT_EQ(100, PowerPC::ppcState.downcount);
|
EXPECT_EQ(100, ppc_state.downcount);
|
||||||
core_timing.ScheduleEvent(1200, cb_e, CB_IDS[4]);
|
core_timing.ScheduleEvent(1200, cb_e, CB_IDS[4]);
|
||||||
EXPECT_EQ(100, PowerPC::ppcState.downcount);
|
EXPECT_EQ(100, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(3, 400);
|
AdvanceAndCheck(system, 3, 400);
|
||||||
AdvanceAndCheck(1, 300);
|
AdvanceAndCheck(system, 1, 300);
|
||||||
AdvanceAndCheck(2, 200);
|
AdvanceAndCheck(system, 2, 200);
|
||||||
AdvanceAndCheck(0, 200);
|
AdvanceAndCheck(system, 0, 200);
|
||||||
AdvanceAndCheck(4, MAX_SLICE_LENGTH);
|
AdvanceAndCheck(system, 4, MAX_SLICE_LENGTH);
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace SharedSlotTest
|
namespace SharedSlotTest
|
||||||
@ -151,6 +152,7 @@ TEST(CoreTiming, SharedSlot)
|
|||||||
|
|
||||||
auto& system = Core::System::GetInstance();
|
auto& system = Core::System::GetInstance();
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", FifoCallback<0>);
|
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", FifoCallback<0>);
|
||||||
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", FifoCallback<1>);
|
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", FifoCallback<1>);
|
||||||
@ -166,14 +168,14 @@ TEST(CoreTiming, SharedSlot)
|
|||||||
|
|
||||||
// Enter slice 0
|
// Enter slice 0
|
||||||
core_timing.Advance();
|
core_timing.Advance();
|
||||||
EXPECT_EQ(1000, PowerPC::ppcState.downcount);
|
EXPECT_EQ(1000, ppc_state.downcount);
|
||||||
|
|
||||||
s_callbacks_ran_flags = 0;
|
s_callbacks_ran_flags = 0;
|
||||||
s_counter = 0;
|
s_counter = 0;
|
||||||
s_lateness = 0;
|
s_lateness = 0;
|
||||||
PowerPC::ppcState.downcount = 0;
|
ppc_state.downcount = 0;
|
||||||
core_timing.Advance();
|
core_timing.Advance();
|
||||||
EXPECT_EQ(MAX_SLICE_LENGTH, PowerPC::ppcState.downcount);
|
EXPECT_EQ(MAX_SLICE_LENGTH, ppc_state.downcount);
|
||||||
EXPECT_EQ(0x1FULL, s_callbacks_ran_flags.to_ullong());
|
EXPECT_EQ(0x1FULL, s_callbacks_ran_flags.to_ullong());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -194,8 +196,8 @@ TEST(CoreTiming, PredictableLateness)
|
|||||||
core_timing.ScheduleEvent(100, cb_a, CB_IDS[0]);
|
core_timing.ScheduleEvent(100, cb_a, CB_IDS[0]);
|
||||||
core_timing.ScheduleEvent(200, cb_b, CB_IDS[1]);
|
core_timing.ScheduleEvent(200, cb_b, CB_IDS[1]);
|
||||||
|
|
||||||
AdvanceAndCheck(0, 90, 10, -10); // (100 - 10)
|
AdvanceAndCheck(system, 0, 90, 10, -10); // (100 - 10)
|
||||||
AdvanceAndCheck(1, MAX_SLICE_LENGTH, 50, -50);
|
AdvanceAndCheck(system, 1, MAX_SLICE_LENGTH, 50, -50);
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace ChainSchedulingTest
|
namespace ChainSchedulingTest
|
||||||
@ -225,6 +227,7 @@ TEST(CoreTiming, ChainScheduling)
|
|||||||
|
|
||||||
auto& system = Core::System::GetInstance();
|
auto& system = Core::System::GetInstance();
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
||||||
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
||||||
@ -239,24 +242,24 @@ TEST(CoreTiming, ChainScheduling)
|
|||||||
core_timing.ScheduleEvent(1000, cb_b, CB_IDS[1]);
|
core_timing.ScheduleEvent(1000, cb_b, CB_IDS[1]);
|
||||||
core_timing.ScheduleEvent(2200, cb_c, CB_IDS[2]);
|
core_timing.ScheduleEvent(2200, cb_c, CB_IDS[2]);
|
||||||
core_timing.ScheduleEvent(1000, cb_rs, reinterpret_cast<u64>(cb_rs));
|
core_timing.ScheduleEvent(1000, cb_rs, reinterpret_cast<u64>(cb_rs));
|
||||||
EXPECT_EQ(800, PowerPC::ppcState.downcount);
|
EXPECT_EQ(800, ppc_state.downcount);
|
||||||
|
|
||||||
s_reschedules = 3;
|
s_reschedules = 3;
|
||||||
AdvanceAndCheck(0, 200); // cb_a
|
AdvanceAndCheck(system, 0, 200); // cb_a
|
||||||
AdvanceAndCheck(1, 1000); // cb_b, cb_rs
|
AdvanceAndCheck(system, 1, 1000); // cb_b, cb_rs
|
||||||
EXPECT_EQ(2, s_reschedules);
|
EXPECT_EQ(2, s_reschedules);
|
||||||
|
|
||||||
PowerPC::ppcState.downcount = 0;
|
ppc_state.downcount = 0;
|
||||||
core_timing.Advance(); // cb_rs
|
core_timing.Advance(); // cb_rs
|
||||||
EXPECT_EQ(1, s_reschedules);
|
EXPECT_EQ(1, s_reschedules);
|
||||||
EXPECT_EQ(200, PowerPC::ppcState.downcount);
|
EXPECT_EQ(200, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(2, 800); // cb_c
|
AdvanceAndCheck(system, 2, 800); // cb_c
|
||||||
|
|
||||||
PowerPC::ppcState.downcount = 0;
|
ppc_state.downcount = 0;
|
||||||
core_timing.Advance(); // cb_rs
|
core_timing.Advance(); // cb_rs
|
||||||
EXPECT_EQ(0, s_reschedules);
|
EXPECT_EQ(0, s_reschedules);
|
||||||
EXPECT_EQ(MAX_SLICE_LENGTH, PowerPC::ppcState.downcount);
|
EXPECT_EQ(MAX_SLICE_LENGTH, ppc_state.downcount);
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace ScheduleIntoPastTest
|
namespace ScheduleIntoPastTest
|
||||||
@ -284,6 +287,7 @@ TEST(CoreTiming, ScheduleIntoPast)
|
|||||||
|
|
||||||
auto& system = Core::System::GetInstance();
|
auto& system = Core::System::GetInstance();
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
s_cb_next = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
s_cb_next = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
||||||
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
||||||
@ -293,9 +297,9 @@ TEST(CoreTiming, ScheduleIntoPast)
|
|||||||
core_timing.Advance();
|
core_timing.Advance();
|
||||||
|
|
||||||
core_timing.ScheduleEvent(1000, cb_chain, CB_IDS[0] + 1);
|
core_timing.ScheduleEvent(1000, cb_chain, CB_IDS[0] + 1);
|
||||||
EXPECT_EQ(1000, PowerPC::ppcState.downcount);
|
EXPECT_EQ(1000, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(0, MAX_SLICE_LENGTH, 1000); // Run cb_chain into late cb_a
|
AdvanceAndCheck(system, 0, MAX_SLICE_LENGTH, 1000); // Run cb_chain into late cb_a
|
||||||
|
|
||||||
// Schedule late from wrong thread
|
// Schedule late from wrong thread
|
||||||
// The problem with scheduling CPU events from outside the CPU Thread is that g_global_timer
|
// The problem with scheduling CPU events from outside the CPU Thread is that g_global_timer
|
||||||
@ -309,14 +313,14 @@ TEST(CoreTiming, ScheduleIntoPast)
|
|||||||
core_timing.ScheduleEvent(0, cb_b, CB_IDS[1], CoreTiming::FromThread::NON_CPU);
|
core_timing.ScheduleEvent(0, cb_b, CB_IDS[1], CoreTiming::FromThread::NON_CPU);
|
||||||
core_timing_globals.global_timer += 1000;
|
core_timing_globals.global_timer += 1000;
|
||||||
Core::DeclareAsCPUThread();
|
Core::DeclareAsCPUThread();
|
||||||
AdvanceAndCheck(1, MAX_SLICE_LENGTH, MAX_SLICE_LENGTH + 1000);
|
AdvanceAndCheck(system, 1, MAX_SLICE_LENGTH, MAX_SLICE_LENGTH + 1000);
|
||||||
|
|
||||||
// Schedule directly into the past from the CPU.
|
// Schedule directly into the past from the CPU.
|
||||||
// This shouldn't happen in practice, but it's best if we don't mess up the slice length and
|
// This shouldn't happen in practice, but it's best if we don't mess up the slice length and
|
||||||
// downcount if we do.
|
// downcount if we do.
|
||||||
core_timing.ScheduleEvent(-1000, s_cb_next, CB_IDS[0]);
|
core_timing.ScheduleEvent(-1000, s_cb_next, CB_IDS[0]);
|
||||||
EXPECT_EQ(0, PowerPC::ppcState.downcount);
|
EXPECT_EQ(0, ppc_state.downcount);
|
||||||
AdvanceAndCheck(0, MAX_SLICE_LENGTH, 1000);
|
AdvanceAndCheck(system, 0, MAX_SLICE_LENGTH, 1000);
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST(CoreTiming, Overclocking)
|
TEST(CoreTiming, Overclocking)
|
||||||
@ -326,6 +330,7 @@ TEST(CoreTiming, Overclocking)
|
|||||||
|
|
||||||
auto& system = Core::System::GetInstance();
|
auto& system = Core::System::GetInstance();
|
||||||
auto& core_timing = system.GetCoreTiming();
|
auto& core_timing = system.GetCoreTiming();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
CoreTiming::EventType* cb_a = core_timing.RegisterEvent("callbackA", CallbackTemplate<0>);
|
||||||
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
CoreTiming::EventType* cb_b = core_timing.RegisterEvent("callbackB", CallbackTemplate<1>);
|
||||||
@ -346,13 +351,13 @@ TEST(CoreTiming, Overclocking)
|
|||||||
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
||||||
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
||||||
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
||||||
EXPECT_EQ(200, PowerPC::ppcState.downcount);
|
EXPECT_EQ(200, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(0, 200); // (200 - 100) * 2
|
AdvanceAndCheck(system, 0, 200); // (200 - 100) * 2
|
||||||
AdvanceAndCheck(1, 400); // (400 - 200) * 2
|
AdvanceAndCheck(system, 1, 400); // (400 - 200) * 2
|
||||||
AdvanceAndCheck(2, 800); // (800 - 400) * 2
|
AdvanceAndCheck(system, 2, 800); // (800 - 400) * 2
|
||||||
AdvanceAndCheck(3, 1600); // (1600 - 800) * 2
|
AdvanceAndCheck(system, 3, 1600); // (1600 - 800) * 2
|
||||||
AdvanceAndCheck(4, MAX_SLICE_LENGTH * 2);
|
AdvanceAndCheck(system, 4, MAX_SLICE_LENGTH * 2);
|
||||||
|
|
||||||
// Underclock
|
// Underclock
|
||||||
Config::SetCurrent(Config::MAIN_OVERCLOCK, 0.5f);
|
Config::SetCurrent(Config::MAIN_OVERCLOCK, 0.5f);
|
||||||
@ -363,13 +368,13 @@ TEST(CoreTiming, Overclocking)
|
|||||||
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
||||||
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
||||||
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
||||||
EXPECT_EQ(50, PowerPC::ppcState.downcount);
|
EXPECT_EQ(50, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(0, 50); // (200 - 100) / 2
|
AdvanceAndCheck(system, 0, 50); // (200 - 100) / 2
|
||||||
AdvanceAndCheck(1, 100); // (400 - 200) / 2
|
AdvanceAndCheck(system, 1, 100); // (400 - 200) / 2
|
||||||
AdvanceAndCheck(2, 200); // (800 - 400) / 2
|
AdvanceAndCheck(system, 2, 200); // (800 - 400) / 2
|
||||||
AdvanceAndCheck(3, 400); // (1600 - 800) / 2
|
AdvanceAndCheck(system, 3, 400); // (1600 - 800) / 2
|
||||||
AdvanceAndCheck(4, MAX_SLICE_LENGTH / 2);
|
AdvanceAndCheck(system, 4, MAX_SLICE_LENGTH / 2);
|
||||||
|
|
||||||
// Try switching the clock mid-emulation
|
// Try switching the clock mid-emulation
|
||||||
Config::SetCurrent(Config::MAIN_OVERCLOCK, 1.0f);
|
Config::SetCurrent(Config::MAIN_OVERCLOCK, 1.0f);
|
||||||
@ -380,14 +385,14 @@ TEST(CoreTiming, Overclocking)
|
|||||||
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
core_timing.ScheduleEvent(400, cb_c, CB_IDS[2]);
|
||||||
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
core_timing.ScheduleEvent(800, cb_d, CB_IDS[3]);
|
||||||
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
core_timing.ScheduleEvent(1600, cb_e, CB_IDS[4]);
|
||||||
EXPECT_EQ(100, PowerPC::ppcState.downcount);
|
EXPECT_EQ(100, ppc_state.downcount);
|
||||||
|
|
||||||
AdvanceAndCheck(0, 100); // (200 - 100)
|
AdvanceAndCheck(system, 0, 100); // (200 - 100)
|
||||||
Config::SetCurrent(Config::MAIN_OVERCLOCK, 2.0f);
|
Config::SetCurrent(Config::MAIN_OVERCLOCK, 2.0f);
|
||||||
AdvanceAndCheck(1, 400); // (400 - 200) * 2
|
AdvanceAndCheck(system, 1, 400); // (400 - 200) * 2
|
||||||
AdvanceAndCheck(2, 800); // (800 - 400) * 2
|
AdvanceAndCheck(system, 2, 800); // (800 - 400) * 2
|
||||||
Config::SetCurrent(Config::MAIN_OVERCLOCK, 0.1f);
|
Config::SetCurrent(Config::MAIN_OVERCLOCK, 0.1f);
|
||||||
AdvanceAndCheck(3, 80); // (1600 - 800) / 10
|
AdvanceAndCheck(system, 3, 80); // (1600 - 800) / 10
|
||||||
Config::SetCurrent(Config::MAIN_OVERCLOCK, 1.0f);
|
Config::SetCurrent(Config::MAIN_OVERCLOCK, 1.0f);
|
||||||
AdvanceAndCheck(4, MAX_SLICE_LENGTH);
|
AdvanceAndCheck(system, 4, MAX_SLICE_LENGTH);
|
||||||
}
|
}
|
||||||
|
@ -34,10 +34,12 @@ public:
|
|||||||
const u8* raw_fprf_double = GetCodePtr();
|
const u8* raw_fprf_double = GetCodePtr();
|
||||||
GenerateFPRF(false);
|
GenerateFPRF(false);
|
||||||
|
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
|
||||||
fprf_single = Common::BitCast<void (*)(u32)>(GetCodePtr());
|
fprf_single = Common::BitCast<void (*)(u32)>(GetCodePtr());
|
||||||
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
||||||
MOV(ARM64Reg::X14, PPC_REG);
|
MOV(ARM64Reg::X14, PPC_REG);
|
||||||
MOVP2R(PPC_REG, &PowerPC::ppcState);
|
MOVP2R(PPC_REG, &ppc_state);
|
||||||
BL(raw_fprf_single);
|
BL(raw_fprf_single);
|
||||||
MOV(ARM64Reg::X30, ARM64Reg::X15);
|
MOV(ARM64Reg::X30, ARM64Reg::X15);
|
||||||
MOV(PPC_REG, ARM64Reg::X14);
|
MOV(PPC_REG, ARM64Reg::X14);
|
||||||
@ -46,7 +48,7 @@ public:
|
|||||||
fprf_double = Common::BitCast<void (*)(u64)>(GetCodePtr());
|
fprf_double = Common::BitCast<void (*)(u64)>(GetCodePtr());
|
||||||
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
||||||
MOV(ARM64Reg::X14, PPC_REG);
|
MOV(ARM64Reg::X14, PPC_REG);
|
||||||
MOVP2R(PPC_REG, &PowerPC::ppcState);
|
MOVP2R(PPC_REG, &ppc_state);
|
||||||
BL(raw_fprf_double);
|
BL(raw_fprf_double);
|
||||||
MOV(ARM64Reg::X30, ARM64Reg::X15);
|
MOV(ARM64Reg::X30, ARM64Reg::X15);
|
||||||
MOV(PPC_REG, ARM64Reg::X14);
|
MOV(PPC_REG, ARM64Reg::X14);
|
||||||
@ -59,29 +61,31 @@ public:
|
|||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
static u32 RunUpdateFPRF(const std::function<void()>& f)
|
static u32 RunUpdateFPRF(PowerPC::PowerPCState& ppc_state, const std::function<void()>& f)
|
||||||
{
|
{
|
||||||
PowerPC::ppcState.fpscr.Hex = 0x12345678;
|
ppc_state.fpscr.Hex = 0x12345678;
|
||||||
f();
|
f();
|
||||||
return PowerPC::ppcState.fpscr.Hex;
|
return ppc_state.fpscr.Hex;
|
||||||
}
|
}
|
||||||
|
|
||||||
TEST(JitArm64, FPRF)
|
TEST(JitArm64, FPRF)
|
||||||
{
|
{
|
||||||
TestFPRF test(Core::System::GetInstance());
|
auto& system = Core::System::GetInstance();
|
||||||
|
auto& ppc_state = system.GetPPCState();
|
||||||
|
TestFPRF test(system);
|
||||||
|
|
||||||
for (const u64 double_input : double_test_values)
|
for (const u64 double_input : double_test_values)
|
||||||
{
|
{
|
||||||
const u32 expected_double = RunUpdateFPRF(
|
const u32 expected_double = RunUpdateFPRF(
|
||||||
[&] { PowerPC::ppcState.UpdateFPRFDouble(Common::BitCast<double>(double_input)); });
|
ppc_state, [&] { ppc_state.UpdateFPRFDouble(Common::BitCast<double>(double_input)); });
|
||||||
const u32 actual_double = RunUpdateFPRF([&] { test.fprf_double(double_input); });
|
const u32 actual_double = RunUpdateFPRF(ppc_state, [&] { test.fprf_double(double_input); });
|
||||||
EXPECT_EQ(expected_double, actual_double);
|
EXPECT_EQ(expected_double, actual_double);
|
||||||
|
|
||||||
const u32 single_input = ConvertToSingle(double_input);
|
const u32 single_input = ConvertToSingle(double_input);
|
||||||
|
|
||||||
const u32 expected_single = RunUpdateFPRF(
|
const u32 expected_single = RunUpdateFPRF(
|
||||||
[&] { PowerPC::ppcState.UpdateFPRFSingle(Common::BitCast<float>(single_input)); });
|
ppc_state, [&] { ppc_state.UpdateFPRFSingle(Common::BitCast<float>(single_input)); });
|
||||||
const u32 actual_single = RunUpdateFPRF([&] { test.fprf_single(single_input); });
|
const u32 actual_single = RunUpdateFPRF(ppc_state, [&] { test.fprf_single(single_input); });
|
||||||
EXPECT_EQ(expected_single, actual_single);
|
EXPECT_EQ(expected_single, actual_single);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -34,7 +34,7 @@ public:
|
|||||||
fres = Common::BitCast<u64 (*)(u64)>(GetCodePtr());
|
fres = Common::BitCast<u64 (*)(u64)>(GetCodePtr());
|
||||||
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
||||||
MOV(ARM64Reg::X14, PPC_REG);
|
MOV(ARM64Reg::X14, PPC_REG);
|
||||||
MOVP2R(PPC_REG, &PowerPC::ppcState);
|
MOVP2R(PPC_REG, &system.GetPPCState());
|
||||||
MOV(ARM64Reg::X1, ARM64Reg::X0);
|
MOV(ARM64Reg::X1, ARM64Reg::X0);
|
||||||
m_float_emit.FMOV(ARM64Reg::D0, ARM64Reg::X0);
|
m_float_emit.FMOV(ARM64Reg::D0, ARM64Reg::X0);
|
||||||
m_float_emit.FRECPE(ARM64Reg::D0, ARM64Reg::D0);
|
m_float_emit.FRECPE(ARM64Reg::D0, ARM64Reg::D0);
|
||||||
|
@ -34,7 +34,7 @@ public:
|
|||||||
frsqrte = Common::BitCast<u64 (*)(u64)>(GetCodePtr());
|
frsqrte = Common::BitCast<u64 (*)(u64)>(GetCodePtr());
|
||||||
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
MOV(ARM64Reg::X15, ARM64Reg::X30);
|
||||||
MOV(ARM64Reg::X14, PPC_REG);
|
MOV(ARM64Reg::X14, PPC_REG);
|
||||||
MOVP2R(PPC_REG, &PowerPC::ppcState);
|
MOVP2R(PPC_REG, &system.GetPPCState());
|
||||||
MOV(ARM64Reg::X1, ARM64Reg::X0);
|
MOV(ARM64Reg::X1, ARM64Reg::X0);
|
||||||
m_float_emit.FMOV(ARM64Reg::D0, ARM64Reg::X0);
|
m_float_emit.FMOV(ARM64Reg::D0, ARM64Reg::X0);
|
||||||
m_float_emit.FRSQRTE(ARM64Reg::D0, ARM64Reg::D0);
|
m_float_emit.FRSQRTE(ARM64Reg::D0, ARM64Reg::D0);
|
||||||
|
Loading…
x
Reference in New Issue
Block a user