[dynarmic] memory-inline JIT implementation w/o exposing specific interfaces

Signed-off-by: lizzie <lizzie@eden-emu.dev>
This commit is contained in:
lizzie 2026-01-24 06:06:46 +00:00
parent d06fbb933e
commit 89f424e61f
9 changed files with 192 additions and 174 deletions

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -64,13 +64,11 @@ struct Jit::Impl final {
}
void ClearCache() {
std::unique_lock lock{invalidation_mutex};
invalidate_entire_cache = true;
HaltExecution(HaltReason::CacheInvalidation);
}
void InvalidateCacheRange(std::uint32_t start_address, std::size_t length) {
std::unique_lock lock{invalidation_mutex};
invalid_cache_ranges.add(boost::icl::discrete_interval<u32>::closed(start_address, static_cast<u32>(start_address + length - 1)));
HaltExecution(HaltReason::CacheInvalidation);
}
@ -132,8 +130,6 @@ struct Jit::Impl final {
private:
void PerformRequestedCacheInvalidation(HaltReason hr) {
if (Has(hr, HaltReason::CacheInvalidation)) {
std::unique_lock lock{invalidation_mutex};
ClearHalt(HaltReason::CacheInvalidation);
if (invalidate_entire_cache) {
@ -160,83 +156,90 @@ private:
A32Core core;
volatile u32 halt_reason = 0;
std::mutex invalidation_mutex;
boost::icl::interval_set<u32> invalid_cache_ranges;
bool invalidate_entire_cache = false;
};
static_assert(sizeof(Jit::Impl) <= sizeof(Jit::impl_storage));
Jit::Jit(UserConfig conf)
: impl(std::make_unique<Impl>(this, conf)) {}
Jit::~Jit() = default;
Jit::Jit(UserConfig conf) {
new (&impl_storage[0]) Jit::Impl(this, conf);
}
Jit::~Jit() {
reinterpret_cast<Jit::Impl*>(&impl_storage[0])->~Impl();
}
inline Jit::Impl* GetImpl(Jit& jit) noexcept {
return reinterpret_cast<Jit::Impl*>(&jit.impl_storage[0]);
}
inline Jit::Impl const* GetImpl(Jit const& jit) noexcept {
return reinterpret_cast<Jit::Impl const*>(&jit.impl_storage[0]);
}
HaltReason Jit::Run() {
return impl->Run();
return GetImpl(*this)->Run();
}
HaltReason Jit::Step() {
return impl->Step();
return GetImpl(*this)->Step();
}
void Jit::ClearCache() {
impl->ClearCache();
GetImpl(*this)->ClearCache();
}
void Jit::InvalidateCacheRange(std::uint32_t start_address, std::size_t length) {
impl->InvalidateCacheRange(start_address, length);
GetImpl(*this)->InvalidateCacheRange(start_address, length);
}
void Jit::Reset() {
impl->Reset();
GetImpl(*this)->Reset();
}
void Jit::HaltExecution(HaltReason hr) {
impl->HaltExecution(hr);
GetImpl(*this)->HaltExecution(hr);
}
void Jit::ClearHalt(HaltReason hr) {
impl->ClearHalt(hr);
GetImpl(*this)->ClearHalt(hr);
}
std::array<std::uint32_t, 16>& Jit::Regs() {
return impl->Regs();
return GetImpl(*this)->Regs();
}
const std::array<std::uint32_t, 16>& Jit::Regs() const {
return impl->Regs();
return GetImpl(*this)->Regs();
}
std::array<std::uint32_t, 64>& Jit::ExtRegs() {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
const std::array<std::uint32_t, 64>& Jit::ExtRegs() const {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
std::uint32_t Jit::Cpsr() const {
return impl->Cpsr();
return GetImpl(*this)->Cpsr();
}
void Jit::SetCpsr(std::uint32_t value) {
impl->SetCpsr(value);
GetImpl(*this)->SetCpsr(value);
}
std::uint32_t Jit::Fpscr() const {
return impl->Fpscr();
return GetImpl(*this)->Fpscr();
}
void Jit::SetFpscr(std::uint32_t value) {
impl->SetFpscr(value);
GetImpl(*this)->SetFpscr(value);
}
void Jit::ClearExclusiveState() {
impl->ClearExclusiveState();
GetImpl(*this)->ClearExclusiveState();
}
std::string Jit::Disassemble() const {
return impl->Disassemble();
return GetImpl(*this)->Disassemble();
}
} // namespace Dynarmic::A32

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -27,13 +27,13 @@ using namespace Backend::Arm64;
struct Jit::Impl final {
Impl(Jit*, A64::UserConfig conf)
: conf(conf)
, current_address_space(conf)
, core(conf) {}
: conf(conf)
, current_address_space(conf)
, core(conf) {}
HaltReason Run() {
ASSERT(!is_executing);
PerformRequestedCacheInvalidation(static_cast<HaltReason>(Atomic::Load(&halt_reason)));
PerformRequestedCacheInvalidation(HaltReason(Atomic::Load(&halt_reason)));
is_executing = true;
SCOPE_EXIT {
@ -49,7 +49,7 @@ struct Jit::Impl final {
HaltReason Step() {
ASSERT(!is_executing);
PerformRequestedCacheInvalidation(static_cast<HaltReason>(Atomic::Load(&halt_reason)));
PerformRequestedCacheInvalidation(HaltReason(Atomic::Load(&halt_reason)));
is_executing = true;
SCOPE_EXIT {
@ -64,13 +64,11 @@ struct Jit::Impl final {
}
void ClearCache() {
std::unique_lock lock{invalidation_mutex};
invalidate_entire_cache = true;
HaltExecution(HaltReason::CacheInvalidation);
}
void InvalidateCacheRange(std::uint64_t start_address, std::size_t length) {
std::unique_lock lock{invalidation_mutex};
invalid_cache_ranges.add(boost::icl::discrete_interval<u64>::closed(start_address, start_address + length - 1));
HaltExecution(HaltReason::CacheInvalidation);
}
@ -158,8 +156,6 @@ struct Jit::Impl final {
private:
void PerformRequestedCacheInvalidation(HaltReason hr) {
if (Has(hr, HaltReason::CacheInvalidation)) {
std::unique_lock lock{invalidation_mutex};
ClearHalt(HaltReason::CacheInvalidation);
if (invalidate_entire_cache) {
@ -185,134 +181,140 @@ private:
A64Core core;
volatile u32 halt_reason = 0;
std::mutex invalidation_mutex;
boost::icl::interval_set<u64> invalid_cache_ranges;
bool invalidate_entire_cache = false;
bool is_executing = false;
};
static_assert(sizeof(Jit::Impl) <= sizeof(Jit::impl_storage));
Jit::Jit(UserConfig conf)
: impl{std::make_unique<Jit::Impl>(this, conf)} {
Jit::Jit(UserConfig conf) {
new (&impl_storage[0]) Jit::Impl(this, conf);
}
Jit::~Jit() {
reinterpret_cast<Jit::Impl*>(&impl_storage[0])->~Impl();
}
inline Jit::Impl* GetImpl(Jit& jit) noexcept {
return reinterpret_cast<Jit::Impl*>(&jit.impl_storage[0]);
}
inline Jit::Impl const* GetImpl(Jit const& jit) noexcept {
return reinterpret_cast<Jit::Impl const*>(&jit.impl_storage[0]);
}
Jit::~Jit() = default;
HaltReason Jit::Run() {
return impl->Run();
return GetImpl(*this)->Run();
}
HaltReason Jit::Step() {
return impl->Step();
return GetImpl(*this)->Step();
}
void Jit::ClearCache() {
impl->ClearCache();
GetImpl(*this)->ClearCache();
}
void Jit::InvalidateCacheRange(std::uint64_t start_address, std::size_t length) {
impl->InvalidateCacheRange(start_address, length);
GetImpl(*this)->InvalidateCacheRange(start_address, length);
}
void Jit::Reset() {
impl->Reset();
GetImpl(*this)->Reset();
}
void Jit::HaltExecution(HaltReason hr) {
impl->HaltExecution(hr);
GetImpl(*this)->HaltExecution(hr);
}
void Jit::ClearHalt(HaltReason hr) {
impl->ClearHalt(hr);
GetImpl(*this)->ClearHalt(hr);
}
std::uint64_t Jit::GetSP() const {
return impl->SP();
return GetImpl(*this)->SP();
}
void Jit::SetSP(std::uint64_t value) {
impl->SetSP(value);
GetImpl(*this)->SetSP(value);
}
std::uint64_t Jit::GetPC() const {
return impl->PC();
return GetImpl(*this)->PC();
}
void Jit::SetPC(std::uint64_t value) {
impl->SetPC(value);
GetImpl(*this)->SetPC(value);
}
std::uint64_t Jit::GetRegister(std::size_t index) const {
return impl->Regs()[index];
return GetImpl(*this)->Regs()[index];
}
void Jit::SetRegister(size_t index, std::uint64_t value) {
impl->Regs()[index] = value;
GetImpl(*this)->Regs()[index] = value;
}
std::array<std::uint64_t, 31> Jit::GetRegisters() const {
return impl->Regs();
return GetImpl(*this)->Regs();
}
void Jit::SetRegisters(const std::array<std::uint64_t, 31>& value) {
impl->Regs() = value;
GetImpl(*this)->Regs() = value;
}
Vector Jit::GetVector(std::size_t index) const {
auto& vec = impl->VecRegs();
auto& vec = GetImpl(*this)->VecRegs();
return {vec[index * 2], vec[index * 2 + 1]};
}
void Jit::SetVector(std::size_t index, Vector value) {
auto& vec = impl->VecRegs();
auto& vec = GetImpl(*this)->VecRegs();
vec[index * 2] = value[0];
vec[index * 2 + 1] = value[1];
}
std::array<Vector, 32> Jit::GetVectors() const {
std::array<Vector, 32> ret;
std::memcpy(ret.data(), impl->VecRegs().data(), sizeof(ret));
std::memcpy(ret.data(), GetImpl(*this)->VecRegs().data(), sizeof(ret));
return ret;
}
void Jit::SetVectors(const std::array<Vector, 32>& value) {
std::memcpy(impl->VecRegs().data(), value.data(), sizeof(value));
std::memcpy(GetImpl(*this)->VecRegs().data(), value.data(), sizeof(value));
}
std::uint32_t Jit::GetFpcr() const {
return impl->Fpcr();
return GetImpl(*this)->Fpcr();
}
void Jit::SetFpcr(std::uint32_t value) {
impl->SetFpcr(value);
GetImpl(*this)->SetFpcr(value);
}
std::uint32_t Jit::GetFpsr() const {
return impl->Fpsr();
return GetImpl(*this)->Fpsr();
}
void Jit::SetFpsr(std::uint32_t value) {
impl->SetFpsr(value);
GetImpl(*this)->SetFpsr(value);
}
std::uint32_t Jit::GetPstate() const {
return impl->Pstate();
return GetImpl(*this)->Pstate();
}
void Jit::SetPstate(std::uint32_t value) {
impl->SetPstate(value);
GetImpl(*this)->SetPstate(value);
}
void Jit::ClearExclusiveState() {
impl->ClearExclusiveState();
GetImpl(*this)->ClearExclusiveState();
}
bool Jit::IsExecuting() const {
return impl->IsExecuting();
return GetImpl(*this)->IsExecuting();
}
std::string Jit::Disassemble() const {
return impl->Disassemble();
return GetImpl(*this)->Disassemble();
}
} // namespace Dynarmic::A64

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -60,13 +60,11 @@ struct Jit::Impl final {
}
void ClearCache() {
std::unique_lock lock{invalidation_mutex};
invalidate_entire_cache = true;
HaltExecution(HaltReason::CacheInvalidation);
}
void InvalidateCacheRange(u32 start_address, size_t length) {
std::unique_lock lock{invalidation_mutex};
invalid_cache_ranges.add(boost::icl::discrete_interval<u32>::closed(start_address, static_cast<u32>(start_address + length - 1)));
HaltExecution(HaltReason::CacheInvalidation);
}
@ -134,79 +132,86 @@ private:
A32Core core;
volatile u32 halt_reason = 0;
std::mutex invalidation_mutex;
boost::icl::interval_set<u32> invalid_cache_ranges;
bool invalidate_entire_cache = false;
};
static_assert(sizeof(Jit::Impl) <= sizeof(Jit::impl_storage));
Jit::Jit(UserConfig conf)
: impl(std::make_unique<Impl>(this, conf)) {}
Jit::~Jit() = default;
Jit::Jit(UserConfig conf) {
new (&impl_storage[0]) Jit::Impl(this, conf);
}
Jit::~Jit() {
reinterpret_cast<Jit::Impl*>(&impl_storage[0])->~Impl();
}
inline Jit::Impl* GetImpl(Jit& jit) noexcept {
return reinterpret_cast<Jit::Impl*>(&jit.impl_storage[0]);
}
inline Jit::Impl const* GetImpl(Jit const& jit) noexcept {
return reinterpret_cast<Jit::Impl const*>(&jit.impl_storage[0]);
}
HaltReason Jit::Run() {
return impl->Run();
return GetImpl(*this)->Run();
}
HaltReason Jit::Step() {
return impl->Step();
return GetImpl(*this)->Step();
}
void Jit::ClearCache() {
impl->ClearCache();
GetImpl(*this)->ClearCache();
}
void Jit::InvalidateCacheRange(u32 start_address, std::size_t length) {
impl->InvalidateCacheRange(start_address, length);
GetImpl(*this)->InvalidateCacheRange(start_address, length);
}
void Jit::Reset() {
impl->Reset();
GetImpl(*this)->Reset();
}
void Jit::HaltExecution(HaltReason hr) {
impl->HaltExecution(hr);
GetImpl(*this)->HaltExecution(hr);
}
void Jit::ClearHalt(HaltReason hr) {
impl->ClearHalt(hr);
GetImpl(*this)->ClearHalt(hr);
}
std::array<u32, 16>& Jit::Regs() {
return impl->Regs();
return GetImpl(*this)->Regs();
}
const std::array<u32, 16>& Jit::Regs() const {
return impl->Regs();
return GetImpl(*this)->Regs();
}
std::array<u32, 64>& Jit::ExtRegs() {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
const std::array<u32, 64>& Jit::ExtRegs() const {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
u32 Jit::Cpsr() const {
return impl->Cpsr();
return GetImpl(*this)->Cpsr();
}
void Jit::SetCpsr(u32 value) {
impl->SetCpsr(value);
GetImpl(*this)->SetCpsr(value);
}
u32 Jit::Fpscr() const {
return impl->Fpscr();
return GetImpl(*this)->Fpscr();
}
void Jit::SetFpscr(u32 value) {
impl->SetFpscr(value);
GetImpl(*this)->SetFpscr(value);
}
void Jit::ClearExclusiveState() {
impl->ClearExclusiveState();
GetImpl(*this)->ClearExclusiveState();
}
} // namespace Dynarmic::A32

View File

@ -81,7 +81,10 @@ FP::FPCR A32EmitContext::FPCR(bool fpcr_controlled) const {
}
A32EmitX64::A32EmitX64(BlockOfCode& code, A32::UserConfig conf, A32::Jit* jit_interface)
: EmitX64(code), conf(std::move(conf)), jit_interface(jit_interface) {
: EmitX64(code)
, conf(std::move(conf))
, jit_interface(jit_interface)
{
GenFastmemFallbacks();
GenTerminalHandlers();
code.PreludeComplete();

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -116,13 +116,11 @@ struct Jit::Impl {
}
void ClearCache() {
std::unique_lock lock{invalidation_mutex};
invalidate_entire_cache = true;
HaltExecution(HaltReason::CacheInvalidation);
}
void InvalidateCacheRange(std::uint32_t start_address, std::size_t length) {
std::unique_lock lock{invalidation_mutex};
invalid_cache_ranges.add(boost::icl::discrete_interval<u32>::closed(start_address, static_cast<u32>(start_address + length - 1)));
HaltExecution(HaltReason::CacheInvalidation);
}
@ -219,8 +217,6 @@ private:
void PerformRequestedCacheInvalidation(HaltReason hr) {
if (Has(hr, HaltReason::CacheInvalidation)) {
std::unique_lock lock{invalidation_mutex};
ClearHalt(HaltReason::CacheInvalidation);
if (!invalidate_entire_cache && invalid_cache_ranges.empty()) {
@ -251,80 +247,88 @@ private:
// Requests made during execution to invalidate the cache are queued up here.
bool invalidate_entire_cache = false;
boost::icl::interval_set<u32> invalid_cache_ranges;
std::mutex invalidation_mutex;
};
static_assert(sizeof(Jit::Impl) <= sizeof(Jit::impl_storage));
Jit::Jit(UserConfig conf)
: impl(std::make_unique<Impl>(this, std::move(conf))) {}
Jit::~Jit() = default;
Jit::Jit(UserConfig conf) {
new (&impl_storage[0]) Jit::Impl(this, conf);
}
Jit::~Jit() {
reinterpret_cast<Jit::Impl*>(&impl_storage[0])->~Impl();
}
inline Jit::Impl* GetImpl(Jit& jit) noexcept {
return reinterpret_cast<Jit::Impl*>(&jit.impl_storage[0]);
}
inline Jit::Impl const* GetImpl(Jit const& jit) noexcept {
return reinterpret_cast<Jit::Impl const*>(&jit.impl_storage[0]);
}
HaltReason Jit::Run() {
return impl->Run();
return GetImpl(*this)->Run();
}
HaltReason Jit::Step() {
return impl->Step();
return GetImpl(*this)->Step();
}
void Jit::ClearCache() {
impl->ClearCache();
GetImpl(*this)->ClearCache();
}
void Jit::InvalidateCacheRange(std::uint32_t start_address, std::size_t length) {
impl->InvalidateCacheRange(start_address, length);
GetImpl(*this)->InvalidateCacheRange(start_address, length);
}
void Jit::Reset() {
impl->Reset();
GetImpl(*this)->Reset();
}
void Jit::HaltExecution(HaltReason hr) {
impl->HaltExecution(hr);
GetImpl(*this)->HaltExecution(hr);
}
void Jit::ClearHalt(HaltReason hr) {
impl->ClearHalt(hr);
GetImpl(*this)->ClearHalt(hr);
}
std::array<std::uint32_t, 16>& Jit::Regs() {
return impl->Regs();
return GetImpl(*this)->Regs();
}
const std::array<std::uint32_t, 16>& Jit::Regs() const {
return impl->Regs();
return GetImpl(*this)->Regs();
}
std::array<std::uint32_t, 64>& Jit::ExtRegs() {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
const std::array<std::uint32_t, 64>& Jit::ExtRegs() const {
return impl->ExtRegs();
return GetImpl(*this)->ExtRegs();
}
std::uint32_t Jit::Cpsr() const {
return impl->Cpsr();
return GetImpl(*this)->Cpsr();
}
void Jit::SetCpsr(std::uint32_t value) {
impl->SetCpsr(value);
GetImpl(*this)->SetCpsr(value);
}
std::uint32_t Jit::Fpscr() const {
return impl->Fpscr();
return GetImpl(*this)->Fpscr();
}
void Jit::SetFpscr(std::uint32_t value) {
impl->SetFpscr(value);
GetImpl(*this)->SetFpscr(value);
}
void Jit::ClearExclusiveState() {
impl->ClearExclusiveState();
GetImpl(*this)->ClearExclusiveState();
}
std::string Jit::Disassemble() const {
return impl->Disassemble();
return GetImpl(*this)->Disassemble();
}
} // namespace Dynarmic::A32

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -115,14 +115,12 @@ public:
}
void ClearCache() {
std::unique_lock lock{invalidation_mutex};
invalidate_entire_cache = true;
HaltExecution(HaltReason::CacheInvalidation);
}
void InvalidateCacheRange(u64 start_address, size_t length) {
std::unique_lock lock{invalidation_mutex};
const auto end_address = static_cast<u64>(start_address + length - 1);
const auto end_address = u64(start_address + length - 1);
const auto range = boost::icl::discrete_interval<u64>::closed(start_address, end_address);
invalid_cache_ranges.add(range);
HaltExecution(HaltReason::CacheInvalidation);
@ -276,8 +274,6 @@ private:
void PerformRequestedCacheInvalidation(HaltReason hr) {
if (Has(hr, HaltReason::CacheInvalidation)) {
std::unique_lock lock{invalidation_mutex};
ClearHalt(HaltReason::CacheInvalidation);
if (!invalidate_entire_cache && invalid_cache_ranges.empty()) {
@ -306,124 +302,132 @@ private:
bool invalidate_entire_cache = false;
boost::icl::interval_set<u64> invalid_cache_ranges;
std::mutex invalidation_mutex;
};
static_assert(sizeof(Jit::Impl) <= sizeof(Jit::impl_storage));
Jit::Jit(UserConfig conf)
: impl(std::make_unique<Jit::Impl>(this, conf)) {}
Jit::~Jit() = default;
Jit::Jit(UserConfig conf) {
new (&impl_storage[0]) Jit::Impl(this, conf);
}
Jit::~Jit() {
reinterpret_cast<Jit::Impl*>(&impl_storage[0])->~Impl();
}
inline Jit::Impl* GetImpl(Jit& jit) noexcept {
return reinterpret_cast<Jit::Impl*>(&jit.impl_storage[0]);
}
inline Jit::Impl const* GetImpl(Jit const& jit) noexcept {
return reinterpret_cast<Jit::Impl const*>(&jit.impl_storage[0]);
}
HaltReason Jit::Run() {
return impl->Run();
return GetImpl(*this)->Run();
}
HaltReason Jit::Step() {
return impl->Step();
return GetImpl(*this)->Step();
}
void Jit::ClearCache() {
impl->ClearCache();
GetImpl(*this)->ClearCache();
}
void Jit::InvalidateCacheRange(u64 start_address, size_t length) {
impl->InvalidateCacheRange(start_address, length);
GetImpl(*this)->InvalidateCacheRange(start_address, length);
}
void Jit::Reset() {
impl->Reset();
GetImpl(*this)->Reset();
}
void Jit::HaltExecution(HaltReason hr) {
impl->HaltExecution(hr);
GetImpl(*this)->HaltExecution(hr);
}
void Jit::ClearHalt(HaltReason hr) {
impl->ClearHalt(hr);
GetImpl(*this)->ClearHalt(hr);
}
u64 Jit::GetSP() const {
return impl->GetSP();
return GetImpl(*this)->GetSP();
}
void Jit::SetSP(u64 value) {
impl->SetSP(value);
GetImpl(*this)->SetSP(value);
}
u64 Jit::GetPC() const {
return impl->GetPC();
return GetImpl(*this)->GetPC();
}
void Jit::SetPC(u64 value) {
impl->SetPC(value);
GetImpl(*this)->SetPC(value);
}
u64 Jit::GetRegister(size_t index) const {
return impl->GetRegister(index);
return GetImpl(*this)->GetRegister(index);
}
void Jit::SetRegister(size_t index, u64 value) {
impl->SetRegister(index, value);
GetImpl(*this)->SetRegister(index, value);
}
std::array<u64, 31> Jit::GetRegisters() const {
return impl->GetRegisters();
return GetImpl(*this)->GetRegisters();
}
void Jit::SetRegisters(const std::array<u64, 31>& value) {
impl->SetRegisters(value);
GetImpl(*this)->SetRegisters(value);
}
Vector Jit::GetVector(size_t index) const {
return impl->GetVector(index);
return GetImpl(*this)->GetVector(index);
}
void Jit::SetVector(size_t index, Vector value) {
impl->SetVector(index, value);
GetImpl(*this)->SetVector(index, value);
}
std::array<Vector, 32> Jit::GetVectors() const {
return impl->GetVectors();
return GetImpl(*this)->GetVectors();
}
void Jit::SetVectors(const std::array<Vector, 32>& value) {
impl->SetVectors(value);
GetImpl(*this)->SetVectors(value);
}
u32 Jit::GetFpcr() const {
return impl->GetFpcr();
return GetImpl(*this)->GetFpcr();
}
void Jit::SetFpcr(u32 value) {
impl->SetFpcr(value);
GetImpl(*this)->SetFpcr(value);
}
u32 Jit::GetFpsr() const {
return impl->GetFpsr();
return GetImpl(*this)->GetFpsr();
}
void Jit::SetFpsr(u32 value) {
impl->SetFpsr(value);
GetImpl(*this)->SetFpsr(value);
}
u32 Jit::GetPstate() const {
return impl->GetPstate();
return GetImpl(*this)->GetPstate();
}
void Jit::SetPstate(u32 value) {
impl->SetPstate(value);
GetImpl(*this)->SetPstate(value);
}
void Jit::ClearExclusiveState() {
impl->ClearExclusiveState();
GetImpl(*this)->ClearExclusiveState();
}
bool Jit::IsExecuting() const {
return impl->IsExecuting();
return GetImpl(*this)->IsExecuting();
}
std::string Jit::Disassemble() const {
return impl->Disassemble();
return GetImpl(*this)->Disassemble();
}
} // namespace Dynarmic::A64

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -197,8 +197,8 @@ private:
RunCodeFuncType run_code = nullptr;
RunCodeFuncType step_code = nullptr;
std::array<const void*, 4> return_from_run_code;
bool prelude_complete = false;
const HostFeature host_features;
bool prelude_complete = false;
void GenRunCode(std::function<void(BlockOfCode&)> rcp);
};

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -96,11 +96,9 @@ public:
/// the resulting instructions as a vector of their string representations.
std::string Disassemble() const;
private:
bool is_executing = false;
struct Impl;
std::unique_ptr<Impl> impl;
bool is_executing = false;
char impl_storage[16788736];
};
} // namespace A32

View File

@ -1,4 +1,4 @@
// SPDX-FileCopyrightText: Copyright 2025 Eden Emulator Project
// SPDX-FileCopyrightText: Copyright 2026 Eden Emulator Project
// SPDX-License-Identifier: GPL-3.0-or-later
/* This file is part of the dynarmic project.
@ -126,9 +126,8 @@ public:
/// the resulting instructions as a vector of their string representations.
std::string Disassemble() const;
private:
struct Impl;
std::unique_ptr<Impl> impl;
char impl_storage[16788736];
};
} // namespace A64