llvm-project

Форк
0
/
DeclTemplate.cpp 
1720 строк · 67.5 Кб
1
//===- DeclTemplate.cpp - Template Declaration AST Node Implementation ----===//
2
//
3
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4
// See https://llvm.org/LICENSE.txt for license information.
5
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6
//
7
//===----------------------------------------------------------------------===//
8
//
9
// This file implements the C++ related Decl classes for templates.
10
//
11
//===----------------------------------------------------------------------===//
12

13
#include "clang/AST/DeclTemplate.h"
14
#include "clang/AST/ASTContext.h"
15
#include "clang/AST/ASTMutationListener.h"
16
#include "clang/AST/DeclCXX.h"
17
#include "clang/AST/DeclarationName.h"
18
#include "clang/AST/Expr.h"
19
#include "clang/AST/ExternalASTSource.h"
20
#include "clang/AST/TemplateBase.h"
21
#include "clang/AST/TemplateName.h"
22
#include "clang/AST/Type.h"
23
#include "clang/AST/TypeLoc.h"
24
#include "clang/Basic/Builtins.h"
25
#include "clang/Basic/LLVM.h"
26
#include "clang/Basic/SourceLocation.h"
27
#include "llvm/ADT/ArrayRef.h"
28
#include "llvm/ADT/FoldingSet.h"
29
#include "llvm/ADT/PointerUnion.h"
30
#include "llvm/ADT/STLExtras.h"
31
#include "llvm/ADT/SmallVector.h"
32
#include "llvm/Support/Casting.h"
33
#include "llvm/Support/ErrorHandling.h"
34
#include <algorithm>
35
#include <cassert>
36
#include <cstdint>
37
#include <memory>
38
#include <optional>
39
#include <utility>
40

41
using namespace clang;
42

43
//===----------------------------------------------------------------------===//
44
// TemplateParameterList Implementation
45
//===----------------------------------------------------------------------===//
46

47

48
TemplateParameterList::TemplateParameterList(const ASTContext& C,
49
                                             SourceLocation TemplateLoc,
50
                                             SourceLocation LAngleLoc,
51
                                             ArrayRef<NamedDecl *> Params,
52
                                             SourceLocation RAngleLoc,
53
                                             Expr *RequiresClause)
54
    : TemplateLoc(TemplateLoc), LAngleLoc(LAngleLoc), RAngleLoc(RAngleLoc),
55
      NumParams(Params.size()), ContainsUnexpandedParameterPack(false),
56
      HasRequiresClause(RequiresClause != nullptr),
57
      HasConstrainedParameters(false) {
58
  for (unsigned Idx = 0; Idx < NumParams; ++Idx) {
59
    NamedDecl *P = Params[Idx];
60
    begin()[Idx] = P;
61

62
    bool IsPack = P->isTemplateParameterPack();
63
    if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P)) {
64
      if (!IsPack && NTTP->getType()->containsUnexpandedParameterPack())
65
        ContainsUnexpandedParameterPack = true;
66
      if (NTTP->hasPlaceholderTypeConstraint())
67
        HasConstrainedParameters = true;
68
    } else if (const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(P)) {
69
      if (!IsPack &&
70
          TTP->getTemplateParameters()->containsUnexpandedParameterPack())
71
        ContainsUnexpandedParameterPack = true;
72
    } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) {
73
      if (const TypeConstraint *TC = TTP->getTypeConstraint()) {
74
        if (TC->getImmediatelyDeclaredConstraint()
75
            ->containsUnexpandedParameterPack())
76
          ContainsUnexpandedParameterPack = true;
77
      }
78
      if (TTP->hasTypeConstraint())
79
        HasConstrainedParameters = true;
80
    } else {
81
      llvm_unreachable("unexpected template parameter type");
82
    }
83
    // FIXME: If a default argument contains an unexpanded parameter pack, the
84
    // template parameter list does too.
85
  }
86

87
  if (HasRequiresClause) {
88
    if (RequiresClause->containsUnexpandedParameterPack())
89
      ContainsUnexpandedParameterPack = true;
90
    *getTrailingObjects<Expr *>() = RequiresClause;
91
  }
92
}
93

94
bool TemplateParameterList::containsUnexpandedParameterPack() const {
95
  if (ContainsUnexpandedParameterPack)
96
    return true;
97
  if (!HasConstrainedParameters)
98
    return false;
99

100
  // An implicit constrained parameter might have had a use of an unexpanded
101
  // pack added to it after the template parameter list was created. All
102
  // implicit parameters are at the end of the parameter list.
103
  for (const NamedDecl *Param : llvm::reverse(asArray())) {
104
    if (!Param->isImplicit())
105
      break;
106

107
    if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(Param)) {
108
      const auto *TC = TTP->getTypeConstraint();
109
      if (TC && TC->getImmediatelyDeclaredConstraint()
110
                    ->containsUnexpandedParameterPack())
111
        return true;
112
    }
113
  }
114

115
  return false;
116
}
117

118
TemplateParameterList *
119
TemplateParameterList::Create(const ASTContext &C, SourceLocation TemplateLoc,
120
                              SourceLocation LAngleLoc,
121
                              ArrayRef<NamedDecl *> Params,
122
                              SourceLocation RAngleLoc, Expr *RequiresClause) {
123
  void *Mem = C.Allocate(totalSizeToAlloc<NamedDecl *, Expr *>(
124
                             Params.size(), RequiresClause ? 1u : 0u),
125
                         alignof(TemplateParameterList));
126
  return new (Mem) TemplateParameterList(C, TemplateLoc, LAngleLoc, Params,
127
                                         RAngleLoc, RequiresClause);
128
}
129

130
void TemplateParameterList::Profile(llvm::FoldingSetNodeID &ID,
131
                                    const ASTContext &C) const {
132
  const Expr *RC = getRequiresClause();
133
  ID.AddBoolean(RC != nullptr);
134
  if (RC)
135
    RC->Profile(ID, C, /*Canonical=*/true);
136
  ID.AddInteger(size());
137
  for (NamedDecl *D : *this) {
138
    if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(D)) {
139
      ID.AddInteger(0);
140
      ID.AddBoolean(NTTP->isParameterPack());
141
      NTTP->getType().getCanonicalType().Profile(ID);
142
      ID.AddBoolean(NTTP->hasPlaceholderTypeConstraint());
143
      if (const Expr *E = NTTP->getPlaceholderTypeConstraint())
144
        E->Profile(ID, C, /*Canonical=*/true);
145
      continue;
146
    }
147
    if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(D)) {
148
      ID.AddInteger(1);
149
      ID.AddBoolean(TTP->isParameterPack());
150
      ID.AddBoolean(TTP->hasTypeConstraint());
151
      if (const TypeConstraint *TC = TTP->getTypeConstraint())
152
        TC->getImmediatelyDeclaredConstraint()->Profile(ID, C,
153
                                                        /*Canonical=*/true);
154
      continue;
155
    }
156
    const auto *TTP = cast<TemplateTemplateParmDecl>(D);
157
    ID.AddInteger(2);
158
    ID.AddBoolean(TTP->isParameterPack());
159
    TTP->getTemplateParameters()->Profile(ID, C);
160
  }
161
}
162

163
unsigned TemplateParameterList::getMinRequiredArguments() const {
164
  unsigned NumRequiredArgs = 0;
165
  for (const NamedDecl *P : asArray()) {
166
    if (P->isTemplateParameterPack()) {
167
      if (std::optional<unsigned> Expansions = getExpandedPackSize(P)) {
168
        NumRequiredArgs += *Expansions;
169
        continue;
170
      }
171
      break;
172
    }
173

174
    if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) {
175
      if (TTP->hasDefaultArgument())
176
        break;
177
    } else if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P)) {
178
      if (NTTP->hasDefaultArgument())
179
        break;
180
    } else if (cast<TemplateTemplateParmDecl>(P)->hasDefaultArgument())
181
      break;
182

183
    ++NumRequiredArgs;
184
  }
185

186
  return NumRequiredArgs;
187
}
188

189
unsigned TemplateParameterList::getDepth() const {
190
  if (size() == 0)
191
    return 0;
192

193
  const NamedDecl *FirstParm = getParam(0);
194
  if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(FirstParm))
195
    return TTP->getDepth();
196
  else if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(FirstParm))
197
    return NTTP->getDepth();
198
  else
199
    return cast<TemplateTemplateParmDecl>(FirstParm)->getDepth();
200
}
201

202
static bool AdoptTemplateParameterList(TemplateParameterList *Params,
203
                                       DeclContext *Owner) {
204
  bool Invalid = false;
205
  for (NamedDecl *P : *Params) {
206
    P->setDeclContext(Owner);
207

208
    if (const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(P))
209
      if (AdoptTemplateParameterList(TTP->getTemplateParameters(), Owner))
210
        Invalid = true;
211

212
    if (P->isInvalidDecl())
213
      Invalid = true;
214
  }
215
  return Invalid;
216
}
217

218
void TemplateParameterList::
219
getAssociatedConstraints(llvm::SmallVectorImpl<const Expr *> &AC) const {
220
  if (HasConstrainedParameters)
221
    for (const NamedDecl *Param : *this) {
222
      if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(Param)) {
223
        if (const auto *TC = TTP->getTypeConstraint())
224
          AC.push_back(TC->getImmediatelyDeclaredConstraint());
225
      } else if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(Param)) {
226
        if (const Expr *E = NTTP->getPlaceholderTypeConstraint())
227
          AC.push_back(E);
228
      }
229
    }
230
  if (HasRequiresClause)
231
    AC.push_back(getRequiresClause());
232
}
233

234
bool TemplateParameterList::hasAssociatedConstraints() const {
235
  return HasRequiresClause || HasConstrainedParameters;
236
}
237

238
bool TemplateParameterList::shouldIncludeTypeForArgument(
239
    const PrintingPolicy &Policy, const TemplateParameterList *TPL,
240
    unsigned Idx) {
241
  if (!TPL || Idx >= TPL->size() || Policy.AlwaysIncludeTypeForTemplateArgument)
242
    return true;
243
  const NamedDecl *TemplParam = TPL->getParam(Idx);
244
  if (const auto *ParamValueDecl =
245
          dyn_cast<NonTypeTemplateParmDecl>(TemplParam))
246
    if (ParamValueDecl->getType()->getContainedDeducedType())
247
      return true;
248
  return false;
249
}
250

251
namespace clang {
252

253
void *allocateDefaultArgStorageChain(const ASTContext &C) {
254
  return new (C) char[sizeof(void*) * 2];
255
}
256

257
} // namespace clang
258

