From cc6d3147ff1f10d2ee2b0751cf799fc4cc1abbae Mon Sep 17 00:00:00 2001 From: Jan Vorlicek Date: Sat, 12 Jun 2021 09:54:58 +0200 Subject: [PATCH] Unify macOS ARM64 write protection holders with W^X ones (#54067) * Unify macOS ARM64 write protection holders with W^X ones This change removes the original holders that were added for changing memory protection for executable code and moves the actual switching to the recently added W^X holders. The unixexports files don't support target specific symbols. So I needed to export a dummy version of the PAL_JitWriteProtect for macOS x64. --- src/coreclr/debug/ee/controller.cpp | 29 ++++---- src/coreclr/debug/ee/debugger.cpp | 12 ++-- src/coreclr/debug/ee/debugger.h | 81 ++-------------------- src/coreclr/debug/inc/amd64/primitives.h | 10 ++- src/coreclr/debug/inc/arm/primitives.h | 6 +- src/coreclr/debug/inc/arm64/primitives.h | 6 +- src/coreclr/debug/inc/i386/primitives.h | 5 +- src/coreclr/dlls/mscordac/mscordac_unixexports.src | 1 + src/coreclr/inc/executableallocator.h | 11 ++- src/coreclr/inc/loaderheap.h | 8 --- src/coreclr/pal/inc/pal.h | 30 ++------ src/coreclr/pal/src/map/virtual.cpp | 31 +++++---- src/coreclr/vm/arm64/arm64singlestepper.cpp | 9 ++- src/coreclr/vm/arm64/asmhelpers.S | 4 +- src/coreclr/vm/arm64/asmhelpers.asm | 2 +- src/coreclr/vm/arm64/stubs.cpp | 47 ++----------- src/coreclr/vm/callcounting.cpp | 4 -- src/coreclr/vm/callhelpers.cpp | 4 -- src/coreclr/vm/ceemain.cpp | 4 -- src/coreclr/vm/codeman.cpp | 17 +---- src/coreclr/vm/comdelegate.cpp | 8 --- src/coreclr/vm/dllimportcallback.cpp | 14 ---- src/coreclr/vm/dllimportcallback.h | 8 --- src/coreclr/vm/dynamicmethod.cpp | 4 -- src/coreclr/vm/eventing/eventpipe/ep-rt-coreclr.h | 4 -- src/coreclr/vm/gccover.cpp | 3 - src/coreclr/vm/methoddescbackpatchinfo.cpp | 4 -- src/coreclr/vm/precode.cpp | 8 --- src/coreclr/vm/prestub.cpp | 8 --- src/coreclr/vm/threads.cpp | 15 ++-- src/coreclr/vm/threadsuspend.cpp | 4 -- src/coreclr/vm/virtualcallstub.cpp | 8 --- 32 files changed, 107 insertions(+), 302 deletions(-) diff --git a/src/coreclr/debug/ee/controller.cpp b/src/coreclr/debug/ee/controller.cpp index 01aedf5..eed3c45 100644 --- a/src/coreclr/debug/ee/controller.cpp +++ b/src/coreclr/debug/ee/controller.cpp @@ -83,7 +83,11 @@ SharedPatchBypassBuffer* DebuggerControllerPatch::GetOrCreateSharedPatchBypassBu if (m_pSharedPatchBypassBuffer == NULL) { - m_pSharedPatchBypassBuffer = new (interopsafeEXEC) SharedPatchBypassBuffer(); + void *pSharedPatchBypassBufferRX = g_pDebugger->GetInteropSafeExecutableHeap()->Alloc(sizeof(SharedPatchBypassBuffer)); + ExecutableWriterHolder sharedPatchBypassBufferWriterHolder((SharedPatchBypassBuffer*)pSharedPatchBypassBufferRX, sizeof(SharedPatchBypassBuffer)); + new (sharedPatchBypassBufferWriterHolder.GetRW()) SharedPatchBypassBuffer(); + m_pSharedPatchBypassBuffer = (SharedPatchBypassBuffer*)pSharedPatchBypassBufferRX; + _ASSERTE(m_pSharedPatchBypassBuffer); TRACE_ALLOC(m_pSharedPatchBypassBuffer); } @@ -1364,9 +1368,7 @@ bool DebuggerController::ApplyPatch(DebuggerControllerPatch *patch) LPVOID baseAddress = (LPVOID)(patch->address); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#else // defined(HOST_OSX) && defined(HOST_ARM64) +#if !defined(HOST_OSX) || !defined(HOST_ARM64) DWORD oldProt; if (!VirtualProtect(baseAddress, @@ -1376,7 +1378,7 @@ bool DebuggerController::ApplyPatch(DebuggerControllerPatch *patch) _ASSERTE(!"VirtualProtect of code page failed"); return false; } -#endif // defined(HOST_OSX) && defined(HOST_ARM64) +#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) patch->opcode = CORDbgGetInstruction(patch->address); @@ -1391,7 +1393,7 @@ bool DebuggerController::ApplyPatch(DebuggerControllerPatch *patch) _ASSERTE(!"VirtualProtect of code page failed"); return false; } -#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) +#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) } // TODO: : determine if this is needed for AMD64 #if defined(TARGET_X86) //REVISIT_TODO what is this?! @@ -1408,12 +1410,14 @@ bool DebuggerController::ApplyPatch(DebuggerControllerPatch *patch) _ASSERTE(!"VirtualProtect of code page failed"); return false; } + patch->opcode = (unsigned int) *(unsigned short*)(patch->address+1); _ASSERTE(patch->opcode != CEE_BREAK); - *(unsigned short *) (patch->address+1) = CEE_BREAK; + ExecutableWriterHolder breakpointWriterHolder((BYTE*)patch->address, 2); + *(unsigned short *) (breakpointWriterHolder.GetRW()+1) = CEE_BREAK; if (!VirtualProtect((void *) patch->address, 2, oldProt, &oldProt)) { @@ -1460,9 +1464,7 @@ bool DebuggerController::UnapplyPatch(DebuggerControllerPatch *patch) LPVOID baseAddress = (LPVOID)(patch->address); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#else // defined(HOST_OSX) && defined(HOST_ARM64) +#if !defined(HOST_OSX) || !defined(HOST_ARM64) DWORD oldProt; if (!VirtualProtect(baseAddress, @@ -1477,7 +1479,7 @@ bool DebuggerController::UnapplyPatch(DebuggerControllerPatch *patch) InitializePRD(&(patch->opcode)); return false; } -#endif // defined(HOST_OSX) && defined(HOST_ARM64) +#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) CORDbgSetInstruction((CORDB_ADDRESS_TYPE *)patch->address, patch->opcode); @@ -1494,7 +1496,7 @@ bool DebuggerController::UnapplyPatch(DebuggerControllerPatch *patch) _ASSERTE(!"VirtualProtect of code page failed"); return false; } -#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) +#endif // !defined(HOST_OSX) || !defined(HOST_ARM64) } else { @@ -1519,7 +1521,8 @@ bool DebuggerController::UnapplyPatch(DebuggerControllerPatch *patch) #if defined(TARGET_X86) _ASSERTE(*(unsigned short*)(patch->address+1) == CEE_BREAK); - *(unsigned short *) (patch->address+1) + ExecutableWriterHolder breakpointWriterHolder((BYTE*)patch->address, 2); + *(unsigned short *) (breakpointWriterHolder.GetRW()+1) = (unsigned short) patch->opcode; #endif //this makes no sense on anything but X86 //VERY IMPORTANT to zero out opcode, else we might mistake diff --git a/src/coreclr/debug/ee/debugger.cpp b/src/coreclr/debug/ee/debugger.cpp index d879136..4706790 100644 --- a/src/coreclr/debug/ee/debugger.cpp +++ b/src/coreclr/debug/ee/debugger.cpp @@ -67,7 +67,6 @@ bool g_EnableSIS = false; // The following instances are used for invoking overloaded new/delete InteropSafe interopsafe; -InteropSafeExecutable interopsafeEXEC; #ifndef DACCESS_COMPILE @@ -1316,16 +1315,15 @@ DebuggerEval::DebuggerEval(CONTEXT * pContext, DebuggerIPCE_FuncEvalInfo * pEval { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // Allocate the breakpoint instruction info in executable memory. - m_bpInfoSegment = new (interopsafeEXEC, nothrow) DebuggerEvalBreakpointInfoSegment(this); + void *bpInfoSegmentRX = g_pDebugger->GetInteropSafeExecutableHeap()->Alloc(sizeof(DebuggerEvalBreakpointInfoSegment)); + ExecutableWriterHolder bpInfoSegmentWriterHolder((DebuggerEvalBreakpointInfoSegment*)bpInfoSegmentRX, sizeof(DebuggerEvalBreakpointInfoSegment)); + new (bpInfoSegmentWriterHolder.GetRW()) DebuggerEvalBreakpointInfoSegment(this); + m_bpInfoSegment = (DebuggerEvalBreakpointInfoSegment*)bpInfoSegmentRX; // This must be non-zero so that the saved opcode is non-zero, and on IA64 we want it to be 0x16 // so that we can have a breakpoint instruction in any slot in the bundle. - m_bpInfoSegment->m_breakpointInstruction[0] = 0x16; + bpInfoSegmentWriterHolder.GetRW()->m_breakpointInstruction[0] = 0x16; #if defined(TARGET_ARM) USHORT *bp = (USHORT*)&m_bpInfoSegment->m_breakpointInstruction; *bp = CORDbg_BREAK_INSTRUCTION; diff --git a/src/coreclr/debug/ee/debugger.h b/src/coreclr/debug/ee/debugger.h index d661986..9d80fb3 100644 --- a/src/coreclr/debug/ee/debugger.h +++ b/src/coreclr/debug/ee/debugger.h @@ -1104,11 +1104,8 @@ struct DECLSPEC_ALIGN(4096) DebuggerHeapExecutableMemoryPage inline void SetNextPage(DebuggerHeapExecutableMemoryPage* nextPage) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - - chunks[0].bookkeeping.nextPage = nextPage; + ExecutableWriterHolder debuggerHeapPageWriterHolder(this, sizeof(DebuggerHeapExecutableMemoryPage)); + debuggerHeapPageWriterHolder.GetRW()->chunks[0].bookkeeping.nextPage = nextPage; } inline uint64_t GetPageOccupancy() const @@ -1118,14 +1115,11 @@ struct DECLSPEC_ALIGN(4096) DebuggerHeapExecutableMemoryPage inline void SetPageOccupancy(uint64_t newOccupancy) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // Can't unset first bit of occupancy! ASSERT((newOccupancy & 0x8000000000000000) != 0); - chunks[0].bookkeeping.pageOccupancy = newOccupancy; + ExecutableWriterHolder debuggerHeapPageWriterHolder(this, sizeof(DebuggerHeapExecutableMemoryPage)); + debuggerHeapPageWriterHolder.GetRW()->chunks[0].bookkeeping.pageOccupancy = newOccupancy; } inline void* GetPointerToChunk(int chunkNum) const @@ -1135,16 +1129,14 @@ struct DECLSPEC_ALIGN(4096) DebuggerHeapExecutableMemoryPage DebuggerHeapExecutableMemoryPage() { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) + ExecutableWriterHolder debuggerHeapPageWriterHolder(this, sizeof(DebuggerHeapExecutableMemoryPage)); SetPageOccupancy(0x8000000000000000); // only the first bit is set. for (uint8_t i = 1; i < sizeof(chunks)/sizeof(chunks[0]); i++) { ASSERT(i != 0); - chunks[i].data.startOfPage = this; - chunks[i].data.chunkNumber = i; + debuggerHeapPageWriterHolder.GetRW()->chunks[i].data.startOfPage = this; + debuggerHeapPageWriterHolder.GetRW()->chunks[i].data.chunkNumber = i; } } @@ -3486,9 +3478,6 @@ public: class InteropSafe {}; extern InteropSafe interopsafe; -class InteropSafeExecutable {}; -extern InteropSafeExecutable interopsafeEXEC; - #ifndef DACCESS_COMPILE inline void * __cdecl operator new(size_t n, const InteropSafe&) { @@ -3631,62 +3620,6 @@ template void DeleteInteropSafe(T *p) } } -inline void * __cdecl operator new(size_t n, const InteropSafeExecutable&) -{ - CONTRACTL - { - THROWS; // throw on OOM - GC_NOTRIGGER; - } - CONTRACTL_END; - - _ASSERTE(g_pDebugger != NULL); - void *result = g_pDebugger->GetInteropSafeExecutableHeap()->Alloc((DWORD)n); - if (result == NULL) { - ThrowOutOfMemory(); - } - return result; -} - -inline void * __cdecl operator new(size_t n, const InteropSafeExecutable&, const NoThrow&) throw() -{ - CONTRACTL - { - NOTHROW; - GC_NOTRIGGER; - } - CONTRACTL_END; - - _ASSERTE(g_pDebugger != NULL); - DebuggerHeap * pHeap = g_pDebugger->GetInteropSafeExecutableHeap_NoThrow(); - if (pHeap == NULL) - { - return NULL; - } - void *result = pHeap->Alloc((DWORD)n); - return result; -} - -// Note: there is no C++ syntax for manually invoking this, but if a constructor throws an exception I understand that -// this delete operator will be invoked automatically to destroy the object. -inline void __cdecl operator delete(void *p, const InteropSafeExecutable&) -{ - CONTRACTL - { - NOTHROW; - GC_NOTRIGGER; - } - CONTRACTL_END; - - if (p != NULL) - { - _ASSERTE(g_pDebugger != NULL); - DebuggerHeap * pHeap = g_pDebugger->GetInteropSafeExecutableHeap_NoThrow(); - _ASSERTE(pHeap != NULL); // should have had heap around if we're deleting - pHeap->Free(p); - } -} - // // Interop safe delete to match the interop safe new's above. There is no C++ syntax for actually invoking those interop // safe delete operators above, so we use this method to accomplish the same thing. diff --git a/src/coreclr/debug/inc/amd64/primitives.h b/src/coreclr/debug/inc/amd64/primitives.h index a119c2b..d42dc66 100644 --- a/src/coreclr/debug/inc/amd64/primitives.h +++ b/src/coreclr/debug/inc/amd64/primitives.h @@ -12,6 +12,8 @@ #ifndef PRIMITIVES_H_ #define PRIMITIVES_H_ +#include "executableallocator.h" + #ifndef CORDB_ADDRESS_TYPE typedef const BYTE CORDB_ADDRESS_TYPE; typedef DPTR(CORDB_ADDRESS_TYPE) PTR_CORDB_ADDRESS_TYPE; @@ -187,7 +189,9 @@ inline void CORDbgInsertBreakpoint(UNALIGNED CORDB_ADDRESS_TYPE *address) { LIMITED_METHOD_CONTRACT; - *((unsigned char*)address) = 0xCC; // int 3 (single byte patch) + ExecutableWriterHolder breakpointWriterHolder((LPVOID)address, CORDbg_BREAK_INSTRUCTION_SIZE); + + *((unsigned char*)breakpointWriterHolder.GetRW()) = 0xCC; // int 3 (single byte patch) FlushInstructionCache(GetCurrentProcess(), address, 1); } @@ -198,7 +202,9 @@ inline void CORDbgSetInstruction(UNALIGNED CORDB_ADDRESS_TYPE* address, // In a DAC build, this function assumes the input is an host address. LIMITED_METHOD_DAC_CONTRACT; - *((unsigned char*)address) = + ExecutableWriterHolder instructionWriterHolder((LPVOID)address, sizeof(unsigned char)); + + *((unsigned char*)instructionWriterHolder.GetRW()) = (unsigned char) instruction; // setting one byte is important FlushInstructionCache(GetCurrentProcess(), address, 1); diff --git a/src/coreclr/debug/inc/arm/primitives.h b/src/coreclr/debug/inc/arm/primitives.h index 269281e..eb29d83 100644 --- a/src/coreclr/debug/inc/arm/primitives.h +++ b/src/coreclr/debug/inc/arm/primitives.h @@ -12,6 +12,8 @@ #ifndef PRIMITIVES_H_ #define PRIMITIVES_H_ +#include "executableallocator.h" + #ifndef THUMB_CODE #define THUMB_CODE 1 #endif @@ -159,7 +161,9 @@ inline void CORDbgSetInstruction(CORDB_ADDRESS_TYPE* address, // In a DAC build, this function assumes the input is an host address. LIMITED_METHOD_DAC_CONTRACT; - CORDB_ADDRESS ptraddr = (CORDB_ADDRESS)address; + ExecutableWriterHolder instructionWriterHolder((LPVOID)address, sizeof(PRD_TYPE)); + + CORDB_ADDRESS ptraddr = (CORDB_ADDRESS)instructionWriterHolder.GetRW(); _ASSERTE(ptraddr & THUMB_CODE); ptraddr &= ~THUMB_CODE; diff --git a/src/coreclr/debug/inc/arm64/primitives.h b/src/coreclr/debug/inc/arm64/primitives.h index f359680..1fb1b9c 100644 --- a/src/coreclr/debug/inc/arm64/primitives.h +++ b/src/coreclr/debug/inc/arm64/primitives.h @@ -12,6 +12,8 @@ #ifndef PRIMITIVES_H_ #define PRIMITIVES_H_ +#include "executableallocator.h" + typedef NEON128 FPRegister64; typedef const BYTE CORDB_ADDRESS_TYPE; typedef DPTR(CORDB_ADDRESS_TYPE) PTR_CORDB_ADDRESS_TYPE; @@ -146,7 +148,9 @@ inline void CORDbgSetInstruction(CORDB_ADDRESS_TYPE* address, // In a DAC build, this function assumes the input is an host address. LIMITED_METHOD_DAC_CONTRACT; - ULONGLONG ptraddr = dac_cast(address); + ExecutableWriterHolder instructionWriterHolder((LPVOID)address, sizeof(PRD_TYPE)); + + ULONGLONG ptraddr = dac_cast(instructionWriterHolder.GetRW()); *(PRD_TYPE *)ptraddr = instruction; FlushInstructionCache(GetCurrentProcess(), address, diff --git a/src/coreclr/debug/inc/i386/primitives.h b/src/coreclr/debug/inc/i386/primitives.h index 980dc27..0c1d4bc 100644 --- a/src/coreclr/debug/inc/i386/primitives.h +++ b/src/coreclr/debug/inc/i386/primitives.h @@ -12,6 +12,7 @@ #ifndef PRIMITIVES_H_ #define PRIMITIVES_H_ +#include "executableallocator.h" typedef const BYTE CORDB_ADDRESS_TYPE; typedef DPTR(CORDB_ADDRESS_TYPE) PTR_CORDB_ADDRESS_TYPE; @@ -148,7 +149,9 @@ inline void CORDbgInsertBreakpoint(UNALIGNED CORDB_ADDRESS_TYPE *address) { LIMITED_METHOD_CONTRACT; - *((unsigned char*)address) = 0xCC; // int 3 (single byte patch) + ExecutableWriterHolder breakpointWriterHolder((LPVOID)address, CORDbg_BREAK_INSTRUCTION_SIZE); + + *((unsigned char*)breakpointWriterHolder.GetRW()) = 0xCC; // int 3 (single byte patch) FlushInstructionCache(GetCurrentProcess(), address, 1); } diff --git a/src/coreclr/dlls/mscordac/mscordac_unixexports.src b/src/coreclr/dlls/mscordac/mscordac_unixexports.src index 4fc0af3..aa7352b 100644 --- a/src/coreclr/dlls/mscordac/mscordac_unixexports.src +++ b/src/coreclr/dlls/mscordac/mscordac_unixexports.src @@ -70,6 +70,7 @@ nativeStringResourceTable_mscorrc #PAL__open #PAL__pread #PAL__close +#PAL_JitWriteProtect #_wcsicmp #_stricmp diff --git a/src/coreclr/inc/executableallocator.h b/src/coreclr/inc/executableallocator.h index 6a2cecd..c71f613 100644 --- a/src/coreclr/inc/executableallocator.h +++ b/src/coreclr/inc/executableallocator.h @@ -30,7 +30,13 @@ class ExecutableWriterHolder void Unmap() { - // TODO: this will be added with the double mapped allocator addition + if (m_addressRX != NULL) + { + // TODO: mapping / unmapping for targets using double memory mapping will be added with the double mapped allocator addition +#if defined(HOST_OSX) && defined(HOST_ARM64) + PAL_JitWriteProtect(false); +#endif + } } public: @@ -57,6 +63,9 @@ public: { m_addressRX = addressRX; m_addressRW = addressRX; +#if defined(HOST_OSX) && defined(HOST_ARM64) + PAL_JitWriteProtect(true); +#endif } ~ExecutableWriterHolder() diff --git a/src/coreclr/inc/loaderheap.h b/src/coreclr/inc/loaderheap.h index 2dc1565..ac0669a 100644 --- a/src/coreclr/inc/loaderheap.h +++ b/src/coreclr/inc/loaderheap.h @@ -554,10 +554,6 @@ private: { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - void *pResult; TaggedMemAllocPtr tmap; @@ -634,10 +630,6 @@ public: { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - CRITSEC_Holder csh(m_CriticalSection); diff --git a/src/coreclr/pal/inc/pal.h b/src/coreclr/pal/inc/pal.h index d22c9ba..69d9052 100644 --- a/src/coreclr/pal/inc/pal.h +++ b/src/coreclr/pal/inc/pal.h @@ -2760,32 +2760,14 @@ VirtualFree( IN SIZE_T dwSize, IN DWORD dwFreeType); -#if defined(HOST_OSX) && defined(HOST_ARM64) -#ifdef __cplusplus -extern "C++" { -struct PAL_JITWriteEnableHolder -{ -public: - PAL_JITWriteEnableHolder(bool jitWriteEnable) - { - m_jitWriteEnableRestore = JITWriteEnable(jitWriteEnable); - }; - ~PAL_JITWriteEnableHolder() - { - JITWriteEnable(m_jitWriteEnableRestore); - } +#if defined(HOST_OSX) -private: - bool JITWriteEnable(bool enable); - bool m_jitWriteEnableRestore; -}; +PALIMPORT +VOID +PALAPI +PAL_JitWriteProtect(bool writeEnable); -inline -PAL_JITWriteEnableHolder -PAL_JITWriteEnable(IN bool enable) { return PAL_JITWriteEnableHolder(enable); } -} -#endif // __cplusplus -#endif // defined(HOST_OSX) && defined(HOST_ARM64) +#endif // defined(HOST_OSX) PALIMPORT BOOL diff --git a/src/coreclr/pal/src/map/virtual.cpp b/src/coreclr/pal/src/map/virtual.cpp index cea55e8..9267f4f 100644 --- a/src/coreclr/pal/src/map/virtual.cpp +++ b/src/coreclr/pal/src/map/virtual.cpp @@ -1760,22 +1760,29 @@ ExitVirtualProtect: return bRetVal; } -#if defined(HOST_OSX) && defined(HOST_ARM64) -bool -PAL_JITWriteEnableHolder::JITWriteEnable(bool writeEnable) +#if defined(HOST_OSX) +PALAPI VOID PAL_JitWriteProtect(bool writeEnable) { - // Use a thread local to track per thread JIT Write enable state - // Per Apple, new threads start with MAP_JIT pages readable and executable (R-X) by default. - thread_local bool enabled = false; - bool result = enabled; - if (enabled != writeEnable) +#if defined(HOST_ARM64) + thread_local int enabledCount = 0; + if (writeEnable) { - pthread_jit_write_protect_np(writeEnable ? 0 : 1); - enabled = writeEnable; + if (enabledCount++ == 0) + { + pthread_jit_write_protect_np(0); + } + } + else + { + if (--enabledCount == 0) + { + pthread_jit_write_protect_np(1); + } + _ASSERTE(enabledCount >= 0); } - return result; +#endif // HOST_ARM64 } -#endif +#endif // HOST_OSX #if HAVE_VM_ALLOCATE //--------------------------------------------------------------------------------------- diff --git a/src/coreclr/vm/arm64/arm64singlestepper.cpp b/src/coreclr/vm/arm64/arm64singlestepper.cpp index 9ad5610..d459253 100644 --- a/src/coreclr/vm/arm64/arm64singlestepper.cpp +++ b/src/coreclr/vm/arm64/arm64singlestepper.cpp @@ -206,9 +206,8 @@ void Arm64SingleStepper::Apply(T_CONTEXT *pCtx) // control in the breakpoint fixup logic we can then reset the PC to its proper location. unsigned int idxNextInstruction = 0; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) + + ExecutableWriterHolder codeWriterHolder(m_rgCode, sizeof(m_rgCode)); if (TryEmulate(pCtx, opcode, false)) { @@ -220,11 +219,11 @@ void Arm64SingleStepper::Apply(T_CONTEXT *pCtx) { LOG((LF_CORDB, LL_INFO100000, "Arm64SingleStepper: Case 2: CopyInstruction.\n")); // Case 2: In all other cases copy the instruction to the buffer and we'll run it directly. - m_rgCode[idxNextInstruction++] = opcode; + codeWriterHolder.GetRW()[idxNextInstruction++] = opcode; } // Always terminate the redirection buffer with a breakpoint. - m_rgCode[idxNextInstruction++] = kBreakpointOp; + codeWriterHolder.GetRW()[idxNextInstruction++] = kBreakpointOp; _ASSERTE(idxNextInstruction <= kMaxCodeBuffer); // Set the thread up so it will redirect to our buffer when execution resumes. diff --git a/src/coreclr/vm/arm64/asmhelpers.S b/src/coreclr/vm/arm64/asmhelpers.S index 78790be..e6b47d0 100644 --- a/src/coreclr/vm/arm64/asmhelpers.S +++ b/src/coreclr/vm/arm64/asmhelpers.S @@ -213,7 +213,7 @@ LEAF_END ThePreStubPatch, _TEXT LEAF_END_MARKED \name, _TEXT .endm -// void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck) +// void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck, size_t writeableOffset) // // Update shadow copies of the various state info required for barrier // @@ -232,6 +232,7 @@ WRITE_BARRIER_ENTRY JIT_UpdateWriteBarrierState // x12 will be used for pointers mov x8, x0 + mov x9, x1 PREPARE_EXTERNAL_VAR g_card_table, x12 ldr x0, [x12] @@ -272,6 +273,7 @@ LOCAL_LABEL(EphemeralCheckEnabled): #ifdef FEATURE_WRITEBARRIER_COPY PREPARE_EXTERNAL_VAR JIT_WriteBarrier_Table_Loc, x12 ldr x12, [x12] + add x12, x12, x9 #else // FEATURE_WRITEBARRIER_COPY adr x12, LOCAL_LABEL(wbs_begin) #endif // FEATURE_WRITEBARRIER_COPY diff --git a/src/coreclr/vm/arm64/asmhelpers.asm b/src/coreclr/vm/arm64/asmhelpers.asm index 304a659..ffbeb9f 100644 --- a/src/coreclr/vm/arm64/asmhelpers.asm +++ b/src/coreclr/vm/arm64/asmhelpers.asm @@ -289,7 +289,7 @@ ThePreStubPatchLabel LEAF_END ;----------------------------------------------------------------------------- -; void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck) +; void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck, size_t writeableOffset) ; ; Update shadow copies of the various state info required for barrier ; diff --git a/src/coreclr/vm/arm64/stubs.cpp b/src/coreclr/vm/arm64/stubs.cpp index a9fbb6d..54cf1c4 100644 --- a/src/coreclr/vm/arm64/stubs.cpp +++ b/src/coreclr/vm/arm64/stubs.cpp @@ -571,10 +571,6 @@ void StubPrecode::Init(StubPrecode* pPrecodeRX, MethodDesc* pMD, LoaderAllocator { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - int n = 0; m_rgCode[n++] = 0x10000089; // adr x9, #16 @@ -608,10 +604,6 @@ void NDirectImportPrecode::Init(NDirectImportPrecode* pPrecodeRX, MethodDesc* pM { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - int n = 0; m_rgCode[n++] = 0x1000008B; // adr x11, #16 @@ -645,10 +637,6 @@ void FixupPrecode::Init(FixupPrecode* pPrecodeRX, MethodDesc* pMD, LoaderAllocat { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - InitCommon(); // Initialize chunk indices only if they are not initialized yet. This is necessary to make MethodDesc::Reset work. @@ -1071,15 +1059,16 @@ void JIT_TailCall() } #if !defined(DACCESS_COMPILE) && !defined(CROSSGEN_COMPILE) -EXTERN_C void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck); +EXTERN_C void JIT_UpdateWriteBarrierState(bool skipEphemeralCheck, size_t writeableOffset); + +extern "C" void STDCALL JIT_PatchedCodeStart(); +extern "C" void STDCALL JIT_PatchedCodeLast(); static void UpdateWriteBarrierState(bool skipEphemeralCheck) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - - JIT_UpdateWriteBarrierState(GCHeapUtilities::IsServerHeap()); + BYTE *writeBarrierCodeStart = GetWriteBarrierCodeLocation((void*)JIT_PatchedCodeStart); + ExecutableWriterHolder writeBarrierWriterHolder(writeBarrierCodeStart, (BYTE*)JIT_PatchedCodeLast - (BYTE*)JIT_PatchedCodeStart); + JIT_UpdateWriteBarrierState(GCHeapUtilities::IsServerHeap(), writeBarrierWriterHolder.GetRW() - writeBarrierCodeStart); } void InitJITHelpers1() @@ -1227,9 +1216,6 @@ UMEntryThunk * UMEntryThunk::Decode(void *pCallback) void UMEntryThunkCode::Encode(UMEntryThunkCode *pEntryThunkCodeRX, BYTE* pTargetCode, void* pvSecretParam) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) // adr x12, _label // ldp x16, x12, [x12] // br x16 @@ -1252,9 +1238,6 @@ void UMEntryThunkCode::Encode(UMEntryThunkCode *pEntryThunkCodeRX, BYTE* pTarget void UMEntryThunkCode::Poison() { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) ExecutableWriterHolder thunkWriterHolder(this, sizeof(UMEntryThunkCode)); UMEntryThunkCode *pThisRW = thunkWriterHolder.GetRW(); @@ -1867,21 +1850,6 @@ void StubLinkerCPU::EmitCallManagedMethod(MethodDesc *pMD, BOOL fTailCall) #define DYNAMIC_HELPER_ALIGNMENT sizeof(TADDR) -#if defined(HOST_OSX) && defined(HOST_ARM64) -#define BEGIN_DYNAMIC_HELPER_EMIT(size) \ - SIZE_T cb = size; \ - SIZE_T cbAligned = ALIGN_UP(cb, DYNAMIC_HELPER_ALIGNMENT); \ - BYTE * pStart = (BYTE *)(void *)pAllocator->GetDynamicHelpersHeap()->AllocAlignedMem(cbAligned, DYNAMIC_HELPER_ALIGNMENT); \ - BYTE * p = pStart; \ - static const size_t rxOffset = 0; \ - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); - -#define END_DYNAMIC_HELPER_EMIT() \ - _ASSERTE(pStart + cb == p); \ - while (p < pStart + cbAligned) { *(DWORD*)p = 0xBADC0DF0; p += 4; }\ - ClrFlushInstructionCache(pStart, cbAligned); \ - return (PCODE)pStart -#else // defined(HOST_OSX) && defined(HOST_ARM64) #define BEGIN_DYNAMIC_HELPER_EMIT(size) \ SIZE_T cb = size; \ SIZE_T cbAligned = ALIGN_UP(cb, DYNAMIC_HELPER_ALIGNMENT); \ @@ -1896,7 +1864,6 @@ void StubLinkerCPU::EmitCallManagedMethod(MethodDesc *pMD, BOOL fTailCall) while (p < pStart + cbAligned) { *(DWORD*)p = 0xBADC0DF0; p += 4; }\ ClrFlushInstructionCache(pStartRX, cbAligned); \ return (PCODE)pStartRX -#endif // defined(HOST_OSX) && defined(HOST_ARM64) // Uses x8 as scratch register to store address of data label // After load x8 is increment to point to next data diff --git a/src/coreclr/vm/callcounting.cpp b/src/coreclr/vm/callcounting.cpp index 80108bd..bdc4bc8 100644 --- a/src/coreclr/vm/callcounting.cpp +++ b/src/coreclr/vm/callcounting.cpp @@ -251,10 +251,6 @@ const CallCountingStub *CallCountingManager::CallCountingStubAllocator::Allocate } CONTRACTL_END; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - LoaderHeap *heap = m_heap; if (heap == nullptr) { diff --git a/src/coreclr/vm/callhelpers.cpp b/src/coreclr/vm/callhelpers.cpp index fa32e4e..1a1545d 100644 --- a/src/coreclr/vm/callhelpers.cpp +++ b/src/coreclr/vm/callhelpers.cpp @@ -62,10 +62,6 @@ void CallDescrWorkerWithHandler( #endif -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(false); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - BEGIN_CALL_TO_MANAGEDEX(fCriticalCall ? EEToManagedCriticalCall : EEToManagedDefault); CallDescrWorker(pCallDescrData); diff --git a/src/coreclr/vm/ceemain.cpp b/src/coreclr/vm/ceemain.cpp index 6ccf233..14e9dd9 100644 --- a/src/coreclr/vm/ceemain.cpp +++ b/src/coreclr/vm/ceemain.cpp @@ -984,10 +984,6 @@ void EEStartupHelper() Assembly::Initialize(); -#if defined(HOST_OSX) && defined(HOST_ARM64) - PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - SystemDomain::System()->Init(); #ifdef PROFILING_SUPPORTED diff --git a/src/coreclr/vm/codeman.cpp b/src/coreclr/vm/codeman.cpp index 0aabeda..171251a 100644 --- a/src/coreclr/vm/codeman.cpp +++ b/src/coreclr/vm/codeman.cpp @@ -1901,10 +1901,6 @@ TaggedMemAllocPtr CodeFragmentHeap::RealAllocAlignedMem(size_t dwRequestedSize { CrstHolder ch(&m_CritSec); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - dwRequestedSize = ALIGN_UP(dwRequestedSize, sizeof(TADDR)); // We will try to batch up allocation of small blocks into one large allocation @@ -1982,10 +1978,6 @@ void CodeFragmentHeap::RealBackoutMem(void *pMem CrstHolder ch(&m_CritSec); { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - ExecutableWriterHolder memWriterHolder((BYTE*)pMem, dwSize); ZeroMemory(memWriterHolder.GetRW(), dwSize); } @@ -2693,6 +2685,7 @@ void EEJitManager::allocCode(MethodDesc* pMD, size_t blockSize, size_t reserveFo pCodeHdr = ((CodeHeader *)pCode) - 1; *pAllocatedSize = sizeof(CodeHeader) + totalSize; +#define FEATURE_WXORX #ifdef FEATURE_WXORX pCodeHdrRW = (CodeHeader *)new BYTE[*pAllocatedSize]; #else @@ -3465,10 +3458,6 @@ void EEJitManager::CleanupCodeHeaps() HostCodeHeap *pHeap = m_cleanupList; m_cleanupList = NULL; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - while (pHeap) { HostCodeHeap *pNextHeap = pHeap->m_pNextHeapToRelease; @@ -4961,10 +4950,6 @@ void ExecutionManager::Unload(LoaderAllocator *pLoaderAllocator) GC_NOTRIGGER; } CONTRACTL_END; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // a size of 0 is a signal to Nirvana to flush the entire cache FlushInstructionCache(GetCurrentProcess(),0,0); diff --git a/src/coreclr/vm/comdelegate.cpp b/src/coreclr/vm/comdelegate.cpp index 599c75a..b6c1726 100644 --- a/src/coreclr/vm/comdelegate.cpp +++ b/src/coreclr/vm/comdelegate.cpp @@ -1046,10 +1046,6 @@ FCIMPL5(FC_BOOL_RET, COMDelegate::BindToMethodInfo, Object* refThisUNSAFE, Objec flags, &fIsOpenDelegate)) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // Initialize the delegate to point to the target method. BindToMethod(&gc.refThis, &gc.refFirstArg, @@ -1622,10 +1618,6 @@ FCIMPL3(void, COMDelegate::DelegateConstruct, Object* refThisUNSAFE, Object* tar // try to catch the easy garbage. _ASSERTE(isMemoryReadable(method, 1)); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - MethodTable *pMTTarg = NULL; if (gc.target != NULL) diff --git a/src/coreclr/vm/dllimportcallback.cpp b/src/coreclr/vm/dllimportcallback.cpp index 1420d18..4a88f81 100644 --- a/src/coreclr/vm/dllimportcallback.cpp +++ b/src/coreclr/vm/dllimportcallback.cpp @@ -74,10 +74,6 @@ public: CrstHolder ch(&m_crst); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - if (m_pHead == NULL) { m_pHead = pThunkRX; @@ -159,9 +155,6 @@ UMEntryThunk *UMEntryThunkCache::GetUMEntryThunk(MethodDesc *pMD) else { // cache miss -> create a new thunk -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) pThunk = UMEntryThunk::CreateUMEntryThunk(); Holder umHolder; umHolder.Assign(pThunk); @@ -284,9 +277,6 @@ void STDCALL UMEntryThunk::DoRunTimeInit(UMEntryThunk* pUMEntryThunk) { GCX_PREEMP(); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) ExecutableWriterHolder uMEntryThunkWriterHolder(pUMEntryThunk, sizeof(UMEntryThunk)); uMEntryThunkWriterHolder.GetRW()->RunTimeInit(pUMEntryThunk); } @@ -331,10 +321,6 @@ void UMEntryThunk::Terminate() if (GetObjectHandle()) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - DestroyLongWeakHandle(GetObjectHandle()); thunkWriterHolder.GetRW()->m_pObjectHandle = 0; } diff --git a/src/coreclr/vm/dllimportcallback.h b/src/coreclr/vm/dllimportcallback.h index f5c5d29..14b7db5 100644 --- a/src/coreclr/vm/dllimportcallback.h +++ b/src/coreclr/vm/dllimportcallback.h @@ -153,10 +153,6 @@ public: } CONTRACTL_END; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - m_pManagedTarget = pManagedTarget; m_pObjectHandle = pObjectHandle; m_pUMThunkMarshInfo = pUMThunkMarshInfo; @@ -189,10 +185,6 @@ public: m_code.Encode(&pUMEntryThunkRX->m_code, (BYTE*)m_pUMThunkMarshInfo->GetExecStubEntryPoint(), pUMEntryThunkRX); #ifdef _DEBUG -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - m_state = kRunTimeInited; #endif // _DEBUG } diff --git a/src/coreclr/vm/dynamicmethod.cpp b/src/coreclr/vm/dynamicmethod.cpp index 565243c..9dae86a 100644 --- a/src/coreclr/vm/dynamicmethod.cpp +++ b/src/coreclr/vm/dynamicmethod.cpp @@ -570,10 +570,6 @@ void HostCodeHeap::AddToFreeList(TrackAllocation *pBlockToInsert, TrackAllocatio LOG((LF_BCL, LL_INFO100, "Level2 - CodeHeap [0x%p] - Add to FreeList [%p, 0x%X]\n", this, pBlockToInsert, pBlockToInsert->size)); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // append to the list in the proper position and coalesce if needed if (m_pFreeList) { diff --git a/src/coreclr/vm/eventing/eventpipe/ep-rt-coreclr.h b/src/coreclr/vm/eventing/eventpipe/ep-rt-coreclr.h index 38d5598..be90259 100644 --- a/src/coreclr/vm/eventing/eventpipe/ep-rt-coreclr.h +++ b/src/coreclr/vm/eventing/eventpipe/ep-rt-coreclr.h @@ -1468,10 +1468,6 @@ void ep_rt_prepare_provider_invoke_callback (EventPipeProviderCallbackData *provider_callback_data) { STATIC_CONTRACT_NOTHROW; - -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(false); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) } static diff --git a/src/coreclr/vm/gccover.cpp b/src/coreclr/vm/gccover.cpp index 26c07ba..be856db 100644 --- a/src/coreclr/vm/gccover.cpp +++ b/src/coreclr/vm/gccover.cpp @@ -1256,9 +1256,6 @@ bool IsGcCoverageInterrupt(LPVOID ip) void RemoveGcCoverageInterrupt(TADDR instrPtr, BYTE * savedInstrPtr, GCCoverageInfo* gcCover, DWORD offset) { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) ExecutableWriterHolder instrPtrWriterHolder((void*)instrPtr, 4); #ifdef TARGET_ARM if (GetARMInstructionLength(savedInstrPtr) == 2) diff --git a/src/coreclr/vm/methoddescbackpatchinfo.cpp b/src/coreclr/vm/methoddescbackpatchinfo.cpp index 5a6bd15..94b4a1b 100644 --- a/src/coreclr/vm/methoddescbackpatchinfo.cpp +++ b/src/coreclr/vm/methoddescbackpatchinfo.cpp @@ -28,10 +28,6 @@ void EntryPointSlots::Backpatch_Locked(TADDR slot, SlotType slotType, PCODE entr _ASSERTE(entryPoint != NULL); _ASSERTE(IS_ALIGNED((SIZE_T)slot, GetRequiredSlotAlignment(slotType))); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - switch (slotType) { case SlotType_Normal: diff --git a/src/coreclr/vm/precode.cpp b/src/coreclr/vm/precode.cpp index 718b4cb..80731c1 100644 --- a/src/coreclr/vm/precode.cpp +++ b/src/coreclr/vm/precode.cpp @@ -405,10 +405,6 @@ void Precode::ResetTargetInterlocked() { WRAPPER_NO_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - PrecodeType precodeType = GetType(); switch (precodeType) { @@ -442,10 +438,6 @@ BOOL Precode::SetTargetInterlocked(PCODE target, BOOL fOnlyRedirectFromPrestub) if (fOnlyRedirectFromPrestub && !IsPointingToPrestub(expected)) return FALSE; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - g_IBCLogger.LogMethodPrecodeWriteAccess(GetMethodDesc()); PrecodeType precodeType = GetType(); diff --git a/src/coreclr/vm/prestub.cpp b/src/coreclr/vm/prestub.cpp index 41c83b0..f75d62b 100644 --- a/src/coreclr/vm/prestub.cpp +++ b/src/coreclr/vm/prestub.cpp @@ -326,10 +326,6 @@ PCODE MethodDesc::PrepareCode(PrepareCodeConfig* pConfig) { STANDARD_VM_CONTRACT; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // If other kinds of code need multi-versioning we could add more cases here, // but for now generation of all other code/stubs occurs in other code paths _ASSERTE(IsIL() || IsNoMetadata()); @@ -2034,10 +2030,6 @@ extern "C" PCODE STDCALL PreStubWorker(TransitionBlock* pTransitionBlock, Method GCX_PREEMP_THREAD_EXISTS(CURRENT_THREAD); { -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - pbRetVal = pMD->DoPrestub(pDispatchingMT, CallerGCMode::Coop); } diff --git a/src/coreclr/vm/threads.cpp b/src/coreclr/vm/threads.cpp index f6b9e89..ee66f3e 100644 --- a/src/coreclr/vm/threads.cpp +++ b/src/coreclr/vm/threads.cpp @@ -659,11 +659,6 @@ Thread* SetupThread() } #endif -#if defined(HOST_OSX) && defined(HOST_ARM64) - // Initialize new threads to JIT Write disabled - auto jitWriteEnableHolder = PAL_JITWriteEnable(false); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - // Normally, HasStarted is called from the thread's entrypoint to introduce it to // the runtime. But sometimes that thread is used for DLL_THREAD_ATTACH notifications // that call into managed code. In that case, a call to SetupThread here must @@ -1151,11 +1146,11 @@ void InitThreadManager() COMPlusThrowWin32(); } -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - - memcpy(s_barrierCopy, (BYTE*)JIT_PatchedCodeStart, (BYTE*)JIT_PatchedCodeLast - (BYTE*)JIT_PatchedCodeStart); + { + size_t writeBarrierSize = (BYTE*)JIT_PatchedCodeLast - (BYTE*)JIT_PatchedCodeStart; + ExecutableWriterHolder barrierWriterHolder(s_barrierCopy, writeBarrierSize); + memcpy(barrierWriterHolder.GetRW(), (BYTE*)JIT_PatchedCodeStart, writeBarrierSize); + } // Store the JIT_WriteBarrier copy location to a global variable so that helpers // can jump to it. diff --git a/src/coreclr/vm/threadsuspend.cpp b/src/coreclr/vm/threadsuspend.cpp index 6233386..d9d2c9b 100644 --- a/src/coreclr/vm/threadsuspend.cpp +++ b/src/coreclr/vm/threadsuspend.cpp @@ -3645,10 +3645,6 @@ void Thread::CommitGCStressInstructionUpdate() assert(pbDestCode != NULL); assert(pbSrcCode != NULL); -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - ExecutableWriterHolder destCodeWriterHolder(pbDestCode, sizeof(DWORD)); #if defined(TARGET_X86) || defined(TARGET_AMD64) diff --git a/src/coreclr/vm/virtualcallstub.cpp b/src/coreclr/vm/virtualcallstub.cpp index 94a5c59..95d568d 100644 --- a/src/coreclr/vm/virtualcallstub.cpp +++ b/src/coreclr/vm/virtualcallstub.cpp @@ -1725,10 +1725,6 @@ PCODE VirtualCallStubManager::ResolveWorker(StubCallSite* pCallSite, PRECONDITION(IsProtectedByGCFrame(protectedObj)); } CONTRACTL_END; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - MethodTable* objectType = (*protectedObj)->GetMethodTable(); CONSISTENCY_CHECK(CheckPointer(objectType)); @@ -2989,10 +2985,6 @@ LookupHolder *VirtualCallStubManager::GenerateLookupStub(PCODE addrOfResolver, s POSTCONDITION(CheckPointer(RETVAL)); } CONTRACT_END; -#if defined(HOST_OSX) && defined(HOST_ARM64) - auto jitWriteEnableHolder = PAL_JITWriteEnable(true); -#endif // defined(HOST_OSX) && defined(HOST_ARM64) - //allocate from the requisite heap and copy the template over it. LookupHolder * holder = (LookupHolder*) (void*) lookup_heap->AllocAlignedMem(sizeof(LookupHolder), CODE_SIZE_ALIGN); ExecutableWriterHolder lookupWriterHolder(holder, sizeof(LookupHolder)); -- 2.7.4