1327952Sdim//===- TypeLoc.cpp - Type Source Info Wrapper -----------------------------===// 2198092Srdivacky// 3353358Sdim// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4353358Sdim// See https://llvm.org/LICENSE.txt for license information. 5353358Sdim// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6198092Srdivacky// 7198092Srdivacky//===----------------------------------------------------------------------===// 8198092Srdivacky// 9198092Srdivacky// This file defines the TypeLoc subclasses implementations. 10198092Srdivacky// 11198092Srdivacky//===----------------------------------------------------------------------===// 12198092Srdivacky 13249423Sdim#include "clang/AST/TypeLoc.h" 14360784Sdim#include "clang/AST/DeclTemplate.h" 15239462Sdim#include "clang/AST/ASTContext.h" 16360784Sdim#include "clang/AST/Attr.h" 17202379Srdivacky#include "clang/AST/Expr.h" 18327952Sdim#include "clang/AST/NestedNameSpecifier.h" 19327952Sdim#include "clang/AST/TemplateBase.h" 20327952Sdim#include "clang/AST/TemplateName.h" 21249423Sdim#include "clang/AST/TypeLocVisitor.h" 22327952Sdim#include "clang/Basic/SourceLocation.h" 23327952Sdim#include "clang/Basic/Specifiers.h" 24202879Srdivacky#include "llvm/Support/ErrorHandling.h" 25327952Sdim#include "llvm/Support/MathExtras.h" 26327952Sdim#include <algorithm> 27327952Sdim#include <cassert> 28327952Sdim#include <cstdint> 29327952Sdim#include <cstring> 30327952Sdim 31198092Srdivackyusing namespace clang; 32198092Srdivacky 33314564Sdimstatic const unsigned TypeLocMaxDataAlign = alignof(void *); 34288943Sdim 35198092Srdivacky//===----------------------------------------------------------------------===// 36198092Srdivacky// TypeLoc Implementation 37198092Srdivacky//===----------------------------------------------------------------------===// 38198092Srdivacky 39198092Srdivackynamespace { 40327952Sdim 41327952Sdimclass TypeLocRanger : public TypeLocVisitor<TypeLocRanger, SourceRange> { 42327952Sdimpublic: 43198398Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 44198112Srdivacky#define TYPELOC(CLASS, PARENT) \ 45327952Sdim SourceRange Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc) { \ 46327952Sdim return TyLoc.getLocalSourceRange(); \ 47327952Sdim } 48198092Srdivacky#include "clang/AST/TypeLocNodes.def" 49327952Sdim}; 50198092Srdivacky 51327952Sdim} // namespace 52327952Sdim 53208600SrdivackySourceRange TypeLoc::getLocalSourceRangeImpl(TypeLoc TL) { 54198398Srdivacky if (TL.isNull()) return SourceRange(); 55198398Srdivacky return TypeLocRanger().Visit(TL); 56198092Srdivacky} 57198092Srdivacky 58198092Srdivackynamespace { 59327952Sdim 60327952Sdimclass TypeAligner : public TypeLocVisitor<TypeAligner, unsigned> { 61327952Sdimpublic: 62261991Sdim#define ABSTRACT_TYPELOC(CLASS, PARENT) 63261991Sdim#define TYPELOC(CLASS, PARENT) \ 64327952Sdim unsigned Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc) { \ 65327952Sdim return TyLoc.getLocalDataAlignment(); \ 66327952Sdim } 67261991Sdim#include "clang/AST/TypeLocNodes.def" 68327952Sdim}; 69261991Sdim 70327952Sdim} // namespace 71327952Sdim 72341825Sdim/// Returns the alignment of the type source info data block. 73261991Sdimunsigned TypeLoc::getLocalAlignmentForType(QualType Ty) { 74261991Sdim if (Ty.isNull()) return 1; 75276479Sdim return TypeAligner().Visit(TypeLoc(Ty, nullptr)); 76261991Sdim} 77261991Sdim 78261991Sdimnamespace { 79327952Sdim 80327952Sdimclass TypeSizer : public TypeLocVisitor<TypeSizer, unsigned> { 81327952Sdimpublic: 82198398Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 83198112Srdivacky#define TYPELOC(CLASS, PARENT) \ 84327952Sdim unsigned Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc) { \ 85327952Sdim return TyLoc.getLocalDataSize(); \ 86327952Sdim } 87198092Srdivacky#include "clang/AST/TypeLocNodes.def" 88327952Sdim}; 89198092Srdivacky 90327952Sdim} // namespace 91327952Sdim 92341825Sdim/// Returns the size of the type source info data block. 93198112Srdivackyunsigned TypeLoc::getFullDataSizeForType(QualType Ty) { 94261991Sdim unsigned Total = 0; 95276479Sdim TypeLoc TyLoc(Ty, nullptr); 96261991Sdim unsigned MaxAlign = 1; 97261991Sdim while (!TyLoc.isNull()) { 98261991Sdim unsigned Align = getLocalAlignmentForType(TyLoc.getType()); 99261991Sdim MaxAlign = std::max(Align, MaxAlign); 100309124Sdim Total = llvm::alignTo(Total, Align); 101261991Sdim Total += TypeSizer().Visit(TyLoc); 102261991Sdim TyLoc = TyLoc.getNextTypeLoc(); 103261991Sdim } 104309124Sdim Total = llvm::alignTo(Total, MaxAlign); 105261991Sdim return Total; 106198092Srdivacky} 107198092Srdivacky 108198092Srdivackynamespace { 109327952Sdim 110327952Sdimclass NextLoc : public TypeLocVisitor<NextLoc, TypeLoc> { 111327952Sdimpublic: 112198398Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 113198398Srdivacky#define TYPELOC(CLASS, PARENT) \ 114327952Sdim TypeLoc Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc) { \ 115327952Sdim return TyLoc.getNextTypeLoc(); \ 116327952Sdim } 117198092Srdivacky#include "clang/AST/TypeLocNodes.def" 118327952Sdim}; 119198092Srdivacky 120327952Sdim} // namespace 121327952Sdim 122341825Sdim/// Get the next TypeLoc pointed by this TypeLoc, e.g for "int*" the 123198092Srdivacky/// TypeLoc is a PointerLoc and next TypeLoc is for "int". 124198398SrdivackyTypeLoc TypeLoc::getNextTypeLocImpl(TypeLoc TL) { 125198398Srdivacky return NextLoc().Visit(TL); 126198092Srdivacky} 127198092Srdivacky 128341825Sdim/// Initializes a type location, and all of its children 129198398Srdivacky/// recursively, as if the entire tree had been written in the 130198398Srdivacky/// given location. 131341825Sdimvoid TypeLoc::initializeImpl(ASTContext &Context, TypeLoc TL, 132218893Sdim SourceLocation Loc) { 133208600Srdivacky while (true) { 134208600Srdivacky switch (TL.getTypeLocClass()) { 135208600Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 136208600Srdivacky#define TYPELOC(CLASS, PARENT) \ 137208600Srdivacky case CLASS: { \ 138249423Sdim CLASS##TypeLoc TLCasted = TL.castAs<CLASS##TypeLoc>(); \ 139218893Sdim TLCasted.initializeLocal(Context, Loc); \ 140208600Srdivacky TL = TLCasted.getNextTypeLoc(); \ 141208600Srdivacky if (!TL) return; \ 142208600Srdivacky continue; \ 143208600Srdivacky } 144208600Srdivacky#include "clang/AST/TypeLocNodes.def" 145208600Srdivacky } 146208600Srdivacky } 147198092Srdivacky} 148200583Srdivacky 149288943Sdimnamespace { 150288943Sdim 151327952Sdimclass TypeLocCopier : public TypeLocVisitor<TypeLocCopier> { 152327952Sdim TypeLoc Source; 153327952Sdim 154327952Sdimpublic: 155327952Sdim TypeLocCopier(TypeLoc source) : Source(source) {} 156327952Sdim 157288943Sdim#define ABSTRACT_TYPELOC(CLASS, PARENT) 158288943Sdim#define TYPELOC(CLASS, PARENT) \ 159327952Sdim void Visit##CLASS##TypeLoc(CLASS##TypeLoc dest) { \ 160327952Sdim dest.copyLocal(Source.castAs<CLASS##TypeLoc>()); \ 161327952Sdim } 162288943Sdim#include "clang/AST/TypeLocNodes.def" 163327952Sdim}; 164288943Sdim 165327952Sdim} // namespace 166288943Sdim 167288943Sdimvoid TypeLoc::copy(TypeLoc other) { 168288943Sdim assert(getFullDataSize() == other.getFullDataSize()); 169288943Sdim 170288943Sdim // If both data pointers are aligned to the maximum alignment, we 171288943Sdim // can memcpy because getFullDataSize() accurately reflects the 172288943Sdim // layout of the data. 173309124Sdim if (reinterpret_cast<uintptr_t>(Data) == 174309124Sdim llvm::alignTo(reinterpret_cast<uintptr_t>(Data), 175309124Sdim TypeLocMaxDataAlign) && 176309124Sdim reinterpret_cast<uintptr_t>(other.Data) == 177309124Sdim llvm::alignTo(reinterpret_cast<uintptr_t>(other.Data), 178309124Sdim TypeLocMaxDataAlign)) { 179288943Sdim memcpy(Data, other.Data, getFullDataSize()); 180288943Sdim return; 181288943Sdim } 182288943Sdim 183288943Sdim // Copy each of the pieces. 184288943Sdim TypeLoc TL(getType(), Data); 185288943Sdim do { 186288943Sdim TypeLocCopier(other).Visit(TL); 187288943Sdim other = other.getNextTypeLoc(); 188288943Sdim } while ((TL = TL.getNextTypeLoc())); 189288943Sdim} 190288943Sdim 191208600SrdivackySourceLocation TypeLoc::getBeginLoc() const { 192208600Srdivacky TypeLoc Cur = *this; 193243830Sdim TypeLoc LeftMost = Cur; 194208600Srdivacky while (true) { 195208600Srdivacky switch (Cur.getTypeLocClass()) { 196208600Srdivacky case Elaborated: 197243830Sdim LeftMost = Cur; 198208600Srdivacky break; 199243830Sdim case FunctionProto: 200249423Sdim if (Cur.castAs<FunctionProtoTypeLoc>().getTypePtr() 201249423Sdim ->hasTrailingReturn()) { 202243830Sdim LeftMost = Cur; 203243830Sdim break; 204243830Sdim } 205327952Sdim LLVM_FALLTHROUGH; 206243830Sdim case FunctionNoProto: 207243830Sdim case ConstantArray: 208243830Sdim case DependentSizedArray: 209243830Sdim case IncompleteArray: 210243830Sdim case VariableArray: 211243830Sdim // FIXME: Currently QualifiedTypeLoc does not have a source range 212243830Sdim case Qualified: 213243830Sdim Cur = Cur.getNextTypeLoc(); 214243830Sdim continue; 215208600Srdivacky default: 216296417Sdim if (Cur.getLocalSourceRange().getBegin().isValid()) 217243830Sdim LeftMost = Cur; 218243830Sdim Cur = Cur.getNextTypeLoc(); 219243830Sdim if (Cur.isNull()) 220243830Sdim break; 221208600Srdivacky continue; 222243830Sdim } // switch 223208600Srdivacky break; 224243830Sdim } // while 225243830Sdim return LeftMost.getLocalSourceRange().getBegin(); 226208600Srdivacky} 227208600Srdivacky 228208600SrdivackySourceLocation TypeLoc::getEndLoc() const { 229208600Srdivacky TypeLoc Cur = *this; 230221345Sdim TypeLoc Last; 231208600Srdivacky while (true) { 232208600Srdivacky switch (Cur.getTypeLocClass()) { 233208600Srdivacky default: 234221345Sdim if (!Last) 235314564Sdim Last = Cur; 236221345Sdim return Last.getLocalSourceRange().getEnd(); 237221345Sdim case Paren: 238221345Sdim case ConstantArray: 239221345Sdim case DependentSizedArray: 240221345Sdim case IncompleteArray: 241221345Sdim case VariableArray: 242221345Sdim case FunctionNoProto: 243221345Sdim Last = Cur; 244208600Srdivacky break; 245243830Sdim case FunctionProto: 246249423Sdim if (Cur.castAs<FunctionProtoTypeLoc>().getTypePtr()->hasTrailingReturn()) 247243830Sdim Last = TypeLoc(); 248243830Sdim else 249243830Sdim Last = Cur; 250243830Sdim break; 251221345Sdim case Pointer: 252221345Sdim case BlockPointer: 253221345Sdim case MemberPointer: 254221345Sdim case LValueReference: 255221345Sdim case RValueReference: 256221345Sdim case PackExpansion: 257221345Sdim if (!Last) 258341825Sdim Last = Cur; 259221345Sdim break; 260208600Srdivacky case Qualified: 261208600Srdivacky case Elaborated: 262221345Sdim break; 263208600Srdivacky } 264221345Sdim Cur = Cur.getNextTypeLoc(); 265208600Srdivacky } 266208600Srdivacky} 267208600Srdivacky 268200583Srdivackynamespace { 269200583Srdivacky 270327952Sdimstruct TSTChecker : public TypeLocVisitor<TSTChecker, bool> { 271327952Sdim // Overload resolution does the real work for us. 272327952Sdim static bool isTypeSpec(TypeSpecTypeLoc _) { return true; } 273327952Sdim static bool isTypeSpec(TypeLoc _) { return false; } 274327952Sdim 275200583Srdivacky#define ABSTRACT_TYPELOC(CLASS, PARENT) 276200583Srdivacky#define TYPELOC(CLASS, PARENT) \ 277327952Sdim bool Visit##CLASS##TypeLoc(CLASS##TypeLoc TyLoc) { \ 278327952Sdim return isTypeSpec(TyLoc); \ 279327952Sdim } 280200583Srdivacky#include "clang/AST/TypeLocNodes.def" 281327952Sdim}; 282200583Srdivacky 283327952Sdim} // namespace 284200583Srdivacky 285341825Sdim/// Determines if the given type loc corresponds to a 286200583Srdivacky/// TypeSpecTypeLoc. Since there is not actually a TypeSpecType in 287200583Srdivacky/// the type hierarchy, this is made somewhat complicated. 288200583Srdivacky/// 289200583Srdivacky/// There are a lot of types that currently use TypeSpecTypeLoc 290200583Srdivacky/// because it's a convenient base class. Ideally we would not accept 291200583Srdivacky/// those here, but ideally we would have better implementations for 292200583Srdivacky/// them. 293249423Sdimbool TypeSpecTypeLoc::isKind(const TypeLoc &TL) { 294249423Sdim if (TL.getType().hasLocalQualifiers()) return false; 295249423Sdim return TSTChecker().Visit(TL); 296200583Srdivacky} 297202379Srdivacky 298360784Sdimbool TagTypeLoc::isDefinition() const { 299360784Sdim TagDecl *D = getDecl(); 300360784Sdim return D->isCompleteDefinition() && 301360784Sdim (D->getIdentifier() == nullptr || D->getLocation() == getNameLoc()); 302360784Sdim} 303360784Sdim 304202379Srdivacky// Reimplemented to account for GNU/C++ extension 305202379Srdivacky// typeof unary-expression 306202379Srdivacky// where there are no parentheses. 307208600SrdivackySourceRange TypeOfExprTypeLoc::getLocalSourceRange() const { 308202379Srdivacky if (getRParenLoc().isValid()) 309202379Srdivacky return SourceRange(getTypeofLoc(), getRParenLoc()); 310202379Srdivacky else 311202379Srdivacky return SourceRange(getTypeofLoc(), 312202379Srdivacky getUnderlyingExpr()->getSourceRange().getEnd()); 313202379Srdivacky} 314202879Srdivacky 315202879Srdivacky 316202879SrdivackyTypeSpecifierType BuiltinTypeLoc::getWrittenTypeSpec() const { 317202879Srdivacky if (needsExtraLocalData()) 318202879Srdivacky return static_cast<TypeSpecifierType>(getWrittenBuiltinSpecs().Type); 319234353Sdim switch (getTypePtr()->getKind()) { 320234353Sdim case BuiltinType::Void: 321234353Sdim return TST_void; 322234353Sdim case BuiltinType::Bool: 323234353Sdim return TST_bool; 324234353Sdim case BuiltinType::Char_U: 325234353Sdim case BuiltinType::Char_S: 326234353Sdim return TST_char; 327341825Sdim case BuiltinType::Char8: 328341825Sdim return TST_char8; 329234353Sdim case BuiltinType::Char16: 330234353Sdim return TST_char16; 331234353Sdim case BuiltinType::Char32: 332234353Sdim return TST_char32; 333234353Sdim case BuiltinType::WChar_S: 334234353Sdim case BuiltinType::WChar_U: 335234353Sdim return TST_wchar; 336234353Sdim case BuiltinType::UChar: 337234353Sdim case BuiltinType::UShort: 338234353Sdim case BuiltinType::UInt: 339234353Sdim case BuiltinType::ULong: 340234353Sdim case BuiltinType::ULongLong: 341234353Sdim case BuiltinType::UInt128: 342234353Sdim case BuiltinType::SChar: 343234353Sdim case BuiltinType::Short: 344234353Sdim case BuiltinType::Int: 345234353Sdim case BuiltinType::Long: 346234353Sdim case BuiltinType::LongLong: 347234353Sdim case BuiltinType::Int128: 348234353Sdim case BuiltinType::Half: 349234353Sdim case BuiltinType::Float: 350234353Sdim case BuiltinType::Double: 351234353Sdim case BuiltinType::LongDouble: 352327952Sdim case BuiltinType::Float16: 353309124Sdim case BuiltinType::Float128: 354341825Sdim case BuiltinType::ShortAccum: 355341825Sdim case BuiltinType::Accum: 356341825Sdim case BuiltinType::LongAccum: 357341825Sdim case BuiltinType::UShortAccum: 358341825Sdim case BuiltinType::UAccum: 359341825Sdim case BuiltinType::ULongAccum: 360341825Sdim case BuiltinType::ShortFract: 361341825Sdim case BuiltinType::Fract: 362341825Sdim case BuiltinType::LongFract: 363341825Sdim case BuiltinType::UShortFract: 364341825Sdim case BuiltinType::UFract: 365341825Sdim case BuiltinType::ULongFract: 366341825Sdim case BuiltinType::SatShortAccum: 367341825Sdim case BuiltinType::SatAccum: 368341825Sdim case BuiltinType::SatLongAccum: 369341825Sdim case BuiltinType::SatUShortAccum: 370341825Sdim case BuiltinType::SatUAccum: 371341825Sdim case BuiltinType::SatULongAccum: 372341825Sdim case BuiltinType::SatShortFract: 373341825Sdim case BuiltinType::SatFract: 374341825Sdim case BuiltinType::SatLongFract: 375341825Sdim case BuiltinType::SatUShortFract: 376341825Sdim case BuiltinType::SatUFract: 377341825Sdim case BuiltinType::SatULongFract: 378234353Sdim llvm_unreachable("Builtin type needs extra local data!"); 379234353Sdim // Fall through, if the impossible happens. 380341825Sdim 381234353Sdim case BuiltinType::NullPtr: 382234353Sdim case BuiltinType::Overload: 383234353Sdim case BuiltinType::Dependent: 384234353Sdim case BuiltinType::BoundMember: 385234353Sdim case BuiltinType::UnknownAny: 386234353Sdim case BuiltinType::ARCUnbridgedCast: 387234353Sdim case BuiltinType::PseudoObject: 388234353Sdim case BuiltinType::ObjCId: 389234353Sdim case BuiltinType::ObjCClass: 390234353Sdim case BuiltinType::ObjCSel: 391309124Sdim#define IMAGE_TYPE(ImgType, Id, SingletonId, Access, Suffix) \ 392309124Sdim case BuiltinType::Id: 393309124Sdim#include "clang/Basic/OpenCLImageTypes.def" 394344779Sdim#define EXT_OPAQUE_TYPE(ExtType, Id, Ext) \ 395344779Sdim case BuiltinType::Id: 396344779Sdim#include "clang/Basic/OpenCLExtensionTypes.def" 397249423Sdim case BuiltinType::OCLSampler: 398249423Sdim case BuiltinType::OCLEvent: 399296417Sdim case BuiltinType::OCLClkEvent: 400296417Sdim case BuiltinType::OCLQueue: 401296417Sdim case BuiltinType::OCLReserveID: 402360784Sdim#define SVE_TYPE(Name, Id, SingletonId) \ 403360784Sdim case BuiltinType::Id: 404360784Sdim#include "clang/Basic/AArch64SVEACLETypes.def" 405243830Sdim case BuiltinType::BuiltinFn: 406296417Sdim case BuiltinType::OMPArraySection: 407234353Sdim return TST_unspecified; 408234353Sdim } 409218893Sdim 410234353Sdim llvm_unreachable("Invalid BuiltinType Kind!"); 411202879Srdivacky} 412218893Sdim 413218893SdimTypeLoc TypeLoc::IgnoreParensImpl(TypeLoc TL) { 414249423Sdim while (ParenTypeLoc PTL = TL.getAs<ParenTypeLoc>()) 415249423Sdim TL = PTL.getInnerLoc(); 416218893Sdim return TL; 417218893Sdim} 418218893Sdim 419288943SdimSourceLocation TypeLoc::findNullabilityLoc() const { 420344779Sdim if (auto ATL = getAs<AttributedTypeLoc>()) { 421344779Sdim const Attr *A = ATL.getAttr(); 422344779Sdim if (A && (isa<TypeNullableAttr>(A) || isa<TypeNonNullAttr>(A) || 423344779Sdim isa<TypeNullUnspecifiedAttr>(A))) 424344779Sdim return A->getLocation(); 425288943Sdim } 426288943Sdim 427327952Sdim return {}; 428288943Sdim} 429288943Sdim 430296417SdimTypeLoc TypeLoc::findExplicitQualifierLoc() const { 431296417Sdim // Qualified types. 432296417Sdim if (auto qual = getAs<QualifiedTypeLoc>()) 433296417Sdim return qual; 434296417Sdim 435296417Sdim TypeLoc loc = IgnoreParens(); 436296417Sdim 437296417Sdim // Attributed types. 438296417Sdim if (auto attr = loc.getAs<AttributedTypeLoc>()) { 439296417Sdim if (attr.isQualifier()) return attr; 440296417Sdim return attr.getModifiedLoc().findExplicitQualifierLoc(); 441296417Sdim } 442296417Sdim 443296417Sdim // C11 _Atomic types. 444296417Sdim if (auto atomic = loc.getAs<AtomicTypeLoc>()) { 445296417Sdim return atomic; 446296417Sdim } 447296417Sdim 448327952Sdim return {}; 449296417Sdim} 450296417Sdim 451314564Sdimvoid ObjCTypeParamTypeLoc::initializeLocal(ASTContext &Context, 452314564Sdim SourceLocation Loc) { 453314564Sdim setNameLoc(Loc); 454314564Sdim if (!getNumProtocols()) return; 455314564Sdim 456314564Sdim setProtocolLAngleLoc(Loc); 457314564Sdim setProtocolRAngleLoc(Loc); 458314564Sdim for (unsigned i = 0, e = getNumProtocols(); i != e; ++i) 459314564Sdim setProtocolLoc(i, Loc); 460314564Sdim} 461314564Sdim 462341825Sdimvoid ObjCObjectTypeLoc::initializeLocal(ASTContext &Context, 463288943Sdim SourceLocation Loc) { 464288943Sdim setHasBaseTypeAsWritten(true); 465288943Sdim setTypeArgsLAngleLoc(Loc); 466288943Sdim setTypeArgsRAngleLoc(Loc); 467288943Sdim for (unsigned i = 0, e = getNumTypeArgs(); i != e; ++i) { 468341825Sdim setTypeArgTInfo(i, 469288943Sdim Context.getTrivialTypeSourceInfo( 470288943Sdim getTypePtr()->getTypeArgsAsWritten()[i], Loc)); 471288943Sdim } 472288943Sdim setProtocolLAngleLoc(Loc); 473288943Sdim setProtocolRAngleLoc(Loc); 474288943Sdim for (unsigned i = 0, e = getNumProtocols(); i != e; ++i) 475288943Sdim setProtocolLoc(i, Loc); 476288943Sdim} 477288943Sdim 478360784SdimSourceRange AttributedTypeLoc::getLocalSourceRange() const { 479360784Sdim // Note that this does *not* include the range of the attribute 480360784Sdim // enclosure, e.g.: 481360784Sdim // __attribute__((foo(bar))) 482360784Sdim // ^~~~~~~~~~~~~~~ ~~ 483360784Sdim // or 484360784Sdim // [[foo(bar)]] 485360784Sdim // ^~ ~~ 486360784Sdim // That enclosure doesn't necessarily belong to a single attribute 487360784Sdim // anyway. 488360784Sdim return getAttr() ? getAttr()->getRange() : SourceRange(); 489360784Sdim} 490360784Sdim 491280031Sdimvoid TypeOfTypeLoc::initializeLocal(ASTContext &Context, 492280031Sdim SourceLocation Loc) { 493280031Sdim TypeofLikeTypeLoc<TypeOfTypeLoc, TypeOfType, TypeOfTypeLocInfo> 494280031Sdim ::initializeLocal(Context, Loc); 495280031Sdim this->getLocalData()->UnderlyingTInfo = Context.getTrivialTypeSourceInfo( 496280031Sdim getUnderlyingType(), Loc); 497280031Sdim} 498280031Sdim 499327952Sdimvoid UnaryTransformTypeLoc::initializeLocal(ASTContext &Context, 500327952Sdim SourceLocation Loc) { 501327952Sdim setKWLoc(Loc); 502327952Sdim setRParenLoc(Loc); 503327952Sdim setLParenLoc(Loc); 504327952Sdim this->setUnderlyingTInfo( 505327952Sdim Context.getTrivialTypeSourceInfo(getTypePtr()->getBaseType(), Loc)); 506327952Sdim} 507327952Sdim 508341825Sdimvoid ElaboratedTypeLoc::initializeLocal(ASTContext &Context, 509221345Sdim SourceLocation Loc) { 510234353Sdim setElaboratedKeywordLoc(Loc); 511221345Sdim NestedNameSpecifierLocBuilder Builder; 512221345Sdim Builder.MakeTrivial(Context, getTypePtr()->getQualifier(), Loc); 513221345Sdim setQualifierLoc(Builder.getWithLocInContext(Context)); 514221345Sdim} 515221345Sdim 516341825Sdimvoid DependentNameTypeLoc::initializeLocal(ASTContext &Context, 517221345Sdim SourceLocation Loc) { 518234353Sdim setElaboratedKeywordLoc(Loc); 519221345Sdim NestedNameSpecifierLocBuilder Builder; 520221345Sdim Builder.MakeTrivial(Context, getTypePtr()->getQualifier(), Loc); 521221345Sdim setQualifierLoc(Builder.getWithLocInContext(Context)); 522221345Sdim setNameLoc(Loc); 523221345Sdim} 524221345Sdim 525234353Sdimvoid 526234353SdimDependentTemplateSpecializationTypeLoc::initializeLocal(ASTContext &Context, 527221345Sdim SourceLocation Loc) { 528234353Sdim setElaboratedKeywordLoc(Loc); 529221345Sdim if (getTypePtr()->getQualifier()) { 530221345Sdim NestedNameSpecifierLocBuilder Builder; 531221345Sdim Builder.MakeTrivial(Context, getTypePtr()->getQualifier(), Loc); 532221345Sdim setQualifierLoc(Builder.getWithLocInContext(Context)); 533221345Sdim } else { 534221345Sdim setQualifierLoc(NestedNameSpecifierLoc()); 535221345Sdim } 536234353Sdim setTemplateKeywordLoc(Loc); 537234353Sdim setTemplateNameLoc(Loc); 538221345Sdim setLAngleLoc(Loc); 539221345Sdim setRAngleLoc(Loc); 540221345Sdim TemplateSpecializationTypeLoc::initializeArgLocs(Context, getNumArgs(), 541221345Sdim getTypePtr()->getArgs(), 542221345Sdim getArgInfos(), Loc); 543221345Sdim} 544221345Sdim 545341825Sdimvoid TemplateSpecializationTypeLoc::initializeArgLocs(ASTContext &Context, 546218893Sdim unsigned NumArgs, 547218893Sdim const TemplateArgument *Args, 548218893Sdim TemplateArgumentLocInfo *ArgInfos, 549218893Sdim SourceLocation Loc) { 550218893Sdim for (unsigned i = 0, e = NumArgs; i != e; ++i) { 551218893Sdim switch (Args[i].getKind()) { 552341825Sdim case TemplateArgument::Null: 553261991Sdim llvm_unreachable("Impossible TemplateArgument"); 554261991Sdim 555261991Sdim case TemplateArgument::Integral: 556218893Sdim case TemplateArgument::Declaration: 557243830Sdim case TemplateArgument::NullPtr: 558261991Sdim ArgInfos[i] = TemplateArgumentLocInfo(); 559261991Sdim break; 560243830Sdim 561218893Sdim case TemplateArgument::Expression: 562234353Sdim ArgInfos[i] = TemplateArgumentLocInfo(Args[i].getAsExpr()); 563218893Sdim break; 564341825Sdim 565218893Sdim case TemplateArgument::Type: 566218893Sdim ArgInfos[i] = TemplateArgumentLocInfo( 567341825Sdim Context.getTrivialTypeSourceInfo(Args[i].getAsType(), 568218893Sdim Loc)); 569218893Sdim break; 570243830Sdim 571218893Sdim case TemplateArgument::Template: 572221345Sdim case TemplateArgument::TemplateExpansion: { 573221345Sdim NestedNameSpecifierLocBuilder Builder; 574261991Sdim TemplateName Template = Args[i].getAsTemplateOrTemplatePattern(); 575221345Sdim if (DependentTemplateName *DTN = Template.getAsDependentTemplateName()) 576221345Sdim Builder.MakeTrivial(Context, DTN->getQualifier(), Loc); 577221345Sdim else if (QualifiedTemplateName *QTN = Template.getAsQualifiedTemplateName()) 578221345Sdim Builder.MakeTrivial(Context, QTN->getQualifier(), Loc); 579261991Sdim 580221345Sdim ArgInfos[i] = TemplateArgumentLocInfo( 581261991Sdim Builder.getWithLocInContext(Context), Loc, 582261991Sdim Args[i].getKind() == TemplateArgument::Template ? SourceLocation() 583261991Sdim : Loc); 584218893Sdim break; 585218893Sdim } 586243830Sdim 587243830Sdim case TemplateArgument::Pack: 588243830Sdim ArgInfos[i] = TemplateArgumentLocInfo(); 589243830Sdim break; 590243830Sdim } 591218893Sdim } 592218893Sdim} 593360784Sdim 594360784SdimDeclarationNameInfo AutoTypeLoc::getConceptNameInfo() const { 595360784Sdim return DeclarationNameInfo(getNamedConcept()->getDeclName(), 596360784Sdim getLocalData()->ConceptNameLoc); 597360784Sdim} 598360784Sdim 599360784Sdimvoid AutoTypeLoc::initializeLocal(ASTContext &Context, SourceLocation Loc) { 600360784Sdim setNestedNameSpecifierLoc(NestedNameSpecifierLoc()); 601360784Sdim setTemplateKWLoc(Loc); 602360784Sdim setConceptNameLoc(Loc); 603360784Sdim setFoundDecl(nullptr); 604360784Sdim setRAngleLoc(Loc); 605360784Sdim setLAngleLoc(Loc); 606360784Sdim TemplateSpecializationTypeLoc::initializeArgLocs(Context, getNumArgs(), 607360784Sdim getTypePtr()->getArgs(), 608360784Sdim getArgInfos(), Loc); 609360784Sdim setNameLoc(Loc); 610360784Sdim} 611360784Sdim 612360784Sdim 613360784Sdimnamespace { 614360784Sdim 615360784Sdim class GetContainedAutoTypeLocVisitor : 616360784Sdim public TypeLocVisitor<GetContainedAutoTypeLocVisitor, TypeLoc> { 617360784Sdim public: 618360784Sdim using TypeLocVisitor<GetContainedAutoTypeLocVisitor, TypeLoc>::Visit; 619360784Sdim 620360784Sdim TypeLoc VisitAutoTypeLoc(AutoTypeLoc TL) { 621360784Sdim return TL; 622360784Sdim } 623360784Sdim 624360784Sdim // Only these types can contain the desired 'auto' type. 625360784Sdim 626360784Sdim TypeLoc VisitElaboratedTypeLoc(ElaboratedTypeLoc T) { 627360784Sdim return Visit(T.getNamedTypeLoc()); 628360784Sdim } 629360784Sdim 630360784Sdim TypeLoc VisitQualifiedTypeLoc(QualifiedTypeLoc T) { 631360784Sdim return Visit(T.getUnqualifiedLoc()); 632360784Sdim } 633360784Sdim 634360784Sdim TypeLoc VisitPointerTypeLoc(PointerTypeLoc T) { 635360784Sdim return Visit(T.getPointeeLoc()); 636360784Sdim } 637360784Sdim 638360784Sdim TypeLoc VisitBlockPointerTypeLoc(BlockPointerTypeLoc T) { 639360784Sdim return Visit(T.getPointeeLoc()); 640360784Sdim } 641360784Sdim 642360784Sdim TypeLoc VisitReferenceTypeLoc(ReferenceTypeLoc T) { 643360784Sdim return Visit(T.getPointeeLoc()); 644360784Sdim } 645360784Sdim 646360784Sdim TypeLoc VisitMemberPointerTypeLoc(MemberPointerTypeLoc T) { 647360784Sdim return Visit(T.getPointeeLoc()); 648360784Sdim } 649360784Sdim 650360784Sdim TypeLoc VisitArrayTypeLoc(ArrayTypeLoc T) { 651360784Sdim return Visit(T.getElementLoc()); 652360784Sdim } 653360784Sdim 654360784Sdim TypeLoc VisitFunctionTypeLoc(FunctionTypeLoc T) { 655360784Sdim return Visit(T.getReturnLoc()); 656360784Sdim } 657360784Sdim 658360784Sdim TypeLoc VisitParenTypeLoc(ParenTypeLoc T) { 659360784Sdim return Visit(T.getInnerLoc()); 660360784Sdim } 661360784Sdim 662360784Sdim TypeLoc VisitAttributedTypeLoc(AttributedTypeLoc T) { 663360784Sdim return Visit(T.getModifiedLoc()); 664360784Sdim } 665360784Sdim 666360784Sdim TypeLoc VisitMacroQualifiedTypeLoc(MacroQualifiedTypeLoc T) { 667360784Sdim return Visit(T.getInnerLoc()); 668360784Sdim } 669360784Sdim 670360784Sdim TypeLoc VisitAdjustedTypeLoc(AdjustedTypeLoc T) { 671360784Sdim return Visit(T.getOriginalLoc()); 672360784Sdim } 673360784Sdim 674360784Sdim TypeLoc VisitPackExpansionTypeLoc(PackExpansionTypeLoc T) { 675360784Sdim return Visit(T.getPatternLoc()); 676360784Sdim } 677360784Sdim }; 678360784Sdim 679360784Sdim} // namespace 680360784Sdim 681360784SdimAutoTypeLoc TypeLoc::getContainedAutoTypeLoc() const { 682360784Sdim TypeLoc Res = GetContainedAutoTypeLocVisitor().Visit(*this); 683360784Sdim if (Res.isNull()) 684360784Sdim return AutoTypeLoc(); 685360784Sdim return Res.getAs<AutoTypeLoc>(); 686360784Sdim} 687