259
//===----------------------------------------------------------------------===//
260
// TemplateDecl Implementation
261
//===----------------------------------------------------------------------===//
262

263
TemplateDecl::TemplateDecl(Kind DK, DeclContext *DC, SourceLocation L,
264
                           DeclarationName Name, TemplateParameterList *Params,
265
                           NamedDecl *Decl)
266
    : NamedDecl(DK, DC, L, Name), TemplatedDecl(Decl), TemplateParams(Params) {}
267

268
void TemplateDecl::anchor() {}
269

270
void TemplateDecl::
271
getAssociatedConstraints(llvm::SmallVectorImpl<const Expr *> &AC) const {
272
  TemplateParams->getAssociatedConstraints(AC);
273
  if (auto *FD = dyn_cast_or_null<FunctionDecl>(getTemplatedDecl()))
274
    if (const Expr *TRC = FD->getTrailingRequiresClause())
275
      AC.push_back(TRC);
276
}
277

278
bool TemplateDecl::hasAssociatedConstraints() const {
279
  if (TemplateParams->hasAssociatedConstraints())
280
    return true;
281
  if (auto *FD = dyn_cast_or_null<FunctionDecl>(getTemplatedDecl()))
282
    return FD->getTrailingRequiresClause();
283
  return false;
284
}
285

286
bool TemplateDecl::isTypeAlias() const {
287
  switch (getKind()) {
288
  case TemplateDecl::TypeAliasTemplate:
289
  case TemplateDecl::BuiltinTemplate:
290
    return true;
291
  default:
292
    return false;
293
  };
294
}
295

296
//===----------------------------------------------------------------------===//
297
// RedeclarableTemplateDecl Implementation
298
//===----------------------------------------------------------------------===//
299

300
void RedeclarableTemplateDecl::anchor() {}
301

302
RedeclarableTemplateDecl::CommonBase *RedeclarableTemplateDecl::getCommonPtr() const {
303
  if (Common)
304
    return Common;
305

306
  // Walk the previous-declaration chain until we either find a declaration
307
  // with a common pointer or we run out of previous declarations.
308
  SmallVector<const RedeclarableTemplateDecl *, 2> PrevDecls;
309
  for (const RedeclarableTemplateDecl *Prev = getPreviousDecl(); Prev;
310
       Prev = Prev->getPreviousDecl()) {
311
    if (Prev->Common) {
312
      Common = Prev->Common;
313
      break;
314
    }
315

316
    PrevDecls.push_back(Prev);
317
  }
318

319
  // If we never found a common pointer, allocate one now.
320
  if (!Common) {
321
    // FIXME: If any of the declarations is from an AST file, we probably
322
    // need an update record to add the common data.
323

324
    Common = newCommon(getASTContext());
325
  }
326

327
  // Update any previous declarations we saw with the common pointer.
328
  for (const RedeclarableTemplateDecl *Prev : PrevDecls)
329
    Prev->Common = Common;
330

331
  return Common;
332
}
333

334
void RedeclarableTemplateDecl::loadLazySpecializationsImpl() const {
335
  // Grab the most recent declaration to ensure we've loaded any lazy
336
  // redeclarations of this template.
337
  CommonBase *CommonBasePtr = getMostRecentDecl()->getCommonPtr();
338
  if (CommonBasePtr->LazySpecializations) {
339
    ASTContext &Context = getASTContext();
340
    GlobalDeclID *Specs = CommonBasePtr->LazySpecializations;
341
    CommonBasePtr->LazySpecializations = nullptr;
342
    unsigned SpecSize = (*Specs++).getRawValue();
343
    for (unsigned I = 0; I != SpecSize; ++I)
344
      (void)Context.getExternalSource()->GetExternalDecl(Specs[I]);
345
  }
346
}
347

348
template<class EntryType, typename... ProfileArguments>
349
typename RedeclarableTemplateDecl::SpecEntryTraits<EntryType>::DeclType *
350
RedeclarableTemplateDecl::findSpecializationImpl(
351
    llvm::FoldingSetVector<EntryType> &Specs, void *&InsertPos,
352
    ProfileArguments&&... ProfileArgs) {
353
  using SETraits = SpecEntryTraits<EntryType>;
354

355
  llvm::FoldingSetNodeID ID;
356
  EntryType::Profile(ID, std::forward<ProfileArguments>(ProfileArgs)...,
357
                     getASTContext());
358
  EntryType *Entry = Specs.FindNodeOrInsertPos(ID, InsertPos);
359
  return Entry ? SETraits::getDecl(Entry)->getMostRecentDecl() : nullptr;
360
}
361

362
template<class Derived, class EntryType>
363
void RedeclarableTemplateDecl::addSpecializationImpl(
364
    llvm::FoldingSetVector<EntryType> &Specializations, EntryType *Entry,
365
    void *InsertPos) {
366
  using SETraits = SpecEntryTraits<EntryType>;
367

368
  if (InsertPos) {
369
#ifndef NDEBUG
370
    void *CorrectInsertPos;
371
    assert(!findSpecializationImpl(Specializations,
372
                                   CorrectInsertPos,
373
                                   SETraits::getTemplateArgs(Entry)) &&
374
           InsertPos == CorrectInsertPos &&
375
           "given incorrect InsertPos for specialization");
376
#endif
377
    Specializations.InsertNode(Entry, InsertPos);
378
  } else {
379
    EntryType *Existing = Specializations.GetOrInsertNode(Entry);
380
    (void)Existing;
381
    assert(SETraits::getDecl(Existing)->isCanonicalDecl() &&
382
           "non-canonical specialization?");
383
  }
384

385
  if (ASTMutationListener *L = getASTMutationListener())
386
    L->AddedCXXTemplateSpecialization(cast<Derived>(this),
387
                                      SETraits::getDecl(Entry));
388
}
389

390
ArrayRef<TemplateArgument> RedeclarableTemplateDecl::getInjectedTemplateArgs() {
391
  TemplateParameterList *Params = getTemplateParameters();
392
  auto *CommonPtr = getCommonPtr();
393
  if (!CommonPtr->InjectedArgs) {
394
    auto &Context = getASTContext();
395
    SmallVector<TemplateArgument, 16> TemplateArgs;
396
    Context.getInjectedTemplateArgs(Params, TemplateArgs);
397
    CommonPtr->InjectedArgs =
398
        new (Context) TemplateArgument[TemplateArgs.size()];
399
    std::copy(TemplateArgs.begin(), TemplateArgs.end(),
400
              CommonPtr->InjectedArgs);
401
  }
402

403
  return llvm::ArrayRef(CommonPtr->InjectedArgs, Params->size());
404
}
405

406
//===----------------------------------------------------------------------===//
407
// FunctionTemplateDecl Implementation
408
//===----------------------------------------------------------------------===//
409

410
FunctionTemplateDecl *
411
FunctionTemplateDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L,
412
                             DeclarationName Name,
413
                             TemplateParameterList *Params, NamedDecl *Decl) {
414
  bool Invalid = AdoptTemplateParameterList(Params, cast<DeclContext>(Decl));
415
  auto *TD = new (C, DC) FunctionTemplateDecl(C, DC, L, Name, Params, Decl);
416
  if (Invalid)
417
    TD->setInvalidDecl();
418
  return TD;
419
}
420

421
FunctionTemplateDecl *
422
FunctionTemplateDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) {
423
  return new (C, ID) FunctionTemplateDecl(C, nullptr, SourceLocation(),
424
                                          DeclarationName(), nullptr, nullptr);
425
}
426

427
RedeclarableTemplateDecl::CommonBase *
428
FunctionTemplateDecl::newCommon(ASTContext &C) const {
429
  auto *CommonPtr = new (C) Common;
430
  C.addDestruction(CommonPtr);
431
  return CommonPtr;
432
}
433

434
void FunctionTemplateDecl::LoadLazySpecializations() const {
435
  loadLazySpecializationsImpl();
436
}
437

438
llvm::FoldingSetVector<FunctionTemplateSpecializationInfo> &
439
FunctionTemplateDecl::getSpecializations() const {
440
  LoadLazySpecializations();
441
  return getCommonPtr()->Specializations;
442
}
443

444
FunctionDecl *
445
FunctionTemplateDecl::findSpecialization(ArrayRef<TemplateArgument> Args,
446
                                         void *&InsertPos) {
447
  return findSpecializationImpl(getSpecializations(), InsertPos, Args);
448
}
449

450
void FunctionTemplateDecl::addSpecialization(
451
      FunctionTemplateSpecializationInfo *Info, void *InsertPos) {
452
  addSpecializationImpl<FunctionTemplateDecl>(getSpecializations(), Info,
453
                                              InsertPos);
454
}
455

456
void FunctionTemplateDecl::mergePrevDecl(FunctionTemplateDecl *Prev) {
457
  using Base = RedeclarableTemplateDecl;
458

459
  // If we haven't created a common pointer yet, then it can just be created
460
  // with the usual method.
461
  if (!Base::Common)
462
    return;
463

464
  Common *ThisCommon = static_cast<Common *>(Base::Common);
465
  Common *PrevCommon = nullptr;
466
  SmallVector<FunctionTemplateDecl *, 8> PreviousDecls;
467
  for (; Prev; Prev = Prev->getPreviousDecl()) {
468
    if (Prev->Base::Common) {
469
      PrevCommon = static_cast<Common *>(Prev->Base::Common);
470
      break;
471
    }
472
    PreviousDecls.push_back(Prev);
473
  }
474

475
  // If the previous redecl chain hasn't created a common pointer yet, then just
476
  // use this common pointer.
477
  if (!PrevCommon) {
478
    for (auto *D : PreviousDecls)
479
      D->Base::Common = ThisCommon;
480
    return;
481
  }
482

483
  // Ensure we don't leak any important state.
484
  assert(ThisCommon->Specializations.size() == 0 &&
485
         "Can't merge incompatible declarations!");
486

487
  Base::Common = PrevCommon;
488
}
489

490
//===----------------------------------------------------------------------===//
491
// ClassTemplateDecl Implementation
492
//===----------------------------------------------------------------------===//
493

494
ClassTemplateDecl *ClassTemplateDecl::Create(ASTContext &C, DeclContext *DC,
495
                                             SourceLocation L,
496
                                             DeclarationName Name,
497
                                             TemplateParameterList *Params,
498
                                             NamedDecl *Decl) {
499
  bool Invalid = AdoptTemplateParameterList(Params, cast<DeclContext>(Decl));
500
  auto *TD = new (C, DC) ClassTemplateDecl(C, DC, L, Name, Params, Decl);
501
  if (Invalid)
502
    TD->setInvalidDecl();
503
  return TD;
504
}
505

