Line data Source code
1 : //===- llvm/CodeGen/WinEHFuncInfo.h -----------------------------*- C++ -*-===//
2 : //
3 : // The LLVM Compiler Infrastructure
4 : //
5 : // This file is distributed under the University of Illinois Open Source
6 : // License. See LICENSE.TXT for details.
7 : //
8 : //===----------------------------------------------------------------------===//
9 : //
10 : // Data structures and associated state for Windows exception handling schemes.
11 : //
12 : //===----------------------------------------------------------------------===//
13 :
14 : #ifndef LLVM_CODEGEN_WINEHFUNCINFO_H
15 : #define LLVM_CODEGEN_WINEHFUNCINFO_H
16 :
17 : #include "llvm/ADT/DenseMap.h"
18 : #include "llvm/ADT/PointerUnion.h"
19 : #include "llvm/ADT/SmallVector.h"
20 : #include <cstdint>
21 : #include <limits>
22 : #include <utility>
23 :
24 : namespace llvm {
25 :
26 : class AllocaInst;
27 : class BasicBlock;
28 : class FuncletPadInst;
29 : class Function;
30 : class GlobalVariable;
31 : class Instruction;
32 : class InvokeInst;
33 : class MachineBasicBlock;
34 : class MCSymbol;
35 :
36 : // The following structs respresent the .xdata tables for various
37 : // Windows-related EH personalities.
38 :
39 : using MBBOrBasicBlock = PointerUnion<const BasicBlock *, MachineBasicBlock *>;
40 :
41 : struct CxxUnwindMapEntry {
42 : int ToState;
43 : MBBOrBasicBlock Cleanup;
44 : };
45 :
46 : /// Similar to CxxUnwindMapEntry, but supports SEH filters.
47 : struct SEHUnwindMapEntry {
48 : /// If unwinding continues through this handler, transition to the handler at
49 : /// this state. This indexes into SEHUnwindMap.
50 : int ToState = -1;
51 :
52 : bool IsFinally = false;
53 :
54 : /// Holds the filter expression function.
55 : const Function *Filter = nullptr;
56 :
57 : /// Holds the __except or __finally basic block.
58 : MBBOrBasicBlock Handler;
59 : };
60 :
61 94 : struct WinEHHandlerType {
62 : int Adjectives;
63 : /// The CatchObj starts out life as an LLVM alloca and is eventually turned
64 : /// frame index.
65 : union {
66 : const AllocaInst *Alloca;
67 : int FrameIndex;
68 : } CatchObj = {};
69 : GlobalVariable *TypeDescriptor;
70 : MBBOrBasicBlock Handler;
71 : };
72 :
73 172 : struct WinEHTryBlockMapEntry {
74 : int TryLow = -1;
75 : int TryHigh = -1;
76 : int CatchHigh = -1;
77 : SmallVector<WinEHHandlerType, 1> HandlerArray;
78 : };
79 :
80 : enum class ClrHandlerType { Catch, Finally, Fault, Filter };
81 :
82 : struct ClrEHUnwindMapEntry {
83 : MBBOrBasicBlock Handler;
84 : uint32_t TypeToken;
85 : int HandlerParentState; ///< Outer handler enclosing this entry's handler
86 : int TryParentState; ///< Outer try region enclosing this entry's try region,
87 : ///< treating later catches on same try as "outer"
88 : ClrHandlerType HandlerType;
89 : };
90 :
91 : struct WinEHFuncInfo {
92 : DenseMap<const Instruction *, int> EHPadStateMap;
93 : DenseMap<const FuncletPadInst *, int> FuncletBaseStateMap;
94 : DenseMap<const InvokeInst *, int> InvokeStateMap;
95 : DenseMap<MCSymbol *, std::pair<int, MCSymbol *>> LabelToStateMap;
96 : SmallVector<CxxUnwindMapEntry, 4> CxxUnwindMap;
97 : SmallVector<WinEHTryBlockMapEntry, 4> TryBlockMap;
98 : SmallVector<SEHUnwindMapEntry, 4> SEHUnwindMap;
99 : SmallVector<ClrEHUnwindMapEntry, 4> ClrEHUnwindMap;
100 : int UnwindHelpFrameIdx = std::numeric_limits<int>::max();
101 : int PSPSymFrameIdx = std::numeric_limits<int>::max();
102 :
103 295 : int getLastStateNumber() const { return CxxUnwindMap.size() - 1; }
104 :
105 : void addIPToStateRange(const InvokeInst *II, MCSymbol *InvokeBegin,
106 : MCSymbol *InvokeEnd);
107 :
108 : int EHRegNodeFrameIndex = std::numeric_limits<int>::max();
109 : int EHRegNodeEndOffset = std::numeric_limits<int>::max();
110 : int EHGuardFrameIndex = std::numeric_limits<int>::max();
111 : int SEHSetFrameOffset = std::numeric_limits<int>::max();
112 :
113 : WinEHFuncInfo();
114 : };
115 :
116 : /// Analyze the IR in ParentFn and it's handlers to build WinEHFuncInfo, which
117 : /// describes the state numbers and tables used by __CxxFrameHandler3. This
118 : /// analysis assumes that WinEHPrepare has already been run.
119 : void calculateWinCXXEHStateNumbers(const Function *ParentFn,
120 : WinEHFuncInfo &FuncInfo);
121 :
122 : void calculateSEHStateNumbers(const Function *ParentFn,
123 : WinEHFuncInfo &FuncInfo);
124 :
125 : void calculateClrEHStateNumbers(const Function *Fn, WinEHFuncInfo &FuncInfo);
126 :
127 : } // end namespace llvm
128 :
129 : #endif // LLVM_CODEGEN_WINEHFUNCINFO_H
|