From 815819767c5794624e3e7bc2bebcabe8ea4de0f6 Mon Sep 17 00:00:00 2001 From: gdkchan Date: Tue, 7 Nov 2023 13:24:10 -0300 Subject: Force all exclusive memory accesses to be ordered on AppleHv (#5898) * Implement reprotect method on virtual memory manager (currently stubbed) * Force all exclusive memory accesses to be ordered on AppleHv * Format whitespace * Fix test build * Fix comment copy/paste * Fix wrong bit for isLoad * Update src/Ryujinx.Cpu/AppleHv/HvMemoryManager.cs Co-authored-by: riperiperi --------- Co-authored-by: riperiperi --- src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs | 62 ++++++++++++++++++++++++++++++++ 1 file changed, 62 insertions(+) create mode 100644 src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs (limited to 'src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs') diff --git a/src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs b/src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs new file mode 100644 index 00000000..876597b7 --- /dev/null +++ b/src/Ryujinx.Cpu/AppleHv/HvCodePatcher.cs @@ -0,0 +1,62 @@ +using System; +using System.Runtime.InteropServices; +using System.Runtime.Intrinsics; + +namespace Ryujinx.Cpu.AppleHv +{ + static class HvCodePatcher + { + private const uint XMask = 0x3f808000u; + private const uint XValue = 0x8000000u; + + private const uint ZrIndex = 31u; + + public static void RewriteUnorderedExclusiveInstructions(Span code) + { + Span codeUint = MemoryMarshal.Cast(code); + Span> codeVector = MemoryMarshal.Cast>(code); + + Vector128 mask = Vector128.Create(XMask); + Vector128 value = Vector128.Create(XValue); + + for (int index = 0; index < codeVector.Length; index++) + { + Vector128 v = codeVector[index]; + + if (Vector128.EqualsAny(Vector128.BitwiseAnd(v, mask), value)) + { + int baseIndex = index * 4; + + for (int instIndex = baseIndex; instIndex < baseIndex + 4; instIndex++) + { + ref uint inst = ref codeUint[instIndex]; + + if ((inst & XMask) != XValue) + { + continue; + } + + bool isPair = (inst & (1u << 21)) != 0; + bool isLoad = (inst & (1u << 22)) != 0; + + uint rt2 = (inst >> 10) & 0x1fu; + uint rs = (inst >> 16) & 0x1fu; + + if (isLoad && rs != ZrIndex) + { + continue; + } + + if (!isPair && rt2 != ZrIndex) + { + continue; + } + + // Set the ordered flag. + inst |= 1u << 15; + } + } + } + } + } +} -- cgit v1.2.3