506
ClassTemplateDecl *ClassTemplateDecl::CreateDeserialized(ASTContext &C,
507
                                                         GlobalDeclID ID) {
508
  return new (C, ID) ClassTemplateDecl(C, nullptr, SourceLocation(),
509
                                       DeclarationName(), nullptr, nullptr);
510
}
511

512
void ClassTemplateDecl::LoadLazySpecializations() const {
513
  loadLazySpecializationsImpl();
514
}
515

516
llvm::FoldingSetVector<ClassTemplateSpecializationDecl> &
517
ClassTemplateDecl::getSpecializations() const {
518
  LoadLazySpecializations();
519
  return getCommonPtr()->Specializations;
520
}
521

522
llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl> &
523
ClassTemplateDecl::getPartialSpecializations() const {
524
  LoadLazySpecializations();
525
  return getCommonPtr()->PartialSpecializations;
526
}
527

528
RedeclarableTemplateDecl::CommonBase *
529
ClassTemplateDecl::newCommon(ASTContext &C) const {
530
  auto *CommonPtr = new (C) Common;
531
  C.addDestruction(CommonPtr);
532
  return CommonPtr;
533
}
534

535
ClassTemplateSpecializationDecl *
536
ClassTemplateDecl::findSpecialization(ArrayRef<TemplateArgument> Args,
537
                                      void *&InsertPos) {
538
  return findSpecializationImpl(getSpecializations(), InsertPos, Args);
539
}
540

541
void ClassTemplateDecl::AddSpecialization(ClassTemplateSpecializationDecl *D,
542
                                          void *InsertPos) {
543
  addSpecializationImpl<ClassTemplateDecl>(getSpecializations(), D, InsertPos);
544
}
545

546
ClassTemplatePartialSpecializationDecl *
547
ClassTemplateDecl::findPartialSpecialization(
548
    ArrayRef<TemplateArgument> Args,
549
    TemplateParameterList *TPL, void *&InsertPos) {
550
  return findSpecializationImpl(getPartialSpecializations(), InsertPos, Args,
551
                                TPL);
552
}
553

554
void ClassTemplatePartialSpecializationDecl::Profile(
555
    llvm::FoldingSetNodeID &ID, ArrayRef<TemplateArgument> TemplateArgs,
556
    TemplateParameterList *TPL, const ASTContext &Context) {
557
  ID.AddInteger(TemplateArgs.size());
558
  for (const TemplateArgument &TemplateArg : TemplateArgs)
559
    TemplateArg.Profile(ID, Context);
560
  TPL->Profile(ID, Context);
561
}
562

563
void ClassTemplateDecl::AddPartialSpecialization(
564
                                      ClassTemplatePartialSpecializationDecl *D,
565
                                      void *InsertPos) {
566
  if (InsertPos)
567
    getPartialSpecializations().InsertNode(D, InsertPos);
568
  else {
569
    ClassTemplatePartialSpecializationDecl *Existing
570
      = getPartialSpecializations().GetOrInsertNode(D);
571
    (void)Existing;
572
    assert(Existing->isCanonicalDecl() && "Non-canonical specialization?");
573
  }
574

575
  if (ASTMutationListener *L = getASTMutationListener())
576
    L->AddedCXXTemplateSpecialization(this, D);
577
}
578

579
void ClassTemplateDecl::getPartialSpecializations(
580
    SmallVectorImpl<ClassTemplatePartialSpecializationDecl *> &PS) const {
581
  llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl> &PartialSpecs
582
    = getPartialSpecializations();
583
  PS.clear();
584
  PS.reserve(PartialSpecs.size());
585
  for (ClassTemplatePartialSpecializationDecl &P : PartialSpecs)
586
    PS.push_back(P.getMostRecentDecl());
587
}
588

589
ClassTemplatePartialSpecializationDecl *
590
ClassTemplateDecl::findPartialSpecialization(QualType T) {
591
  ASTContext &Context = getASTContext();
592
  for (ClassTemplatePartialSpecializationDecl &P :
593
       getPartialSpecializations()) {
594
    if (Context.hasSameType(P.getInjectedSpecializationType(), T))
595
      return P.getMostRecentDecl();
596
  }
597

598
  return nullptr;
599
}
600

601
ClassTemplatePartialSpecializationDecl *
602
ClassTemplateDecl::findPartialSpecInstantiatedFromMember(
603
                                    ClassTemplatePartialSpecializationDecl *D) {
604
  Decl *DCanon = D->getCanonicalDecl();
605
  for (ClassTemplatePartialSpecializationDecl &P : getPartialSpecializations()) {
606
    if (P.getInstantiatedFromMember()->getCanonicalDecl() == DCanon)
607
      return P.getMostRecentDecl();
608
  }
609

610
  return nullptr;
611
}
612

613
QualType
614
ClassTemplateDecl::getInjectedClassNameSpecialization() {
615
  Common *CommonPtr = getCommonPtr();
616
  if (!CommonPtr->InjectedClassNameType.isNull())
617
    return CommonPtr->InjectedClassNameType;
618

619
  // C++0x [temp.dep.type]p2:
620
  //  The template argument list of a primary template is a template argument
621
  //  list in which the nth template argument has the value of the nth template
622
  //  parameter of the class template. If the nth template parameter is a
623
  //  template parameter pack (14.5.3), the nth template argument is a pack
624
  //  expansion (14.5.3) whose pattern is the name of the template parameter
625
  //  pack.
626
  ASTContext &Context = getASTContext();
627
  TemplateParameterList *Params = getTemplateParameters();
628
  SmallVector<TemplateArgument, 16> TemplateArgs;
629
  Context.getInjectedTemplateArgs(Params, TemplateArgs);
630
  TemplateName Name = Context.getQualifiedTemplateName(
631
      /*NNS=*/nullptr, /*TemplateKeyword=*/false, TemplateName(this));
632
  CommonPtr->InjectedClassNameType =
633
      Context.getTemplateSpecializationType(Name, TemplateArgs);
634
  return CommonPtr->InjectedClassNameType;
635
}
636

637
//===----------------------------------------------------------------------===//
638
// TemplateTypeParm Allocation/Deallocation Method Implementations
639
//===----------------------------------------------------------------------===//
640

641
TemplateTypeParmDecl *TemplateTypeParmDecl::Create(
642
    const ASTContext &C, DeclContext *DC, SourceLocation KeyLoc,
643
    SourceLocation NameLoc, unsigned D, unsigned P, IdentifierInfo *Id,
644
    bool Typename, bool ParameterPack, bool HasTypeConstraint,
645
    std::optional<unsigned> NumExpanded) {
646
  auto *TTPDecl =
647
      new (C, DC,
648
           additionalSizeToAlloc<TypeConstraint>(HasTypeConstraint ? 1 : 0))
649
      TemplateTypeParmDecl(DC, KeyLoc, NameLoc, Id, Typename,
650
                           HasTypeConstraint, NumExpanded);
651
  QualType TTPType = C.getTemplateTypeParmType(D, P, ParameterPack, TTPDecl);
652
  TTPDecl->setTypeForDecl(TTPType.getTypePtr());
653
  return TTPDecl;
654
}
655

656
TemplateTypeParmDecl *
657
TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, GlobalDeclID ID) {
658
  return new (C, ID)
659
      TemplateTypeParmDecl(nullptr, SourceLocation(), SourceLocation(), nullptr,
660
                           false, false, std::nullopt);
661
}
662

663
TemplateTypeParmDecl *
664
TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, GlobalDeclID ID,
665
                                         bool HasTypeConstraint) {
666
  return new (C, ID,
667
              additionalSizeToAlloc<TypeConstraint>(HasTypeConstraint ? 1 : 0))
668
      TemplateTypeParmDecl(nullptr, SourceLocation(), SourceLocation(), nullptr,
669
                           false, HasTypeConstraint, std::nullopt);
670
}
671

672
SourceLocation TemplateTypeParmDecl::getDefaultArgumentLoc() const {
673
  return hasDefaultArgument() ? getDefaultArgument().getLocation()
674
                              : SourceLocation();
675
}
676

677
SourceRange TemplateTypeParmDecl::getSourceRange() const {
678
  if (hasDefaultArgument() && !defaultArgumentWasInherited())
679
    return SourceRange(getBeginLoc(),
680
                       getDefaultArgument().getSourceRange().getEnd());
681
  // TypeDecl::getSourceRange returns a range containing name location, which is
682
  // wrong for unnamed template parameters. e.g:
683
  // it will return <[[typename>]] instead of <[[typename]]>
684
  if (getDeclName().isEmpty())
685
    return SourceRange(getBeginLoc());
686
  return TypeDecl::getSourceRange();
687
}
688

689
void TemplateTypeParmDecl::setDefaultArgument(
690
    const ASTContext &C, const TemplateArgumentLoc &DefArg) {
691
  if (DefArg.getArgument().isNull())
692
    DefaultArgument.set(nullptr);
693
  else
694
    DefaultArgument.set(new (C) TemplateArgumentLoc(DefArg));
695
}
696

697
unsigned TemplateTypeParmDecl::getDepth() const {
698
  return getTypeForDecl()->castAs<TemplateTypeParmType>()->getDepth();
699
}
700

701
unsigned TemplateTypeParmDecl::getIndex() const {
702
  return getTypeForDecl()->castAs<TemplateTypeParmType>()->getIndex();
703
}
704

705
bool TemplateTypeParmDecl::isParameterPack() const {
706
  return getTypeForDecl()->castAs<TemplateTypeParmType>()->isParameterPack();
707
}
708

709
void TemplateTypeParmDecl::setTypeConstraint(
710
    ConceptReference *Loc, Expr *ImmediatelyDeclaredConstraint) {
711
  assert(HasTypeConstraint &&
712
         "HasTypeConstraint=true must be passed at construction in order to "
713
         "call setTypeConstraint");
714
  assert(!TypeConstraintInitialized &&
715
         "TypeConstraint was already initialized!");
716
  new (getTrailingObjects<TypeConstraint>())
717
      TypeConstraint(Loc, ImmediatelyDeclaredConstraint);
718
  TypeConstraintInitialized = true;
719
}
720

721
//===----------------------------------------------------------------------===//
722
// NonTypeTemplateParmDecl Method Implementations
723
//===----------------------------------------------------------------------===//
724

