Home | History | Annotate | Download | only in Basic
      1 //===----- ABI.h - ABI related declarations ---------------------*- 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 /// \file
     11 /// \brief Enums/classes describing ABI related information about constructors,
     12 /// destructors and thunks.
     13 ///
     14 //===----------------------------------------------------------------------===//
     15 
     16 #ifndef LLVM_CLANG_BASIC_ABI_H
     17 #define LLVM_CLANG_BASIC_ABI_H
     18 
     19 #include "llvm/Support/DataTypes.h"
     20 #include <cstring>
     21 
     22 namespace clang {
     23 
     24 /// \brief C++ constructor types.
     25 enum CXXCtorType {
     26   Ctor_Complete,       ///< Complete object ctor
     27   Ctor_Base,           ///< Base object ctor
     28   Ctor_Comdat,         ///< The COMDAT used for ctors
     29   Ctor_CopyingClosure, ///< Copying closure variant of a ctor
     30   Ctor_DefaultClosure, ///< Default closure variant of a ctor
     31 };
     32 
     33 /// \brief C++ destructor types.
     34 enum CXXDtorType {
     35     Dtor_Deleting, ///< Deleting dtor
     36     Dtor_Complete, ///< Complete object dtor
     37     Dtor_Base,     ///< Base object dtor
     38     Dtor_Comdat    ///< The COMDAT used for dtors
     39 };
     40 
     41 /// \brief A return adjustment.
     42 struct ReturnAdjustment {
     43   /// \brief The non-virtual adjustment from the derived object to its
     44   /// nearest virtual base.
     45   int64_t NonVirtual;
     46 
     47   /// \brief Holds the ABI-specific information about the virtual return
     48   /// adjustment, if needed.
     49   union VirtualAdjustment {
     50     // Itanium ABI
     51     struct {
     52       /// \brief The offset (in bytes), relative to the address point
     53       /// of the virtual base class offset.
     54       int64_t VBaseOffsetOffset;
     55     } Itanium;
     56 
     57     // Microsoft ABI
     58     struct {
     59       /// \brief The offset (in bytes) of the vbptr, relative to the beginning
     60       /// of the derived class.
     61       uint32_t VBPtrOffset;
     62 
     63       /// \brief Index of the virtual base in the vbtable.
     64       uint32_t VBIndex;
     65     } Microsoft;
     66 
     67     VirtualAdjustment() {
     68       memset(this, 0, sizeof(*this));
     69     }
     70 
     71     bool Equals(const VirtualAdjustment &Other) const {
     72       return memcmp(this, &Other, sizeof(Other)) == 0;
     73     }
     74 
     75     bool isEmpty() const {
     76       VirtualAdjustment Zero;
     77       return Equals(Zero);
     78     }
     79 
     80     bool Less(const VirtualAdjustment &RHS) const {
     81       return memcmp(this, &RHS, sizeof(RHS)) < 0;
     82     }
     83   } Virtual;
     84 
     85   ReturnAdjustment() : NonVirtual(0) {}
     86 
     87   bool isEmpty() const { return !NonVirtual && Virtual.isEmpty(); }
     88 
     89   friend bool operator==(const ReturnAdjustment &LHS,
     90                          const ReturnAdjustment &RHS) {
     91     return LHS.NonVirtual == RHS.NonVirtual && LHS.Virtual.Equals(RHS.Virtual);
     92   }
     93 
     94   friend bool operator!=(const ReturnAdjustment &LHS, const ReturnAdjustment &RHS) {
     95     return !(LHS == RHS);
     96   }
     97 
     98   friend bool operator<(const ReturnAdjustment &LHS,
     99                         const ReturnAdjustment &RHS) {
    100     if (LHS.NonVirtual < RHS.NonVirtual)
    101       return true;
    102 
    103     return LHS.NonVirtual == RHS.NonVirtual && LHS.Virtual.Less(RHS.Virtual);
    104   }
    105 };
    106 
    107 /// \brief A \c this pointer adjustment.
    108 struct ThisAdjustment {
    109   /// \brief The non-virtual adjustment from the derived object to its
    110   /// nearest virtual base.
    111   int64_t NonVirtual;
    112 
    113   /// \brief Holds the ABI-specific information about the virtual this
    114   /// adjustment, if needed.
    115   union VirtualAdjustment {
    116     // Itanium ABI
    117     struct {
    118       /// \brief The offset (in bytes), relative to the address point,
    119       /// of the virtual call offset.
    120       int64_t VCallOffsetOffset;
    121     } Itanium;
    122 
    123     struct {
    124       /// \brief The offset of the vtordisp (in bytes), relative to the ECX.
    125       int32_t VtordispOffset;
    126 
    127       /// \brief The offset of the vbptr of the derived class (in bytes),
    128       /// relative to the ECX after vtordisp adjustment.
    129       int32_t VBPtrOffset;
    130 
    131       /// \brief The offset (in bytes) of the vbase offset in the vbtable.
    132       int32_t VBOffsetOffset;
    133     } Microsoft;
    134 
    135     VirtualAdjustment() {
    136       memset(this, 0, sizeof(*this));
    137     }
    138 
    139     bool Equals(const VirtualAdjustment &Other) const {
    140       return memcmp(this, &Other, sizeof(Other)) == 0;
    141     }
    142 
    143     bool isEmpty() const {
    144       VirtualAdjustment Zero;
    145       return Equals(Zero);
    146     }
    147 
    148     bool Less(const VirtualAdjustment &RHS) const {
    149       return memcmp(this, &RHS, sizeof(RHS)) < 0;
    150     }
    151   } Virtual;
    152 
    153   ThisAdjustment() : NonVirtual(0) { }
    154 
    155   bool isEmpty() const { return !NonVirtual && Virtual.isEmpty(); }
    156 
    157   friend bool operator==(const ThisAdjustment &LHS,
    158                          const ThisAdjustment &RHS) {
    159     return LHS.NonVirtual == RHS.NonVirtual && LHS.Virtual.Equals(RHS.Virtual);
    160   }
    161 
    162   friend bool operator!=(const ThisAdjustment &LHS, const ThisAdjustment &RHS) {
    163     return !(LHS == RHS);
    164   }
    165 
    166   friend bool operator<(const ThisAdjustment &LHS,
    167                         const ThisAdjustment &RHS) {
    168     if (LHS.NonVirtual < RHS.NonVirtual)
    169       return true;
    170 
    171     return LHS.NonVirtual == RHS.NonVirtual && LHS.Virtual.Less(RHS.Virtual);
    172   }
    173 };
    174 
    175 class CXXMethodDecl;
    176 
    177 /// \brief The \c this pointer adjustment as well as an optional return
    178 /// adjustment for a thunk.
    179 struct ThunkInfo {
    180   /// \brief The \c this pointer adjustment.
    181   ThisAdjustment This;
    182 
    183   /// \brief The return adjustment.
    184   ReturnAdjustment Return;
    185 
    186   /// \brief Holds a pointer to the overridden method this thunk is for,
    187   /// if needed by the ABI to distinguish different thunks with equal
    188   /// adjustments. Otherwise, null.
    189   /// CAUTION: In the unlikely event you need to sort ThunkInfos, consider using
    190   /// an ABI-specific comparator.
    191   const CXXMethodDecl *Method;
    192 
    193   ThunkInfo() : Method(nullptr) { }
    194 
    195   ThunkInfo(const ThisAdjustment &This, const ReturnAdjustment &Return,
    196             const CXXMethodDecl *Method = nullptr)
    197       : This(This), Return(Return), Method(Method) {}
    198 
    199   friend bool operator==(const ThunkInfo &LHS, const ThunkInfo &RHS) {
    200     return LHS.This == RHS.This && LHS.Return == RHS.Return &&
    201            LHS.Method == RHS.Method;
    202   }
    203 
    204   bool isEmpty() const {
    205     return This.isEmpty() && Return.isEmpty() && Method == nullptr;
    206   }
    207 };
    208 
    209 } // end namespace clang
    210 
    211 #endif
    212