Merge pull request #3227 from MerryMage/cro
Allow for partial invalidation of instruction cache
This commit is contained in:
commit
d8ba07a430
|
@ -1 +1 @@
|
|||
Subproject commit f343c56268ef3f8fbed5bbc513fbc56430a47255
|
||||
Subproject commit 4110494ac4edc83f74c65834ab3ba6ddd166f42e
|
|
@ -4,6 +4,7 @@
|
|||
|
||||
#pragma once
|
||||
|
||||
#include <cstddef>
|
||||
#include "common/common_types.h"
|
||||
#include "core/arm/skyeye_common/arm_regformat.h"
|
||||
#include "core/arm/skyeye_common/vfp/asm_vfp.h"
|
||||
|
@ -33,6 +34,13 @@ public:
|
|||
/// Clear all instruction cache
|
||||
virtual void ClearInstructionCache() = 0;
|
||||
|
||||
/**
|
||||
* Invalidate the code cache at a range of addresses.
|
||||
* @param start_address The starting address of the range to invalidate.
|
||||
* @param length The length (in bytes) of the range to invalidate.
|
||||
*/
|
||||
virtual void InvalidateCacheRange(u32 start_address, size_t length) = 0;
|
||||
|
||||
/// Notify CPU emulation that page tables have changed
|
||||
virtual void PageTableChanged() = 0;
|
||||
|
||||
|
|
|
@ -187,6 +187,10 @@ void ARM_Dynarmic::ClearInstructionCache() {
|
|||
}
|
||||
}
|
||||
|
||||
void ARM_Dynarmic::InvalidateCacheRange(u32 start_address, size_t length) {
|
||||
jit->InvalidateCacheRange(start_address, length);
|
||||
}
|
||||
|
||||
void ARM_Dynarmic::PageTableChanged() {
|
||||
current_page_table = Memory::GetCurrentPageTable();
|
||||
|
||||
|
|
|
@ -41,6 +41,7 @@ public:
|
|||
void PrepareReschedule() override;
|
||||
|
||||
void ClearInstructionCache() override;
|
||||
void InvalidateCacheRange(u32 start_address, size_t length) override;
|
||||
void PageTableChanged() override;
|
||||
|
||||
private:
|
||||
|
|
|
@ -34,6 +34,10 @@ void ARM_DynCom::ClearInstructionCache() {
|
|||
trans_cache_buf_top = 0;
|
||||
}
|
||||
|
||||
void ARM_DynCom::InvalidateCacheRange(u32, size_t) {
|
||||
ClearInstructionCache();
|
||||
}
|
||||
|
||||
void ARM_DynCom::PageTableChanged() {
|
||||
ClearInstructionCache();
|
||||
}
|
||||
|
|
|
@ -19,6 +19,7 @@ public:
|
|||
void Step() override;
|
||||
|
||||
void ClearInstructionCache() override;
|
||||
void InvalidateCacheRange(u32 start_address, size_t length) override;
|
||||
void PageTableChanged() override;
|
||||
|
||||
void SetPC(u32 pc) override;
|
||||
|
|
|
@ -5,6 +5,8 @@
|
|||
#include "common/alignment.h"
|
||||
#include "common/logging/log.h"
|
||||
#include "common/scope_exit.h"
|
||||
#include "core/arm/arm_interface.h"
|
||||
#include "core/core.h"
|
||||
#include "core/hle/service/ldr_ro/cro_helper.h"
|
||||
|
||||
namespace Service {
|
||||
|
@ -61,9 +63,11 @@ ResultCode CROHelper::ApplyRelocation(VAddr target_address, RelocationType reloc
|
|||
case RelocationType::AbsoluteAddress:
|
||||
case RelocationType::AbsoluteAddress2:
|
||||
Memory::Write32(target_address, symbol_address + addend);
|
||||
Core::CPU().InvalidateCacheRange(target_address, sizeof(u32));
|
||||
break;
|
||||
case RelocationType::RelativeAddress:
|
||||
Memory::Write32(target_address, symbol_address + addend - target_future_address);
|
||||
Core::CPU().InvalidateCacheRange(target_address, sizeof(u32));
|
||||
break;
|
||||
case RelocationType::ThumbBranch:
|
||||
case RelocationType::ArmBranch:
|
||||
|
@ -86,6 +90,7 @@ ResultCode CROHelper::ClearRelocation(VAddr target_address, RelocationType reloc
|
|||
case RelocationType::AbsoluteAddress2:
|
||||
case RelocationType::RelativeAddress:
|
||||
Memory::Write32(target_address, 0);
|
||||
Core::CPU().InvalidateCacheRange(target_address, sizeof(u32));
|
||||
break;
|
||||
case RelocationType::ThumbBranch:
|
||||
case RelocationType::ArmBranch:
|
||||
|
|
|
@ -439,7 +439,7 @@ static void LoadCRO(Interface* self, bool link_on_load_bug_fix) {
|
|||
}
|
||||
}
|
||||
|
||||
Core::CPU().ClearInstructionCache();
|
||||
Core::CPU().InvalidateCacheRange(cro_address, cro_size);
|
||||
|
||||
LOG_INFO(Service_LDR, "CRO \"%s\" loaded at 0x%08X, fixed_end=0x%08X", cro.ModuleName().data(),
|
||||
cro_address, cro_address + fix_size);
|
||||
|
@ -535,7 +535,7 @@ static void UnloadCRO(Interface* self) {
|
|||
memory_synchronizer.RemoveMemoryBlock(cro_address, cro_buffer_ptr);
|
||||
}
|
||||
|
||||
Core::CPU().ClearInstructionCache();
|
||||
Core::CPU().InvalidateCacheRange(cro_address, fixed_size);
|
||||
|
||||
rb.Push(result);
|
||||
}
|
||||
|
@ -588,7 +588,6 @@ static void LinkCRO(Interface* self) {
|
|||
}
|
||||
|
||||
memory_synchronizer.SynchronizeOriginalMemory();
|
||||
Core::CPU().ClearInstructionCache();
|
||||
|
||||
rb.Push(result);
|
||||
}
|
||||
|
@ -641,7 +640,6 @@ static void UnlinkCRO(Interface* self) {
|
|||
}
|
||||
|
||||
memory_synchronizer.SynchronizeOriginalMemory();
|
||||
Core::CPU().ClearInstructionCache();
|
||||
|
||||
rb.Push(result);
|
||||
}
|
||||
|
|
Reference in New Issue