1 //===-- JumpInstrTables.h: Jump-Instruction Tables --------------*- C++ -*-===// 2 // 3 // This file is distributed under the University of Illinois Open Source 4 // License. See LICENSE.TXT for details. 5 // 6 //===----------------------------------------------------------------------===// 7 /// 8 /// \file 9 /// \brief An implementation of tables consisting of jump instructions 10 /// 11 //===----------------------------------------------------------------------===// 12 13 #ifndef LLVM_CODEGEN_JUMPINSTRTABLES_H 14 #define LLVM_CODEGEN_JUMPINSTRTABLES_H 15 16 #include "llvm/ADT/DenseMap.h" 17 #include "llvm/Pass.h" 18 #include "llvm/Target/TargetOptions.h" 19 20 namespace llvm { 21 class Constant; 22 class Function; 23 class FunctionType; 24 class JumpInstrTableInfo; 25 class Module; 26 27 /// A class to manage a set of jump tables indexed on function type. It looks at 28 /// each function in the module to find all the functions that have the 29 /// jumptable attribute set. For each such function, it creates a new 30 /// jump-instruction-table function and stores the mapping in the ImmutablePass 31 /// JumpInstrTableInfo. 32 /// 33 /// These special functions get lowered in AsmPrinter to assembly of the form: 34 /// \verbatim 35 /// .globl f 36 /// .type f,@function 37 /// .align 8,0x90 38 /// f: 39 /// jmp f_orig@PLT 40 /// \endverbatim 41 /// 42 /// Support for an architecture depends on three functions in TargetInstrInfo: 43 /// getUnconditionalBranch, getTrap, and getJumpInstrTableEntryBound. AsmPrinter 44 /// uses these to generate the appropriate instructions for the jump statement 45 /// (an unconditional branch) and for padding to make the table have a size that 46 /// is a power of two. This padding uses a trap instruction to ensure that calls 47 /// to this area halt the program. The default implementations of these 48 /// functions call llvm_unreachable, except for getJumpInstrTableEntryBound, 49 /// which returns 0 by default. 50 class JumpInstrTables : public ModulePass { 51 public: 52 static char ID; 53 54 JumpInstrTables(); 55 JumpInstrTables(JumpTable::JumpTableType JTT); 56 virtual ~JumpInstrTables(); 57 bool runOnModule(Module &M) override; getPassName()58 const char *getPassName() const override { return "Jump-Instruction Tables"; } 59 void getAnalysisUsage(AnalysisUsage &AU) const override; 60 61 /// Creates a jump-instruction table function for the Target and adds it to 62 /// the tables. 63 Function *insertEntry(Module &M, Function *Target); 64 65 /// Checks to see if there is already a table for the given FunctionType. 66 bool hasTable(FunctionType *FunTy); 67 68 /// Maps the function into a subset of function types, depending on the 69 /// jump-instruction table style selected from JumpTableTypes in 70 /// JumpInstrTables.cpp. The choice of mapping determines the number of 71 /// jump-instruction tables generated by this pass. E.g., the simplest mapping 72 /// converts every function type into void f(); so, all functions end up in a 73 /// single table. 74 static FunctionType *transformType(JumpTable::JumpTableType JTT, 75 FunctionType *FunTy); 76 private: 77 /// The metadata used while a jump table is being built 78 struct TableMeta { 79 /// The number of this table 80 unsigned TableNum; 81 82 /// The current number of jump entries in the table. 83 unsigned Count; 84 }; 85 86 typedef DenseMap<FunctionType *, struct TableMeta> JumpMap; 87 88 /// The current state of functions and jump entries in the table(s). 89 JumpMap Metadata; 90 91 /// The ImmutablePass that stores information about the generated tables. 92 JumpInstrTableInfo *JITI; 93 94 /// The total number of tables. 95 unsigned TableCount; 96 97 /// The type of tables to build. 98 JumpTable::JumpTableType JTType; 99 }; 100 101 /// Creates a JumpInstrTables pass for the given type of jump table. 102 ModulePass *createJumpInstrTablesPass(JumpTable::JumpTableType JTT); 103 } 104 105 #endif /* LLVM_CODEGEN_JUMPINSTRTABLES_H */ 106