Home | History | Annotate | Download | only in CodeGen
      1 //===----- CGCall.h - Encapsulate calling convention details ----*- 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 // These classes wrap the information about a call or function
     11 // definition used to handle ABI compliancy.
     12 //
     13 //===----------------------------------------------------------------------===//
     14 
     15 #ifndef CLANG_CODEGEN_CGCALL_H
     16 #define CLANG_CODEGEN_CGCALL_H
     17 
     18 #include "CGValue.h"
     19 #include "EHScopeStack.h"
     20 #include "clang/AST/CanonicalType.h"
     21 #include "clang/AST/Type.h"
     22 #include "llvm/ADT/FoldingSet.h"
     23 #include "llvm/IR/Value.h"
     24 
     25 // FIXME: Restructure so we don't have to expose so much stuff.
     26 #include "ABIInfo.h"
     27 
     28 namespace llvm {
     29   class AttributeSet;
     30   class Function;
     31   class Type;
     32   class Value;
     33 }
     34 
     35 namespace clang {
     36   class ASTContext;
     37   class Decl;
     38   class FunctionDecl;
     39   class ObjCMethodDecl;
     40   class VarDecl;
     41 
     42 namespace CodeGen {
     43   typedef SmallVector<llvm::AttributeSet, 8> AttributeListType;
     44 
     45   struct CallArg {
     46     RValue RV;
     47     QualType Ty;
     48     bool NeedsCopy;
     49     CallArg(RValue rv, QualType ty, bool needscopy)
     50     : RV(rv), Ty(ty), NeedsCopy(needscopy)
     51     { }
     52   };
     53 
     54   /// CallArgList - Type for representing both the value and type of
     55   /// arguments in a call.
     56   class CallArgList :
     57     public SmallVector<CallArg, 16> {
     58   public:
     59     CallArgList() : StackBase(nullptr), StackBaseMem(nullptr) {}
     60 
     61     struct Writeback {
     62       /// The original argument.  Note that the argument l-value
     63       /// is potentially null.
     64       LValue Source;
     65 
     66       /// The temporary alloca.
     67       llvm::Value *Temporary;
     68 
     69       /// A value to "use" after the writeback, or null.
     70       llvm::Value *ToUse;
     71     };
     72 
     73     struct CallArgCleanup {
     74       EHScopeStack::stable_iterator Cleanup;
     75 
     76       /// The "is active" insertion point.  This instruction is temporary and
     77       /// will be removed after insertion.
     78       llvm::Instruction *IsActiveIP;
     79     };
     80 
     81     void add(RValue rvalue, QualType type, bool needscopy = false) {
     82       push_back(CallArg(rvalue, type, needscopy));
     83     }
     84 
     85     void addFrom(const CallArgList &other) {
     86       insert(end(), other.begin(), other.end());
     87       Writebacks.insert(Writebacks.end(),
     88                         other.Writebacks.begin(), other.Writebacks.end());
     89     }
     90 
     91     void addWriteback(LValue srcLV, llvm::Value *temporary,
     92                       llvm::Value *toUse) {
     93       Writeback writeback;
     94       writeback.Source = srcLV;
     95       writeback.Temporary = temporary;
     96       writeback.ToUse = toUse;
     97       Writebacks.push_back(writeback);
     98     }
     99 
    100     bool hasWritebacks() const { return !Writebacks.empty(); }
    101 
    102     typedef llvm::iterator_range<SmallVectorImpl<Writeback>::const_iterator>
    103       writeback_const_range;
    104 
    105     writeback_const_range writebacks() const {
    106       return writeback_const_range(Writebacks.begin(), Writebacks.end());
    107     }
    108 
    109     void addArgCleanupDeactivation(EHScopeStack::stable_iterator Cleanup,
    110                                    llvm::Instruction *IsActiveIP) {
    111       CallArgCleanup ArgCleanup;
    112       ArgCleanup.Cleanup = Cleanup;
    113       ArgCleanup.IsActiveIP = IsActiveIP;
    114       CleanupsToDeactivate.push_back(ArgCleanup);
    115     }
    116 
    117     ArrayRef<CallArgCleanup> getCleanupsToDeactivate() const {
    118       return CleanupsToDeactivate;
    119     }
    120 
    121     void allocateArgumentMemory(CodeGenFunction &CGF);
    122     llvm::Instruction *getStackBase() const { return StackBase; }
    123     void freeArgumentMemory(CodeGenFunction &CGF) const;
    124 
    125     /// \brief Returns if we're using an inalloca struct to pass arguments in
    126     /// memory.
    127     bool isUsingInAlloca() const { return StackBase; }
    128 
    129   private:
    130     SmallVector<Writeback, 1> Writebacks;
    131 
    132     /// Deactivate these cleanups immediately before making the call.  This
    133     /// is used to cleanup objects that are owned by the callee once the call
    134     /// occurs.
    135     SmallVector<CallArgCleanup, 1> CleanupsToDeactivate;
    136 
    137     /// The stacksave call.  It dominates all of the argument evaluation.
    138     llvm::CallInst *StackBase;
    139 
    140     /// The alloca holding the stackbase.  We need it to maintain SSA form.
    141     llvm::AllocaInst *StackBaseMem;
    142 
    143     /// The iterator pointing to the stack restore cleanup.  We manually run and
    144     /// deactivate this cleanup after the call in the unexceptional case because
    145     /// it doesn't run in the normal order.
    146     EHScopeStack::stable_iterator StackCleanup;
    147   };
    148 
    149   /// FunctionArgList - Type for representing both the decl and type
    150   /// of parameters to a function. The decl must be either a
    151   /// ParmVarDecl or ImplicitParamDecl.
    152   class FunctionArgList : public SmallVector<const VarDecl*, 16> {
    153   };
    154 
    155   /// ReturnValueSlot - Contains the address where the return value of a
    156   /// function can be stored, and whether the address is volatile or not.
    157   class ReturnValueSlot {
    158     llvm::PointerIntPair<llvm::Value *, 1, bool> Value;
    159 
    160   public:
    161     ReturnValueSlot() {}
    162     ReturnValueSlot(llvm::Value *Value, bool IsVolatile)
    163       : Value(Value, IsVolatile) {}
    164 
    165     bool isNull() const { return !getValue(); }
    166 
    167     bool isVolatile() const { return Value.getInt(); }
    168     llvm::Value *getValue() const { return Value.getPointer(); }
    169   };
    170 
    171 }  // end namespace CodeGen
    172 }  // end namespace clang
    173 
    174 #endif
    175