LLVM API Documentation
00001 //===-- EHStreamer.h - Exception Handling Directive Streamer ---*- C++ -*--===// 00002 // 00003 // The LLVM Compiler Infrastructure 00004 // 00005 // This file is distributed under the University of Illinois Open Source 00006 // License. See LICENSE.TXT for details. 00007 // 00008 //===----------------------------------------------------------------------===// 00009 // 00010 // This file contains support for writing exception info into assembly files. 00011 // 00012 //===----------------------------------------------------------------------===// 00013 00014 #ifndef LLVM_LIB_CODEGEN_ASMPRINTER_EHSTREAMER_H 00015 #define LLVM_LIB_CODEGEN_ASMPRINTER_EHSTREAMER_H 00016 00017 #include "AsmPrinterHandler.h" 00018 #include "llvm/ADT/DenseMap.h" 00019 00020 namespace llvm { 00021 struct LandingPadInfo; 00022 class MachineModuleInfo; 00023 class MachineInstr; 00024 class MachineFunction; 00025 class AsmPrinter; 00026 00027 template <typename T> 00028 class SmallVectorImpl; 00029 00030 /// Emits exception handling directives. 00031 class EHStreamer : public AsmPrinterHandler { 00032 protected: 00033 /// Target of directive emission. 00034 AsmPrinter *Asm; 00035 00036 /// Collected machine module information. 00037 MachineModuleInfo *MMI; 00038 00039 /// How many leading type ids two landing pads have in common. 00040 static unsigned sharedTypeIDs(const LandingPadInfo *L, 00041 const LandingPadInfo *R); 00042 00043 /// Structure holding a try-range and the associated landing pad. 00044 struct PadRange { 00045 // The index of the landing pad. 00046 unsigned PadIndex; 00047 // The index of the begin and end labels in the landing pad's label lists. 00048 unsigned RangeIndex; 00049 }; 00050 00051 typedef DenseMap<MCSymbol *, PadRange> RangeMapType; 00052 00053 /// Structure describing an entry in the actions table. 00054 struct ActionEntry { 00055 int ValueForTypeID; // The value to write - may not be equal to the type id. 00056 int NextAction; 00057 unsigned Previous; 00058 }; 00059 00060 /// Structure describing an entry in the call-site table. 00061 struct CallSiteEntry { 00062 // The 'try-range' is BeginLabel .. EndLabel. 00063 MCSymbol *BeginLabel; // zero indicates the start of the function. 00064 MCSymbol *EndLabel; // zero indicates the end of the function. 00065 00066 // The landing pad starts at PadLabel. 00067 MCSymbol *PadLabel; // zero indicates that there is no landing pad. 00068 unsigned Action; 00069 }; 00070 00071 /// Compute the actions table and gather the first action index for each 00072 /// landing pad site. 00073 unsigned computeActionsTable(const SmallVectorImpl<const LandingPadInfo*>&LPs, 00074 SmallVectorImpl<ActionEntry> &Actions, 00075 SmallVectorImpl<unsigned> &FirstActions); 00076 00077 /// Return `true' if this is a call to a function marked `nounwind'. Return 00078 /// `false' otherwise. 00079 bool callToNoUnwindFunction(const MachineInstr *MI); 00080 00081 /// Compute the call-site table. The entry for an invoke has a try-range 00082 /// containing the call, a non-zero landing pad and an appropriate action. 00083 /// The entry for an ordinary call has a try-range containing the call and 00084 /// zero for the landing pad and the action. Calls marked 'nounwind' have 00085 /// no entry and must not be contained in the try-range of any entry - they 00086 /// form gaps in the table. Entries must be ordered by try-range address. 00087 00088 void computeCallSiteTable(SmallVectorImpl<CallSiteEntry> &CallSites, 00089 const RangeMapType &PadMap, 00090 const SmallVectorImpl<const LandingPadInfo *> &LPs, 00091 const SmallVectorImpl<unsigned> &FirstActions); 00092 00093 /// Emit landing pads and actions. 00094 /// 00095 /// The general organization of the table is complex, but the basic concepts 00096 /// are easy. First there is a header which describes the location and 00097 /// organization of the three components that follow. 00098 /// 1. The landing pad site information describes the range of code covered 00099 /// by the try. In our case it's an accumulation of the ranges covered 00100 /// by the invokes in the try. There is also a reference to the landing 00101 /// pad that handles the exception once processed. Finally an index into 00102 /// the actions table. 00103 /// 2. The action table, in our case, is composed of pairs of type ids 00104 /// and next action offset. Starting with the action index from the 00105 /// landing pad site, each type Id is checked for a match to the current 00106 /// exception. If it matches then the exception and type id are passed 00107 /// on to the landing pad. Otherwise the next action is looked up. This 00108 /// chain is terminated with a next action of zero. If no type id is 00109 /// found the frame is unwound and handling continues. 00110 /// 3. Type id table contains references to all the C++ typeinfo for all 00111 /// catches in the function. This tables is reversed indexed base 1. 00112 void emitExceptionTable(); 00113 00114 virtual void emitTypeInfos(unsigned TTypeEncoding); 00115 00116 public: 00117 EHStreamer(AsmPrinter *A); 00118 virtual ~EHStreamer(); 00119 00120 /// Emit all exception information that should come after the content. 00121 void endModule() override; 00122 00123 /// Gather pre-function exception information. Assumes being emitted 00124 /// immediately after the function entry point. 00125 void beginFunction(const MachineFunction *MF) override; 00126 00127 /// Gather and emit post-function exception information. 00128 void endFunction(const MachineFunction *) override; 00129 00130 // Unused. 00131 void setSymbolSize(const MCSymbol *Sym, uint64_t Size) override {} 00132 void beginInstruction(const MachineInstr *MI) override {} 00133 void endInstruction() override {} 00134 }; 00135 } 00136 00137 #endif 00138