725
NonTypeTemplateParmDecl::NonTypeTemplateParmDecl(
726
    DeclContext *DC, SourceLocation StartLoc, SourceLocation IdLoc, unsigned D,
727
    unsigned P, const IdentifierInfo *Id, QualType T, TypeSourceInfo *TInfo,
728
    ArrayRef<QualType> ExpandedTypes, ArrayRef<TypeSourceInfo *> ExpandedTInfos)
729
    : DeclaratorDecl(NonTypeTemplateParm, DC, IdLoc, Id, T, TInfo, StartLoc),
730
      TemplateParmPosition(D, P), ParameterPack(true),
731
      ExpandedParameterPack(true), NumExpandedTypes(ExpandedTypes.size()) {
732
  if (!ExpandedTypes.empty() && !ExpandedTInfos.empty()) {
733
    auto TypesAndInfos =
734
        getTrailingObjects<std::pair<QualType, TypeSourceInfo *>>();
735
    for (unsigned I = 0; I != NumExpandedTypes; ++I) {
736
      new (&TypesAndInfos[I].first) QualType(ExpandedTypes[I]);
737
      TypesAndInfos[I].second = ExpandedTInfos[I];
738
    }
739
  }
740
}
741

742
NonTypeTemplateParmDecl *NonTypeTemplateParmDecl::Create(
743
    const ASTContext &C, DeclContext *DC, SourceLocation StartLoc,
744
    SourceLocation IdLoc, unsigned D, unsigned P, const IdentifierInfo *Id,
745
    QualType T, bool ParameterPack, TypeSourceInfo *TInfo) {
746
  AutoType *AT =
747
      C.getLangOpts().CPlusPlus20 ? T->getContainedAutoType() : nullptr;
748
  return new (C, DC,
749
              additionalSizeToAlloc<std::pair<QualType, TypeSourceInfo *>,
750
                                    Expr *>(0,
751
                                            AT && AT->isConstrained() ? 1 : 0))
752
      NonTypeTemplateParmDecl(DC, StartLoc, IdLoc, D, P, Id, T, ParameterPack,
753
                              TInfo);
754
}
755

756
NonTypeTemplateParmDecl *NonTypeTemplateParmDecl::Create(
757
    const ASTContext &C, DeclContext *DC, SourceLocation StartLoc,
758
    SourceLocation IdLoc, unsigned D, unsigned P, const IdentifierInfo *Id,
759
    QualType T, TypeSourceInfo *TInfo, ArrayRef<QualType> ExpandedTypes,
760
    ArrayRef<TypeSourceInfo *> ExpandedTInfos) {
761
  AutoType *AT = TInfo->getType()->getContainedAutoType();
762
  return new (C, DC,
763
              additionalSizeToAlloc<std::pair<QualType, TypeSourceInfo *>,
764
                                    Expr *>(
765
                  ExpandedTypes.size(), AT && AT->isConstrained() ? 1 : 0))
766
      NonTypeTemplateParmDecl(DC, StartLoc, IdLoc, D, P, Id, T, TInfo,
767
                              ExpandedTypes, ExpandedTInfos);
768
}
769

770
NonTypeTemplateParmDecl *
771
NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID,
772
                                            bool HasTypeConstraint) {
773
  return new (C, ID, additionalSizeToAlloc<std::pair<QualType,
774
                                                     TypeSourceInfo *>,
775
                                           Expr *>(0,
776
                                                   HasTypeConstraint ? 1 : 0))
777
          NonTypeTemplateParmDecl(nullptr, SourceLocation(), SourceLocation(),
778
                                  0, 0, nullptr, QualType(), false, nullptr);
779
}
780

781
NonTypeTemplateParmDecl *
782
NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID,
783
                                            unsigned NumExpandedTypes,
784
                                            bool HasTypeConstraint) {
785
  auto *NTTP =
786
      new (C, ID,
787
           additionalSizeToAlloc<std::pair<QualType, TypeSourceInfo *>, Expr *>(
788
               NumExpandedTypes, HasTypeConstraint ? 1 : 0))
789
          NonTypeTemplateParmDecl(nullptr, SourceLocation(), SourceLocation(),
790
                                  0, 0, nullptr, QualType(), nullptr,
791
                                  std::nullopt, std::nullopt);
792
  NTTP->NumExpandedTypes = NumExpandedTypes;
793
  return NTTP;
794
}
795

796
SourceRange NonTypeTemplateParmDecl::getSourceRange() const {
797
  if (hasDefaultArgument() && !defaultArgumentWasInherited())
798
    return SourceRange(getOuterLocStart(),
799
                       getDefaultArgument().getSourceRange().getEnd());
800
  return DeclaratorDecl::getSourceRange();
801
}
802

803
SourceLocation NonTypeTemplateParmDecl::getDefaultArgumentLoc() const {
804
  return hasDefaultArgument() ? getDefaultArgument().getSourceRange().getBegin()
805
                              : SourceLocation();
806
}
807

808
void NonTypeTemplateParmDecl::setDefaultArgument(
809
    const ASTContext &C, const TemplateArgumentLoc &DefArg) {
810
  if (DefArg.getArgument().isNull())
811
    DefaultArgument.set(nullptr);
812
  else
813
    DefaultArgument.set(new (C) TemplateArgumentLoc(DefArg));
814
}
815

816
//===----------------------------------------------------------------------===//
817
// TemplateTemplateParmDecl Method Implementations
818
//===----------------------------------------------------------------------===//
819

820
void TemplateTemplateParmDecl::anchor() {}
821

822
TemplateTemplateParmDecl::TemplateTemplateParmDecl(
823
    DeclContext *DC, SourceLocation L, unsigned D, unsigned P,
824
    IdentifierInfo *Id, bool Typename, TemplateParameterList *Params,
825
    ArrayRef<TemplateParameterList *> Expansions)
826
    : TemplateDecl(TemplateTemplateParm, DC, L, Id, Params),
827
      TemplateParmPosition(D, P), Typename(Typename), ParameterPack(true),
828
      ExpandedParameterPack(true), NumExpandedParams(Expansions.size()) {
829
  if (!Expansions.empty())
830
    std::uninitialized_copy(Expansions.begin(), Expansions.end(),
831
                            getTrailingObjects<TemplateParameterList *>());
832
}
833

834
TemplateTemplateParmDecl *
835
TemplateTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
836
                                 SourceLocation L, unsigned D, unsigned P,
837
                                 bool ParameterPack, IdentifierInfo *Id,
838
                                 bool Typename, TemplateParameterList *Params) {
839
  return new (C, DC) TemplateTemplateParmDecl(DC, L, D, P, ParameterPack, Id,
840
                                              Typename, Params);
841
}
842

843
TemplateTemplateParmDecl *
844
TemplateTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
845
                                 SourceLocation L, unsigned D, unsigned P,
846
                                 IdentifierInfo *Id, bool Typename,
847
                                 TemplateParameterList *Params,
848
                                 ArrayRef<TemplateParameterList *> Expansions) {
849
  return new (C, DC,
850
              additionalSizeToAlloc<TemplateParameterList *>(Expansions.size()))
851
      TemplateTemplateParmDecl(DC, L, D, P, Id, Typename, Params, Expansions);
852
}
853

854
TemplateTemplateParmDecl *
855
TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) {
856
  return new (C, ID) TemplateTemplateParmDecl(nullptr, SourceLocation(), 0, 0,
857
                                              false, nullptr, false, nullptr);
858
}
859

860
TemplateTemplateParmDecl *
861
TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID,
862
                                             unsigned NumExpansions) {
863
  auto *TTP =
864
      new (C, ID, additionalSizeToAlloc<TemplateParameterList *>(NumExpansions))
865
          TemplateTemplateParmDecl(nullptr, SourceLocation(), 0, 0, nullptr,
866
                                   false, nullptr, std::nullopt);
867
  TTP->NumExpandedParams = NumExpansions;
868
  return TTP;
869
}
870

871
SourceLocation TemplateTemplateParmDecl::getDefaultArgumentLoc() const {
872
  return hasDefaultArgument() ? getDefaultArgument().getLocation()
873
                              : SourceLocation();
874
}
875

876
void TemplateTemplateParmDecl::setDefaultArgument(
877
    const ASTContext &C, const TemplateArgumentLoc &DefArg) {
878
  if (DefArg.getArgument().isNull())
879
    DefaultArgument.set(nullptr);
880
  else
881
    DefaultArgument.set(new (C) TemplateArgumentLoc(DefArg));
882
}
883

884
//===----------------------------------------------------------------------===//
885
// TemplateArgumentList Implementation
886
//===----------------------------------------------------------------------===//
887
TemplateArgumentList::TemplateArgumentList(ArrayRef<TemplateArgument> Args)
888
    : NumArguments(Args.size()) {
889
  std::uninitialized_copy(Args.begin(), Args.end(),
890
                          getTrailingObjects<TemplateArgument>());
891
}
892

893
TemplateArgumentList *
894
TemplateArgumentList::CreateCopy(ASTContext &Context,
895
                                 ArrayRef<TemplateArgument> Args) {
896
  void *Mem = Context.Allocate(totalSizeToAlloc<TemplateArgument>(Args.size()));
897
  return new (Mem) TemplateArgumentList(Args);
898
}
899

900
FunctionTemplateSpecializationInfo *FunctionTemplateSpecializationInfo::Create(
901
    ASTContext &C, FunctionDecl *FD, FunctionTemplateDecl *Template,
902
    TemplateSpecializationKind TSK, TemplateArgumentList *TemplateArgs,
903
    const TemplateArgumentListInfo *TemplateArgsAsWritten, SourceLocation POI,
904
    MemberSpecializationInfo *MSInfo) {
905
  const ASTTemplateArgumentListInfo *ArgsAsWritten = nullptr;
906
  if (TemplateArgsAsWritten)
907
    ArgsAsWritten = ASTTemplateArgumentListInfo::Create(C,
908
                                                        *TemplateArgsAsWritten);
909

910
  void *Mem =
911
      C.Allocate(totalSizeToAlloc<MemberSpecializationInfo *>(MSInfo ? 1 : 0));
912
  return new (Mem) FunctionTemplateSpecializationInfo(
913
      FD, Template, TSK, TemplateArgs, ArgsAsWritten, POI, MSInfo);
914
}
915

916
//===----------------------------------------------------------------------===//
917
// ClassTemplateSpecializationDecl Implementation
918
//===----------------------------------------------------------------------===//
919

