summaryrefslogtreecommitdiff
path: root/src/vm
diff options
context:
space:
mode:
authorantofik <antofik@gmail.com>2018-01-22 05:03:51 +0300
committerJan Kotas <jkotas@microsoft.com>2018-01-21 18:03:51 -0800
commit59714b683f40fac869050ca08acc5503e84dc776 (patch)
tree1512f4562d579977288002abb6432b32a2df2e8f /src/vm
parent3bd16103e76fbad8de7a37cb37f6a6f74ce46dfd (diff)
downloadcoreclr-59714b683f40fac869050ca08acc5503e84dc776.tar.gz
coreclr-59714b683f40fac869050ca08acc5503e84dc776.tar.bz2
coreclr-59714b683f40fac869050ca08acc5503e84dc776.zip
Remove AppDomainLeaks configuration option (#15956)
Removed all usages of AppDomainLeaks configuration option and CHECK_APP_DOMAIN_LEAKS feature Fix #12094
Diffstat (limited to 'src/vm')
-rw-r--r--src/vm/amd64/JitHelpers_Fast.asm16
-rw-r--r--src/vm/amd64/jithelpers_fast.S16
-rw-r--r--src/vm/appdomain.cpp15
-rw-r--r--src/vm/appdomain.hpp4
-rw-r--r--src/vm/arm/stubs.cpp5
-rw-r--r--src/vm/array.cpp2
-rw-r--r--src/vm/callhelpers.cpp25
-rw-r--r--src/vm/class.cpp4
-rw-r--r--src/vm/class.h8
-rw-r--r--src/vm/clrex.cpp29
-rw-r--r--src/vm/common.h4
-rw-r--r--src/vm/excep.cpp15
-rw-r--r--src/vm/field.cpp4
-rw-r--r--src/vm/field.h2
-rw-r--r--src/vm/finalizerthread.cpp7
-rw-r--r--src/vm/frames.cpp4
-rw-r--r--src/vm/gcenv.ee.common.cpp4
-rw-r--r--src/vm/gchandleutilities.cpp13
-rw-r--r--src/vm/gchelpers.cpp20
-rw-r--r--src/vm/gcinfodecoder.cpp4
-rw-r--r--src/vm/i386/jitinterfacex86.cpp112
-rw-r--r--src/vm/jithelpers.cpp49
-rw-r--r--src/vm/jitinterface.cpp18
-rw-r--r--src/vm/methodtablebuilder.cpp2
-rw-r--r--src/vm/object.cpp1013
-rw-r--r--src/vm/object.h187
-rw-r--r--src/vm/olevariant.cpp16
-rw-r--r--src/vm/syncblk.cpp57
-rw-r--r--src/vm/syncblk.h42
-rw-r--r--src/vm/typehandle.cpp4
-rw-r--r--src/vm/typehandle.h2
31 files changed, 12 insertions, 1691 deletions
diff --git a/src/vm/amd64/JitHelpers_Fast.asm b/src/vm/amd64/JitHelpers_Fast.asm
index 5e0d79f74f..6b94c66782 100644
--- a/src/vm/amd64/JitHelpers_Fast.asm
+++ b/src/vm/amd64/JitHelpers_Fast.asm
@@ -754,22 +754,6 @@ LEAF_ENTRY JIT_Stelem_Ref, _TEXT
test r8, r8
jz AssigningNull
-ifdef CHECK_APP_DOMAIN_LEAKS
- ; get Array TypeHandle
- mov r9, [r10 + OFFSETOF__MethodTable__m_ElementType] ; 10h -> typehandle offset
- ; check for non-MT
- test r9, 2
- jnz NoCheck
-
- ; Check VMflags of element type
- mov r9, [r9 + OFFSETOF__MethodTable__m_pEEClass]
- mov r9d, dword ptr [r9 + OFFSETOF__EEClass__m_wAuxFlags]
- test r9d, EEClassFlags
- jnz ArrayStoreCheck_Helper
-
- NoCheck:
-endif
-
mov r9, [r10 + OFFSETOF__MethodTable__m_ElementType] ; 10h -> typehandle offset
; check for exact match
diff --git a/src/vm/amd64/jithelpers_fast.S b/src/vm/amd64/jithelpers_fast.S
index 0ec63f7c5c..63b54297a6 100644
--- a/src/vm/amd64/jithelpers_fast.S
+++ b/src/vm/amd64/jithelpers_fast.S
@@ -410,22 +410,6 @@ LEAF_ENTRY JIT_Stelem_Ref, _TEXT
test rdx, rdx
jz LOCAL_LABEL(AssigningNull)
-#ifdef CHECK_APP_DOMAIN_LEAKS
- // get Array TypeHandle
- mov rcx, [r10 + OFFSETOF__MethodTable__m_ElementType] // 10h -> typehandle offset,
- // check for non-MT
- test rcx, 2
- jnz LOCAL_LABEL(NoCheck)
-
- // Check VMflags of element type
- mov rcx, [rcx + OFFSETOF__MethodTable__m_pEEClass]
- mov ecx, dword ptr [rcx + OFFSETOF__EEClass__m_wAuxFlags]
- test ecx, EEClassFlags
- jnz C_FUNC(ArrayStoreCheck_Helper)
-
- LOCAL_LABEL(NoCheck):
-#endif
-
mov rcx, [r10 + OFFSETOF__MethodTable__m_ElementType] // 10h -> typehandle offset
// check for exact match
diff --git a/src/vm/appdomain.cpp b/src/vm/appdomain.cpp
index bab3f65c02..96fd088c03 100644
--- a/src/vm/appdomain.cpp
+++ b/src/vm/appdomain.cpp
@@ -2292,9 +2292,6 @@ void SystemDomain::PreallocateSpecialObjects()
_ASSERTE(g_pPreallocatedSentinelObject == NULL);
OBJECTREF pPreallocatedSentinalObject = AllocateObject(g_pObjectClass);
-#if CHECK_APP_DOMAIN_LEAKS
- pPreallocatedSentinalObject->SetSyncBlockAppDomainAgile();
-#endif
g_pPreallocatedSentinelObject = CreatePinningHandle( pPreallocatedSentinalObject );
#ifdef FEATURE_PREJIT
@@ -2346,9 +2343,6 @@ void SystemDomain::CreatePreallocatedExceptions()
EXCEPTIONREF pRudeAbortException = (EXCEPTIONREF)AllocateObject(g_pThreadAbortExceptionClass);
-#if CHECK_APP_DOMAIN_LEAKS
- pRudeAbortException->SetSyncBlockAppDomainAgile();
-#endif
pRudeAbortException->SetHResult(COR_E_THREADABORTED);
pRudeAbortException->SetXCode(EXCEPTION_COMPLUS);
_ASSERTE(g_pPreallocatedRudeThreadAbortException == NULL);
@@ -2356,9 +2350,6 @@ void SystemDomain::CreatePreallocatedExceptions()
EXCEPTIONREF pAbortException = (EXCEPTIONREF)AllocateObject(g_pThreadAbortExceptionClass);
-#if CHECK_APP_DOMAIN_LEAKS
- pAbortException->SetSyncBlockAppDomainAgile();
-#endif
pAbortException->SetHResult(COR_E_THREADABORTED);
pAbortException->SetXCode(EXCEPTION_COMPLUS);
_ASSERTE(g_pPreallocatedThreadAbortException == NULL);
@@ -8200,12 +8191,6 @@ void AppDomain::Close()
LOG((LF_APPDOMAIN | LF_CORDB, LL_INFO10, "AppDomain::Domain [%d] %#08x %ls is collected.\n",
GetId().m_dwId, this, GetFriendlyNameForLogging()));
-
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- // at this point shouldn't have any non-agile objects in the heap because we finalized all the non-agile ones.
- SyncBlockCache::GetSyncBlockCache()->CheckForUnloadedInstances(GetIndex());
-#endif // CHECK_APP_DOMAIN_LEAKS
{
GCX_PREEMP();
RemoveMemoryPressure();
diff --git a/src/vm/appdomain.hpp b/src/vm/appdomain.hpp
index ea1c471759..d92aabb535 100644
--- a/src/vm/appdomain.hpp
+++ b/src/vm/appdomain.hpp
@@ -1290,10 +1290,6 @@ public:
OBJECTHANDLE CreatePinningHandle(OBJECTREF object)
{
WRAPPER_NO_CONTRACT;
-#if CHECK_APP_DOMAIN_LEAKS
- if(IsAppDomain())
- object->TryAssignAppDomain((AppDomain*)this,TRUE);
-#endif
return ::CreatePinningHandle(m_handleStore, object);
}
diff --git a/src/vm/arm/stubs.cpp b/src/vm/arm/stubs.cpp
index 7e5b58c54b..38009167e3 100644
--- a/src/vm/arm/stubs.cpp
+++ b/src/vm/arm/stubs.cpp
@@ -2512,11 +2512,6 @@ void InitJITHelpers1()
{
STANDARD_VM_CONTRACT;
-#if CHECK_APP_DOMAIN_LEAKS
- if(g_pConfig->AppDomainLeaks())
- SetJitHelperFunction(CORINFO_HELP_ARRADDR_ST, JIT_Stelem_Ref_Portable);
-#endif
-
// Allocation helpers, faster but non-logging.
if (!(TrackAllocationsEnabled()
|| LoggingOn(LF_GCALLOC, LL_INFO10)
diff --git a/src/vm/array.cpp b/src/vm/array.cpp
index 3a33aff43a..08a86a39d7 100644
--- a/src/vm/array.cpp
+++ b/src/vm/array.cpp
@@ -432,7 +432,7 @@ MethodTable* Module::CreateArrayMethodTable(TypeHandle elemTypeHnd, CorElementTy
pClass->SetArrayElementType (elemType);
pClass->SetMethodTable (pMT);
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
// Non-covariant arrays of agile types are agile
if (elemType != ELEMENT_TYPE_CLASS && elemTypeHnd.IsAppDomainAgile())
pClass->SetAppDomainAgile();
diff --git a/src/vm/callhelpers.cpp b/src/vm/callhelpers.cpp
index c575ee615d..c555751c23 100644
--- a/src/vm/callhelpers.cpp
+++ b/src/vm/callhelpers.cpp
@@ -418,20 +418,6 @@ void MethodDescCallSite::CallTargetWorker(const ARG_SLOT *pArguments, ARG_SLOT *
}
#endif // DEBUGGING_SUPPORTED
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- {
- // See if we are in the correct domain to call on the object
- if (m_methodSig.HasThis() && !m_pMD->GetMethodTable()->IsValueType())
- {
- CONTRACT_VIOLATION(ThrowsViolation|GCViolation|FaultViolation);
- OBJECTREF pThis = ArgSlotToObj(pArguments[0]);
- if (!pThis->AssignAppDomain(GetAppDomain()))
- _ASSERTE(!"Attempt to call method on object in wrong domain");
- }
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
#ifdef _DEBUG
{
#ifdef FEATURE_UNIX_AMD64_STRUCT_PASSING
@@ -547,17 +533,6 @@ void MethodDescCallSite::CallTargetWorker(const ARG_SLOT *pArguments, ARG_SLOT *
}
#endif
-#if CHECK_APP_DOMAIN_LEAKS
- // Make sure the arg is in the right app domain
- if (g_pConfig->AppDomainLeaks() && m_argIt.GetArgType() == ELEMENT_TYPE_CLASS)
- {
- CONTRACT_VIOLATION(ThrowsViolation|GCViolation|FaultViolation);
- OBJECTREF objRef = ArgSlotToObj(pArguments[arg]);
- if (!objRef->AssignAppDomain(GetAppDomain()))
- _ASSERTE(!"Attempt to pass object in wrong app domain to method");
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
ArgDestination argDest(pTransitionBlock, ofs, m_argIt.GetArgLocDescForStructInRegs());
UINT32 stackSize = m_argIt.GetArgSize();
diff --git a/src/vm/class.cpp b/src/vm/class.cpp
index 99156ffb59..ea02ca7bd9 100644
--- a/src/vm/class.cpp
+++ b/src/vm/class.cpp
@@ -1034,7 +1034,7 @@ CorElementType EEClass::ComputeInternalCorElementTypeForValueType(MethodTable *
return ELEMENT_TYPE_VALUETYPE;
}
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
//*******************************************************************************
void EEClass::GetPredefinedAgility(Module *pModule, mdTypeDef td,
BOOL *pfIsAgile, BOOL *pfCheckAgile)
@@ -1506,7 +1506,7 @@ exit:
LOG((LF_CLASSLOADER, LL_INFO1000, "CLASSLOADER: AppDomainAgileAttribute for %s is %d\n", pClass->GetDebugClassName(), pClass->IsAppDomainAgile()));
pClass->SetAppDomainAgilityDone();
}
-#endif // defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#endif // defined(_DEBUG)
//*******************************************************************************
//
diff --git a/src/vm/class.h b/src/vm/class.h
index 8bbbf55b9b..5e349f75b1 100644
--- a/src/vm/class.h
+++ b/src/vm/class.h
@@ -1793,7 +1793,7 @@ public:
SigPointer sp,
CorGenericParamAttr position);
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
public:
enum{
AUXFLAG_APP_DOMAIN_AGILE = 0x00000001,
@@ -1890,7 +1890,7 @@ public:
static void SetAppDomainAgileAttribute(MethodTable * pMT);
static void GetPredefinedAgility(Module *pModule, mdTypeDef td, BOOL *pfIsAgile, BOOL *pfIsCheckAgile);
-#endif // defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#endif // defined(_DEBUG)
//-------------------------------------------------------------
// CONCRETE DATA LAYOUT
@@ -2033,10 +2033,10 @@ private:
DWORD m_VMFlags;
/*
- * We maintain some auxillary flags in DEBUG or CHECK_APP_DOMAIN_LEAKS builds,
+ * We maintain some auxillary flags in DEBUG builds,
* this frees up some bits in m_wVMFlags
*/
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
WORD m_wAuxFlags;
#endif
diff --git a/src/vm/clrex.cpp b/src/vm/clrex.cpp
index 3b21d649d6..930ac5d6d1 100644
--- a/src/vm/clrex.cpp
+++ b/src/vm/clrex.cpp
@@ -2527,35 +2527,6 @@ CLRLastThrownObjectException* CLRLastThrownObjectException::Validate()
"To suppress this assert 'set COMPlus_SuppressLostExceptionTypeAssert=1'");
}
}
- else
- { // If there IS a LastThrownObject, then, for
- // exceptions other than the pre-allocated ones...
- if (!CLRException::IsPreallocatedExceptionObject(throwable))
- { // ...check that the exception is from the current appdomain.
-#if CHECK_APP_DOMAIN_LEAKS
- if (!throwable->CheckAppDomain(GetAppDomain()))
- { // We've lost track of the exception's type. Raise an assert. (This is configurable to allow
- // stress labs to turn off the assert.)
-
- static int iSuppress = -1;
- if (iSuppress == -1)
- iSuppress = CLRConfig::GetConfigValue(CLRConfig::INTERNAL_SuppressLostExceptionTypeAssert);
- if (!iSuppress)
- {
- // Raising an assert message can cause a mode violation.
- CONTRACT_VIOLATION(ModeViolation);
-
- // Use DbgAssertDialog to get the formatting right.
- DbgAssertDialog(__FILE__, __LINE__,
- "The 'LastThrownObject' does not belong to the current appdomain.\n"
- "The runtime may have lost track of the type of an exception in flight.\n"
- "Please get a good stack trace, find the caller of Validate, and file a bug against the owner.\n\n"
- "To suppress this assert 'set COMPlus_SuppressLostExceptionTypeAssert=1'");
- }
- }
-#endif
- }
- }
GCPROTECT_END();
diff --git a/src/vm/common.h b/src/vm/common.h
index 54ebf362c9..1008533ddd 100644
--- a/src/vm/common.h
+++ b/src/vm/common.h
@@ -265,10 +265,6 @@ FORCEINLINE void* memcpyUnsafe(void *dest, const void *src, size_t len)
extern "C" void * __cdecl GCSafeMemCpy(void *, const void *, size_t);
#define memcpy(dest, src, len) GCSafeMemCpy(dest, src, len)
#endif // !defined(memcpy)
-
- #if !defined(CHECK_APP_DOMAIN_LEAKS)
- #define CHECK_APP_DOMAIN_LEAKS 1
- #endif
#else // !_DEBUG && !DACCESS_COMPILE && !CROSSGEN_COMPILE
FORCEINLINE void* memcpyNoGCRefs(void * dest, const void * src, size_t len) {
WRAPPER_NO_CONTRACT;
diff --git a/src/vm/excep.cpp b/src/vm/excep.cpp
index 7e182dc787..35a207457c 100644
--- a/src/vm/excep.cpp
+++ b/src/vm/excep.cpp
@@ -2931,21 +2931,6 @@ VOID DECLSPEC_NORETURN RaiseTheExceptionInternalOnly(OBJECTREF throwable, BOOL r
_ASSERTE(param.pThread);
param.pExState = param.pThread->GetExceptionState();
- // Make sure that the object being thrown belongs in the current appdomain.
- #if defined(_DEBUG) && CHECK_APP_DOMAIN_LEAKS
- if (param.throwable != NULL)
- {
- GCPROTECT_BEGIN(param.throwable);
- if (!CLRException::IsPreallocatedExceptionObject(param.throwable))
- _ASSERTE(param.throwable->CheckAppDomain(GetAppDomain()));
- GCPROTECT_END();
- }
- else
- { // throwable is NULL -- that shouldn't happen
- _ASSERTE(NingenEnabled() || param.throwable != NULL);
- }
- #endif
-
if (param.pThread->IsRudeAbortInitiated())
{
// Nobody should be able to swallow rude thread abort.
diff --git a/src/vm/field.cpp b/src/vm/field.cpp
index defccd7269..78cb7f5bd0 100644
--- a/src/vm/field.cpp
+++ b/src/vm/field.cpp
@@ -62,10 +62,6 @@ VOID FieldDesc::Init(mdFieldDef mb, CorElementType FieldType, DWORD dwMemberAttr
m_debugName = (LPUTF8)pszFieldName;
#endif
-#if CHECK_APP_DOMAIN_LEAKS
- m_isDangerousAppDomainAgileField = 0;
-#endif
-
_ASSERTE(GetMemberDef() == mb); // no truncation
_ASSERTE(GetFieldType() == FieldType);
_ASSERTE(GetFieldProtection() == (fdFieldAccessMask & dwMemberAttrs));
diff --git a/src/vm/field.h b/src/vm/field.h
index 52b9d682cd..8d5b17fb71 100644
--- a/src/vm/field.h
+++ b/src/vm/field.h
@@ -313,7 +313,7 @@ public:
);
}
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
BOOL IsDangerousAppDomainAgileField()
{
LIMITED_METHOD_CONTRACT;
diff --git a/src/vm/finalizerthread.cpp b/src/vm/finalizerthread.cpp
index 2955decbd7..7d9e8abba8 100644
--- a/src/vm/finalizerthread.cpp
+++ b/src/vm/finalizerthread.cpp
@@ -147,13 +147,6 @@ Object * FinalizerThread::DoOneFinalization(Object* fobj, Thread* pThread,int bi
{
// if can't get into domain to finalize it, then it must be agile so finalize in current domain
targetAppDomain = currentDomain;
-#if CHECK_APP_DOMAIN_LEAKS
- {
- // object must be agile if can't get into it's domain
- if (g_pConfig->AppDomainLeaks() && !fobj->TrySetAppDomainAgile(FALSE))
- _ASSERTE(!"Found non-agile GC object which should have been finalized during app domain unload.");
- }
-#endif
}
if (targetAppDomain == currentDomain)
diff --git a/src/vm/frames.cpp b/src/vm/frames.cpp
index d7210fc3ff..38815bf757 100644
--- a/src/vm/frames.cpp
+++ b/src/vm/frames.cpp
@@ -41,11 +41,7 @@
#include "argdestination.h"
-#if CHECK_APP_DOMAIN_LEAKS
-#define CHECK_APP_DOMAIN GC_CALL_CHECK_APP_DOMAIN
-#else
#define CHECK_APP_DOMAIN 0
-#endif
//-----------------------------------------------------------------------
#if _DEBUG
diff --git a/src/vm/gcenv.ee.common.cpp b/src/vm/gcenv.ee.common.cpp
index ca7349091f..6ec5735e2c 100644
--- a/src/vm/gcenv.ee.common.cpp
+++ b/src/vm/gcenv.ee.common.cpp
@@ -191,10 +191,6 @@ StackWalkAction GcStackCrawlCallBack(CrawlFrame* pCF, VOID* pData)
Frame *pFrame;
GCCONTEXT *gcctx = (GCCONTEXT*) pData;
-#if CHECK_APP_DOMAIN_LEAKS
- gcctx->sc->pCurrentDomain = pCF->GetAppDomain();
-#endif //CHECK_APP_DOMAIN_LEAKS
-
#ifdef FEATURE_APPDOMAIN_RESOURCE_MONITORING
if (g_fEnableARM)
{
diff --git a/src/vm/gchandleutilities.cpp b/src/vm/gchandleutilities.cpp
index 7433945951..9345a18429 100644
--- a/src/vm/gchandleutilities.cpp
+++ b/src/vm/gchandleutilities.cpp
@@ -20,19 +20,6 @@ void ValidateObjectAndAppDomain(OBJECTREF objRef, ADIndex appDomainIndex)
assert(domain != nullptr);
assert(!domain->NoAccessToHandleTable());
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks() && objRef != NULL)
- {
- if (appDomainIndex.m_dwIndex)
- {
- objRef->TryAssignAppDomain(domain);
- }
- else
- {
- objRef->TrySetAppDomainAgile();
- }
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
#endif // _DEBUG_IMPL
}
diff --git a/src/vm/gchelpers.cpp b/src/vm/gchelpers.cpp
index 046f06e2d5..4684edeaf5 100644
--- a/src/vm/gchelpers.cpp
+++ b/src/vm/gchelpers.cpp
@@ -628,11 +628,6 @@ OBJECTREF AllocateArrayEx(MethodTable *pArrayMT, INT32 *pArgs, DWORD dwNumArgs,
orArray = (ArrayBase *) OBJECTREFToObject(objref);
#endif
-#if CHECK_APP_DOMAIN_LEAKS
- if (!bDontSetAppDomain && g_pConfig->AppDomainLeaks())
- orArray->SetAppDomain();
-#endif
-
if (kind == ELEMENT_TYPE_ARRAY)
{
INT32 *pCountsPtr = (INT32 *) orArray->GetBoundsPtr();
@@ -859,11 +854,6 @@ OBJECTREF FastAllocatePrimitiveArray(MethodTable* pMT, DWORD cElements, BOOL b
g_IBCLogger.LogMethodTableAccess(pMT);
LogAlloc(totalSize, pMT, orObject);
-
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- orObject->SetAppDomain();
-#endif
return( ObjectToOBJECTREF((Object*)orObject) );
}
@@ -1066,11 +1056,6 @@ STRINGREF SlowAllocateString( DWORD cchStringLength )
LogAlloc(ObjectSize, g_pStringClass, orObject);
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- orObject->SetAppDomain();
-#endif
-
return( ObjectToSTRINGREF(orObject) );
}
@@ -1187,11 +1172,6 @@ OBJECTREF AllocateObject(MethodTable *pMT
orObject->SetMethodTable(pMT);
}
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- orObject->SetAppDomain();
- else
-#endif
if (pMT->HasFinalizer())
orObject->SetAppDomain();
diff --git a/src/vm/gcinfodecoder.cpp b/src/vm/gcinfodecoder.cpp
index 7c0881c880..558247c9bf 100644
--- a/src/vm/gcinfodecoder.cpp
+++ b/src/vm/gcinfodecoder.cpp
@@ -10,12 +10,8 @@
#ifdef USE_GC_INFO_DECODER
#ifndef CHECK_APP_DOMAIN
-#if CHECK_APP_DOMAIN_LEAKS
-#define CHECK_APP_DOMAIN GC_CALL_CHECK_APP_DOMAIN
-#else
#define CHECK_APP_DOMAIN 0
#endif
-#endif
#ifndef GCINFODECODER_CONTRACT
#define GCINFODECODER_CONTRACT LIMITED_METHOD_CONTRACT
diff --git a/src/vm/i386/jitinterfacex86.cpp b/src/vm/i386/jitinterfacex86.cpp
index 3994c2e216..642c417598 100644
--- a/src/vm/i386/jitinterfacex86.cpp
+++ b/src/vm/i386/jitinterfacex86.cpp
@@ -58,11 +58,6 @@ private:
static void EmitDummyObject(CPUSTUBLINKER *psl, X86Reg regTestAlign, Flags flags);
static void EmitCore(CPUSTUBLINKER *psl, CodeLabel *noLock, CodeLabel *noAlloc, Flags flags);
static void EmitNoAllocCode(CPUSTUBLINKER *psl, Flags flags);
-
-#if CHECK_APP_DOMAIN_LEAKS
- static void EmitSetAppDomain(CPUSTUBLINKER *psl);
- static void EmitCheckRestore(CPUSTUBLINKER *psl);
-#endif
};
extern "C" LONG g_global_alloc_lock;
@@ -113,10 +108,6 @@ __declspec(naked) void F_CALL_CONV JIT_Stelem_Ref(PtrArray* array, unsigned idx,
STATIC_CONTRACT_GC_TRIGGERS;
enum { CanCast = TypeHandle::CanCast,
-#if CHECK_APP_DOMAIN_LEAKS
- EEClassFlags = EEClass::AUXFLAG_APP_DOMAIN_AGILE |
- EEClass::AUXFLAG_CHECK_APP_DOMAIN_AGILE,
-#endif // CHECK_APP_DOMAIN_LEAKS
};
__asm {
@@ -131,25 +122,6 @@ __declspec(naked) void F_CALL_CONV JIT_Stelem_Ref(PtrArray* array, unsigned idx,
test EAX, EAX
jz Assigning0
-#if CHECK_APP_DOMAIN_LEAKS
- mov EAX,[g_pConfig]
- movzx EAX, [EAX]EEConfig.fAppDomainLeaks;
- test EAX, EAX
- jz NoCheck
- // Check if the instance is agile or check agile
- mov EAX, [ECX]
- mov EAX, [EAX]MethodTable.m_ElementTypeHnd
- test EAX, 2 // Check for non-MT
- jnz NoCheck
- // Check VMflags of element type
- mov EAX, [EAX]MethodTable.m_pEEClass
- mov EAX, dword ptr [EAX]EEClass.m_wAuxFlags
- test EAX, EEClassFlags
- jnz NeedFrame // Jump to the generic case so we can do an app domain check
- NoCheck:
- mov EAX, [ESP+4] // EAX = val
-#endif // CHECK_APP_DOMAIN_LEAKS
-
push EDX
mov EDX, [ECX]
mov EDX, [EDX]MethodTable.m_ElementTypeHnd
@@ -192,9 +164,6 @@ NotExactMatch:
cmp EAX, CanCast
je DoWrite
-#if CHECK_APP_DOMAIN_LEAKS
-NeedFrame:
-#endif
// Call the helper that knows how to erect a frame
push EDX
push ECX
@@ -424,21 +393,6 @@ void STDCALL JIT_TailCallHelper(Thread * pThread)
}
#endif // FEATURE_HIJACK
-#if CHECK_APP_DOMAIN_LEAKS
-HCIMPL1(void *, SetObjectAppDomain, Object *pObject)
-{
- FCALL_CONTRACT;
- DEBUG_ONLY_FUNCTION;
-
- HELPER_METHOD_FRAME_BEGIN_RET_ATTRIB_NOPOLL(Frame::FRAME_ATTR_CAPTURE_DEPTH_2|Frame::FRAME_ATTR_EXACT_DEPTH|Frame::FRAME_ATTR_NO_THREAD_ABORT);
- pObject->SetAppDomain();
- HELPER_METHOD_FRAME_END();
-
- return pObject;
-}
-HCIMPLEND
-#endif // CHECK_APP_DOMAIN_LEAKS
-
// emit code that adds MIN_OBJECT_SIZE to reg if reg is unaligned thus making it aligned
void JIT_TrialAlloc::EmitAlignmentRoundup(CPUSTUBLINKER *psl, X86Reg testAlignReg, X86Reg adjReg, Flags flags)
{
@@ -497,10 +451,6 @@ void JIT_TrialAlloc::EmitDummyObject(CPUSTUBLINKER *psl, X86Reg alignTestReg, Fl
// mov [EAX], EDX
psl->X86EmitOffsetModRM(0x89, kEDX, kEAX, 0);
-#if CHECK_APP_DOMAIN_LEAKS
- EmitSetAppDomain(psl);
-#endif
-
// add EAX, MIN_OBJECT_SIZE
psl->X86EmitAddReg(kEAX, MIN_OBJECT_SIZE);
@@ -652,52 +602,6 @@ void JIT_TrialAlloc::EmitCore(CPUSTUBLINKER *psl, CodeLabel *noLock, CodeLabel *
#endif // INCREMENTAL_MEMCLR
}
-#if CHECK_APP_DOMAIN_LEAKS
-void JIT_TrialAlloc::EmitSetAppDomain(CPUSTUBLINKER *psl)
-{
- STANDARD_VM_CONTRACT;
-
- if (!g_pConfig->AppDomainLeaks())
- return;
-
- // At both entry & exit, eax contains the allocated object.
- // ecx is preserved, edx is not.
-
- //
- // Add in a call to SetAppDomain. (Note that this
- // probably would have been easier to implement by just not using
- // the generated helpers in a checked build, but we'd lose code
- // coverage that way.)
- //
-
- // Save ECX over function call
- psl->X86EmitPushReg(kECX);
-
-#ifdef UNIX_X86_ABI
-#define STACK_ALIGN_PADDING 8
- // sub esp, STACK_ALIGN_PADDING; to align the stack
- psl->X86EmitSubEsp(STACK_ALIGN_PADDING);
-#endif // UNIX_X86_ABI
-
- // mov object to ECX
- // mov ecx, eax
- psl->Emit16(0xc88b);
-
- // SetObjectAppDomain pops its arg & returns object in EAX
- psl->X86EmitCall(psl->NewExternalCodeLabel((LPVOID)SetObjectAppDomain), 4);
-
-#ifdef UNIX_X86_ABI
- // add esp, STACK_ALIGN_PADDING
- psl->X86EmitAddEsp(STACK_ALIGN_PADDING);
-#undef STACK_ALIGN_PADDING
-#endif // UNIX_X86_ABI
-
- psl->X86EmitPopReg(kECX);
-}
-
-#endif // CHECK_APP_DOMAIN_LEAKS
-
-
void JIT_TrialAlloc::EmitNoAllocCode(CPUSTUBLINKER *psl, Flags flags)
{
STANDARD_VM_CONTRACT;
@@ -728,10 +632,6 @@ void *JIT_TrialAlloc::GenAllocSFast(Flags flags)
// Emit the main body of the trial allocator, be it SP or MP
EmitCore(&sl, noLock, noAlloc, flags);
-#if CHECK_APP_DOMAIN_LEAKS
- EmitSetAppDomain(&sl);
-#endif
-
// Here we are at the end of the success case - just emit a ret
sl.X86EmitReturn(0);
@@ -786,10 +686,6 @@ void *JIT_TrialAlloc::GenBox(Flags flags)
// Emit the main body of the trial allocator
EmitCore(&sl, noLock, noAlloc, flags);
-#if CHECK_APP_DOMAIN_LEAKS
- EmitSetAppDomain(&sl);
-#endif
-
// Here we are at the end of the success case
// Check whether the object contains pointers
@@ -1082,10 +978,6 @@ void *JIT_TrialAlloc::GenAllocArray(Flags flags)
// mov dword ptr [eax]ArrayBase.m_NumComponents, edx
sl.X86EmitIndexRegStore(kEAX, offsetof(ArrayBase,m_NumComponents), kEDX);
-#if CHECK_APP_DOMAIN_LEAKS
- EmitSetAppDomain(&sl);
-#endif
-
// no stack parameters
sl.X86EmitReturn(0);
@@ -1198,10 +1090,6 @@ void *JIT_TrialAlloc::GenAllocString(Flags flags)
// mov dword ptr [eax]ArrayBase.m_StringLength, ecx
sl.X86EmitIndexRegStore(kEAX, offsetof(StringObject,m_StringLength), kECX);
-#if CHECK_APP_DOMAIN_LEAKS
- EmitSetAppDomain(&sl);
-#endif
-
// no stack parameters
sl.X86EmitReturn(0);
diff --git a/src/vm/jithelpers.cpp b/src/vm/jithelpers.cpp
index 9f887e6616..48b8b94808 100644
--- a/src/vm/jithelpers.cpp
+++ b/src/vm/jithelpers.cpp
@@ -2777,13 +2777,6 @@ HCIMPL1(Object*, JIT_NewS_MP_FastPortable, CORINFO_CLASS_HANDLE typeHnd_)
_ASSERTE(object->HasEmptySyncBlockInfo());
object->SetMethodTable(methodTable);
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- {
- object->SetAppDomain();
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
return object;
} while (false);
@@ -2880,13 +2873,6 @@ HCIMPL1(StringObject*, AllocateString_MP_FastPortable, DWORD stringLength)
stringObject->SetStringLength(stringLength);
_ASSERTE(stringObject->GetBuffer()[stringLength] == W('\0'));
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- {
- stringObject->SetAppDomain();
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
return stringObject;
} while (false);
@@ -3055,13 +3041,6 @@ HCIMPL2(Object*, JIT_NewArr1VC_MP_FastPortable, CORINFO_CLASS_HANDLE arrayMT, IN
_ASSERTE(static_cast<DWORD>(componentCount) == componentCount);
array->m_NumComponents = static_cast<DWORD>(componentCount);
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- {
- array->SetAppDomain();
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
return array;
} while (false);
@@ -3121,13 +3100,6 @@ HCIMPL2(Object*, JIT_NewArr1OBJ_MP_FastPortable, CORINFO_CLASS_HANDLE arrayMT, I
_ASSERTE(static_cast<DWORD>(componentCount) == componentCount);
array->m_NumComponents = static_cast<DWORD>(componentCount);
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- {
- array->SetAppDomain();
- }
-#endif // CHECK_APP_DOMAIN_LEAKS
-
return array;
} while (false);
@@ -3369,11 +3341,6 @@ HCIMPL2(LPVOID, ArrayStoreCheck, Object** pElement, PtrArray** pArray)
GCStress<cfg_any, EeconfigFastGcSPolicy>::MaybeTrigger();
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->AppDomainLeaks())
- (*pElement)->AssignAppDomain((*pArray)->GetAppDomain());
-#endif // CHECK_APP_DOMAIN_LEAKS
-
if (!ObjIsInstanceOf(*pElement, (*pArray)->GetArrayElementTypeHandle()))
COMPlusThrow(kArrayTypeMismatchException);
@@ -3404,22 +3371,6 @@ HCIMPL3(void, JIT_Stelem_Ref_Portable, PtrArray* array, unsigned idx, Object *va
MethodTable *valMT = val->GetMethodTable();
TypeHandle arrayElemTH = array->GetArrayElementTypeHandle();
-#if CHECK_APP_DOMAIN_LEAKS
- // If the instance is agile or check agile
- if (g_pConfig->AppDomainLeaks() && !arrayElemTH.IsAppDomainAgile() && !arrayElemTH.IsCheckAppDomainAgile())
- {
- // FCALL_CONTRACT increase ForbidGC count. Normally, HELPER_METHOD_FRAME macros decrease the count.
- // But to avoid perf hit, we manually decrease the count here before calling another HCCALL.
- ENDFORBIDGC();
-
- if (HCCALL2(ArrayStoreCheck,(Object**)&val, (PtrArray**)&array) != NULL)
- {
- // This return is never executed. It helps epilog walker to find its way out.
- return;
- }
- }
- else
-#endif
if (arrayElemTH != TypeHandle(valMT) && arrayElemTH != TypeHandle(g_pObjectClass))
{
TypeHandle::CastResult result = ObjIsInstanceOfNoGC(val, arrayElemTH);
diff --git a/src/vm/jitinterface.cpp b/src/vm/jitinterface.cpp
index 5340e2ddb0..874beae85b 100644
--- a/src/vm/jitinterface.cpp
+++ b/src/vm/jitinterface.cpp
@@ -1645,24 +1645,6 @@ void CEEInfo::getFieldInfo (CORINFO_RESOLVED_TOKEN * pResolvedToken,
{
BOOL fInstanceHelper = FALSE;
-#if CHECK_APP_DOMAIN_LEAKS
- if (g_pConfig->EnableFullDebug()
- && pField->IsDangerousAppDomainAgileField()
- && CorTypeInfo::IsObjRef(pField->GetFieldType()))
- {
- //
- // In a checked field with all checks turned on, we use a helper to enforce the app domain
- // agile invariant.
- //
- // <REVISIT_TODO>@todo: we'd like to check this for value type fields as well - we
- // just need to add some code to iterate through the fields for
- // references during the assignment.
- // </REVISIT_TODO>
- fInstanceHelper = TRUE;
- }
- else
-#endif // CHECK_APP_DOMAIN_LEAKS
-
if (fInstanceHelper)
{
if (flags & CORINFO_ACCESS_ADDRESS)
diff --git a/src/vm/methodtablebuilder.cpp b/src/vm/methodtablebuilder.cpp
index 725fb2d863..1a6b39af5c 100644
--- a/src/vm/methodtablebuilder.cpp
+++ b/src/vm/methodtablebuilder.cpp
@@ -1904,7 +1904,7 @@ MethodTableBuilder::BuildMethodTableThrowing(
SetFinalizationSemantics();
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
// Figure out if we're domain agile..
// Note that this checks a bunch of field directly on the class & method table,
// so it needs to come late in the game.
diff --git a/src/vm/object.cpp b/src/vm/object.cpp
index 32d066c708..aff6a835ae 100644
--- a/src/vm/object.cpp
+++ b/src/vm/object.cpp
@@ -422,38 +422,6 @@ AppDomain *Object::GetAppDomain()
return NULL;
AppDomain *pDomain = SystemDomain::TestGetAppDomainAtIndex(index);
-
-#if CHECK_APP_DOMAIN_LEAKS
- if (! g_pConfig->AppDomainLeaks())
- return pDomain;
-
- if (IsAppDomainAgile())
- return NULL;
-
- //
- // If an object has an index of an unloaded domain (its ok to be of a
- // domain where an unload is in progress through), go ahead
- // and make it agile. If this fails, we have an invalid reference
- // to an unloaded domain. If it succeeds, the object is no longer
- // contained in that app domain so we can continue.
- //
-
- if (pDomain == NULL)
- {
- if (SystemDomain::IndexOfAppDomainBeingUnloaded() == index) {
- // if appdomain is unloading but still alive and is valid to have instances
- // in that domain, then use it.
- AppDomain *tmpDomain = SystemDomain::AppDomainBeingUnloaded();
- if (tmpDomain && tmpDomain->ShouldHaveInstances())
- pDomain = tmpDomain;
- }
- if (!pDomain && ! TrySetAppDomainAgile(FALSE))
- {
- _ASSERTE(!"Attempt to reference an object belonging to an unloaded domain");
- }
- }
-#endif
-
return pDomain;
}
@@ -483,826 +451,6 @@ CHARARRAYREF AllocateCharArray(DWORD dwArrayLength)
return (CHARARRAYREF)AllocatePrimitiveArray(ELEMENT_TYPE_CHAR, dwArrayLength);
}
-#if CHECK_APP_DOMAIN_LEAKS
-
-BOOL Object::IsAppDomainAgile()
-{
- WRAPPER_NO_CONTRACT;
- DEBUG_ONLY_FUNCTION;
-
- SyncBlock *psb = PassiveGetSyncBlock();
-
- if (psb)
- {
- if (psb->IsAppDomainAgile())
- return TRUE;
- if (psb->IsCheckedForAppDomainAgile())
- return FALSE;
- }
- return CheckAppDomain(NULL);
-}
-
-BOOL Object::TrySetAppDomainAgile(BOOL raiseAssert)
-{
- LIMITED_METHOD_CONTRACT;
- FAULT_NOT_FATAL();
- DEBUG_ONLY_FUNCTION;
-
- BOOL ret = TRUE;
-
- EX_TRY
- {
- ret = SetAppDomainAgile(raiseAssert);
- }
- EX_CATCH{}
- EX_END_CATCH(SwallowAllExceptions);
-
- return ret;
-}
-
-
-BOOL Object::ShouldCheckAppDomainAgile (BOOL raiseAssert, BOOL *pfResult)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- if (!g_pConfig->AppDomainLeaks())
- {
- *pfResult = TRUE;
- return FALSE;
- }
-
- if (this == NULL)
- {
- *pfResult = TRUE;
- return FALSE;
- }
-
- if (IsAppDomainAgile())
- {
- *pfResult = TRUE;
- return FALSE;
- }
-
- // if it's not agile and we've already checked it, just bail early
- if (IsCheckedForAppDomainAgile())
- {
- *pfResult = FALSE;
- return FALSE;
- }
-
- if (IsTypeNeverAppDomainAgile())
- {
- if (raiseAssert)
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- *pfResult = FALSE;
- return FALSE;
- }
-
- //
- // Do not allow any object to be set to be agile unless we
- // are compiling field access checking into the class. This
- // will help guard against unintentional "agile" propagation
- // as well.
- //
-
- if (!IsTypeAppDomainAgile() && !IsTypeCheckAppDomainAgile())
- {
- if (raiseAssert)
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- *pfResult = FALSE;
- return FALSE;
- }
-
- return TRUE;
-}
-
-
-BOOL Object::SetAppDomainAgile(BOOL raiseAssert, SetAppDomainAgilePendingTable *pTable)
-{
- CONTRACTL
- {
- THROWS;
- GC_NOTRIGGER;
- INJECT_FAULT(COMPlusThrowOM(););
- DEBUG_ONLY;
- }
- CONTRACTL_END;
- BEGIN_DEBUG_ONLY_CODE;
- BOOL fResult;
- if (!this->ShouldCheckAppDomainAgile(raiseAssert, &fResult))
- return fResult;
-
- //
- // If a SetAppDomainAgilePendingTable is provided, then SetAppDomainAgile
- // was called via SetAppDomainAgile. Simply store this object in the
- // table, and let the calling SetAppDomainAgile process it later in a
- // non-recursive manner.
- //
-
- if (pTable == NULL)
- {
- pTable = (SetAppDomainAgilePendingTable *)ClrFlsGetValue(TlsIdx_AppDomainAgilePendingTable);
- }
- if (pTable)
- {
- //
- // If the object is already being checked (on this thread or another),
- // don't duplicate the effort. Return TRUE to tell the caller to
- // continue processing other references. Since we're just testing
- // the bit we don't need to take the spin lock.
- //
-
- ObjHeader* pOh = this->GetHeader();
- _ASSERTE(pOh);
-
- if (pOh->GetBits() & BIT_SBLK_AGILE_IN_PROGRESS)
- {
- return TRUE;
- }
-
- pTable->PushReference(this);
- }
- else
- {
- //
- // Initialize the table of pending objects
- //
-
- SetAppDomainAgilePendingTable table;
- class ResetPendingTable
- {
- public:
- ResetPendingTable(SetAppDomainAgilePendingTable *pTable)
- {
- ClrFlsSetValue(TlsIdx_AppDomainAgilePendingTable, pTable);
- }
- ~ResetPendingTable()
- {
- ClrFlsSetValue(TlsIdx_AppDomainAgilePendingTable, NULL);
- }
- };
-
- ResetPendingTable resetPendingTable(&table);
-
- //
- // Iterate over the table, processing all referenced objects until the
- // entire graph has its sync block marked, or a non-agile object is
- // found. The loop will start with the current object, as though we
- // just removed it from the table as a pending reference.
- //
-
- Object *pObject = this;
-
- do
- {
- //
- // Mark the object to identify recursion.
- // ~SetAppDomainAgilePendingTable will clean up
- // BIT_SBLK_AGILE_IN_PROGRESS, so attempt to push the object first
- // in case it needs to throw an exception.
- //
-
- table.PushParent(pObject);
-
- ObjHeader* pOh = pObject->GetHeader();
- _ASSERTE(pOh);
-
- bool fInProgress = false;
-
- {
- ENTER_SPIN_LOCK(pOh);
- {
- if (pOh->GetBits() & BIT_SBLK_AGILE_IN_PROGRESS)
- {
- fInProgress = true;
- }
- else
- {
- pOh->SetBit(BIT_SBLK_AGILE_IN_PROGRESS);
- }
- }
- LEAVE_SPIN_LOCK(pOh);
- }
-
- if (fInProgress)
- {
- //
- // Object is already being processed, so just remove it from
- // the table and look for another object.
- //
-
- bool fReturnedToParent = false;
- Object *pLastObject = table.GetPendingObject(&fReturnedToParent);
- CONSISTENCY_CHECK(pLastObject == pObject && fReturnedToParent);
- }
- else
- {
-
- //
- // Finish processing this object. Any references will be added to
- // the table.
- //
-
- if (!pObject->SetAppDomainAgileWorker(raiseAssert, &table))
- return FALSE;
- }
-
- //
- // Find the next object to explore.
- //
-
- for (;;)
- {
- bool fReturnedToParent;
- pObject = table.GetPendingObject(&fReturnedToParent);
-
- //
- // No more objects in the table?
- //
-
- if (!pObject)
- break;
-
- //
- // If we've processed all objects reachable through an object,
- // then clear BIT_SBLK_AGILE_IN_PROGRESS, and look for another
- // object in the table.
- //
-
- if (fReturnedToParent)
- {
- pOh = pObject->GetHeader();
- _ASSERTE(pOh);
-
- ENTER_SPIN_LOCK(pOh);
- pOh->ClrBit(BIT_SBLK_AGILE_IN_PROGRESS);
- LEAVE_SPIN_LOCK(pOh);
- }
- else
- {
- //
- // Re-check whether we should explore through this reference.
- //
-
- if (pObject->ShouldCheckAppDomainAgile(raiseAssert, &fResult))
- break;
-
- if (!fResult)
- return FALSE;
- }
- }
- }
- while (pObject);
- }
- END_DEBUG_ONLY_CODE;
- return TRUE;
-}
-
-
-BOOL Object::SetAppDomainAgileWorker(BOOL raiseAssert, SetAppDomainAgilePendingTable *pTable)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- BOOL ret = TRUE;
-
- if (! IsTypeAppDomainAgile() && ! SetFieldsAgile(raiseAssert, pTable))
- {
- SetIsCheckedForAppDomainAgile();
-
- ret = FALSE;
- }
-
- if (ret)
- {
- SetSyncBlockAppDomainAgile();
- }
-
- return ret;
-}
-
-
-SetAppDomainAgilePendingTable::SetAppDomainAgilePendingTable ()
- : m_Stack(sizeof(PendingEntry))
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-}
-
-
-SetAppDomainAgilePendingTable::~SetAppDomainAgilePendingTable ()
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- while (TRUE)
- {
- Object *pObj;
- bool fObjMarked;
- pObj = GetPendingObject(&fObjMarked);
- if (pObj == NULL)
- {
- break;
- }
-
- if (fObjMarked)
- {
- ObjHeader* pOh = pObj->GetHeader();
- _ASSERTE(pOh);
-
- ENTER_SPIN_LOCK(pOh);
- pOh->ClrBit(BIT_SBLK_AGILE_IN_PROGRESS);
- LEAVE_SPIN_LOCK(pOh);
- }
-}
-}
-
-
-void Object::SetSyncBlockAppDomainAgile()
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- SyncBlock *psb = PassiveGetSyncBlock();
- if (! psb)
- {
- psb = GetSyncBlock();
- }
- psb->SetIsAppDomainAgile();
-}
-
-#if CHECK_APP_DOMAIN_LEAKS
-BOOL Object::CheckAppDomain(AppDomain *pAppDomain)
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- DEBUG_ONLY_FUNCTION;
-
- if (!g_pConfig->AppDomainLeaks())
- return TRUE;
-
- if (this == NULL)
- return TRUE;
-
- if (IsAppDomainAgileRaw())
- return TRUE;
-
-#ifndef _DEBUG
- MethodTable *pMT = GetGCSafeMethodTable();
-
- if (!pMT->IsDomainNeutral())
- return pAppDomain == pMT->GetDomain();
-#endif
-
- ADIndex index = GetHeader()->GetAppDomainIndex();
-
- _ASSERTE(index.m_dwIndex != 0);
-
- return (pAppDomain != NULL && index == pAppDomain->GetIndex());
-}
-#endif
-
-BOOL Object::IsTypeAppDomainAgile()
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- DEBUG_ONLY_FUNCTION;
-
- MethodTable *pMT = GetGCSafeMethodTable();
-
- if (pMT->IsArray())
- {
- TypeHandle th = pMT->GetApproxArrayElementTypeHandle();
- return th.IsArrayOfElementsAppDomainAgile();
- }
- else
- return pMT->GetClass()->IsAppDomainAgile();
-}
-
-BOOL Object::IsTypeCheckAppDomainAgile()
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- DEBUG_ONLY_FUNCTION;
-
- MethodTable *pMT = GetGCSafeMethodTable();
-
- if (pMT->IsArray())
- {
- TypeHandle th = pMT->GetApproxArrayElementTypeHandle();
- return th.IsArrayOfElementsCheckAppDomainAgile();
- }
- else
- return pMT->GetClass()->IsCheckAppDomainAgile();
-}
-
-BOOL Object::IsTypeNeverAppDomainAgile()
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- DEBUG_ONLY_FUNCTION;
-
- return !IsTypeAppDomainAgile() && !IsTypeCheckAppDomainAgile();
-}
-
-BOOL Object::IsTypeTypesafeAppDomainAgile()
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- DEBUG_ONLY_FUNCTION;
-
- return IsTypeAppDomainAgile() && !IsTypeCheckAppDomainAgile();
-}
-
-BOOL Object::TryAssignAppDomain(AppDomain *pAppDomain, BOOL raiseAssert)
-{
- LIMITED_METHOD_CONTRACT;
- FAULT_NOT_FATAL();
- DEBUG_ONLY_FUNCTION;
-
- BOOL ret = TRUE;
-
- EX_TRY
- {
- ret = AssignAppDomain(pAppDomain,raiseAssert);
- }
- EX_CATCH{}
- EX_END_CATCH(SwallowAllExceptions);
-
- return ret;
-}
-
-BOOL Object::AssignAppDomain(AppDomain *pAppDomain, BOOL raiseAssert)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- if (!g_pConfig->AppDomainLeaks())
- return TRUE;
-
- if (CheckAppDomain(pAppDomain))
- return TRUE;
-
- //
- // App domain does not match; try to make this object agile
- //
-
- if (IsTypeNeverAppDomainAgile())
- {
- if (raiseAssert)
- {
- if (pAppDomain == NULL)
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- else
- _ASSERTE(!"Attempt to reference a domain bound object from a different domain");
- }
- return FALSE;
- }
- else
- {
- //
- // Make object agile
- //
-
- if (! IsTypeAppDomainAgile() && ! SetFieldsAgile(raiseAssert))
- {
- SetIsCheckedForAppDomainAgile();
- return FALSE;
- }
-
- SetSyncBlockAppDomainAgile();
-
- return TRUE;
- }
-}
-
-BOOL Object::AssignValueTypeAppDomain(MethodTable *pMT, void *base, AppDomain *pAppDomain, BOOL raiseAssert)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
- DEBUG_ONLY_FUNCTION;
-
- if (!g_pConfig->AppDomainLeaks())
- return TRUE;
-
- if (pMT->GetClass()->IsAppDomainAgile())
- return TRUE;
-
- if (pAppDomain == NULL)
- {
- //
- // Do not allow any object to be set to be agile unless we
- // are compiling field access checking into the class. This
- // will help guard against unintentional "agile" propagation
- // as well.
- //
-
- if (pMT->GetClass()->IsNeverAppDomainAgile())
- {
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- return FALSE;
- }
-
- return SetClassFieldsAgile(pMT, base, TRUE/*=baseIsVT*/, raiseAssert);
- }
- else
- {
- return ValidateClassFields(pMT, base, TRUE/*=baseIsVT*/, pAppDomain, raiseAssert);
- }
-}
-
-BOOL Object::SetFieldsAgile(BOOL raiseAssert, SetAppDomainAgilePendingTable *pTable)
-{
- CONTRACTL
- {
- THROWS;
- GC_NOTRIGGER;
- INJECT_FAULT(COMPlusThrowOM(););
- DEBUG_ONLY;
- }
- CONTRACTL_END;
-
- BOOL result = TRUE;
-
- MethodTable *pMT= GetGCSafeMethodTable();
-
- if (pMT->IsArray())
- {
- switch (pMT->GetArrayElementType())
- {
- case ELEMENT_TYPE_CLASS:
- case ELEMENT_TYPE_ARRAY:
- case ELEMENT_TYPE_SZARRAY:
- {
- PtrArray *pArray = (PtrArray *) this;
-
- DWORD n = pArray->GetNumComponents();
- OBJECTREF *p = (OBJECTREF *)
- (((BYTE*)pArray) + ArrayBase::GetDataPtrOffset(GetGCSafeMethodTable()));
-
- for (DWORD i=0; i<n; i++)
- {
- if (!p[i]->SetAppDomainAgile(raiseAssert, pTable))
- result = FALSE;
- }
-
- break;
- }
- case ELEMENT_TYPE_VALUETYPE:
- {
- ArrayBase *pArray = (ArrayBase *) this;
-
- MethodTable *pElemMT = pMT->GetApproxArrayElementTypeHandle().GetMethodTable();
-
- BYTE *p = ((BYTE*)pArray) + ArrayBase::GetDataPtrOffset(GetGCSafeMethodTable());
- SIZE_T size = pArray->GetComponentSize();
- SIZE_T n = pArray->GetNumComponents();
-
- for (SIZE_T i=0; i<n; i++)
- if (!SetClassFieldsAgile(pElemMT, p + i*size, TRUE/*=baseIsVT*/, raiseAssert, pTable))
- result = FALSE;
-
- break;
- }
-
- default:
- _ASSERTE(!"Unexpected array type");
- }
- }
- else
- {
- if (pMT->GetClass()->IsNeverAppDomainAgile())
- {
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- return FALSE;
- }
-
- while (pMT != NULL && !pMT->GetClass()->IsTypesafeAppDomainAgile())
- {
- if (!SetClassFieldsAgile(pMT, this, FALSE/*=baseIsVT*/, raiseAssert, pTable))
- result = FALSE;
-
- pMT = pMT->GetParentMethodTable();
-
- if (pMT->GetClass()->IsNeverAppDomainAgile())
- {
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- return FALSE;
- }
- }
- }
-
- return result;
-}
-
-BOOL Object::SetClassFieldsAgile(MethodTable *pMT, void *base, BOOL baseIsVT, BOOL raiseAssert, SetAppDomainAgilePendingTable *pTable)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- BOOL result = TRUE;
-
- if (pMT->GetClass()->IsNeverAppDomainAgile())
- {
- _ASSERTE(!"Attempt to reference a domain bound object from an agile location");
- return FALSE;
- }
-
- // This type approximation is OK since we are only checking some layout information
- // and all compatible instantiations share the same GC characteristics
- ApproxFieldDescIterator fdIterator(pMT, ApproxFieldDescIterator::INSTANCE_FIELDS);
- FieldDesc* pField;
-
- while ((pField = fdIterator.Next()) != NULL)
- {
- if (pField->IsDangerousAppDomainAgileField())
- {
- if (pField->GetFieldType() == ELEMENT_TYPE_CLASS)
- {
- OBJECTREF ref;
-
- if (baseIsVT)
- ref = *(OBJECTREF*) pField->GetAddressNoThrowNoGC(base);
- else
- ref = *(OBJECTREF*) pField->GetAddressGuaranteedInHeap(base);
-
- if (ref != 0 && !ref->IsAppDomainAgile())
- {
- if (!ref->SetAppDomainAgile(raiseAssert, pTable))
- result = FALSE;
- }
- }
- else if (pField->GetFieldType() == ELEMENT_TYPE_VALUETYPE)
- {
- // Be careful here - we may not have loaded a value
- // type field of a class under prejit, and we don't
- // want to trigger class loading here.
-
- TypeHandle th = pField->LookupFieldTypeHandle();
- if (!th.IsNull())
- {
- void *nestedBase;
-
- if (baseIsVT)
- nestedBase = pField->GetAddressNoThrowNoGC(base);
- else
- nestedBase = pField->GetAddressGuaranteedInHeap(base);
-
- if (!SetClassFieldsAgile(th.GetMethodTable(),
- nestedBase,
- TRUE/*=baseIsVT*/,
- raiseAssert,
- pTable))
- {
- result = FALSE;
- }
- }
- }
- else
- {
- _ASSERTE(!"Bad field type");
- }
- }
- }
-
- return result;
-}
-
-BOOL Object::ValidateAppDomain(AppDomain *pAppDomain)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
-
- if (!g_pConfig->AppDomainLeaks())
- return TRUE;
-
- if (this == NULL)
- return TRUE;
-
- if (CheckAppDomain())
- return ValidateAppDomainFields(pAppDomain);
-
- return AssignAppDomain(pAppDomain);
-}
-
-BOOL Object::ValidateAppDomainFields(AppDomain *pAppDomain)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- BOOL result = TRUE;
-
- MethodTable *pMT = GetGCSafeMethodTable();
-
- while (pMT != NULL && !pMT->GetClass()->IsTypesafeAppDomainAgile())
- {
- if (!ValidateClassFields(pMT, this, FALSE/*=baseIsVT*/, pAppDomain))
- result = FALSE;
-
- pMT = pMT->GetParentMethodTable();
- }
-
- return result;
-}
-
-BOOL Object::ValidateValueTypeAppDomain(MethodTable *pMT, void *base, AppDomain *pAppDomain, BOOL raiseAssert)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- if (!g_pConfig->AppDomainLeaks())
- return TRUE;
-
- if (pAppDomain == NULL)
- {
- if (pMT->GetClass()->IsTypesafeAppDomainAgile())
- return TRUE;
- else if (pMT->GetClass()->IsNeverAppDomainAgile())
- {
- if (raiseAssert)
- _ASSERTE(!"Value type cannot be app domain agile");
- return FALSE;
- }
- }
-
- return ValidateClassFields(pMT, base, TRUE/*=baseIsVT*/, pAppDomain, raiseAssert);
-}
-
-BOOL Object::ValidateClassFields(MethodTable *pMT, void *base, BOOL baseIsVT, AppDomain *pAppDomain, BOOL raiseAssert)
-{
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- BOOL result = TRUE;
-
- // This type approximation is OK since we are only checking some layout information
- // and all compatible instantiations share the same GC characteristics
- ApproxFieldDescIterator fdIterator(pMT, ApproxFieldDescIterator::INSTANCE_FIELDS);
- FieldDesc* pField;
-
- while ((pField = fdIterator.Next()) != NULL)
- {
- if (!pMT->GetClass()->IsCheckAppDomainAgile()
- || pField->IsDangerousAppDomainAgileField())
- {
- if (pField->GetFieldType() == ELEMENT_TYPE_CLASS)
- {
- OBJECTREF ref;
-
- if (baseIsVT)
- ref = ObjectToOBJECTREF(*(Object**) pField->GetAddressNoThrowNoGC(base));
- else
- ref = ObjectToOBJECTREF(*(Object**) pField->GetAddressGuaranteedInHeap(base));
-
- if (ref != 0 && !ref->AssignAppDomain(pAppDomain, raiseAssert))
- result = FALSE;
- }
- else if (pField->GetFieldType() == ELEMENT_TYPE_VALUETYPE)
- {
- // Be careful here - we may not have loaded a value
- // type field of a class under prejit, and we don't
- // want to trigger class loading here.
-
- TypeHandle th = pField->LookupFieldTypeHandle();
- if (!th.IsNull())
- {
- void *nestedBase;
-
- if (baseIsVT)
- nestedBase = pField->GetAddressNoThrowNoGC(base);
- else
- nestedBase = pField->GetAddressGuaranteedInHeap(base);
-
- if (!ValidateValueTypeAppDomain(th.GetMethodTable(),
- nestedBase,
- pAppDomain,
- raiseAssert
- ))
- result = FALSE;
-
- }
- }
- }
- }
-
- return result;
-}
-
-#endif // CHECK_APP_DOMAIN_LEAKS
-
void Object::ValidatePromote(ScanContext *sc, DWORD flags)
{
STATIC_CONTRACT_NOTHROW;
@@ -1313,30 +461,6 @@ void Object::ValidatePromote(ScanContext *sc, DWORD flags)
#if defined (VERIFY_HEAP)
Validate();
#endif
-
-#if CHECK_APP_DOMAIN_LEAKS
- // Do app domain integrity checking here
- if (g_pConfig->AppDomainLeaks())
- {
- AppDomain *pDomain = GetAppDomain();
-
-// This assert will incorrectly trip when
-// InternalCrossContextCallback is on the stack. InternalCrossContextCallback
-// intentionally passes an object across domains on the same thread.
-#if 0
- if (flags & GC_CALL_CHECK_APP_DOMAIN)
- _ASSERTE(TryAssignAppDomain(sc->pCurrentDomain));
-#endif
-
- if ((flags & GC_CALL_CHECK_APP_DOMAIN)
- && pDomain != NULL
- && !pDomain->ShouldHaveRoots()
- && !TrySetAppDomainAgile(FALSE))
- {
- _ASSERTE(!"Found GC object which should have been purged during app domain unload.");
- }
- }
-#endif
}
void Object::ValidateHeap(Object *from, BOOL bDeep)
@@ -1350,51 +474,6 @@ void Object::ValidateHeap(Object *from, BOOL bDeep)
//since this is called in verify_heap, which will verfiy every object anyway
Validate(bDeep, FALSE);
#endif
-
-#if CHECK_APP_DOMAIN_LEAKS
- // Do app domain integrity checking here
- if (g_pConfig->AppDomainLeaks() && bDeep)
- {
- AppDomain *pDomain = from->GetAppDomain();
-
- //
- // Don't perform check if we're checking for agility, and the containing type is not
- // marked checked agile - this will cover "proxy" type agility
- // where cross references are allowed
- //
-
- // Changed the GetMethodTable calls in this function to GetGCSafeMethodTable
- // because GC could use the mark bit to simulate a mark and can have it set during
- // verify heap (and would be cleared when verify heap is done).
- // We'd get AV pretty soon anyway if it was truly mistakenly set.
- if (pDomain != NULL || from->GetGCSafeMethodTable()->GetClass()->IsCheckAppDomainAgile())
- {
- //special case:thread object is allowed to hold a context belonging to current domain
- if (from->GetGCSafeMethodTable() == g_pThreadClass &&
- (
- false))
- {
- if (((ThreadBaseObject *)from)->m_InternalThread)
- _ASSERTE (CheckAppDomain (((ThreadBaseObject *)from)->m_InternalThread->GetDomain ()));
- }
- // special case: Overlapped has a field OverlappedData which may be moved to default domain
- // during AD unload
- else if (GetGCSafeMethodTable() == g_pOverlappedDataClass &&
- GetAppDomainIndex() == SystemDomain::System()->DefaultDomain()->GetIndex())
- {
- }
- else
- {
- TryAssignAppDomain(pDomain);
- }
- }
-
- if (pDomain != NULL
- && !pDomain->ShouldHaveInstances()
- && !TrySetAppDomainAgile(FALSE))
- _ASSERTE(!"Found GC object which should have been purged during app domain unload.");
- }
-#endif
}
void Object::SetOffsetObjectRef(DWORD dwOffset, size_t dwValue)
@@ -1414,32 +493,6 @@ void Object::SetOffsetObjectRef(DWORD dwOffset, size_t dwValue)
SetObjectReference( location, o, GetAppDomain() );
}
-/******************************************************************/
-/*
- * Write Barrier Helper
- *
- * Use this function to assign an object reference into
- * another object.
- *
- * It will set the appropriate GC Write Barrier data
- */
-
-#if CHECK_APP_DOMAIN_LEAKS
-void SetObjectReferenceChecked(OBJECTREF *dst,OBJECTREF ref,AppDomain *pAppDomain)
-{
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- STATIC_CONTRACT_MODE_COOPERATIVE;
- STATIC_CONTRACT_CANNOT_TAKE_LOCK;
-
- DEBUG_ONLY_FUNCTION;
-
- ref->TryAssignAppDomain(pAppDomain);
- return SetObjectReferenceUnchecked(dst,ref);
-}
-#endif
-
void SetObjectReferenceUnchecked(OBJECTREF *dst,OBJECTREF ref)
{
STATIC_CONTRACT_NOTHROW;
@@ -1457,59 +510,6 @@ void SetObjectReferenceUnchecked(OBJECTREF *dst,OBJECTREF ref)
#endif
ErectWriteBarrier(dst, ref);
}
-
-/******************************************************************/
- // copies src to dest worrying about write barriers.
- // Note that it can work on normal objects (but not arrays)
- // if dest, points just after the VTABLE.
-#if CHECK_APP_DOMAIN_LEAKS
-void CopyValueClassChecked(void* dest, void* src, MethodTable *pMT, AppDomain *pDomain)
-{
- STATIC_CONTRACT_DEBUG_ONLY;
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- STATIC_CONTRACT_MODE_COOPERATIVE;
-
- DEBUG_ONLY_FUNCTION;
-
- FAULT_NOT_FATAL();
- EX_TRY
- {
- Object::AssignValueTypeAppDomain(pMT, src, pDomain);
- }
- EX_CATCH
- {
- }
- EX_END_CATCH(SwallowAllExceptions);
- CopyValueClassUnchecked(dest,src,pMT);
-}
-
-// Copy value class into the argument specified by the argDest, performing an appdomain check first.
-// The destOffset is nonzero when copying values into Nullable<T>, it is the offset
-// of the T value inside of the Nullable<T>
-void CopyValueClassArgChecked(ArgDestination *argDest, void* src, MethodTable *pMT, AppDomain *pDomain, int destOffset)
-{
- STATIC_CONTRACT_DEBUG_ONLY;
- STATIC_CONTRACT_NOTHROW;
- STATIC_CONTRACT_GC_NOTRIGGER;
- STATIC_CONTRACT_FORBID_FAULT;
- STATIC_CONTRACT_MODE_COOPERATIVE;
-
- DEBUG_ONLY_FUNCTION;
-
- FAULT_NOT_FATAL();
- EX_TRY
- {
- Object::AssignValueTypeAppDomain(pMT, src, pDomain);
- }
- EX_CATCH
- {
- }
- EX_END_CATCH(SwallowAllExceptions);
- CopyValueClassArgUnchecked(argDest, src, pMT, destOffset);
-}
-#endif
void STDCALL CopyValueClassUnchecked(void* dest, void* src, MethodTable *pMT)
{
@@ -1771,19 +771,6 @@ VOID Object::ValidateInner(BOOL bDeep, BOOL bVerifyNextHeader, BOOL bVerifySyncB
lastTest = 6;
-#if CHECK_APP_DOMAIN_LEAKS
- // when it's not safe to verify the fields, it's not safe to verify AppDomain either
- // because the process might try to access fields.
- if (bDeep && g_pConfig->AppDomainLeaks())
- {
- //
- // Check to see that our domain is valid. This will assert if it has been unloaded.
- //
- SCAN_IGNORE_FAULT;
- GetAppDomain();
- }
-#endif
-
lastTest = 7;
_ASSERTE(GCHeapUtilities::IsGCHeapInitialized());
diff --git a/src/vm/object.h b/src/vm/object.h
index 8db3c17ffc..3ba892af0d 100644
--- a/src/vm/object.h
+++ b/src/vm/object.h
@@ -97,71 +97,6 @@ class ArgDestination;
struct RCW;
-#if CHECK_APP_DOMAIN_LEAKS
-
-class Object;
-
-class SetAppDomainAgilePendingTable
-{
-public:
-
- SetAppDomainAgilePendingTable ();
- ~SetAppDomainAgilePendingTable ();
-
- void PushReference (Object *pObject)
- {
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- PendingEntry entry;
- entry.pObject = pObject;
-
- m_Stack.Push(entry);
- }
-
- void PushParent (Object *pObject)
- {
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- PendingEntry entry;
- entry.pObject = (Object*)((size_t)pObject | 1);
-
- m_Stack.Push(entry);
- }
-
- Object *GetPendingObject (bool *pfReturnedToParent)
- {
- STATIC_CONTRACT_THROWS;
- STATIC_CONTRACT_GC_NOTRIGGER;
-
- if (!m_Stack.Count())
- return NULL;
-
- PendingEntry *pPending = m_Stack.Pop();
-
- *pfReturnedToParent = pPending->fMarked != 0;
- return (Object*)((size_t)pPending->pObject & ~1);
- }
-
-private:
-
- union PendingEntry
- {
- Object *pObject;
-
- // Indicates whether the current thread set BIT_SBLK_AGILE_IN_PROGRESS
- // on the object. Entries without this flag set are unexplored
- // objects.
- size_t fMarked:1;
- };
-
- CStackArray<PendingEntry> m_Stack;
-};
-
-#endif //CHECK_APP_DOMAIN_LEAKS
-
-
//
// The generational GC requires that every object be at least 12 bytes
// in size.
@@ -357,101 +292,6 @@ class Object
void DEBUG_SetAppDomain(AppDomain *pDomain);
#endif //_DEBUG
-
-#if CHECK_APP_DOMAIN_LEAKS
-
- // Mark object as app domain agile
- BOOL SetAppDomainAgile(BOOL raiseAssert=TRUE, SetAppDomainAgilePendingTable *pTable = NULL);
- BOOL TrySetAppDomainAgile(BOOL raiseAssert=TRUE);
-
- // Mark sync block as app domain agile
- void SetSyncBlockAppDomainAgile();
-
- // Check if object is app domain agile
- BOOL IsAppDomainAgile();
-
- // Check if object is app domain agile
- BOOL IsAppDomainAgileRaw()
- {
- WRAPPER_NO_CONTRACT;
-
- SyncBlock *psb = PassiveGetSyncBlock();
-
- return (psb && psb->IsAppDomainAgile());
- }
-
- BOOL IsCheckedForAppDomainAgile()
- {
- WRAPPER_NO_CONTRACT;
-
- SyncBlock *psb = PassiveGetSyncBlock();
- return (psb && psb->IsCheckedForAppDomainAgile());
- }
-
- void SetIsCheckedForAppDomainAgile()
- {
- WRAPPER_NO_CONTRACT;
-
- SyncBlock *psb = PassiveGetSyncBlock();
- if (psb)
- psb->SetIsCheckedForAppDomainAgile();
- }
-
- // Check object to see if it is usable in the current domain
- BOOL CheckAppDomain() { WRAPPER_NO_CONTRACT; return CheckAppDomain(::GetAppDomain()); }
-
- //Check object to see if it is usable in the given domain
- BOOL CheckAppDomain(AppDomain *pDomain);
-
- // Check if the object's type is app domain agile
- BOOL IsTypeAppDomainAgile();
-
- // Check if the object's type is conditionally app domain agile
- BOOL IsTypeCheckAppDomainAgile();
-
- // Check if the object's type is naturally app domain agile
- BOOL IsTypeTypesafeAppDomainAgile();
-
- // Check if the object's type is possibly app domain agile
- BOOL IsTypeNeverAppDomainAgile();
-
- // Validate object & fields to see that it's usable from the current app domain
- BOOL ValidateAppDomain() { WRAPPER_NO_CONTRACT; return ValidateAppDomain(::GetAppDomain()); }
-
- // Validate object & fields to see that it's usable from any app domain
- BOOL ValidateAppDomainAgile() { WRAPPER_NO_CONTRACT; return ValidateAppDomain(NULL); }
-
- // Validate object & fields to see that it's usable from the given app domain (or null for agile)
- BOOL ValidateAppDomain(AppDomain *pAppDomain);
-
- // Validate fields to see that they are usable from the object's app domain
- // (or from any domain if the object is agile)
- BOOL ValidateAppDomainFields() { WRAPPER_NO_CONTRACT; return ValidateAppDomainFields(GetAppDomain()); }
-
- // Validate fields to see that they are usable from the given app domain (or null for agile)
- BOOL ValidateAppDomainFields(AppDomain *pAppDomain);
-
- // Validate a value type's fields to see that it's usable from the current app domain
- static BOOL ValidateValueTypeAppDomain(MethodTable *pMT, void *base, BOOL raiseAssert = TRUE)
- { WRAPPER_NO_CONTRACT; return ValidateValueTypeAppDomain(pMT, base, ::GetAppDomain(), raiseAssert); }
-
- // Validate a value type's fields to see that it's usable from any app domain
- static BOOL ValidateValueTypeAppDomainAgile(MethodTable *pMT, void *base, BOOL raiseAssert = TRUE)
- { WRAPPER_NO_CONTRACT; return ValidateValueTypeAppDomain(pMT, base, NULL, raiseAssert); }
-
- // Validate a value type's fields to see that it's usable from the given app domain (or null for agile)
- static BOOL ValidateValueTypeAppDomain(MethodTable *pMT, void *base, AppDomain *pAppDomain, BOOL raiseAssert = TRUE);
-
- // Call when we are assigning this object to a dangerous field
- // in an object in a given app domain (or agile if null)
- BOOL AssignAppDomain(AppDomain *pAppDomain, BOOL raiseAssert = TRUE);
- BOOL TryAssignAppDomain(AppDomain *pAppDomain, BOOL raiseAssert = TRUE);
-
- // Call when we are assigning to a dangerous value type field
- // in an object in a given app domain (or agile if null)
- static BOOL AssignValueTypeAppDomain(MethodTable *pMT, void *base, AppDomain *pAppDomain, BOOL raiseAssert = TRUE);
-
-#endif // CHECK_APP_DOMAIN_LEAKS
// DO NOT ADD ANY ASSERTS TO THIS METHOD.
// DO NOT USE THIS METHOD.
@@ -672,15 +512,6 @@ class Object
private:
VOID ValidateInner(BOOL bDeep, BOOL bVerifyNextHeader, BOOL bVerifySyncBlock);
-#if CHECK_APP_DOMAIN_LEAKS
- friend class ObjHeader;
- BOOL SetFieldsAgile(BOOL raiseAssert = TRUE, SetAppDomainAgilePendingTable *pTable = NULL);
- static BOOL SetClassFieldsAgile(MethodTable *pMT, void *base, BOOL baseIsVT, BOOL raiseAssert = TRUE, SetAppDomainAgilePendingTable *pTable = NULL);
- static BOOL ValidateClassFields(MethodTable *pMT, void *base, BOOL baseIsVT, AppDomain *pAppDomain, BOOL raiseAssert = TRUE);
- BOOL SetAppDomainAgileWorker(BOOL raiseAssert, SetAppDomainAgilePendingTable *pTable);
- BOOL ShouldCheckAppDomainAgile(BOOL raiseAssert, BOOL *pfResult);
-#endif
-
#ifdef _DEBUG
void AssertNotArray()
{
@@ -733,24 +564,10 @@ inline void InitValueClass(void *dest, MethodTable *pMT)
// Initialize value class argument
void InitValueClassArg(ArgDestination *argDest, MethodTable *pMT);
-#if CHECK_APP_DOMAIN_LEAKS
-
-void SetObjectReferenceChecked(OBJECTREF *dst,OBJECTREF ref, AppDomain *pAppDomain);
-void CopyValueClassChecked(void* dest, void* src, MethodTable *pMT, AppDomain *pAppDomain);
-void CopyValueClassArgChecked(ArgDestination *argDest, void* src, MethodTable *pMT, AppDomain *pAppDomain, int destOffset);
-
-#define SetObjectReference(_d,_r,_a) SetObjectReferenceChecked(_d, _r, _a)
-#define CopyValueClass(_d,_s,_m,_a) CopyValueClassChecked(_d,_s,_m,_a)
-#define CopyValueClassArg(_d,_s,_m,_a,_o) CopyValueClassArgChecked(_d,_s,_m,_a,_o)
-
-#else
-
#define SetObjectReference(_d,_r,_a) SetObjectReferenceUnchecked(_d, _r)
#define CopyValueClass(_d,_s,_m,_a) CopyValueClassUnchecked(_d,_s,_m)
#define CopyValueClassArg(_d,_s,_m,_a,_o) CopyValueClassArgUnchecked(_d,_s,_m,_o)
-#endif
-
#include <pshpack4.h>
@@ -840,11 +657,7 @@ public:
SIZE_T GetComponentSize() const {
WRAPPER_NO_CONTRACT;
MethodTable * pMT;
-#if CHECK_APP_DOMAIN_LEAKS
- pMT = GetGCSafeMethodTable();
-#else
pMT = GetMethodTable();
-#endif //CHECK_APP_DOMAIN_LEAKS
_ASSERTE(pMT->HasComponentSize());
return pMT->RawGetComponentSize();
}
diff --git a/src/vm/olevariant.cpp b/src/vm/olevariant.cpp
index 1ec6f70213..95c0b9b0cc 100644
--- a/src/vm/olevariant.cpp
+++ b/src/vm/olevariant.cpp
@@ -1721,10 +1721,6 @@ void OleVariant::MarshalInterfaceArrayOleToCom(void *oleArray, BASEARRAYREF *pCo
BASEARRAYREF unprotectedArray = *pComArray;
OBJECTREF *pCom = (OBJECTREF *) unprotectedArray->GetDataPtr();
-#if CHECK_APP_DOMAIN_LEAKS
- AppDomain *pDomain = unprotectedArray->GetAppDomain();
-#endif // CHECK_APP_DOMAIN_LEAKS
-
OBJECTREF obj = NULL;
GCPROTECT_BEGIN(obj)
{
@@ -1886,10 +1882,6 @@ void OleVariant::MarshalBSTRArrayOleToCom(void *oleArray, BASEARRAYREF *pComArra
BASEARRAYREF unprotectedArray = *pComArray;
STRINGREF *pCom = (STRINGREF *) unprotectedArray->GetDataPtr();
-
-#if CHECK_APP_DOMAIN_LEAKS
- AppDomain *pDomain = unprotectedArray->GetAppDomain();
-#endif // CHECK_APP_DOMAIN_LEAKS
while (pOle < pOleEnd)
{
@@ -2104,10 +2096,6 @@ void OleVariant::MarshalLPWSTRArrayOleToCom(void *oleArray, BASEARRAYREF *pComAr
BASEARRAYREF unprotectedArray = *pComArray;
STRINGREF *pCom = (STRINGREF *) unprotectedArray->GetDataPtr();
-
-#if CHECK_APP_DOMAIN_LEAKS
- AppDomain *pDomain = unprotectedArray->GetAppDomain();
-#endif // CHECK_APP_DOMAIN_LEAKS
while (pOle < pOleEnd)
{
@@ -2244,10 +2232,6 @@ void OleVariant::MarshalLPSTRArrayOleToCom(void *oleArray, BASEARRAYREF *pComArr
BASEARRAYREF unprotectedArray = *pComArray;
STRINGREF *pCom = (STRINGREF *) unprotectedArray->GetDataPtr();
-
-#if CHECK_APP_DOMAIN_LEAKS
- AppDomain *pDomain = unprotectedArray->GetAppDomain();
-#endif // CHECK_APP_DOMAIN_LEAKS
while (pOle < pOleEnd)
{
diff --git a/src/vm/syncblk.cpp b/src/vm/syncblk.cpp
index 8f6f5448f9..11151a32c5 100644
--- a/src/vm/syncblk.cpp
+++ b/src/vm/syncblk.cpp
@@ -1724,46 +1724,6 @@ void SyncBlockCache::VerifySyncTableEntry()
#endif // VERIFY_HEAP
-#if CHECK_APP_DOMAIN_LEAKS
-void SyncBlockCache::CheckForUnloadedInstances(ADIndex unloadingIndex)
-{
- CONTRACTL
- {
- INSTANCE_CHECK;
- NOTHROW;
- GC_NOTRIGGER;
- MODE_ANY;
- }
- CONTRACTL_END;
-
- // Can only do in leak mode because agile objects will be in the domain with
- // their index set to their creating domain and check will fail.
- if (! g_pConfig->AppDomainLeaks())
- return;
-
- for (DWORD nb = 1; nb < m_FreeSyncTableIndex; nb++)
- {
- SyncTableEntry *pEntry = &SyncTableEntry::GetSyncTableEntry()[nb];
- Object *oref = (Object *) pEntry->m_Object;
- if (((size_t) oref & 1) != 0)
- continue;
-
- ADIndex idx;
- if (oref)
- idx = pEntry->m_Object->GetHeader()->GetRawAppDomainIndex();
- if (! idx.m_dwIndex && pEntry->m_SyncBlock)
- idx = pEntry->m_SyncBlock->GetAppDomainIndex();
- // if the following assert fires, someobody is holding a reference to an object in an unloaded appdomain
- if (idx == unloadingIndex)
- {
- // object must be agile to have survived the unload. If can't make it agile, that's a bug
- if (!oref->TrySetAppDomainAgile(TRUE))
- _ASSERTE(!"Detected instance of unloaded appdomain that survived GC\n");
- }
- }
-}
-#endif
-
#ifdef _DEBUG
void DumpSyncBlockCache()
@@ -2580,25 +2540,8 @@ BOOL ObjHeader::Validate (BOOL bVerifySyncBlkIndex)
}
else
{
-#if CHECK_APP_DOMAIN_LEAKS
- if (bVerifyMore)
- {
- if (bits & BIT_SBLK_AGILE_IN_PROGRESS)
- {
- BOOL fResult;
- ASSERT_AND_CHECK (
- //BIT_SBLK_AGILE_IN_PROGRESS is set only if the object needs to check appdomain agile
- obj->ShouldCheckAppDomainAgile(FALSE, &fResult)
- //before BIT_SBLK_AGILE_IN_PROGRESS is cleared, the object might already be marked as agile
- ||(obj->PassiveGetSyncBlock () && obj->PassiveGetSyncBlock ()->IsAppDomainAgile ())
- ||(obj->PassiveGetSyncBlock () && obj->PassiveGetSyncBlock ()->IsCheckedForAppDomainAgile ())
- );
- }
- }
-#else //CHECK_APP_DOMAIN_LEAKS
//BIT_SBLK_AGILE_IN_PROGRESS is set only in debug build
ASSERT_AND_CHECK (!(bits & BIT_SBLK_AGILE_IN_PROGRESS));
-#endif //CHECK_APP_DOMAIN_LEAKS
if (bits & BIT_SBLK_FINALIZER_RUN)
{
ASSERT_AND_CHECK (obj->GetGCSafeMethodTable ()->HasFinalizer ());
diff --git a/src/vm/syncblk.h b/src/vm/syncblk.h
index 212a726eb5..ab32fc76aa 100644
--- a/src/vm/syncblk.h
+++ b/src/vm/syncblk.h
@@ -844,14 +844,6 @@ class SyncBlock
// can never be 0. ObjectNative::GetHashCode in COMObject.cpp makes sure to enforce this.
DWORD m_dwHashCode;
-#if CHECK_APP_DOMAIN_LEAKS
- DWORD m_dwFlags;
-
- enum {
- IsObjectAppDomainAgile = 1,
- IsObjectCheckedForAppDomainAgile = 2,
- };
-#endif
// In some early version of VB when there were no arrays developers used to use BSTR as arrays
// The way this was done was by adding a trail byte at the end of the BSTR
// To support this scenario, we need to use the sync block for this special case and
@@ -866,9 +858,6 @@ class SyncBlock
, m_pEnCInfo(PTR_NULL)
#endif // EnC_SUPPORTED
, m_dwHashCode(0)
-#if CHECK_APP_DOMAIN_LEAKS
- , m_dwFlags(0)
-#endif
, m_BSTRTrailByte(0)
{
LIMITED_METHOD_CONTRACT;
@@ -1088,34 +1077,6 @@ class SyncBlock
SyncBlockPrecious = 0x80000000,
};
-#if CHECK_APP_DOMAIN_LEAKS
- BOOL IsAppDomainAgile()
- {
- LIMITED_METHOD_CONTRACT;
- return m_dwFlags & IsObjectAppDomainAgile;
- }
- void SetIsAppDomainAgile()
- {
- LIMITED_METHOD_CONTRACT;
- m_dwFlags |= IsObjectAppDomainAgile;
- }
- void UnsetIsAppDomainAgile()
- {
- LIMITED_METHOD_CONTRACT;
- m_dwFlags = m_dwFlags & ~IsObjectAppDomainAgile;
- }
- BOOL IsCheckedForAppDomainAgile()
- {
- LIMITED_METHOD_CONTRACT;
- return m_dwFlags & IsObjectCheckedForAppDomainAgile;
- }
- void SetIsCheckedForAppDomainAgile()
- {
- LIMITED_METHOD_CONTRACT;
- m_dwFlags |= IsObjectCheckedForAppDomainAgile;
- }
-#endif //CHECK_APP_DOMAIN_LEAKS
-
BOOL HasCOMBstrTrailByte()
{
LIMITED_METHOD_CONTRACT;
@@ -1315,9 +1276,6 @@ class SyncBlockCache
};
friend class LockHolder;
-#if CHECK_APP_DOMAIN_LEAKS
- void CheckForUnloadedInstances(ADIndex unloadingIndex);
-#endif
#ifdef _DEBUG
friend void DumpSyncBlockCache();
#endif
diff --git a/src/vm/typehandle.cpp b/src/vm/typehandle.cpp
index 9e8afba82f..c8c6362dd6 100644
--- a/src/vm/typehandle.cpp
+++ b/src/vm/typehandle.cpp
@@ -1442,7 +1442,7 @@ OBJECTREF TypeHandle::GetManagedClassObjectFast() const
#endif // #ifndef DACCESS_COMPILE
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
BOOL TypeHandle::IsAppDomainAgile() const
{
@@ -1534,7 +1534,7 @@ BOOL TypeHandle::IsArrayOfElementsCheckAppDomainAgile() const
}
}
-#endif // defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#endif // defined(_DEBUG)
BOOL TypeHandle::IsByRef() const
diff --git a/src/vm/typehandle.h b/src/vm/typehandle.h
index cec772e3be..5cb9eaa7a6 100644
--- a/src/vm/typehandle.h
+++ b/src/vm/typehandle.h
@@ -574,7 +574,7 @@ public:
INDEBUGIMPL(BOOL Verify();) // DEBUGGING Make certain this is a valid type handle
-#if defined(CHECK_APP_DOMAIN_LEAKS) || defined(_DEBUG)
+#if defined(_DEBUG)
BOOL IsAppDomainAgile() const;
BOOL IsCheckAppDomainAgile() const;