Skip to content
This repository has been archived by the owner on Jan 23, 2023. It is now read-only.

[3.1] Protect against a rare invalid lock acquision attempt during etw processing during shutdown #27241

Merged
merged 3 commits into from
Oct 24, 2019
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 4 additions & 5 deletions src/vm/ceemain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1323,6 +1323,10 @@ void STDMETHODCALLTYPE EEShutDownHelper(BOOL fIsDllUnloading)

if (fIsDllUnloading)
{
// The process is detaching, so set the global state.
// This is used to get around FreeLibrary problems.
g_fProcessDetach = true;

ETW::EnumerationLog::ProcessShutdown();
}

Expand All @@ -1339,11 +1343,6 @@ void STDMETHODCALLTYPE EEShutDownHelper(BOOL fIsDllUnloading)
Thread * pThisThread = GetThread();
#endif

// If the process is detaching then set the global state.
// This is used to get around FreeLibrary problems.
if(fIsDllUnloading)
g_fProcessDetach = true;

if (IsDbgHelperSpecialThread())
{
// Our debugger helper thread does not allow Thread object to be set up.
Expand Down
8 changes: 7 additions & 1 deletion src/vm/prestub.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1197,7 +1197,13 @@ PrepareCodeConfig::JitOptimizationTier PrepareCodeConfig::GetJitOptimizationTier
_ASSERTE(methodDesc != nullptr);
_ASSERTE(config == nullptr || methodDesc == config->GetMethodDesc());

if (config != nullptr)
// The code inside this block may take one or more locks. If process detach has already occurred, then other threads would
// have already been abruptly terminated, which may have left locks orphaned, so it would not be feasible to attempt taking
// a lock on process detach. This function is called from ETW-related code on shutdown where unfortunately it processes and
// sends rundown events upon process detach. If process detach has already occurred, then resort to best-effort behavior
// that may return inaccurate information. This is a temporary and targeted fix for a clear problem, and should not be used
// long-term.
if (config != nullptr && !g_fProcessDetach)
{
if (config->JitSwitchedToMinOpt())
{
Expand Down