blob: fc31d2f55bed9acc88d4218e02d181b6ae23938f [file] [log] [blame]
Sebastian Redl06a59bb2009-10-23 22:13:42 +00001//===--- DeclTemplate.cpp - Template Declaration AST Node Implementation --===//
Douglas Gregoraaba5e32009-02-04 19:02:06 +00002//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file implements the C++ related Decl classes for templates.
11//
12//===----------------------------------------------------------------------===//
13
14#include "clang/AST/DeclCXX.h"
15#include "clang/AST/DeclTemplate.h"
Douglas Gregor55f6b142009-02-09 18:46:07 +000016#include "clang/AST/Expr.h"
Douglas Gregorb95cc972011-01-04 02:33:52 +000017#include "clang/AST/ExprCXX.h"
Douglas Gregoraaba5e32009-02-04 19:02:06 +000018#include "clang/AST/ASTContext.h"
John McCall833ca992009-10-29 08:12:44 +000019#include "clang/AST/TypeLoc.h"
Argyrios Kyrtzidisbef1a7b2010-10-28 07:38:42 +000020#include "clang/AST/ASTMutationListener.h"
Douglas Gregoraaba5e32009-02-04 19:02:06 +000021#include "clang/Basic/IdentifierTable.h"
22#include "llvm/ADT/STLExtras.h"
Douglas Gregor910f8002010-11-07 23:05:16 +000023#include <memory>
Douglas Gregoraaba5e32009-02-04 19:02:06 +000024using namespace clang;
25
26//===----------------------------------------------------------------------===//
27// TemplateParameterList Implementation
28//===----------------------------------------------------------------------===//
29
Douglas Gregorddc29e12009-02-06 22:42:48 +000030TemplateParameterList::TemplateParameterList(SourceLocation TemplateLoc,
31 SourceLocation LAngleLoc,
Douglas Gregorbf4ea562009-09-15 16:23:51 +000032 NamedDecl **Params, unsigned NumParams,
Douglas Gregorddc29e12009-02-06 22:42:48 +000033 SourceLocation RAngleLoc)
34 : TemplateLoc(TemplateLoc), LAngleLoc(LAngleLoc), RAngleLoc(RAngleLoc),
Richard Smith6964b3f2012-09-07 02:06:42 +000035 NumParams(NumParams), ContainsUnexpandedParameterPack(false) {
36 assert(this->NumParams == NumParams && "Too many template parameters");
37 for (unsigned Idx = 0; Idx < NumParams; ++Idx) {
38 NamedDecl *P = Params[Idx];
39 begin()[Idx] = P;
40
41 if (!P->isTemplateParameterPack()) {
42 if (NonTypeTemplateParmDecl *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P))
43 if (NTTP->getType()->containsUnexpandedParameterPack())
44 ContainsUnexpandedParameterPack = true;
45
46 if (TemplateTemplateParmDecl *TTP = dyn_cast<TemplateTemplateParmDecl>(P))
47 if (TTP->getTemplateParameters()->containsUnexpandedParameterPack())
48 ContainsUnexpandedParameterPack = true;
49
50 // FIXME: If a default argument contains an unexpanded parameter pack, the
51 // template parameter list does too.
52 }
53 }
Douglas Gregoraaba5e32009-02-04 19:02:06 +000054}
55
56TemplateParameterList *
Jay Foad4ba2a172011-01-12 09:06:06 +000057TemplateParameterList::Create(const ASTContext &C, SourceLocation TemplateLoc,
Douglas Gregorbf4ea562009-09-15 16:23:51 +000058 SourceLocation LAngleLoc, NamedDecl **Params,
Douglas Gregorddc29e12009-02-06 22:42:48 +000059 unsigned NumParams, SourceLocation RAngleLoc) {
Douglas Gregorbf4ea562009-09-15 16:23:51 +000060 unsigned Size = sizeof(TemplateParameterList)
61 + sizeof(NamedDecl *) * NumParams;
Richard Smith1a30edb2012-08-16 22:51:34 +000062 unsigned Align = std::max(llvm::alignOf<TemplateParameterList>(),
63 llvm::alignOf<NamedDecl*>());
Douglas Gregoraaba5e32009-02-04 19:02:06 +000064 void *Mem = C.Allocate(Size, Align);
Mike Stump1eb44332009-09-09 15:08:12 +000065 return new (Mem) TemplateParameterList(TemplateLoc, LAngleLoc, Params,
Douglas Gregorddc29e12009-02-06 22:42:48 +000066 NumParams, RAngleLoc);
Douglas Gregoraaba5e32009-02-04 19:02:06 +000067}
68
Douglas Gregor62cb18d2009-02-11 18:16:40 +000069unsigned TemplateParameterList::getMinRequiredArguments() const {
Douglas Gregor6952f1e2011-01-19 20:10:05 +000070 unsigned NumRequiredArgs = 0;
71 for (iterator P = const_cast<TemplateParameterList *>(this)->begin(),
72 PEnd = const_cast<TemplateParameterList *>(this)->end();
73 P != PEnd; ++P) {
74 if ((*P)->isTemplateParameterPack()) {
75 if (NonTypeTemplateParmDecl *NTTP = dyn_cast<NonTypeTemplateParmDecl>(*P))
76 if (NTTP->isExpandedParameterPack()) {
77 NumRequiredArgs += NTTP->getNumExpansionTypes();
78 continue;
79 }
80
Douglas Gregor62cb18d2009-02-11 18:16:40 +000081 break;
Douglas Gregor6952f1e2011-01-19 20:10:05 +000082 }
83
84 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(*P)) {
85 if (TTP->hasDefaultArgument())
86 break;
87 } else if (NonTypeTemplateParmDecl *NTTP
88 = dyn_cast<NonTypeTemplateParmDecl>(*P)) {
89 if (NTTP->hasDefaultArgument())
90 break;
91 } else if (cast<TemplateTemplateParmDecl>(*P)->hasDefaultArgument())
92 break;
93
94 ++NumRequiredArgs;
Douglas Gregor62cb18d2009-02-11 18:16:40 +000095 }
Douglas Gregor6952f1e2011-01-19 20:10:05 +000096
Douglas Gregor62cb18d2009-02-11 18:16:40 +000097 return NumRequiredArgs;
98}
99
Douglas Gregored9c0f92009-10-29 00:04:11 +0000100unsigned TemplateParameterList::getDepth() const {
101 if (size() == 0)
102 return 0;
103
104 const NamedDecl *FirstParm = getParam(0);
105 if (const TemplateTypeParmDecl *TTP
106 = dyn_cast<TemplateTypeParmDecl>(FirstParm))
107 return TTP->getDepth();
108 else if (const NonTypeTemplateParmDecl *NTTP
109 = dyn_cast<NonTypeTemplateParmDecl>(FirstParm))
110 return NTTP->getDepth();
111 else
112 return cast<TemplateTemplateParmDecl>(FirstParm)->getDepth();
113}
114
Douglas Gregor787a40d2011-03-04 18:32:38 +0000115static void AdoptTemplateParameterList(TemplateParameterList *Params,
116 DeclContext *Owner) {
117 for (TemplateParameterList::iterator P = Params->begin(),
118 PEnd = Params->end();
119 P != PEnd; ++P) {
120 (*P)->setDeclContext(Owner);
121
122 if (TemplateTemplateParmDecl *TTP = dyn_cast<TemplateTemplateParmDecl>(*P))
123 AdoptTemplateParameterList(TTP->getTemplateParameters(), Owner);
124 }
125}
126
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000127//===----------------------------------------------------------------------===//
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000128// RedeclarableTemplateDecl Implementation
129//===----------------------------------------------------------------------===//
130
131RedeclarableTemplateDecl::CommonBase *RedeclarableTemplateDecl::getCommonPtr() {
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000132 if (!Common) {
133 // Walk the previous-declaration chain until we either find a declaration
134 // with a common pointer or we run out of previous declarations.
135 llvm::SmallVector<RedeclarableTemplateDecl *, 2> PrevDecls;
Douglas Gregoref96ee02012-01-14 16:38:05 +0000136 for (RedeclarableTemplateDecl *Prev = getPreviousDecl(); Prev;
137 Prev = Prev->getPreviousDecl()) {
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000138 if (Prev->Common) {
139 Common = Prev->Common;
140 break;
141 }
142
143 PrevDecls.push_back(Prev);
144 }
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000145
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000146 // If we never found a common pointer, allocate one now.
Douglas Gregor8a8950b2012-01-14 15:30:55 +0000147 if (!Common) {
148 // FIXME: If any of the declarations is from an AST file, we probably
149 // need an update record to add the common data.
150
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000151 Common = newCommon(getASTContext());
Douglas Gregor8a8950b2012-01-14 15:30:55 +0000152 }
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000153
154 // Update any previous declarations we saw with the common pointer.
155 for (unsigned I = 0, N = PrevDecls.size(); I != N; ++I)
156 PrevDecls[I]->Common = Common;
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000157 }
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000158
Douglas Gregor7c99bb5c2012-01-14 15:13:49 +0000159 return Common;
Peter Collingbournef88718e2010-07-29 16:12:09 +0000160}
161
Peter Collingbourne40485902010-07-30 17:09:04 +0000162template <class EntryType>
163typename RedeclarableTemplateDecl::SpecEntryTraits<EntryType>::DeclType*
164RedeclarableTemplateDecl::findSpecializationImpl(
Chandler Carruthd964d632012-05-03 23:49:05 +0000165 llvm::FoldingSetVector<EntryType> &Specs,
Peter Collingbourne40485902010-07-30 17:09:04 +0000166 const TemplateArgument *Args, unsigned NumArgs,
167 void *&InsertPos) {
168 typedef SpecEntryTraits<EntryType> SETraits;
169 llvm::FoldingSetNodeID ID;
170 EntryType::Profile(ID,Args,NumArgs, getASTContext());
171 EntryType *Entry = Specs.FindNodeOrInsertPos(ID, InsertPos);
Douglas Gregoref96ee02012-01-14 16:38:05 +0000172 return Entry ? SETraits::getMostRecentDecl(Entry) : 0;
Peter Collingbourne40485902010-07-30 17:09:04 +0000173}
174
Douglas Gregorc494f772011-03-05 17:54:25 +0000175/// \brief Generate the injected template arguments for the given template
176/// parameter list, e.g., for the injected-class-name of a class template.
177static void GenerateInjectedTemplateArgs(ASTContext &Context,
178 TemplateParameterList *Params,
179 TemplateArgument *Args) {
180 for (TemplateParameterList::iterator Param = Params->begin(),
181 ParamEnd = Params->end();
182 Param != ParamEnd; ++Param) {
183 TemplateArgument Arg;
184 if (TemplateTypeParmDecl *TTP = dyn_cast<TemplateTypeParmDecl>(*Param)) {
185 QualType ArgType = Context.getTypeDeclType(TTP);
186 if (TTP->isParameterPack())
187 ArgType = Context.getPackExpansionType(ArgType,
188 llvm::Optional<unsigned>());
189
190 Arg = TemplateArgument(ArgType);
191 } else if (NonTypeTemplateParmDecl *NTTP =
192 dyn_cast<NonTypeTemplateParmDecl>(*Param)) {
John McCallf4b88a42012-03-10 09:33:50 +0000193 Expr *E = new (Context) DeclRefExpr(NTTP, /*enclosing*/ false,
Douglas Gregorc494f772011-03-05 17:54:25 +0000194 NTTP->getType().getNonLValueExprType(Context),
195 Expr::getValueKindForType(NTTP->getType()),
196 NTTP->getLocation());
197
198 if (NTTP->isParameterPack())
199 E = new (Context) PackExpansionExpr(Context.DependentTy, E,
200 NTTP->getLocation(),
201 llvm::Optional<unsigned>());
202 Arg = TemplateArgument(E);
203 } else {
204 TemplateTemplateParmDecl *TTP = cast<TemplateTemplateParmDecl>(*Param);
205 if (TTP->isParameterPack())
206 Arg = TemplateArgument(TemplateName(TTP), llvm::Optional<unsigned>());
207 else
208 Arg = TemplateArgument(TemplateName(TTP));
209 }
210
211 if ((*Param)->isTemplateParameterPack())
212 Arg = TemplateArgument::CreatePackCopy(Context, &Arg, 1);
213
214 *Args++ = Arg;
215 }
216}
217
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000218//===----------------------------------------------------------------------===//
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000219// FunctionTemplateDecl Implementation
220//===----------------------------------------------------------------------===//
221
Douglas Gregor00545312010-05-23 18:26:36 +0000222void FunctionTemplateDecl::DeallocateCommon(void *Ptr) {
223 static_cast<Common *>(Ptr)->~Common();
224}
225
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000226FunctionTemplateDecl *FunctionTemplateDecl::Create(ASTContext &C,
227 DeclContext *DC,
228 SourceLocation L,
229 DeclarationName Name,
Douglas Gregor127102b2009-06-29 20:59:39 +0000230 TemplateParameterList *Params,
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000231 NamedDecl *Decl) {
Douglas Gregor787a40d2011-03-04 18:32:38 +0000232 AdoptTemplateParameterList(Params, cast<DeclContext>(Decl));
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000233 return new (C) FunctionTemplateDecl(DC, L, Name, Params, Decl);
234}
235
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000236FunctionTemplateDecl *FunctionTemplateDecl::CreateDeserialized(ASTContext &C,
237 unsigned ID) {
238 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(FunctionTemplateDecl));
239 return new (Mem) FunctionTemplateDecl(0, SourceLocation(), DeclarationName(),
240 0, 0);
Douglas Gregor9a299e02011-03-04 17:52:15 +0000241}
242
Argyrios Kyrtzidis6b541512010-09-08 19:31:22 +0000243RedeclarableTemplateDecl::CommonBase *
244FunctionTemplateDecl::newCommon(ASTContext &C) {
245 Common *CommonPtr = new (C) Common;
246 C.AddDeallocation(DeallocateCommon, CommonPtr);
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000247 return CommonPtr;
248}
249
Argyrios Kyrtzidis2c853e42010-07-20 13:59:58 +0000250FunctionDecl *
251FunctionTemplateDecl::findSpecialization(const TemplateArgument *Args,
252 unsigned NumArgs, void *&InsertPos) {
Peter Collingbourne40485902010-07-30 17:09:04 +0000253 return findSpecializationImpl(getSpecializations(), Args, NumArgs, InsertPos);
Argyrios Kyrtzidis2c853e42010-07-20 13:59:58 +0000254}
255
Sebastian Redl5bbcdbf2011-04-14 14:07:59 +0000256void FunctionTemplateDecl::addSpecialization(
257 FunctionTemplateSpecializationInfo *Info, void *InsertPos) {
Douglas Gregor1e1e9722012-03-28 14:34:23 +0000258 if (InsertPos)
259 getSpecializations().InsertNode(Info, InsertPos);
260 else
261 getSpecializations().GetOrInsertNode(Info);
Sebastian Redl5bbcdbf2011-04-14 14:07:59 +0000262 if (ASTMutationListener *L = getASTMutationListener())
263 L->AddedCXXTemplateSpecialization(this, Info->Function);
264}
265
Douglas Gregorc494f772011-03-05 17:54:25 +0000266std::pair<const TemplateArgument *, unsigned>
267FunctionTemplateDecl::getInjectedTemplateArgs() {
268 TemplateParameterList *Params = getTemplateParameters();
269 Common *CommonPtr = getCommonPtr();
270 if (!CommonPtr->InjectedArgs) {
271 CommonPtr->InjectedArgs
272 = new (getASTContext()) TemplateArgument [Params->size()];
273 GenerateInjectedTemplateArgs(getASTContext(), Params,
274 CommonPtr->InjectedArgs);
275 }
276
277 return std::make_pair(CommonPtr->InjectedArgs, Params->size());
278}
279
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000280//===----------------------------------------------------------------------===//
281// ClassTemplateDecl Implementation
282//===----------------------------------------------------------------------===//
283
Douglas Gregor00545312010-05-23 18:26:36 +0000284void ClassTemplateDecl::DeallocateCommon(void *Ptr) {
285 static_cast<Common *>(Ptr)->~Common();
286}
287
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000288ClassTemplateDecl *ClassTemplateDecl::Create(ASTContext &C,
289 DeclContext *DC,
290 SourceLocation L,
291 DeclarationName Name,
292 TemplateParameterList *Params,
Douglas Gregor5953d8b2009-03-19 17:26:29 +0000293 NamedDecl *Decl,
294 ClassTemplateDecl *PrevDecl) {
Douglas Gregor787a40d2011-03-04 18:32:38 +0000295 AdoptTemplateParameterList(Params, cast<DeclContext>(Decl));
Argyrios Kyrtzidis8731ca72010-06-19 19:29:09 +0000296 ClassTemplateDecl *New = new (C) ClassTemplateDecl(DC, L, Name, Params, Decl);
Argyrios Kyrtzidis5bf1bdc2010-06-21 10:57:41 +0000297 New->setPreviousDeclaration(PrevDecl);
Argyrios Kyrtzidis8731ca72010-06-19 19:29:09 +0000298 return New;
Douglas Gregor5953d8b2009-03-19 17:26:29 +0000299}
300
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000301ClassTemplateDecl *ClassTemplateDecl::CreateDeserialized(ASTContext &C,
302 unsigned ID) {
303 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(ClassTemplateDecl));
304 return new (Mem) ClassTemplateDecl(EmptyShell());
Douglas Gregor9a299e02011-03-04 17:52:15 +0000305}
306
Douglas Gregorc8e5cf82010-10-27 22:21:36 +0000307void ClassTemplateDecl::LoadLazySpecializations() {
308 Common *CommonPtr = getCommonPtr();
309 if (CommonPtr->LazySpecializations) {
310 ASTContext &Context = getASTContext();
311 uint32_t *Specs = CommonPtr->LazySpecializations;
312 CommonPtr->LazySpecializations = 0;
313 for (uint32_t I = 0, N = *Specs++; I != N; ++I)
314 (void)Context.getExternalSource()->GetExternalDecl(Specs[I]);
315 }
316}
317
Chandler Carruthd964d632012-05-03 23:49:05 +0000318llvm::FoldingSetVector<ClassTemplateSpecializationDecl> &
Douglas Gregorc8e5cf82010-10-27 22:21:36 +0000319ClassTemplateDecl::getSpecializations() {
320 LoadLazySpecializations();
321 return getCommonPtr()->Specializations;
322}
323
Chandler Carruthd964d632012-05-03 23:49:05 +0000324llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl> &
Douglas Gregorc8e5cf82010-10-27 22:21:36 +0000325ClassTemplateDecl::getPartialSpecializations() {
326 LoadLazySpecializations();
327 return getCommonPtr()->PartialSpecializations;
328}
329
Argyrios Kyrtzidis6b541512010-09-08 19:31:22 +0000330RedeclarableTemplateDecl::CommonBase *
331ClassTemplateDecl::newCommon(ASTContext &C) {
332 Common *CommonPtr = new (C) Common;
333 C.AddDeallocation(DeallocateCommon, CommonPtr);
Peter Collingbourne9eabeba2010-07-29 16:11:51 +0000334 return CommonPtr;
335}
336
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000337ClassTemplateSpecializationDecl *
338ClassTemplateDecl::findSpecialization(const TemplateArgument *Args,
339 unsigned NumArgs, void *&InsertPos) {
Peter Collingbourne40485902010-07-30 17:09:04 +0000340 return findSpecializationImpl(getSpecializations(), Args, NumArgs, InsertPos);
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000341}
342
Argyrios Kyrtzidisbef1a7b2010-10-28 07:38:42 +0000343void ClassTemplateDecl::AddSpecialization(ClassTemplateSpecializationDecl *D,
344 void *InsertPos) {
Douglas Gregor1e1e9722012-03-28 14:34:23 +0000345 if (InsertPos)
346 getSpecializations().InsertNode(D, InsertPos);
347 else {
348 ClassTemplateSpecializationDecl *Existing
349 = getSpecializations().GetOrInsertNode(D);
350 (void)Existing;
351 assert(Existing->isCanonicalDecl() && "Non-canonical specialization?");
352 }
Argyrios Kyrtzidisbef1a7b2010-10-28 07:38:42 +0000353 if (ASTMutationListener *L = getASTMutationListener())
354 L->AddedCXXTemplateSpecialization(this, D);
355}
356
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000357ClassTemplatePartialSpecializationDecl *
358ClassTemplateDecl::findPartialSpecialization(const TemplateArgument *Args,
359 unsigned NumArgs,
360 void *&InsertPos) {
Peter Collingbourne40485902010-07-30 17:09:04 +0000361 return findSpecializationImpl(getPartialSpecializations(), Args, NumArgs,
362 InsertPos);
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000363}
364
Argyrios Kyrtzidisbef1a7b2010-10-28 07:38:42 +0000365void ClassTemplateDecl::AddPartialSpecialization(
366 ClassTemplatePartialSpecializationDecl *D,
367 void *InsertPos) {
Douglas Gregor1e1e9722012-03-28 14:34:23 +0000368 if (InsertPos)
369 getPartialSpecializations().InsertNode(D, InsertPos);
370 else {
371 ClassTemplatePartialSpecializationDecl *Existing
372 = getPartialSpecializations().GetOrInsertNode(D);
373 (void)Existing;
374 assert(Existing->isCanonicalDecl() && "Non-canonical specialization?");
375 }
376
Argyrios Kyrtzidisbef1a7b2010-10-28 07:38:42 +0000377 if (ASTMutationListener *L = getASTMutationListener())
378 L->AddedCXXTemplateSpecialization(this, D);
379}
380
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000381void ClassTemplateDecl::getPartialSpecializations(
Chris Lattner5f9e2722011-07-23 10:55:15 +0000382 SmallVectorImpl<ClassTemplatePartialSpecializationDecl *> &PS) {
Chandler Carruthd964d632012-05-03 23:49:05 +0000383 llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl> &PartialSpecs
Argyrios Kyrtzidis5bf1bdc2010-06-21 10:57:41 +0000384 = getPartialSpecializations();
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000385 PS.clear();
386 PS.resize(PartialSpecs.size());
Chandler Carruthd964d632012-05-03 23:49:05 +0000387 for (llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl>::iterator
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000388 P = PartialSpecs.begin(), PEnd = PartialSpecs.end();
389 P != PEnd; ++P) {
390 assert(!PS[P->getSequenceNumber()]);
Douglas Gregoref96ee02012-01-14 16:38:05 +0000391 PS[P->getSequenceNumber()] = P->getMostRecentDecl();
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000392 }
393}
394
Douglas Gregorb88e8882009-07-30 17:40:51 +0000395ClassTemplatePartialSpecializationDecl *
396ClassTemplateDecl::findPartialSpecialization(QualType T) {
397 ASTContext &Context = getASTContext();
Chandler Carruthd964d632012-05-03 23:49:05 +0000398 using llvm::FoldingSetVector;
399 typedef FoldingSetVector<ClassTemplatePartialSpecializationDecl>::iterator
Douglas Gregorb88e8882009-07-30 17:40:51 +0000400 partial_spec_iterator;
401 for (partial_spec_iterator P = getPartialSpecializations().begin(),
402 PEnd = getPartialSpecializations().end();
403 P != PEnd; ++P) {
John McCall31f17ec2010-04-27 00:57:59 +0000404 if (Context.hasSameType(P->getInjectedSpecializationType(), T))
Douglas Gregoref96ee02012-01-14 16:38:05 +0000405 return P->getMostRecentDecl();
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000406 }
407
408 return 0;
409}
410
411ClassTemplatePartialSpecializationDecl *
412ClassTemplateDecl::findPartialSpecInstantiatedFromMember(
413 ClassTemplatePartialSpecializationDecl *D) {
414 Decl *DCanon = D->getCanonicalDecl();
Chandler Carruthd964d632012-05-03 23:49:05 +0000415 for (llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl>::iterator
Argyrios Kyrtzidiscc0b1bc2010-07-20 13:59:28 +0000416 P = getPartialSpecializations().begin(),
417 PEnd = getPartialSpecializations().end();
418 P != PEnd; ++P) {
419 if (P->getInstantiatedFromMember()->getCanonicalDecl() == DCanon)
Douglas Gregoref96ee02012-01-14 16:38:05 +0000420 return P->getMostRecentDecl();
Douglas Gregorb88e8882009-07-30 17:40:51 +0000421 }
Mike Stump1eb44332009-09-09 15:08:12 +0000422
Douglas Gregorb88e8882009-07-30 17:40:51 +0000423 return 0;
424}
425
John McCall3cb0ebd2010-03-10 03:28:59 +0000426QualType
Douglas Gregor24bae922010-07-08 18:37:38 +0000427ClassTemplateDecl::getInjectedClassNameSpecialization() {
Argyrios Kyrtzidis5bf1bdc2010-06-21 10:57:41 +0000428 Common *CommonPtr = getCommonPtr();
Douglas Gregor7da97d02009-05-10 22:57:19 +0000429 if (!CommonPtr->InjectedClassNameType.isNull())
430 return CommonPtr->InjectedClassNameType;
431
Douglas Gregorb7d09d62010-12-23 16:00:30 +0000432 // C++0x [temp.dep.type]p2:
433 // The template argument list of a primary template is a template argument
434 // list in which the nth template argument has the value of the nth template
435 // parameter of the class template. If the nth template parameter is a
436 // template parameter pack (14.5.3), the nth template argument is a pack
437 // expansion (14.5.3) whose pattern is the name of the template parameter
438 // pack.
Douglas Gregor24bae922010-07-08 18:37:38 +0000439 ASTContext &Context = getASTContext();
Douglas Gregor7da97d02009-05-10 22:57:19 +0000440 TemplateParameterList *Params = getTemplateParameters();
Chris Lattner5f9e2722011-07-23 10:55:15 +0000441 SmallVector<TemplateArgument, 16> TemplateArgs;
Douglas Gregorc494f772011-03-05 17:54:25 +0000442 TemplateArgs.resize(Params->size());
443 GenerateInjectedTemplateArgs(getASTContext(), Params, TemplateArgs.data());
Douglas Gregor7da97d02009-05-10 22:57:19 +0000444 CommonPtr->InjectedClassNameType
Douglas Gregor1275ae02009-07-28 23:00:59 +0000445 = Context.getTemplateSpecializationType(TemplateName(this),
Douglas Gregor7da97d02009-05-10 22:57:19 +0000446 &TemplateArgs[0],
Douglas Gregor1275ae02009-07-28 23:00:59 +0000447 TemplateArgs.size());
Douglas Gregor7da97d02009-05-10 22:57:19 +0000448 return CommonPtr->InjectedClassNameType;
449}
450
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000451//===----------------------------------------------------------------------===//
452// TemplateTypeParm Allocation/Deallocation Method Implementations
453//===----------------------------------------------------------------------===//
454
455TemplateTypeParmDecl *
Jay Foad4ba2a172011-01-12 09:06:06 +0000456TemplateTypeParmDecl::Create(const ASTContext &C, DeclContext *DC,
Abramo Bagnara344577e2011-03-06 15:48:19 +0000457 SourceLocation KeyLoc, SourceLocation NameLoc,
458 unsigned D, unsigned P, IdentifierInfo *Id,
459 bool Typename, bool ParameterPack) {
Chandler Carruth4fb86f82011-05-01 00:51:33 +0000460 TemplateTypeParmDecl *TTPDecl =
461 new (C) TemplateTypeParmDecl(DC, KeyLoc, NameLoc, Id, Typename);
462 QualType TTPType = C.getTemplateTypeParmType(D, P, ParameterPack, TTPDecl);
463 TTPDecl->TypeForDecl = TTPType.getTypePtr();
464 return TTPDecl;
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000465}
466
Argyrios Kyrtzidisb8b03e62010-07-02 11:54:55 +0000467TemplateTypeParmDecl *
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000468TemplateTypeParmDecl::CreateDeserialized(const ASTContext &C, unsigned ID) {
469 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(TemplateTypeParmDecl));
470 return new (Mem) TemplateTypeParmDecl(0, SourceLocation(), SourceLocation(),
471 0, false);
Argyrios Kyrtzidisb8b03e62010-07-02 11:54:55 +0000472}
473
John McCall833ca992009-10-29 08:12:44 +0000474SourceLocation TemplateTypeParmDecl::getDefaultArgumentLoc() const {
Abramo Bagnara77d4ee22011-03-04 12:42:03 +0000475 return hasDefaultArgument()
476 ? DefaultArgument->getTypeLoc().getBeginLoc()
477 : SourceLocation();
478}
479
480SourceRange TemplateTypeParmDecl::getSourceRange() const {
481 if (hasDefaultArgument() && !defaultArgumentWasInherited())
Abramo Bagnara344577e2011-03-06 15:48:19 +0000482 return SourceRange(getLocStart(),
Abramo Bagnara77d4ee22011-03-04 12:42:03 +0000483 DefaultArgument->getTypeLoc().getEndLoc());
484 else
Abramo Bagnara344577e2011-03-06 15:48:19 +0000485 return TypeDecl::getSourceRange();
John McCall833ca992009-10-29 08:12:44 +0000486}
487
Douglas Gregored9c0f92009-10-29 00:04:11 +0000488unsigned TemplateTypeParmDecl::getDepth() const {
489 return TypeForDecl->getAs<TemplateTypeParmType>()->getDepth();
490}
491
492unsigned TemplateTypeParmDecl::getIndex() const {
493 return TypeForDecl->getAs<TemplateTypeParmType>()->getIndex();
494}
495
Chandler Carruth4fb86f82011-05-01 00:51:33 +0000496bool TemplateTypeParmDecl::isParameterPack() const {
497 return TypeForDecl->getAs<TemplateTypeParmType>()->isParameterPack();
498}
499
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000500//===----------------------------------------------------------------------===//
501// NonTypeTemplateParmDecl Method Implementations
502//===----------------------------------------------------------------------===//
503
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000504NonTypeTemplateParmDecl::NonTypeTemplateParmDecl(DeclContext *DC,
Abramo Bagnaraff676cb2011-03-08 08:55:46 +0000505 SourceLocation StartLoc,
506 SourceLocation IdLoc,
507 unsigned D, unsigned P,
508 IdentifierInfo *Id,
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000509 QualType T,
510 TypeSourceInfo *TInfo,
511 const QualType *ExpandedTypes,
512 unsigned NumExpandedTypes,
513 TypeSourceInfo **ExpandedTInfos)
Abramo Bagnaraff676cb2011-03-08 08:55:46 +0000514 : DeclaratorDecl(NonTypeTemplateParm, DC, IdLoc, Id, T, TInfo, StartLoc),
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000515 TemplateParmPosition(D, P), DefaultArgumentAndInherited(0, false),
516 ParameterPack(true), ExpandedParameterPack(true),
517 NumExpandedTypes(NumExpandedTypes)
518{
519 if (ExpandedTypes && ExpandedTInfos) {
520 void **TypesAndInfos = reinterpret_cast<void **>(this + 1);
521 for (unsigned I = 0; I != NumExpandedTypes; ++I) {
522 TypesAndInfos[2*I] = ExpandedTypes[I].getAsOpaquePtr();
523 TypesAndInfos[2*I + 1] = ExpandedTInfos[I];
524 }
525 }
526}
527
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000528NonTypeTemplateParmDecl *
Jay Foad4ba2a172011-01-12 09:06:06 +0000529NonTypeTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
Abramo Bagnaraff676cb2011-03-08 08:55:46 +0000530 SourceLocation StartLoc, SourceLocation IdLoc,
531 unsigned D, unsigned P, IdentifierInfo *Id,
532 QualType T, bool ParameterPack,
533 TypeSourceInfo *TInfo) {
534 return new (C) NonTypeTemplateParmDecl(DC, StartLoc, IdLoc, D, P, Id,
535 T, ParameterPack, TInfo);
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000536}
537
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000538NonTypeTemplateParmDecl *
539NonTypeTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
Abramo Bagnaraff676cb2011-03-08 08:55:46 +0000540 SourceLocation StartLoc, SourceLocation IdLoc,
541 unsigned D, unsigned P,
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000542 IdentifierInfo *Id, QualType T,
543 TypeSourceInfo *TInfo,
544 const QualType *ExpandedTypes,
545 unsigned NumExpandedTypes,
546 TypeSourceInfo **ExpandedTInfos) {
547 unsigned Size = sizeof(NonTypeTemplateParmDecl)
548 + NumExpandedTypes * 2 * sizeof(void*);
549 void *Mem = C.Allocate(Size);
Abramo Bagnaraff676cb2011-03-08 08:55:46 +0000550 return new (Mem) NonTypeTemplateParmDecl(DC, StartLoc, IdLoc,
551 D, P, Id, T, TInfo,
Douglas Gregor6952f1e2011-01-19 20:10:05 +0000552 ExpandedTypes, NumExpandedTypes,
553 ExpandedTInfos);
554}
555
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000556NonTypeTemplateParmDecl *
557NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, unsigned ID) {
558 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(NonTypeTemplateParmDecl));
559 return new (Mem) NonTypeTemplateParmDecl(0, SourceLocation(),
560 SourceLocation(), 0, 0, 0,
561 QualType(), false, 0);
562}
563
564NonTypeTemplateParmDecl *
565NonTypeTemplateParmDecl::CreateDeserialized(ASTContext &C, unsigned ID,
566 unsigned NumExpandedTypes) {
567 unsigned Size = sizeof(NonTypeTemplateParmDecl)
568 + NumExpandedTypes * 2 * sizeof(void*);
569
570 void *Mem = AllocateDeserializedDecl(C, ID, Size);
571 return new (Mem) NonTypeTemplateParmDecl(0, SourceLocation(),
572 SourceLocation(), 0, 0, 0,
573 QualType(), 0, 0, NumExpandedTypes,
574 0);
575}
576
John McCall76a40212011-02-09 01:13:10 +0000577SourceRange NonTypeTemplateParmDecl::getSourceRange() const {
Abramo Bagnaraee4bfd42011-03-04 11:03:48 +0000578 if (hasDefaultArgument() && !defaultArgumentWasInherited())
Abramo Bagnaraa2026c92011-03-08 16:41:52 +0000579 return SourceRange(getOuterLocStart(),
580 getDefaultArgument()->getSourceRange().getEnd());
581 return DeclaratorDecl::getSourceRange();
John McCall76a40212011-02-09 01:13:10 +0000582}
583
Douglas Gregord684b002009-02-10 19:49:53 +0000584SourceLocation NonTypeTemplateParmDecl::getDefaultArgumentLoc() const {
Abramo Bagnarad92f7a22010-06-09 09:26:05 +0000585 return hasDefaultArgument()
586 ? getDefaultArgument()->getSourceRange().getBegin()
587 : SourceLocation();
Douglas Gregord684b002009-02-10 19:49:53 +0000588}
589
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000590//===----------------------------------------------------------------------===//
591// TemplateTemplateParmDecl Method Implementations
592//===----------------------------------------------------------------------===//
593
David Blaikie99ba9e32011-12-20 02:48:34 +0000594void TemplateTemplateParmDecl::anchor() { }
595
Richard Smith6964b3f2012-09-07 02:06:42 +0000596TemplateTemplateParmDecl::TemplateTemplateParmDecl(
597 DeclContext *DC, SourceLocation L, unsigned D, unsigned P,
598 IdentifierInfo *Id, TemplateParameterList *Params,
599 unsigned NumExpansions, TemplateParameterList * const *Expansions)
600 : TemplateDecl(TemplateTemplateParm, DC, L, Id, Params),
601 TemplateParmPosition(D, P), DefaultArgument(),
602 DefaultArgumentWasInherited(false), ParameterPack(true),
603 ExpandedParameterPack(true), NumExpandedParams(NumExpansions) {
604 if (Expansions)
605 std::memcpy(reinterpret_cast<void*>(this + 1), Expansions,
606 sizeof(TemplateParameterList*) * NumExpandedParams);
607}
608
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000609TemplateTemplateParmDecl *
Jay Foad4ba2a172011-01-12 09:06:06 +0000610TemplateTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000611 SourceLocation L, unsigned D, unsigned P,
Douglas Gregor61c4d282011-01-05 15:48:55 +0000612 bool ParameterPack, IdentifierInfo *Id,
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000613 TemplateParameterList *Params) {
Douglas Gregor61c4d282011-01-05 15:48:55 +0000614 return new (C) TemplateTemplateParmDecl(DC, L, D, P, ParameterPack, Id,
615 Params);
Douglas Gregoraaba5e32009-02-04 19:02:06 +0000616}
617
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000618TemplateTemplateParmDecl *
Richard Smith6964b3f2012-09-07 02:06:42 +0000619TemplateTemplateParmDecl::Create(const ASTContext &C, DeclContext *DC,
620 SourceLocation L, unsigned D, unsigned P,
621 IdentifierInfo *Id,
622 TemplateParameterList *Params,
623 llvm::ArrayRef<TemplateParameterList*> Expansions) {
624 void *Mem = C.Allocate(sizeof(TemplateTemplateParmDecl) +
625 sizeof(TemplateParameterList*) * Expansions.size());
626 return new (Mem) TemplateTemplateParmDecl(DC, L, D, P, Id, Params,
627 Expansions.size(),
628 Expansions.data());
629}
630
631TemplateTemplateParmDecl *
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000632TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, unsigned ID) {
633 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(TemplateTemplateParmDecl));
634 return new (Mem) TemplateTemplateParmDecl(0, SourceLocation(), 0, 0, false,
635 0, 0);
636}
637
Richard Smith6964b3f2012-09-07 02:06:42 +0000638TemplateTemplateParmDecl *
639TemplateTemplateParmDecl::CreateDeserialized(ASTContext &C, unsigned ID,
640 unsigned NumExpansions) {
641 unsigned Size = sizeof(TemplateTemplateParmDecl) +
642 sizeof(TemplateParameterList*) * NumExpansions;
643 void *Mem = AllocateDeserializedDecl(C, ID, Size);
644 return new (Mem) TemplateTemplateParmDecl(0, SourceLocation(), 0, 0, 0, 0,
645 NumExpansions, 0);
646}
647
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000648//===----------------------------------------------------------------------===//
Douglas Gregor7e063902009-05-11 23:53:27 +0000649// TemplateArgumentList Implementation
650//===----------------------------------------------------------------------===//
Douglas Gregor910f8002010-11-07 23:05:16 +0000651TemplateArgumentList *
652TemplateArgumentList::CreateCopy(ASTContext &Context,
653 const TemplateArgument *Args,
654 unsigned NumArgs) {
655 std::size_t Size = sizeof(TemplateArgumentList)
656 + NumArgs * sizeof(TemplateArgument);
657 void *Mem = Context.Allocate(Size);
658 TemplateArgument *StoredArgs
659 = reinterpret_cast<TemplateArgument *>(
660 static_cast<TemplateArgumentList *>(Mem) + 1);
661 std::uninitialized_copy(Args, Args + NumArgs, StoredArgs);
662 return new (Mem) TemplateArgumentList(StoredArgs, NumArgs, true);
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000663}
664
Argyrios Kyrtzidis71a76052011-09-22 20:07:09 +0000665FunctionTemplateSpecializationInfo *
666FunctionTemplateSpecializationInfo::Create(ASTContext &C, FunctionDecl *FD,
667 FunctionTemplateDecl *Template,
668 TemplateSpecializationKind TSK,
669 const TemplateArgumentList *TemplateArgs,
670 const TemplateArgumentListInfo *TemplateArgsAsWritten,
671 SourceLocation POI) {
672 const ASTTemplateArgumentListInfo *ArgsAsWritten = 0;
673 if (TemplateArgsAsWritten)
674 ArgsAsWritten = ASTTemplateArgumentListInfo::Create(C,
675 *TemplateArgsAsWritten);
676
677 return new (C) FunctionTemplateSpecializationInfo(FD, Template, TSK,
678 TemplateArgs,
679 ArgsAsWritten,
680 POI);
681}
682
Douglas Gregor7e063902009-05-11 23:53:27 +0000683//===----------------------------------------------------------------------===//
David Blaikie99ba9e32011-12-20 02:48:34 +0000684// TemplateDecl Implementation
685//===----------------------------------------------------------------------===//
686
687void TemplateDecl::anchor() { }
688
689//===----------------------------------------------------------------------===//
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000690// ClassTemplateSpecializationDecl Implementation
691//===----------------------------------------------------------------------===//
692ClassTemplateSpecializationDecl::
Douglas Gregor13c85772010-05-06 00:28:52 +0000693ClassTemplateSpecializationDecl(ASTContext &Context, Kind DK, TagKind TK,
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000694 DeclContext *DC, SourceLocation StartLoc,
695 SourceLocation IdLoc,
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000696 ClassTemplateDecl *SpecializedTemplate,
Douglas Gregor910f8002010-11-07 23:05:16 +0000697 const TemplateArgument *Args,
698 unsigned NumArgs,
Douglas Gregor8e9e9ef2009-07-29 23:36:44 +0000699 ClassTemplateSpecializationDecl *PrevDecl)
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000700 : CXXRecordDecl(DK, TK, DC, StartLoc, IdLoc,
Douglas Gregor8e9e9ef2009-07-29 23:36:44 +0000701 SpecializedTemplate->getIdentifier(),
702 PrevDecl),
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000703 SpecializedTemplate(SpecializedTemplate),
Abramo Bagnarac98971d2010-06-12 07:44:57 +0000704 ExplicitInfo(0),
Douglas Gregor910f8002010-11-07 23:05:16 +0000705 TemplateArgs(TemplateArgumentList::CreateCopy(Context, Args, NumArgs)),
Douglas Gregor7e063902009-05-11 23:53:27 +0000706 SpecializationKind(TSK_Undeclared) {
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000707}
Mike Stump1eb44332009-09-09 15:08:12 +0000708
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000709ClassTemplateSpecializationDecl::ClassTemplateSpecializationDecl(Kind DK)
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000710 : CXXRecordDecl(DK, TTK_Struct, 0, SourceLocation(), SourceLocation(), 0, 0),
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000711 ExplicitInfo(0),
712 SpecializationKind(TSK_Undeclared) {
713}
714
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000715ClassTemplateSpecializationDecl *
Douglas Gregor13c85772010-05-06 00:28:52 +0000716ClassTemplateSpecializationDecl::Create(ASTContext &Context, TagKind TK,
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000717 DeclContext *DC,
718 SourceLocation StartLoc,
719 SourceLocation IdLoc,
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000720 ClassTemplateDecl *SpecializedTemplate,
Douglas Gregor910f8002010-11-07 23:05:16 +0000721 const TemplateArgument *Args,
722 unsigned NumArgs,
Douglas Gregorcc636682009-02-17 23:15:12 +0000723 ClassTemplateSpecializationDecl *PrevDecl) {
Douglas Gregorcc636682009-02-17 23:15:12 +0000724 ClassTemplateSpecializationDecl *Result
Mike Stump1eb44332009-09-09 15:08:12 +0000725 = new (Context)ClassTemplateSpecializationDecl(Context,
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000726 ClassTemplateSpecialization,
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000727 TK, DC, StartLoc, IdLoc,
Douglas Gregor7e063902009-05-11 23:53:27 +0000728 SpecializedTemplate,
Douglas Gregor910f8002010-11-07 23:05:16 +0000729 Args, NumArgs,
Douglas Gregor8e9e9ef2009-07-29 23:36:44 +0000730 PrevDecl);
Douglas Gregorcc636682009-02-17 23:15:12 +0000731 Context.getTypeDeclType(Result, PrevDecl);
732 return Result;
Douglas Gregor3e00bad2009-02-17 01:05:43 +0000733}
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000734
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000735ClassTemplateSpecializationDecl *
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000736ClassTemplateSpecializationDecl::CreateDeserialized(ASTContext &C,
737 unsigned ID) {
738 void *Mem = AllocateDeserializedDecl(C, ID,
739 sizeof(ClassTemplateSpecializationDecl));
740 return new (Mem) ClassTemplateSpecializationDecl(ClassTemplateSpecialization);
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000741}
742
Douglas Gregorda2142f2011-02-19 18:51:44 +0000743void
744ClassTemplateSpecializationDecl::getNameForDiagnostic(std::string &S,
745 const PrintingPolicy &Policy,
746 bool Qualified) const {
747 NamedDecl::getNameForDiagnostic(S, Policy, Qualified);
748
749 const TemplateArgumentList &TemplateArgs = getTemplateArgs();
750 S += TemplateSpecializationType::PrintTemplateArgumentList(
751 TemplateArgs.data(),
752 TemplateArgs.size(),
753 Policy);
754}
755
Douglas Gregor37d93e92009-08-02 23:24:31 +0000756ClassTemplateDecl *
Mike Stump1eb44332009-09-09 15:08:12 +0000757ClassTemplateSpecializationDecl::getSpecializedTemplate() const {
758 if (SpecializedPartialSpecialization *PartialSpec
Douglas Gregor37d93e92009-08-02 23:24:31 +0000759 = SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
760 return PartialSpec->PartialSpecialization->getSpecializedTemplate();
761 return SpecializedTemplate.get<ClassTemplateDecl*>();
762}
763
Abramo Bagnara4a85a732011-03-04 14:20:30 +0000764SourceRange
765ClassTemplateSpecializationDecl::getSourceRange() const {
Abramo Bagnara09d82122011-10-03 20:34:03 +0000766 if (ExplicitInfo) {
767 SourceLocation Begin = getExternLoc();
768 if (Begin.isInvalid())
769 Begin = getTemplateKeywordLoc();
770 SourceLocation End = getRBraceLoc();
771 if (End.isInvalid())
772 End = getTypeAsWritten()->getTypeLoc().getEndLoc();
773 return SourceRange(Begin, End);
774 }
775 else {
776 // No explicit info available.
777 llvm::PointerUnion<ClassTemplateDecl *,
778 ClassTemplatePartialSpecializationDecl *>
779 inst_from = getInstantiatedFrom();
780 if (inst_from.isNull())
781 return getSpecializedTemplate()->getSourceRange();
782 if (ClassTemplateDecl *ctd = inst_from.dyn_cast<ClassTemplateDecl*>())
783 return ctd->getSourceRange();
784 return inst_from.get<ClassTemplatePartialSpecializationDecl*>()
785 ->getSourceRange();
786 }
Abramo Bagnara4a85a732011-03-04 14:20:30 +0000787}
788
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000789//===----------------------------------------------------------------------===//
790// ClassTemplatePartialSpecializationDecl Implementation
791//===----------------------------------------------------------------------===//
David Blaikie99ba9e32011-12-20 02:48:34 +0000792void ClassTemplatePartialSpecializationDecl::anchor() { }
793
Douglas Gregor9a299e02011-03-04 17:52:15 +0000794ClassTemplatePartialSpecializationDecl::
795ClassTemplatePartialSpecializationDecl(ASTContext &Context, TagKind TK,
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000796 DeclContext *DC,
797 SourceLocation StartLoc,
798 SourceLocation IdLoc,
Douglas Gregor9a299e02011-03-04 17:52:15 +0000799 TemplateParameterList *Params,
800 ClassTemplateDecl *SpecializedTemplate,
801 const TemplateArgument *Args,
802 unsigned NumArgs,
803 TemplateArgumentLoc *ArgInfos,
804 unsigned NumArgInfos,
805 ClassTemplatePartialSpecializationDecl *PrevDecl,
806 unsigned SequenceNumber)
807 : ClassTemplateSpecializationDecl(Context,
808 ClassTemplatePartialSpecialization,
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000809 TK, DC, StartLoc, IdLoc,
810 SpecializedTemplate,
Douglas Gregor9a299e02011-03-04 17:52:15 +0000811 Args, NumArgs, PrevDecl),
812 TemplateParams(Params), ArgsAsWritten(ArgInfos),
813 NumArgsAsWritten(NumArgInfos), SequenceNumber(SequenceNumber),
814 InstantiatedFromMember(0, false)
815{
Douglas Gregor787a40d2011-03-04 18:32:38 +0000816 AdoptTemplateParameterList(Params, this);
Douglas Gregor9a299e02011-03-04 17:52:15 +0000817}
818
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000819ClassTemplatePartialSpecializationDecl *
820ClassTemplatePartialSpecializationDecl::
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000821Create(ASTContext &Context, TagKind TK,DeclContext *DC,
822 SourceLocation StartLoc, SourceLocation IdLoc,
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000823 TemplateParameterList *Params,
824 ClassTemplateDecl *SpecializedTemplate,
Douglas Gregor910f8002010-11-07 23:05:16 +0000825 const TemplateArgument *Args,
826 unsigned NumArgs,
John McCalld5532b62009-11-23 01:53:49 +0000827 const TemplateArgumentListInfo &ArgInfos,
John McCall3cb0ebd2010-03-10 03:28:59 +0000828 QualType CanonInjectedType,
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000829 ClassTemplatePartialSpecializationDecl *PrevDecl,
830 unsigned SequenceNumber) {
John McCalld5532b62009-11-23 01:53:49 +0000831 unsigned N = ArgInfos.size();
John McCall833ca992009-10-29 08:12:44 +0000832 TemplateArgumentLoc *ClonedArgs = new (Context) TemplateArgumentLoc[N];
833 for (unsigned I = 0; I != N; ++I)
834 ClonedArgs[I] = ArgInfos[I];
835
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000836 ClassTemplatePartialSpecializationDecl *Result
Abramo Bagnaraba877ad2011-03-09 14:09:51 +0000837 = new (Context)ClassTemplatePartialSpecializationDecl(Context, TK, DC,
838 StartLoc, IdLoc,
839 Params,
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000840 SpecializedTemplate,
Douglas Gregor910f8002010-11-07 23:05:16 +0000841 Args, NumArgs,
John McCall833ca992009-10-29 08:12:44 +0000842 ClonedArgs, N,
Douglas Gregordc60c1e2010-04-30 05:56:50 +0000843 PrevDecl,
844 SequenceNumber);
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000845 Result->setSpecializationKind(TSK_ExplicitSpecialization);
John McCall3cb0ebd2010-03-10 03:28:59 +0000846
847 Context.getInjectedClassNameType(Result, CanonInjectedType);
Douglas Gregorc8ab2562009-05-31 09:31:02 +0000848 return Result;
849}
John McCalldd4a3b02009-09-16 22:47:08 +0000850
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000851ClassTemplatePartialSpecializationDecl *
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000852ClassTemplatePartialSpecializationDecl::CreateDeserialized(ASTContext &C,
853 unsigned ID) {
854 void *Mem = AllocateDeserializedDecl(C, ID,
855 sizeof(ClassTemplatePartialSpecializationDecl));
856 return new (Mem) ClassTemplatePartialSpecializationDecl();
Argyrios Kyrtzidis94d228d2010-06-23 13:48:23 +0000857}
858
John McCalldd4a3b02009-09-16 22:47:08 +0000859//===----------------------------------------------------------------------===//
860// FriendTemplateDecl Implementation
861//===----------------------------------------------------------------------===//
862
David Blaikie99ba9e32011-12-20 02:48:34 +0000863void FriendTemplateDecl::anchor() { }
864
John McCalldd4a3b02009-09-16 22:47:08 +0000865FriendTemplateDecl *FriendTemplateDecl::Create(ASTContext &Context,
866 DeclContext *DC,
867 SourceLocation L,
868 unsigned NParams,
869 TemplateParameterList **Params,
870 FriendUnion Friend,
871 SourceLocation FLoc) {
872 FriendTemplateDecl *Result
873 = new (Context) FriendTemplateDecl(DC, L, NParams, Params, Friend, FLoc);
874 return Result;
875}
Argyrios Kyrtzidis554e6aa2010-07-22 16:04:10 +0000876
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000877FriendTemplateDecl *FriendTemplateDecl::CreateDeserialized(ASTContext &C,
878 unsigned ID) {
879 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(FriendTemplateDecl));
880 return new (Mem) FriendTemplateDecl(EmptyShell());
Argyrios Kyrtzidis554e6aa2010-07-22 16:04:10 +0000881}
Richard Smith3e4c6c42011-05-05 21:57:07 +0000882
883//===----------------------------------------------------------------------===//
884// TypeAliasTemplateDecl Implementation
885//===----------------------------------------------------------------------===//
886
887TypeAliasTemplateDecl *TypeAliasTemplateDecl::Create(ASTContext &C,
888 DeclContext *DC,
889 SourceLocation L,
890 DeclarationName Name,
891 TemplateParameterList *Params,
892 NamedDecl *Decl) {
893 AdoptTemplateParameterList(Params, DC);
894 return new (C) TypeAliasTemplateDecl(DC, L, Name, Params, Decl);
895}
896
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000897TypeAliasTemplateDecl *TypeAliasTemplateDecl::CreateDeserialized(ASTContext &C,
898 unsigned ID) {
899 void *Mem = AllocateDeserializedDecl(C, ID, sizeof(TypeAliasTemplateDecl));
900 return new (Mem) TypeAliasTemplateDecl(0, SourceLocation(), DeclarationName(),
901 0, 0);
Richard Smith3e4c6c42011-05-05 21:57:07 +0000902}
903
904void TypeAliasTemplateDecl::DeallocateCommon(void *Ptr) {
905 static_cast<Common *>(Ptr)->~Common();
906}
907RedeclarableTemplateDecl::CommonBase *
908TypeAliasTemplateDecl::newCommon(ASTContext &C) {
909 Common *CommonPtr = new (C) Common;
910 C.AddDeallocation(DeallocateCommon, CommonPtr);
911 return CommonPtr;
912}
913
David Blaikie99ba9e32011-12-20 02:48:34 +0000914//===----------------------------------------------------------------------===//
915// ClassScopeFunctionSpecializationDecl Implementation
916//===----------------------------------------------------------------------===//
917
918void ClassScopeFunctionSpecializationDecl::anchor() { }
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000919
920ClassScopeFunctionSpecializationDecl *
921ClassScopeFunctionSpecializationDecl::CreateDeserialized(ASTContext &C,
922 unsigned ID) {
923 void *Mem = AllocateDeserializedDecl(C, ID,
924 sizeof(ClassScopeFunctionSpecializationDecl));
Nico Weber6b020092012-06-25 17:21:05 +0000925 return new (Mem) ClassScopeFunctionSpecializationDecl(0, SourceLocation(), 0,
926 false, TemplateArgumentListInfo());
Douglas Gregor1e68ecc2012-01-05 21:55:30 +0000927}