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** Header: DebugDebugger.h
8**
9** Purpose: Native methods on System.Debug.Debugger
10**
11**
12
13===========================================================*/
14
15#ifndef __DEBUG_DEBUGGER_h__
16#define __DEBUG_DEBUGGER_h__
17#include <object.h>
18
19
20class DebugDebugger
21{
22public:
23 static FCDECL0(void, Break);
24 static FCDECL0(FC_BOOL_RET, Launch);
25 static FCDECL0(FC_BOOL_RET, IsDebuggerAttached);
26 static FCDECL3(void, Log, INT32 Level, StringObject* strModule, StringObject* strMessage);
27
28 // receives a custom notification object from the target and sends it to the RS via
29 // code:Debugger::SendCustomDebuggerNotification
30 static FCDECL1(void, CustomNotification, Object * dataUNSAFE);
31
32 static FCDECL0(FC_BOOL_RET, IsLogging);
33
34protected:
35 static BOOL IsLoggingHelper();
36};
37
38
39class StackFrameHelper : public Object
40{
41 // READ ME:
42 // Modifying the order or fields of this object may require other changes to the
43 // classlib defintion of the StackFrameHelper class.
44public:
45 THREADBASEREF targetThread;
46 I4ARRAYREF rgiOffset;
47 I4ARRAYREF rgiILOffset;
48 PTRARRAYREF dynamicMethods;
49 BASEARRAYREF rgMethodHandle;
50 PTRARRAYREF rgAssemblyPath;
51 BASEARRAYREF rgLoadedPeAddress;
52 I4ARRAYREF rgiLoadedPeSize;
53 BASEARRAYREF rgInMemoryPdbAddress;
54 I4ARRAYREF rgiInMemoryPdbSize;
55 // if rgiMethodToken[i] == 0, then don't attempt to get the portable PDB source/info
56 I4ARRAYREF rgiMethodToken;
57 PTRARRAYREF rgFilename;
58 I4ARRAYREF rgiLineNumber;
59 I4ARRAYREF rgiColumnNumber;
60
61 BOOLARRAYREF rgiLastFrameFromForeignExceptionStackTrace;
62
63 int iFrameCount;
64
65protected:
66 StackFrameHelper() {}
67 ~StackFrameHelper() {}
68
69public:
70 void SetFrameCount(int iCount)
71 {
72 iFrameCount = iCount;
73 }
74
75 int GetFrameCount(void)
76 {
77 return iFrameCount;
78 }
79
80};
81
82#ifdef USE_CHECKED_OBJECTREFS
83typedef REF <StackFrameHelper> STACKFRAMEHELPERREF;
84#else
85typedef StackFrameHelper* STACKFRAMEHELPERREF;
86#endif
87
88
89class DebugStackTrace
90{
91public:
92
93#ifndef DACCESS_COMPILE
94// the DAC directly uses the GetStackFramesData and DebugStackTraceElement types
95private:
96#endif // DACCESS_COMPILE
97 struct DebugStackTraceElement {
98 DWORD dwOffset; // native offset
99 DWORD dwILOffset;
100 MethodDesc *pFunc;
101 PCODE ip;
102 // TRUE if this element represents the last frame of the foreign
103 // exception stack trace.
104 BOOL fIsLastFrameFromForeignStackTrace;
105
106 // Initialization done under TSL.
107 // This is used when first collecting the stack frame data.
108 void InitPass1(
109 DWORD dwNativeOffset,
110 MethodDesc *pFunc,
111 PCODE ip
112 , BOOL fIsLastFrameFromForeignStackTrace = FALSE
113 );
114
115 // Initialization done outside the TSL.
116 // This will init the dwILOffset field (and potentially anything else
117 // that can't be done under the TSL).
118 void InitPass2();
119 };
120
121public:
122
123 struct GetStackFramesData {
124
125 // Used for the integer-skip version
126 INT32 skip;
127 INT32 NumFramesRequested;
128 INT32 cElementsAllocated;
129 INT32 cElements;
130 DebugStackTraceElement* pElements;
131 THREADBASEREF TargetThread;
132 AppDomain *pDomain;
133 BOOL fDoWeHaveAnyFramesFromForeignStackTrace;
134
135
136 GetStackFramesData() : skip(0),
137 NumFramesRequested (0),
138 cElementsAllocated(0),
139 cElements(0),
140 pElements(NULL),
141 TargetThread((THREADBASEREF)(TADDR)NULL)
142 {
143 LIMITED_METHOD_CONTRACT;
144 fDoWeHaveAnyFramesFromForeignStackTrace = FALSE;
145
146 }
147
148 ~GetStackFramesData()
149 {
150 delete [] pElements;
151 }
152 };
153
154 static FCDECL4(void,
155 GetStackFramesInternal,
156 StackFrameHelper* pStackFrameHelper,
157 INT32 iSkip,
158 CLR_BOOL fNeedFileInfo,
159 Object* pException
160 );
161
162 static void GetStackFramesFromException(OBJECTREF * e, GetStackFramesData *pData, PTRARRAYREF * pDynamicMethodArray = NULL);
163
164#ifndef DACCESS_COMPILE
165// the DAC directly calls GetStackFramesFromException
166private:
167#endif
168
169 static void GetStackFramesHelper(Frame *pStartFrame, void* pStopStack, GetStackFramesData *pData);
170
171 static void GetStackFrames(Frame *pStartFrame, void* pStopStack, GetStackFramesData *pData);
172
173 static StackWalkAction GetStackFramesCallback(CrawlFrame* pCf, VOID* data);
174
175};
176
177#endif // __DEBUG_DEBUGGER_h__
178