A32: Add yuzu-specific hacks

This commit is contained in:
MerryMage 2020-06-16 16:38:43 +01:00
parent 2c1a4843ad
commit a1c9bb94a8
7 changed files with 57 additions and 14 deletions

View file

@ -59,6 +59,16 @@ public:
*/ */
void HaltExecution(); void HaltExecution();
/**
* HACK:
* Exits execution from a callback, the callback must rewind the stack or
* never return to dynarmic from it's current stack.
*/
void ExceptionalExit();
/// HACK: Change processor ID.
void ChangeProcessorID(std::size_t new_processor);
/// View and modify registers. /// View and modify registers.
std::array<std::uint32_t, 16>& Regs(); std::array<std::uint32_t, 16>& Regs();
const std::array<std::uint32_t, 16>& Regs() const; const std::array<std::uint32_t, 16>& Regs() const;

View file

@ -139,6 +139,11 @@ struct UserConfig {
/// definite behaviour for some unpredictable instructions. /// definite behaviour for some unpredictable instructions.
bool define_unpredictable_behaviour = false; bool define_unpredictable_behaviour = false;
/// HACK:
/// This tells the translator a wall clock will be used, thus allowing it
/// to avoid writting certain unnecessary code only needed for cycle timers.
bool wall_clock_cntpct = false;
/// This enables the fast dispatcher. /// This enables the fast dispatcher.
bool enable_fast_dispatch = true; bool enable_fast_dispatch = true;

View file

@ -61,11 +61,15 @@ public:
void HaltExecution(); void HaltExecution();
/** /**
* HACK:
* Exits execution from a callback, the callback must rewind the stack or * Exits execution from a callback, the callback must rewind the stack or
* never return to dynarmic from it's current stack. * never return to dynarmic from it's current stack.
*/ */
void ExceptionalExit(); void ExceptionalExit();
/// HACK: Change processor ID.
void ChangeProcessorID(std::size_t new_processor);
/// Read Stack Pointer /// Read Stack Pointer
std::uint64_t GetSP() const; std::uint64_t GetSP() const;
/// Modify Stack Pointer /// Modify Stack Pointer
@ -111,8 +115,6 @@ public:
/// Modify PSTATE /// Modify PSTATE
void SetPstate(std::uint32_t value); void SetPstate(std::uint32_t value);
void ChangeProcessorID(std::size_t new_processor);
/// Clears exclusive state for this core. /// Clears exclusive state for this core.
void ClearExclusiveState(); void ClearExclusiveState();

View file

@ -194,12 +194,12 @@ struct UserConfig {
/// page boundary. /// page boundary.
bool only_detect_misalignment_via_page_table_on_page_boundary = false; bool only_detect_misalignment_via_page_table_on_page_boundary = false;
/// This option relates to translation. Generally when we run into an unpredictable /// This option relates to translation. Generally when we run into an unpredictable
/// instruction the ExceptionRaised callback is called. If this is true, we define /// instruction the ExceptionRaised callback is called. If this is true, we define
/// definite behaviour for some unpredictable instructions. /// definite behaviour for some unpredictable instructions.
bool define_unpredictable_behaviour = false; bool define_unpredictable_behaviour = false;
/// HACK:
/// This tells the translator a wall clock will be used, thus allowing it /// This tells the translator a wall clock will be used, thus allowing it
/// to avoid writting certain unnecessary code only needed for cycle timers. /// to avoid writting certain unnecessary code only needed for cycle timers.
bool wall_clock_cntpct = false; bool wall_clock_cntpct = false;

View file

@ -47,8 +47,12 @@ public:
void InvalidateCacheRanges(const boost::icl::interval_set<u32>& ranges); void InvalidateCacheRanges(const boost::icl::interval_set<u32>& ranges);
void ChangeProcessorID(size_t value) {
conf.processor_id = value;
}
protected: protected:
const A32::UserConfig conf; A32::UserConfig conf;
A32::Jit* jit_interface; A32::Jit* jit_interface;
BlockRangeInformation<u32> block_ranges; BlockRangeInformation<u32> block_ranges;

View file

@ -63,7 +63,7 @@ struct Jit::Impl {
BlockOfCode block_of_code; BlockOfCode block_of_code;
A32EmitX64 emitter; A32EmitX64 emitter;
const A32::UserConfig conf; A32::UserConfig conf;
// Requests made during execution to invalidate the cache are queued up here. // Requests made during execution to invalidate the cache are queued up here.
size_t invalid_cache_generation = 0; size_t invalid_cache_generation = 0;
@ -89,6 +89,19 @@ struct Jit::Impl {
block_of_code.StepCode(&jit_state, GetCurrentSingleStep()); block_of_code.StepCode(&jit_state, GetCurrentSingleStep());
} }
void ExceptionalExit() {
if (!conf.wall_clock_cntpct) {
const s64 ticks = jit_state.cycles_to_run - jit_state.cycles_remaining;
conf.callbacks->AddTicks(ticks);
}
PerformCacheInvalidation();
}
void ChangeProcessorID(size_t value) {
conf.processor_id = value;
emitter.ChangeProcessorID(value);
}
std::string Disassemble(const IR::LocationDescriptor& descriptor) { std::string Disassemble(const IR::LocationDescriptor& descriptor) {
auto block = GetBasicBlock(descriptor); auto block = GetBasicBlock(descriptor);
std::string result = fmt::format("address: {}\nsize: {} bytes\n", block.entrypoint, block.size); std::string result = fmt::format("address: {}\nsize: {} bytes\n", block.entrypoint, block.size);
@ -218,6 +231,15 @@ void Jit::HaltExecution() {
impl->jit_state.halt_requested = true; impl->jit_state.halt_requested = true;
} }
void Jit::ExceptionalExit() {
impl->ExceptionalExit();
is_executing = false;
}
void Jit::ChangeProcessorID(size_t new_processor) {
impl->ChangeProcessorID(new_processor);
}
std::array<u32, 16>& Jit::Regs() { std::array<u32, 16>& Jit::Regs() {
return impl->jit_state.Reg; return impl->jit_state.Reg;
} }

View file

@ -92,6 +92,11 @@ public:
is_executing = false; is_executing = false;
} }
void ChangeProcessorID(size_t value) {
conf.processor_id = value;
emitter.ChangeProcessorID(value);
}
void ClearCache() { void ClearCache() {
invalidate_entire_cache = true; invalidate_entire_cache = true;
RequestCacheInvalidation(); RequestCacheInvalidation();
@ -194,11 +199,6 @@ public:
jit_state.SetPstate(value); jit_state.SetPstate(value);
} }
void ChangeProcessorID(size_t value) {
conf.processor_id = value;
emitter.ChangeProcessorID(value);
}
void ClearExclusiveState() { void ClearExclusiveState() {
jit_state.exclusive_state = 0; jit_state.exclusive_state = 0;
} }
@ -326,6 +326,10 @@ void Jit::ExceptionalExit() {
impl->ExceptionalExit(); impl->ExceptionalExit();
} }
void Jit::ChangeProcessorID(size_t new_processor) {
impl->ChangeProcessorID(new_processor);
}
u64 Jit::GetSP() const { u64 Jit::GetSP() const {
return impl->GetSP(); return impl->GetSP();
} }
@ -398,10 +402,6 @@ void Jit::SetPstate(u32 value) {
impl->SetPstate(value); impl->SetPstate(value);
} }
void Jit::ChangeProcessorID(size_t new_processor) {
impl->ChangeProcessorID(new_processor);
}
void Jit::ClearExclusiveState() { void Jit::ClearExclusiveState() {
impl->ClearExclusiveState(); impl->ClearExclusiveState();
} }