From 6af41edc29a791942588167d9f6a1fced3bfd402 Mon Sep 17 00:00:00 2001 From: Jan Kotas Date: Wed, 18 Oct 2017 02:38:55 -0700 Subject: [PATCH] Improve thread statics performance (#14560) - Disable code to handle multiple appdomains - Use more efficient object array accessor --- src/vm/appdomain.cpp | 16 -------- src/vm/ceeload.h | 12 ++++-- src/vm/corhost.cpp | 99 +++++++++++++++++--------------------------------- src/vm/object.h | 7 ++++ src/vm/threadstatics.h | 4 +- 5 files changed, 52 insertions(+), 86 deletions(-) diff --git a/src/vm/appdomain.cpp b/src/vm/appdomain.cpp index edcc3df..1fe8a96 100644 --- a/src/vm/appdomain.cpp +++ b/src/vm/appdomain.cpp @@ -11911,19 +11911,3 @@ void ZapperSetBindingPaths(ICorCompilationDomain *pDomain, SString &trustedPlatf } #endif - -#if !defined(CROSSGEN_COMPILE) -bool IsSingleAppDomain() -{ - STARTUP_FLAGS flags = CorHost2::GetStartupFlags(); - if(flags & STARTUP_SINGLE_APPDOMAIN) - return TRUE; - else - return FALSE; -} -#else -bool IsSingleAppDomain() -{ - return FALSE; -} -#endif diff --git a/src/vm/ceeload.h b/src/vm/ceeload.h index b70ea51..62facce 100644 --- a/src/vm/ceeload.h +++ b/src/vm/ceeload.h @@ -3101,8 +3101,10 @@ public: static BOOL IsEncodedModuleIndex(SIZE_T ModuleID) { LIMITED_METHOD_DAC_CONTRACT; - - return (ModuleID&1)==1; + + // We should never see encoded module index in CoreCLR + _ASSERTE((ModuleID&1)==0); + return FALSE; } static SIZE_T IndexToID(ModuleIndex index) @@ -3553,6 +3555,10 @@ struct VASigCookieEx : public VASigCookie const BYTE *m_pArgs; // pointer to first unfixed unmanaged arg }; -bool IsSingleAppDomain(); +inline bool IsSingleAppDomain() +{ + // CoreCLR always runs as single AppDomain + return true; +} #endif // !CEELOAD_H_ diff --git a/src/vm/corhost.cpp b/src/vm/corhost.cpp index b1e5a8a..7fe542e 100644 --- a/src/vm/corhost.cpp +++ b/src/vm/corhost.cpp @@ -564,13 +564,6 @@ HRESULT CorHost2::ExecuteInAppDomain(DWORD dwAppDomainId, return HOST_E_CLRNOTAVAILABLE; } - if(!(m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN)) - { - // Ensure that code is not loaded in the Default AppDomain - if (dwAppDomainId == DefaultADID) - return HOST_E_INVALIDOPERATION; - } - // Moved this here since no point validating the pointer // if the basic checks [above] fail if( pCallback == NULL) @@ -626,7 +619,7 @@ HRESULT CorHost2::_CreateAppDomain( HRESULT hr=S_OK; //cannot call the function more than once when single appDomain is allowed - if (m_fAppDomainCreated && (m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN)) + if (m_fAppDomainCreated) { return HOST_E_INVALIDOPERATION; } @@ -655,15 +648,7 @@ HRESULT CorHost2::_CreateAppDomain( AppDomainCreationHolder pDomain; - // If StartupFlag specifies single appDomain then return the default domain instead of creating new one - if(m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN) - { - pDomain.Assign(SystemDomain::System()->DefaultDomain()); - } - else - { - AppDomain::CreateUnmanagedObject(pDomain); - } + pDomain.Assign(SystemDomain::System()->DefaultDomain()); ETW::LoaderLog::DomainLoad(pDomain, (LPWSTR)wszFriendlyName); @@ -738,11 +723,7 @@ HRESULT CorHost2::_CreateAppDomain( *pAppDomainID=pDomain->GetId().m_dwId; - // If StartupFlag specifies single appDomain then set the flag that appdomain has already been created - if(m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN) - { - m_fAppDomainCreated = TRUE; - } + m_fAppDomainCreated = TRUE; } #ifdef PROFILING_SUPPORTED EX_HOOK @@ -815,13 +796,6 @@ HRESULT CorHost2::_CreateDelegate( if (!m_fStarted) return HOST_E_INVALIDOPERATION; - if(!(m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN)) - { - // Ensure that code is not loaded in the Default AppDomain - if (appDomainID == DefaultADID) - return HOST_E_INVALIDOPERATION; - } - BEGIN_ENTRYPOINT_NOTHROW; BEGIN_EXTERNAL_ENTRYPOINT(&hr); @@ -1180,57 +1154,52 @@ STDMETHODIMP CorHost2::UnloadAppDomain2(DWORD dwDomainId, BOOL fWaitUntilDone, i if (!m_fStarted) return HOST_E_INVALIDOPERATION; - if(m_dwStartupFlags & STARTUP_SINGLE_APPDOMAIN) + if (!g_fEEStarted) { - if (!g_fEEStarted) - { - return HOST_E_CLRNOTAVAILABLE; - } + return HOST_E_CLRNOTAVAILABLE; + } - if(!m_fAppDomainCreated) - { - return HOST_E_INVALIDOPERATION; - } + if(!m_fAppDomainCreated) + { + return HOST_E_INVALIDOPERATION; + } - HRESULT hr=S_OK; - BEGIN_ENTRYPOINT_NOTHROW; + HRESULT hr=S_OK; + BEGIN_ENTRYPOINT_NOTHROW; - if (!m_fFirstToLoadCLR) + if (!m_fFirstToLoadCLR) + { + _ASSERTE(!"Not reachable"); + hr = HOST_E_CLRNOTAVAILABLE; + } + else + { + LONG refCount = m_RefCount; + if (refCount == 0) { - _ASSERTE(!"Not reachable"); hr = HOST_E_CLRNOTAVAILABLE; } else + if (1 == refCount) { - LONG refCount = m_RefCount; - if (refCount == 0) - { - hr = HOST_E_CLRNOTAVAILABLE; - } - else - if (1 == refCount) - { - // Stop coreclr on unload. - m_fStarted = FALSE; - EEShutDown(FALSE); - } - else - { - _ASSERTE(!"Not reachable"); - hr = S_FALSE; - } + // Stop coreclr on unload. + m_fStarted = FALSE; + EEShutDown(FALSE); } - END_ENTRYPOINT_NOTHROW; - - if (pLatchedExitCode) + else { - *pLatchedExitCode = GetLatchedExitCode(); + _ASSERTE(!"Not reachable"); + hr = S_FALSE; } + } + END_ENTRYPOINT_NOTHROW; - return hr; + if (pLatchedExitCode) + { + *pLatchedExitCode = GetLatchedExitCode(); } - return CorRuntimeHostBase::UnloadAppDomain2(dwDomainId, fWaitUntilDone, pLatchedExitCode); + return hr; } HRESULT CorRuntimeHostBase::UnloadAppDomain(DWORD dwDomainId, BOOL fWaitUntilDone) diff --git a/src/vm/object.h b/src/vm/object.h index 20d7d50..7de739a 100644 --- a/src/vm/object.h +++ b/src/vm/object.h @@ -952,6 +952,13 @@ public: return GetMethodTable()->GetApproxArrayElementTypeHandle(); } + PTR_OBJECTREF GetDataPtr() + { + LIMITED_METHOD_CONTRACT; + SUPPORTS_DAC; + return dac_cast(dac_cast(this) + GetDataOffset()); + } + static SIZE_T GetDataOffset() { LIMITED_METHOD_CONTRACT; diff --git a/src/vm/threadstatics.h b/src/vm/threadstatics.h index bd52496..970f730 100644 --- a/src/vm/threadstatics.h +++ b/src/vm/threadstatics.h @@ -66,7 +66,7 @@ struct ThreadLocalModule _ASSERTE(m_pGCStatics != NULL); - return dac_cast((PTR_OBJECTREF)((PTRARRAYREF)ObjectFromHandle(m_pGCStatics))->GetDataPtr()); + return dac_cast(((PTRARRAYREF)ObjectFromHandle(m_pGCStatics))->GetDataPtr()); } inline PTR_BYTE GetGCStaticsBaseHandle() { @@ -125,7 +125,7 @@ struct ThreadLocalModule _ASSERTE(m_pGCStatics != NULL); - return (PTR_OBJECTREF)((PTRARRAYREF)ObjectFromHandle(m_pGCStatics))->GetDataPtr(); + return ((PTRARRAYREF)ObjectFromHandle(m_pGCStatics))->GetDataPtr(); } inline OBJECTHANDLE GetPrecomputedGCStaticsBaseHandle() -- 2.7.4