1 //===- SwiftErrorValueTracking.h - Track swifterror VReg vals --*- C++ -*--===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This implements a limited mem2reg-like analysis to promote uses of function 10 // arguments and allocas marked with swiftalloc from memory into virtual 11 // registers tracked by this class. 12 // 13 //===----------------------------------------------------------------------===// 14 15 #ifndef LLVM_CODEGEN_SWIFTERRORVALUETRACKING_H 16 #define LLVM_CODEGEN_SWIFTERRORVALUETRACKING_H 17 18 #include "llvm/ADT/DenseMap.h" 19 #include "llvm/ADT/SmallVector.h" 20 #include "llvm/CodeGen/Register.h" 21 #include "llvm/IR/BasicBlock.h" 22 #include "llvm/IR/DebugLoc.h" 23 #include <functional> 24 #include <type_traits> 25 #include <utility> 26 27 28 namespace llvm { 29 class Function; 30 class MachineBasicBlock; 31 class MachineFunction; 32 class MachineInstr; 33 class TargetInstrInfo; 34 class TargetLowering; 35 36 class SwiftErrorValueTracking { 37 // Some useful objects to reduce the number of function arguments needed. 38 MachineFunction *MF; 39 const Function *Fn; 40 const TargetLowering *TLI; 41 const TargetInstrInfo *TII; 42 43 /// A map from swifterror value in a basic block to the virtual register it is 44 /// currently represented by. 45 DenseMap<std::pair<const MachineBasicBlock *, const Value *>, Register> 46 VRegDefMap; 47 48 /// A list of upward exposed vreg uses that need to be satisfied by either a 49 /// copy def or a phi node at the beginning of the basic block representing 50 /// the predecessor(s) swifterror value. 51 DenseMap<std::pair<const MachineBasicBlock *, const Value *>, Register> 52 VRegUpwardsUse; 53 54 /// A map from instructions that define/use a swifterror value to the virtual 55 /// register that represents that def/use. 56 llvm::DenseMap<PointerIntPair<const Instruction *, 1, bool>, Register> 57 VRegDefUses; 58 59 /// The swifterror argument of the current function. 60 const Value *SwiftErrorArg; 61 62 using SwiftErrorValues = SmallVector<const Value*, 1>; 63 /// A function can only have a single swifterror argument. And if it does 64 /// have a swifterror argument, it must be the first entry in 65 /// SwiftErrorVals. 66 SwiftErrorValues SwiftErrorVals; 67 68 public: 69 /// Initialize data structures for specified new function. 70 void setFunction(MachineFunction &MF); 71 72 /// Get the (unique) function argument that was marked swifterror, or nullptr 73 /// if this function has no swifterror args. 74 const Value *getFunctionArg() const { 75 return SwiftErrorArg; 76 } 77 78 /// Get or create the swifterror value virtual register in 79 /// VRegDefMap for this basic block. 80 Register getOrCreateVReg(const MachineBasicBlock *, const Value *); 81 82 /// Set the swifterror virtual register in the VRegDefMap for this 83 /// basic block. 84 void setCurrentVReg(const MachineBasicBlock *MBB, const Value *, Register); 85 86 /// Get or create the swifterror value virtual register for a def of a 87 /// swifterror by an instruction. 88 Register getOrCreateVRegDefAt(const Instruction *, const MachineBasicBlock *, 89 const Value *); 90 91 /// Get or create the swifterror value virtual register for a use of a 92 /// swifterror by an instruction. 93 Register getOrCreateVRegUseAt(const Instruction *, const MachineBasicBlock *, 94 const Value *); 95 96 /// Create initial definitions of swifterror values in the entry block of the 97 /// current function. 98 bool createEntriesInEntryBlock(DebugLoc DbgLoc); 99 100 /// Propagate assigned swifterror vregs through a function, synthesizing PHI 101 /// nodes when needed to maintain consistency. 102 void propagateVRegs(); 103 104 void preassignVRegs(MachineBasicBlock *MBB, BasicBlock::const_iterator Begin, 105 BasicBlock::const_iterator End); 106 }; 107 108 } 109 110 #endif 111