920
ClassTemplateSpecializationDecl::
921
ClassTemplateSpecializationDecl(ASTContext &Context, Kind DK, TagKind TK,
922
                                DeclContext *DC, SourceLocation StartLoc,
923
                                SourceLocation IdLoc,
924
                                ClassTemplateDecl *SpecializedTemplate,
925
                                ArrayRef<TemplateArgument> Args,
926
                                ClassTemplateSpecializationDecl *PrevDecl)
927
    : CXXRecordDecl(DK, TK, Context, DC, StartLoc, IdLoc,
928
                    SpecializedTemplate->getIdentifier(), PrevDecl),
929
    SpecializedTemplate(SpecializedTemplate),
930
    TemplateArgs(TemplateArgumentList::CreateCopy(Context, Args)),
931
    SpecializationKind(TSK_Undeclared) {
932
}
933

934
ClassTemplateSpecializationDecl::ClassTemplateSpecializationDecl(ASTContext &C,
935
                                                                 Kind DK)
936
    : CXXRecordDecl(DK, TagTypeKind::Struct, C, nullptr, SourceLocation(),
937
                    SourceLocation(), nullptr, nullptr),
938
      SpecializationKind(TSK_Undeclared) {}
939

940
ClassTemplateSpecializationDecl *
941
ClassTemplateSpecializationDecl::Create(ASTContext &Context, TagKind TK,
942
                                        DeclContext *DC,
943
                                        SourceLocation StartLoc,
944
                                        SourceLocation IdLoc,
945
                                        ClassTemplateDecl *SpecializedTemplate,
946
                                        ArrayRef<TemplateArgument> Args,
947
                                   ClassTemplateSpecializationDecl *PrevDecl) {
948
  auto *Result =
949
      new (Context, DC) ClassTemplateSpecializationDecl(
950
          Context, ClassTemplateSpecialization, TK, DC, StartLoc, IdLoc,
951
          SpecializedTemplate, Args, PrevDecl);
952
  Result->setMayHaveOutOfDateDef(false);
953

954
  // If the template decl is incomplete, copy the external lexical storage from
955
  // the base template. This allows instantiations of incomplete types to
956
  // complete using the external AST if the template's declaration came from an
957
  // external AST.
958
  if (!SpecializedTemplate->getTemplatedDecl()->isCompleteDefinition())
959
    Result->setHasExternalLexicalStorage(
960
      SpecializedTemplate->getTemplatedDecl()->hasExternalLexicalStorage());
961

962
  Context.getTypeDeclType(Result, PrevDecl);
963
  return Result;
964
}
965

966
ClassTemplateSpecializationDecl *
967
ClassTemplateSpecializationDecl::CreateDeserialized(ASTContext &C,
968
                                                    GlobalDeclID ID) {
969
  auto *Result =
970
    new (C, ID) ClassTemplateSpecializationDecl(C, ClassTemplateSpecialization);
971
  Result->setMayHaveOutOfDateDef(false);
972
  return Result;
973
}
974

975
void ClassTemplateSpecializationDecl::getNameForDiagnostic(
976
    raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const {
977
  NamedDecl::getNameForDiagnostic(OS, Policy, Qualified);
978

979
  const auto *PS = dyn_cast<ClassTemplatePartialSpecializationDecl>(this);
980
  if (const ASTTemplateArgumentListInfo *ArgsAsWritten =
981
          PS ? PS->getTemplateArgsAsWritten() : nullptr) {
982
    printTemplateArgumentList(
983
        OS, ArgsAsWritten->arguments(), Policy,
984
        getSpecializedTemplate()->getTemplateParameters());
985
  } else {
986
    const TemplateArgumentList &TemplateArgs = getTemplateArgs();
987
    printTemplateArgumentList(
988
        OS, TemplateArgs.asArray(), Policy,
989
        getSpecializedTemplate()->getTemplateParameters());
990
  }
991
}
992

993
ClassTemplateDecl *
994
ClassTemplateSpecializationDecl::getSpecializedTemplate() const {
995
  if (const auto *PartialSpec =
996
          SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
997
    return PartialSpec->PartialSpecialization->getSpecializedTemplate();
998
  return SpecializedTemplate.get<ClassTemplateDecl*>();
999
}
1000

1001
SourceRange
1002
ClassTemplateSpecializationDecl::getSourceRange() const {
1003
  switch (getSpecializationKind()) {
1004
  case TSK_Undeclared:
1005
  case TSK_ImplicitInstantiation: {
1006
    llvm::PointerUnion<ClassTemplateDecl *,
1007
                       ClassTemplatePartialSpecializationDecl *>
1008
        Pattern = getSpecializedTemplateOrPartial();
1009
    assert(!Pattern.isNull() &&
1010
           "Class template specialization without pattern?");
1011
    if (const auto *CTPSD =
1012
            Pattern.dyn_cast<ClassTemplatePartialSpecializationDecl *>())
1013
      return CTPSD->getSourceRange();
1014
    return Pattern.get<ClassTemplateDecl *>()->getSourceRange();
1015
  }
1016
  case TSK_ExplicitSpecialization: {
1017
    SourceRange Range = CXXRecordDecl::getSourceRange();
1018
    if (const ASTTemplateArgumentListInfo *Args = getTemplateArgsAsWritten();
1019
        !isThisDeclarationADefinition() && Args)
1020
      Range.setEnd(Args->getRAngleLoc());
1021
    return Range;
1022
  }
1023
  case TSK_ExplicitInstantiationDeclaration:
1024
  case TSK_ExplicitInstantiationDefinition: {
1025
    SourceRange Range = CXXRecordDecl::getSourceRange();
1026
    if (SourceLocation ExternKW = getExternKeywordLoc(); ExternKW.isValid())
1027
      Range.setBegin(ExternKW);
1028
    else if (SourceLocation TemplateKW = getTemplateKeywordLoc();
1029
             TemplateKW.isValid())
1030
      Range.setBegin(TemplateKW);
1031
    if (const ASTTemplateArgumentListInfo *Args = getTemplateArgsAsWritten())
1032
      Range.setEnd(Args->getRAngleLoc());
1033
    return Range;
1034
  }
1035
  }
1036
  llvm_unreachable("unhandled template specialization kind");
1037
}
1038

1039
void ClassTemplateSpecializationDecl::setExternKeywordLoc(SourceLocation Loc) {
1040
  auto *Info = ExplicitInfo.dyn_cast<ExplicitInstantiationInfo *>();
1041
  if (!Info) {
1042
    // Don't allocate if the location is invalid.
1043
    if (Loc.isInvalid())
1044
      return;
1045
    Info = new (getASTContext()) ExplicitInstantiationInfo;
1046
    Info->TemplateArgsAsWritten = getTemplateArgsAsWritten();
1047
    ExplicitInfo = Info;
1048
  }
1049
  Info->ExternKeywordLoc = Loc;
1050
}
1051

1052
void ClassTemplateSpecializationDecl::setTemplateKeywordLoc(
1053
    SourceLocation Loc) {
1054
  auto *Info = ExplicitInfo.dyn_cast<ExplicitInstantiationInfo *>();
1055
  if (!Info) {
1056
    // Don't allocate if the location is invalid.
1057
    if (Loc.isInvalid())
1058
      return;
1059
    Info = new (getASTContext()) ExplicitInstantiationInfo;
1060
    Info->TemplateArgsAsWritten = getTemplateArgsAsWritten();
1061
    ExplicitInfo = Info;
1062
  }
1063
  Info->TemplateKeywordLoc = Loc;
1064
}
1065

1066
//===----------------------------------------------------------------------===//
1067
// ConceptDecl Implementation
1068
//===----------------------------------------------------------------------===//
1069
ConceptDecl *ConceptDecl::Create(ASTContext &C, DeclContext *DC,
1070
                                 SourceLocation L, DeclarationName Name,
1071
                                 TemplateParameterList *Params,
1072
                                 Expr *ConstraintExpr) {
1073
  bool Invalid = AdoptTemplateParameterList(Params, DC);
1074
  auto *TD = new (C, DC) ConceptDecl(DC, L, Name, Params, ConstraintExpr);
1075
  if (Invalid)
1076
    TD->setInvalidDecl();
1077
  return TD;
1078
}
1079

1080
ConceptDecl *ConceptDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) {
1081
  ConceptDecl *Result = new (C, ID) ConceptDecl(nullptr, SourceLocation(),
1082
                                                DeclarationName(),
1083
                                                nullptr, nullptr);
1084

1085
  return Result;
1086
}
1087

1088
//===----------------------------------------------------------------------===//
1089
// ImplicitConceptSpecializationDecl Implementation
1090
//===----------------------------------------------------------------------===//
1091
ImplicitConceptSpecializationDecl::ImplicitConceptSpecializationDecl(
1092
    DeclContext *DC, SourceLocation SL,
1093
    ArrayRef<TemplateArgument> ConvertedArgs)
1094
    : Decl(ImplicitConceptSpecialization, DC, SL),
1095
      NumTemplateArgs(ConvertedArgs.size()) {
1096
  setTemplateArguments(ConvertedArgs);
1097
}
1098

1099
ImplicitConceptSpecializationDecl::ImplicitConceptSpecializationDecl(
1100
    EmptyShell Empty, unsigned NumTemplateArgs)
1101
    : Decl(ImplicitConceptSpecialization, Empty),
1102
      NumTemplateArgs(NumTemplateArgs) {}
1103

1104
ImplicitConceptSpecializationDecl *ImplicitConceptSpecializationDecl::Create(
1105
    const ASTContext &C, DeclContext *DC, SourceLocation SL,
1106
    ArrayRef<TemplateArgument> ConvertedArgs) {
1107
  return new (C, DC,
1108
              additionalSizeToAlloc<TemplateArgument>(ConvertedArgs.size()))
1109
      ImplicitConceptSpecializationDecl(DC, SL, ConvertedArgs);
1110
}
1111

1112
ImplicitConceptSpecializationDecl *
1113
ImplicitConceptSpecializationDecl::CreateDeserialized(
1114
    const ASTContext &C, GlobalDeclID ID, unsigned NumTemplateArgs) {
1115
  return new (C, ID, additionalSizeToAlloc<TemplateArgument>(NumTemplateArgs))
1116
      ImplicitConceptSpecializationDecl(EmptyShell{}, NumTemplateArgs);
1117
}
1118

1119
void ImplicitConceptSpecializationDecl::setTemplateArguments(
1120
    ArrayRef<TemplateArgument> Converted) {
1121
  assert(Converted.size() == NumTemplateArgs);
1122
  std::uninitialized_copy(Converted.begin(), Converted.end(),
1123
                          getTrailingObjects<TemplateArgument>());
1124
}
1125

1126
//===----------------------------------------------------------------------===//
1127
// ClassTemplatePartialSpecializationDecl Implementation
1128
//===----------------------------------------------------------------------===//
1129
void ClassTemplatePartialSpecializationDecl::anchor() {}
1130

1131
ClassTemplatePartialSpecializationDecl::ClassTemplatePartialSpecializationDecl(
1132
    ASTContext &Context, TagKind TK, DeclContext *DC, SourceLocation StartLoc,
1133
    SourceLocation IdLoc, TemplateParameterList *Params,
1134
    ClassTemplateDecl *SpecializedTemplate, ArrayRef<TemplateArgument> Args,
1135
    ClassTemplatePartialSpecializationDecl *PrevDecl)
1136
    : ClassTemplateSpecializationDecl(
1137
          Context, ClassTemplatePartialSpecialization, TK, DC, StartLoc, IdLoc,
1138
          SpecializedTemplate, Args, PrevDecl),
1139
      TemplateParams(Params), InstantiatedFromMember(nullptr, false) {
1140
  if (AdoptTemplateParameterList(Params, this))
1141
    setInvalidDecl();
1142
}
1143

1144
ClassTemplatePartialSpecializationDecl *
1145
ClassTemplatePartialSpecializationDecl::Create(
1146
    ASTContext &Context, TagKind TK, DeclContext *DC, SourceLocation StartLoc,
1147
    SourceLocation IdLoc, TemplateParameterList *Params,
1148
    ClassTemplateDecl *SpecializedTemplate, ArrayRef<TemplateArgument> Args,
1149
    QualType CanonInjectedType,
1150
    ClassTemplatePartialSpecializationDecl *PrevDecl) {
1151
  auto *Result = new (Context, DC) ClassTemplatePartialSpecializationDecl(
1152
      Context, TK, DC, StartLoc, IdLoc, Params, SpecializedTemplate, Args,
1153
      PrevDecl);
1154
  Result->setSpecializationKind(TSK_ExplicitSpecialization);
1155
  Result->setMayHaveOutOfDateDef(false);
1156

1157
  Context.getInjectedClassNameType(Result, CanonInjectedType);
1158
  return Result;
1159
}
1160

1161
ClassTemplatePartialSpecializationDecl *
1162
ClassTemplatePartialSpecializationDecl::CreateDeserialized(ASTContext &C,
1163
                                                           GlobalDeclID ID) {
1164
  auto *Result = new (C, ID) ClassTemplatePartialSpecializationDecl(C);
1165
  Result->setMayHaveOutOfDateDef(false);
1166
  return Result;
1167
}
1168

1169
SourceRange ClassTemplatePartialSpecializationDecl::getSourceRange() const {
1170
  if (const ClassTemplatePartialSpecializationDecl *MT =
1171
          getInstantiatedFromMember();
1172
      MT && !isMemberSpecialization())
1173
    return MT->getSourceRange();
1174
  SourceRange Range = ClassTemplateSpecializationDecl::getSourceRange();
1175
  if (const TemplateParameterList *TPL = getTemplateParameters();
1176
      TPL && !getNumTemplateParameterLists())
1177
    Range.setBegin(TPL->getTemplateLoc());
1178
  return Range;
1179
}
1180

1181
//===----------------------------------------------------------------------===//
1182
// FriendTemplateDecl Implementation
1183
//===----------------------------------------------------------------------===//
1184

1185
void FriendTemplateDecl::anchor() {}
1186

1187
FriendTemplateDecl *
1188
FriendTemplateDecl::Create(ASTContext &Context, DeclContext *DC,
1189
                           SourceLocation L,
1190
                           MutableArrayRef<TemplateParameterList *> Params,
1191
                           FriendUnion Friend, SourceLocation FLoc) {
1192
  TemplateParameterList **TPL = nullptr;
1193
  if (!Params.empty()) {
1194
    TPL = new (Context) TemplateParameterList *[Params.size()];
1195
    llvm::copy(Params, TPL);
1196
  }
1197
  return new (Context, DC)
1198
      FriendTemplateDecl(DC, L, TPL, Params.size(), Friend, FLoc);
1199
}
1200

1201
FriendTemplateDecl *FriendTemplateDecl::CreateDeserialized(ASTContext &C,
1202
                                                           GlobalDeclID ID) {
1203
  return new (C, ID) FriendTemplateDecl(EmptyShell());
1204
}
1205

1206
//===----------------------------------------------------------------------===//
1207
// TypeAliasTemplateDecl Implementation
1208
//===----------------------------------------------------------------------===//
1209

1210
TypeAliasTemplateDecl *
1211
TypeAliasTemplateDecl::Create(ASTContext &C, DeclContext *DC, SourceLocation L,
1212
                              DeclarationName Name,
1213
                              TemplateParameterList *Params, NamedDecl *Decl) {
1214
  bool Invalid = AdoptTemplateParameterList(Params, DC);
1215
  auto *TD = new (C, DC) TypeAliasTemplateDecl(C, DC, L, Name, Params, Decl);
1216
  if (Invalid)
1217
    TD->setInvalidDecl();
1218
  return TD;
1219
}
1220

1221
TypeAliasTemplateDecl *
1222
TypeAliasTemplateDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) {
1223
  return new (C, ID) TypeAliasTemplateDecl(C, nullptr, SourceLocation(),
1224
                                           DeclarationName(), nullptr, nullptr);
1225
}
1226

