diff options
Diffstat (limited to 'src/vm/mdaBoilerplate.exe.mda.config')
-rw-r--r-- | src/vm/mdaBoilerplate.exe.mda.config | 1134 |
1 files changed, 1134 insertions, 0 deletions
diff --git a/src/vm/mdaBoilerplate.exe.mda.config b/src/vm/mdaBoilerplate.exe.mda.config new file mode 100644 index 0000000000..1cbd20037e --- /dev/null +++ b/src/vm/mdaBoilerplate.exe.mda.config @@ -0,0 +1,1134 @@ +<?xml version="1.0" encoding="UTF-8" ?> +<!-- +************************************************ + PLEASE KEEP MDAS IN ALPHABETICAL ORDER! +************************************************ +--> + +<!-- + +FEEDBACK: + Please add yourself to clrmda discussion alias (just paste this link into + IE: http://autogroup/JoinGroup.asp?GroupAlias=clrmda). Once you join, + please send out a "Hello World" mail letting us know what problem your + trying to solve with MDAs. We're interested in feedback on activation, + reporting, VS integration, new MDA requests etc. We'll also send out mail + for any breaking changes or new MDAs. + +OVERVIEW: + Managed Debugging Assistants (MDAs) are switches shipped in the retail + runtime to help debug managed code. Each MDA and the problem it addresses + is documented below. + +ACTIVATION\REPORTING QUICK START: + Decide which MDAs you'd like enabled by reading their documentation below and then + set the environment variable COMPLUS_MDA equal to a semi-colen delemited list of + the names of the MDAs you want enabled. The list is not case sensitive. So, for + instance if you want the memberInfoCacheCreation, gcUnmanagedToManaged and + gcManagedToUnmanaged MDAs enabled + + set complus_mda=mEmBeRInFoCacheCreation;gcUnmanagedToManaged;gcManagedToUnmanaged + + Any managed program run from that command shell will now have these MDAs enabled. If + an MDA fires and no debugger is attached then the dialog very much like the dialog you + would get if an unhandled exception occurred which will tell you what MDA fired and + give you a chance to attach a debugger so you can get a stack trace indicating where + the MDA fired. + + If you launch under a debugger you'll have to ensure that the debugger won't ignore the MDAs + you enabled. You can force VS to report all MDAs by checking the "Managed Debugging Assistants" + box in the exceptions dialog. VS uses the same dialog exceptions use to report MDA messages. + Cordbg and windbg report all MDAs by default by splashing the message to the console. + +ACTIVATION\REPORTING SCENARIOS: + The MDA activation and reporting featurs support a variety of scenarios. Those scenarios + and the supporting features are described below. + +--> + + +<!-- + Constrained Execution Region (CER) MDA + - InvalidCERCall + - VirtualCERCall + - OpenGenericCERCall + - IllegalPrepareConstrainedRegion + + These all fire during the analysis of CER call graphs. This analysis + can occur for a number of reasons: + + Early bound; triggered by jitting or ngen'ing a method containing a + RuntimeHelpers.PrepareConstrainedRegions() call. Call graph is + rooted at the catch/finally/filter/fault blocks belonging to the + exception handler the PCR call is associated with. + + At instantiation of "critical" objects. Instances derived from + CriticalFinalizerObject prepare a CER rooted at the finalizer method. + Instances derived from SafeHandle or CriticalHandle additionally have + the ReleaseHandle(), Dispose() and IsInvalid property getter methods + prepared as CER roots. + + Explicitly via RuntimeHelpers.PrepareMethod() or PrepareDelegates() calls + (the CER root method is passed as an argument, indirectly in the case of + PrepareDelegate() and possibly with exact generic instantiation information + for PrepareMethod()). + + Note that for the early bound (PCR precipitated) case the jit time semantics + imply the probe will fire some time before the method which contains the CER + root is called (typically just prior to the first call to that method). Since + the entire CER call graph is scanned in one go, probes relating to methods + deep within the CER will be reported at that time as well (putting the report + even further away from the execution). The probes will not fire each time the + method is executed (and if the image is ngen'd then they will not fire at runtime at all). + + Even in the late bound cases a given probe will fire at most once (we remember + which CERs we've prepared already, subsequent prepare operations on the same + graphs are no-ops). Note that CER graphs that are qualified by generic type + parameters (i.e. those CERs whose root method has generic method or class + type variables) are considered to define distinct CERs for each possible + instantiation of that root method. Therefore multiple calls to PrepareMethod() + with such a root method and different instantiations will cause the analysis + to be run multiple times and therefore any probes will fire on each invocation + (provided the instantiation given hasn't been prepared for that method before). + This last case (multiple CER preparations from the same root differing only by + generic instantiation) will occur at jit time only for generic instantiations + that contain only non-reference types (we jit a separate copy of the code for + each of those instantiations). We will refuse to jit-time prepare any method + with a generic instantiation containing one or more reference types, since + code for those cases is shared (and thus at jit time we cannot predict which + exact instantiations will be required at runtime). See the description of + the openGenericCERCall probe. + + --> + +<mdaConfig> + <assistants> + + <!-- + AsynchronousThreadAbort (weiwenli) + + DESCRIPTION: + Causes the runtime to fire a MDA message when someone attempts to abort another thread. + + BEHAVIORAL IMPACT: + None. + + --> + <asynchronousThreadAbort enable="false" /> + + + <!-- + BindingFailure (t-daveh) + + DESCRIPTION: + This probe fires when an Assembly fails to load. + + SCENARIOS: + This probe is intended for use in debugging Assembly binding failures. In addition to general information + identifying the failure and Assembly, the binding context the Assembly would have been loaded in is included. + See http://blogs.msdn.com/suzcook/archive/2003/05/29/57143.aspx for more information. + + BEHAVIORAL IMPACT: None. + + OUTPUT: An MDA message is output for each Assembly that fails to load. It includes the failing HRESULT as well + as the display name, code base, binding context index, and AppDomain ID that the Assembly would have had. + --> + <bindingFailure enable="false" /> + + + <!-- + CallbackOnCollectedDelegate (chriseck) + + DESCRIPTION: Detects when unmanaged code is trying to call back into the runtime via a delegate which + has been garbage collected. Will store up to listSize number of delegates after the GC has released them. + The default listSize is 1000 members. The minimum is 50 members. The maximum is 2000. + + SCENARIOS: + + SYMPTOM: + User code AVs when trying to call back into the runtime on a function pointer which was marshaled from + a managed delegate. The failure is non-deterministic; sometimes the call on the function + pointer succeeds and sometimes it fails. + + CAUSE: + The delegate which from which the function pointer was created and exposed to unmanaged code was collected + so when the unmanaged component tries to call on the function pointer it AVs. By enabling this assistant the runtime + will not collect "all" of the delegate - instead it leaks just enough of the delegate so that if someone + tries to call back on it the MDA will fire. + --> + <callbackOnCollectedDelegate listSize="1000" enable="false" /> + + <!-- + ContextSwitchDeadlock (chriseck) + + DESCRIPTION: + Causes the runtime to fire a MDA message when a deadlock is detected during an attempted context transition + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + A native context transition appears to be deadlocked. + + CAUSE: + Most likely cause is a non-pumping STA thread. + + OUTPUT: + An XML message specifying the violation. + --> + <contextSwitchDeadlock enable="false" /> + + <!-- + DangerousThreadingAPI (weiwenli) + + DESCRIPTION: + Causes the runtime to fire a MDA message when someone attempts to call dangerous threading API. + + BEHAVIORAL IMPACT: + None. + + --> + <dangerousThreadingAPI enable="false" /> + + <!-- + DateTimeInvalidLocalFormat (amoore) + + ACTIVATION: + Activated by default under a managed debugger. + + DESCRIPTION: + Indicates when a DateTime instance that represents a UTC time is formatted with a format that should + only be used with local instances. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + An application is manually serializing a UTC DateTime instance using a local format: + + DateTime myDateTime = DateTime.UtcNow; + Serialize(myDateTime.ToString("yyyy-MM-dd'T'HH:mm:ss.fffffffzzz")); + + CAUSE: + The 'z' format for DateTime.ToString outputs the local time zone offset, e.g "+10:00" for Sydney time. + As such, it will only output a meaningful result if the value of the DateTime is local. If the value + is UTC, DateTime.ToString will still output the local time zone offset. + + CORRECTION: + UTC DateTime instances should be formatted in a way that indicates that they are UTC. The recommended + format for UTC times to use a 'Z' to denote UTC time: + + DateTime myDateTime = DateTime.UtcNow; + Serialize(myDateTime.ToString("yyyy-MM-dd'T'HH:mm:ss.fffffffZ")); + + There is also a short-hand "o" format that will serialize a DateTime making use of the DateTime.Kind + property that will serialize correctly regardless of whether the instance is Local, Utc or Unspecified: + + DateTime myDateTime = DateTime.UtcNow; + Serialize(myDateTime.ToString("o")); + + SYMPTOM: + An application is indirectly serializing a UTC DateTime with a library like XMLConvert or DataSet + serialization : + + DateTime myDateTime = DateTime.UtcNow; + String serialized = XMLConvert.ToString(myDateTime); + + CAUSE: + XmlConvert and DataSet serialization use local formats for serialization by default. + Additional options are required to serialize other kinds of DateTime, such as UTC. + + CORRECTION: + For XML Convert, pass in XmlConvertDateTimeOption.RoundTrip. + + DateTime myDateTime = DateTime.UtcNow; + String serialized = XmlConvert.ToString(myDateTime, XmlDateTimeSerializationMode.RoundtripKind); + + If using DataSet, set the DateTimeMode on the DataColumn object to DataSetDateTime.Utc. + + + --> + <dateTimeInvalidLocalFormat enable="false" /> + + <!-- + DirtyCastAndCallOnInterface (chriseck) + + DESCRIPTION: + A native component makes a call on an IUnknown or IDispatch interface without first QI-ing for the correct interface. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + AVs or unexpected memory corruption when making a call from native code into the CLR on a CCW. + + CAUSE: + Caller neglected to QI for the correct interface. + + OUTPUT: + An XML message specifying the violation. + --> + <dirtyCastAndCallOnInterface enable="false" /> + + <!-- + DisconnectedContext (chriseck) + + DESCRIPTION: + The CLR attempts to transition into a dead context while trying to service a request concerning a + COM object living in that dead context. This can happen while cleaning up RCWs or servicing QIs. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + Calls on RCWs living in dead contexts are not serviced, or cleanup of COM interface pointers occurs in + a context other than the one in which the interface pointers live. + + CAUSE: + The OLE context is disconnected. + + OUTPUT: + An XML message specifying the violation. + --> + <disconnectedContext enable="false" /> + + + <!-- + DllMainReturnsFalse (slidin) + + ACTIVATION: + Activated by default under a managed debugger. + --> + <dllMainReturnsFalse enable="false" /> + + <!-- + ExceptionSwallowedOnCallFromCom (dmortens) + + DESCRIPTION: + Causes the runtime to fire a MDA message when an error occurs while determining how to marshal the parameters + of a member member to be called from COM. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + A failure HRESULT is returned to COM without the managed method having been called. + + CAUSE: + This is most likely due to an incompatible MarshalAs attribute on one of the parameters. + + OUTPUT: + An XML message specifying the violation. + --> + <exceptionSwallowedOnCallFromCom enable="false" /> + + + <!-- + FailedQI (chriseck) + + DESCRIPTION: + Causes the runtime to fire a MDA message when the runtime calls QueryInterface on a COM interface pointer + on behalf of a RCW, and the QueryInterface call fails because the call was attempted in the wrong context or + because an OLE owned proxy returned a failure HRESULT. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + A cast on a RCW fails, or a call to COM from a RCW fails unexpectedly. + + CAUSE: + Calling from the wrong context or the registered proxy is failing the QueryInterface call. + + OUTPUT: + An XML message specifying the violation. + --> + <failedQI enable="false" /> + + + <!-- + GcManagedToUnmanaged (chrisk) + + DESCRIPTION: Causes a garbage collection whenever a thread transitions from managed to unmanaged + code (also see gcUnmanagedToManaged). + + SCENARIOS: + + SYMPTOM: An unmanaged user component AVs when trying to use a managed object which had been exposed to + COM. The COM object appears to have been released. The AV is non-deterministic. + + CAUSE: If an unmanaged component is not ref counting a managed COM object correctly + then the runtime could collect a managed object exposed to COM when the unmanaged component still + holds a reference to the object. The runtime calls release during GCs so if the user component uses the + object before the GC than it will not yet have been collected which is the source of the non-determinism. + Enabling this assistant will reduce the time between when the object is eligible for collection and release + is called helping to track down which unmanaged component first tries to access the collected object. + + OUTPUT: None + --> + <gcManagedToUnmanaged enable="false" /> + + <!-- + GcUnmanagedToManaged (chrisk) + + DESCRIPTION: + Causes a garbage collection whenever a thread transitions from unmanaged to + managed code (also see gcManagedToUnmanaged). + + BEHAVIORAL IMPACT: + This assistant changes the behavior of the runtime. When enabled more GC will occur. + + SCENARIOS: + + SYMPTOM: + An application running unmanaged user components (COM\PInvoke) is showing a non-deterministic AV + in runtime code. + + CAUSE: + If an application is running unmanaged user components then those components may have corrupted + the GC heap. This will cause the runtime to AV when the GC tries to walk the object graph. + Enabling this assistant will reduce the time between when the unmanaged component corrupts the GC + heap and when the AV happens by forcing a GC to occur before every managed transition. + + OUTPUT: None + --> + + <gcUnmanagedToManaged enable="false" /> + + + <!-- + IllegalPrepareConstrainedRegion (rudim) + + This is an error event. The RuntimeHelpers.PrepareConstrainedRegions() method (PCR) + call we use to mark exception handlers as introducing CERs in their catch/finally/fault/filter + blocks are only valid when used in that context. They must immediately precede the try + statement of the exception handler. (This is at the IL level, so it's obviously permissible + to have non-code generating source in between the two, such as comments). In the future + these markers will be generated by a compiler (from a new, higher level syntax for marking + CERs) and the code author won't have to worry about this. But until then we help the author + out by generating this MDA when the PCR call appears anywhere else in the code: + + If this MDA is firing the sort of symptoms you'd expect are probably as if CERs had + stopped working (i.e. runtime errors from jitting, thread aborts or generics lazy type + loading occurring inside CER regions). This is because they probably intended to declare + a CER region but failed by mispositioning the PCR call. + --> + <illegalPrepareConstrainedRegion enable="false" /> + + <!-- + InvalidApartmentStateChange (chriseck) + + DESCRIPTION: + Causes the runtime to fire a MDA message when someone attempts to change the COM apartment state of a thread which + has already been COM initialized to a different apartment state. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + A thread's COM apartment state is not what was requested. + + CAUSE: + The thread was previously initialized to a different COM apartment state. + + OUTPUT: + An XML message specifying the violation. + --> + <invalidApartmentStateChange enable="false" /> + + <!-- + InvalidCERCall (rudim) + + This is an error report. It occurs whenever a location within the CER graph + calls a method which has no reliability contract or an excessively weak contract. + A weak contract is one which declares that the worst case state corruption is of + greater scope than the instance passed to the call (i.e. the appdomain or process + state may become corrupted) or that its result is not always deterministically + computable when called within a CER. Either of these states indicates that the + code called may thwart the efforts of the rest of the CER to maintain consistent + state (CERs allow an author to treat errors in a very deterministic manner as a + way on maintaining whatever internal invariants are important to the particular + application and thus allow it to continue running in the face of transient errors + such as out of memory). + + In terms of reliability contract syntax a weak contract is one that does not specify + a Consistency enumeration or specifies ones one of Consistency.MayCorruptProcess or + Consistency.MayCorruptAppDomain or that does not specify a CER enumeration or specifies CER.None. + + When this probe fires there's a chance that the method being called in the CER + can fail in a way that the caller didn't expect or that leaves the appdomain or + process state corrupted or non-recoverable. Of course the called code may actually + work perfectly and the author merely hasn't gotten round to adding a contract. But + the issues involved in hardening code in this way are subtle and most "random" + code doesn't fall out this way. The contracts serve as markers that the author + has done their homework and hardened their algorithms and also as promises that + these guarantees will never backslide in future revisions of the code. (I.e. + they're declarations of intent rather than mere indicators of implementation). + + Because any method with a weak or non-existent contract may potentially fail in + all sorts of unpredictable manners anyway, the runtime doesn't attempt to remove + any of its own unpredictable failures from the method (introduced by lazy jitting + or generics dictionary population or thread aborts for instance). That is, when + this MDA fires it indicates that the runtime didn't include the called method in + the CER being defined; the call graph was pruned at this node (to carry on preparing + this sub-tree would just serve to help mask the potential error). + + So the symptoms this MDA may indicate are unfortunately very broad. They could see + an unexpected OutOfMemory or ThreadAbort exception (among others, we don't guarantee + the list) at the callsite into the "bad" method because the runtime didn't prepare + it ahead of time or protect it from ThreadAbort exceptions at runtime. But worse than + that, any exception that comes from this method at runtime could be leaving the + appdomain or process in a bad state, which is presumably counter to the wishes of + the CER author, since the only reason to declare a CER is to avoid large scale state + corruptions such as these in the first place. How corrupt state manifests itself is + very application specific (since the definition of consistent state belongs to the + application). + --> + <invalidCERCall enable="false" /> + + <!-- + InvalidFunctionPointerInDelegate (chriseck) + + DESCRIPTION: + An invalid function pointer is passed in to construct a delegate over a native function pointer. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + AVs or unexpected memory corruption when using a delegate over a function pointer. + + CAUSE: + An invalid function pointer was specified. + + OUTPUT: + An XML message specifying the violation. + --> + <invalidFunctionPointerInDelegate enable="false" /> + + <!-- + InvalidGCHandleCookie (chriseck) + + This error event is fired when an invalid IntPtr cookie->GCHandle retrieval is attempted. + The cookie is likely invalid because it was not originally created from a GCHandle, + represents a GCHandle that has already been freed, is a cookie to a GCHandle in + a different appdomain, or was marshaled to native code as a GCHandle but passed back into + the CLR as an IntPtr where a cast was attempted. + + The symptoms the user will see is undefined behavior (AVs, memory corruption, etc.) while + attempting to use or retrieve a GCHandle from a IntPtr. + --> + <invalidGCHandleCookie enable="false" /> + + + <!-- + InvalidIUnknown (chriseck) + + DESCRIPTION: + An invalid IUnknown* is passed to managed code from native code. The IUnknown fails to return success + when queried for the IUnknown interface. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + Unexpected error when marshaling a COM interface pointer during argument marshaling. + + CAUSE: + A misbehaving QueryInterface implemenation on the COM interface passed to the runtime. + + OUTPUT: + An XML message specifying the violation. + --> + <invalidIUnknown enable="false" /> + + <!-- + InvalidMemberDeclaration (dmortens) + + DESCRIPTION: + Causes the runtime to fire a MDA message when an error occurs while determining how to marshal the parameters + of a member member to be called from COM. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + A failure HRESULT is returned to COM without the managed method having been called. + + CAUSE: + This is most likely due to an incompatible MarshalAs attribute on one of the parameters. + + OUTPUT: + An XML message specifying the violation. + --> + <invalidMemberDeclaration enable="false" /> + + <!-- + InvalidOverlappedToPinvoke (mstanton) + + DESCRIPTION: + This probe fires when an overlapped pointer not created on the gc heap is passed to a popular + Win32 function. The potential for heap corruption is high when this is done because the + AppDomain where the call is made may unload. In that case, the user code will either free + the memory for the overlapped pointer, causing corruption when the operation finishes, or + the code will leak the memory, causing difficulties later. + + Here are the functions that this MDA tracks: + + Module Function + HttpApi.dll HttpReceiveHttpRequest + IpHlpApi.dll NotifyAddrChange + IpHlpApi.dll NotifyRouteChange + kernel32.dll ReadFile + kernel32.dll ReadFileEx + kernel32.dll WriteFile + kernel32.dll WriteFileEx + kernel32.dll ReadDirectoryChangesW + kernel32.dll PostQueuedCompletionStatus + MSWSock.dll ConnectEx + WS2_32.dll WSASend + WS2_32.dll WSASendTo + WS2_32.dll WSARecv + WS2_32.dll WSARecvFrom + MQRT.dll MQReceiveMessage + + The way to fix this problem is to use a System.Threading.Overlapped object, calling + Overlapped.Pack() to get a NativeOverlapped structure that can be passed to the + function. If the AppDomain unloads, the CLR will wait until the async operation completes + before freeing the pointer. + + Note that this MDA is by default only fires if the P/Invoke is defined in your + code, using your debugger to report the JustMyCode status of each method. + A debugger that doesn't understand JustMyCode (such as mdbg with no extensions) + will not let this MDA fire. You can activate this MDA using a config file + if you explicitly set justMyCode="false" in your .mda.config file. + + OUTPUT: + An XML message specifying the overlapped pointer address, the module name, and the win32 + function that was called. + --> + <invalidOverlappedToPinvoke enable="false" justMyCode="true"/> + + + <!-- + InvalidVariant (chriseck) + + DESCRIPTION: + Causes the runtime to fire a MDA message when an invalid VARIANT structure is encountered. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + Unexpected behavior during a transition between native and managed code involving the marshaling + of an object to a VARIANT or vice versa. + + CAUSE: + The native code is passing a malformed VARIANT structure to the runtime. + + OUTPUT: + An XML message specifying the violation. + --> + <invalidVariant enable="false" /> + + + <!-- + JitCompilationStart (chrisk) + + DESCRIPTION: + Enabling this assistant causes a message to be generated whenever a method which matches the filter is jitted. + This assistant was primarily used to test the MDA framework but could also be used. + + BEHAVIORAL IMPACT: + None. The performance difference should also be negligible as this assistant is only fired when the method is + first jitted. + + SCENARIOS: + + SYMPTOM: + clrjit.dll is loaded in a performance scenario in which all assemblies are ngened. + + CAUSE: + This would likely be a bug in the runtime. Enabling this assistant will help determine which method is + being jitted. + + OUTPUT: + Methods which match the filter that are being jitted. + --> + <jitCompilationStart enable="false"> + <methods justMyCode="true"> + <match break="false" name="MyMethod" /> + </methods> + </jitCompilationStart > + + <!-- + LoaderLock (cbrumme) + + DESCRIPTION: + It is unsafe to execute managed code on a thread that holds the operating system's LoaderLock. + Violating this rule can lead to deadlocks or calls into DLLs that have not yet been initialized. + Such failures are somewhat random and can appear or disappear from run to run of a process. + On some platforms, we can detect whether the current thread holds the LoaderLock during a + transition from native to managed code. + + BEHAVIORAL IMPACT: + The extra checks can cause a slight slowdown on calls from native code to managed code. This + slowdown is on the order of 10 instructions. + + --> + <loaderLock enable="false" /> + + + <!-- + LoadFromContext (t-daveh) + + DESCRIPTION: + This probe fires when an Assembly loads in the LoadFrom binding context. This happens on some but not all calls + to Assembly.LoadFrom and can also occur when loading dependencies for a separate Assembly loading call. + + SCENARIOS: + This probe is primarily intended for use in debugging Assembly binding failures, which often occur because a call + to Assembly.LoadFrom does not imply that the Assembly will be loaded in the LoadFrom context. Binding contexts + affect Assembly behavior, and in almost all cases it is recommended that the LoadFrom context be avoided. See + http://blogs.msdn.com/suzcook/archive/2003/05/29/57143.aspx for more information. + + BEHAVIORAL IMPACT: None. + + OUTPUT: An MDA message is output for each Assembly loaded in the LoadFrom context. It includes the display name + of the Assembly and its code base. + --> + <loadFromContext enable="false" /> + + + <!-- + MarshalCleanupError (chriseck) + + DESCRIPTION: + The CLR encounters an error while attempting to clean up temporary structures and memory required for marshaling data types between + native / managed code boundaries. It is likely that a memory leak will occur. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + Memory leak occurs when making native / managed code transitions, runtime state such as thread culture is not restored, or errors occur + in SafeHandle cleanup. + + CAUSE: + An unexpected error occurred while cleaning up temporary structures. Review all SafeHandle destructor / finalizer implementations and + custom-marshaler implementations for errors. + + OUTPUT: + An XML message specifying the encountered problem. + --> + <marshalCleanupError enable="false" /> + + <!-- + Reflection (chrisk) + + DESCRIPTION: + This probe fires when reflection creates a MemberInfo cache. This happens on calls to + Type.GetMethod, Type.GetProperty, Type.GetField etc. Creation of this cache is expensive in working set + because it pages in metadata which is usually stored in a cold section of the PE file and because + reflection eagerly caches MemberInfos. The Reflection team has plans in Beta2 to make the cache lazy. + + SCENARIOS: + This probe is primarily intended for use in a regression test which ensures that "heavy" reflection is + not used is an optimized scenario. + + BEHAVIORAL IMPACT: None. + + OUTPUT: A MDA message is output for each time a MemberInfoCache is created. + --> + <memberInfoCacheCreation enable="false"/> + + <!-- + ModuloObjectHashcode (chrisk) + + DESCRIPTION: + Enabling this assistant causes Object.GetHashcode to return the modulus of the hashcode it would + have otherwise returned. This does not affect any other implementation of GetHashcode. + + BEHAVIORAL IMPACT: + See Description. + + SCENARIOS: + + SYMPTOM: + Varied. Generally, after debugging, it is discovered that an object with the wrong identity + is being manipulated. + + CAUSE: + Program is using an objects hashcode to identify the object. While it is true that if two + object references are the same their hashcodes are the same, the converse is not true. If two + object references have the same hashcodes that does not imply they refer to the same object. + Making this assumption will cause incorrect program behavior in the very rare case when it is false. + Enabling this assistant will make it much more likely to have "hashcode collisions" and flesh out bugs. + + OUTPUT: None + --> + <moduloObjectHashcode modulus="1" enable="false" /> + + <!-- + NonComVisibleBaseClass (dmortens) + + This error event is fired when a QueryInterface call is made on a CCW requesting the class + interface or the default IDispatch, not implemented by an explicit interface, of a COM visible + managed class that derives from a non COM visible base class. + + The symptoms the user will see is the QueryInterface call failing with a + COR_E_INVALIDOPERATION HRESULT. + --> + <nonComVisibleBaseClass enable="false" /> + + + <!-- + NotMarshalable (chriseck) + + DESCRIPTION: + The CLR encounters a COM interface pointer with no valid proxy/stub registered or a misbehaving IMarshalable implementation while attempting + to marshal the interface across contexts. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + Calls are not serviced, or calls occur in the wrong context for COM interface pointers. + + CAUSE: + The CLR encounters a COM interface pointer with no valid proxy/stub registered or a misbehaving IMarshalable implementation. + + OUTPUT: + An XML message specifying the violation. + --> + <notMarshalable enable="false" /> + + <!-- + OpenGenericCERCall (rudim) + + This event is a warning. It is generated when a CER graph with generic type + variables at the root method is being processed at jit/ngen time and at least + one of the generic type variables is an object reference type. Since at jit time + an instantiation containing an object reference type is only representative (the + resultant code is shared such that each of the object reference type variables may + in fact be any object reference type) we cannot guarantee prepare all runtime + resources ahead of time. In particular methods with generic type variables sometimes + lazily allocate resources behind the user's back (these are referred to as generic + dictionary entries). For instance the statement "List<T> list = new List<T>();" where + T is a generic type variable will need to lookup and possibly create the exact + instantiation (e.g. List<Object>, List<String> etc.) at runtime and this might + fail for a variety of reasons beyond the author's control (out of memory, for instance). + + This probe shouldn't fire for any of the non-jit cases (they always provide an + exact instantiation to work with). + + When this probe fires the likely symptoms you might see are that CERs will appear not + to work at all for the bad instantiations (in fact we don't even attempt to implement + a CER in the circumstances where the event fires). So if the author uses a shared + instantiation of the CER they will not avoid runtime injected jit or generics type + loading errors or thread aborts within the region of the supposed CER. + --> + <openGenericCERCall enable="false" /> + + <!-- + OverlappedFreeError (mstanton) + + DESCRIPTION: + This probe fires if code calls System.Threading.Overlapped.Free(NativeOverlapped *) before + the overlapped operation has completed. The overlapped operation needs to be cancelled + before this. + + OUTPUT: + An XML message specifying the overlapped pointer address that was freed pre-maturely. + --> + <overlappedFreeError enable="false" /> + + <!-- + PInvokeLog (chrisk) + + DESCRIPTION: + Logs a message the first time a PInvoke call is call is made. + + OUTPUT: + An XML message specifying the managed PInvoke signature and target which was called for the first time. + --> + <pInvokeLog enable="false" /> + + <!-- + PInvokeStackImbalance (chrisk) + + DESCRIPTION: + Causes the runtime to compare the actual stack depth before and after a PInvoke call against + what the call depth should be given the calling conventions specified in the DllImport attribute + and the arguments. If the depths do not agree than the MDA will fire. (Future versions of this + assistant will also check the stack depth of "reverse-PInvoke" or calling back into managed code via + a function pointer representing a managed delegate.) + + BEHAVIORAL IMPACT: + This assistants disables PInvoke marshaling optimizations and so PInvoke calls will be slower. + + ACTIVATION: + Activated by default under a managed debugger. + + SCENARIOS: + + SYMPTOM: + An application AVs when placing or just after placing a PInvoke call. + + CAUSE: + Very likely that the managed signature, the DllImportAttribute, does not match the unmanaged + signature. Either the number or size of the parameters does not match or the calling convention + does not match. Try explicitly specifying the calling convention on both the managed and unmanaged + sides. It is also possible, though much less likely, that the unmanaged function unbalanced the + stack for some other reason such as a bug in the unmanaged compiler. + + OUTPUT: + An XML message specifying the managed PInvoke signature which detected the unbalanced stack. + --> + <pInvokeStackImbalance enable="false" /> + + <!-- + RaceOnRCWCleanup (chriseck) + + DESCRIPTION: + Causes the runtime to fire a MDA message when it detects that a RCW is in use while the user attempts + to free it via Marshal.ReleaseComObject or other such construct. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + + SYMPTOM: + AVs or memory corruption during or after freeing a RCW via Marshal.ReleaseComObject or other such construct. + + CAUSE: + The RCW is in use on another thread or further up the freeing thread stack. It is illegal to free + a RCW that is in use. + + OUTPUT: + An XML message specifying the violation. + --> + <raceOnRCWCleanup enable="false" /> + + <!-- + Reentrancy (cbrumme) + + DESCRIPTION: + Threads that switch between native and managed code in either direction must perform an + orderly transition. However, certain low level extensibility points in the operating system + (like the Vectored Exception Handler) allow switches from managed to native code without + performing an orderly transition. Any native code that executes inside these extensibility points + must avoid calling back into managed code. If this rule is violated, the object heap can become + corrupted and other serious errors can occur. This assistant can detect attempts to transition + from native to managed code in cases where a prior switch from managed to native code was + not performed through an orderly transition. + + BEHAVIORAL IMPACT: + The extra checks can cause a slight slowdown on calls from native code to managed code. This + slowdown is on the order of 5 instructions. + + --> + <reentrancy enable="false" /> + + + <!-- + ReleaseHandleFailed (rudim) + + This is an error event. It fired when the ReleaseHandle method of a SafeHandle or + CriticalHandle subclass returns false. These methods are provided by the author subclassing + SafeHandle or CriticalHandle so the circumstances are handle specific, but the contract + is the following: + + Safe and critical handles represent wrappers around vital process resources that + cannot be permitted to leak (otherwise the process will become unusable over time). + + Therefore the ReleaseHandle method must not fail to perform its function + (once we've acquired such a resource, ReleaseHandle is the only means we have + of releasing it, so failure implies resource leakage). + + Therefore any failure which does occur during ReleaseHandle (and impedes the + release of the resource) is a serious bug on the part of the author of the ReleaseHandle + method itself (it is their responsibility to make sure the contract is fulfilled, even + if they're calling other people's code to achieve the end effect). + + To aid in debugging such leaks we allow ReleaseHandle to return a boolean result and + if that result is false we generate this MDA with some state information that might + help track down the problem. (We used to throw an IOException in earlier builds of Whidbey). + + The symptoms the user might see in situations where this MDA fires is resource + leakage (for whatever resource the safe or critical handle is a wrapper for or at + least handles against that resource which can be scarce in their own rite). + --> + <releaseHandleFailed enable="false" /> + + + <!-- + ReportAvOnComRelease (chriseck) + + DESCRIPTION: + Occasionally an exception is thrown due to user refcount errors while performing COM Interop and + using Marshal.Release or Marshal.ReleaseComObject mixed with raw COM calls. Today, this exception + is simply discarded, since not doing so would cause an AV in the runtime and bring it down. Using + this assistant, such exceptions can be detected and reported instead of simply discarded. + + Two modes are available " if AllowAV is true, then the assistant simply strips the exception handling + from the function. If it is false (by default), then the exception handling occurs, but a warning + message is reported to the user to indicate that an exception was handled. + --> + <reportAvOnComRelease allowAv="false" enable="false" /> + + <!-- + Marshaling (chriseck) + + DESCRIPTION: + This assistant fires when the CLR sets up marshaling information for a method parameter or a field of a structure. + It prints out the type of the parameter or field both in the managed and unmanaged worlds, as well as indicating + the structure or method where the type lives. + <marshaling enable="false" /> + --> + + + <!-- + StreamWriterBufferedDataLost (BrianGru) + + DESCRIPTION: + Intended to detect when users write data to a StreamWriter but + don't flush or close the StreamWriter. That data is then lost, + because StreamWriter cannot reliably write data to the underlying + Stream from its finalizer. Users should use a using block when + possible to ensure they always close the StreamWriter. + + Poorly written code: + void Foo() { + StreamWriter sw = new StreamWriter("file.txt"); + sw.WriteLine("Data"); + // Forgot to close the StreamWriter. + } + + This MDA was implemented by adding a finalizer to StreamWriter + that looks for data in its buffer. As such, it requires your + program to get around to running finalizers before exiting. + This should happen in long-running apps automatically over time, + but can be forced in short-lived test apps (like the above) by + calling GC.Collect then GC.WaitForPendingFinalizers. + + BEHAVIORAL IMPACT: + None. + + SCENARIOS: + SYMPTOM: + User attempts to write to a file, but the last 1K - 4K of data + haven't been written to the file. This MDA detects this + data loss during finalization of the StreamWriter. + + CAUSE: + User did not properly close their StreamWriter, or arrange for + it to be flushed. + + CORRECTION: + Use the using statement in C# & VB. In managed C++, use a + try/finally to call Dispose. + + void Foo() { + using(StreamWriter sw = new StreamWriter("file.txt")) { + sw.WriteLine("Data"); + } + } + + Or users can use the long form, expanding out the using clause: + + void Foo() { + StreamWriter sw; + try { + sw = new StreamWriter("file.txt")); + sw.WriteLine("Data"); + } + finally { + if (sw != null) + sw.Close(); + } + } + + If neither of these solutions can be used (say, if you have a + StreamWriter stored in a static variable and thus you cannot + easily run code at the end of its lifetime), then calling Flush + on the StreamWriter after its last use or setting its AutoFlush + property to true before its first use will be sufficient. + Here's an example: + + internal static class Foo { + private static StreamWriter _log; + + static Foo() { // Static class constructor + StreamWriter sw = new StreamWriter("log.txt"); + sw.AutoFlush = true; + // Now publish the StreamWriter for other threads. + _log = sw; + } + } + + OUTPUT: + An XML message, indicating this violation occurred. To the + effect of "You lost data because you didn't close your + StreamWriter." It may include a file name and a stack trace + showing where the StreamWriter was allocated, to help track + down incorrect code. + --> + <streamWriterBufferedDataLost enable="true" captureAllocatedCallStack="false"/> + + + <!-- + VirtualCERCall (rudim) + + This is just a warning. It indicates that a callsite within a CER call graph + refers to a virtual target (i.e. a virtual call to a non-final virtual method + or a call via an interface). The runtime cannot predict the destination method + of these calls from IL and metadata analysis alone (which is all we have), so + we won't descend into that call tree and prepare it as part of the CER graph (or + automatically block thread aborts in that subtree either). So this warns of cases + where a CER might need to be extended manually via explicit calls to PrepareMethod() + (once the additional information required to compute the call target is known at + runtime). + + Symptoms of a problem reported via this probe are pretty much the same as above. The + callsite can experience a failure from the runtime if the target wasn't explicitly + prepared by another means (e.g. PrepareMethod) and it's not defined whether or not + the code to be run meets any reliability contracts since the runtime couldn't scan + ahead to tell. If the eventual target wasn't hardened for deterministic operation + then it could surprise the author of the CER as above. + + --> + <virtualCERCall enable="false" /> + + </assistants> +</mdaConfig> + + + |