diff options
| author | MerryMage <MerryMage@users.noreply.github.com> | 2018-12-21 21:21:02 +0000 |
|---|---|---|
| committer | MerryMage <MerryMage@users.noreply.github.com> | 2018-12-23 18:03:29 +0000 |
| commit | 5236dc31a6deabc85608b41553e5d5aca61c7a67 (patch) | |
| tree | 36dfa10e4f4d5893fd42e739bd47fb24d353b4d1 /Source/Core | |
| parent | 490dffc7915586be9bfdf2f7792f24b040924724 (diff) | |
Jit64: Check downcount at block exit, not block entry
Diffstat (limited to 'Source/Core')
| -rw-r--r-- | Source/Core/Core/PowerPC/Jit64/Jit.cpp | 42 | ||||
| -rw-r--r-- | Source/Core/Core/PowerPC/Jit64Common/BlockCache.cpp | 4 |
2 files changed, 26 insertions, 20 deletions
diff --git a/Source/Core/Core/PowerPC/Jit64/Jit.cpp b/Source/Core/Core/PowerPC/Jit64/Jit.cpp index 2cdad6e54d..b2e893e2c0 100644 --- a/Source/Core/Core/PowerPC/Jit64/Jit.cpp +++ b/Source/Core/Core/PowerPC/Jit64/Jit.cpp @@ -442,21 +442,36 @@ void Jit64::JustWriteExit(u32 destination, bool bl, u32 after) JitBlock::LinkData linkData; linkData.exitAddress = destination; linkData.linkStatus = false; + linkData.call = bl; MOV(32, PPCSTATE(pc), Imm32(destination)); - linkData.exitPtrs = GetWritableCodePtr(); - if (bl) - CALL(asm_routines.dispatcher); - else - JMP(asm_routines.dispatcher, true); - - b->linkData.push_back(linkData); + // Perform downcount flag check, followed by the requested exit if (bl) { + FixupBranch do_timing = J_CC(CC_LE, true); + SwitchToFarCode(); + SetJumpTarget(do_timing); + CALL(asm_routines.do_timing); + FixupBranch after_fixup = J(true); + SwitchToNearCode(); + + linkData.exitPtrs = GetWritableCodePtr(); + CALL(asm_routines.dispatcher_no_check); + + SetJumpTarget(after_fixup); POP(RSCRATCH); JustWriteExit(after, false, 0); } + else + { + J_CC(CC_LE, asm_routines.do_timing); + + linkData.exitPtrs = GetWritableCodePtr(); + JMP(asm_routines.dispatcher_no_check, true); + } + + b->linkData.push_back(linkData); } void Jit64::WriteExitDestInRSCRATCH(bool bl, u32 after) @@ -660,16 +675,7 @@ u8* Jit64::DoJit(u32 em_address, JitBlock* b, u32 nextPC) // TODO: Test if this or AlignCode16 make a difference from GetCodePtr u8* const start = AlignCode4(); b->checkedEntry = start; - - // Downcount flag check. The last block decremented downcounter, and the flag should still be - // available. - FixupBranch skip = J_CC(CC_G); - MOV(32, PPCSTATE(pc), Imm32(js.blockStart)); - JMP(asm_routines.do_timing, true); // downcount hit zero - go do_timing. - SetJumpTarget(skip); - - u8* const normal_entry = GetWritableCodePtr(); - b->normalEntry = normal_entry; + b->normalEntry = start; // Used to get a trace of the last few blocks before a crash, sometimes VERY useful if (ImHereDebug) @@ -955,7 +961,7 @@ u8* Jit64::DoJit(u32 em_address, JitBlock* b, u32 nextPC) LogGeneratedX86(code_block.m_num_instructions, m_code_buffer, start, b); #endif - return normal_entry; + return start; } BitSet8 Jit64::ComputeStaticGQRs(const PPCAnalyst::CodeBlock& cb) const diff --git a/Source/Core/Core/PowerPC/Jit64Common/BlockCache.cpp b/Source/Core/Core/PowerPC/Jit64Common/BlockCache.cpp index 096a46f57d..e857226265 100644 --- a/Source/Core/Core/PowerPC/Jit64Common/BlockCache.cpp +++ b/Source/Core/Core/PowerPC/Jit64Common/BlockCache.cpp @@ -15,9 +15,9 @@ JitBlockCache::JitBlockCache(JitBase& jit) : JitBaseBlockCache{jit} void JitBlockCache::WriteLinkBlock(const JitBlock::LinkData& source, const JitBlock* dest) { u8* location = source.exitPtrs; - const u8* address = dest ? dest->checkedEntry : m_jit.GetAsmRoutines()->dispatcher; + const u8* address = dest ? dest->checkedEntry : m_jit.GetAsmRoutines()->dispatcher_no_check; Gen::XEmitter emit(location); - if (*location == 0xE8) + if (source.call) { emit.CALL(address); } |