1227
RedeclarableTemplateDecl::CommonBase *
1228
TypeAliasTemplateDecl::newCommon(ASTContext &C) const {
1229
  auto *CommonPtr = new (C) Common;
1230
  C.addDestruction(CommonPtr);
1231
  return CommonPtr;
1232
}
1233

1234
//===----------------------------------------------------------------------===//
1235
// VarTemplateDecl Implementation
1236
//===----------------------------------------------------------------------===//
1237

1238
VarTemplateDecl *VarTemplateDecl::getDefinition() {
1239
  VarTemplateDecl *CurD = this;
1240
  while (CurD) {
1241
    if (CurD->isThisDeclarationADefinition())
1242
      return CurD;
1243
    CurD = CurD->getPreviousDecl();
1244
  }
1245
  return nullptr;
1246
}
1247

1248
VarTemplateDecl *VarTemplateDecl::Create(ASTContext &C, DeclContext *DC,
1249
                                         SourceLocation L, DeclarationName Name,
1250
                                         TemplateParameterList *Params,
1251
                                         VarDecl *Decl) {
1252
  bool Invalid = AdoptTemplateParameterList(Params, DC);
1253
  auto *TD = new (C, DC) VarTemplateDecl(C, DC, L, Name, Params, Decl);
1254
  if (Invalid)
1255
    TD->setInvalidDecl();
1256
  return TD;
1257
}
1258

1259
VarTemplateDecl *VarTemplateDecl::CreateDeserialized(ASTContext &C,
1260
                                                     GlobalDeclID ID) {
1261
  return new (C, ID) VarTemplateDecl(C, nullptr, SourceLocation(),
1262
                                     DeclarationName(), nullptr, nullptr);
1263
}
1264

1265
void VarTemplateDecl::LoadLazySpecializations() const {
1266
  loadLazySpecializationsImpl();
1267
}
1268

1269
llvm::FoldingSetVector<VarTemplateSpecializationDecl> &
1270
VarTemplateDecl::getSpecializations() const {
1271
  LoadLazySpecializations();
1272
  return getCommonPtr()->Specializations;
1273
}
1274

1275
llvm::FoldingSetVector<VarTemplatePartialSpecializationDecl> &
1276
VarTemplateDecl::getPartialSpecializations() const {
1277
  LoadLazySpecializations();
1278
  return getCommonPtr()->PartialSpecializations;
1279
}
1280

1281
RedeclarableTemplateDecl::CommonBase *
1282
VarTemplateDecl::newCommon(ASTContext &C) const {
1283
  auto *CommonPtr = new (C) Common;
1284
  C.addDestruction(CommonPtr);
1285
  return CommonPtr;
1286
}
1287

1288
VarTemplateSpecializationDecl *
1289
VarTemplateDecl::findSpecialization(ArrayRef<TemplateArgument> Args,
1290
                                    void *&InsertPos) {
1291
  return findSpecializationImpl(getSpecializations(), InsertPos, Args);
1292
}
1293

1294
void VarTemplateDecl::AddSpecialization(VarTemplateSpecializationDecl *D,
1295
                                        void *InsertPos) {
1296
  addSpecializationImpl<VarTemplateDecl>(getSpecializations(), D, InsertPos);
1297
}
1298

1299
VarTemplatePartialSpecializationDecl *
1300
VarTemplateDecl::findPartialSpecialization(ArrayRef<TemplateArgument> Args,
1301
     TemplateParameterList *TPL, void *&InsertPos) {
1302
  return findSpecializationImpl(getPartialSpecializations(), InsertPos, Args,
1303
                                TPL);
1304
}
1305

1306
void VarTemplatePartialSpecializationDecl::Profile(
1307
    llvm::FoldingSetNodeID &ID, ArrayRef<TemplateArgument> TemplateArgs,
1308
    TemplateParameterList *TPL, const ASTContext &Context) {
1309
  ID.AddInteger(TemplateArgs.size());
1310
  for (const TemplateArgument &TemplateArg : TemplateArgs)
1311
    TemplateArg.Profile(ID, Context);
1312
  TPL->Profile(ID, Context);
1313
}
1314

1315
void VarTemplateDecl::AddPartialSpecialization(
1316
    VarTemplatePartialSpecializationDecl *D, void *InsertPos) {
1317
  if (InsertPos)
1318
    getPartialSpecializations().InsertNode(D, InsertPos);
1319
  else {
1320
    VarTemplatePartialSpecializationDecl *Existing =
1321
        getPartialSpecializations().GetOrInsertNode(D);
1322
    (void)Existing;
1323
    assert(Existing->isCanonicalDecl() && "Non-canonical specialization?");
1324
  }
1325

1326
  if (ASTMutationListener *L = getASTMutationListener())
1327
    L->AddedCXXTemplateSpecialization(this, D);
1328
}
1329

1330
void VarTemplateDecl::getPartialSpecializations(
1331
    SmallVectorImpl<VarTemplatePartialSpecializationDecl *> &PS) const {
1332
  llvm::FoldingSetVector<VarTemplatePartialSpecializationDecl> &PartialSpecs =
1333
      getPartialSpecializations();
1334
  PS.clear();
1335
  PS.reserve(PartialSpecs.size());
1336
  for (VarTemplatePartialSpecializationDecl &P : PartialSpecs)
1337
    PS.push_back(P.getMostRecentDecl());
1338
}
1339

