Home | History | Annotate | Line # | Download | only in AST
      1 //===- TypeLoc.h - Type Source Info Wrapper ---------------------*- 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 /// \file
     10 /// Defines the clang::TypeLoc interface and its subclasses.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 
     14 #ifndef LLVM_CLANG_AST_TYPELOC_H
     15 #define LLVM_CLANG_AST_TYPELOC_H
     16 
     17 #include "clang/AST/DeclarationName.h"
     18 #include "clang/AST/NestedNameSpecifier.h"
     19 #include "clang/AST/TemplateBase.h"
     20 #include "clang/AST/Type.h"
     21 #include "clang/Basic/LLVM.h"
     22 #include "clang/Basic/SourceLocation.h"
     23 #include "clang/Basic/Specifiers.h"
     24 #include "llvm/ADT/ArrayRef.h"
     25 #include "llvm/Support/Casting.h"
     26 #include "llvm/Support/Compiler.h"
     27 #include "llvm/Support/MathExtras.h"
     28 #include <algorithm>
     29 #include <cassert>
     30 #include <cstdint>
     31 #include <cstring>
     32 
     33 namespace clang {
     34 
     35 class Attr;
     36 class ASTContext;
     37 class CXXRecordDecl;
     38 class ConceptDecl;
     39 class Expr;
     40 class ObjCInterfaceDecl;
     41 class ObjCProtocolDecl;
     42 class ObjCTypeParamDecl;
     43 class ParmVarDecl;
     44 class TemplateTypeParmDecl;
     45 class UnqualTypeLoc;
     46 class UnresolvedUsingTypenameDecl;
     47 
     48 // Predeclare all the type nodes.
     49 #define ABSTRACT_TYPELOC(Class, Base)
     50 #define TYPELOC(Class, Base) \
     51   class Class##TypeLoc;
     52 #include "clang/AST/TypeLocNodes.def"
     53 
     54 /// Base wrapper for a particular "section" of type source info.
     55 ///
     56 /// A client should use the TypeLoc subclasses through castAs()/getAs()
     57 /// in order to get at the actual information.
     58 class TypeLoc {
     59 protected:
     60   // The correctness of this relies on the property that, for Type *Ty,
     61   //   QualType(Ty, 0).getAsOpaquePtr() == (void*) Ty
     62   const void *Ty = nullptr;
     63   void *Data = nullptr;
     64 
     65 public:
     66   TypeLoc() = default;
     67   TypeLoc(QualType ty, void *opaqueData)
     68       : Ty(ty.getAsOpaquePtr()), Data(opaqueData) {}
     69   TypeLoc(const Type *ty, void *opaqueData)
     70       : Ty(ty), Data(opaqueData) {}
     71 
     72   /// Convert to the specified TypeLoc type, asserting that this TypeLoc
     73   /// is of the desired type.
     74   ///
     75   /// \pre T::isKind(*this)
     76   template<typename T>
     77   T castAs() const {
     78     assert(T::isKind(*this));
     79     T t;
     80     TypeLoc& tl = t;
     81     tl = *this;
     82     return t;
     83   }
     84 
     85   /// Convert to the specified TypeLoc type, returning a null TypeLoc if
     86   /// this TypeLoc is not of the desired type.
     87   template<typename T>
     88   T getAs() const {
     89     if (!T::isKind(*this))
     90       return {};
     91     T t;
     92     TypeLoc& tl = t;
     93     tl = *this;
     94     return t;
     95   }
     96 
     97   /// Convert to the specified TypeLoc type, returning a null TypeLoc if
     98   /// this TypeLoc is not of the desired type. It will consider type
     99   /// adjustments from a type that was written as a T to another type that is
    100   /// still canonically a T (ignores parens, attributes, elaborated types, etc).
    101   template <typename T>
    102   T getAsAdjusted() const;
    103 
    104   /// The kinds of TypeLocs.  Equivalent to the Type::TypeClass enum,
    105   /// except it also defines a Qualified enum that corresponds to the
    106   /// QualifiedLoc class.
    107   enum TypeLocClass {
    108 #define ABSTRACT_TYPE(Class, Base)
    109 #define TYPE(Class, Base) \
    110     Class = Type::Class,
    111 #include "clang/AST/TypeNodes.inc"
    112     Qualified
    113   };
    114 
    115   TypeLocClass getTypeLocClass() const {
    116     if (getType().hasLocalQualifiers()) return Qualified;
    117     return (TypeLocClass) getType()->getTypeClass();
    118   }
    119 
    120   bool isNull() const { return !Ty; }
    121   explicit operator bool() const { return Ty; }
    122 
    123   /// Returns the size of type source info data block for the given type.
    124   static unsigned getFullDataSizeForType(QualType Ty);
    125 
    126   /// Returns the alignment of type source info data block for
    127   /// the given type.
    128   static unsigned getLocalAlignmentForType(QualType Ty);
    129 
    130   /// Get the type for which this source info wrapper provides
    131   /// information.
    132   QualType getType() const {
    133     return QualType::getFromOpaquePtr(Ty);
    134   }
    135 
    136   const Type *getTypePtr() const {
    137     return QualType::getFromOpaquePtr(Ty).getTypePtr();
    138   }
    139 
    140   /// Get the pointer where source information is stored.
    141   void *getOpaqueData() const {
    142     return Data;
    143   }
    144 
    145   /// Get the begin source location.
    146   SourceLocation getBeginLoc() const;
    147 
    148   /// Get the end source location.
    149   SourceLocation getEndLoc() const;
    150 
    151   /// Get the full source range.
    152   SourceRange getSourceRange() const LLVM_READONLY {
    153     return SourceRange(getBeginLoc(), getEndLoc());
    154   }
    155 
    156 
    157   /// Get the local source range.
    158   SourceRange getLocalSourceRange() const {
    159     return getLocalSourceRangeImpl(*this);
    160   }
    161 
    162   /// Returns the size of the type source info data block.
    163   unsigned getFullDataSize() const {
    164     return getFullDataSizeForType(getType());
    165   }
    166 
    167   /// Get the next TypeLoc pointed by this TypeLoc, e.g for "int*" the
    168   /// TypeLoc is a PointerLoc and next TypeLoc is for "int".
    169   TypeLoc getNextTypeLoc() const {
    170     return getNextTypeLocImpl(*this);
    171   }
    172 
    173   /// Skips past any qualifiers, if this is qualified.
    174   UnqualTypeLoc getUnqualifiedLoc() const; // implemented in this header
    175 
    176   TypeLoc IgnoreParens() const;
    177 
    178   /// Find a type with the location of an explicit type qualifier.
    179   ///
    180   /// The result, if non-null, will be one of:
    181   ///   QualifiedTypeLoc
    182   ///   AtomicTypeLoc
    183   ///   AttributedTypeLoc, for those type attributes that behave as qualifiers
    184   TypeLoc findExplicitQualifierLoc() const;
    185 
    186   /// Get the typeloc of an AutoType whose type will be deduced for a variable
    187   /// with an initializer of this type. This looks through declarators like
    188   /// pointer types, but not through decltype or typedefs.
    189   AutoTypeLoc getContainedAutoTypeLoc() const;
    190 
    191   /// Initializes this to state that every location in this
    192   /// type is the given location.
    193   ///
    194   /// This method exists to provide a simple transition for code that
    195   /// relies on location-less types.
    196   void initialize(ASTContext &Context, SourceLocation Loc) const {
    197     initializeImpl(Context, *this, Loc);
    198   }
    199 
    200   /// Initializes this by copying its information from another
    201   /// TypeLoc of the same type.
    202   void initializeFullCopy(TypeLoc Other) {
    203     assert(getType() == Other.getType());
    204     copy(Other);
    205   }
    206 
    207   /// Initializes this by copying its information from another
    208   /// TypeLoc of the same type.  The given size must be the full data
    209   /// size.
    210   void initializeFullCopy(TypeLoc Other, unsigned Size) {
    211     assert(getType() == Other.getType());
    212     assert(getFullDataSize() == Size);
    213     copy(Other);
    214   }
    215 
    216   /// Copies the other type loc into this one.
    217   void copy(TypeLoc other);
    218 
    219   friend bool operator==(const TypeLoc &LHS, const TypeLoc &RHS) {
    220     return LHS.Ty == RHS.Ty && LHS.Data == RHS.Data;
    221   }
    222 
    223   friend bool operator!=(const TypeLoc &LHS, const TypeLoc &RHS) {
    224     return !(LHS == RHS);
    225   }
    226 
    227   /// Find the location of the nullability specifier (__nonnull,
    228   /// __nullable, or __null_unspecifier), if there is one.
    229   SourceLocation findNullabilityLoc() const;
    230 
    231 private:
    232   static bool isKind(const TypeLoc&) {
    233     return true;
    234   }
    235 
    236   static void initializeImpl(ASTContext &Context, TypeLoc TL,
    237                              SourceLocation Loc);
    238   static TypeLoc getNextTypeLocImpl(TypeLoc TL);
    239   static TypeLoc IgnoreParensImpl(TypeLoc TL);
    240   static SourceRange getLocalSourceRangeImpl(TypeLoc TL);
    241 };
    242 
    243 /// Return the TypeLoc for a type source info.
    244 inline TypeLoc TypeSourceInfo::getTypeLoc() const {
    245   // TODO: is this alignment already sufficient?
    246   return TypeLoc(Ty, const_cast<void*>(static_cast<const void*>(this + 1)));
    247 }
    248 
    249 /// Wrapper of type source information for a type with
    250 /// no direct qualifiers.
    251 class UnqualTypeLoc : public TypeLoc {
    252 public:
    253   UnqualTypeLoc() = default;
    254   UnqualTypeLoc(const Type *Ty, void *Data) : TypeLoc(Ty, Data) {}
    255 
    256   const Type *getTypePtr() const {
    257     return reinterpret_cast<const Type*>(Ty);
    258   }
    259 
    260   TypeLocClass getTypeLocClass() const {
    261     return (TypeLocClass) getTypePtr()->getTypeClass();
    262   }
    263 
    264 private:
    265   friend class TypeLoc;
    266 
    267   static bool isKind(const TypeLoc &TL) {
    268     return !TL.getType().hasLocalQualifiers();
    269   }
    270 };
    271 
    272 /// Wrapper of type source information for a type with
    273 /// non-trivial direct qualifiers.
    274 ///
    275 /// Currently, we intentionally do not provide source location for
    276 /// type qualifiers.
    277 class QualifiedTypeLoc : public TypeLoc {
    278 public:
    279   SourceRange getLocalSourceRange() const { return {}; }
    280 
    281   UnqualTypeLoc getUnqualifiedLoc() const {
    282     unsigned align =
    283         TypeLoc::getLocalAlignmentForType(QualType(getTypePtr(), 0));
    284     auto dataInt = reinterpret_cast<uintptr_t>(Data);
    285     dataInt = llvm::alignTo(dataInt, align);
    286     return UnqualTypeLoc(getTypePtr(), reinterpret_cast<void*>(dataInt));
    287   }
    288 
    289   /// Initializes the local data of this type source info block to
    290   /// provide no information.
    291   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
    292     // do nothing
    293   }
    294 
    295   void copyLocal(TypeLoc other) {
    296     // do nothing
    297   }
    298 
    299   TypeLoc getNextTypeLoc() const {
    300     return getUnqualifiedLoc();
    301   }
    302 
    303   /// Returns the size of the type source info data block that is
    304   /// specific to this type.
    305   unsigned getLocalDataSize() const {
    306     // In fact, we don't currently preserve any location information
    307     // for qualifiers.
    308     return 0;
    309   }
    310 
    311   /// Returns the alignment of the type source info data block that is
    312   /// specific to this type.
    313   unsigned getLocalDataAlignment() const {
    314     // We don't preserve any location information.
    315     return 1;
    316   }
    317 
    318 private:
    319   friend class TypeLoc;
    320 
    321   static bool isKind(const TypeLoc &TL) {
    322     return TL.getType().hasLocalQualifiers();
    323   }
    324 };
    325 
    326 inline UnqualTypeLoc TypeLoc::getUnqualifiedLoc() const {
    327   if (QualifiedTypeLoc Loc = getAs<QualifiedTypeLoc>())
    328     return Loc.getUnqualifiedLoc();
    329   return castAs<UnqualTypeLoc>();
    330 }
    331 
    332 /// A metaprogramming base class for TypeLoc classes which correspond
    333 /// to a particular Type subclass.  It is accepted for a single
    334 /// TypeLoc class to correspond to multiple Type classes.
    335 ///
    336 /// \tparam Base a class from which to derive
    337 /// \tparam Derived the class deriving from this one
    338 /// \tparam TypeClass the concrete Type subclass associated with this
    339 ///   location type
    340 /// \tparam LocalData the structure type of local location data for
    341 ///   this type
    342 ///
    343 /// TypeLocs with non-constant amounts of local data should override
    344 /// getExtraLocalDataSize(); getExtraLocalData() will then point to
    345 /// this extra memory.
    346 ///
    347 /// TypeLocs with an inner type should define
    348 ///   QualType getInnerType() const
    349 /// and getInnerTypeLoc() will then point to this inner type's
    350 /// location data.
    351 ///
    352 /// A word about hierarchies: this template is not designed to be
    353 /// derived from multiple times in a hierarchy.  It is also not
    354 /// designed to be used for classes where subtypes might provide
    355 /// different amounts of source information.  It should be subclassed
    356 /// only at the deepest portion of the hierarchy where all children
    357 /// have identical source information; if that's an abstract type,
    358 /// then further descendents should inherit from
    359 /// InheritingConcreteTypeLoc instead.
    360 template <class Base, class Derived, class TypeClass, class LocalData>
    361 class ConcreteTypeLoc : public Base {
    362   friend class TypeLoc;
    363 
    364   const Derived *asDerived() const {
    365     return static_cast<const Derived*>(this);
    366   }
    367 
    368   static bool isKind(const TypeLoc &TL) {
    369     return !TL.getType().hasLocalQualifiers() &&
    370            Derived::classofType(TL.getTypePtr());
    371   }
    372 
    373   static bool classofType(const Type *Ty) {
    374     return TypeClass::classof(Ty);
    375   }
    376 
    377 public:
    378   unsigned getLocalDataAlignment() const {
    379     return std::max(unsigned(alignof(LocalData)),
    380                     asDerived()->getExtraLocalDataAlignment());
    381   }
    382 
    383   unsigned getLocalDataSize() const {
    384     unsigned size = sizeof(LocalData);
    385     unsigned extraAlign = asDerived()->getExtraLocalDataAlignment();
    386     size = llvm::alignTo(size, extraAlign);
    387     size += asDerived()->getExtraLocalDataSize();
    388     return size;
    389   }
    390 
    391   void copyLocal(Derived other) {
    392     // Some subclasses have no data to copy.
    393     if (asDerived()->getLocalDataSize() == 0) return;
    394 
    395     // Copy the fixed-sized local data.
    396     memcpy(getLocalData(), other.getLocalData(), sizeof(LocalData));
    397 
    398     // Copy the variable-sized local data. We need to do this
    399     // separately because the padding in the source and the padding in
    400     // the destination might be different.
    401     memcpy(getExtraLocalData(), other.getExtraLocalData(),
    402            asDerived()->getExtraLocalDataSize());
    403   }
    404 
    405   TypeLoc getNextTypeLoc() const {
    406     return getNextTypeLoc(asDerived()->getInnerType());
    407   }
    408 
    409   const TypeClass *getTypePtr() const {
    410     return cast<TypeClass>(Base::getTypePtr());
    411   }
    412 
    413 protected:
    414   unsigned getExtraLocalDataSize() const {
    415     return 0;
    416   }
    417 
    418   unsigned getExtraLocalDataAlignment() const {
    419     return 1;
    420   }
    421 
    422   LocalData *getLocalData() const {
    423     return static_cast<LocalData*>(Base::Data);
    424   }
    425 
    426   /// Gets a pointer past the Info structure; useful for classes with
    427   /// local data that can't be captured in the Info (e.g. because it's
    428   /// of variable size).
    429   void *getExtraLocalData() const {
    430     unsigned size = sizeof(LocalData);
    431     unsigned extraAlign = asDerived()->getExtraLocalDataAlignment();
    432     size = llvm::alignTo(size, extraAlign);
    433     return reinterpret_cast<char*>(Base::Data) + size;
    434   }
    435 
    436   void *getNonLocalData() const {
    437     auto data = reinterpret_cast<uintptr_t>(Base::Data);
    438     data += asDerived()->getLocalDataSize();
    439     data = llvm::alignTo(data, getNextTypeAlign());
    440     return reinterpret_cast<void*>(data);
    441   }
    442 
    443   struct HasNoInnerType {};
    444   HasNoInnerType getInnerType() const { return HasNoInnerType(); }
    445 
    446   TypeLoc getInnerTypeLoc() const {
    447     return TypeLoc(asDerived()->getInnerType(), getNonLocalData());
    448   }
    449 
    450 private:
    451   unsigned getInnerTypeSize() const {
    452     return getInnerTypeSize(asDerived()->getInnerType());
    453   }
    454 
    455   unsigned getInnerTypeSize(HasNoInnerType _) const {
    456     return 0;
    457   }
    458 
    459   unsigned getInnerTypeSize(QualType _) const {
    460     return getInnerTypeLoc().getFullDataSize();
    461   }
    462 
    463   unsigned getNextTypeAlign() const {
    464     return getNextTypeAlign(asDerived()->getInnerType());
    465   }
    466 
    467   unsigned getNextTypeAlign(HasNoInnerType _) const {
    468     return 1;
    469   }
    470 
    471   unsigned getNextTypeAlign(QualType T) const {
    472     return TypeLoc::getLocalAlignmentForType(T);
    473   }
    474 
    475   TypeLoc getNextTypeLoc(HasNoInnerType _) const { return {}; }
    476 
    477   TypeLoc getNextTypeLoc(QualType T) const {
    478     return TypeLoc(T, getNonLocalData());
    479   }
    480 };
    481 
    482 /// A metaprogramming class designed for concrete subtypes of abstract
    483 /// types where all subtypes share equivalently-structured source
    484 /// information.  See the note on ConcreteTypeLoc.
    485 template <class Base, class Derived, class TypeClass>
    486 class InheritingConcreteTypeLoc : public Base {
    487   friend class TypeLoc;
    488 
    489   static bool classofType(const Type *Ty) {
    490     return TypeClass::classof(Ty);
    491   }
    492 
    493   static bool isKind(const TypeLoc &TL) {
    494     return !TL.getType().hasLocalQualifiers() &&
    495            Derived::classofType(TL.getTypePtr());
    496   }
    497   static bool isKind(const UnqualTypeLoc &TL) {
    498     return Derived::classofType(TL.getTypePtr());
    499   }
    500 
    501 public:
    502   const TypeClass *getTypePtr() const {
    503     return cast<TypeClass>(Base::getTypePtr());
    504   }
    505 };
    506 
    507 struct TypeSpecLocInfo {
    508   SourceLocation NameLoc;
    509 };
    510 
    511 /// A reasonable base class for TypeLocs that correspond to
    512 /// types that are written as a type-specifier.
    513 class TypeSpecTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
    514                                                TypeSpecTypeLoc,
    515                                                Type,
    516                                                TypeSpecLocInfo> {
    517 public:
    518   enum {
    519     LocalDataSize = sizeof(TypeSpecLocInfo),
    520     LocalDataAlignment = alignof(TypeSpecLocInfo)
    521   };
    522 
    523   SourceLocation getNameLoc() const {
    524     return this->getLocalData()->NameLoc;
    525   }
    526 
    527   void setNameLoc(SourceLocation Loc) {
    528     this->getLocalData()->NameLoc = Loc;
    529   }
    530 
    531   SourceRange getLocalSourceRange() const {
    532     return SourceRange(getNameLoc(), getNameLoc());
    533   }
    534 
    535   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
    536     setNameLoc(Loc);
    537   }
    538 
    539 private:
    540   friend class TypeLoc;
    541 
    542   static bool isKind(const TypeLoc &TL);
    543 };
    544 
    545 struct BuiltinLocInfo {
    546   SourceRange BuiltinRange;
    547 };
    548 
    549 /// Wrapper for source info for builtin types.
    550 class BuiltinTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
    551                                               BuiltinTypeLoc,
    552                                               BuiltinType,
    553                                               BuiltinLocInfo> {
    554 public:
    555   SourceLocation getBuiltinLoc() const {
    556     return getLocalData()->BuiltinRange.getBegin();
    557   }
    558 
    559   void setBuiltinLoc(SourceLocation Loc) {
    560     getLocalData()->BuiltinRange = Loc;
    561   }
    562 
    563   void expandBuiltinRange(SourceRange Range) {
    564     SourceRange &BuiltinRange = getLocalData()->BuiltinRange;
    565     if (!BuiltinRange.getBegin().isValid()) {
    566       BuiltinRange = Range;
    567     } else {
    568       BuiltinRange.setBegin(std::min(Range.getBegin(), BuiltinRange.getBegin()));
    569       BuiltinRange.setEnd(std::max(Range.getEnd(), BuiltinRange.getEnd()));
    570     }
    571   }
    572 
    573   SourceLocation getNameLoc() const { return getBuiltinLoc(); }
    574 
    575   WrittenBuiltinSpecs& getWrittenBuiltinSpecs() {
    576     return *(static_cast<WrittenBuiltinSpecs*>(getExtraLocalData()));
    577   }
    578   const WrittenBuiltinSpecs& getWrittenBuiltinSpecs() const {
    579     return *(static_cast<WrittenBuiltinSpecs*>(getExtraLocalData()));
    580   }
    581 
    582   bool needsExtraLocalData() const {
    583     BuiltinType::Kind bk = getTypePtr()->getKind();
    584     return (bk >= BuiltinType::UShort && bk <= BuiltinType::UInt128)
    585       || (bk >= BuiltinType::Short && bk <= BuiltinType::Float128)
    586       || bk == BuiltinType::UChar
    587       || bk == BuiltinType::SChar;
    588   }
    589 
    590   unsigned getExtraLocalDataSize() const {
    591     return needsExtraLocalData() ? sizeof(WrittenBuiltinSpecs) : 0;
    592   }
    593 
    594   unsigned getExtraLocalDataAlignment() const {
    595     return needsExtraLocalData() ? alignof(WrittenBuiltinSpecs) : 1;
    596   }
    597 
    598   SourceRange getLocalSourceRange() const {
    599     return getLocalData()->BuiltinRange;
    600   }
    601 
    602   TypeSpecifierSign getWrittenSignSpec() const {
    603     if (needsExtraLocalData())
    604       return static_cast<TypeSpecifierSign>(getWrittenBuiltinSpecs().Sign);
    605     else
    606       return TypeSpecifierSign::Unspecified;
    607   }
    608 
    609   bool hasWrittenSignSpec() const {
    610     return getWrittenSignSpec() != TypeSpecifierSign::Unspecified;
    611   }
    612 
    613   void setWrittenSignSpec(TypeSpecifierSign written) {
    614     if (needsExtraLocalData())
    615       getWrittenBuiltinSpecs().Sign = static_cast<unsigned>(written);
    616   }
    617 
    618   TypeSpecifierWidth getWrittenWidthSpec() const {
    619     if (needsExtraLocalData())
    620       return static_cast<TypeSpecifierWidth>(getWrittenBuiltinSpecs().Width);
    621     else
    622       return TypeSpecifierWidth::Unspecified;
    623   }
    624 
    625   bool hasWrittenWidthSpec() const {
    626     return getWrittenWidthSpec() != TypeSpecifierWidth::Unspecified;
    627   }
    628 
    629   void setWrittenWidthSpec(TypeSpecifierWidth written) {
    630     if (needsExtraLocalData())
    631       getWrittenBuiltinSpecs().Width = static_cast<unsigned>(written);
    632   }
    633 
    634   TypeSpecifierType getWrittenTypeSpec() const;
    635 
    636   bool hasWrittenTypeSpec() const {
    637     return getWrittenTypeSpec() != TST_unspecified;
    638   }
    639 
    640   void setWrittenTypeSpec(TypeSpecifierType written) {
    641     if (needsExtraLocalData())
    642       getWrittenBuiltinSpecs().Type = written;
    643   }
    644 
    645   bool hasModeAttr() const {
    646     if (needsExtraLocalData())
    647       return getWrittenBuiltinSpecs().ModeAttr;
    648     else
    649       return false;
    650   }
    651 
    652   void setModeAttr(bool written) {
    653     if (needsExtraLocalData())
    654       getWrittenBuiltinSpecs().ModeAttr = written;
    655   }
    656 
    657   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
    658     setBuiltinLoc(Loc);
    659     if (needsExtraLocalData()) {
    660       WrittenBuiltinSpecs &wbs = getWrittenBuiltinSpecs();
    661       wbs.Sign = static_cast<unsigned>(TypeSpecifierSign::Unspecified);
    662       wbs.Width = static_cast<unsigned>(TypeSpecifierWidth::Unspecified);
    663       wbs.Type = TST_unspecified;
    664       wbs.ModeAttr = false;
    665     }
    666   }
    667 };
    668 
    669 /// Wrapper for source info for typedefs.
    670 class TypedefTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    671                                                         TypedefTypeLoc,
    672                                                         TypedefType> {
    673 public:
    674   TypedefNameDecl *getTypedefNameDecl() const {
    675     return getTypePtr()->getDecl();
    676   }
    677 };
    678 
    679 /// Wrapper for source info for injected class names of class
    680 /// templates.
    681 class InjectedClassNameTypeLoc :
    682     public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    683                                      InjectedClassNameTypeLoc,
    684                                      InjectedClassNameType> {
    685 public:
    686   CXXRecordDecl *getDecl() const {
    687     return getTypePtr()->getDecl();
    688   }
    689 };
    690 
    691 /// Wrapper for source info for unresolved typename using decls.
    692 class UnresolvedUsingTypeLoc :
    693     public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    694                                      UnresolvedUsingTypeLoc,
    695                                      UnresolvedUsingType> {
    696 public:
    697   UnresolvedUsingTypenameDecl *getDecl() const {
    698     return getTypePtr()->getDecl();
    699   }
    700 };
    701 
    702 /// Wrapper for source info for tag types.  Note that this only
    703 /// records source info for the name itself; a type written 'struct foo'
    704 /// should be represented as an ElaboratedTypeLoc.  We currently
    705 /// only do that when C++ is enabled because of the expense of
    706 /// creating an ElaboratedType node for so many type references in C.
    707 class TagTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    708                                                     TagTypeLoc,
    709                                                     TagType> {
    710 public:
    711   TagDecl *getDecl() const { return getTypePtr()->getDecl(); }
    712 
    713   /// True if the tag was defined in this type specifier.
    714   bool isDefinition() const;
    715 };
    716 
    717 /// Wrapper for source info for record types.
    718 class RecordTypeLoc : public InheritingConcreteTypeLoc<TagTypeLoc,
    719                                                        RecordTypeLoc,
    720                                                        RecordType> {
    721 public:
    722   RecordDecl *getDecl() const { return getTypePtr()->getDecl(); }
    723 };
    724 
    725 /// Wrapper for source info for enum types.
    726 class EnumTypeLoc : public InheritingConcreteTypeLoc<TagTypeLoc,
    727                                                      EnumTypeLoc,
    728                                                      EnumType> {
    729 public:
    730   EnumDecl *getDecl() const { return getTypePtr()->getDecl(); }
    731 };
    732 
    733 /// Wrapper for template type parameters.
    734 class TemplateTypeParmTypeLoc :
    735     public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    736                                      TemplateTypeParmTypeLoc,
    737                                      TemplateTypeParmType> {
    738 public:
    739   TemplateTypeParmDecl *getDecl() const { return getTypePtr()->getDecl(); }
    740 };
    741 
    742 struct ObjCTypeParamTypeLocInfo {
    743   SourceLocation NameLoc;
    744 };
    745 
    746 /// ProtocolLAngleLoc, ProtocolRAngleLoc, and the source locations for
    747 /// protocol qualifiers are stored after Info.
    748 class ObjCTypeParamTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
    749                                      ObjCTypeParamTypeLoc,
    750                                      ObjCTypeParamType,
    751                                      ObjCTypeParamTypeLocInfo> {
    752   // SourceLocations are stored after Info, one for each protocol qualifier.
    753   SourceLocation *getProtocolLocArray() const {
    754     return (SourceLocation*)this->getExtraLocalData() + 2;
    755   }
    756 
    757 public:
    758   ObjCTypeParamDecl *getDecl() const { return getTypePtr()->getDecl(); }
    759 
    760   SourceLocation getNameLoc() const {
    761     return this->getLocalData()->NameLoc;
    762   }
    763 
    764   void setNameLoc(SourceLocation Loc) {
    765     this->getLocalData()->NameLoc = Loc;
    766   }
    767 
    768   SourceLocation getProtocolLAngleLoc() const {
    769     return getNumProtocols()  ?
    770       *((SourceLocation*)this->getExtraLocalData()) :
    771       SourceLocation();
    772   }
    773 
    774   void setProtocolLAngleLoc(SourceLocation Loc) {
    775     *((SourceLocation*)this->getExtraLocalData()) = Loc;
    776   }
    777 
    778   SourceLocation getProtocolRAngleLoc() const {
    779     return getNumProtocols()  ?
    780       *((SourceLocation*)this->getExtraLocalData() + 1) :
    781       SourceLocation();
    782   }
    783 
    784   void setProtocolRAngleLoc(SourceLocation Loc) {
    785     *((SourceLocation*)this->getExtraLocalData() + 1) = Loc;
    786   }
    787 
    788   unsigned getNumProtocols() const {
    789     return this->getTypePtr()->getNumProtocols();
    790   }
    791 
    792   SourceLocation getProtocolLoc(unsigned i) const {
    793     assert(i < getNumProtocols() && "Index is out of bounds!");
    794     return getProtocolLocArray()[i];
    795   }
    796 
    797   void setProtocolLoc(unsigned i, SourceLocation Loc) {
    798     assert(i < getNumProtocols() && "Index is out of bounds!");
    799     getProtocolLocArray()[i] = Loc;
    800   }
    801 
    802   ObjCProtocolDecl *getProtocol(unsigned i) const {
    803     assert(i < getNumProtocols() && "Index is out of bounds!");
    804     return *(this->getTypePtr()->qual_begin() + i);
    805   }
    806 
    807   ArrayRef<SourceLocation> getProtocolLocs() const {
    808     return llvm::makeArrayRef(getProtocolLocArray(), getNumProtocols());
    809   }
    810 
    811   void initializeLocal(ASTContext &Context, SourceLocation Loc);
    812 
    813   unsigned getExtraLocalDataSize() const {
    814     if (!this->getNumProtocols()) return 0;
    815     // When there are protocol qualifers, we have LAngleLoc and RAngleLoc
    816     // as well.
    817     return (this->getNumProtocols() + 2) * sizeof(SourceLocation) ;
    818   }
    819 
    820   unsigned getExtraLocalDataAlignment() const {
    821     return alignof(SourceLocation);
    822   }
    823 
    824   SourceRange getLocalSourceRange() const {
    825     SourceLocation start = getNameLoc();
    826     SourceLocation end = getProtocolRAngleLoc();
    827     if (end.isInvalid()) return SourceRange(start, start);
    828     return SourceRange(start, end);
    829   }
    830 };
    831 
    832 /// Wrapper for substituted template type parameters.
    833 class SubstTemplateTypeParmTypeLoc :
    834     public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    835                                      SubstTemplateTypeParmTypeLoc,
    836                                      SubstTemplateTypeParmType> {
    837 };
    838 
    839   /// Wrapper for substituted template type parameters.
    840 class SubstTemplateTypeParmPackTypeLoc :
    841     public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
    842                                      SubstTemplateTypeParmPackTypeLoc,
    843                                      SubstTemplateTypeParmPackType> {
    844 };
    845 
    846 struct AttributedLocInfo {
    847   const Attr *TypeAttr;
    848 };
    849 
    850 /// Type source information for an attributed type.
    851 class AttributedTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
    852                                                  AttributedTypeLoc,
    853                                                  AttributedType,
    854                                                  AttributedLocInfo> {
    855 public:
    856   attr::Kind getAttrKind() const {
    857     return getTypePtr()->getAttrKind();
    858   }
    859 
    860   bool isQualifier() const {
    861     return getTypePtr()->isQualifier();
    862   }
    863 
    864   /// The modified type, which is generally canonically different from
    865   /// the attribute type.
    866   ///    int main(int, char**) __attribute__((noreturn))
    867   ///    ~~~     ~~~~~~~~~~~~~
    868   TypeLoc getModifiedLoc() const {
    869     return getInnerTypeLoc();
    870   }
    871 
    872   /// The type attribute.
    873   const Attr *getAttr() const {
    874     return getLocalData()->TypeAttr;
    875   }
    876   void setAttr(const Attr *A) {
    877     getLocalData()->TypeAttr = A;
    878   }
    879 
    880   template<typename T> const T *getAttrAs() {
    881     return dyn_cast_or_null<T>(getAttr());
    882   }
    883 
    884   SourceRange getLocalSourceRange() const;
    885 
    886   void initializeLocal(ASTContext &Context, SourceLocation loc) {
    887     setAttr(nullptr);
    888   }
    889 
    890   QualType getInnerType() const {
    891     return getTypePtr()->getModifiedType();
    892   }
    893 };
    894 
    895 struct ObjCObjectTypeLocInfo {
    896   SourceLocation TypeArgsLAngleLoc;
    897   SourceLocation TypeArgsRAngleLoc;
    898   SourceLocation ProtocolLAngleLoc;
    899   SourceLocation ProtocolRAngleLoc;
    900   bool HasBaseTypeAsWritten;
    901 };
    902 
    903 // A helper class for defining ObjC TypeLocs that can qualified with
    904 // protocols.
    905 //
    906 // TypeClass basically has to be either ObjCInterfaceType or
    907 // ObjCObjectPointerType.
    908 class ObjCObjectTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
    909                                                  ObjCObjectTypeLoc,
    910                                                  ObjCObjectType,
    911                                                  ObjCObjectTypeLocInfo> {
    912   // TypeSourceInfo*'s are stored after Info, one for each type argument.
    913   TypeSourceInfo **getTypeArgLocArray() const {
    914     return (TypeSourceInfo**)this->getExtraLocalData();
    915   }
    916 
    917   // SourceLocations are stored after the type argument information, one for
    918   // each Protocol.
    919   SourceLocation *getProtocolLocArray() const {
    920     return (SourceLocation*)(getTypeArgLocArray() + getNumTypeArgs());
    921   }
    922 
    923 public:
    924   SourceLocation getTypeArgsLAngleLoc() const {
    925     return this->getLocalData()->TypeArgsLAngleLoc;
    926   }
    927 
    928   void setTypeArgsLAngleLoc(SourceLocation Loc) {
    929     this->getLocalData()->TypeArgsLAngleLoc = Loc;
    930   }
    931 
    932   SourceLocation getTypeArgsRAngleLoc() const {
    933     return this->getLocalData()->TypeArgsRAngleLoc;
    934   }
    935 
    936   void setTypeArgsRAngleLoc(SourceLocation Loc) {
    937     this->getLocalData()->TypeArgsRAngleLoc = Loc;
    938   }
    939 
    940   unsigned getNumTypeArgs() const {
    941     return this->getTypePtr()->getTypeArgsAsWritten().size();
    942   }
    943 
    944   TypeSourceInfo *getTypeArgTInfo(unsigned i) const {
    945     assert(i < getNumTypeArgs() && "Index is out of bounds!");
    946     return getTypeArgLocArray()[i];
    947   }
    948 
    949   void setTypeArgTInfo(unsigned i, TypeSourceInfo *TInfo) {
    950     assert(i < getNumTypeArgs() && "Index is out of bounds!");
    951     getTypeArgLocArray()[i] = TInfo;
    952   }
    953 
    954   SourceLocation getProtocolLAngleLoc() const {
    955     return this->getLocalData()->ProtocolLAngleLoc;
    956   }
    957 
    958   void setProtocolLAngleLoc(SourceLocation Loc) {
    959     this->getLocalData()->ProtocolLAngleLoc = Loc;
    960   }
    961 
    962   SourceLocation getProtocolRAngleLoc() const {
    963     return this->getLocalData()->ProtocolRAngleLoc;
    964   }
    965 
    966   void setProtocolRAngleLoc(SourceLocation Loc) {
    967     this->getLocalData()->ProtocolRAngleLoc = Loc;
    968   }
    969 
    970   unsigned getNumProtocols() const {
    971     return this->getTypePtr()->getNumProtocols();
    972   }
    973 
    974   SourceLocation getProtocolLoc(unsigned i) const {
    975     assert(i < getNumProtocols() && "Index is out of bounds!");
    976     return getProtocolLocArray()[i];
    977   }
    978 
    979   void setProtocolLoc(unsigned i, SourceLocation Loc) {
    980     assert(i < getNumProtocols() && "Index is out of bounds!");
    981     getProtocolLocArray()[i] = Loc;
    982   }
    983 
    984   ObjCProtocolDecl *getProtocol(unsigned i) const {
    985     assert(i < getNumProtocols() && "Index is out of bounds!");
    986     return *(this->getTypePtr()->qual_begin() + i);
    987   }
    988 
    989 
    990   ArrayRef<SourceLocation> getProtocolLocs() const {
    991     return llvm::makeArrayRef(getProtocolLocArray(), getNumProtocols());
    992   }
    993 
    994   bool hasBaseTypeAsWritten() const {
    995     return getLocalData()->HasBaseTypeAsWritten;
    996   }
    997 
    998   void setHasBaseTypeAsWritten(bool HasBaseType) {
    999     getLocalData()->HasBaseTypeAsWritten = HasBaseType;
   1000   }
   1001 
   1002   TypeLoc getBaseLoc() const {
   1003     return getInnerTypeLoc();
   1004   }
   1005 
   1006   SourceRange getLocalSourceRange() const {
   1007     SourceLocation start = getTypeArgsLAngleLoc();
   1008     if (start.isInvalid())
   1009       start = getProtocolLAngleLoc();
   1010     SourceLocation end = getProtocolRAngleLoc();
   1011     if (end.isInvalid())
   1012       end = getTypeArgsRAngleLoc();
   1013     return SourceRange(start, end);
   1014   }
   1015 
   1016   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   1017 
   1018   unsigned getExtraLocalDataSize() const {
   1019     return this->getNumTypeArgs() * sizeof(TypeSourceInfo *)
   1020          + this->getNumProtocols() * sizeof(SourceLocation);
   1021   }
   1022 
   1023   unsigned getExtraLocalDataAlignment() const {
   1024     static_assert(alignof(ObjCObjectTypeLoc) >= alignof(TypeSourceInfo *),
   1025                   "not enough alignment for tail-allocated data");
   1026     return alignof(TypeSourceInfo *);
   1027   }
   1028 
   1029   QualType getInnerType() const {
   1030     return getTypePtr()->getBaseType();
   1031   }
   1032 };
   1033 
   1034 struct ObjCInterfaceLocInfo {
   1035   SourceLocation NameLoc;
   1036   SourceLocation NameEndLoc;
   1037 };
   1038 
   1039 /// Wrapper for source info for ObjC interfaces.
   1040 class ObjCInterfaceTypeLoc : public ConcreteTypeLoc<ObjCObjectTypeLoc,
   1041                                                     ObjCInterfaceTypeLoc,
   1042                                                     ObjCInterfaceType,
   1043                                                     ObjCInterfaceLocInfo> {
   1044 public:
   1045   ObjCInterfaceDecl *getIFaceDecl() const {
   1046     return getTypePtr()->getDecl();
   1047   }
   1048 
   1049   SourceLocation getNameLoc() const {
   1050     return getLocalData()->NameLoc;
   1051   }
   1052 
   1053   void setNameLoc(SourceLocation Loc) {
   1054     getLocalData()->NameLoc = Loc;
   1055   }
   1056 
   1057   SourceRange getLocalSourceRange() const {
   1058     return SourceRange(getNameLoc(), getNameEndLoc());
   1059   }
   1060 
   1061   SourceLocation getNameEndLoc() const {
   1062     return getLocalData()->NameEndLoc;
   1063   }
   1064 
   1065   void setNameEndLoc(SourceLocation Loc) {
   1066     getLocalData()->NameEndLoc = Loc;
   1067   }
   1068 
   1069   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1070     setNameLoc(Loc);
   1071     setNameEndLoc(Loc);
   1072   }
   1073 };
   1074 
   1075 struct MacroQualifiedLocInfo {
   1076   SourceLocation ExpansionLoc;
   1077 };
   1078 
   1079 class MacroQualifiedTypeLoc
   1080     : public ConcreteTypeLoc<UnqualTypeLoc, MacroQualifiedTypeLoc,
   1081                              MacroQualifiedType, MacroQualifiedLocInfo> {
   1082 public:
   1083   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1084     setExpansionLoc(Loc);
   1085   }
   1086 
   1087   TypeLoc getInnerLoc() const { return getInnerTypeLoc(); }
   1088 
   1089   const IdentifierInfo *getMacroIdentifier() const {
   1090     return getTypePtr()->getMacroIdentifier();
   1091   }
   1092 
   1093   SourceLocation getExpansionLoc() const {
   1094     return this->getLocalData()->ExpansionLoc;
   1095   }
   1096 
   1097   void setExpansionLoc(SourceLocation Loc) {
   1098     this->getLocalData()->ExpansionLoc = Loc;
   1099   }
   1100 
   1101   QualType getInnerType() const { return getTypePtr()->getUnderlyingType(); }
   1102 
   1103   SourceRange getLocalSourceRange() const {
   1104     return getInnerLoc().getLocalSourceRange();
   1105   }
   1106 };
   1107 
   1108 struct ParenLocInfo {
   1109   SourceLocation LParenLoc;
   1110   SourceLocation RParenLoc;
   1111 };
   1112 
   1113 class ParenTypeLoc
   1114   : public ConcreteTypeLoc<UnqualTypeLoc, ParenTypeLoc, ParenType,
   1115                            ParenLocInfo> {
   1116 public:
   1117   SourceLocation getLParenLoc() const {
   1118     return this->getLocalData()->LParenLoc;
   1119   }
   1120 
   1121   SourceLocation getRParenLoc() const {
   1122     return this->getLocalData()->RParenLoc;
   1123   }
   1124 
   1125   void setLParenLoc(SourceLocation Loc) {
   1126     this->getLocalData()->LParenLoc = Loc;
   1127   }
   1128 
   1129   void setRParenLoc(SourceLocation Loc) {
   1130     this->getLocalData()->RParenLoc = Loc;
   1131   }
   1132 
   1133   SourceRange getLocalSourceRange() const {
   1134     return SourceRange(getLParenLoc(), getRParenLoc());
   1135   }
   1136 
   1137   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1138     setLParenLoc(Loc);
   1139     setRParenLoc(Loc);
   1140   }
   1141 
   1142   TypeLoc getInnerLoc() const {
   1143     return getInnerTypeLoc();
   1144   }
   1145 
   1146   QualType getInnerType() const {
   1147     return this->getTypePtr()->getInnerType();
   1148   }
   1149 };
   1150 
   1151 inline TypeLoc TypeLoc::IgnoreParens() const {
   1152   if (ParenTypeLoc::isKind(*this))
   1153     return IgnoreParensImpl(*this);
   1154   return *this;
   1155 }
   1156 
   1157 struct AdjustedLocInfo {}; // Nothing.
   1158 
   1159 class AdjustedTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, AdjustedTypeLoc,
   1160                                                AdjustedType, AdjustedLocInfo> {
   1161 public:
   1162   TypeLoc getOriginalLoc() const {
   1163     return getInnerTypeLoc();
   1164   }
   1165 
   1166   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1167     // do nothing
   1168   }
   1169 
   1170   QualType getInnerType() const {
   1171     // The inner type is the undecayed type, since that's what we have source
   1172     // location information for.
   1173     return getTypePtr()->getOriginalType();
   1174   }
   1175 
   1176   SourceRange getLocalSourceRange() const { return {}; }
   1177 
   1178   unsigned getLocalDataSize() const {
   1179     // sizeof(AdjustedLocInfo) is 1, but we don't need its address to be unique
   1180     // anyway.  TypeLocBuilder can't handle data sizes of 1.
   1181     return 0;  // No data.
   1182   }
   1183 };
   1184 
   1185 /// Wrapper for source info for pointers decayed from arrays and
   1186 /// functions.
   1187 class DecayedTypeLoc : public InheritingConcreteTypeLoc<
   1188                            AdjustedTypeLoc, DecayedTypeLoc, DecayedType> {
   1189 };
   1190 
   1191 struct PointerLikeLocInfo {
   1192   SourceLocation StarLoc;
   1193 };
   1194 
   1195 /// A base class for
   1196 template <class Derived, class TypeClass, class LocalData = PointerLikeLocInfo>
   1197 class PointerLikeTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, Derived,
   1198                                                   TypeClass, LocalData> {
   1199 public:
   1200   SourceLocation getSigilLoc() const {
   1201     return this->getLocalData()->StarLoc;
   1202   }
   1203 
   1204   void setSigilLoc(SourceLocation Loc) {
   1205     this->getLocalData()->StarLoc = Loc;
   1206   }
   1207 
   1208   TypeLoc getPointeeLoc() const {
   1209     return this->getInnerTypeLoc();
   1210   }
   1211 
   1212   SourceRange getLocalSourceRange() const {
   1213     return SourceRange(getSigilLoc(), getSigilLoc());
   1214   }
   1215 
   1216   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1217     setSigilLoc(Loc);
   1218   }
   1219 
   1220   QualType getInnerType() const {
   1221     return this->getTypePtr()->getPointeeType();
   1222   }
   1223 };
   1224 
   1225 /// Wrapper for source info for pointers.
   1226 class PointerTypeLoc : public PointerLikeTypeLoc<PointerTypeLoc,
   1227                                                  PointerType> {
   1228 public:
   1229   SourceLocation getStarLoc() const {
   1230     return getSigilLoc();
   1231   }
   1232 
   1233   void setStarLoc(SourceLocation Loc) {
   1234     setSigilLoc(Loc);
   1235   }
   1236 };
   1237 
   1238 /// Wrapper for source info for block pointers.
   1239 class BlockPointerTypeLoc : public PointerLikeTypeLoc<BlockPointerTypeLoc,
   1240                                                       BlockPointerType> {
   1241 public:
   1242   SourceLocation getCaretLoc() const {
   1243     return getSigilLoc();
   1244   }
   1245 
   1246   void setCaretLoc(SourceLocation Loc) {
   1247     setSigilLoc(Loc);
   1248   }
   1249 };
   1250 
   1251 struct MemberPointerLocInfo : public PointerLikeLocInfo {
   1252   TypeSourceInfo *ClassTInfo;
   1253 };
   1254 
   1255 /// Wrapper for source info for member pointers.
   1256 class MemberPointerTypeLoc : public PointerLikeTypeLoc<MemberPointerTypeLoc,
   1257                                                        MemberPointerType,
   1258                                                        MemberPointerLocInfo> {
   1259 public:
   1260   SourceLocation getStarLoc() const {
   1261     return getSigilLoc();
   1262   }
   1263 
   1264   void setStarLoc(SourceLocation Loc) {
   1265     setSigilLoc(Loc);
   1266   }
   1267 
   1268   const Type *getClass() const {
   1269     return getTypePtr()->getClass();
   1270   }
   1271 
   1272   TypeSourceInfo *getClassTInfo() const {
   1273     return getLocalData()->ClassTInfo;
   1274   }
   1275 
   1276   void setClassTInfo(TypeSourceInfo* TI) {
   1277     getLocalData()->ClassTInfo = TI;
   1278   }
   1279 
   1280   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1281     setSigilLoc(Loc);
   1282     setClassTInfo(nullptr);
   1283   }
   1284 
   1285   SourceRange getLocalSourceRange() const {
   1286     if (TypeSourceInfo *TI = getClassTInfo())
   1287       return SourceRange(TI->getTypeLoc().getBeginLoc(), getStarLoc());
   1288     else
   1289       return SourceRange(getStarLoc());
   1290   }
   1291 };
   1292 
   1293 /// Wraps an ObjCPointerType with source location information.
   1294 class ObjCObjectPointerTypeLoc :
   1295     public PointerLikeTypeLoc<ObjCObjectPointerTypeLoc,
   1296                               ObjCObjectPointerType> {
   1297 public:
   1298   SourceLocation getStarLoc() const {
   1299     return getSigilLoc();
   1300   }
   1301 
   1302   void setStarLoc(SourceLocation Loc) {
   1303     setSigilLoc(Loc);
   1304   }
   1305 };
   1306 
   1307 class ReferenceTypeLoc : public PointerLikeTypeLoc<ReferenceTypeLoc,
   1308                                                    ReferenceType> {
   1309 public:
   1310   QualType getInnerType() const {
   1311     return getTypePtr()->getPointeeTypeAsWritten();
   1312   }
   1313 };
   1314 
   1315 class LValueReferenceTypeLoc :
   1316     public InheritingConcreteTypeLoc<ReferenceTypeLoc,
   1317                                      LValueReferenceTypeLoc,
   1318                                      LValueReferenceType> {
   1319 public:
   1320   SourceLocation getAmpLoc() const {
   1321     return getSigilLoc();
   1322   }
   1323 
   1324   void setAmpLoc(SourceLocation Loc) {
   1325     setSigilLoc(Loc);
   1326   }
   1327 };
   1328 
   1329 class RValueReferenceTypeLoc :
   1330     public InheritingConcreteTypeLoc<ReferenceTypeLoc,
   1331                                      RValueReferenceTypeLoc,
   1332                                      RValueReferenceType> {
   1333 public:
   1334   SourceLocation getAmpAmpLoc() const {
   1335     return getSigilLoc();
   1336   }
   1337 
   1338   void setAmpAmpLoc(SourceLocation Loc) {
   1339     setSigilLoc(Loc);
   1340   }
   1341 };
   1342 
   1343 struct FunctionLocInfo {
   1344   SourceLocation LocalRangeBegin;
   1345   SourceLocation LParenLoc;
   1346   SourceLocation RParenLoc;
   1347   SourceLocation LocalRangeEnd;
   1348 };
   1349 
   1350 /// Wrapper for source info for functions.
   1351 class FunctionTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
   1352                                                FunctionTypeLoc,
   1353                                                FunctionType,
   1354                                                FunctionLocInfo> {
   1355   bool hasExceptionSpec() const {
   1356     if (auto *FPT = dyn_cast<FunctionProtoType>(getTypePtr())) {
   1357       return FPT->hasExceptionSpec();
   1358     }
   1359     return false;
   1360   }
   1361 
   1362   SourceRange *getExceptionSpecRangePtr() const {
   1363     assert(hasExceptionSpec() && "No exception spec range");
   1364     // After the Info comes the ParmVarDecl array, and after that comes the
   1365     // exception specification information.
   1366     return (SourceRange *)(getParmArray() + getNumParams());
   1367   }
   1368 
   1369 public:
   1370   SourceLocation getLocalRangeBegin() const {
   1371     return getLocalData()->LocalRangeBegin;
   1372   }
   1373 
   1374   void setLocalRangeBegin(SourceLocation L) {
   1375     getLocalData()->LocalRangeBegin = L;
   1376   }
   1377 
   1378   SourceLocation getLocalRangeEnd() const {
   1379     return getLocalData()->LocalRangeEnd;
   1380   }
   1381 
   1382   void setLocalRangeEnd(SourceLocation L) {
   1383     getLocalData()->LocalRangeEnd = L;
   1384   }
   1385 
   1386   SourceLocation getLParenLoc() const {
   1387     return this->getLocalData()->LParenLoc;
   1388   }
   1389 
   1390   void setLParenLoc(SourceLocation Loc) {
   1391     this->getLocalData()->LParenLoc = Loc;
   1392   }
   1393 
   1394   SourceLocation getRParenLoc() const {
   1395     return this->getLocalData()->RParenLoc;
   1396   }
   1397 
   1398   void setRParenLoc(SourceLocation Loc) {
   1399     this->getLocalData()->RParenLoc = Loc;
   1400   }
   1401 
   1402   SourceRange getParensRange() const {
   1403     return SourceRange(getLParenLoc(), getRParenLoc());
   1404   }
   1405 
   1406   SourceRange getExceptionSpecRange() const {
   1407     if (hasExceptionSpec())
   1408       return *getExceptionSpecRangePtr();
   1409     return {};
   1410   }
   1411 
   1412   void setExceptionSpecRange(SourceRange R) {
   1413     if (hasExceptionSpec())
   1414       *getExceptionSpecRangePtr() = R;
   1415   }
   1416 
   1417   ArrayRef<ParmVarDecl *> getParams() const {
   1418     return llvm::makeArrayRef(getParmArray(), getNumParams());
   1419   }
   1420 
   1421   // ParmVarDecls* are stored after Info, one for each parameter.
   1422   ParmVarDecl **getParmArray() const {
   1423     return (ParmVarDecl**) getExtraLocalData();
   1424   }
   1425 
   1426   unsigned getNumParams() const {
   1427     if (isa<FunctionNoProtoType>(getTypePtr()))
   1428       return 0;
   1429     return cast<FunctionProtoType>(getTypePtr())->getNumParams();
   1430   }
   1431 
   1432   ParmVarDecl *getParam(unsigned i) const { return getParmArray()[i]; }
   1433   void setParam(unsigned i, ParmVarDecl *VD) { getParmArray()[i] = VD; }
   1434 
   1435   TypeLoc getReturnLoc() const {
   1436     return getInnerTypeLoc();
   1437   }
   1438 
   1439   SourceRange getLocalSourceRange() const {
   1440     return SourceRange(getLocalRangeBegin(), getLocalRangeEnd());
   1441   }
   1442 
   1443   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1444     setLocalRangeBegin(Loc);
   1445     setLParenLoc(Loc);
   1446     setRParenLoc(Loc);
   1447     setLocalRangeEnd(Loc);
   1448     for (unsigned i = 0, e = getNumParams(); i != e; ++i)
   1449       setParam(i, nullptr);
   1450     if (hasExceptionSpec())
   1451       setExceptionSpecRange(Loc);
   1452   }
   1453 
   1454   /// Returns the size of the type source info data block that is
   1455   /// specific to this type.
   1456   unsigned getExtraLocalDataSize() const {
   1457     unsigned ExceptSpecSize = hasExceptionSpec() ? sizeof(SourceRange) : 0;
   1458     return (getNumParams() * sizeof(ParmVarDecl *)) + ExceptSpecSize;
   1459   }
   1460 
   1461   unsigned getExtraLocalDataAlignment() const { return alignof(ParmVarDecl *); }
   1462 
   1463   QualType getInnerType() const { return getTypePtr()->getReturnType(); }
   1464 };
   1465 
   1466 class FunctionProtoTypeLoc :
   1467     public InheritingConcreteTypeLoc<FunctionTypeLoc,
   1468                                      FunctionProtoTypeLoc,
   1469                                      FunctionProtoType> {
   1470 };
   1471 
   1472 class FunctionNoProtoTypeLoc :
   1473     public InheritingConcreteTypeLoc<FunctionTypeLoc,
   1474                                      FunctionNoProtoTypeLoc,
   1475                                      FunctionNoProtoType> {
   1476 };
   1477 
   1478 struct ArrayLocInfo {
   1479   SourceLocation LBracketLoc, RBracketLoc;
   1480   Expr *Size;
   1481 };
   1482 
   1483 /// Wrapper for source info for arrays.
   1484 class ArrayTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
   1485                                             ArrayTypeLoc,
   1486                                             ArrayType,
   1487                                             ArrayLocInfo> {
   1488 public:
   1489   SourceLocation getLBracketLoc() const {
   1490     return getLocalData()->LBracketLoc;
   1491   }
   1492 
   1493   void setLBracketLoc(SourceLocation Loc) {
   1494     getLocalData()->LBracketLoc = Loc;
   1495   }
   1496 
   1497   SourceLocation getRBracketLoc() const {
   1498     return getLocalData()->RBracketLoc;
   1499   }
   1500 
   1501   void setRBracketLoc(SourceLocation Loc) {
   1502     getLocalData()->RBracketLoc = Loc;
   1503   }
   1504 
   1505   SourceRange getBracketsRange() const {
   1506     return SourceRange(getLBracketLoc(), getRBracketLoc());
   1507   }
   1508 
   1509   Expr *getSizeExpr() const {
   1510     return getLocalData()->Size;
   1511   }
   1512 
   1513   void setSizeExpr(Expr *Size) {
   1514     getLocalData()->Size = Size;
   1515   }
   1516 
   1517   TypeLoc getElementLoc() const {
   1518     return getInnerTypeLoc();
   1519   }
   1520 
   1521   SourceRange getLocalSourceRange() const {
   1522     return SourceRange(getLBracketLoc(), getRBracketLoc());
   1523   }
   1524 
   1525   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1526     setLBracketLoc(Loc);
   1527     setRBracketLoc(Loc);
   1528     setSizeExpr(nullptr);
   1529   }
   1530 
   1531   QualType getInnerType() const { return getTypePtr()->getElementType(); }
   1532 };
   1533 
   1534 class ConstantArrayTypeLoc :
   1535     public InheritingConcreteTypeLoc<ArrayTypeLoc,
   1536                                      ConstantArrayTypeLoc,
   1537                                      ConstantArrayType> {
   1538 };
   1539 
   1540 class IncompleteArrayTypeLoc :
   1541     public InheritingConcreteTypeLoc<ArrayTypeLoc,
   1542                                      IncompleteArrayTypeLoc,
   1543                                      IncompleteArrayType> {
   1544 };
   1545 
   1546 class DependentSizedArrayTypeLoc :
   1547     public InheritingConcreteTypeLoc<ArrayTypeLoc,
   1548                                      DependentSizedArrayTypeLoc,
   1549                                      DependentSizedArrayType> {
   1550 public:
   1551   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1552     ArrayTypeLoc::initializeLocal(Context, Loc);
   1553     setSizeExpr(getTypePtr()->getSizeExpr());
   1554   }
   1555 };
   1556 
   1557 class VariableArrayTypeLoc :
   1558     public InheritingConcreteTypeLoc<ArrayTypeLoc,
   1559                                      VariableArrayTypeLoc,
   1560                                      VariableArrayType> {
   1561 };
   1562 
   1563 // Location information for a TemplateName.  Rudimentary for now.
   1564 struct TemplateNameLocInfo {
   1565   SourceLocation NameLoc;
   1566 };
   1567 
   1568 struct TemplateSpecializationLocInfo : TemplateNameLocInfo {
   1569   SourceLocation TemplateKWLoc;
   1570   SourceLocation LAngleLoc;
   1571   SourceLocation RAngleLoc;
   1572 };
   1573 
   1574 class TemplateSpecializationTypeLoc :
   1575     public ConcreteTypeLoc<UnqualTypeLoc,
   1576                            TemplateSpecializationTypeLoc,
   1577                            TemplateSpecializationType,
   1578                            TemplateSpecializationLocInfo> {
   1579 public:
   1580   SourceLocation getTemplateKeywordLoc() const {
   1581     return getLocalData()->TemplateKWLoc;
   1582   }
   1583 
   1584   void setTemplateKeywordLoc(SourceLocation Loc) {
   1585     getLocalData()->TemplateKWLoc = Loc;
   1586   }
   1587 
   1588   SourceLocation getLAngleLoc() const {
   1589     return getLocalData()->LAngleLoc;
   1590   }
   1591 
   1592   void setLAngleLoc(SourceLocation Loc) {
   1593     getLocalData()->LAngleLoc = Loc;
   1594   }
   1595 
   1596   SourceLocation getRAngleLoc() const {
   1597     return getLocalData()->RAngleLoc;
   1598   }
   1599 
   1600   void setRAngleLoc(SourceLocation Loc) {
   1601     getLocalData()->RAngleLoc = Loc;
   1602   }
   1603 
   1604   unsigned getNumArgs() const {
   1605     return getTypePtr()->getNumArgs();
   1606   }
   1607 
   1608   void setArgLocInfo(unsigned i, TemplateArgumentLocInfo AI) {
   1609     getArgInfos()[i] = AI;
   1610   }
   1611 
   1612   TemplateArgumentLocInfo getArgLocInfo(unsigned i) const {
   1613     return getArgInfos()[i];
   1614   }
   1615 
   1616   TemplateArgumentLoc getArgLoc(unsigned i) const {
   1617     return TemplateArgumentLoc(getTypePtr()->getArg(i), getArgLocInfo(i));
   1618   }
   1619 
   1620   SourceLocation getTemplateNameLoc() const {
   1621     return getLocalData()->NameLoc;
   1622   }
   1623 
   1624   void setTemplateNameLoc(SourceLocation Loc) {
   1625     getLocalData()->NameLoc = Loc;
   1626   }
   1627 
   1628   /// - Copy the location information from the given info.
   1629   void copy(TemplateSpecializationTypeLoc Loc) {
   1630     unsigned size = getFullDataSize();
   1631     assert(size == Loc.getFullDataSize());
   1632 
   1633     // We're potentially copying Expr references here.  We don't
   1634     // bother retaining them because TypeSourceInfos live forever, so
   1635     // as long as the Expr was retained when originally written into
   1636     // the TypeLoc, we're okay.
   1637     memcpy(Data, Loc.Data, size);
   1638   }
   1639 
   1640   SourceRange getLocalSourceRange() const {
   1641     if (getTemplateKeywordLoc().isValid())
   1642       return SourceRange(getTemplateKeywordLoc(), getRAngleLoc());
   1643     else
   1644       return SourceRange(getTemplateNameLoc(), getRAngleLoc());
   1645   }
   1646 
   1647   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1648     setTemplateKeywordLoc(Loc);
   1649     setTemplateNameLoc(Loc);
   1650     setLAngleLoc(Loc);
   1651     setRAngleLoc(Loc);
   1652     initializeArgLocs(Context, getNumArgs(), getTypePtr()->getArgs(),
   1653                       getArgInfos(), Loc);
   1654   }
   1655 
   1656   static void initializeArgLocs(ASTContext &Context, unsigned NumArgs,
   1657                                 const TemplateArgument *Args,
   1658                                 TemplateArgumentLocInfo *ArgInfos,
   1659                                 SourceLocation Loc);
   1660 
   1661   unsigned getExtraLocalDataSize() const {
   1662     return getNumArgs() * sizeof(TemplateArgumentLocInfo);
   1663   }
   1664 
   1665   unsigned getExtraLocalDataAlignment() const {
   1666     return alignof(TemplateArgumentLocInfo);
   1667   }
   1668 
   1669 private:
   1670   TemplateArgumentLocInfo *getArgInfos() const {
   1671     return static_cast<TemplateArgumentLocInfo*>(getExtraLocalData());
   1672   }
   1673 };
   1674 
   1675 struct DependentAddressSpaceLocInfo {
   1676   Expr *ExprOperand;
   1677   SourceRange OperandParens;
   1678   SourceLocation AttrLoc;
   1679 };
   1680 
   1681 class DependentAddressSpaceTypeLoc
   1682     : public ConcreteTypeLoc<UnqualTypeLoc,
   1683                              DependentAddressSpaceTypeLoc,
   1684                              DependentAddressSpaceType,
   1685                              DependentAddressSpaceLocInfo> {
   1686 public:
   1687   /// The location of the attribute name, i.e.
   1688   ///    int * __attribute__((address_space(11)))
   1689   ///                         ^~~~~~~~~~~~~
   1690   SourceLocation getAttrNameLoc() const {
   1691     return getLocalData()->AttrLoc;
   1692   }
   1693   void setAttrNameLoc(SourceLocation loc) {
   1694     getLocalData()->AttrLoc = loc;
   1695   }
   1696 
   1697   /// The attribute's expression operand, if it has one.
   1698   ///    int * __attribute__((address_space(11)))
   1699   ///                                       ^~
   1700   Expr *getAttrExprOperand() const {
   1701     return getLocalData()->ExprOperand;
   1702   }
   1703   void setAttrExprOperand(Expr *e) {
   1704     getLocalData()->ExprOperand = e;
   1705   }
   1706 
   1707   /// The location of the parentheses around the operand, if there is
   1708   /// an operand.
   1709   ///    int * __attribute__((address_space(11)))
   1710   ///                                      ^  ^
   1711   SourceRange getAttrOperandParensRange() const {
   1712     return getLocalData()->OperandParens;
   1713   }
   1714   void setAttrOperandParensRange(SourceRange range) {
   1715     getLocalData()->OperandParens = range;
   1716   }
   1717 
   1718   SourceRange getLocalSourceRange() const {
   1719     SourceRange range(getAttrNameLoc());
   1720     range.setEnd(getAttrOperandParensRange().getEnd());
   1721     return range;
   1722   }
   1723 
   1724   ///  Returns the type before the address space attribute application
   1725   ///  area.
   1726   ///    int * __attribute__((address_space(11))) *
   1727   ///    ^   ^
   1728   QualType getInnerType() const {
   1729     return this->getTypePtr()->getPointeeType();
   1730   }
   1731 
   1732   TypeLoc getPointeeTypeLoc() const {
   1733     return this->getInnerTypeLoc();
   1734   }
   1735 
   1736   void initializeLocal(ASTContext &Context, SourceLocation loc) {
   1737     setAttrNameLoc(loc);
   1738     setAttrOperandParensRange(loc);
   1739     setAttrOperandParensRange(SourceRange(loc));
   1740     setAttrExprOperand(getTypePtr()->getAddrSpaceExpr());
   1741   }
   1742 };
   1743 
   1744 //===----------------------------------------------------------------------===//
   1745 //
   1746 //  All of these need proper implementations.
   1747 //
   1748 //===----------------------------------------------------------------------===//
   1749 
   1750 // FIXME: size expression and attribute locations (or keyword if we
   1751 // ever fully support altivec syntax).
   1752 struct VectorTypeLocInfo {
   1753   SourceLocation NameLoc;
   1754 };
   1755 
   1756 class VectorTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, VectorTypeLoc,
   1757                                              VectorType, VectorTypeLocInfo> {
   1758 public:
   1759   SourceLocation getNameLoc() const { return this->getLocalData()->NameLoc; }
   1760 
   1761   void setNameLoc(SourceLocation Loc) { this->getLocalData()->NameLoc = Loc; }
   1762 
   1763   SourceRange getLocalSourceRange() const {
   1764     return SourceRange(getNameLoc(), getNameLoc());
   1765   }
   1766 
   1767   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1768     setNameLoc(Loc);
   1769   }
   1770 
   1771   TypeLoc getElementLoc() const { return getInnerTypeLoc(); }
   1772 
   1773   QualType getInnerType() const { return this->getTypePtr()->getElementType(); }
   1774 };
   1775 
   1776 // FIXME: size expression and attribute locations (or keyword if we
   1777 // ever fully support altivec syntax).
   1778 class DependentVectorTypeLoc
   1779     : public ConcreteTypeLoc<UnqualTypeLoc, DependentVectorTypeLoc,
   1780                              DependentVectorType, VectorTypeLocInfo> {
   1781 public:
   1782   SourceLocation getNameLoc() const { return this->getLocalData()->NameLoc; }
   1783 
   1784   void setNameLoc(SourceLocation Loc) { this->getLocalData()->NameLoc = Loc; }
   1785 
   1786   SourceRange getLocalSourceRange() const {
   1787     return SourceRange(getNameLoc(), getNameLoc());
   1788   }
   1789 
   1790   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1791     setNameLoc(Loc);
   1792   }
   1793 
   1794   TypeLoc getElementLoc() const { return getInnerTypeLoc(); }
   1795 
   1796   QualType getInnerType() const { return this->getTypePtr()->getElementType(); }
   1797 };
   1798 
   1799 // FIXME: size expression and attribute locations.
   1800 class ExtVectorTypeLoc
   1801     : public InheritingConcreteTypeLoc<VectorTypeLoc, ExtVectorTypeLoc,
   1802                                        ExtVectorType> {};
   1803 
   1804 // FIXME: attribute locations.
   1805 // For some reason, this isn't a subtype of VectorType.
   1806 class DependentSizedExtVectorTypeLoc
   1807     : public ConcreteTypeLoc<UnqualTypeLoc, DependentSizedExtVectorTypeLoc,
   1808                              DependentSizedExtVectorType, VectorTypeLocInfo> {
   1809 public:
   1810   SourceLocation getNameLoc() const { return this->getLocalData()->NameLoc; }
   1811 
   1812   void setNameLoc(SourceLocation Loc) { this->getLocalData()->NameLoc = Loc; }
   1813 
   1814   SourceRange getLocalSourceRange() const {
   1815     return SourceRange(getNameLoc(), getNameLoc());
   1816   }
   1817 
   1818   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1819     setNameLoc(Loc);
   1820   }
   1821 
   1822   TypeLoc getElementLoc() const { return getInnerTypeLoc(); }
   1823 
   1824   QualType getInnerType() const { return this->getTypePtr()->getElementType(); }
   1825 };
   1826 
   1827 struct MatrixTypeLocInfo {
   1828   SourceLocation AttrLoc;
   1829   SourceRange OperandParens;
   1830   Expr *RowOperand;
   1831   Expr *ColumnOperand;
   1832 };
   1833 
   1834 class MatrixTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, MatrixTypeLoc,
   1835                                              MatrixType, MatrixTypeLocInfo> {
   1836 public:
   1837   /// The location of the attribute name, i.e.
   1838   ///    float __attribute__((matrix_type(4, 2)))
   1839   ///                         ^~~~~~~~~~~~~~~~~
   1840   SourceLocation getAttrNameLoc() const { return getLocalData()->AttrLoc; }
   1841   void setAttrNameLoc(SourceLocation loc) { getLocalData()->AttrLoc = loc; }
   1842 
   1843   /// The attribute's row operand, if it has one.
   1844   ///    float __attribute__((matrix_type(4, 2)))
   1845   ///                                     ^
   1846   Expr *getAttrRowOperand() const { return getLocalData()->RowOperand; }
   1847   void setAttrRowOperand(Expr *e) { getLocalData()->RowOperand = e; }
   1848 
   1849   /// The attribute's column operand, if it has one.
   1850   ///    float __attribute__((matrix_type(4, 2)))
   1851   ///                                        ^
   1852   Expr *getAttrColumnOperand() const { return getLocalData()->ColumnOperand; }
   1853   void setAttrColumnOperand(Expr *e) { getLocalData()->ColumnOperand = e; }
   1854 
   1855   /// The location of the parentheses around the operand, if there is
   1856   /// an operand.
   1857   ///    float __attribute__((matrix_type(4, 2)))
   1858   ///                                    ^    ^
   1859   SourceRange getAttrOperandParensRange() const {
   1860     return getLocalData()->OperandParens;
   1861   }
   1862   void setAttrOperandParensRange(SourceRange range) {
   1863     getLocalData()->OperandParens = range;
   1864   }
   1865 
   1866   SourceRange getLocalSourceRange() const {
   1867     SourceRange range(getAttrNameLoc());
   1868     range.setEnd(getAttrOperandParensRange().getEnd());
   1869     return range;
   1870   }
   1871 
   1872   void initializeLocal(ASTContext &Context, SourceLocation loc) {
   1873     setAttrNameLoc(loc);
   1874     setAttrOperandParensRange(loc);
   1875     setAttrRowOperand(nullptr);
   1876     setAttrColumnOperand(nullptr);
   1877   }
   1878 };
   1879 
   1880 class ConstantMatrixTypeLoc
   1881     : public InheritingConcreteTypeLoc<MatrixTypeLoc, ConstantMatrixTypeLoc,
   1882                                        ConstantMatrixType> {};
   1883 
   1884 class DependentSizedMatrixTypeLoc
   1885     : public InheritingConcreteTypeLoc<MatrixTypeLoc,
   1886                                        DependentSizedMatrixTypeLoc,
   1887                                        DependentSizedMatrixType> {};
   1888 
   1889 // FIXME: location of the '_Complex' keyword.
   1890 class ComplexTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
   1891                                                         ComplexTypeLoc,
   1892                                                         ComplexType> {
   1893 };
   1894 
   1895 struct TypeofLocInfo {
   1896   SourceLocation TypeofLoc;
   1897   SourceLocation LParenLoc;
   1898   SourceLocation RParenLoc;
   1899 };
   1900 
   1901 struct TypeOfExprTypeLocInfo : public TypeofLocInfo {
   1902 };
   1903 
   1904 struct TypeOfTypeLocInfo : public TypeofLocInfo {
   1905   TypeSourceInfo* UnderlyingTInfo;
   1906 };
   1907 
   1908 template <class Derived, class TypeClass, class LocalData = TypeofLocInfo>
   1909 class TypeofLikeTypeLoc
   1910   : public ConcreteTypeLoc<UnqualTypeLoc, Derived, TypeClass, LocalData> {
   1911 public:
   1912   SourceLocation getTypeofLoc() const {
   1913     return this->getLocalData()->TypeofLoc;
   1914   }
   1915 
   1916   void setTypeofLoc(SourceLocation Loc) {
   1917     this->getLocalData()->TypeofLoc = Loc;
   1918   }
   1919 
   1920   SourceLocation getLParenLoc() const {
   1921     return this->getLocalData()->LParenLoc;
   1922   }
   1923 
   1924   void setLParenLoc(SourceLocation Loc) {
   1925     this->getLocalData()->LParenLoc = Loc;
   1926   }
   1927 
   1928   SourceLocation getRParenLoc() const {
   1929     return this->getLocalData()->RParenLoc;
   1930   }
   1931 
   1932   void setRParenLoc(SourceLocation Loc) {
   1933     this->getLocalData()->RParenLoc = Loc;
   1934   }
   1935 
   1936   SourceRange getParensRange() const {
   1937     return SourceRange(getLParenLoc(), getRParenLoc());
   1938   }
   1939 
   1940   void setParensRange(SourceRange range) {
   1941       setLParenLoc(range.getBegin());
   1942       setRParenLoc(range.getEnd());
   1943   }
   1944 
   1945   SourceRange getLocalSourceRange() const {
   1946     return SourceRange(getTypeofLoc(), getRParenLoc());
   1947   }
   1948 
   1949   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   1950     setTypeofLoc(Loc);
   1951     setLParenLoc(Loc);
   1952     setRParenLoc(Loc);
   1953   }
   1954 };
   1955 
   1956 class TypeOfExprTypeLoc : public TypeofLikeTypeLoc<TypeOfExprTypeLoc,
   1957                                                    TypeOfExprType,
   1958                                                    TypeOfExprTypeLocInfo> {
   1959 public:
   1960   Expr* getUnderlyingExpr() const {
   1961     return getTypePtr()->getUnderlyingExpr();
   1962   }
   1963 
   1964   // Reimplemented to account for GNU/C++ extension
   1965   //     typeof unary-expression
   1966   // where there are no parentheses.
   1967   SourceRange getLocalSourceRange() const;
   1968 };
   1969 
   1970 class TypeOfTypeLoc
   1971   : public TypeofLikeTypeLoc<TypeOfTypeLoc, TypeOfType, TypeOfTypeLocInfo> {
   1972 public:
   1973   QualType getUnderlyingType() const {
   1974     return this->getTypePtr()->getUnderlyingType();
   1975   }
   1976 
   1977   TypeSourceInfo* getUnderlyingTInfo() const {
   1978     return this->getLocalData()->UnderlyingTInfo;
   1979   }
   1980 
   1981   void setUnderlyingTInfo(TypeSourceInfo* TI) const {
   1982     this->getLocalData()->UnderlyingTInfo = TI;
   1983   }
   1984 
   1985   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   1986 };
   1987 
   1988 // FIXME: location of the 'decltype' and parens.
   1989 class DecltypeTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
   1990                                                          DecltypeTypeLoc,
   1991                                                          DecltypeType> {
   1992 public:
   1993   Expr *getUnderlyingExpr() const { return getTypePtr()->getUnderlyingExpr(); }
   1994 };
   1995 
   1996 struct UnaryTransformTypeLocInfo {
   1997   // FIXME: While there's only one unary transform right now, future ones may
   1998   // need different representations
   1999   SourceLocation KWLoc, LParenLoc, RParenLoc;
   2000   TypeSourceInfo *UnderlyingTInfo;
   2001 };
   2002 
   2003 class UnaryTransformTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
   2004                                                     UnaryTransformTypeLoc,
   2005                                                     UnaryTransformType,
   2006                                                     UnaryTransformTypeLocInfo> {
   2007 public:
   2008   SourceLocation getKWLoc() const { return getLocalData()->KWLoc; }
   2009   void setKWLoc(SourceLocation Loc) { getLocalData()->KWLoc = Loc; }
   2010 
   2011   SourceLocation getLParenLoc() const { return getLocalData()->LParenLoc; }
   2012   void setLParenLoc(SourceLocation Loc) { getLocalData()->LParenLoc = Loc; }
   2013 
   2014   SourceLocation getRParenLoc() const { return getLocalData()->RParenLoc; }
   2015   void setRParenLoc(SourceLocation Loc) { getLocalData()->RParenLoc = Loc; }
   2016 
   2017   TypeSourceInfo* getUnderlyingTInfo() const {
   2018     return getLocalData()->UnderlyingTInfo;
   2019   }
   2020 
   2021   void setUnderlyingTInfo(TypeSourceInfo *TInfo) {
   2022     getLocalData()->UnderlyingTInfo = TInfo;
   2023   }
   2024 
   2025   SourceRange getLocalSourceRange() const {
   2026     return SourceRange(getKWLoc(), getRParenLoc());
   2027   }
   2028 
   2029   SourceRange getParensRange() const {
   2030     return SourceRange(getLParenLoc(), getRParenLoc());
   2031   }
   2032 
   2033   void setParensRange(SourceRange Range) {
   2034     setLParenLoc(Range.getBegin());
   2035     setRParenLoc(Range.getEnd());
   2036   }
   2037 
   2038   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   2039 };
   2040 
   2041 class DeducedTypeLoc
   2042     : public InheritingConcreteTypeLoc<TypeSpecTypeLoc, DeducedTypeLoc,
   2043                                        DeducedType> {};
   2044 
   2045 struct AutoTypeLocInfo : TypeSpecLocInfo {
   2046   NestedNameSpecifierLoc NestedNameSpec;
   2047   SourceLocation TemplateKWLoc;
   2048   SourceLocation ConceptNameLoc;
   2049   NamedDecl *FoundDecl;
   2050   SourceLocation LAngleLoc;
   2051   SourceLocation RAngleLoc;
   2052 };
   2053 
   2054 class AutoTypeLoc
   2055     : public ConcreteTypeLoc<DeducedTypeLoc,
   2056                              AutoTypeLoc,
   2057                              AutoType,
   2058                              AutoTypeLocInfo> {
   2059 public:
   2060   AutoTypeKeyword getAutoKeyword() const {
   2061     return getTypePtr()->getKeyword();
   2062   }
   2063 
   2064   bool isConstrained() const {
   2065     return getTypePtr()->isConstrained();
   2066   }
   2067 
   2068   const NestedNameSpecifierLoc &getNestedNameSpecifierLoc() const {
   2069     return getLocalData()->NestedNameSpec;
   2070   }
   2071 
   2072   void setNestedNameSpecifierLoc(NestedNameSpecifierLoc NNS) {
   2073     getLocalData()->NestedNameSpec = NNS;
   2074   }
   2075 
   2076   SourceLocation getTemplateKWLoc() const {
   2077     return getLocalData()->TemplateKWLoc;
   2078   }
   2079 
   2080   void setTemplateKWLoc(SourceLocation Loc) {
   2081     getLocalData()->TemplateKWLoc = Loc;
   2082   }
   2083 
   2084   SourceLocation getConceptNameLoc() const {
   2085     return getLocalData()->ConceptNameLoc;
   2086   }
   2087 
   2088   void setConceptNameLoc(SourceLocation Loc) {
   2089     getLocalData()->ConceptNameLoc = Loc;
   2090   }
   2091 
   2092   NamedDecl *getFoundDecl() const {
   2093     return getLocalData()->FoundDecl;
   2094   }
   2095 
   2096   void setFoundDecl(NamedDecl *D) {
   2097     getLocalData()->FoundDecl = D;
   2098   }
   2099 
   2100   ConceptDecl *getNamedConcept() const {
   2101     return getTypePtr()->getTypeConstraintConcept();
   2102   }
   2103 
   2104   DeclarationNameInfo getConceptNameInfo() const;
   2105 
   2106   bool hasExplicitTemplateArgs() const {
   2107     return getLocalData()->LAngleLoc.isValid();
   2108   }
   2109 
   2110   SourceLocation getLAngleLoc() const {
   2111     return this->getLocalData()->LAngleLoc;
   2112   }
   2113 
   2114   void setLAngleLoc(SourceLocation Loc) {
   2115     this->getLocalData()->LAngleLoc = Loc;
   2116   }
   2117 
   2118   SourceLocation getRAngleLoc() const {
   2119     return this->getLocalData()->RAngleLoc;
   2120   }
   2121 
   2122   void setRAngleLoc(SourceLocation Loc) {
   2123     this->getLocalData()->RAngleLoc = Loc;
   2124   }
   2125 
   2126   unsigned getNumArgs() const {
   2127     return getTypePtr()->getNumArgs();
   2128   }
   2129 
   2130   void setArgLocInfo(unsigned i, TemplateArgumentLocInfo AI) {
   2131     getArgInfos()[i] = AI;
   2132   }
   2133 
   2134   TemplateArgumentLocInfo getArgLocInfo(unsigned i) const {
   2135     return getArgInfos()[i];
   2136   }
   2137 
   2138   TemplateArgumentLoc getArgLoc(unsigned i) const {
   2139     return TemplateArgumentLoc(getTypePtr()->getTypeConstraintArguments()[i],
   2140                                getArgLocInfo(i));
   2141   }
   2142 
   2143   SourceRange getLocalSourceRange() const {
   2144     return{
   2145         isConstrained()
   2146           ? (getNestedNameSpecifierLoc()
   2147                ? getNestedNameSpecifierLoc().getBeginLoc()
   2148                : (getTemplateKWLoc().isValid()
   2149                   ? getTemplateKWLoc()
   2150                   : getConceptNameLoc()))
   2151           : getNameLoc(),
   2152         getNameLoc()
   2153     };
   2154   }
   2155 
   2156   void copy(AutoTypeLoc Loc) {
   2157     unsigned size = getFullDataSize();
   2158     assert(size == Loc.getFullDataSize());
   2159     memcpy(Data, Loc.Data, size);
   2160   }
   2161 
   2162   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   2163 
   2164   unsigned getExtraLocalDataSize() const {
   2165     return getNumArgs() * sizeof(TemplateArgumentLocInfo);
   2166   }
   2167 
   2168   unsigned getExtraLocalDataAlignment() const {
   2169     return alignof(TemplateArgumentLocInfo);
   2170   }
   2171 
   2172 private:
   2173   TemplateArgumentLocInfo *getArgInfos() const {
   2174     return static_cast<TemplateArgumentLocInfo*>(getExtraLocalData());
   2175   }
   2176 };
   2177 
   2178 class DeducedTemplateSpecializationTypeLoc
   2179     : public InheritingConcreteTypeLoc<DeducedTypeLoc,
   2180                                        DeducedTemplateSpecializationTypeLoc,
   2181                                        DeducedTemplateSpecializationType> {
   2182 public:
   2183   SourceLocation getTemplateNameLoc() const {
   2184     return getNameLoc();
   2185   }
   2186 
   2187   void setTemplateNameLoc(SourceLocation Loc) {
   2188     setNameLoc(Loc);
   2189   }
   2190 };
   2191 
   2192 struct ElaboratedLocInfo {
   2193   SourceLocation ElaboratedKWLoc;
   2194 
   2195   /// Data associated with the nested-name-specifier location.
   2196   void *QualifierData;
   2197 };
   2198 
   2199 class ElaboratedTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
   2200                                                  ElaboratedTypeLoc,
   2201                                                  ElaboratedType,
   2202                                                  ElaboratedLocInfo> {
   2203 public:
   2204   SourceLocation getElaboratedKeywordLoc() const {
   2205     return this->getLocalData()->ElaboratedKWLoc;
   2206   }
   2207 
   2208   void setElaboratedKeywordLoc(SourceLocation Loc) {
   2209     this->getLocalData()->ElaboratedKWLoc = Loc;
   2210   }
   2211 
   2212   NestedNameSpecifierLoc getQualifierLoc() const {
   2213     return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
   2214                                   getLocalData()->QualifierData);
   2215   }
   2216 
   2217   void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
   2218     assert(QualifierLoc.getNestedNameSpecifier()
   2219                                             == getTypePtr()->getQualifier() &&
   2220            "Inconsistent nested-name-specifier pointer");
   2221     getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
   2222   }
   2223 
   2224   SourceRange getLocalSourceRange() const {
   2225     if (getElaboratedKeywordLoc().isValid())
   2226       if (getQualifierLoc())
   2227         return SourceRange(getElaboratedKeywordLoc(),
   2228                            getQualifierLoc().getEndLoc());
   2229       else
   2230         return SourceRange(getElaboratedKeywordLoc());
   2231     else
   2232       return getQualifierLoc().getSourceRange();
   2233   }
   2234 
   2235   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   2236 
   2237   TypeLoc getNamedTypeLoc() const {
   2238     return getInnerTypeLoc();
   2239   }
   2240 
   2241   QualType getInnerType() const {
   2242     return getTypePtr()->getNamedType();
   2243   }
   2244 
   2245   void copy(ElaboratedTypeLoc Loc) {
   2246     unsigned size = getFullDataSize();
   2247     assert(size == Loc.getFullDataSize());
   2248     memcpy(Data, Loc.Data, size);
   2249   }
   2250 };
   2251 
   2252 // This is exactly the structure of an ElaboratedTypeLoc whose inner
   2253 // type is some sort of TypeDeclTypeLoc.
   2254 struct DependentNameLocInfo : ElaboratedLocInfo {
   2255   SourceLocation NameLoc;
   2256 };
   2257 
   2258 class DependentNameTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
   2259                                                     DependentNameTypeLoc,
   2260                                                     DependentNameType,
   2261                                                     DependentNameLocInfo> {
   2262 public:
   2263   SourceLocation getElaboratedKeywordLoc() const {
   2264     return this->getLocalData()->ElaboratedKWLoc;
   2265   }
   2266 
   2267   void setElaboratedKeywordLoc(SourceLocation Loc) {
   2268     this->getLocalData()->ElaboratedKWLoc = Loc;
   2269   }
   2270 
   2271   NestedNameSpecifierLoc getQualifierLoc() const {
   2272     return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
   2273                                   getLocalData()->QualifierData);
   2274   }
   2275 
   2276   void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
   2277     assert(QualifierLoc.getNestedNameSpecifier()
   2278                                             == getTypePtr()->getQualifier() &&
   2279            "Inconsistent nested-name-specifier pointer");
   2280     getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
   2281   }
   2282 
   2283   SourceLocation getNameLoc() const {
   2284     return this->getLocalData()->NameLoc;
   2285   }
   2286 
   2287   void setNameLoc(SourceLocation Loc) {
   2288     this->getLocalData()->NameLoc = Loc;
   2289   }
   2290 
   2291   SourceRange getLocalSourceRange() const {
   2292     if (getElaboratedKeywordLoc().isValid())
   2293       return SourceRange(getElaboratedKeywordLoc(), getNameLoc());
   2294     else
   2295       return SourceRange(getQualifierLoc().getBeginLoc(), getNameLoc());
   2296   }
   2297 
   2298   void copy(DependentNameTypeLoc Loc) {
   2299     unsigned size = getFullDataSize();
   2300     assert(size == Loc.getFullDataSize());
   2301     memcpy(Data, Loc.Data, size);
   2302   }
   2303 
   2304   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   2305 };
   2306 
   2307 struct DependentTemplateSpecializationLocInfo : DependentNameLocInfo {
   2308   SourceLocation TemplateKWLoc;
   2309   SourceLocation LAngleLoc;
   2310   SourceLocation RAngleLoc;
   2311   // followed by a TemplateArgumentLocInfo[]
   2312 };
   2313 
   2314 class DependentTemplateSpecializationTypeLoc :
   2315     public ConcreteTypeLoc<UnqualTypeLoc,
   2316                            DependentTemplateSpecializationTypeLoc,
   2317                            DependentTemplateSpecializationType,
   2318                            DependentTemplateSpecializationLocInfo> {
   2319 public:
   2320   SourceLocation getElaboratedKeywordLoc() const {
   2321     return this->getLocalData()->ElaboratedKWLoc;
   2322   }
   2323 
   2324   void setElaboratedKeywordLoc(SourceLocation Loc) {
   2325     this->getLocalData()->ElaboratedKWLoc = Loc;
   2326   }
   2327 
   2328   NestedNameSpecifierLoc getQualifierLoc() const {
   2329     if (!getLocalData()->QualifierData)
   2330       return NestedNameSpecifierLoc();
   2331 
   2332     return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
   2333                                   getLocalData()->QualifierData);
   2334   }
   2335 
   2336   void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
   2337     if (!QualifierLoc) {
   2338       // Even if we have a nested-name-specifier in the dependent
   2339       // template specialization type, we won't record the nested-name-specifier
   2340       // location information when this type-source location information is
   2341       // part of a nested-name-specifier.
   2342       getLocalData()->QualifierData = nullptr;
   2343       return;
   2344     }
   2345 
   2346     assert(QualifierLoc.getNestedNameSpecifier()
   2347                                         == getTypePtr()->getQualifier() &&
   2348            "Inconsistent nested-name-specifier pointer");
   2349     getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
   2350   }
   2351 
   2352   SourceLocation getTemplateKeywordLoc() const {
   2353     return getLocalData()->TemplateKWLoc;
   2354   }
   2355 
   2356   void setTemplateKeywordLoc(SourceLocation Loc) {
   2357     getLocalData()->TemplateKWLoc = Loc;
   2358   }
   2359 
   2360   SourceLocation getTemplateNameLoc() const {
   2361     return this->getLocalData()->NameLoc;
   2362   }
   2363 
   2364   void setTemplateNameLoc(SourceLocation Loc) {
   2365     this->getLocalData()->NameLoc = Loc;
   2366   }
   2367 
   2368   SourceLocation getLAngleLoc() const {
   2369     return this->getLocalData()->LAngleLoc;
   2370   }
   2371 
   2372   void setLAngleLoc(SourceLocation Loc) {
   2373     this->getLocalData()->LAngleLoc = Loc;
   2374   }
   2375 
   2376   SourceLocation getRAngleLoc() const {
   2377     return this->getLocalData()->RAngleLoc;
   2378   }
   2379 
   2380   void setRAngleLoc(SourceLocation Loc) {
   2381     this->getLocalData()->RAngleLoc = Loc;
   2382   }
   2383 
   2384   unsigned getNumArgs() const {
   2385     return getTypePtr()->getNumArgs();
   2386   }
   2387 
   2388   void setArgLocInfo(unsigned i, TemplateArgumentLocInfo AI) {
   2389     getArgInfos()[i] = AI;
   2390   }
   2391 
   2392   TemplateArgumentLocInfo getArgLocInfo(unsigned i) const {
   2393     return getArgInfos()[i];
   2394   }
   2395 
   2396   TemplateArgumentLoc getArgLoc(unsigned i) const {
   2397     return TemplateArgumentLoc(getTypePtr()->getArg(i), getArgLocInfo(i));
   2398   }
   2399 
   2400   SourceRange getLocalSourceRange() const {
   2401     if (getElaboratedKeywordLoc().isValid())
   2402       return SourceRange(getElaboratedKeywordLoc(), getRAngleLoc());
   2403     else if (getQualifierLoc())
   2404       return SourceRange(getQualifierLoc().getBeginLoc(), getRAngleLoc());
   2405     else if (getTemplateKeywordLoc().isValid())
   2406       return SourceRange(getTemplateKeywordLoc(), getRAngleLoc());
   2407     else
   2408       return SourceRange(getTemplateNameLoc(), getRAngleLoc());
   2409   }
   2410 
   2411   void copy(DependentTemplateSpecializationTypeLoc Loc) {
   2412     unsigned size = getFullDataSize();
   2413     assert(size == Loc.getFullDataSize());
   2414     memcpy(Data, Loc.Data, size);
   2415   }
   2416 
   2417   void initializeLocal(ASTContext &Context, SourceLocation Loc);
   2418 
   2419   unsigned getExtraLocalDataSize() const {
   2420     return getNumArgs() * sizeof(TemplateArgumentLocInfo);
   2421   }
   2422 
   2423   unsigned getExtraLocalDataAlignment() const {
   2424     return alignof(TemplateArgumentLocInfo);
   2425   }
   2426 
   2427 private:
   2428   TemplateArgumentLocInfo *getArgInfos() const {
   2429     return static_cast<TemplateArgumentLocInfo*>(getExtraLocalData());
   2430   }
   2431 };
   2432 
   2433 struct PackExpansionTypeLocInfo {
   2434   SourceLocation EllipsisLoc;
   2435 };
   2436 
   2437 class PackExpansionTypeLoc
   2438   : public ConcreteTypeLoc<UnqualTypeLoc, PackExpansionTypeLoc,
   2439                            PackExpansionType, PackExpansionTypeLocInfo> {
   2440 public:
   2441   SourceLocation getEllipsisLoc() const {
   2442     return this->getLocalData()->EllipsisLoc;
   2443   }
   2444 
   2445   void setEllipsisLoc(SourceLocation Loc) {
   2446     this->getLocalData()->EllipsisLoc = Loc;
   2447   }
   2448 
   2449   SourceRange getLocalSourceRange() const {
   2450     return SourceRange(getEllipsisLoc(), getEllipsisLoc());
   2451   }
   2452 
   2453   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   2454     setEllipsisLoc(Loc);
   2455   }
   2456 
   2457   TypeLoc getPatternLoc() const {
   2458     return getInnerTypeLoc();
   2459   }
   2460 
   2461   QualType getInnerType() const {
   2462     return this->getTypePtr()->getPattern();
   2463   }
   2464 };
   2465 
   2466 struct AtomicTypeLocInfo {
   2467   SourceLocation KWLoc, LParenLoc, RParenLoc;
   2468 };
   2469 
   2470 class AtomicTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, AtomicTypeLoc,
   2471                                              AtomicType, AtomicTypeLocInfo> {
   2472 public:
   2473   TypeLoc getValueLoc() const {
   2474     return this->getInnerTypeLoc();
   2475   }
   2476 
   2477   SourceRange getLocalSourceRange() const {
   2478     return SourceRange(getKWLoc(), getRParenLoc());
   2479   }
   2480 
   2481   SourceLocation getKWLoc() const {
   2482     return this->getLocalData()->KWLoc;
   2483   }
   2484 
   2485   void setKWLoc(SourceLocation Loc) {
   2486     this->getLocalData()->KWLoc = Loc;
   2487   }
   2488 
   2489   SourceLocation getLParenLoc() const {
   2490     return this->getLocalData()->LParenLoc;
   2491   }
   2492 
   2493   void setLParenLoc(SourceLocation Loc) {
   2494     this->getLocalData()->LParenLoc = Loc;
   2495   }
   2496 
   2497   SourceLocation getRParenLoc() const {
   2498     return this->getLocalData()->RParenLoc;
   2499   }
   2500 
   2501   void setRParenLoc(SourceLocation Loc) {
   2502     this->getLocalData()->RParenLoc = Loc;
   2503   }
   2504 
   2505   SourceRange getParensRange() const {
   2506     return SourceRange(getLParenLoc(), getRParenLoc());
   2507   }
   2508 
   2509   void setParensRange(SourceRange Range) {
   2510     setLParenLoc(Range.getBegin());
   2511     setRParenLoc(Range.getEnd());
   2512   }
   2513 
   2514   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   2515     setKWLoc(Loc);
   2516     setLParenLoc(Loc);
   2517     setRParenLoc(Loc);
   2518   }
   2519 
   2520   QualType getInnerType() const {
   2521     return this->getTypePtr()->getValueType();
   2522   }
   2523 };
   2524 
   2525 struct PipeTypeLocInfo {
   2526   SourceLocation KWLoc;
   2527 };
   2528 
   2529 class PipeTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, PipeTypeLoc, PipeType,
   2530                                            PipeTypeLocInfo> {
   2531 public:
   2532   TypeLoc getValueLoc() const { return this->getInnerTypeLoc(); }
   2533 
   2534   SourceRange getLocalSourceRange() const { return SourceRange(getKWLoc()); }
   2535 
   2536   SourceLocation getKWLoc() const { return this->getLocalData()->KWLoc; }
   2537   void setKWLoc(SourceLocation Loc) { this->getLocalData()->KWLoc = Loc; }
   2538 
   2539   void initializeLocal(ASTContext &Context, SourceLocation Loc) {
   2540     setKWLoc(Loc);
   2541   }
   2542 
   2543   QualType getInnerType() const { return this->getTypePtr()->getElementType(); }
   2544 };
   2545 
   2546 template <typename T>
   2547 inline T TypeLoc::getAsAdjusted() const {
   2548   TypeLoc Cur = *this;
   2549   while (!T::isKind(Cur)) {
   2550     if (auto PTL = Cur.getAs<ParenTypeLoc>())
   2551       Cur = PTL.getInnerLoc();
   2552     else if (auto ATL = Cur.getAs<AttributedTypeLoc>())
   2553       Cur = ATL.getModifiedLoc();
   2554     else if (auto ETL = Cur.getAs<ElaboratedTypeLoc>())
   2555       Cur = ETL.getNamedTypeLoc();
   2556     else if (auto ATL = Cur.getAs<AdjustedTypeLoc>())
   2557       Cur = ATL.getOriginalLoc();
   2558     else if (auto MQL = Cur.getAs<MacroQualifiedTypeLoc>())
   2559       Cur = MQL.getInnerLoc();
   2560     else
   2561       break;
   2562   }
   2563   return Cur.getAs<T>();
   2564 }
   2565 class ExtIntTypeLoc final
   2566     : public InheritingConcreteTypeLoc<TypeSpecTypeLoc, ExtIntTypeLoc,
   2567                                         ExtIntType> {};
   2568 class DependentExtIntTypeLoc final
   2569     : public InheritingConcreteTypeLoc<TypeSpecTypeLoc, DependentExtIntTypeLoc,
   2570                                         DependentExtIntType> {};
   2571 
   2572 } // namespace clang
   2573 
   2574 #endif // LLVM_CLANG_AST_TYPELOC_H
   2575