| 361 | } |
| 362 | |
| 363 | void LockJITContext() { |
| 364 | uint32_t Expected = GetTLS().ControlWord().load(), New; |
| 365 | |
| 366 | // Spin until PAUSED is unset, setting IN_JIT when that occurs |
| 367 | do { |
| 368 | Expected = Expected & ~ControlBits::PAUSED; |
| 369 | New = (Expected | ControlBits::IN_JIT) & ~ControlBits::WOW_CPU_AREA_DIRTY; |
| 370 | } while (!GetTLS().ControlWord().compare_exchange_weak(Expected, New, std::memory_order::relaxed)); |
| 371 | std::atomic_signal_fence(std::memory_order::seq_cst); |
| 372 | |
| 373 | // If the CPU area is dirty, flush it to the JIT context before reentry |
| 374 | if (Expected & ControlBits::WOW_CPU_AREA_DIRTY) { |
| 375 | WOW64_CONTEXT* WowContext; |
| 376 | RtlWow64GetCurrentCpuArea(nullptr, reinterpret_cast<void**>(&WowContext), nullptr); |
| 377 | Context::LoadStateFromWowContext(GetTLS().ThreadState(), GetWowTEB(NtCurrentTeb()), WowContext); |
| 378 | } |
| 379 | } |
| 380 | |
| 381 | void UnlockJITContext() { |
| 382 | std::atomic_signal_fence(std::memory_order::seq_cst); |
no test coverage detected