1340
VarTemplatePartialSpecializationDecl *
1341
VarTemplateDecl::findPartialSpecInstantiatedFromMember(
1342
    VarTemplatePartialSpecializationDecl *D) {
1343
  Decl *DCanon = D->getCanonicalDecl();
1344
  for (VarTemplatePartialSpecializationDecl &P : getPartialSpecializations()) {
1345
    if (P.getInstantiatedFromMember()->getCanonicalDecl() == DCanon)
1346
      return P.getMostRecentDecl();
1347
  }
1348

1349
  return nullptr;
1350
}
1351

1352
//===----------------------------------------------------------------------===//
1353
// VarTemplateSpecializationDecl Implementation
1354
//===----------------------------------------------------------------------===//
1355

1356
VarTemplateSpecializationDecl::VarTemplateSpecializationDecl(
1357
    Kind DK, ASTContext &Context, DeclContext *DC, SourceLocation StartLoc,
1358
    SourceLocation IdLoc, VarTemplateDecl *SpecializedTemplate, QualType T,
1359
    TypeSourceInfo *TInfo, StorageClass S, ArrayRef<TemplateArgument> Args)
1360
    : VarDecl(DK, Context, DC, StartLoc, IdLoc,
1361
              SpecializedTemplate->getIdentifier(), T, TInfo, S),
1362
      SpecializedTemplate(SpecializedTemplate),
1363
      TemplateArgs(TemplateArgumentList::CreateCopy(Context, Args)),
1364
      SpecializationKind(TSK_Undeclared), IsCompleteDefinition(false) {}
1365

1366
VarTemplateSpecializationDecl::VarTemplateSpecializationDecl(Kind DK,
1367
                                                             ASTContext &C)
1368
    : VarDecl(DK, C, nullptr, SourceLocation(), SourceLocation(), nullptr,
1369
              QualType(), nullptr, SC_None),
1370
      SpecializationKind(TSK_Undeclared), IsCompleteDefinition(false) {}
1371

1372
VarTemplateSpecializationDecl *VarTemplateSpecializationDecl::Create(
1373
    ASTContext &Context, DeclContext *DC, SourceLocation StartLoc,
1374
    SourceLocation IdLoc, VarTemplateDecl *SpecializedTemplate, QualType T,
1375
    TypeSourceInfo *TInfo, StorageClass S, ArrayRef<TemplateArgument> Args) {
1376
  return new (Context, DC) VarTemplateSpecializationDecl(
1377
      VarTemplateSpecialization, Context, DC, StartLoc, IdLoc,
1378
      SpecializedTemplate, T, TInfo, S, Args);
1379
}
1380

1381
VarTemplateSpecializationDecl *
1382
VarTemplateSpecializationDecl::CreateDeserialized(ASTContext &C,
1383
                                                  GlobalDeclID ID) {
1384
  return new (C, ID)
1385
      VarTemplateSpecializationDecl(VarTemplateSpecialization, C);
1386
}
1387

1388
void VarTemplateSpecializationDecl::getNameForDiagnostic(
1389
    raw_ostream &OS, const PrintingPolicy &Policy, bool Qualified) const {
1390
  NamedDecl::getNameForDiagnostic(OS, Policy, Qualified);
1391

1392
  const auto *PS = dyn_cast<VarTemplatePartialSpecializationDecl>(this);
1393
  if (const ASTTemplateArgumentListInfo *ArgsAsWritten =
1394
          PS ? PS->getTemplateArgsAsWritten() : nullptr) {
1395
    printTemplateArgumentList(
1396
        OS, ArgsAsWritten->arguments(), Policy,
1397
        getSpecializedTemplate()->getTemplateParameters());
1398
  } else {
1399
    const TemplateArgumentList &TemplateArgs = getTemplateArgs();
1400
    printTemplateArgumentList(
1401
        OS, TemplateArgs.asArray(), Policy,
1402
        getSpecializedTemplate()->getTemplateParameters());
1403
  }
1404
}
1405

1406
VarTemplateDecl *VarTemplateSpecializationDecl::getSpecializedTemplate() const {
1407
  if (const auto *PartialSpec =
1408
          SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization *>())
1409
    return PartialSpec->PartialSpecialization->getSpecializedTemplate();
1410
  return SpecializedTemplate.get<VarTemplateDecl *>();
1411
}
1412

1413
SourceRange VarTemplateSpecializationDecl::getSourceRange() const {
1414
  switch (getSpecializationKind()) {
1415
  case TSK_Undeclared:
1416
  case TSK_ImplicitInstantiation: {
1417
    llvm::PointerUnion<VarTemplateDecl *,
1418
                       VarTemplatePartialSpecializationDecl *>
1419
        Pattern = getSpecializedTemplateOrPartial();
1420
    assert(!Pattern.isNull() &&
1421
           "Variable template specialization without pattern?");
1422
    if (const auto *VTPSD =
1423
            Pattern.dyn_cast<VarTemplatePartialSpecializationDecl *>())
1424
      return VTPSD->getSourceRange();
1425
    VarTemplateDecl *VTD = Pattern.get<VarTemplateDecl *>();
1426
    if (hasInit()) {
1427
      if (VarTemplateDecl *Definition = VTD->getDefinition())
1428
        return Definition->getSourceRange();
1429
    }
1430
    return VTD->getCanonicalDecl()->getSourceRange();
1431
  }
1432
  case TSK_ExplicitSpecialization: {
1433
    SourceRange Range = VarDecl::getSourceRange();
1434
    if (const ASTTemplateArgumentListInfo *Args = getTemplateArgsAsWritten();
1435
        !hasInit() && Args)
1436
      Range.setEnd(Args->getRAngleLoc());
1437
    return Range;
1438
  }
1439
  case TSK_ExplicitInstantiationDeclaration:
1440
  case TSK_ExplicitInstantiationDefinition: {
1441
    SourceRange Range = VarDecl::getSourceRange();
1442
    if (SourceLocation ExternKW = getExternKeywordLoc(); ExternKW.isValid())
1443
      Range.setBegin(ExternKW);
1444
    else if (SourceLocation TemplateKW = getTemplateKeywordLoc();
1445
             TemplateKW.isValid())
1446
      Range.setBegin(TemplateKW);
1447
    if (const ASTTemplateArgumentListInfo *Args = getTemplateArgsAsWritten())
1448
      Range.setEnd(Args->getRAngleLoc());
1449
    return Range;
1450
  }
1451
  }
1452
  llvm_unreachable("unhandled template specialization kind");
1453
}
1454

1455
void VarTemplateSpecializationDecl::setExternKeywordLoc(SourceLocation Loc) {
1456
  auto *Info = ExplicitInfo.dyn_cast<ExplicitInstantiationInfo *>();
1457
  if (!Info) {
1458
    // Don't allocate if the location is invalid.
1459
    if (Loc.isInvalid())
1460
      return;
1461
    Info = new (getASTContext()) ExplicitInstantiationInfo;
1462
    Info->TemplateArgsAsWritten = getTemplateArgsAsWritten();
1463
    ExplicitInfo = Info;
1464
  }
1465
  Info->ExternKeywordLoc = Loc;
1466
}
1467

1468
void VarTemplateSpecializationDecl::setTemplateKeywordLoc(SourceLocation Loc) {
1469
  auto *Info = ExplicitInfo.dyn_cast<ExplicitInstantiationInfo *>();
1470
  if (!Info) {
1471
    // Don't allocate if the location is invalid.
1472
    if (Loc.isInvalid())
1473
      return;
1474
    Info = new (getASTContext()) ExplicitInstantiationInfo;
1475
    Info->TemplateArgsAsWritten = getTemplateArgsAsWritten();
1476
    ExplicitInfo = Info;
1477
  }
1478
  Info->TemplateKeywordLoc = Loc;
1479
}
1480

1481
//===----------------------------------------------------------------------===//
1482
// VarTemplatePartialSpecializationDecl Implementation
1483
//===----------------------------------------------------------------------===//
1484

1485
void VarTemplatePartialSpecializationDecl::anchor() {}
1486

1487
VarTemplatePartialSpecializationDecl::VarTemplatePartialSpecializationDecl(
1488
    ASTContext &Context, DeclContext *DC, SourceLocation StartLoc,
1489
    SourceLocation IdLoc, TemplateParameterList *Params,
1490
    VarTemplateDecl *SpecializedTemplate, QualType T, TypeSourceInfo *TInfo,
1491
    StorageClass S, ArrayRef<TemplateArgument> Args)
1492
    : VarTemplateSpecializationDecl(VarTemplatePartialSpecialization, Context,
1493
                                    DC, StartLoc, IdLoc, SpecializedTemplate, T,
1494
                                    TInfo, S, Args),
1495
      TemplateParams(Params), InstantiatedFromMember(nullptr, false) {
1496
  if (AdoptTemplateParameterList(Params, DC))
1497
    setInvalidDecl();
1498
}
1499

1500
VarTemplatePartialSpecializationDecl *
1501
VarTemplatePartialSpecializationDecl::Create(
1502
    ASTContext &Context, DeclContext *DC, SourceLocation StartLoc,
1503
    SourceLocation IdLoc, TemplateParameterList *Params,
1504
    VarTemplateDecl *SpecializedTemplate, QualType T, TypeSourceInfo *TInfo,
1505
    StorageClass S, ArrayRef<TemplateArgument> Args) {
1506
  auto *Result = new (Context, DC) VarTemplatePartialSpecializationDecl(
1507
      Context, DC, StartLoc, IdLoc, Params, SpecializedTemplate, T, TInfo, S,
1508
      Args);
1509
  Result->setSpecializationKind(TSK_ExplicitSpecialization);
1510
  return Result;
1511
}
1512

1513
VarTemplatePartialSpecializationDecl *
1514
VarTemplatePartialSpecializationDecl::CreateDeserialized(ASTContext &C,
1515
                                                         GlobalDeclID ID) {
1516
  return new (C, ID) VarTemplatePartialSpecializationDecl(C);
1517
}
1518

1519
SourceRange VarTemplatePartialSpecializationDecl::getSourceRange() const {
1520
  if (const VarTemplatePartialSpecializationDecl *MT =
1521
          getInstantiatedFromMember();
1522
      MT && !isMemberSpecialization())
1523
    return MT->getSourceRange();
1524
  SourceRange Range = VarTemplateSpecializationDecl::getSourceRange();
1525
  if (const TemplateParameterList *TPL = getTemplateParameters();
1526
      TPL && !getNumTemplateParameterLists())
1527
    Range.setBegin(TPL->getTemplateLoc());
1528
  return Range;
1529
}
1530

