diff --git a/llvm/include/llvm/IR/CallSite.h b/llvm/include/llvm/IR/CallSite.h --- a/llvm/include/llvm/IR/CallSite.h +++ b/llvm/include/llvm/IR/CallSite.h @@ -6,30 +6,14 @@ // //===----------------------------------------------------------------------===// // -// This file defines the CallSite class, which is a handy wrapper for code that -// wants to treat Call, Invoke and CallBr instructions in a generic way. When -// in non-mutation context (e.g. an analysis) ImmutableCallSite should be used. -// Finally, when some degree of customization is necessary between these two -// extremes, CallSiteBase<> can be supplied with fine-tuned parameters. -// -// NOTE: These classes are supposed to have "value semantics". So they should be -// passed by value, not by reference; they should not be "new"ed or "delete"d. -// They are efficiently copyable, assignable and constructable, with cost -// equivalent to copying a pointer (notice that they have only a single data -// member). The internal representation carries a flag which indicates which of -// the three variants is enclosed. This allows for cheaper checks when various -// accessors of CallSite are employed. +// This file defines the AbstractCallSite class, which is a is a wrapper that +// allows treating direct, indirect, and callback calls the same. // //===----------------------------------------------------------------------===// #ifndef LLVM_IR_CALLSITE_H #define LLVM_IR_CALLSITE_H -#include "llvm/ADT/Optional.h" -#include "llvm/ADT/PointerIntPair.h" -#include "llvm/ADT/iterator_range.h" -#include "llvm/IR/Attributes.h" -#include "llvm/IR/CallingConv.h" #include "llvm/IR/Function.h" #include "llvm/IR/InstrTypes.h" #include "llvm/IR/Instruction.h" @@ -44,688 +28,6 @@ namespace llvm { -namespace Intrinsic { -typedef unsigned ID; -} - -template -class CallSiteBase { -protected: - PointerIntPair I; - - CallSiteBase() = default; - CallSiteBase(CallTy *CI) : I(CI, 1) { assert(CI); } - CallSiteBase(InvokeTy *II) : I(II, 0) { assert(II); } - CallSiteBase(CallBrTy *CBI) : I(CBI, 2) { assert(CBI); } - explicit CallSiteBase(ValTy *II) { *this = get(II); } - -private: - /// This static method is like a constructor. It will create an appropriate - /// call site for a Call, Invoke or CallBr instruction, but it can also create - /// a null initialized CallSiteBase object for something which is NOT a call - /// site. - static CallSiteBase get(ValTy *V) { - if (InstrTy *II = dyn_cast(V)) { - if (II->getOpcode() == Instruction::Call) - return CallSiteBase(static_cast(II)); - if (II->getOpcode() == Instruction::Invoke) - return CallSiteBase(static_cast(II)); - if (II->getOpcode() == Instruction::CallBr) - return CallSiteBase(static_cast(II)); - } - return CallSiteBase(); - } - -public: - /// Return true if a CallInst is enclosed. - bool isCall() const { return I.getInt() == 1; } - - /// Return true if a InvokeInst is enclosed. !I.getInt() may also signify a - /// NULL instruction pointer, so check that. - bool isInvoke() const { return getInstruction() && I.getInt() == 0; } - - /// Return true if a CallBrInst is enclosed. - bool isCallBr() const { return I.getInt() == 2; } - - InstrTy *getInstruction() const { return I.getPointer(); } - InstrTy *operator->() const { return I.getPointer(); } - explicit operator bool() const { return I.getPointer(); } - - /// Get the basic block containing the call site. - BBTy* getParent() const { return getInstruction()->getParent(); } - - /// Return the pointer to function that is being called. - ValTy *getCalledValue() const { - assert(getInstruction() && "Not a call, invoke or callbr instruction!"); - return *getCallee(); - } - - /// Return the function being called if this is a direct call, otherwise - /// return null (if it's an indirect call). - FunTy *getCalledFunction() const { - return dyn_cast(getCalledValue()); - } - - /// Return true if the callsite is an indirect call. - bool isIndirectCall() const { - const Value *V = getCalledValue(); - if (!V) - return false; - if (isa(V) || isa(V)) - return false; - if (const CallBase *CB = dyn_cast(getInstruction())) - if (CB->isInlineAsm()) - return false; - return true; - } - - /// Set the callee to the specified value. Unlike the function of the same - /// name on CallBase, does not modify the type! - void setCalledFunction(Value *V) { - assert(getInstruction() && "Not a call, callbr, or invoke instruction!"); - assert(cast(V->getType())->getElementType() == - cast(getInstruction())->getFunctionType() && - "New callee type does not match FunctionType on call"); - *getCallee() = V; - } - - /// Return the intrinsic ID of the intrinsic called by this CallSite, - /// or Intrinsic::not_intrinsic if the called function is not an - /// intrinsic, or if this CallSite is an indirect call. - Intrinsic::ID getIntrinsicID() const { - if (auto *F = getCalledFunction()) - return F->getIntrinsicID(); - // Don't use Intrinsic::not_intrinsic, as it will require pulling - // Intrinsics.h into every header that uses CallSite. - return static_cast(0); - } - - /// Return if this call is to an intrinsic. - bool isIntrinsic() const { - if (auto *F = getCalledFunction()) - return F->isIntrinsic(); - return false; - } - - /// Determine whether the passed iterator points to the callee operand's Use. - bool isCallee(Value::const_user_iterator UI) const { - return isCallee(&UI.getUse()); - } - - /// Determine whether this Use is the callee operand's Use. - bool isCallee(const Use *U) const { return getCallee() == U; } - - /// Determine whether the passed iterator points to an argument operand. - bool isArgOperand(Value::const_user_iterator UI) const { - return isArgOperand(&UI.getUse()); - } - - /// Determine whether the passed use points to an argument operand. - bool isArgOperand(const Use *U) const { - assert(getInstruction() == U->getUser()); - return arg_begin() <= U && U < arg_end(); - } - - /// Determine whether the passed iterator points to a bundle operand. - bool isBundleOperand(Value::const_user_iterator UI) const { - return isBundleOperand(&UI.getUse()); - } - - /// Determine whether the passed use points to a bundle operand. - bool isBundleOperand(const Use *U) const { - assert(getInstruction() == U->getUser()); - if (!hasOperandBundles()) - return false; - unsigned OperandNo = U - (*this)->op_begin(); - return getBundleOperandsStartIndex() <= OperandNo && - OperandNo < getBundleOperandsEndIndex(); - } - - /// Determine whether the passed iterator points to a data operand. - bool isDataOperand(Value::const_user_iterator UI) const { - return isDataOperand(&UI.getUse()); - } - - /// Determine whether the passed use points to a data operand. - bool isDataOperand(const Use *U) const { - return data_operands_begin() <= U && U < data_operands_end(); - } - - ValTy *getArgument(unsigned ArgNo) const { - assert(arg_begin() + ArgNo < arg_end() && "Argument # out of range!"); - return *(arg_begin() + ArgNo); - } - - void setArgument(unsigned ArgNo, Value* newVal) { - assert(getInstruction() && "Not a call, invoke or callbr instruction!"); - assert(arg_begin() + ArgNo < arg_end() && "Argument # out of range!"); - getInstruction()->setOperand(ArgNo, newVal); - } - - /// Given a value use iterator, returns the argument that corresponds to it. - /// Iterator must actually correspond to an argument. - unsigned getArgumentNo(Value::const_user_iterator I) const { - return getArgumentNo(&I.getUse()); - } - - /// Given a use for an argument, get the argument number that corresponds to - /// it. - unsigned getArgumentNo(const Use *U) const { - assert(getInstruction() && "Not a call, invoke or callbr instruction!"); - assert(isArgOperand(U) && "Argument # out of range!"); - return U - arg_begin(); - } - - /// The type of iterator to use when looping over actual arguments at this - /// call site. - using arg_iterator = IterTy; - - iterator_range args() const { - return make_range(arg_begin(), arg_end()); - } - bool arg_empty() const { return arg_end() == arg_begin(); } - unsigned arg_size() const { return unsigned(arg_end() - arg_begin()); } - - /// Given a value use iterator, return the data operand corresponding to it. - /// Iterator must actually correspond to a data operand. - unsigned getDataOperandNo(Value::const_user_iterator UI) const { - return getDataOperandNo(&UI.getUse()); - } - - /// Given a use for a data operand, get the data operand number that - /// corresponds to it. - unsigned getDataOperandNo(const Use *U) const { - assert(getInstruction() && "Not a call, invoke or callbr instruction!"); - assert(isDataOperand(U) && "Data operand # out of range!"); - return U - data_operands_begin(); - } - - /// Type of iterator to use when looping over data operands at this call site - /// (see below). - using data_operand_iterator = IterTy; - - /// data_operands_begin/data_operands_end - Return iterators iterating over - /// the call / invoke / callbr argument list and bundle operands. For invokes, - /// this is the set of instruction operands except the invoke target and the - /// two successor blocks; for calls this is the set of instruction operands - /// except the call target; for callbrs the number of labels to skip must be - /// determined first. - - IterTy data_operands_begin() const { - assert(getInstruction() && "Not a call or invoke instruction!"); - return cast(getInstruction())->data_operands_begin(); - } - IterTy data_operands_end() const { - assert(getInstruction() && "Not a call or invoke instruction!"); - return cast(getInstruction())->data_operands_end(); - } - iterator_range data_ops() const { - return make_range(data_operands_begin(), data_operands_end()); - } - bool data_operands_empty() const { - return data_operands_end() == data_operands_begin(); - } - unsigned data_operands_size() const { - return std::distance(data_operands_begin(), data_operands_end()); - } - - /// Return the type of the instruction that generated this call site. - Type *getType() const { return (*this)->getType(); } - - /// Return the caller function for this call site. - FunTy *getCaller() const { return (*this)->getParent()->getParent(); } - - /// Tests if this call site must be tail call optimized. Only a CallInst can - /// be tail call optimized. - bool isMustTailCall() const { - return isCall() && cast(getInstruction())->isMustTailCall(); - } - - /// Tests if this call site is marked as a tail call. - bool isTailCall() const { - return isCall() && cast(getInstruction())->isTailCall(); - } - -#define CALLSITE_DELEGATE_GETTER(METHOD) \ - InstrTy *II = getInstruction(); \ - return isCall() ? cast(II)->METHOD \ - : isCallBr() ? cast(II)->METHOD \ - : cast(II)->METHOD - -#define CALLSITE_DELEGATE_SETTER(METHOD) \ - InstrTy *II = getInstruction(); \ - if (isCall()) \ - cast(II)->METHOD; \ - else if (isCallBr()) \ - cast(II)->METHOD; \ - else \ - cast(II)->METHOD - - unsigned getNumArgOperands() const { - CALLSITE_DELEGATE_GETTER(getNumArgOperands()); - } - - ValTy *getArgOperand(unsigned i) const { - CALLSITE_DELEGATE_GETTER(getArgOperand(i)); - } - - ValTy *getReturnedArgOperand() const { - CALLSITE_DELEGATE_GETTER(getReturnedArgOperand()); - } - - bool isInlineAsm() const { - return cast(getInstruction())->isInlineAsm(); - } - - /// Get the calling convention of the call. - CallingConv::ID getCallingConv() const { - CALLSITE_DELEGATE_GETTER(getCallingConv()); - } - /// Set the calling convention of the call. - void setCallingConv(CallingConv::ID CC) { - CALLSITE_DELEGATE_SETTER(setCallingConv(CC)); - } - - FunctionType *getFunctionType() const { - CALLSITE_DELEGATE_GETTER(getFunctionType()); - } - - void mutateFunctionType(FunctionType *Ty) const { - CALLSITE_DELEGATE_SETTER(mutateFunctionType(Ty)); - } - - /// Get the parameter attributes of the call. - AttributeList getAttributes() const { - CALLSITE_DELEGATE_GETTER(getAttributes()); - } - /// Set the parameter attributes of the call. - void setAttributes(AttributeList PAL) { - CALLSITE_DELEGATE_SETTER(setAttributes(PAL)); - } - - void addAttribute(unsigned i, Attribute::AttrKind Kind) { - CALLSITE_DELEGATE_SETTER(addAttribute(i, Kind)); - } - - void addAttribute(unsigned i, Attribute Attr) { - CALLSITE_DELEGATE_SETTER(addAttribute(i, Attr)); - } - - void addParamAttr(unsigned ArgNo, Attribute::AttrKind Kind) { - CALLSITE_DELEGATE_SETTER(addParamAttr(ArgNo, Kind)); - } - - void removeAttribute(unsigned i, Attribute::AttrKind Kind) { - CALLSITE_DELEGATE_SETTER(removeAttribute(i, Kind)); - } - - void removeAttribute(unsigned i, StringRef Kind) { - CALLSITE_DELEGATE_SETTER(removeAttribute(i, Kind)); - } - - void removeParamAttr(unsigned ArgNo, Attribute::AttrKind Kind) { - CALLSITE_DELEGATE_SETTER(removeParamAttr(ArgNo, Kind)); - } - - /// Return true if this function has the given attribute. - bool hasFnAttr(Attribute::AttrKind Kind) const { - CALLSITE_DELEGATE_GETTER(hasFnAttr(Kind)); - } - - /// Return true if this function has the given attribute. - bool hasFnAttr(StringRef Kind) const { - CALLSITE_DELEGATE_GETTER(hasFnAttr(Kind)); - } - - /// Return true if this return value has the given attribute. - bool hasRetAttr(Attribute::AttrKind Kind) const { - CALLSITE_DELEGATE_GETTER(hasRetAttr(Kind)); - } - - /// Return true if the call or the callee has the given attribute. - bool paramHasAttr(unsigned ArgNo, Attribute::AttrKind Kind) const { - CALLSITE_DELEGATE_GETTER(paramHasAttr(ArgNo, Kind)); - } - - Attribute getAttribute(unsigned i, Attribute::AttrKind Kind) const { - CALLSITE_DELEGATE_GETTER(getAttribute(i, Kind)); - } - - Attribute getAttribute(unsigned i, StringRef Kind) const { - CALLSITE_DELEGATE_GETTER(getAttribute(i, Kind)); - } - - /// Return true if the data operand at index \p i directly or indirectly has - /// the attribute \p A. - /// - /// Normal call, invoke or callbr arguments have per operand attributes, as - /// specified in the attribute set attached to this instruction, while operand - /// bundle operands may have some attributes implied by the type of its - /// containing operand bundle. - bool dataOperandHasImpliedAttr(unsigned i, Attribute::AttrKind Kind) const { - CALLSITE_DELEGATE_GETTER(dataOperandHasImpliedAttr(i, Kind)); - } - - /// Extract the alignment of the return value. - /// FIXME: Remove when the transition to Align is over. - unsigned getRetAlignment() const { - if (auto MA = getRetAlign()) - return MA->value(); - return 0; - } - - /// Extract the alignment of the return value. - MaybeAlign getRetAlign() const { CALLSITE_DELEGATE_GETTER(getRetAlign()); } - - /// Extract the alignment for a call or parameter (0=unknown). - /// FIXME: Remove when the transition to Align is over. - unsigned getParamAlignment(unsigned ArgNo) const { - if (auto MA = getParamAlign(ArgNo)) - return MA->value(); - return 0; - } - - /// Extract the alignment for a call or parameter (0=unknown). - MaybeAlign getParamAlign(unsigned ArgNo) const { - CALLSITE_DELEGATE_GETTER(getParamAlign(ArgNo)); - } - - /// Extract the byval type for a call or parameter (nullptr=unknown). - Type *getParamByValType(unsigned ArgNo) const { - CALLSITE_DELEGATE_GETTER(getParamByValType(ArgNo)); - } - - /// Extract the number of dereferenceable bytes for a call or parameter - /// (0=unknown). - uint64_t getDereferenceableBytes(unsigned i) const { - CALLSITE_DELEGATE_GETTER(getDereferenceableBytes(i)); - } - - /// Extract the number of dereferenceable_or_null bytes for a call or - /// parameter (0=unknown). - uint64_t getDereferenceableOrNullBytes(unsigned i) const { - CALLSITE_DELEGATE_GETTER(getDereferenceableOrNullBytes(i)); - } - - /// Determine if the return value is marked with NoAlias attribute. - bool returnDoesNotAlias() const { - CALLSITE_DELEGATE_GETTER(returnDoesNotAlias()); - } - - /// Return true if the call should not be treated as a call to a builtin. - bool isNoBuiltin() const { - CALLSITE_DELEGATE_GETTER(isNoBuiltin()); - } - - /// Return true if the call requires strict floating point semantics. - bool isStrictFP() const { - CALLSITE_DELEGATE_GETTER(isStrictFP()); - } - - /// Return true if the call should not be inlined. - bool isNoInline() const { - CALLSITE_DELEGATE_GETTER(isNoInline()); - } - void setIsNoInline(bool Value = true) { - CALLSITE_DELEGATE_SETTER(setIsNoInline(Value)); - } - - /// Determine if the call does not access memory. - bool doesNotAccessMemory() const { - CALLSITE_DELEGATE_GETTER(doesNotAccessMemory()); - } - void setDoesNotAccessMemory() { - CALLSITE_DELEGATE_SETTER(setDoesNotAccessMemory()); - } - - /// Determine if the call does not access or only reads memory. - bool onlyReadsMemory() const { - CALLSITE_DELEGATE_GETTER(onlyReadsMemory()); - } - void setOnlyReadsMemory() { - CALLSITE_DELEGATE_SETTER(setOnlyReadsMemory()); - } - - /// Determine if the call does not access or only writes memory. - bool doesNotReadMemory() const { - CALLSITE_DELEGATE_GETTER(doesNotReadMemory()); - } - void setDoesNotReadMemory() { - CALLSITE_DELEGATE_SETTER(setDoesNotReadMemory()); - } - - /// Determine if the call can access memmory only using pointers based - /// on its arguments. - bool onlyAccessesArgMemory() const { - CALLSITE_DELEGATE_GETTER(onlyAccessesArgMemory()); - } - void setOnlyAccessesArgMemory() { - CALLSITE_DELEGATE_SETTER(setOnlyAccessesArgMemory()); - } - - /// Determine if the function may only access memory that is - /// inaccessible from the IR. - bool onlyAccessesInaccessibleMemory() const { - CALLSITE_DELEGATE_GETTER(onlyAccessesInaccessibleMemory()); - } - void setOnlyAccessesInaccessibleMemory() { - CALLSITE_DELEGATE_SETTER(setOnlyAccessesInaccessibleMemory()); - } - - /// Determine if the function may only access memory that is - /// either inaccessible from the IR or pointed to by its arguments. - bool onlyAccessesInaccessibleMemOrArgMem() const { - CALLSITE_DELEGATE_GETTER(onlyAccessesInaccessibleMemOrArgMem()); - } - void setOnlyAccessesInaccessibleMemOrArgMem() { - CALLSITE_DELEGATE_SETTER(setOnlyAccessesInaccessibleMemOrArgMem()); - } - - /// Determine if the call cannot return. - bool doesNotReturn() const { - CALLSITE_DELEGATE_GETTER(doesNotReturn()); - } - void setDoesNotReturn() { - CALLSITE_DELEGATE_SETTER(setDoesNotReturn()); - } - - /// Determine if the call cannot unwind. - bool doesNotThrow() const { - CALLSITE_DELEGATE_GETTER(doesNotThrow()); - } - void setDoesNotThrow() { - CALLSITE_DELEGATE_SETTER(setDoesNotThrow()); - } - - /// Determine if the call can be duplicated. - bool cannotDuplicate() const { - CALLSITE_DELEGATE_GETTER(cannotDuplicate()); - } - void setCannotDuplicate() { - CALLSITE_DELEGATE_SETTER(setCannotDuplicate()); - } - - /// Determine if the call is convergent. - bool isConvergent() const { - CALLSITE_DELEGATE_GETTER(isConvergent()); - } - void setConvergent() { - CALLSITE_DELEGATE_SETTER(setConvergent()); - } - void setNotConvergent() { - CALLSITE_DELEGATE_SETTER(setNotConvergent()); - } - - unsigned getNumOperandBundles() const { - CALLSITE_DELEGATE_GETTER(getNumOperandBundles()); - } - - bool hasOperandBundles() const { - CALLSITE_DELEGATE_GETTER(hasOperandBundles()); - } - - unsigned getBundleOperandsStartIndex() const { - CALLSITE_DELEGATE_GETTER(getBundleOperandsStartIndex()); - } - - unsigned getBundleOperandsEndIndex() const { - CALLSITE_DELEGATE_GETTER(getBundleOperandsEndIndex()); - } - - unsigned getNumTotalBundleOperands() const { - CALLSITE_DELEGATE_GETTER(getNumTotalBundleOperands()); - } - - OperandBundleUse getOperandBundleAt(unsigned Index) const { - CALLSITE_DELEGATE_GETTER(getOperandBundleAt(Index)); - } - - Optional getOperandBundle(StringRef Name) const { - CALLSITE_DELEGATE_GETTER(getOperandBundle(Name)); - } - - Optional getOperandBundle(uint32_t ID) const { - CALLSITE_DELEGATE_GETTER(getOperandBundle(ID)); - } - - unsigned countOperandBundlesOfType(uint32_t ID) const { - CALLSITE_DELEGATE_GETTER(countOperandBundlesOfType(ID)); - } - - bool isBundleOperand(unsigned Idx) const { - CALLSITE_DELEGATE_GETTER(isBundleOperand(Idx)); - } - - IterTy arg_begin() const { - CALLSITE_DELEGATE_GETTER(arg_begin()); - } - - IterTy arg_end() const { - CALLSITE_DELEGATE_GETTER(arg_end()); - } - -#undef CALLSITE_DELEGATE_GETTER -#undef CALLSITE_DELEGATE_SETTER - - void getOperandBundlesAsDefs(SmallVectorImpl &Defs) const { - // Since this is actually a getter that "looks like" a setter, don't use the - // above macros to avoid confusion. - cast(getInstruction())->getOperandBundlesAsDefs(Defs); - } - - /// Determine whether this data operand is not captured. - bool doesNotCapture(unsigned OpNo) const { - return dataOperandHasImpliedAttr(OpNo + 1, Attribute::NoCapture); - } - - /// Determine whether this argument is passed by value. - bool isByValArgument(unsigned ArgNo) const { - return paramHasAttr(ArgNo, Attribute::ByVal); - } - - /// Determine whether this argument is passed in an alloca. - bool isInAllocaArgument(unsigned ArgNo) const { - return paramHasAttr(ArgNo, Attribute::InAlloca); - } - - /// Determine whether this argument is passed by value or in an alloca. - bool isByValOrInAllocaArgument(unsigned ArgNo) const { - return paramHasAttr(ArgNo, Attribute::ByVal) || - paramHasAttr(ArgNo, Attribute::InAlloca); - } - - /// Determine if there are is an inalloca argument. Only the last argument can - /// have the inalloca attribute. - bool hasInAllocaArgument() const { - return !arg_empty() && paramHasAttr(arg_size() - 1, Attribute::InAlloca); - } - - bool doesNotAccessMemory(unsigned OpNo) const { - return dataOperandHasImpliedAttr(OpNo + 1, Attribute::ReadNone); - } - - bool onlyReadsMemory(unsigned OpNo) const { - return dataOperandHasImpliedAttr(OpNo + 1, Attribute::ReadOnly) || - dataOperandHasImpliedAttr(OpNo + 1, Attribute::ReadNone); - } - - bool doesNotReadMemory(unsigned OpNo) const { - return dataOperandHasImpliedAttr(OpNo + 1, Attribute::WriteOnly) || - dataOperandHasImpliedAttr(OpNo + 1, Attribute::ReadNone); - } - - /// Return true if the return value is known to be not null. - /// This may be because it has the nonnull attribute, or because at least - /// one byte is dereferenceable and the pointer is in addrspace(0). - bool isReturnNonNull() const { - if (hasRetAttr(Attribute::NonNull)) - return true; - else if (getDereferenceableBytes(AttributeList::ReturnIndex) > 0 && - !NullPointerIsDefined(getCaller(), - getType()->getPointerAddressSpace())) - return true; - - return false; - } - - /// Returns true if this CallSite passes the given Value* as an argument to - /// the called function. - bool hasArgument(const Value *Arg) const { - for (arg_iterator AI = this->arg_begin(), E = this->arg_end(); AI != E; - ++AI) - if (AI->get() == Arg) - return true; - return false; - } - -private: - IterTy getCallee() const { - return cast(getInstruction())->op_end() - 1; - } -}; - -class CallSite : public CallSiteBase { -public: - CallSite() = default; - CallSite(CallSiteBase B) : CallSiteBase(B) {} - CallSite(CallInst *CI) : CallSiteBase(CI) {} - CallSite(InvokeInst *II) : CallSiteBase(II) {} - CallSite(CallBrInst *CBI) : CallSiteBase(CBI) {} - explicit CallSite(Instruction *II) : CallSiteBase(II) {} - explicit CallSite(Value *V) : CallSiteBase(V) {} - - bool operator==(const CallSite &CS) const { return I == CS.I; } - bool operator!=(const CallSite &CS) const { return I != CS.I; } - bool operator<(const CallSite &CS) const { - return getInstruction() < CS.getInstruction(); - } - -private: - friend struct DenseMapInfo; - - User::op_iterator getCallee() const; -}; - -/// Establish a view to a call site for examination. -class ImmutableCallSite : public CallSiteBase<> { -public: - ImmutableCallSite() = default; - ImmutableCallSite(const CallInst *CI) : CallSiteBase(CI) {} - ImmutableCallSite(const InvokeInst *II) : CallSiteBase(II) {} - ImmutableCallSite(const CallBrInst *CBI) : CallSiteBase(CBI) {} - explicit ImmutableCallSite(const Instruction *II) : CallSiteBase(II) {} - explicit ImmutableCallSite(const Value *V) : CallSiteBase(V) {} - ImmutableCallSite(CallSite CS) : CallSiteBase(CS.getInstruction()) {} -}; - /// AbstractCallSite /// /// An abstract call site is a wrapper that allows to treat direct, @@ -916,30 +218,6 @@ } }; -template <> struct DenseMapInfo { - using BaseInfo = DenseMapInfo; - - static CallSite getEmptyKey() { - CallSite CS; - CS.I = BaseInfo::getEmptyKey(); - return CS; - } - - static CallSite getTombstoneKey() { - CallSite CS; - CS.I = BaseInfo::getTombstoneKey(); - return CS; - } - - static unsigned getHashValue(const CallSite &CS) { - return BaseInfo::getHashValue(CS.I); - } - - static bool isEqual(const CallSite &LHS, const CallSite &RHS) { - return LHS == RHS; - } -}; - } // end namespace llvm #endif // LLVM_IR_CALLSITE_H diff --git a/llvm/include/llvm/IR/InstVisitor.h b/llvm/include/llvm/IR/InstVisitor.h --- a/llvm/include/llvm/IR/InstVisitor.h +++ b/llvm/include/llvm/IR/InstVisitor.h @@ -10,7 +10,6 @@ #ifndef LLVM_IR_INSTVISITOR_H #define LLVM_IR_INSTVISITOR_H -#include "llvm/IR/CallSite.h" #include "llvm/IR/Function.h" #include "llvm/IR/Instructions.h" #include "llvm/IR/IntrinsicInst.h" @@ -217,18 +216,9 @@ RetTy visitVAEndInst(VAEndInst &I) { DELEGATE(IntrinsicInst); } RetTy visitVACopyInst(VACopyInst &I) { DELEGATE(IntrinsicInst); } RetTy visitIntrinsicInst(IntrinsicInst &I) { DELEGATE(CallInst); } - - // Call, Invoke and CallBr are slightly different as they delegate first - // through a generic CallSite visitor. - RetTy visitCallInst(CallInst &I) { - return static_cast(this)->visitCallSite(&I); - } - RetTy visitInvokeInst(InvokeInst &I) { - return static_cast(this)->visitCallSite(&I); - } - RetTy visitCallBrInst(CallBrInst &I) { - return static_cast(this)->visitCallSite(&I); - } + RetTy visitCallInst(CallInst &I) { DELEGATE(CallBase); } + RetTy visitInvokeInst(InvokeInst &I) { DELEGATE(CallBase); } + RetTy visitCallBrInst(CallBrInst &I) { DELEGATE(CallBase); } // While terminators don't have a distinct type modeling them, we support // intercepting them with dedicated a visitor callback. @@ -280,16 +270,6 @@ DELEGATE(Instruction); } - // Provide a legacy visitor for a 'callsite' that visits calls, invokes, - // and calbrs. - // - // Prefer overriding the type system based `CallBase` instead. - RetTy visitCallSite(CallSite CS) { - assert(CS); - Instruction &I = *CS.getInstruction(); - DELEGATE(CallBase); - } - // If the user wants a 'default' case, they can choose to override this // function. If this function is not overloaded in the user's subclass, then // this instruction just gets ignored. diff --git a/llvm/lib/IR/Instructions.cpp b/llvm/lib/IR/Instructions.cpp --- a/llvm/lib/IR/Instructions.cpp +++ b/llvm/lib/IR/Instructions.cpp @@ -18,7 +18,6 @@ #include "llvm/ADT/Twine.h" #include "llvm/IR/Attributes.h" #include "llvm/IR/BasicBlock.h" -#include "llvm/IR/CallSite.h" #include "llvm/IR/Constant.h" #include "llvm/IR/Constants.h" #include "llvm/IR/DataLayout.h" @@ -62,14 +61,6 @@ return Size; } -//===----------------------------------------------------------------------===// -// CallSite Class -//===----------------------------------------------------------------------===// - -User::op_iterator CallSite::getCallee() const { - return cast(getInstruction())->op_end() - 1; -} - //===----------------------------------------------------------------------===// // SelectInst Class //===----------------------------------------------------------------------===//