1 //===--- TypeLoc.h - Type Source Info Wrapper -------------------*- C++ -*-===//
3 // The LLVM Compiler Infrastructure
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
8 //===----------------------------------------------------------------------===//
10 // This file defines the TypeLoc interface and subclasses.
12 //===----------------------------------------------------------------------===//
14 #ifndef LLVM_CLANG_AST_TYPELOC_H
15 #define LLVM_CLANG_AST_TYPELOC_H
17 #include "clang/AST/Type.h"
18 #include "clang/AST/Decl.h"
19 #include "clang/AST/TemplateBase.h"
20 #include "clang/Basic/Specifiers.h"
21 #include "llvm/Support/Compiler.h"
29 // Predeclare all the type nodes.
30 #define ABSTRACT_TYPELOC(Class, Base)
31 #define TYPELOC(Class, Base) \
33 #include "clang/AST/TypeLocNodes.def"
35 /// \brief Base wrapper for a particular "section" of type source info.
37 /// A client should use the TypeLoc subclasses through cast/dyn_cast in order to
38 /// get at the actual information.
41 // The correctness of this relies on the property that, for Type *Ty,
42 // QualType(Ty, 0).getAsOpaquePtr() == (void*) Ty
47 /// The kinds of TypeLocs. Equivalent to the Type::TypeClass enum,
48 /// except it also defines a Qualified enum that corresponds to the
49 /// QualifiedLoc class.
51 #define ABSTRACT_TYPE(Class, Base)
52 #define TYPE(Class, Base) \
54 #include "clang/AST/TypeNodes.def"
58 TypeLoc() : Ty(0), Data(0) { }
59 TypeLoc(QualType ty, void *opaqueData)
60 : Ty(ty.getAsOpaquePtr()), Data(opaqueData) { }
61 TypeLoc(const Type *ty, void *opaqueData)
62 : Ty(ty), Data(opaqueData) { }
64 TypeLocClass getTypeLocClass() const {
65 if (getType().hasLocalQualifiers()) return Qualified;
66 return (TypeLocClass) getType()->getTypeClass();
69 bool isNull() const { return !Ty; }
70 operator bool() const { return Ty; }
72 /// \brief Returns the size of type source info data block for the given type.
73 static unsigned getFullDataSizeForType(QualType Ty);
75 /// \brief Get the type for which this source info wrapper provides
77 QualType getType() const {
78 return QualType::getFromOpaquePtr(Ty);
81 const Type *getTypePtr() const {
82 return QualType::getFromOpaquePtr(Ty).getTypePtr();
85 /// \brief Get the pointer where source information is stored.
86 void *getOpaqueData() const {
90 /// \brief Get the begin source location.
91 SourceLocation getBeginLoc() const;
93 /// \brief Get the end source location.
94 SourceLocation getEndLoc() const;
96 /// \brief Get the full source range.
97 SourceRange getSourceRange() const LLVM_READONLY {
98 return SourceRange(getBeginLoc(), getEndLoc());
100 SourceLocation getLocStart() const LLVM_READONLY { return getBeginLoc(); }
101 SourceLocation getLocEnd() const LLVM_READONLY { return getEndLoc(); }
103 /// \brief Get the local source range.
104 SourceRange getLocalSourceRange() const {
105 return getLocalSourceRangeImpl(*this);
108 /// \brief Returns the size of the type source info data block.
109 unsigned getFullDataSize() const {
110 return getFullDataSizeForType(getType());
113 /// \brief Get the next TypeLoc pointed by this TypeLoc, e.g for "int*" the
114 /// TypeLoc is a PointerLoc and next TypeLoc is for "int".
115 TypeLoc getNextTypeLoc() const {
116 return getNextTypeLocImpl(*this);
119 /// \brief Skips past any qualifiers, if this is qualified.
120 UnqualTypeLoc getUnqualifiedLoc() const; // implemented in this header
122 TypeLoc IgnoreParens() const {
123 if (isa<ParenTypeLoc>(this))
124 return IgnoreParensImpl(*this);
128 /// \brief Initializes this to state that every location in this
129 /// type is the given location.
131 /// This method exists to provide a simple transition for code that
132 /// relies on location-less types.
133 void initialize(ASTContext &Context, SourceLocation Loc) const {
134 initializeImpl(Context, *this, Loc);
137 /// \brief Initializes this by copying its information from another
138 /// TypeLoc of the same type.
139 void initializeFullCopy(TypeLoc Other) const {
140 assert(getType() == Other.getType());
141 size_t Size = getFullDataSize();
142 memcpy(getOpaqueData(), Other.getOpaqueData(), Size);
145 /// \brief Initializes this by copying its information from another
146 /// TypeLoc of the same type. The given size must be the full data
148 void initializeFullCopy(TypeLoc Other, unsigned Size) const {
149 assert(getType() == Other.getType());
150 assert(getFullDataSize() == Size);
151 memcpy(getOpaqueData(), Other.getOpaqueData(), Size);
154 friend bool operator==(const TypeLoc &LHS, const TypeLoc &RHS) {
155 return LHS.Ty == RHS.Ty && LHS.Data == RHS.Data;
158 friend bool operator!=(const TypeLoc &LHS, const TypeLoc &RHS) {
159 return !(LHS == RHS);
163 static void initializeImpl(ASTContext &Context, TypeLoc TL,
165 static TypeLoc getNextTypeLocImpl(TypeLoc TL);
166 static TypeLoc IgnoreParensImpl(TypeLoc TL);
167 static SourceRange getLocalSourceRangeImpl(TypeLoc TL);
170 /// \brief Return the TypeLoc for a type source info.
171 inline TypeLoc TypeSourceInfo::getTypeLoc() const {
172 return TypeLoc(Ty, const_cast<void*>(static_cast<const void*>(this + 1)));
175 /// \brief Wrapper of type source information for a type with
176 /// no direct qualifiers.
177 class UnqualTypeLoc : public TypeLoc {
180 UnqualTypeLoc(const Type *Ty, void *Data) : TypeLoc(Ty, Data) {}
182 const Type *getTypePtr() const {
183 return reinterpret_cast<const Type*>(Ty);
186 TypeLocClass getTypeLocClass() const {
187 return (TypeLocClass) getTypePtr()->getTypeClass();
190 static bool classof(const TypeLoc *TL) {
191 return !TL->getType().hasLocalQualifiers();
195 /// \brief Wrapper of type source information for a type with
196 /// non-trivial direct qualifiers.
198 /// Currently, we intentionally do not provide source location for
200 class QualifiedTypeLoc : public TypeLoc {
202 SourceRange getLocalSourceRange() const {
203 return SourceRange();
206 UnqualTypeLoc getUnqualifiedLoc() const {
207 return UnqualTypeLoc(getTypePtr(), Data);
210 /// Initializes the local data of this type source info block to
211 /// provide no information.
212 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
216 TypeLoc getNextTypeLoc() const {
217 return getUnqualifiedLoc();
220 /// \brief Returns the size of the type source info data block that is
221 /// specific to this type.
222 unsigned getLocalDataSize() const {
223 // In fact, we don't currently preserve any location information
228 /// \brief Returns the size of the type source info data block.
229 unsigned getFullDataSize() const {
230 return getLocalDataSize() +
231 getFullDataSizeForType(getType().getLocalUnqualifiedType());
234 static bool classof(const TypeLoc *TL) {
235 return TL->getType().hasLocalQualifiers();
239 inline UnqualTypeLoc TypeLoc::getUnqualifiedLoc() const {
240 if (isa<QualifiedTypeLoc>(this))
241 return cast<QualifiedTypeLoc>(this)->getUnqualifiedLoc();
242 return cast<UnqualTypeLoc>(*this);
245 /// A metaprogramming base class for TypeLoc classes which correspond
246 /// to a particular Type subclass. It is accepted for a single
247 /// TypeLoc class to correspond to multiple Type classes.
249 /// \tparam Base a class from which to derive
250 /// \tparam Derived the class deriving from this one
251 /// \tparam TypeClass the concrete Type subclass associated with this
253 /// \tparam LocalData the structure type of local location data for
256 /// sizeof(LocalData) needs to be a multiple of sizeof(void*) or
257 /// else the world will end.
259 /// TypeLocs with non-constant amounts of local data should override
260 /// getExtraLocalDataSize(); getExtraLocalData() will then point to
261 /// this extra memory.
263 /// TypeLocs with an inner type should define
264 /// QualType getInnerType() const
265 /// and getInnerTypeLoc() will then point to this inner type's
268 /// A word about hierarchies: this template is not designed to be
269 /// derived from multiple times in a hierarchy. It is also not
270 /// designed to be used for classes where subtypes might provide
271 /// different amounts of source information. It should be subclassed
272 /// only at the deepest portion of the hierarchy where all children
273 /// have identical source information; if that's an abstract type,
274 /// then further descendents should inherit from
275 /// InheritingConcreteTypeLoc instead.
276 template <class Base, class Derived, class TypeClass, class LocalData>
277 class ConcreteTypeLoc : public Base {
279 const Derived *asDerived() const {
280 return static_cast<const Derived*>(this);
284 unsigned getLocalDataSize() const {
285 return sizeof(LocalData) + asDerived()->getExtraLocalDataSize();
287 // Give a default implementation that's useful for leaf types.
288 unsigned getFullDataSize() const {
289 return asDerived()->getLocalDataSize() + getInnerTypeSize();
292 static bool classofType(const Type *Ty) {
293 return TypeClass::classof(Ty);
296 static bool classof(const TypeLoc *TL) {
297 return Derived::classofType(TL->getTypePtr());
299 static bool classof(const UnqualTypeLoc *TL) {
300 return Derived::classofType(TL->getTypePtr());
303 TypeLoc getNextTypeLoc() const {
304 return getNextTypeLoc(asDerived()->getInnerType());
307 const TypeClass *getTypePtr() const {
308 return cast<TypeClass>(Base::getTypePtr());
312 unsigned getExtraLocalDataSize() const {
316 LocalData *getLocalData() const {
317 return static_cast<LocalData*>(Base::Data);
320 /// Gets a pointer past the Info structure; useful for classes with
321 /// local data that can't be captured in the Info (e.g. because it's
322 /// of variable size).
323 void *getExtraLocalData() const {
324 return getLocalData() + 1;
327 void *getNonLocalData() const {
328 return static_cast<char*>(Base::Data) + asDerived()->getLocalDataSize();
331 struct HasNoInnerType {};
332 HasNoInnerType getInnerType() const { return HasNoInnerType(); }
334 TypeLoc getInnerTypeLoc() const {
335 return TypeLoc(asDerived()->getInnerType(), getNonLocalData());
339 unsigned getInnerTypeSize() const {
340 return getInnerTypeSize(asDerived()->getInnerType());
343 unsigned getInnerTypeSize(HasNoInnerType _) const {
347 unsigned getInnerTypeSize(QualType _) const {
348 return getInnerTypeLoc().getFullDataSize();
351 TypeLoc getNextTypeLoc(HasNoInnerType _) const {
355 TypeLoc getNextTypeLoc(QualType T) const {
356 return TypeLoc(T, getNonLocalData());
360 /// A metaprogramming class designed for concrete subtypes of abstract
361 /// types where all subtypes share equivalently-structured source
362 /// information. See the note on ConcreteTypeLoc.
363 template <class Base, class Derived, class TypeClass>
364 class InheritingConcreteTypeLoc : public Base {
366 static bool classofType(const Type *Ty) {
367 return TypeClass::classof(Ty);
370 static bool classof(const TypeLoc *TL) {
371 return Derived::classofType(TL->getTypePtr());
373 static bool classof(const UnqualTypeLoc *TL) {
374 return Derived::classofType(TL->getTypePtr());
377 const TypeClass *getTypePtr() const {
378 return cast<TypeClass>(Base::getTypePtr());
383 struct TypeSpecLocInfo {
384 SourceLocation NameLoc;
387 /// \brief A reasonable base class for TypeLocs that correspond to
388 /// types that are written as a type-specifier.
389 class TypeSpecTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
394 enum { LocalDataSize = sizeof(TypeSpecLocInfo) };
396 SourceLocation getNameLoc() const {
397 return this->getLocalData()->NameLoc;
399 void setNameLoc(SourceLocation Loc) {
400 this->getLocalData()->NameLoc = Loc;
402 SourceRange getLocalSourceRange() const {
403 return SourceRange(getNameLoc(), getNameLoc());
405 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
409 static bool classof(const TypeLoc *TL);
413 struct BuiltinLocInfo {
414 SourceLocation BuiltinLoc;
417 /// \brief Wrapper for source info for builtin types.
418 class BuiltinTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
423 enum { LocalDataSize = sizeof(BuiltinLocInfo) };
425 SourceLocation getBuiltinLoc() const {
426 return getLocalData()->BuiltinLoc;
428 void setBuiltinLoc(SourceLocation Loc) {
429 getLocalData()->BuiltinLoc = Loc;
432 SourceLocation getNameLoc() const { return getBuiltinLoc(); }
434 WrittenBuiltinSpecs& getWrittenBuiltinSpecs() {
435 return *(static_cast<WrittenBuiltinSpecs*>(getExtraLocalData()));
437 const WrittenBuiltinSpecs& getWrittenBuiltinSpecs() const {
438 return *(static_cast<WrittenBuiltinSpecs*>(getExtraLocalData()));
441 bool needsExtraLocalData() const {
442 BuiltinType::Kind bk = getTypePtr()->getKind();
443 return (bk >= BuiltinType::UShort && bk <= BuiltinType::UInt128)
444 || (bk >= BuiltinType::Short && bk <= BuiltinType::LongDouble)
445 || bk == BuiltinType::UChar
446 || bk == BuiltinType::SChar;
449 unsigned getExtraLocalDataSize() const {
450 return needsExtraLocalData() ? sizeof(WrittenBuiltinSpecs) : 0;
453 SourceRange getLocalSourceRange() const {
454 return SourceRange(getBuiltinLoc(), getBuiltinLoc());
457 TypeSpecifierSign getWrittenSignSpec() const {
458 if (needsExtraLocalData())
459 return static_cast<TypeSpecifierSign>(getWrittenBuiltinSpecs().Sign);
461 return TSS_unspecified;
463 bool hasWrittenSignSpec() const {
464 return getWrittenSignSpec() != TSS_unspecified;
466 void setWrittenSignSpec(TypeSpecifierSign written) {
467 if (needsExtraLocalData())
468 getWrittenBuiltinSpecs().Sign = written;
471 TypeSpecifierWidth getWrittenWidthSpec() const {
472 if (needsExtraLocalData())
473 return static_cast<TypeSpecifierWidth>(getWrittenBuiltinSpecs().Width);
475 return TSW_unspecified;
477 bool hasWrittenWidthSpec() const {
478 return getWrittenWidthSpec() != TSW_unspecified;
480 void setWrittenWidthSpec(TypeSpecifierWidth written) {
481 if (needsExtraLocalData())
482 getWrittenBuiltinSpecs().Width = written;
485 TypeSpecifierType getWrittenTypeSpec() const;
486 bool hasWrittenTypeSpec() const {
487 return getWrittenTypeSpec() != TST_unspecified;
489 void setWrittenTypeSpec(TypeSpecifierType written) {
490 if (needsExtraLocalData())
491 getWrittenBuiltinSpecs().Type = written;
494 bool hasModeAttr() const {
495 if (needsExtraLocalData())
496 return getWrittenBuiltinSpecs().ModeAttr;
500 void setModeAttr(bool written) {
501 if (needsExtraLocalData())
502 getWrittenBuiltinSpecs().ModeAttr = written;
505 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
507 if (needsExtraLocalData()) {
508 WrittenBuiltinSpecs &wbs = getWrittenBuiltinSpecs();
509 wbs.Sign = TSS_unspecified;
510 wbs.Width = TSW_unspecified;
511 wbs.Type = TST_unspecified;
512 wbs.ModeAttr = false;
518 /// \brief Wrapper for source info for typedefs.
519 class TypedefTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
523 TypedefNameDecl *getTypedefNameDecl() const {
524 return getTypePtr()->getDecl();
528 /// \brief Wrapper for source info for injected class names of class
530 class InjectedClassNameTypeLoc :
531 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
532 InjectedClassNameTypeLoc,
533 InjectedClassNameType> {
535 CXXRecordDecl *getDecl() const {
536 return getTypePtr()->getDecl();
540 /// \brief Wrapper for source info for unresolved typename using decls.
541 class UnresolvedUsingTypeLoc :
542 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
543 UnresolvedUsingTypeLoc,
544 UnresolvedUsingType> {
546 UnresolvedUsingTypenameDecl *getDecl() const {
547 return getTypePtr()->getDecl();
551 /// \brief Wrapper for source info for tag types. Note that this only
552 /// records source info for the name itself; a type written 'struct foo'
553 /// should be represented as an ElaboratedTypeLoc. We currently
554 /// only do that when C++ is enabled because of the expense of
555 /// creating an ElaboratedType node for so many type references in C.
556 class TagTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
560 TagDecl *getDecl() const { return getTypePtr()->getDecl(); }
562 /// \brief True if the tag was defined in this type specifier.
563 bool isDefinition() const {
564 TagDecl *D = getDecl();
565 return D->isCompleteDefinition() &&
566 (D->getIdentifier() == 0 || D->getLocation() == getNameLoc());
570 /// \brief Wrapper for source info for record types.
571 class RecordTypeLoc : public InheritingConcreteTypeLoc<TagTypeLoc,
575 RecordDecl *getDecl() const { return getTypePtr()->getDecl(); }
578 /// \brief Wrapper for source info for enum types.
579 class EnumTypeLoc : public InheritingConcreteTypeLoc<TagTypeLoc,
583 EnumDecl *getDecl() const { return getTypePtr()->getDecl(); }
586 /// \brief Wrapper for template type parameters.
587 class TemplateTypeParmTypeLoc :
588 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
589 TemplateTypeParmTypeLoc,
590 TemplateTypeParmType> {
592 TemplateTypeParmDecl *getDecl() const { return getTypePtr()->getDecl(); }
595 /// \brief Wrapper for substituted template type parameters.
596 class SubstTemplateTypeParmTypeLoc :
597 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
598 SubstTemplateTypeParmTypeLoc,
599 SubstTemplateTypeParmType> {
602 /// \brief Wrapper for substituted template type parameters.
603 class SubstTemplateTypeParmPackTypeLoc :
604 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
605 SubstTemplateTypeParmPackTypeLoc,
606 SubstTemplateTypeParmPackType> {
609 struct AttributedLocInfo {
613 /// A raw SourceLocation.
614 unsigned EnumOperandLoc;
617 SourceRange OperandParens;
619 SourceLocation AttrLoc;
622 /// \brief Type source information for an attributed type.
623 class AttributedTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
628 AttributedType::Kind getAttrKind() const {
629 return getTypePtr()->getAttrKind();
632 bool hasAttrExprOperand() const {
633 return (getAttrKind() >= AttributedType::FirstExprOperandKind &&
634 getAttrKind() <= AttributedType::LastExprOperandKind);
637 bool hasAttrEnumOperand() const {
638 return (getAttrKind() >= AttributedType::FirstEnumOperandKind &&
639 getAttrKind() <= AttributedType::LastEnumOperandKind);
642 bool hasAttrOperand() const {
643 return hasAttrExprOperand() || hasAttrEnumOperand();
646 /// The modified type, which is generally canonically different from
647 /// the attribute type.
648 /// int main(int, char**) __attribute__((noreturn))
649 /// ~~~ ~~~~~~~~~~~~~
650 TypeLoc getModifiedLoc() const {
651 return getInnerTypeLoc();
654 /// The location of the attribute name, i.e.
655 /// __attribute__((regparm(1000)))
657 SourceLocation getAttrNameLoc() const {
658 return getLocalData()->AttrLoc;
660 void setAttrNameLoc(SourceLocation loc) {
661 getLocalData()->AttrLoc = loc;
664 /// The attribute's expression operand, if it has one.
665 /// void *cur_thread __attribute__((address_space(21)))
667 Expr *getAttrExprOperand() const {
668 assert(hasAttrExprOperand());
669 return getLocalData()->ExprOperand;
671 void setAttrExprOperand(Expr *e) {
672 assert(hasAttrExprOperand());
673 getLocalData()->ExprOperand = e;
676 /// The location of the attribute's enumerated operand, if it has one.
677 /// void * __attribute__((objc_gc(weak)))
679 SourceLocation getAttrEnumOperandLoc() const {
680 assert(hasAttrEnumOperand());
681 return SourceLocation::getFromRawEncoding(getLocalData()->EnumOperandLoc);
683 void setAttrEnumOperandLoc(SourceLocation loc) {
684 assert(hasAttrEnumOperand());
685 getLocalData()->EnumOperandLoc = loc.getRawEncoding();
688 /// The location of the parentheses around the operand, if there is
690 /// void * __attribute__((objc_gc(weak)))
692 SourceRange getAttrOperandParensRange() const {
693 assert(hasAttrOperand());
694 return getLocalData()->OperandParens;
696 void setAttrOperandParensRange(SourceRange range) {
697 assert(hasAttrOperand());
698 getLocalData()->OperandParens = range;
701 SourceRange getLocalSourceRange() const {
702 // Note that this does *not* include the range of the attribute
704 // __attribute__((foo(bar)))
705 // ^~~~~~~~~~~~~~~ ~~
709 // That enclosure doesn't necessarily belong to a single attribute
711 SourceRange range(getAttrNameLoc());
712 if (hasAttrOperand())
713 range.setEnd(getAttrOperandParensRange().getEnd());
717 void initializeLocal(ASTContext &Context, SourceLocation loc) {
719 if (hasAttrExprOperand()) {
720 setAttrOperandParensRange(SourceRange(loc));
721 setAttrExprOperand(0);
722 } else if (hasAttrEnumOperand()) {
723 setAttrOperandParensRange(SourceRange(loc));
724 setAttrEnumOperandLoc(loc);
728 QualType getInnerType() const {
729 return getTypePtr()->getModifiedType();
734 struct ObjCProtocolListLocInfo {
735 SourceLocation LAngleLoc;
736 SourceLocation RAngleLoc;
737 bool HasBaseTypeAsWritten;
740 // A helper class for defining ObjC TypeLocs that can qualified with
743 // TypeClass basically has to be either ObjCInterfaceType or
744 // ObjCObjectPointerType.
745 class ObjCObjectTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
748 ObjCProtocolListLocInfo> {
749 // SourceLocations are stored after Info, one for each Protocol.
750 SourceLocation *getProtocolLocArray() const {
751 return (SourceLocation*) this->getExtraLocalData();
755 SourceLocation getLAngleLoc() const {
756 return this->getLocalData()->LAngleLoc;
758 void setLAngleLoc(SourceLocation Loc) {
759 this->getLocalData()->LAngleLoc = Loc;
762 SourceLocation getRAngleLoc() const {
763 return this->getLocalData()->RAngleLoc;
765 void setRAngleLoc(SourceLocation Loc) {
766 this->getLocalData()->RAngleLoc = Loc;
769 unsigned getNumProtocols() const {
770 return this->getTypePtr()->getNumProtocols();
773 SourceLocation getProtocolLoc(unsigned i) const {
774 assert(i < getNumProtocols() && "Index is out of bounds!");
775 return getProtocolLocArray()[i];
777 void setProtocolLoc(unsigned i, SourceLocation Loc) {
778 assert(i < getNumProtocols() && "Index is out of bounds!");
779 getProtocolLocArray()[i] = Loc;
782 ObjCProtocolDecl *getProtocol(unsigned i) const {
783 assert(i < getNumProtocols() && "Index is out of bounds!");
784 return *(this->getTypePtr()->qual_begin() + i);
787 bool hasBaseTypeAsWritten() const {
788 return getLocalData()->HasBaseTypeAsWritten;
791 void setHasBaseTypeAsWritten(bool HasBaseType) {
792 getLocalData()->HasBaseTypeAsWritten = HasBaseType;
795 TypeLoc getBaseLoc() const {
796 return getInnerTypeLoc();
799 SourceRange getLocalSourceRange() const {
800 return SourceRange(getLAngleLoc(), getRAngleLoc());
803 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
804 setHasBaseTypeAsWritten(true);
807 for (unsigned i = 0, e = getNumProtocols(); i != e; ++i)
808 setProtocolLoc(i, Loc);
811 unsigned getExtraLocalDataSize() const {
812 return this->getNumProtocols() * sizeof(SourceLocation);
815 QualType getInnerType() const {
816 return getTypePtr()->getBaseType();
821 struct ObjCInterfaceLocInfo {
822 SourceLocation NameLoc;
823 SourceLocation NameEndLoc;
826 /// \brief Wrapper for source info for ObjC interfaces.
827 class ObjCInterfaceTypeLoc : public ConcreteTypeLoc<ObjCObjectTypeLoc,
828 ObjCInterfaceTypeLoc,
830 ObjCInterfaceLocInfo> {
832 ObjCInterfaceDecl *getIFaceDecl() const {
833 return getTypePtr()->getDecl();
836 SourceLocation getNameLoc() const {
837 return getLocalData()->NameLoc;
840 void setNameLoc(SourceLocation Loc) {
841 getLocalData()->NameLoc = Loc;
844 SourceRange getLocalSourceRange() const {
845 return SourceRange(getNameLoc(), getNameEndLoc());
848 SourceLocation getNameEndLoc() const {
849 return getLocalData()->NameEndLoc;
852 void setNameEndLoc(SourceLocation Loc) {
853 getLocalData()->NameEndLoc = Loc;
856 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
862 struct ParenLocInfo {
863 SourceLocation LParenLoc;
864 SourceLocation RParenLoc;
868 : public ConcreteTypeLoc<UnqualTypeLoc, ParenTypeLoc, ParenType,
871 SourceLocation getLParenLoc() const {
872 return this->getLocalData()->LParenLoc;
874 SourceLocation getRParenLoc() const {
875 return this->getLocalData()->RParenLoc;
877 void setLParenLoc(SourceLocation Loc) {
878 this->getLocalData()->LParenLoc = Loc;
880 void setRParenLoc(SourceLocation Loc) {
881 this->getLocalData()->RParenLoc = Loc;
884 SourceRange getLocalSourceRange() const {
885 return SourceRange(getLParenLoc(), getRParenLoc());
888 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
893 TypeLoc getInnerLoc() const {
894 return getInnerTypeLoc();
897 QualType getInnerType() const {
898 return this->getTypePtr()->getInnerType();
903 struct PointerLikeLocInfo {
904 SourceLocation StarLoc;
908 template <class Derived, class TypeClass, class LocalData = PointerLikeLocInfo>
909 class PointerLikeTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, Derived,
910 TypeClass, LocalData> {
912 SourceLocation getSigilLoc() const {
913 return this->getLocalData()->StarLoc;
915 void setSigilLoc(SourceLocation Loc) {
916 this->getLocalData()->StarLoc = Loc;
919 TypeLoc getPointeeLoc() const {
920 return this->getInnerTypeLoc();
923 SourceRange getLocalSourceRange() const {
924 return SourceRange(getSigilLoc(), getSigilLoc());
927 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
931 QualType getInnerType() const {
932 return this->getTypePtr()->getPointeeType();
937 /// \brief Wrapper for source info for pointers.
938 class PointerTypeLoc : public PointerLikeTypeLoc<PointerTypeLoc,
941 SourceLocation getStarLoc() const {
942 return getSigilLoc();
944 void setStarLoc(SourceLocation Loc) {
950 /// \brief Wrapper for source info for block pointers.
951 class BlockPointerTypeLoc : public PointerLikeTypeLoc<BlockPointerTypeLoc,
954 SourceLocation getCaretLoc() const {
955 return getSigilLoc();
957 void setCaretLoc(SourceLocation Loc) {
962 struct MemberPointerLocInfo : public PointerLikeLocInfo {
963 TypeSourceInfo *ClassTInfo;
966 /// \brief Wrapper for source info for member pointers.
967 class MemberPointerTypeLoc : public PointerLikeTypeLoc<MemberPointerTypeLoc,
969 MemberPointerLocInfo> {
971 SourceLocation getStarLoc() const {
972 return getSigilLoc();
974 void setStarLoc(SourceLocation Loc) {
978 const Type *getClass() const {
979 return getTypePtr()->getClass();
981 TypeSourceInfo *getClassTInfo() const {
982 return getLocalData()->ClassTInfo;
984 void setClassTInfo(TypeSourceInfo* TI) {
985 getLocalData()->ClassTInfo = TI;
988 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
993 SourceRange getLocalSourceRange() const {
994 if (TypeSourceInfo *TI = getClassTInfo())
995 return SourceRange(TI->getTypeLoc().getBeginLoc(), getStarLoc());
997 return SourceRange(getStarLoc());
1001 /// Wraps an ObjCPointerType with source location information.
1002 class ObjCObjectPointerTypeLoc :
1003 public PointerLikeTypeLoc<ObjCObjectPointerTypeLoc,
1004 ObjCObjectPointerType> {
1006 SourceLocation getStarLoc() const {
1007 return getSigilLoc();
1010 void setStarLoc(SourceLocation Loc) {
1016 class ReferenceTypeLoc : public PointerLikeTypeLoc<ReferenceTypeLoc,
1019 QualType getInnerType() const {
1020 return getTypePtr()->getPointeeTypeAsWritten();
1024 class LValueReferenceTypeLoc :
1025 public InheritingConcreteTypeLoc<ReferenceTypeLoc,
1026 LValueReferenceTypeLoc,
1027 LValueReferenceType> {
1029 SourceLocation getAmpLoc() const {
1030 return getSigilLoc();
1032 void setAmpLoc(SourceLocation Loc) {
1037 class RValueReferenceTypeLoc :
1038 public InheritingConcreteTypeLoc<ReferenceTypeLoc,
1039 RValueReferenceTypeLoc,
1040 RValueReferenceType> {
1042 SourceLocation getAmpAmpLoc() const {
1043 return getSigilLoc();
1045 void setAmpAmpLoc(SourceLocation Loc) {
1051 struct FunctionLocInfo {
1052 SourceLocation LocalRangeBegin;
1053 SourceLocation LParenLoc;
1054 SourceLocation RParenLoc;
1055 SourceLocation LocalRangeEnd;
1058 /// \brief Wrapper for source info for functions.
1059 class FunctionTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
1064 SourceLocation getLocalRangeBegin() const {
1065 return getLocalData()->LocalRangeBegin;
1067 void setLocalRangeBegin(SourceLocation L) {
1068 getLocalData()->LocalRangeBegin = L;
1071 SourceLocation getLocalRangeEnd() const {
1072 return getLocalData()->LocalRangeEnd;
1074 void setLocalRangeEnd(SourceLocation L) {
1075 getLocalData()->LocalRangeEnd = L;
1078 SourceLocation getLParenLoc() const {
1079 return this->getLocalData()->LParenLoc;
1081 void setLParenLoc(SourceLocation Loc) {
1082 this->getLocalData()->LParenLoc = Loc;
1085 SourceLocation getRParenLoc() const {
1086 return this->getLocalData()->RParenLoc;
1088 void setRParenLoc(SourceLocation Loc) {
1089 this->getLocalData()->RParenLoc = Loc;
1092 SourceRange getParensRange() const {
1093 return SourceRange(getLParenLoc(), getRParenLoc());
1096 ArrayRef<ParmVarDecl *> getParams() const {
1097 return ArrayRef<ParmVarDecl *>(getParmArray(), getNumArgs());
1100 // ParmVarDecls* are stored after Info, one for each argument.
1101 ParmVarDecl **getParmArray() const {
1102 return (ParmVarDecl**) getExtraLocalData();
1105 unsigned getNumArgs() const {
1106 if (isa<FunctionNoProtoType>(getTypePtr()))
1108 return cast<FunctionProtoType>(getTypePtr())->getNumArgs();
1110 ParmVarDecl *getArg(unsigned i) const { return getParmArray()[i]; }
1111 void setArg(unsigned i, ParmVarDecl *VD) { getParmArray()[i] = VD; }
1113 TypeLoc getResultLoc() const {
1114 return getInnerTypeLoc();
1117 SourceRange getLocalSourceRange() const {
1118 return SourceRange(getLocalRangeBegin(), getLocalRangeEnd());
1121 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1122 setLocalRangeBegin(Loc);
1125 setLocalRangeEnd(Loc);
1126 for (unsigned i = 0, e = getNumArgs(); i != e; ++i)
1130 /// \brief Returns the size of the type source info data block that is
1131 /// specific to this type.
1132 unsigned getExtraLocalDataSize() const {
1133 return getNumArgs() * sizeof(ParmVarDecl*);
1136 QualType getInnerType() const { return getTypePtr()->getResultType(); }
1139 class FunctionProtoTypeLoc :
1140 public InheritingConcreteTypeLoc<FunctionTypeLoc,
1141 FunctionProtoTypeLoc,
1142 FunctionProtoType> {
1145 class FunctionNoProtoTypeLoc :
1146 public InheritingConcreteTypeLoc<FunctionTypeLoc,
1147 FunctionNoProtoTypeLoc,
1148 FunctionNoProtoType> {
1152 struct ArrayLocInfo {
1153 SourceLocation LBracketLoc, RBracketLoc;
1157 /// \brief Wrapper for source info for arrays.
1158 class ArrayTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
1163 SourceLocation getLBracketLoc() const {
1164 return getLocalData()->LBracketLoc;
1166 void setLBracketLoc(SourceLocation Loc) {
1167 getLocalData()->LBracketLoc = Loc;
1170 SourceLocation getRBracketLoc() const {
1171 return getLocalData()->RBracketLoc;
1173 void setRBracketLoc(SourceLocation Loc) {
1174 getLocalData()->RBracketLoc = Loc;
1177 SourceRange getBracketsRange() const {
1178 return SourceRange(getLBracketLoc(), getRBracketLoc());
1181 Expr *getSizeExpr() const {
1182 return getLocalData()->Size;
1184 void setSizeExpr(Expr *Size) {
1185 getLocalData()->Size = Size;
1188 TypeLoc getElementLoc() const {
1189 return getInnerTypeLoc();
1192 SourceRange getLocalSourceRange() const {
1193 return SourceRange(getLBracketLoc(), getRBracketLoc());
1196 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1197 setLBracketLoc(Loc);
1198 setRBracketLoc(Loc);
1202 QualType getInnerType() const { return getTypePtr()->getElementType(); }
1205 class ConstantArrayTypeLoc :
1206 public InheritingConcreteTypeLoc<ArrayTypeLoc,
1207 ConstantArrayTypeLoc,
1208 ConstantArrayType> {
1211 class IncompleteArrayTypeLoc :
1212 public InheritingConcreteTypeLoc<ArrayTypeLoc,
1213 IncompleteArrayTypeLoc,
1214 IncompleteArrayType> {
1217 class DependentSizedArrayTypeLoc :
1218 public InheritingConcreteTypeLoc<ArrayTypeLoc,
1219 DependentSizedArrayTypeLoc,
1220 DependentSizedArrayType> {
1224 class VariableArrayTypeLoc :
1225 public InheritingConcreteTypeLoc<ArrayTypeLoc,
1226 VariableArrayTypeLoc,
1227 VariableArrayType> {
1231 // Location information for a TemplateName. Rudimentary for now.
1232 struct TemplateNameLocInfo {
1233 SourceLocation NameLoc;
1236 struct TemplateSpecializationLocInfo : TemplateNameLocInfo {
1237 SourceLocation TemplateKWLoc;
1238 SourceLocation LAngleLoc;
1239 SourceLocation RAngleLoc;
1242 class TemplateSpecializationTypeLoc :
1243 public ConcreteTypeLoc<UnqualTypeLoc,
1244 TemplateSpecializationTypeLoc,
1245 TemplateSpecializationType,
1246 TemplateSpecializationLocInfo> {
1248 SourceLocation getTemplateKeywordLoc() const {
1249 return getLocalData()->TemplateKWLoc;
1251 void setTemplateKeywordLoc(SourceLocation Loc) {
1252 getLocalData()->TemplateKWLoc = Loc;
1255 SourceLocation getLAngleLoc() const {
1256 return getLocalData()->LAngleLoc;
1258 void setLAngleLoc(SourceLocation Loc) {
1259 getLocalData()->LAngleLoc = Loc;
1262 SourceLocation getRAngleLoc() const {
1263 return getLocalData()->RAngleLoc;
1265 void setRAngleLoc(SourceLocation Loc) {
1266 getLocalData()->RAngleLoc = Loc;
1269 unsigned getNumArgs() const {
1270 return getTypePtr()->getNumArgs();
1272 void setArgLocInfo(unsigned i, TemplateArgumentLocInfo AI) {
1273 getArgInfos()[i] = AI;
1275 TemplateArgumentLocInfo getArgLocInfo(unsigned i) const {
1276 return getArgInfos()[i];
1279 TemplateArgumentLoc getArgLoc(unsigned i) const {
1280 return TemplateArgumentLoc(getTypePtr()->getArg(i), getArgLocInfo(i));
1283 SourceLocation getTemplateNameLoc() const {
1284 return getLocalData()->NameLoc;
1286 void setTemplateNameLoc(SourceLocation Loc) {
1287 getLocalData()->NameLoc = Loc;
1290 /// \brief - Copy the location information from the given info.
1291 void copy(TemplateSpecializationTypeLoc Loc) {
1292 unsigned size = getFullDataSize();
1293 assert(size == Loc.getFullDataSize());
1295 // We're potentially copying Expr references here. We don't
1296 // bother retaining them because TypeSourceInfos live forever, so
1297 // as long as the Expr was retained when originally written into
1298 // the TypeLoc, we're okay.
1299 memcpy(Data, Loc.Data, size);
1302 SourceRange getLocalSourceRange() const {
1303 if (getTemplateKeywordLoc().isValid())
1304 return SourceRange(getTemplateKeywordLoc(), getRAngleLoc());
1306 return SourceRange(getTemplateNameLoc(), getRAngleLoc());
1309 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1310 setTemplateKeywordLoc(Loc);
1311 setTemplateNameLoc(Loc);
1314 initializeArgLocs(Context, getNumArgs(), getTypePtr()->getArgs(),
1315 getArgInfos(), Loc);
1318 static void initializeArgLocs(ASTContext &Context, unsigned NumArgs,
1319 const TemplateArgument *Args,
1320 TemplateArgumentLocInfo *ArgInfos,
1321 SourceLocation Loc);
1323 unsigned getExtraLocalDataSize() const {
1324 return getNumArgs() * sizeof(TemplateArgumentLocInfo);
1328 TemplateArgumentLocInfo *getArgInfos() const {
1329 return static_cast<TemplateArgumentLocInfo*>(getExtraLocalData());
1333 //===----------------------------------------------------------------------===//
1335 // All of these need proper implementations.
1337 //===----------------------------------------------------------------------===//
1339 // FIXME: size expression and attribute locations (or keyword if we
1340 // ever fully support altivec syntax).
1341 class VectorTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
1346 // FIXME: size expression and attribute locations.
1347 class ExtVectorTypeLoc : public InheritingConcreteTypeLoc<VectorTypeLoc,
1352 // FIXME: attribute locations.
1353 // For some reason, this isn't a subtype of VectorType.
1354 class DependentSizedExtVectorTypeLoc :
1355 public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
1356 DependentSizedExtVectorTypeLoc,
1357 DependentSizedExtVectorType> {
1360 // FIXME: location of the '_Complex' keyword.
1361 class ComplexTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
1366 struct TypeofLocInfo {
1367 SourceLocation TypeofLoc;
1368 SourceLocation LParenLoc;
1369 SourceLocation RParenLoc;
1372 struct TypeOfExprTypeLocInfo : public TypeofLocInfo {
1375 struct TypeOfTypeLocInfo : public TypeofLocInfo {
1376 TypeSourceInfo* UnderlyingTInfo;
1379 template <class Derived, class TypeClass, class LocalData = TypeofLocInfo>
1380 class TypeofLikeTypeLoc
1381 : public ConcreteTypeLoc<UnqualTypeLoc, Derived, TypeClass, LocalData> {
1383 SourceLocation getTypeofLoc() const {
1384 return this->getLocalData()->TypeofLoc;
1386 void setTypeofLoc(SourceLocation Loc) {
1387 this->getLocalData()->TypeofLoc = Loc;
1390 SourceLocation getLParenLoc() const {
1391 return this->getLocalData()->LParenLoc;
1393 void setLParenLoc(SourceLocation Loc) {
1394 this->getLocalData()->LParenLoc = Loc;
1397 SourceLocation getRParenLoc() const {
1398 return this->getLocalData()->RParenLoc;
1400 void setRParenLoc(SourceLocation Loc) {
1401 this->getLocalData()->RParenLoc = Loc;
1404 SourceRange getParensRange() const {
1405 return SourceRange(getLParenLoc(), getRParenLoc());
1407 void setParensRange(SourceRange range) {
1408 setLParenLoc(range.getBegin());
1409 setRParenLoc(range.getEnd());
1412 SourceRange getLocalSourceRange() const {
1413 return SourceRange(getTypeofLoc(), getRParenLoc());
1416 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1423 class TypeOfExprTypeLoc : public TypeofLikeTypeLoc<TypeOfExprTypeLoc,
1425 TypeOfExprTypeLocInfo> {
1427 Expr* getUnderlyingExpr() const {
1428 return getTypePtr()->getUnderlyingExpr();
1430 // Reimplemented to account for GNU/C++ extension
1431 // typeof unary-expression
1432 // where there are no parentheses.
1433 SourceRange getLocalSourceRange() const;
1437 : public TypeofLikeTypeLoc<TypeOfTypeLoc, TypeOfType, TypeOfTypeLocInfo> {
1439 QualType getUnderlyingType() const {
1440 return this->getTypePtr()->getUnderlyingType();
1442 TypeSourceInfo* getUnderlyingTInfo() const {
1443 return this->getLocalData()->UnderlyingTInfo;
1445 void setUnderlyingTInfo(TypeSourceInfo* TI) const {
1446 this->getLocalData()->UnderlyingTInfo = TI;
1450 // FIXME: location of the 'decltype' and parens.
1451 class DecltypeTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
1455 Expr *getUnderlyingExpr() const { return getTypePtr()->getUnderlyingExpr(); }
1458 struct UnaryTransformTypeLocInfo {
1459 // FIXME: While there's only one unary transform right now, future ones may
1460 // need different representations
1461 SourceLocation KWLoc, LParenLoc, RParenLoc;
1462 TypeSourceInfo *UnderlyingTInfo;
1465 class UnaryTransformTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
1466 UnaryTransformTypeLoc,
1468 UnaryTransformTypeLocInfo> {
1470 SourceLocation getKWLoc() const { return getLocalData()->KWLoc; }
1471 void setKWLoc(SourceLocation Loc) { getLocalData()->KWLoc = Loc; }
1473 SourceLocation getLParenLoc() const { return getLocalData()->LParenLoc; }
1474 void setLParenLoc(SourceLocation Loc) { getLocalData()->LParenLoc = Loc; }
1476 SourceLocation getRParenLoc() const { return getLocalData()->RParenLoc; }
1477 void setRParenLoc(SourceLocation Loc) { getLocalData()->RParenLoc = Loc; }
1479 TypeSourceInfo* getUnderlyingTInfo() const {
1480 return getLocalData()->UnderlyingTInfo;
1482 void setUnderlyingTInfo(TypeSourceInfo *TInfo) {
1483 getLocalData()->UnderlyingTInfo = TInfo;
1486 SourceRange getLocalSourceRange() const {
1487 return SourceRange(getKWLoc(), getRParenLoc());
1490 SourceRange getParensRange() const {
1491 return SourceRange(getLParenLoc(), getRParenLoc());
1493 void setParensRange(SourceRange Range) {
1494 setLParenLoc(Range.getBegin());
1495 setRParenLoc(Range.getEnd());
1498 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1505 class AutoTypeLoc : public InheritingConcreteTypeLoc<TypeSpecTypeLoc,
1510 struct ElaboratedLocInfo {
1511 SourceLocation ElaboratedKWLoc;
1512 /// \brief Data associated with the nested-name-specifier location.
1513 void *QualifierData;
1516 class ElaboratedTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
1519 ElaboratedLocInfo> {
1521 SourceLocation getElaboratedKeywordLoc() const {
1522 return this->getLocalData()->ElaboratedKWLoc;
1524 void setElaboratedKeywordLoc(SourceLocation Loc) {
1525 this->getLocalData()->ElaboratedKWLoc = Loc;
1528 NestedNameSpecifierLoc getQualifierLoc() const {
1529 return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
1530 getLocalData()->QualifierData);
1533 void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
1534 assert(QualifierLoc.getNestedNameSpecifier()
1535 == getTypePtr()->getQualifier() &&
1536 "Inconsistent nested-name-specifier pointer");
1537 getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
1540 SourceRange getLocalSourceRange() const {
1541 if (getElaboratedKeywordLoc().isValid())
1542 if (getQualifierLoc())
1543 return SourceRange(getElaboratedKeywordLoc(),
1544 getQualifierLoc().getEndLoc());
1546 return SourceRange(getElaboratedKeywordLoc());
1548 return getQualifierLoc().getSourceRange();
1551 void initializeLocal(ASTContext &Context, SourceLocation Loc);
1553 TypeLoc getNamedTypeLoc() const {
1554 return getInnerTypeLoc();
1557 QualType getInnerType() const {
1558 return getTypePtr()->getNamedType();
1561 void copy(ElaboratedTypeLoc Loc) {
1562 unsigned size = getFullDataSize();
1563 assert(size == Loc.getFullDataSize());
1564 memcpy(Data, Loc.Data, size);
1568 // This is exactly the structure of an ElaboratedTypeLoc whose inner
1569 // type is some sort of TypeDeclTypeLoc.
1570 struct DependentNameLocInfo : ElaboratedLocInfo {
1571 SourceLocation NameLoc;
1574 class DependentNameTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc,
1575 DependentNameTypeLoc,
1577 DependentNameLocInfo> {
1579 SourceLocation getElaboratedKeywordLoc() const {
1580 return this->getLocalData()->ElaboratedKWLoc;
1582 void setElaboratedKeywordLoc(SourceLocation Loc) {
1583 this->getLocalData()->ElaboratedKWLoc = Loc;
1586 NestedNameSpecifierLoc getQualifierLoc() const {
1587 return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
1588 getLocalData()->QualifierData);
1591 void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
1592 assert(QualifierLoc.getNestedNameSpecifier()
1593 == getTypePtr()->getQualifier() &&
1594 "Inconsistent nested-name-specifier pointer");
1595 getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
1598 SourceLocation getNameLoc() const {
1599 return this->getLocalData()->NameLoc;
1601 void setNameLoc(SourceLocation Loc) {
1602 this->getLocalData()->NameLoc = Loc;
1605 SourceRange getLocalSourceRange() const {
1606 if (getElaboratedKeywordLoc().isValid())
1607 return SourceRange(getElaboratedKeywordLoc(), getNameLoc());
1609 return SourceRange(getQualifierLoc().getBeginLoc(), getNameLoc());
1612 void copy(DependentNameTypeLoc Loc) {
1613 unsigned size = getFullDataSize();
1614 assert(size == Loc.getFullDataSize());
1615 memcpy(Data, Loc.Data, size);
1618 void initializeLocal(ASTContext &Context, SourceLocation Loc);
1621 struct DependentTemplateSpecializationLocInfo : DependentNameLocInfo {
1622 SourceLocation TemplateKWLoc;
1623 SourceLocation LAngleLoc;
1624 SourceLocation RAngleLoc;
1625 // followed by a TemplateArgumentLocInfo[]
1628 class DependentTemplateSpecializationTypeLoc :
1629 public ConcreteTypeLoc<UnqualTypeLoc,
1630 DependentTemplateSpecializationTypeLoc,
1631 DependentTemplateSpecializationType,
1632 DependentTemplateSpecializationLocInfo> {
1634 SourceLocation getElaboratedKeywordLoc() const {
1635 return this->getLocalData()->ElaboratedKWLoc;
1637 void setElaboratedKeywordLoc(SourceLocation Loc) {
1638 this->getLocalData()->ElaboratedKWLoc = Loc;
1641 NestedNameSpecifierLoc getQualifierLoc() const {
1642 if (!getLocalData()->QualifierData)
1643 return NestedNameSpecifierLoc();
1645 return NestedNameSpecifierLoc(getTypePtr()->getQualifier(),
1646 getLocalData()->QualifierData);
1649 void setQualifierLoc(NestedNameSpecifierLoc QualifierLoc) {
1650 if (!QualifierLoc) {
1651 // Even if we have a nested-name-specifier in the dependent
1652 // template specialization type, we won't record the nested-name-specifier
1653 // location information when this type-source location information is
1654 // part of a nested-name-specifier.
1655 getLocalData()->QualifierData = 0;
1659 assert(QualifierLoc.getNestedNameSpecifier()
1660 == getTypePtr()->getQualifier() &&
1661 "Inconsistent nested-name-specifier pointer");
1662 getLocalData()->QualifierData = QualifierLoc.getOpaqueData();
1665 SourceLocation getTemplateKeywordLoc() const {
1666 return getLocalData()->TemplateKWLoc;
1668 void setTemplateKeywordLoc(SourceLocation Loc) {
1669 getLocalData()->TemplateKWLoc = Loc;
1672 SourceLocation getTemplateNameLoc() const {
1673 return this->getLocalData()->NameLoc;
1675 void setTemplateNameLoc(SourceLocation Loc) {
1676 this->getLocalData()->NameLoc = Loc;
1679 SourceLocation getLAngleLoc() const {
1680 return this->getLocalData()->LAngleLoc;
1682 void setLAngleLoc(SourceLocation Loc) {
1683 this->getLocalData()->LAngleLoc = Loc;
1686 SourceLocation getRAngleLoc() const {
1687 return this->getLocalData()->RAngleLoc;
1689 void setRAngleLoc(SourceLocation Loc) {
1690 this->getLocalData()->RAngleLoc = Loc;
1693 unsigned getNumArgs() const {
1694 return getTypePtr()->getNumArgs();
1697 void setArgLocInfo(unsigned i, TemplateArgumentLocInfo AI) {
1698 getArgInfos()[i] = AI;
1700 TemplateArgumentLocInfo getArgLocInfo(unsigned i) const {
1701 return getArgInfos()[i];
1704 TemplateArgumentLoc getArgLoc(unsigned i) const {
1705 return TemplateArgumentLoc(getTypePtr()->getArg(i), getArgLocInfo(i));
1708 SourceRange getLocalSourceRange() const {
1709 if (getElaboratedKeywordLoc().isValid())
1710 return SourceRange(getElaboratedKeywordLoc(), getRAngleLoc());
1711 else if (getQualifierLoc())
1712 return SourceRange(getQualifierLoc().getBeginLoc(), getRAngleLoc());
1713 else if (getTemplateKeywordLoc().isValid())
1714 return SourceRange(getTemplateKeywordLoc(), getRAngleLoc());
1716 return SourceRange(getTemplateNameLoc(), getRAngleLoc());
1719 void copy(DependentTemplateSpecializationTypeLoc Loc) {
1720 unsigned size = getFullDataSize();
1721 assert(size == Loc.getFullDataSize());
1722 memcpy(Data, Loc.Data, size);
1725 void initializeLocal(ASTContext &Context, SourceLocation Loc);
1727 unsigned getExtraLocalDataSize() const {
1728 return getNumArgs() * sizeof(TemplateArgumentLocInfo);
1732 TemplateArgumentLocInfo *getArgInfos() const {
1733 return static_cast<TemplateArgumentLocInfo*>(getExtraLocalData());
1738 struct PackExpansionTypeLocInfo {
1739 SourceLocation EllipsisLoc;
1742 class PackExpansionTypeLoc
1743 : public ConcreteTypeLoc<UnqualTypeLoc, PackExpansionTypeLoc,
1744 PackExpansionType, PackExpansionTypeLocInfo> {
1746 SourceLocation getEllipsisLoc() const {
1747 return this->getLocalData()->EllipsisLoc;
1750 void setEllipsisLoc(SourceLocation Loc) {
1751 this->getLocalData()->EllipsisLoc = Loc;
1754 SourceRange getLocalSourceRange() const {
1755 return SourceRange(getEllipsisLoc(), getEllipsisLoc());
1758 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1759 setEllipsisLoc(Loc);
1762 TypeLoc getPatternLoc() const {
1763 return getInnerTypeLoc();
1766 QualType getInnerType() const {
1767 return this->getTypePtr()->getPattern();
1771 struct AtomicTypeLocInfo {
1772 SourceLocation KWLoc, LParenLoc, RParenLoc;
1775 class AtomicTypeLoc : public ConcreteTypeLoc<UnqualTypeLoc, AtomicTypeLoc,
1776 AtomicType, AtomicTypeLocInfo> {
1778 TypeLoc getValueLoc() const {
1779 return this->getInnerTypeLoc();
1782 SourceRange getLocalSourceRange() const {
1783 return SourceRange(getKWLoc(), getRParenLoc());
1786 SourceLocation getKWLoc() const {
1787 return this->getLocalData()->KWLoc;
1789 void setKWLoc(SourceLocation Loc) {
1790 this->getLocalData()->KWLoc = Loc;
1793 SourceLocation getLParenLoc() const {
1794 return this->getLocalData()->LParenLoc;
1796 void setLParenLoc(SourceLocation Loc) {
1797 this->getLocalData()->LParenLoc = Loc;
1800 SourceLocation getRParenLoc() const {
1801 return this->getLocalData()->RParenLoc;
1803 void setRParenLoc(SourceLocation Loc) {
1804 this->getLocalData()->RParenLoc = Loc;
1807 SourceRange getParensRange() const {
1808 return SourceRange(getLParenLoc(), getRParenLoc());
1810 void setParensRange(SourceRange Range) {
1811 setLParenLoc(Range.getBegin());
1812 setRParenLoc(Range.getEnd());
1815 void initializeLocal(ASTContext &Context, SourceLocation Loc) {
1821 QualType getInnerType() const {
1822 return this->getTypePtr()->getValueType();