Merge pull request #23934 from franksinankaya/gcc_cleanup_18
[platform/upstream/coreclr.git] / src / ilasm / method.hpp
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 // method.hpp
6 //
7 #ifndef _METHOD_HPP
8 #define _METHOD_HPP
9
10 class Assembler;
11 class PermissionDecl;
12 class PermissionSetDecl;
13
14 #define MAX_EXCEPTIONS 16   // init.number; increased by 16 when needed
15
16 extern unsigned int g_uCodePage;
17 extern WCHAR    wzUniBuf[];
18
19 /**************************************************************************/
20 struct LinePC
21 {
22     ULONG   Line;
23     ULONG   Column;
24     ULONG   LineEnd;
25     ULONG   ColumnEnd;
26     ULONG   PC;
27     ISymUnmanagedDocumentWriter* pWriter;
28 };
29 typedef FIFO<LinePC> LinePCList;
30
31
32 struct PInvokeDescriptor
33 {
34     mdModuleRef mrDll;
35     char*   szAlias;
36     DWORD   dwAttrs;
37 };
38
39 struct TokenRelocDescr // for OBJ generation only!
40 {
41     DWORD   offset;
42     mdToken token;
43     TokenRelocDescr(DWORD off, mdToken tk) { offset = off; token = tk; };
44 };
45 typedef FIFO<TokenRelocDescr> TRDList;
46 /* structure - element of [local] signature name list */
47
48 struct  ARG_NAME_LIST
49 {
50     LPCUTF8 szName; //szName[1024];
51     DWORD dwName;
52     BinStr*   pSig; // argument's signature  ptr
53     BinStr*   pMarshal;
54     BinStr*   pValue;
55     int  nNum;
56     DWORD     dwAttr;
57     CustomDescrList CustDList;
58     ARG_NAME_LIST *pNext;
59     __forceinline ARG_NAME_LIST(int i, LPCUTF8 sz, BinStr *pbSig, BinStr *pbMarsh, DWORD attr)
60     {
61         nNum = i;
62         //dwName = (DWORD)strlen(sz);
63         //strcpy(szName,sz);
64         szName = sz;
65         dwName = (sz == NULL) ? 0 : (DWORD)strlen(sz);
66         pNext = NULL;
67         pSig=pbSig;
68         pMarshal = pbMarsh;
69         dwAttr = attr;
70         pValue=NULL;
71     };
72     inline ~ARG_NAME_LIST()
73     {
74         if(pSig) delete pSig;
75         if(pMarshal) delete pMarshal;
76         if(pValue) delete pValue;
77         if(szName) delete [] szName;
78     }
79 };
80
81 class Scope;
82 typedef FIFO<Scope> ScopeList;
83 class Scope
84 {
85 public:
86     DWORD   dwStart;
87     DWORD   dwEnd;
88     ARG_NAME_LIST*  pLocals;
89     ScopeList       SubScope;
90     Scope*          pSuperScope;
91     Scope() { dwStart = dwEnd = 0; pLocals = NULL; pSuperScope = NULL; };
92     ~Scope() { Reset(); };
93     void Reset()
94     {
95         ARG_NAME_LIST* pNext;
96         while(pLocals) { pNext = pLocals->pNext; delete pLocals; pLocals = pNext; }
97         Scope* pS;
98         while((pS = SubScope.POP()) != NULL) delete pS;
99         pSuperScope = NULL;
100         dwStart = dwEnd = 0;
101     };
102 };
103 struct VarDescr
104 {
105     DWORD   dwSlot;
106     BinStr* pbsSig;
107     BOOL    bInScope;
108     VarDescr() { dwSlot = (DWORD) -1; pbsSig = NULL; bInScope = FALSE; };
109 };
110 typedef FIFO<VarDescr> VarDescrList;
111
112
113 struct Label
114 {
115 //public:
116     LPCUTF8  m_szName;
117     DWORD   m_PC;
118
119     Label() :m_szName(NULL),m_PC(0){};
120     Label(LPCUTF8 pszName, DWORD PC):m_szName(pszName),m_PC(PC){};
121     ~Label(){ delete [] m_szName; };
122     int ComparedTo(Label* L) { return strcmp(m_szName,L->m_szName); };
123     //int Compare(char* L) { return strcmp(L,m_szName); };
124     LPCUTF8 NameOf() { return m_szName; };
125 };
126 //typedef SORTEDARRAY<Label> LabelList;
127 typedef FIFO_INDEXED<Label> LabelList;
128
129 class GlobalFixup
130 {
131 public:
132     LPCUTF8  m_szLabel;
133     BYTE *  m_pReference;               // The place to fix up
134
135     GlobalFixup(LPCUTF8 pszName, BYTE* pReference)
136     {
137         m_pReference   = pReference;
138         m_szLabel = pszName;
139     }
140     ~GlobalFixup(){ delete [] m_szLabel; }
141 };
142 typedef FIFO<GlobalFixup> GlobalFixupList;
143
144
145 class Fixup
146 {
147 public:
148     LPCUTF8  m_szLabel;
149     BYTE *  m_pBytes; // where to make the fixup
150     DWORD   m_RelativeToPC;
151     BYTE    m_FixupSize;
152
153     Fixup(LPCUTF8 pszName, BYTE *pBytes, DWORD RelativeToPC, BYTE FixupSize)
154     {
155         m_pBytes        = pBytes;
156         m_RelativeToPC  = RelativeToPC;
157         m_FixupSize     = FixupSize;
158         m_szLabel = pszName;
159     }
160     ~Fixup(){ delete [] m_szLabel; }
161 };
162 typedef FIFO<Fixup> FixupList;
163
164 typedef enum { ilRVA, ilToken, ilGlobal} ILFixupType;
165
166 class ILFixup
167 {
168 public:
169     ILFixupType   m_Kind;
170     DWORD         m_OffsetInMethod;
171     GlobalFixup * m_Fixup;
172
173     ILFixup(DWORD Offset, ILFixupType Kind, GlobalFixup *Fix)
174     {
175       m_Kind           = Kind;
176       m_OffsetInMethod = Offset;
177       m_Fixup          = Fix;
178     }
179 };
180 typedef FIFO<ILFixup> ILFixupList;
181
182 class Method
183 {
184 public:
185     Class  *m_pClass;
186     //BinStr **m_TyParBounds;
187     //LPCWSTR *m_TyParNames;
188     TyParDescr* m_TyPars;
189     DWORD   m_NumTyPars;
190     DWORD   m_SigInfoCount;
191     USHORT  m_MaxStack;
192     mdSignature  m_LocalsSig;
193     DWORD   m_Flags;
194     char*   m_szName;
195     DWORD   m_dwName;
196     char*   m_szExportAlias;
197     DWORD   m_dwExportOrdinal;
198     COR_ILMETHOD_SECT_EH_CLAUSE_FAT *m_ExceptionList;
199     DWORD   m_dwNumExceptions;
200     DWORD   m_dwMaxNumExceptions;
201     DWORD*  m_EndfilterOffsetList;
202     DWORD   m_dwNumEndfilters;
203     DWORD   m_dwMaxNumEndfilters;
204     DWORD   m_Attr;
205     BOOL    m_fEntryPoint;
206     BOOL    m_fGlobalMethod;
207     BOOL    m_fNewBody;
208     BOOL    m_fNew;
209     DWORD   m_methodOffset;
210     DWORD   m_headerOffset;
211     BYTE *  m_pCode;
212     DWORD   m_CodeSize;
213     WORD    m_wImplAttr;
214     ULONG   m_ulLines[2];
215     ULONG   m_ulColumns[2];
216     // PInvoke attributes
217     PInvokeDescriptor* m_pPInvoke;
218     // Security attributes
219     PermissionDecl* m_pPermissions;
220     PermissionSetDecl* m_pPermissionSets;
221     // VTable attributes
222     WORD            m_wVTEntry;
223     WORD            m_wVTSlot;
224     // Return marshaling
225     BinStr* m_pRetMarshal;
226     BinStr* m_pRetValue;
227     DWORD   m_dwRetAttr;
228     CustomDescrList m_RetCustDList;
229     ILFixupList     m_lstILFixup;
230     FixupList       m_lstFixup;
231 //    LabelList       m_lstLabel;
232     // Member ref fixups
233     LocalMemberRefFixupList  m_LocalMemberRefFixupList;
234     // Method body (header+code+EH)
235     BinStr* m_pbsBody;
236     mdToken m_Tok;
237     Method(Assembler *pAssembler, Class *pClass, __in __nullterminated char *pszName, BinStr* pbsSig, DWORD Attr);
238     ~Method()
239     {
240         m_lstFixup.RESET(true);
241         //m_lstLabel.RESET(true);
242         delete [] m_szName;
243         if(m_szExportAlias) delete [] m_szExportAlias;
244         delArgNameList(m_firstArgName);
245         delArgNameList(m_firstVarName);
246         delete m_pbsMethodSig;
247         delete [] m_ExceptionList;
248         delete [] m_EndfilterOffsetList;
249         if(m_pRetMarshal) delete m_pRetMarshal;
250         if(m_pRetValue) delete m_pRetValue;
251         while(m_MethodImplDList.POP()); // ptrs in m_MethodImplDList are dups of those in Assembler
252         if(m_pbsBody) delete m_pbsBody;
253         if(m_TyPars) delete [] m_TyPars;
254     };
255
256     BOOL IsGlobalMethod()
257     {
258         return m_fGlobalMethod;
259     };
260
261     void SetIsGlobalMethod()
262     {
263         m_fGlobalMethod = TRUE;
264     };
265
266     void delArgNameList(ARG_NAME_LIST *pFirst)
267     {
268         ARG_NAME_LIST *pArgList=pFirst, *pArgListNext;
269         for(; pArgList; pArgListNext=pArgList->pNext,
270                         delete pArgList,
271                         pArgList=pArgListNext);
272     };
273
274     ARG_NAME_LIST *catArgNameList(ARG_NAME_LIST *pBase, ARG_NAME_LIST *pAdd)
275     {
276         if(pAdd) //even if nothing to concatenate, result == head
277         {
278             ARG_NAME_LIST *pAN = pBase;
279             if(pBase)
280             {
281                 int i;
282                 for(; pAN->pNext; pAN = pAN->pNext) ;
283                 pAN->pNext = pAdd;
284                 i = pAN->nNum;
285                 for(pAN = pAdd; pAN; pAN->nNum = ++i, pAN = pAN->pNext);
286             }
287             else pBase = pAdd; //nothing to concatenate to, result == tail
288         }
289         return pBase;
290     };
291
292     int findArgNum(ARG_NAME_LIST *pFirst, LPCUTF8 szArgName, DWORD dwArgName)
293     {
294         int ret=-1;
295         if(dwArgName)
296         {
297             ARG_NAME_LIST *pAN;
298             for(pAN=pFirst; pAN; pAN = pAN->pNext)
299             {
300                 if((pAN->dwName == dwArgName)&& ((dwArgName==0)||(!strcmp(pAN->szName,szArgName))))
301                 {
302                     ret = pAN->nNum;
303                     break;
304                 }
305             }
306         }
307         return ret;
308     };
309
310     int findLocSlot(ARG_NAME_LIST *pFirst, LPCUTF8 szArgName, DWORD dwArgName)
311     {
312         int ret=-1;
313         if(dwArgName)
314         {
315             ARG_NAME_LIST *pAN;
316             for(pAN=pFirst; pAN; pAN = pAN->pNext)
317             {
318                 if((pAN->dwName == dwArgName)&& ((dwArgName==0)||(!strcmp(pAN->szName,szArgName))))
319                 {
320                     ret = (int)(pAN->dwAttr);
321                     break;
322                 }
323             }
324         }
325         return ret;
326     };
327
328     BinStr  *m_pbsMethodSig;
329     COR_SIGNATURE*  m_pMethodSig;
330     DWORD   m_dwMethodCSig;
331     ARG_NAME_LIST *m_firstArgName;
332     ARG_NAME_LIST *m_firstVarName;
333     // to call error() from Method:
334     const char* m_FileName;
335     unsigned m_LineNum;
336     // debug info
337     LinePCList m_LinePCList;
338     // custom values
339     CustomDescrList m_CustomDescrList;
340     // token relocs (used for OBJ generation only)
341     TRDList m_TRDList;
342     // method's own list of method impls
343     MethodImplDList m_MethodImplDList;
344     // lexical scope handling
345     Assembler*      m_pAssembler;
346     Scope           m_MainScope;
347     Scope*          m_pCurrScope;
348     VarDescrList    m_Locals;
349     void OpenScope();
350     void CloseScope();
351
352     Label *FindLabel(LPCUTF8 pszName);
353     Label *FindLabel(DWORD PC);
354
355     int FindTyPar(__in __nullterminated WCHAR* wz)
356     {
357         int i,retval=-1;
358         for(i=0; i < (int)m_NumTyPars; i++)
359         {
360             if(!wcscmp(wz,m_TyPars[i].Name()))
361             {
362                 retval = i;
363             }
364         }
365         return retval;
366     };
367     int FindTyPar(__in __nullterminated char* sz)
368     {
369         if(sz)
370         {
371             wzUniBuf[0] = 0;
372             WszMultiByteToWideChar(g_uCodePage,0,sz,-1,wzUniBuf,dwUniBuf);
373             return FindTyPar(wzUniBuf);
374         }
375         else return -1;
376     };
377 };
378
379 #endif /* _METHOD_HPP */
380