1531
static TemplateParameterList *
1532
createMakeIntegerSeqParameterList(const ASTContext &C, DeclContext *DC) {
1533
  // typename T
1534
  auto *T = TemplateTypeParmDecl::Create(
1535
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/1, /*Position=*/0,
1536
      /*Id=*/nullptr, /*Typename=*/true, /*ParameterPack=*/false,
1537
      /*HasTypeConstraint=*/false);
1538
  T->setImplicit(true);
1539

1540
  // T ...Ints
1541
  TypeSourceInfo *TI =
1542
      C.getTrivialTypeSourceInfo(QualType(T->getTypeForDecl(), 0));
1543
  auto *N = NonTypeTemplateParmDecl::Create(
1544
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/0, /*Position=*/1,
1545
      /*Id=*/nullptr, TI->getType(), /*ParameterPack=*/true, TI);
1546
  N->setImplicit(true);
1547

1548
  // <typename T, T ...Ints>
1549
  NamedDecl *P[2] = {T, N};
1550
  auto *TPL = TemplateParameterList::Create(
1551
      C, SourceLocation(), SourceLocation(), P, SourceLocation(), nullptr);
1552

1553
  // template <typename T, ...Ints> class IntSeq
1554
  auto *TemplateTemplateParm = TemplateTemplateParmDecl::Create(
1555
      C, DC, SourceLocation(), /*Depth=*/0, /*Position=*/0,
1556
      /*ParameterPack=*/false, /*Id=*/nullptr, /*Typename=*/false, TPL);
1557
  TemplateTemplateParm->setImplicit(true);
1558

1559
  // typename T
1560
  auto *TemplateTypeParm = TemplateTypeParmDecl::Create(
1561
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/0, /*Position=*/1,
1562
      /*Id=*/nullptr, /*Typename=*/true, /*ParameterPack=*/false,
1563
      /*HasTypeConstraint=*/false);
1564
  TemplateTypeParm->setImplicit(true);
1565

1566
  // T N
1567
  TypeSourceInfo *TInfo = C.getTrivialTypeSourceInfo(
1568
      QualType(TemplateTypeParm->getTypeForDecl(), 0));
1569
  auto *NonTypeTemplateParm = NonTypeTemplateParmDecl::Create(
1570
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/0, /*Position=*/2,
1571
      /*Id=*/nullptr, TInfo->getType(), /*ParameterPack=*/false, TInfo);
1572
  NamedDecl *Params[] = {TemplateTemplateParm, TemplateTypeParm,
1573
                         NonTypeTemplateParm};
1574

1575
  // template <template <typename T, T ...Ints> class IntSeq, typename T, T N>
1576
  return TemplateParameterList::Create(C, SourceLocation(), SourceLocation(),
1577
                                       Params, SourceLocation(), nullptr);
1578
}
1579

1580
static TemplateParameterList *
1581
createTypePackElementParameterList(const ASTContext &C, DeclContext *DC) {
1582
  // std::size_t Index
1583
  TypeSourceInfo *TInfo = C.getTrivialTypeSourceInfo(C.getSizeType());
1584
  auto *Index = NonTypeTemplateParmDecl::Create(
1585
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/0, /*Position=*/0,
1586
      /*Id=*/nullptr, TInfo->getType(), /*ParameterPack=*/false, TInfo);
1587

1588
  // typename ...T
1589
  auto *Ts = TemplateTypeParmDecl::Create(
1590
      C, DC, SourceLocation(), SourceLocation(), /*Depth=*/0, /*Position=*/1,
1591
      /*Id=*/nullptr, /*Typename=*/true, /*ParameterPack=*/true,
1592
      /*HasTypeConstraint=*/false);
1593
  Ts->setImplicit(true);
1594

1595
  // template <std::size_t Index, typename ...T>
1596
  NamedDecl *Params[] = {Index, Ts};
1597
  return TemplateParameterList::Create(C, SourceLocation(), SourceLocation(),
1598
                                       llvm::ArrayRef(Params), SourceLocation(),
1599
                                       nullptr);
1600
}
1601

1602
static TemplateParameterList *createBuiltinTemplateParameterList(
1603
    const ASTContext &C, DeclContext *DC, BuiltinTemplateKind BTK) {
1604
  switch (BTK) {
1605
  case BTK__make_integer_seq:
1606
    return createMakeIntegerSeqParameterList(C, DC);
1607
  case BTK__type_pack_element:
1608
    return createTypePackElementParameterList(C, DC);
1609
  }
1610

1611
  llvm_unreachable("unhandled BuiltinTemplateKind!");
1612
}
1613

1614
void BuiltinTemplateDecl::anchor() {}
1615

1616
BuiltinTemplateDecl::BuiltinTemplateDecl(const ASTContext &C, DeclContext *DC,
1617
                                         DeclarationName Name,
1618
                                         BuiltinTemplateKind BTK)
1619
    : TemplateDecl(BuiltinTemplate, DC, SourceLocation(), Name,
1620
                   createBuiltinTemplateParameterList(C, DC, BTK)),
1621
      BTK(BTK) {}
1622

1623
TemplateParamObjectDecl *TemplateParamObjectDecl::Create(const ASTContext &C,
1624
                                                         QualType T,
1625
                                                         const APValue &V) {
1626
  DeclContext *DC = C.getTranslationUnitDecl();
1627
  auto *TPOD = new (C, DC) TemplateParamObjectDecl(DC, T, V);
1628
  C.addDestruction(&TPOD->Value);
1629
  return TPOD;
1630
}
1631

1632
TemplateParamObjectDecl *
1633
TemplateParamObjectDecl::CreateDeserialized(ASTContext &C, GlobalDeclID ID) {
1634
  auto *TPOD = new (C, ID) TemplateParamObjectDecl(nullptr, QualType(), APValue());
1635
  C.addDestruction(&TPOD->Value);
1636
  return TPOD;
1637
}
1638

1639
void TemplateParamObjectDecl::printName(llvm::raw_ostream &OS,
1640
                                        const PrintingPolicy &Policy) const {
1641
  OS << "<template param ";
1642
  printAsExpr(OS, Policy);
1643
  OS << ">";
1644
}
1645

1646
void TemplateParamObjectDecl::printAsExpr(llvm::raw_ostream &OS) const {
1647
  printAsExpr(OS, getASTContext().getPrintingPolicy());
1648
}
1649

1650
void TemplateParamObjectDecl::printAsExpr(llvm::raw_ostream &OS,
1651
                                          const PrintingPolicy &Policy) const {
1652
  getType().getUnqualifiedType().print(OS, Policy);
1653
  printAsInit(OS, Policy);
1654
}
1655

1656
void TemplateParamObjectDecl::printAsInit(llvm::raw_ostream &OS) const {
1657
  printAsInit(OS, getASTContext().getPrintingPolicy());
1658
}
1659

1660
void TemplateParamObjectDecl::printAsInit(llvm::raw_ostream &OS,
1661
                                          const PrintingPolicy &Policy) const {
1662
  getValue().printPretty(OS, Policy, getType(), &getASTContext());
1663
}
1664

1665
TemplateParameterList *clang::getReplacedTemplateParameterList(Decl *D) {
1666
  switch (D->getKind()) {
1667
  case Decl::Kind::CXXRecord:
1668
    return cast<CXXRecordDecl>(D)
1669
        ->getDescribedTemplate()
1670
        ->getTemplateParameters();
1671
  case Decl::Kind::ClassTemplate:
1672
    return cast<ClassTemplateDecl>(D)->getTemplateParameters();
1673
  case Decl::Kind::ClassTemplateSpecialization: {
1674
    const auto *CTSD = cast<ClassTemplateSpecializationDecl>(D);
1675
    auto P = CTSD->getSpecializedTemplateOrPartial();
1676
    if (const auto *CTPSD =
1677
            P.dyn_cast<ClassTemplatePartialSpecializationDecl *>())
1678
      return CTPSD->getTemplateParameters();
1679
    return cast<ClassTemplateDecl *>(P)->getTemplateParameters();
1680
  }
1681
  case Decl::Kind::ClassTemplatePartialSpecialization:
1682
    return cast<ClassTemplatePartialSpecializationDecl>(D)
1683
        ->getTemplateParameters();
1684
  case Decl::Kind::TypeAliasTemplate:
1685
    return cast<TypeAliasTemplateDecl>(D)->getTemplateParameters();
1686
  case Decl::Kind::BuiltinTemplate:
1687
    return cast<BuiltinTemplateDecl>(D)->getTemplateParameters();
1688
  case Decl::Kind::CXXDeductionGuide:
1689
  case Decl::Kind::CXXConversion:
1690
  case Decl::Kind::CXXConstructor:
1691
  case Decl::Kind::CXXDestructor:
1692
  case Decl::Kind::CXXMethod:
1693
  case Decl::Kind::Function:
1694
    return cast<FunctionDecl>(D)
1695
        ->getTemplateSpecializationInfo()
1696
        ->getTemplate()
1697
        ->getTemplateParameters();
1698
  case Decl::Kind::FunctionTemplate:
1699
    return cast<FunctionTemplateDecl>(D)->getTemplateParameters();
1700
  case Decl::Kind::VarTemplate:
1701
    return cast<VarTemplateDecl>(D)->getTemplateParameters();
1702
  case Decl::Kind::VarTemplateSpecialization: {
1703
    const auto *VTSD = cast<VarTemplateSpecializationDecl>(D);
1704
    auto P = VTSD->getSpecializedTemplateOrPartial();
1705
    if (const auto *VTPSD =
1706
            P.dyn_cast<VarTemplatePartialSpecializationDecl *>())
1707
      return VTPSD->getTemplateParameters();
1708
    return cast<VarTemplateDecl *>(P)->getTemplateParameters();
1709
  }
1710
  case Decl::Kind::VarTemplatePartialSpecialization:
1711
    return cast<VarTemplatePartialSpecializationDecl>(D)
1712
        ->getTemplateParameters();
1713
  case Decl::Kind::TemplateTemplateParm:
1714
    return cast<TemplateTemplateParmDecl>(D)->getTemplateParameters();
1715
  case Decl::Kind::Concept:
1716
    return cast<ConceptDecl>(D)->getTemplateParameters();
1717
  default:
1718
    llvm_unreachable("Unhandled templated declaration kind");
1719
  }
1720
}
1721

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.