1// Licensed to the .NET Foundation under one or more agreements.
2// The .NET Foundation licenses this file to you under the MIT license.
3// See the LICENSE file in the project root for more information.
4//
5
6//
7
8
9#ifndef __ExInfo_h__
10#define __ExInfo_h__
11#if !defined(WIN64EXCEPTIONS)
12
13#include "exstatecommon.h"
14
15typedef DPTR(class ExInfo) PTR_ExInfo;
16class ExInfo
17{
18 friend class ThreadExceptionState;
19 friend class ClrDataExceptionState;
20
21public:
22
23 BOOL IsHeapAllocated()
24 {
25 LIMITED_METHOD_CONTRACT;
26 return m_StackAddress != (void *) this;
27 }
28
29 void CopyAndClearSource(ExInfo *from);
30
31 void UnwindExInfo(VOID* limit);
32
33 // Q: Why does this thing take an EXCEPTION_RECORD rather than an ExceptionCode?
34 // A: Because m_ExceptionCode and Ex_WasThrownByUs have to be kept
35 // in sync and this function needs the exception parms inside the record to figure
36 // out the "IsTagged" part.
37 void SetExceptionCode(const EXCEPTION_RECORD *pCER);
38
39 DWORD GetExceptionCode()
40 {
41 LIMITED_METHOD_CONTRACT;
42 return m_ExceptionCode;
43 }
44
45public: // @TODO: make more of these private!
46 // Note: the debugger assumes that m_pThrowable is a strong
47 // reference so it can check it for NULL with preemptive GC
48 // enabled.
49 OBJECTHANDLE m_hThrowable; // thrown exception
50 PTR_Frame m_pSearchBoundary; // topmost frame for current managed frame group
51private:
52 DWORD m_ExceptionCode; // After a catch of a COM+ exception, pointers/context are trashed.
53public:
54 PTR_EXCEPTION_REGISTRATION_RECORD m_pBottomMostHandler; // most recent EH record registered
55
56 // Reference to the topmost handler we saw during an SO that goes past us
57 PTR_EXCEPTION_REGISTRATION_RECORD m_pTopMostHandlerDuringSO;
58
59 LPVOID m_dEsp; // Esp when fault occurred, OR esp to restore on endcatch
60
61 StackTraceInfo m_StackTraceInfo;
62
63 PTR_ExInfo m_pPrevNestedInfo; // pointer to nested info if are handling nested exception
64
65 size_t* m_pShadowSP; // Zero this after endcatch
66
67 PTR_EXCEPTION_RECORD m_pExceptionRecord;
68 PTR_EXCEPTION_POINTERS m_pExceptionPointers;
69 PTR_CONTEXT m_pContext;
70
71 // We have a rare case where (re-entry to the EE from an unmanaged filter) where we
72 // need to create a new ExInfo ... but don't have a nested handler for it. The handlers
73 // use stack addresses to figure out their correct lifetimes. This stack location is
74 // used for that. For most records, it will be the stack address of the ExInfo ... but
75 // for some records, it will be a pseudo stack location -- the place where we think
76 // the record should have been (except for the re-entry case).
77 //
78 //
79 //
80 void* m_StackAddress; // A pseudo or real stack location for this record.
81
82#ifndef FEATURE_PAL
83private:
84 EHWatsonBucketTracker m_WatsonBucketTracker;
85public:
86 inline PTR_EHWatsonBucketTracker GetWatsonBucketTracker()
87 {
88 LIMITED_METHOD_CONTRACT;
89 return PTR_EHWatsonBucketTracker(PTR_HOST_MEMBER_TADDR(ExInfo, this, m_WatsonBucketTracker));
90 }
91#endif
92
93#ifdef FEATURE_CORRUPTING_EXCEPTIONS
94private:
95 CorruptionSeverity m_CorruptionSeverity;
96public:
97 inline CorruptionSeverity GetCorruptionSeverity()
98 {
99 LIMITED_METHOD_CONTRACT;
100
101 return (CorruptionSeverity)GET_CORRUPTION_SEVERITY(m_CorruptionSeverity);
102 }
103
104 inline void SetCorruptionSeverity(CorruptionSeverity severityToSet)
105 {
106 LIMITED_METHOD_CONTRACT;
107
108 m_CorruptionSeverity = severityToSet;
109 }
110#endif // FEATURE_CORRUPTING_EXCEPTIONS
111
112private:
113 BOOL m_fDeliveredFirstChanceNotification;
114public:
115 inline BOOL DeliveredFirstChanceNotification()
116 {
117 LIMITED_METHOD_CONTRACT;
118
119 return m_fDeliveredFirstChanceNotification;
120 }
121
122 inline void SetFirstChanceNotificationStatus(BOOL fDelivered)
123 {
124 LIMITED_METHOD_CONTRACT;
125
126 m_fDeliveredFirstChanceNotification = fDelivered;
127 }
128
129 // Returns the exception tracker previous to the current
130 inline PTR_ExInfo GetPreviousExceptionTracker()
131 {
132 LIMITED_METHOD_CONTRACT;
133
134 return m_pPrevNestedInfo;
135 }
136
137 // Returns the throwable associated with the tracker
138 inline OBJECTREF GetThrowable()
139 {
140 LIMITED_METHOD_CONTRACT;
141
142 return (m_hThrowable != NULL)?ObjectFromHandle(m_hThrowable):NULL;
143 }
144
145 // Returns the throwble associated with the tracker as handle
146 inline OBJECTHANDLE GetThrowableAsHandle()
147 {
148 LIMITED_METHOD_CONTRACT;
149
150 return m_hThrowable;
151 }
152
153public:
154
155 DebuggerExState m_DebuggerExState;
156 EHClauseInfo m_EHClauseInfo;
157 ExceptionFlags m_ExceptionFlags;
158
159#if defined(_TARGET_X86_) && defined(DEBUGGING_SUPPORTED)
160 EHContext m_InterceptionContext;
161 BOOL m_ValidInterceptionContext;
162#endif
163
164#ifdef DACCESS_COMPILE
165 void EnumMemoryRegions(CLRDataEnumMemoryFlags flags);
166#endif
167
168 void Init();
169 ExInfo() DAC_EMPTY();
170
171 void DestroyExceptionHandle();
172
173private:
174 // Don't allow this
175 ExInfo& operator=(const ExInfo &from);
176};
177
178#if defined(_TARGET_X86_)
179PTR_ExInfo GetEHTrackerForPreallocatedException(OBJECTREF oPreAllocThrowable, PTR_ExInfo pStartingEHTracker);
180#endif // _TARGET_X86_
181
182#endif // !WIN64EXCEPTIONS
183#endif // __ExInfo_h__
184