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