mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-07-10 17:01:24 +12:00
PPU/LLVM: Add debug tool for LLVM recompiler
This commit is contained in:
parent
1e9c266457
commit
e459d01927
4 changed files with 92 additions and 35 deletions
|
@ -279,6 +279,7 @@ std::shared_ptr<RecompilationEngine> RecompilationEngine::s_the_instance = nullp
|
|||
|
||||
RecompilationEngine::RecompilationEngine()
|
||||
: m_log(nullptr)
|
||||
, m_currentId(0)
|
||||
, m_last_cache_clear_time(std::chrono::high_resolution_clock::now())
|
||||
, m_compiler(*this, CPUHybridDecoderRecompiler::ExecuteFunction, CPUHybridDecoderRecompiler::ExecuteTillReturn, CPUHybridDecoderRecompiler::PollStatus) {
|
||||
m_compiler.RunAllTests();
|
||||
|
@ -312,6 +313,9 @@ const Executable *RecompilationEngine::GetCompiledExecutableIfAvailable(u32 addr
|
|||
return nullptr;
|
||||
if (std::get<1>(It->second) == nullptr)
|
||||
return nullptr;
|
||||
u32 id = std::get<3>(It->second);
|
||||
if (Ini.LLVMExclusionRange.GetValue() && (id >= Ini.LLVMMinId.GetValue() && id <= Ini.LLVMMaxId.GetValue()))
|
||||
return nullptr;
|
||||
return &(std::get<0>(It->second));
|
||||
}
|
||||
|
||||
|
@ -495,7 +499,7 @@ void RecompilationEngine::ProcessExecutionTrace(const ExecutionTrace & execution
|
|||
for (auto i = processed_execution_trace_i->second.begin(); i != processed_execution_trace_i->second.end(); i++) {
|
||||
if (!(*i)->is_compiled) {
|
||||
(*i)->num_hits++;
|
||||
if ((*i)->num_hits >= 1000) { // TODO: Make this configurable
|
||||
if ((*i)->num_hits >= Ini.LLVMThreshold.GetValue()) {
|
||||
CompileBlock(*(*i));
|
||||
}
|
||||
}
|
||||
|
@ -569,6 +573,9 @@ void RecompilationEngine::CompileBlock(BlockEntry & block_entry) {
|
|||
|
||||
std::get<1>(m_address_to_function[block_entry.cfg.start_address]) = std::unique_ptr<llvm::ExecutionEngine>(compileResult.second);
|
||||
std::get<0>(m_address_to_function[block_entry.cfg.start_address]) = compileResult.first;
|
||||
std::get<3>(m_address_to_function[block_entry.cfg.start_address]) = m_currentId;
|
||||
Log() << "ID IS " << m_currentId << "\n";
|
||||
m_currentId++;
|
||||
block_entry.last_compiled_cfg_size = block_entry.cfg.GetSize();
|
||||
block_entry.is_compiled = true;
|
||||
}
|
||||
|
@ -722,39 +729,43 @@ u32 ppu_recompiler_llvm::CPUHybridDecoderRecompiler::ExecuteTillReturn(PPUThread
|
|||
mut->second.fetch_add(1);
|
||||
}
|
||||
const Executable *executable = execution_engine->m_recompilation_engine->GetCompiledExecutableIfAvailable(ppu_state->PC);
|
||||
auto entry = ppu_state->PC;
|
||||
u32 exit = (u32)(*executable)(ppu_state, 0);
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::ExitFromCompiledBlock, entry, exit);
|
||||
mut->second.fetch_sub(1);
|
||||
if (exit == 0)
|
||||
return 0;
|
||||
} else {
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::Instruction, ppu_state->PC, 0);
|
||||
u32 instruction = vm::ps3::read32(ppu_state->PC);
|
||||
u32 oldPC = ppu_state->PC;
|
||||
execution_engine->m_decoder.Decode(instruction);
|
||||
auto branch_type = ppu_state->PC != oldPC ? GetBranchTypeFromInstruction(instruction) : BranchType::NonBranch;
|
||||
ppu_state->PC += 4;
|
||||
if (executable)
|
||||
{
|
||||
auto entry = ppu_state->PC;
|
||||
u32 exit = (u32)(*executable)(ppu_state, 0);
|
||||
mut->second.fetch_sub(1);
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::ExitFromCompiledBlock, entry, exit);
|
||||
if (exit == 0)
|
||||
return 0;
|
||||
continue;
|
||||
}
|
||||
mut->second.fetch_add(1);
|
||||
}
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::Instruction, ppu_state->PC, 0);
|
||||
u32 instruction = vm::ps3::read32(ppu_state->PC);
|
||||
u32 oldPC = ppu_state->PC;
|
||||
execution_engine->m_decoder.Decode(instruction);
|
||||
auto branch_type = ppu_state->PC != oldPC ? GetBranchTypeFromInstruction(instruction) : BranchType::NonBranch;
|
||||
ppu_state->PC += 4;
|
||||
|
||||
switch (branch_type) {
|
||||
case BranchType::Return:
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::Return, 0, 0);
|
||||
if (Emu.GetCPUThreadStop() == ppu_state->PC) ppu_state->fast_stop();
|
||||
return 0;
|
||||
case BranchType::FunctionCall: {
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::CallFunction, ppu_state->PC, 0);
|
||||
const Executable *executable = execution_engine->m_recompilation_engine->GetExecutable(ppu_state->PC, true);
|
||||
(*executable)(ppu_state, 0);
|
||||
break;
|
||||
}
|
||||
case BranchType::LocalBranch:
|
||||
break;
|
||||
case BranchType::NonBranch:
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
switch (branch_type) {
|
||||
case BranchType::Return:
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::Return, 0, 0);
|
||||
if (Emu.GetCPUThreadStop() == ppu_state->PC) ppu_state->fast_stop();
|
||||
return 0;
|
||||
case BranchType::FunctionCall: {
|
||||
execution_engine->m_tracer.Trace(Tracer::TraceType::CallFunction, ppu_state->PC, 0);
|
||||
const Executable *executable = execution_engine->m_recompilation_engine->GetExecutable(ppu_state->PC, true);
|
||||
(*executable)(ppu_state, 0);
|
||||
break;
|
||||
}
|
||||
case BranchType::LocalBranch:
|
||||
break;
|
||||
case BranchType::NonBranch:
|
||||
break;
|
||||
default:
|
||||
assert(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue