mirror of
https://git.eden-emu.dev/eden-emu/eden.git
synced 2026-08-31 18:46:08 +00:00
Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| 4e784cc82a | |||
| beee79a06d | |||
| be790d08f3 |
@@ -42,7 +42,7 @@ u64 DynarmicCallbacks32::MemoryRead64(u32 vaddr) {
|
||||
std::optional<u32> DynarmicCallbacks32::MemoryReadCode(u32 vaddr) {
|
||||
if (!m_memory.IsValidVirtualAddressRange(vaddr, sizeof(u32)))
|
||||
return std::nullopt;
|
||||
auto const aligned_vaddr = vaddr & ~Core::Memory::YUZU_PAGEMASK;
|
||||
auto const aligned_vaddr = vaddr & u32(~Core::Memory::YUZU_PAGEMASK);
|
||||
if (last_code_addr != aligned_vaddr) {
|
||||
m_memory.ReadBlock(aligned_vaddr, &cached_code_page, sizeof(cached_code_page));
|
||||
last_code_addr = aligned_vaddr;
|
||||
@@ -420,11 +420,13 @@ void ArmDynarmic32::SignalInterrupt(Kernel::KThread* thread) {
|
||||
}
|
||||
|
||||
void ArmDynarmic32::ClearInstructionCache() {
|
||||
m_cb->last_code_addr = u32(-1);
|
||||
m_jit->ClearCache();
|
||||
}
|
||||
|
||||
void ArmDynarmic32::InvalidateCacheRange(u64 addr, std::size_t size) {
|
||||
m_jit->InvalidateCacheRange(static_cast<u32>(addr), size);
|
||||
m_cb->last_code_addr = u32(-1);
|
||||
m_jit->InvalidateCacheRange(u32(addr), size);
|
||||
}
|
||||
|
||||
} // namespace Core
|
||||
|
||||
@@ -36,7 +36,7 @@ public:
|
||||
u64 MemoryRead64(u32 vaddr) override;
|
||||
std::optional<u32> MemoryReadCode(u32 vaddr) override;
|
||||
void InstructionSynchronizationBarrierRaised() override {
|
||||
last_code_addr = u64(-1); //reset back, force refetch
|
||||
last_code_addr = u32(-1); //reset back, force refetch
|
||||
}
|
||||
void MemoryWrite8(u32 vaddr, u8 value) override;
|
||||
void MemoryWrite16(u32 vaddr, u16 value) override;
|
||||
@@ -54,7 +54,7 @@ public:
|
||||
void ReturnException(u32 pc, Dynarmic::HaltReason hr);
|
||||
//
|
||||
Dynarmic::CodePage cached_code_page;
|
||||
u64 last_code_addr = u64(-1);
|
||||
u32 last_code_addr = u32(-1);
|
||||
ArmDynarmic32& m_parent;
|
||||
Core::Memory::Memory& m_memory;
|
||||
Kernel::KProcess* m_process{};
|
||||
|
||||
@@ -105,7 +105,7 @@ void DynarmicCallbacks64::InstructionCacheOperationRaised(Dynarmic::A64::Instruc
|
||||
last_code_addr = u64(-1); //invalidate cached page
|
||||
switch (op) {
|
||||
case Dynarmic::A64::InstructionCacheOperation::InvalidateByVAToPoU: {
|
||||
static constexpr u64 ICACHE_LINE_SIZE = 64;
|
||||
constexpr u64 ICACHE_LINE_SIZE = 64;
|
||||
const u64 cache_line_start = value & ~(ICACHE_LINE_SIZE - 1);
|
||||
m_parent.InvalidateCacheRange(cache_line_start, ICACHE_LINE_SIZE);
|
||||
break;
|
||||
@@ -447,10 +447,12 @@ void ArmDynarmic64::SignalInterrupt(Kernel::KThread* thread) {
|
||||
}
|
||||
|
||||
void ArmDynarmic64::ClearInstructionCache() {
|
||||
m_cb->last_code_addr = u64(-1);
|
||||
m_jit->ClearCache();
|
||||
}
|
||||
|
||||
void ArmDynarmic64::InvalidateCacheRange(u64 addr, std::size_t size) {
|
||||
m_cb->last_code_addr = u64(-1);
|
||||
m_jit->InvalidateCacheRange(addr, size);
|
||||
}
|
||||
|
||||
|
||||
@@ -76,34 +76,57 @@ void ProtectMemory(const void* base, size_t size, bool is_executable) {
|
||||
}
|
||||
#endif
|
||||
|
||||
static const HostFeature features = []() {
|
||||
HostFeature f{};
|
||||
HostFeature GetHostFeatures() {
|
||||
HostFeature features = {};
|
||||
#ifdef DYNARMIC_ENABLE_CPU_FEATURE_DETECTION
|
||||
using Cpu = Xbyak::util::Cpu;
|
||||
Xbyak::util::Cpu cpu_info{};
|
||||
if (cpu_info.has(Cpu::tSSSE3)) f |= HostFeature::SSSE3;
|
||||
if (cpu_info.has(Cpu::tSSE41)) f |= HostFeature::SSE41;
|
||||
if (cpu_info.has(Cpu::tSSE42)) f |= HostFeature::SSE42;
|
||||
if (cpu_info.has(Cpu::tAVX)) f |= HostFeature::AVX;
|
||||
if (cpu_info.has(Cpu::tAVX2)) f |= HostFeature::AVX2;
|
||||
if (cpu_info.has(Cpu::tAVX512F)) f |= HostFeature::AVX512F;
|
||||
if (cpu_info.has(Cpu::tAVX512CD)) f |= HostFeature::AVX512CD;
|
||||
if (cpu_info.has(Cpu::tAVX512VL)) f |= HostFeature::AVX512VL;
|
||||
if (cpu_info.has(Cpu::tAVX512BW)) f |= HostFeature::AVX512BW;
|
||||
if (cpu_info.has(Cpu::tAVX512DQ)) f |= HostFeature::AVX512DQ;
|
||||
if (cpu_info.has(Cpu::tAVX512_BITALG)) f |= HostFeature::AVX512BITALG;
|
||||
if (cpu_info.has(Cpu::tAVX512VBMI)) f |= HostFeature::AVX512VBMI;
|
||||
if (cpu_info.has(Cpu::tPCLMULQDQ)) f |= HostFeature::PCLMULQDQ;
|
||||
if (cpu_info.has(Cpu::tF16C)) f |= HostFeature::F16C;
|
||||
if (cpu_info.has(Cpu::tFMA)) f |= HostFeature::FMA;
|
||||
if (cpu_info.has(Cpu::tAESNI)) f |= HostFeature::AES;
|
||||
if (cpu_info.has(Cpu::tSHA)) f |= HostFeature::SHA;
|
||||
if (cpu_info.has(Cpu::tPOPCNT)) f |= HostFeature::POPCNT;
|
||||
if (cpu_info.has(Cpu::tBMI1)) f |= HostFeature::BMI1;
|
||||
if (cpu_info.has(Cpu::tBMI2)) f |= HostFeature::BMI2;
|
||||
if (cpu_info.has(Cpu::tLZCNT)) f |= HostFeature::LZCNT;
|
||||
if (cpu_info.has(Cpu::tGFNI)) f |= HostFeature::GFNI;
|
||||
if (cpu_info.has(Cpu::tWAITPKG)) f |= HostFeature::WAITPKG;
|
||||
if (cpu_info.has(Cpu::tSSSE3))
|
||||
features |= HostFeature::SSSE3;
|
||||
if (cpu_info.has(Cpu::tSSE41))
|
||||
features |= HostFeature::SSE41;
|
||||
if (cpu_info.has(Cpu::tSSE42))
|
||||
features |= HostFeature::SSE42;
|
||||
if (cpu_info.has(Cpu::tAVX))
|
||||
features |= HostFeature::AVX;
|
||||
if (cpu_info.has(Cpu::tAVX2))
|
||||
features |= HostFeature::AVX2;
|
||||
if (cpu_info.has(Cpu::tAVX512F))
|
||||
features |= HostFeature::AVX512F;
|
||||
if (cpu_info.has(Cpu::tAVX512CD))
|
||||
features |= HostFeature::AVX512CD;
|
||||
if (cpu_info.has(Cpu::tAVX512VL))
|
||||
features |= HostFeature::AVX512VL;
|
||||
if (cpu_info.has(Cpu::tAVX512BW))
|
||||
features |= HostFeature::AVX512BW;
|
||||
if (cpu_info.has(Cpu::tAVX512DQ))
|
||||
features |= HostFeature::AVX512DQ;
|
||||
if (cpu_info.has(Cpu::tAVX512_BITALG))
|
||||
features |= HostFeature::AVX512BITALG;
|
||||
if (cpu_info.has(Cpu::tAVX512VBMI))
|
||||
features |= HostFeature::AVX512VBMI;
|
||||
if (cpu_info.has(Cpu::tPCLMULQDQ))
|
||||
features |= HostFeature::PCLMULQDQ;
|
||||
if (cpu_info.has(Cpu::tF16C))
|
||||
features |= HostFeature::F16C;
|
||||
if (cpu_info.has(Cpu::tFMA))
|
||||
features |= HostFeature::FMA;
|
||||
if (cpu_info.has(Cpu::tAESNI))
|
||||
features |= HostFeature::AES;
|
||||
if (cpu_info.has(Cpu::tSHA))
|
||||
features |= HostFeature::SHA;
|
||||
if (cpu_info.has(Cpu::tPOPCNT))
|
||||
features |= HostFeature::POPCNT;
|
||||
if (cpu_info.has(Cpu::tBMI1))
|
||||
features |= HostFeature::BMI1;
|
||||
if (cpu_info.has(Cpu::tBMI2))
|
||||
features |= HostFeature::BMI2;
|
||||
if (cpu_info.has(Cpu::tLZCNT))
|
||||
features |= HostFeature::LZCNT;
|
||||
if (cpu_info.has(Cpu::tGFNI))
|
||||
features |= HostFeature::GFNI;
|
||||
if (cpu_info.has(Cpu::tWAITPKG))
|
||||
features |= HostFeature::WAITPKG;
|
||||
if (cpu_info.has(Cpu::tBMI2)) {
|
||||
// BMI2 instructions such as pdep and pext have been very slow up until Zen 3.
|
||||
// Check for Zen 3 or newer by its family (0x19).
|
||||
@@ -115,15 +138,12 @@ static const HostFeature features = []() {
|
||||
const u32 family_extended = mcl::bit::get_bits<20, 27>(data[0]);
|
||||
const u32 family = family_base + family_extended;
|
||||
if (family >= 0x19)
|
||||
f |= HostFeature::FastBMI2;
|
||||
features |= HostFeature::FastBMI2;
|
||||
} else {
|
||||
f |= HostFeature::FastBMI2;
|
||||
features |= HostFeature::FastBMI2;
|
||||
}
|
||||
}
|
||||
return f;
|
||||
#endif
|
||||
}();
|
||||
HostFeature GetHostFeatures() {
|
||||
return features;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user