DeclTemplate.h revision be2fa7ebf01259b63dc52fe46c8d101c18e72269
1aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//===-- DeclTemplate.h - Classes for representing C++ templates -*- C++ -*-===//
2aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//
3aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//                     The LLVM Compiler Infrastructure
4aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//
5aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor// This file is distributed under the University of Illinois Open Source
6aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor// License. See LICENSE.TXT for details.
7aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//
8aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//===----------------------------------------------------------------------===//
9d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
10d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \file
11d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Defines the C++ template declaration subclasses.
12d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
13aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor//===----------------------------------------------------------------------===//
14aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
15aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor#ifndef LLVM_CLANG_AST_DECLTEMPLATE_H
16aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor#define LLVM_CLANG_AST_DECLTEMPLATE_H
17aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
1855f6b14230c94272efbbcdd89a92224c8db9f225Douglas Gregor#include "clang/AST/DeclCXX.h"
197c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor#include "clang/AST/Redeclarable.h"
20275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall#include "clang/AST/TemplateBase.h"
21f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor#include "llvm/ADT/PointerUnion.h"
22aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar#include "llvm/Support/Compiler.h"
233f3ce82674b44a58a2af7d90feb55acd906dd762Anders Carlsson#include <limits>
2455f6b14230c94272efbbcdd89a92224c8db9f225Douglas Gregor
25aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregornamespace clang {
26aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
27aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass TemplateParameterList;
28aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass TemplateDecl;
299eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourneclass RedeclarableTemplateDecl;
30aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass FunctionTemplateDecl;
31aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass ClassTemplateDecl;
32c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregorclass ClassTemplatePartialSpecializationDecl;
33aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass TemplateTypeParmDecl;
34aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass NonTypeTemplateParmDecl;
35aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass TemplateTemplateParmDecl;
363e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smithclass TypeAliasTemplateDecl;
37aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
38f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor/// \brief Stores a template parameter of any kind.
39f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregortypedef llvm::PointerUnion3<TemplateTypeParmDecl*, NonTypeTemplateParmDecl*,
40f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor                            TemplateTemplateParmDecl*> TemplateParameter;
41f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor
42d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Stores a list of template parameters for a TemplateDecl and its
43d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// derived classes.
44aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorclass TemplateParameterList {
45ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  /// The location of the 'template' keyword.
46ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  SourceLocation TemplateLoc;
47ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor
48ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  /// The locations of the '<' and '>' angle brackets.
49ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  SourceLocation LAngleLoc, RAngleLoc;
50ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor
51ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  /// The number of template parameters in this template
52aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  /// parameter list.
536964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  unsigned NumParams : 31;
546964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
556964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// Whether this template parameter list contains an unexpanded parameter
566964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// pack.
576964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  unsigned ContainsUnexpandedParameterPack : 1;
58aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
59483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smithprotected:
60ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  TemplateParameterList(SourceLocation TemplateLoc, SourceLocation LAngleLoc,
61bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor                        NamedDecl **Params, unsigned NumParams,
62ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor                        SourceLocation RAngleLoc);
63aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
64aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorpublic:
654ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad  static TemplateParameterList *Create(const ASTContext &C,
66ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor                                       SourceLocation TemplateLoc,
67ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor                                       SourceLocation LAngleLoc,
68bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor                                       NamedDecl **Params,
69ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor                                       unsigned NumParams,
70ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor                                       SourceLocation RAngleLoc);
71aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
72d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Iterates through the template parameters in this list.
73bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor  typedef NamedDecl** iterator;
74aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
75d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Iterates through the template parameters in this list.
76bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor  typedef NamedDecl* const* const_iterator;
77aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
78bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor  iterator begin() { return reinterpret_cast<NamedDecl **>(this + 1); }
79aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  const_iterator begin() const {
80bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor    return reinterpret_cast<NamedDecl * const *>(this + 1);
81aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  }
82aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  iterator end() { return begin() + NumParams; }
83aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  const_iterator end() const { return begin() + NumParams; }
84aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
85aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  unsigned size() const { return NumParams; }
86ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor
87bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor  NamedDecl* getParam(unsigned Idx) {
88f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor    assert(Idx < size() && "Template parameter index out-of-range");
89f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor    return begin()[Idx];
90f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor  }
91f67875d5addf36b951ad37fb04509ab2b572c88aDouglas Gregor
92bf4ea56cdc376cef5a12abf6bf18dc34805c2226Douglas Gregor  const NamedDecl* getParam(unsigned Idx) const {
9340808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor    assert(Idx < size() && "Template parameter index out-of-range");
9440808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor    return begin()[Idx];
9540808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor  }
9640808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor
97910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// \brief Returns the minimum number of arguments needed to form a
98d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// template specialization.
99d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  ///
100d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// This may be fewer than the number of template parameters, if some of
101d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// the parameters have default arguments or if there is a parameter pack.
10262cb18dd11472965e03374d40bc27d650bc331b6Douglas Gregor  unsigned getMinRequiredArguments() const;
10362cb18dd11472965e03374d40bc27d650bc331b6Douglas Gregor
104ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \brief Get the depth of this template parameter list in the set of
105ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// template parameter lists.
106ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
107ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// The first template parameter list in a declaration will have depth 0,
108ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// the second template parameter list will have depth 1, etc.
109ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  unsigned getDepth() const;
110ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1116964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Determine whether this template parameter list contains an
1126964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// unexpanded parameter pack.
1136964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  bool containsUnexpandedParameterPack() const {
1146964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    return ContainsUnexpandedParameterPack;
1156964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  }
1166964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
117ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  SourceLocation getTemplateLoc() const { return TemplateLoc; }
118ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  SourceLocation getLAngleLoc() const { return LAngleLoc; }
119ddc29e116db3c3f4144355e67a0137b38b6bb6d1Douglas Gregor  SourceLocation getRAngleLoc() const { return RAngleLoc; }
12062cb18dd11472965e03374d40bc27d650bc331b6Douglas Gregor
121aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY {
12262cb18dd11472965e03374d40bc27d650bc331b6Douglas Gregor    return SourceRange(TemplateLoc, RAngleLoc);
12362cb18dd11472965e03374d40bc27d650bc331b6Douglas Gregor  }
124aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor};
125aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
126d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Stores a list of template parameters for a TemplateDecl and its
127d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// derived classes. Suitable for creating on the stack.
128483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smithtemplate<size_t N>
129483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smithclass FixedSizeTemplateParameterList : public TemplateParameterList {
130483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith  NamedDecl *Params[N];
131483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith
132483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smithpublic:
133ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  FixedSizeTemplateParameterList(SourceLocation TemplateLoc,
134ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie                                 SourceLocation LAngleLoc,
135483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith                                 NamedDecl **Params, SourceLocation RAngleLoc) :
136483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith    TemplateParameterList(TemplateLoc, LAngleLoc, Params, N, RAngleLoc) {
137483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith  }
138483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith};
139483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith
140127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// \brief A template argument list.
141127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorclass TemplateArgumentList {
142127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief The template argument list.
143127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  ///
144127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// The integer value will be non-zero to indicate that this
14556ef550c5eeea0714c635782776389df2a177584Chris Lattner  /// template argument list does own the pointer.
146910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  llvm::PointerIntPair<const TemplateArgument *, 1> Arguments;
1471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
148127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief The number of template arguments in this template
149127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// argument list.
150910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  unsigned NumArguments;
1511eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
152be2fa7ebf01259b63dc52fe46c8d101c18e72269Craig Topper  TemplateArgumentList(const TemplateArgumentList &Other) LLVM_DELETED_FUNCTION;
153be2fa7ebf01259b63dc52fe46c8d101c18e72269Craig Topper  void operator=(const TemplateArgumentList &Other) LLVM_DELETED_FUNCTION;
154910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor
155910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  TemplateArgumentList(const TemplateArgument *Args, unsigned NumArgs,
156910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                       bool Owned)
157910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    : Arguments(Args, Owned), NumArguments(NumArgs) { }
158910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor
159aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregorpublic:
160ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Type used to indicate that the template argument list itself is a
161910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// stack object. It does not own its template arguments.
162910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  enum OnStackType { OnStack };
163910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor
164910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// \brief Create a new template argument list that copies the given set of
165910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// template arguments.
166910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  static TemplateArgumentList *CreateCopy(ASTContext &Context,
167910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                          const TemplateArgument *Args,
168910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                          unsigned NumArgs);
169910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor
170910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// \brief Construct a new, temporary template argument list on the stack.
171910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  ///
172910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// The template argument list does not own the template arguments
173910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// provided.
174ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  explicit TemplateArgumentList(OnStackType,
175910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                const TemplateArgument *Args, unsigned NumArgs)
176910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    : Arguments(Args, false), NumArguments(NumArgs) { }
177ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
178ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Produces a shallow copy of the given template argument list.
179ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  ///
180910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// This operation assumes that the input argument list outlives it.
181910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// This takes the list as a pointer to avoid looking like a copy
182910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// constructor, since this really really isn't safe to use that
183910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// way.
184910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  explicit TemplateArgumentList(const TemplateArgumentList *Other)
185910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    : Arguments(Other->data(), false), NumArguments(Other->size()) { }
1861eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
187127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the template argument at a given index.
1881eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  const TemplateArgument &get(unsigned Idx) const {
189910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    assert(Idx < NumArguments && "Invalid template argument index");
190910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    return data()[Idx];
191127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  }
1921eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
193127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the template argument at a given index.
194127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  const TemplateArgument &operator[](unsigned Idx) const { return get(Idx); }
1951eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
196127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the number of template arguments in this
197127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// template argument list.
198910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  unsigned size() const { return NumArguments; }
1991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
200910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// \brief Retrieve a pointer to the template argument list.
201910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  const TemplateArgument *data() const {
202910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    return Arguments.getPointer();
203127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  }
204127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor};
2051eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
206127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor//===----------------------------------------------------------------------===//
207127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor// Kinds of Templates
208127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor//===----------------------------------------------------------------------===//
209aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
210d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief The base class of all kinds of template declarations (e.g.,
211d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// class, function, etc.).
212d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
213d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// The TemplateDecl class stores the list of template parameters and a
214d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// reference to the templated scoped declaration: the underlying AST node.
215127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorclass TemplateDecl : public NamedDecl {
21699ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie  virtual void anchor();
217127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorprotected:
218127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // This is probably never used.
219127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateDecl(Kind DK, DeclContext *DC, SourceLocation L,
220127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor               DeclarationName Name)
2211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    : NamedDecl(DK, DC, L, Name), TemplatedDecl(0), TemplateParams(0) { }
222d684b0027e16163c4bdba3e2f8bfadda7d62a0d3Douglas Gregor
223127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Construct a template decl with the given name and parameters.
224127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Used when there is not templated element (tt-params, alias?).
225127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateDecl(Kind DK, DeclContext *DC, SourceLocation L,
226127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor               DeclarationName Name, TemplateParameterList *Params)
2271eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    : NamedDecl(DK, DC, L, Name), TemplatedDecl(0), TemplateParams(Params) { }
228d684b0027e16163c4bdba3e2f8bfadda7d62a0d3Douglas Gregor
229127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Construct a template decl with name, parameters, and templated element.
230127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateDecl(Kind DK, DeclContext *DC, SourceLocation L,
231127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor               DeclarationName Name, TemplateParameterList *Params,
232127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor               NamedDecl *Decl)
233127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    : NamedDecl(DK, DC, L, Name), TemplatedDecl(Decl),
234127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor      TemplateParams(Params) { }
235127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorpublic:
236127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// Get the list of template parameters
237127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateParameterList *getTemplateParameters() const {
238127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    return TemplateParams;
239d684b0027e16163c4bdba3e2f8bfadda7d62a0d3Douglas Gregor  }
240d684b0027e16163c4bdba3e2f8bfadda7d62a0d3Douglas Gregor
241127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// Get the underlying, templated declaration.
242127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  NamedDecl *getTemplatedDecl() const { return TemplatedDecl; }
243127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
244aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  // Implement isa/cast/dyncast/etc.
24580cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
246127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const TemplateDecl *D) { return true; }
2479eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classof(const RedeclarableTemplateDecl *D) { return true; }
248127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const FunctionTemplateDecl *D) { return true; }
249127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const ClassTemplateDecl *D) { return true; }
250aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor  static bool classof(const TemplateTemplateParmDecl *D) { return true; }
2513e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static bool classof(const TypeAliasTemplateDecl *D) { return true; }
25280cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) {
2539a55591af3e5506b95a9718e15380129fbfc5ebcSean Hunt    return K >= firstTemplate && K <= lastTemplate;
25480cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  }
255aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
256aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY {
25780484d0de0dccee66d9f1760127c3e6e218987daDouglas Gregor    return SourceRange(TemplateParams->getTemplateLoc(),
25880484d0de0dccee66d9f1760127c3e6e218987daDouglas Gregor                       TemplatedDecl->getSourceRange().getEnd());
25980484d0de0dccee66d9f1760127c3e6e218987daDouglas Gregor  }
26080484d0de0dccee66d9f1760127c3e6e218987daDouglas Gregor
261127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorprotected:
262127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  NamedDecl *TemplatedDecl;
263127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateParameterList* TemplateParams;
264ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
2658731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidispublic:
2668731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  /// \brief Initialize the underlying templated declaration and
2678731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  /// template parameters.
2688731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  void init(NamedDecl *templatedDecl, TemplateParameterList* templateParams) {
2698731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis    assert(TemplatedDecl == 0 && "TemplatedDecl already set!");
2708731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis    assert(TemplateParams == 0 && "TemplateParams already set!");
2718731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis    TemplatedDecl = templatedDecl;
2728731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis    TemplateParams = templateParams;
2738731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  }
274127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor};
2751eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
2761eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// \brief Provides information about a function template specialization,
277127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// which is a FunctionDecl that has been explicitly specialization or
278127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// instantiated from a function template.
279127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorclass FunctionTemplateSpecializationInfo : public llvm::FoldingSetNode {
280a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis  FunctionTemplateSpecializationInfo(FunctionDecl *FD,
281a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis                                     FunctionTemplateDecl *Template,
282a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis                                     TemplateSpecializationKind TSK,
283a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis                                     const TemplateArgumentList *TemplateArgs,
28471a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis                       const ASTTemplateArgumentListInfo *TemplateArgsAsWritten,
285a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis                                     SourceLocation POI)
286a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis  : Function(FD),
287a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis    Template(Template, TSK - 1),
288a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis    TemplateArguments(TemplateArgs),
289a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis    TemplateArgumentsAsWritten(TemplateArgsAsWritten),
290a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis    PointOfInstantiation(POI) { }
291a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis
292127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorpublic:
293a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis  static FunctionTemplateSpecializationInfo *
294a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis  Create(ASTContext &C, FunctionDecl *FD, FunctionTemplateDecl *Template,
295a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis         TemplateSpecializationKind TSK,
296a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis         const TemplateArgumentList *TemplateArgs,
297a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis         const TemplateArgumentListInfo *TemplateArgsAsWritten,
29871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis         SourceLocation POI);
299a626a3d0fb74455651f742c0938902a42e6e71c8Argyrios Kyrtzidis
3001eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  /// \brief The function template specialization that this structure
301127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// describes.
302127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  FunctionDecl *Function;
3031eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3041eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  /// \brief The function template from which this function template
305127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// specialization was generated.
3061fd2dd145d9bcdf0b8d60a88e1795b6ae83656f5Douglas Gregor  ///
307d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  /// The two bits are contain the top 4 values of TemplateSpecializationKind.
308d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  llvm::PointerIntPair<FunctionTemplateDecl *, 2> Template;
3091eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
310127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief The template arguments used to produce the function template
311127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// specialization from the function template.
312127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  const TemplateArgumentList *TemplateArguments;
3131eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
314e03db98d67111ebf7622d9086951aacc24406b66Abramo Bagnara  /// \brief The template arguments as written in the sources, if provided.
31571a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  const ASTTemplateArgumentListInfo *TemplateArgumentsAsWritten;
316e03db98d67111ebf7622d9086951aacc24406b66Abramo Bagnara
317b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// \brief The point at which this function template specialization was
318ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// first instantiated.
319b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  SourceLocation PointOfInstantiation;
320ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
3211fd2dd145d9bcdf0b8d60a88e1795b6ae83656f5Douglas Gregor  /// \brief Retrieve the template from which this function was specialized.
3221fd2dd145d9bcdf0b8d60a88e1795b6ae83656f5Douglas Gregor  FunctionTemplateDecl *getTemplate() const { return Template.getPointer(); }
323d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor
324d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  /// \brief Determine what kind of template specialization this is.
325d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  TemplateSpecializationKind getTemplateSpecializationKind() const {
326d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor    return (TemplateSpecializationKind)(Template.getInt() + 1);
327d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  }
328d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor
3296ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall  bool isExplicitSpecialization() const {
3306ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall    return getTemplateSpecializationKind() == TSK_ExplicitSpecialization;
3316ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall  }
3326ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall
333d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  /// \brief Set the template specialization kind.
334d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  void setTemplateSpecializationKind(TemplateSpecializationKind TSK) {
3351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    assert(TSK != TSK_Undeclared &&
336d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor         "Cannot encode TSK_Undeclared for a function template specialization");
337d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor    Template.setInt(TSK - 1);
3381fd2dd145d9bcdf0b8d60a88e1795b6ae83656f5Douglas Gregor  }
3391eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
340b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// \brief Retrieve the first point of instantiation of this function
341b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// template specialization.
342b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  ///
343b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// The point of instantiation may be an invalid source location if this
344b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// function has yet to be instantiated.
345ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  SourceLocation getPointOfInstantiation() const {
346ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie    return PointOfInstantiation;
347b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  }
348ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
349b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// \brief Set the (first) point of instantiation of this function template
350b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// specialization.
351b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  void setPointOfInstantiation(SourceLocation POI) {
352b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor    PointOfInstantiation = POI;
353b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  }
354ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
355127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  void Profile(llvm::FoldingSetNodeID &ID) {
356910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    Profile(ID, TemplateArguments->data(),
357910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor            TemplateArguments->size(),
3581eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump            Function->getASTContext());
359127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  }
3601eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
3611eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  static void
3621eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  Profile(llvm::FoldingSetNodeID &ID, const TemplateArgument *TemplateArgs,
363828e226ab7ed08b3eb766549e9d3306432137460Douglas Gregor          unsigned NumTemplateArgs, ASTContext &Context) {
364127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    ID.AddInteger(NumTemplateArgs);
365127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    for (unsigned Arg = 0; Arg != NumTemplateArgs; ++Arg)
366828e226ab7ed08b3eb766549e9d3306432137460Douglas Gregor      TemplateArgs[Arg].Profile(ID, Context);
3671eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  }
368127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor};
3691eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
370ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie/// \brief Provides information a specialization of a member of a class
371f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith/// template, which may be a member function, static data member,
372f1c66b40213784a1c4612f04c14cafa2b0e89988Richard Smith/// member class or member enumeration.
3732db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregorclass MemberSpecializationInfo {
37444e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor  // The member declaration from which this member was instantiated, and the
37544e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor  // manner in which the instantiation occurred (in the lower two bits).
37644e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor  llvm::PointerIntPair<NamedDecl *, 2> MemberAndTSK;
377ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
378b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  // The point at which this member was first instantiated.
379b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  SourceLocation PointOfInstantiation;
380ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
3812db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregorpublic:
382ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  explicit
3839421adc43891e272156fab640e5d5ee5054b779cArgyrios Kyrtzidis  MemberSpecializationInfo(NamedDecl *IF, TemplateSpecializationKind TSK,
3849421adc43891e272156fab640e5d5ee5054b779cArgyrios Kyrtzidis                           SourceLocation POI = SourceLocation())
3859421adc43891e272156fab640e5d5ee5054b779cArgyrios Kyrtzidis    : MemberAndTSK(IF, TSK - 1), PointOfInstantiation(POI) {
386ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie    assert(TSK != TSK_Undeclared &&
38744e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor           "Cannot encode undeclared template specializations for members");
38844e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor  }
389ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
3902db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  /// \brief Retrieve the member declaration from which this member was
3912db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  /// instantiated.
39244e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor  NamedDecl *getInstantiatedFrom() const { return MemberAndTSK.getPointer(); }
393ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
3942db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  /// \brief Determine what kind of template specialization this is.
3952db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  TemplateSpecializationKind getTemplateSpecializationKind() const {
39644e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor    return (TemplateSpecializationKind)(MemberAndTSK.getInt() + 1);
3972db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  }
398ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
3992db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  /// \brief Set the template specialization kind.
4002db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  void setTemplateSpecializationKind(TemplateSpecializationKind TSK) {
401ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie    assert(TSK != TSK_Undeclared &&
40244e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor           "Cannot encode undeclared template specializations for members");
40344e368b6a85c42d681148ccd5e0052418ff9751eDouglas Gregor    MemberAndTSK.setInt(TSK - 1);
4042db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor  }
405ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
406ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Retrieve the first point of instantiation of this member.
407b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// If the point of instantiation is an invalid location, then this member
408b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// has not yet been instantiated.
409ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  SourceLocation getPointOfInstantiation() const {
410ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie    return PointOfInstantiation;
411b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  }
412ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
413b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  /// \brief Set the first point of instantiation.
414b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  void setPointOfInstantiation(SourceLocation POI) {
415b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor    PointOfInstantiation = POI;
416b3ae4fcd4314a9c1c46d41b200883599c32025b4Douglas Gregor  }
4172db323294ac02296125e1e0beb4c3595992e75bbDouglas Gregor};
418af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
419af2094e7cecadf36667deb61a83587ffdd979bd3John McCall/// \brief Provides information about a dependent function-template
420d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// specialization declaration.
421d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
422d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// Since explicit function template specialization and instantiation
423d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// declarations can only appear in namespace scope, and you can only
424d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// specialize a member of a fully-specialized class, the only way to
425d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// get one of these is in a friend declaration like the following:
426af2094e7cecadf36667deb61a83587ffdd979bd3John McCall///
427d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \code
428d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///   template \<class T> void foo(T);
429d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///   template \<class T> class A {
430af2094e7cecadf36667deb61a83587ffdd979bd3John McCall///     friend void foo<>(T);
431af2094e7cecadf36667deb61a83587ffdd979bd3John McCall///   };
432d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \endcode
433af2094e7cecadf36667deb61a83587ffdd979bd3John McCallclass DependentFunctionTemplateSpecializationInfo {
434af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  union {
435af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    // Force sizeof to be a multiple of sizeof(void*) so that the
436af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    // trailing data is aligned.
437ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie    void *Aligner;
438af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
439af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    struct {
440af2094e7cecadf36667deb61a83587ffdd979bd3John McCall      /// The number of potential template candidates.
441af2094e7cecadf36667deb61a83587ffdd979bd3John McCall      unsigned NumTemplates;
442af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
443af2094e7cecadf36667deb61a83587ffdd979bd3John McCall      /// The number of template arguments.
444ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie      unsigned NumArgs;
445af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    } d;
446af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  };
447af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
448af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// The locations of the left and right angle brackets.
449af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  SourceRange AngleLocs;
450af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
451af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  FunctionTemplateDecl * const *getTemplates() const {
452af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return reinterpret_cast<FunctionTemplateDecl*const*>(this+1);
453af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
454af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
455af2094e7cecadf36667deb61a83587ffdd979bd3John McCallpublic:
456af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  DependentFunctionTemplateSpecializationInfo(
457af2094e7cecadf36667deb61a83587ffdd979bd3John McCall                                 const UnresolvedSetImpl &Templates,
458af2094e7cecadf36667deb61a83587ffdd979bd3John McCall                                 const TemplateArgumentListInfo &TemplateArgs);
459af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
460af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// \brief Returns the number of function templates that this might
461af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// be a specialization of.
462af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  unsigned getNumTemplates() const {
463af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return d.NumTemplates;
464af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
465af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
466af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// \brief Returns the i'th template candidate.
467af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  FunctionTemplateDecl *getTemplate(unsigned I) const {
468af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    assert(I < getNumTemplates() && "template index out of range");
469af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return getTemplates()[I];
470af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
471af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
472e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor  /// \brief Returns the explicit template arguments that were given.
473e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor  const TemplateArgumentLoc *getTemplateArgs() const {
474e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor    return reinterpret_cast<const TemplateArgumentLoc*>(
475ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie                                            &getTemplates()[getNumTemplates()]);
476e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor  }
477e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor
478af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// \brief Returns the number of explicit template arguments that were given.
479af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  unsigned getNumTemplateArgs() const {
480af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return d.NumArgs;
481af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
482af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
483af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  /// \brief Returns the nth template argument.
484af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  const TemplateArgumentLoc &getTemplateArg(unsigned I) const {
485af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    assert(I < getNumTemplateArgs() && "template arg index out of range");
486af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return getTemplateArgs()[I];
487af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
488af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
489af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  SourceLocation getLAngleLoc() const {
490af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return AngleLocs.getBegin();
491af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
492af2094e7cecadf36667deb61a83587ffdd979bd3John McCall
493af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  SourceLocation getRAngleLoc() const {
494af2094e7cecadf36667deb61a83587ffdd979bd3John McCall    return AngleLocs.getEnd();
495af2094e7cecadf36667deb61a83587ffdd979bd3John McCall  }
496af2094e7cecadf36667deb61a83587ffdd979bd3John McCall};
497ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
4989eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne/// Declaration of a redeclarable template.
4997c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregorclass RedeclarableTemplateDecl : public TemplateDecl,
5007c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor                                 public Redeclarable<RedeclarableTemplateDecl>
5017c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor{
5027c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  typedef Redeclarable<RedeclarableTemplateDecl> redeclarable_base;
5037c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  virtual RedeclarableTemplateDecl *getNextRedeclaration() {
5047c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return RedeclLink.getNext();
5059eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
506ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  virtual RedeclarableTemplateDecl *getPreviousDeclImpl() {
507ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    return getPreviousDecl();
508ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  }
509ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  virtual RedeclarableTemplateDecl *getMostRecentDeclImpl() {
510ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    return getMostRecentDecl();
511ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  }
5121eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
5139eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourneprotected:
51444dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne  template <typename EntryType> struct SpecEntryTraits {
51544dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne    typedef EntryType DeclType;
51644dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne
517ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    static DeclType *getMostRecentDecl(EntryType *D) {
518ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor      return D->getMostRecentDecl();
51944dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne    }
52044dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne  };
52144dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne
5229f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  template <typename EntryType,
5239f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne            typename _SETraits = SpecEntryTraits<EntryType>,
5249f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne            typename _DeclType = typename _SETraits::DeclType>
5259f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  class SpecIterator : public std::iterator<std::forward_iterator_tag,
5269f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne                                            _DeclType*, ptrdiff_t,
5279f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne                                            _DeclType*, _DeclType*> {
5289f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    typedef _SETraits SETraits;
5299f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    typedef _DeclType DeclType;
5309f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
531d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth    typedef typename llvm::FoldingSetVector<EntryType>::iterator
532d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth      SetIteratorType;
5339f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5349f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    SetIteratorType SetIter;
5359f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5369f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  public:
5379f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    SpecIterator() : SetIter() {}
5389f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    SpecIterator(SetIteratorType SetIter) : SetIter(SetIter) {}
5399f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5409f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    DeclType *operator*() const {
541ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor      return SETraits::getMostRecentDecl(&*SetIter);
5429f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    }
5439f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    DeclType *operator->() const { return **this; }
5449f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5459f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    SpecIterator &operator++() { ++SetIter; return *this; }
5469f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    SpecIterator operator++(int) {
5479f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne      SpecIterator tmp(*this);
5489f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne      ++(*this);
5499f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne      return tmp;
5509f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    }
5519f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5529f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    bool operator==(SpecIterator Other) const {
5539f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne      return SetIter == Other.SetIter;
5549f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    }
5559f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    bool operator!=(SpecIterator Other) const {
5569f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne      return SetIter != Other.SetIter;
5579f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    }
5589f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  };
5599f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5609f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  template <typename EntryType>
561d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  SpecIterator<EntryType>
562d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  makeSpecIterator(llvm::FoldingSetVector<EntryType> &Specs, bool isEnd) {
5639f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return SpecIterator<EntryType>(isEnd ? Specs.end() : Specs.begin());
5649f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
5659f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
5664048590d5774fd4b08661b5cf59b6f90b62f283aPeter Collingbourne  template <class EntryType> typename SpecEntryTraits<EntryType>::DeclType*
567d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  findSpecializationImpl(llvm::FoldingSetVector<EntryType> &Specs,
5684048590d5774fd4b08661b5cf59b6f90b62f283aPeter Collingbourne                         const TemplateArgument *Args, unsigned NumArgs,
5694048590d5774fd4b08661b5cf59b6f90b62f283aPeter Collingbourne                         void *&InsertPos);
5704048590d5774fd4b08661b5cf59b6f90b62f283aPeter Collingbourne
5719eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  struct CommonBase {
5729eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    CommonBase() : InstantiatedFromMember(0, false) { }
5739eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
5749eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    /// \brief The template from which this was most
575d60e105e6d1624da647ef7dd35a9cf6fad1b763eDouglas Gregor    /// directly instantiated (or null).
576fd056bc86a8b22a9421b5d921bbca276d0f9d0f7Douglas Gregor    ///
5779eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    /// The boolean value indicates whether this template
578fd056bc86a8b22a9421b5d921bbca276d0f9d0f7Douglas Gregor    /// was explicitly specialized.
5799eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    llvm::PointerIntPair<RedeclarableTemplateDecl*, 1, bool>
5809eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne      InstantiatedFromMember;
5813e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  };
5821eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
5837c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  /// \brief Pointer to the common data shared by all declarations of this
5847c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  /// template.
5857c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  CommonBase *Common;
5867c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor
5879eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieves the "common" pointer shared by all (re-)declarations of
5889eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// the same template. Calling this routine may implicitly allocate memory
5899eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// for the common pointer.
5909eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  CommonBase *getCommonPtr();
5911eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
592da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor  virtual CommonBase *newCommon(ASTContext &C) = 0;
5932c853e401ca406d417eb916e867226050e7be06bArgyrios Kyrtzidis
5949eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  // Construct a template decl with name, parameters, and templated element.
5959eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  RedeclarableTemplateDecl(Kind DK, DeclContext *DC, SourceLocation L,
5969eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne                           DeclarationName Name, TemplateParameterList *Params,
5979eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne                           NamedDecl *Decl)
5987c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    : TemplateDecl(DK, DC, L, Name, Params, Decl), Common() { }
5991eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
6003e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregorpublic:
6019eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  template <class decl_type> friend class RedeclarableTemplate;
6029eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
603d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Retrieves the canonical declaration of this template.
6047c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  RedeclarableTemplateDecl *getCanonicalDecl() { return getFirstDeclaration(); }
6057c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  const RedeclarableTemplateDecl *getCanonicalDecl() const {
6067c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return getFirstDeclaration();
607ba5ff8ccf3f2a4d8fa3e91b58733707fb1caed6bArgyrios Kyrtzidis  }
608ba5ff8ccf3f2a4d8fa3e91b58733707fb1caed6bArgyrios Kyrtzidis
609ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Determines whether this template was a specialization of a
6109eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// member template.
6119eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ///
6129eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// In the following example, the function template \c X<int>::f and the
6139eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// member template \c X<int>::Inner are member specializations.
6149eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ///
6159eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \code
6169eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// template<typename T>
6179eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// struct X {
6189eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ///   template<typename U> void f(T, U);
6199eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ///   template<typename U> struct Inner;
6209eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// };
6219eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ///
6229eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// template<> template<typename T>
6239eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// void X<int>::f(int, T);
6249eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// template<> template<typename T>
6259eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// struct X<int>::Inner { /* ... */ };
6269eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \endcode
6279eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  bool isMemberSpecialization() {
6289eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return getCommonPtr()->InstantiatedFromMember.getInt();
6299eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
630ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
6319eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Note that this member template is a specialization.
6329eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  void setMemberSpecialization() {
6339eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    assert(getCommonPtr()->InstantiatedFromMember.getPointer() &&
6349eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne           "Only member templates can be member template specializations");
6359eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    getCommonPtr()->InstantiatedFromMember.setInt(true);
6369eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
637ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
6380f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \brief Retrieve the member template from which this template was
6390f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// instantiated, or NULL if this template was not instantiated from a
6400f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// member template.
6410f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6420f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// A template is instantiated from a member template when the member
6430f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template itself is part of a class template (or member thereof). For
6440f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// example, given
6450f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6460f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \code
6470f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template<typename T>
6480f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// struct X {
6490f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///   template<typename U> void f(T, U);
6500f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// };
6510f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6520f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// void test(X<int> x) {
6530f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///   x.f(1, 'a');
6540f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// };
6550f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \endcode
6560f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6570f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \c X<int>::f is a FunctionTemplateDecl that describes the function
6580f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template
6590f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6600f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \code
6610f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template<typename U> void X<int>::f(int, U);
6620f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \endcode
6630f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6640f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// which was itself created during the instantiation of \c X<int>. Calling
6650f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// getInstantiatedFromMemberTemplate() on this FunctionTemplateDecl will
666d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// retrieve the FunctionTemplateDecl for the original template \c f within
6670f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// the class template \c X<T>, i.e.,
6680f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  ///
6690f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \code
6700f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template<typename T>
6710f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// template<typename U>
6720f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// void X<T>::f(T, U);
6730f5897bf5f919df28c76013d1efa17441f7241ffDouglas Gregor  /// \endcode
6749eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  RedeclarableTemplateDecl *getInstantiatedFromMemberTemplate() {
6757c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return getCommonPtr()->InstantiatedFromMember.getPointer();
6767c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  }
6777c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor
6787c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  void setInstantiatedFromMemberTemplate(RedeclarableTemplateDecl *TD) {
6797c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    assert(!getCommonPtr()->InstantiatedFromMember.getPointer());
6807c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    getCommonPtr()->InstantiatedFromMember.setPointer(TD);
6819eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
6829eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
683a54fbf2499c7cc999e22abb9be484ce976ed9689Douglas Gregor  typedef redeclarable_base::redecl_iterator redecl_iterator;
684ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  using redeclarable_base::redecls_begin;
685ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  using redeclarable_base::redecls_end;
686ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  using redeclarable_base::getPreviousDecl;
687ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  using redeclarable_base::getMostRecentDecl;
688f785a7d611404cf4747287a2bbc59b4d0e6a5a8cDouglas Gregor
6899eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  // Implement isa/cast/dyncast/etc.
6909eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
6919eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classof(const RedeclarableTemplateDecl *D) { return true; }
6929eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classof(const FunctionTemplateDecl *D) { return true; }
6939eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classof(const ClassTemplateDecl *D) { return true; }
6943e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static bool classof(const TypeAliasTemplateDecl *D) { return true; }
6959eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static bool classofKind(Kind K) {
6969eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return K >= firstRedeclarableTemplate && K <= lastRedeclarableTemplate;
6979eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
6989eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
6997c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor  friend class ASTReader;
700d527cc06d78fe5afa5f20105b51697637eb02c56Sebastian Redl  friend class ASTDeclReader;
7013397c5570369f19b2d6c52e898f708d75ceede1fSebastian Redl  friend class ASTDeclWriter;
7029eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne};
7039eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
70444dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbournetemplate <> struct RedeclarableTemplateDecl::
70544dd0b440efdb37ff4c6e49f243faa3b0580b120Peter CollingbourneSpecEntryTraits<FunctionTemplateSpecializationInfo> {
70644dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne  typedef FunctionDecl DeclType;
70744dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne
70844dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne  static DeclType *
709ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  getMostRecentDecl(FunctionTemplateSpecializationInfo *I) {
710ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor    return I->Function->getMostRecentDecl();
71144dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne  }
71244dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne};
71344dd0b440efdb37ff4c6e49f243faa3b0580b120Peter Collingbourne
7149eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne/// Declaration of a template function.
7157c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregorclass FunctionTemplateDecl : public RedeclarableTemplateDecl {
7169eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  static void DeallocateCommon(void *Ptr);
7179eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7189eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourneprotected:
7199eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Data that is common to all of the declarations of a given
7209eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// function template.
7219eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  struct Common : CommonBase {
722c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    Common() : InjectedArgs(0) { }
723ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
7249eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    /// \brief The function template specializations for this function
7259eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    /// template, including explicit specializations and instantiations.
726d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth    llvm::FoldingSetVector<FunctionTemplateSpecializationInfo> Specializations;
727ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
728c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// \brief The set of "injected" template arguments used within this
729c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// function template.
730c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    ///
731c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// This pointer refers to the template arguments (there are as
732c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// many template arguments as template parameaters) for the function
733c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// template, and is allocated lazily, since most function templates do not
734c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    /// require the use of this information.
735c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor    TemplateArgument *InjectedArgs;
7369eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  };
7379eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7389eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  FunctionTemplateDecl(DeclContext *DC, SourceLocation L, DeclarationName Name,
7399eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne                       TemplateParameterList *Params, NamedDecl *Decl)
7409eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    : RedeclarableTemplateDecl(FunctionTemplate, DC, L, Name, Params, Decl) { }
7419eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7426b5415196327fa8ef00f028ba175fafef1738ae1Argyrios Kyrtzidis  CommonBase *newCommon(ASTContext &C);
7439eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7449eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  Common *getCommonPtr() {
7459eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return static_cast<Common *>(RedeclarableTemplateDecl::getCommonPtr());
746fd056bc86a8b22a9421b5d921bbca276d0f9d0f7Douglas Gregor  }
7479eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7486b5415196327fa8ef00f028ba175fafef1738ae1Argyrios Kyrtzidis  friend class FunctionDecl;
749da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor
7509eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieve the set of function template specializations of this
7519eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// function template.
752d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  llvm::FoldingSetVector<FunctionTemplateSpecializationInfo> &
753d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  getSpecializations() {
7549eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return getCommonPtr()->Specializations;
755fd056bc86a8b22a9421b5d921bbca276d0f9d0f7Douglas Gregor  }
7565bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl
7575bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl  /// \brief Add a specialization of this function template.
7585bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl  ///
759d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  /// \param InsertPos Insert position in the FoldingSetVector, must have been
7605bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl  ///        retrieved by an earlier call to findSpecialization().
7615bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl  void addSpecialization(FunctionTemplateSpecializationInfo* Info,
7625bbcdbf36f8cf79d99703ef20848c55960065e43Sebastian Redl                         void *InsertPos);
763ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
7649eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbournepublic:
7659eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// Get the underlying function declaration of the template.
7669eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  FunctionDecl *getTemplatedDecl() const {
7679eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return static_cast<FunctionDecl*>(TemplatedDecl);
7689eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
7699eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
77013fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  /// Returns whether this template declaration defines the primary
77113fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  /// pattern.
77213fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  bool isThisDeclarationADefinition() const {
77313fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall    return getTemplatedDecl()->isThisDeclarationADefinition();
77413fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  }
77513fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall
7769eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Return the specialization with the provided arguments if it exists,
7779eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// otherwise return the insertion point.
7789eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  FunctionDecl *findSpecialization(const TemplateArgument *Args,
7799eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne                                   unsigned NumArgs, void *&InsertPos);
7809eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7819eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  FunctionTemplateDecl *getCanonicalDecl() {
7827c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<FunctionTemplateDecl>(
7837c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
7849eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
7859eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  const FunctionTemplateDecl *getCanonicalDecl() const {
7867c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<FunctionTemplateDecl>(
7877c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
7889eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
7899eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7909eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieve the previous declaration of this function template, or
7919eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// NULL if no such declaration exists.
792ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  FunctionTemplateDecl *getPreviousDecl() {
7937c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<FunctionTemplateDecl>(
794ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
7959eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
7969eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
7979eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieve the previous declaration of this function template, or
7989eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// NULL if no such declaration exists.
799ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  const FunctionTemplateDecl *getPreviousDecl() const {
8007c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<FunctionTemplateDecl>(
801ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
8029eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
8039eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
8049eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  FunctionTemplateDecl *getInstantiatedFromMemberTemplate() {
8057c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<FunctionTemplateDecl>(
8067c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getInstantiatedFromMemberTemplate());
8079eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
8089eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
8099f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  typedef SpecIterator<FunctionTemplateSpecializationInfo> spec_iterator;
8109f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
8119f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  spec_iterator spec_begin() {
8129f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getSpecializations(), false);
8139f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
8149f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
8159f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  spec_iterator spec_end() {
8169f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getSpecializations(), true);
8179f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
8189f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
819c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  /// \brief Retrieve the "injected" template arguments that correspond to the
820c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  /// template parameters of this function template.
821ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  ///
822c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  /// Although the C++ standard has no notion of the "injected" template
823c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  /// arguments for a function template, the notion is convenient when
824c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  /// we need to perform substitutions inside the definition of a function
825ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// template.
826c494f77363f057dd8619fec4e885c4f80e3d1b66Douglas Gregor  std::pair<const TemplateArgument *, unsigned> getInjectedTemplateArgs();
827ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
8289a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor  /// \brief Create a function template node.
829127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static FunctionTemplateDecl *Create(ASTContext &C, DeclContext *DC,
830127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      SourceLocation L,
831127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      DeclarationName Name,
832127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      TemplateParameterList *Params,
833127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      NamedDecl *Decl);
8343e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
8359a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor  /// \brief Create an empty function template node.
8361e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static FunctionTemplateDecl *CreateDeserialized(ASTContext &C, unsigned ID);
8379a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor
838127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Implement isa/cast/dyncast support
83980cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
84080cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const FunctionTemplateDecl *D) { return true; }
84180cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == FunctionTemplate; }
842c8f9af2943699ff623ca08f2e5ed4d72e0351189Argyrios Kyrtzidis
843d527cc06d78fe5afa5f20105b51697637eb02c56Sebastian Redl  friend class ASTDeclReader;
8443397c5570369f19b2d6c52e898f708d75ceede1fSebastian Redl  friend class ASTDeclWriter;
845127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor};
846d01b1da213aeb71fd40ff7fb78a194613cc1ece7Anders Carlsson
847127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor//===----------------------------------------------------------------------===//
848127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor// Kinds of Template Parameters
849127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor//===----------------------------------------------------------------------===//
85040808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor
851d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Defines the position of a template parameter within a template
852d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// parameter list.
853d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
854d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// Because template parameter can be listed
855127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// sequentially for out-of-line template members, each template parameter is
856127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// given a Depth - the nesting of template parameter scopes - and a Position -
857127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// the occurrence within the parameter list.
858127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// This class is inheritedly privately by different kinds of template
859127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// parameters and is not part of the Decl hierarchy. Just a facility.
8601eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpclass TemplateParmPosition {
861127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorprotected:
862127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // FIXME: This should probably never be called, but it's here as
863127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateParmPosition()
864127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    : Depth(0), Position(0)
865b219cfc4d75f0a03630b7c4509ef791b7e97b2c8David Blaikie  { /* llvm_unreachable("Cannot create positionless template parameter"); */ }
8663e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
867127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateParmPosition(unsigned D, unsigned P)
868127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    : Depth(D), Position(P)
869127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  { }
8703e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
871127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // FIXME: These probably don't need to be ints. int:5 for depth, int:8 for
872127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // position? Maybe?
873127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  unsigned Depth;
874127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  unsigned Position;
8753e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
876127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorpublic:
877127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// Get the nesting depth of the template parameter.
878127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  unsigned getDepth() const { return Depth; }
879b24e199fbd17af780ab000c5862d191e4daffc0fArgyrios Kyrtzidis  void setDepth(unsigned D) { Depth = D; }
8803e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
881127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// Get the position of the template parameter within its parameter list.
882127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  unsigned getPosition() const { return Position; }
883b24e199fbd17af780ab000c5862d191e4daffc0fArgyrios Kyrtzidis  void setPosition(unsigned P) { Position = P; }
8841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
885127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// Get the index of the template parameter within its parameter list.
886127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  unsigned getIndex() const { return Position; }
887127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor};
8883e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
889d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Declaration of a template type parameter.
890d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
891d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// For example, "T" in
892d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \code
893127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// template<typename T> class vector;
894d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \endcode
895127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorclass TemplateTypeParmDecl : public TypeDecl {
896127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Whether this template type parameter was declaration with
897d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// the 'typename' keyword.
898d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  ///
899d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// If false, it was declared with the 'class' keyword.
900127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  bool Typename : 1;
9013e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
902127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Whether this template type parameter inherited its
903127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// default argument.
904127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  bool InheritedDefault : 1;
9053e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
906127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief The default template argument, if any.
907a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  TypeSourceInfo *DefaultArgument;
908127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
909344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara  TemplateTypeParmDecl(DeclContext *DC, SourceLocation KeyLoc,
910344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara                       SourceLocation IdLoc, IdentifierInfo *Id,
9114fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth                       bool Typename)
912344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara    : TypeDecl(TemplateTypeParm, DC, IdLoc, Id, KeyLoc), Typename(Typename),
9134fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth      InheritedDefault(false), DefaultArgument() { }
9143e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
915483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith  /// Sema creates these on the stack during auto type deduction.
916483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith  friend class Sema;
917483b9f3bc05c5409e2c6643f1c9d91e21c8ff9d2Richard Smith
918127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorpublic:
9194ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad  static TemplateTypeParmDecl *Create(const ASTContext &C, DeclContext *DC,
920344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara                                      SourceLocation KeyLoc,
921344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara                                      SourceLocation NameLoc,
922344577e6b58f42d18dc8118c8903b49a85dc005eAbramo Bagnara                                      unsigned D, unsigned P,
923127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      IdentifierInfo *Id, bool Typename,
924127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                      bool ParameterPack);
9251e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static TemplateTypeParmDecl *CreateDeserialized(const ASTContext &C,
9261e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                                  unsigned ID);
927c971f8694661776ecdec2ccc33fbe0333eeaf191Douglas Gregor
928127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Whether this template type parameter was declared with
929d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// the 'typename' keyword.
930d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  ///
931d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// If not, it was declared with the 'class' keyword.
932127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  bool wasDeclaredWithTypename() const { return Typename; }
933c971f8694661776ecdec2ccc33fbe0333eeaf191Douglas Gregor
934127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Determine whether this template parameter has a default
935127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// argument.
936833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  bool hasDefaultArgument() const { return DefaultArgument != 0; }
937199d99192fbcca9f043596c40ead4afab4999dbaDouglas Gregor
938127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the default argument, if any.
939833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  QualType getDefaultArgument() const { return DefaultArgument->getType(); }
94040808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor
941833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// \brief Retrieves the default argument's source information, if any.
942a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  TypeSourceInfo *getDefaultArgumentInfo() const { return DefaultArgument; }
943833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
944833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// \brief Retrieves the location of the default argument declaration.
945833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  SourceLocation getDefaultArgumentLoc() const;
94640808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor
947127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Determines whether the default argument was inherited
948127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// from a previous declaration of this template.
949127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  bool defaultArgumentWasInherited() const { return InheritedDefault; }
950f670c8cfa58b4c224eb8fb566130dc47844dd3deDouglas Gregor
951127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Set the default argument for this template parameter, and
952127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// whether that default argument was inherited from another
953127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// declaration.
954a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  void setDefaultArgument(TypeSourceInfo *DefArg, bool Inherited) {
955127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    DefaultArgument = DefArg;
956127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    InheritedDefault = Inherited;
957f670c8cfa58b4c224eb8fb566130dc47844dd3deDouglas Gregor  }
95840808ce6ac04b102c3b56244a635d6b98eed6d97Douglas Gregor
959833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// \brief Removes the default argument of this template parameter.
960833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  void removeDefaultArgument() {
961833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    DefaultArgument = 0;
962833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    InheritedDefault = false;
963833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
964ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
9658731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  /// \brief Set whether this template type parameter was declared with
9668731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  /// the 'typename' or 'class' keyword.
9678731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis  void setDeclaredWithTypename(bool withTypename) { Typename = withTypename; }
9688731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis
969ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \brief Retrieve the depth of the template parameter.
970ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  unsigned getDepth() const;
971ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
972ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \brief Retrieve the index of the template parameter.
973ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  unsigned getIndex() const;
974ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor
975127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Returns whether this is a parameter pack.
9764fb86f8c4585e53c21c847ad3de9e3b2de123cd9Chandler Carruth  bool isParameterPack() const;
977fb25052736439d72a557cddd41dfb927bcb3d3e5Anders Carlsson
978aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY;
97977d4ee2bfc90b77ec8b818de985cd4aceeef757bAbramo Bagnara
980127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Implement isa/cast/dyncast/etc.
98180cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
982127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const TemplateTypeParmDecl *D) { return true; }
98380cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == TemplateTypeParm; }
9843e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor};
9853e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
986127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// NonTypeTemplateParmDecl - Declares a non-type template parameter,
987127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// e.g., "Size" in
988127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// @code
989127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// template<int Size> class array { };
990127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// @endcode
991127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorclass NonTypeTemplateParmDecl
99276a40219ee5624d78aba167dce02bdbaa930955fJohn McCall  : public DeclaratorDecl, protected TemplateParmPosition {
993d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief The default template argument, if any, and whether or not
994d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// it was inherited.
995d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  llvm::PointerIntPair<Expr*, 1, bool> DefaultArgumentAndInherited;
996127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
99710738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  // FIXME: Collapse this into TemplateParamPosition; or, just move depth/index
99810738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  // down here to save memory.
999ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
100010738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// \brief Whether this non-type template parameter is a parameter pack.
100110738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  bool ParameterPack;
1002ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1003ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Whether this non-type template parameter is an "expanded"
10046952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// parameter pack, meaning that its type is a pack expansion and we
10056952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// already know the set of types that expansion expands to.
10066952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  bool ExpandedParameterPack;
1007ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
10086952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// \brief The number of types in an expanded parameter pack.
10096952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  unsigned NumExpandedTypes;
1010ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1011ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara  NonTypeTemplateParmDecl(DeclContext *DC, SourceLocation StartLoc,
1012ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara                          SourceLocation IdLoc, unsigned D, unsigned P,
1013ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara                          IdentifierInfo *Id, QualType T,
101410738d36b150aa65206890c1c845cdba076e4200Douglas Gregor                          bool ParameterPack, TypeSourceInfo *TInfo)
1015ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara    : DeclaratorDecl(NonTypeTemplateParm, DC, IdLoc, Id, T, TInfo, StartLoc),
101610738d36b150aa65206890c1c845cdba076e4200Douglas Gregor      TemplateParmPosition(D, P), DefaultArgumentAndInherited(0, false),
10176952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor      ParameterPack(ParameterPack), ExpandedParameterPack(false),
10186952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor      NumExpandedTypes(0)
1019127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  { }
1020127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
1021ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara  NonTypeTemplateParmDecl(DeclContext *DC, SourceLocation StartLoc,
1022ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara                          SourceLocation IdLoc, unsigned D, unsigned P,
1023ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara                          IdentifierInfo *Id, QualType T,
10246952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor                          TypeSourceInfo *TInfo,
10256952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor                          const QualType *ExpandedTypes,
10266952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor                          unsigned NumExpandedTypes,
10276952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor                          TypeSourceInfo **ExpandedTInfos);
10286952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor
102910738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  friend class ASTDeclReader;
1030ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
10311c5976e5e933c0d74f7e04e8f907a93f5edbfec1Anders Carlssonpublic:
1032127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static NonTypeTemplateParmDecl *
1033ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara  Create(const ASTContext &C, DeclContext *DC, SourceLocation StartLoc,
1034ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara         SourceLocation IdLoc, unsigned D, unsigned P, IdentifierInfo *Id,
1035ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara         QualType T, bool ParameterPack, TypeSourceInfo *TInfo);
10369ba41645892da0000fe8a7832b80208f44dafedaAnders Carlsson
10376952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  static NonTypeTemplateParmDecl *
1038ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara  Create(const ASTContext &C, DeclContext *DC, SourceLocation StartLoc,
1039ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara         SourceLocation IdLoc, unsigned D, unsigned P, IdentifierInfo *Id,
1040ff676cb48fe8bf7be2feaa251dc7c5fb15af4730Abramo Bagnara         QualType T, TypeSourceInfo *TInfo,
10416952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor         const QualType *ExpandedTypes, unsigned NumExpandedTypes,
10426952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor         TypeSourceInfo **ExpandedTInfos);
10436952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor
10441e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static NonTypeTemplateParmDecl *CreateDeserialized(ASTContext &C,
10451e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                                     unsigned ID);
10461e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static NonTypeTemplateParmDecl *CreateDeserialized(ASTContext &C,
10471e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                                     unsigned ID,
10481e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                                     unsigned NumExpandedTypes);
10491e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor
1050127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getDepth;
1051b24e199fbd17af780ab000c5862d191e4daffc0fArgyrios Kyrtzidis  using TemplateParmPosition::setDepth;
1052127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getPosition;
1053b24e199fbd17af780ab000c5862d191e4daffc0fArgyrios Kyrtzidis  using TemplateParmPosition::setPosition;
1054127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getIndex;
10551eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1056aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY;
105776a40219ee5624d78aba167dce02bdbaa930955fJohn McCall
1058127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Determine whether this template parameter has a default
1059127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// argument.
1060d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  bool hasDefaultArgument() const {
1061d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return DefaultArgumentAndInherited.getPointer() != 0;
1062d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1063fb25052736439d72a557cddd41dfb927bcb3d3e5Anders Carlsson
1064127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the default argument, if any.
1065d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  Expr *getDefaultArgument() const {
1066d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return DefaultArgumentAndInherited.getPointer();
1067d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1068127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
1069127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the location of the default argument, if any.
1070127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  SourceLocation getDefaultArgumentLoc() const;
1071127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
1072d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Determines whether the default argument was inherited
1073d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// from a previous declaration of this template.
1074d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  bool defaultArgumentWasInherited() const {
1075d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return DefaultArgumentAndInherited.getInt();
1076d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1077d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara
1078d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Set the default argument for this template parameter, and
1079d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// whether that default argument was inherited from another
1080d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// declaration.
1081d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  void setDefaultArgument(Expr *DefArg, bool Inherited) {
1082d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentAndInherited.setPointer(DefArg);
1083d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentAndInherited.setInt(Inherited);
1084d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1085d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara
1086d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Removes the default argument of this template parameter.
1087d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  void removeDefaultArgument() {
1088d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentAndInherited.setPointer(0);
1089d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentAndInherited.setInt(false);
10903b36b66a00b7d5bab71b486a54694f0ae397bddbAnders Carlsson  }
1091127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor
109210738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// \brief Whether this parameter is a non-type template parameter pack.
109310738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  ///
109410738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// If the parameter is a parameter pack, the type may be a
109510738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// \c PackExpansionType. In the following example, the \c Dims parameter
109610738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// is a parameter pack (whose type is 'unsigned').
109710738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  ///
109810738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// \code
109910738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// template<typename T, unsigned ...Dims> struct multi_array;
110010738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  /// \endcode
110110738d36b150aa65206890c1c845cdba076e4200Douglas Gregor  bool isParameterPack() const { return ParameterPack; }
1102ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
11036964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Whether this parameter pack is a pack expansion.
11046964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///
11056964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// A non-type template parameter pack is a pack expansion if its type
11066964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// contains an unexpanded parameter pack. In this case, we will have
11076964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// built a PackExpansionType wrapping the type.
11086964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  bool isPackExpansion() const {
11096964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    return ParameterPack && getType()->getAs<PackExpansionType>();
11106964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  }
11116964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
11126952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// \brief Whether this parameter is a non-type template parameter pack
11136964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// that has a known list of different types at different positions.
11146952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  ///
11156952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// A parameter pack is an expanded parameter pack when the original
11166952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// parameter pack's type was itself a pack expansion, and that expansion
11176952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// has already been expanded. For example, given:
11186952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  ///
11196952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// \code
11206952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// template<typename ...Types>
11216952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// struct X {
11226952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  ///   template<Types ...Values>
11236952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  ///   struct Y { /* ... */ };
11246952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// };
11256952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// \endcode
1126ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  ///
11276952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// The parameter pack \c Values has a \c PackExpansionType as its type,
11286952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// which expands \c Types. When \c Types is supplied with template arguments
1129ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// by instantiating \c X, the instantiation of \c Values becomes an
1130ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// expanded parameter pack. For example, instantiating
11316952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// \c X<int, unsigned int> results in \c Values being an expanded parameter
11326952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// pack with expansion types \c int and \c unsigned int.
11336952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  ///
1134ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// The \c getExpansionType() and \c getExpansionTypeSourceInfo() functions
11356952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// return the expansion types.
11366952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  bool isExpandedParameterPack() const { return ExpandedParameterPack; }
1137ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1138ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Retrieves the number of expansion types in an expanded parameter
1139ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// pack.
11406952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  unsigned getNumExpansionTypes() const {
11416952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    assert(ExpandedParameterPack && "Not an expansion parameter pack");
11426952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    return NumExpandedTypes;
11436952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  }
11446952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor
1145ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Retrieve a particular expansion type within an expanded parameter
11466952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// pack.
11476952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  QualType getExpansionType(unsigned I) const {
11486952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    assert(I < NumExpandedTypes && "Out-of-range expansion type index");
11496952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    void * const *TypesAndInfos = reinterpret_cast<void * const*>(this + 1);
11506952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    return QualType::getFromOpaquePtr(TypesAndInfos[2*I]);
11516952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  }
11526952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor
1153ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Retrieve a particular expansion type source info within an
11546952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  /// expanded parameter pack.
11556952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  TypeSourceInfo *getExpansionTypeSourceInfo(unsigned I) const {
11566952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    assert(I < NumExpandedTypes && "Out-of-range expansion type index");
11576952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    void * const *TypesAndInfos = reinterpret_cast<void * const*>(this + 1);
11586952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor    return static_cast<TypeSourceInfo *>(TypesAndInfos[2*I+1]);
11596952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor  }
11606952f1e4256c5b43aee5e98cea4e9b663bd1d413Douglas Gregor
1161127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Implement isa/cast/dyncast/etc.
116280cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1163127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const NonTypeTemplateParmDecl *D) { return true; }
116480cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == NonTypeTemplateParm; }
11651c5976e5e933c0d74f7e04e8f907a93f5edbfec1Anders Carlsson};
11661c5976e5e933c0d74f7e04e8f907a93f5edbfec1Anders Carlsson
1167127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// TemplateTemplateParmDecl - Declares a template template parameter,
1168127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// e.g., "T" in
1169127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// @code
1170127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// template <template <typename> class T> class container { };
1171127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// @endcode
1172127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// A template template parameter is a TemplateDecl because it defines the
1173127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor/// name of a template and the template parameters allowable for substitution.
11741e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregorclass TemplateTemplateParmDecl : public TemplateDecl,
11751e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                 protected TemplateParmPosition
11761e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor{
117799ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie  virtual void anchor();
11787e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
1179d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// DefaultArgument - The default template argument, if any.
1180788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  TemplateArgumentLoc DefaultArgument;
1181d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// Whether or not the default argument was inherited.
1182d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  bool DefaultArgumentWasInherited;
11837e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
118461c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor  /// \brief Whether this parameter is a parameter pack.
118561c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor  bool ParameterPack;
1186ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
11876964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Whether this template template parameter is an "expanded"
11886964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// parameter pack, meaning that it is a pack expansion and we
11896964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// already know the set of template parameters that expansion expands to.
11906964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  bool ExpandedParameterPack;
11916964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
11926964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief The number of parameters in an expanded parameter pack.
11936964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  unsigned NumExpandedParams;
11946964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
1195127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  TemplateTemplateParmDecl(DeclContext *DC, SourceLocation L,
119661c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor                           unsigned D, unsigned P, bool ParameterPack,
1197127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                           IdentifierInfo *Id, TemplateParameterList *Params)
1198127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    : TemplateDecl(TemplateTemplateParm, DC, L, Id, Params),
1199d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara      TemplateParmPosition(D, P), DefaultArgument(),
12006964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith      DefaultArgumentWasInherited(false), ParameterPack(ParameterPack),
12016964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith      ExpandedParameterPack(false), NumExpandedParams(0)
1202127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    { }
12037e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
12046964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  TemplateTemplateParmDecl(DeclContext *DC, SourceLocation L,
12056964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                           unsigned D, unsigned P,
12066964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                           IdentifierInfo *Id, TemplateParameterList *Params,
12076964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                           unsigned NumExpansions,
12086964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                           TemplateParameterList * const *Expansions);
12096964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
1210127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregorpublic:
12114ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad  static TemplateTemplateParmDecl *Create(const ASTContext &C, DeclContext *DC,
1212127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                          SourceLocation L, unsigned D,
121361c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor                                          unsigned P, bool ParameterPack,
121461c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor                                          IdentifierInfo *Id,
1215127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor                                          TemplateParameterList *Params);
12166964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  static TemplateTemplateParmDecl *Create(const ASTContext &C, DeclContext *DC,
12176964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                          SourceLocation L, unsigned D,
12186964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                          unsigned P,
12196964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                          IdentifierInfo *Id,
12206964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                          TemplateParameterList *Params,
12216964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                             llvm::ArrayRef<TemplateParameterList*> Expansions);
12227e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
12236964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  static TemplateTemplateParmDecl *CreateDeserialized(ASTContext &C,
12241e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor                                                      unsigned ID);
12256964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  static TemplateTemplateParmDecl *CreateDeserialized(ASTContext &C,
12266964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                                      unsigned ID,
12276964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith                                                      unsigned NumExpansions);
12281e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor
1229127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getDepth;
1230127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getPosition;
1231127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  using TemplateParmPosition::getIndex;
12321eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
1233d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// \brief Whether this template template parameter is a template
1234d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// parameter pack.
1235d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  ///
1236d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// \code
1237d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// template<template <class T> ...MetaFunctions> struct Apply;
1238d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// \endcode
123961c4d28e36cd3f1be392cb77f07436d1fa6b0f9fDouglas Gregor  bool isParameterPack() const { return ParameterPack; }
1240d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor
12416964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Whether this parameter pack is a pack expansion.
12426964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///
12436964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// A template template parameter pack is a pack expansion if its template
12446964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// parameter list contains an unexpanded parameter pack.
12456964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  bool isPackExpansion() const {
12466964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    return ParameterPack &&
12476964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith           getTemplateParameters()->containsUnexpandedParameterPack();
12486964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  }
12496964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
12506964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Whether this parameter is a template template parameter pack that
12516964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// has a known list of different template parameter lists at different
12526964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// positions.
12536964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///
12546964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// A parameter pack is an expanded parameter pack when the original parameter
12556964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// pack's template parameter list was itself a pack expansion, and that
12566964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// expansion has already been expanded. For exampe, given:
12576964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///
12586964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \code
12596964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// template<typename...Types> struct Outer {
12606964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///   template<template<Types> class...Templates> struct Inner;
12616964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// };
12626964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \endcode
12636964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  ///
12646964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// The parameter pack \c Templates is a pack expansion, which expands the
12656964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// pack \c Types. When \c Types is supplied with template arguments by
12666964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// instantiating \c Outer, the instantiation of \c Templates is an expanded
12676964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// parameter pack.
12686964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  bool isExpandedParameterPack() const { return ExpandedParameterPack; }
12696964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
12706964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Retrieves the number of expansion template parameters in
12716964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// an expanded parameter pack.
12726964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  unsigned getNumExpansionTemplateParameters() const {
12736964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    assert(ExpandedParameterPack && "Not an expansion parameter pack");
12746964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    return NumExpandedParams;
12756964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  }
12766964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
12776964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// \brief Retrieve a particular expansion type within an expanded parameter
12786964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  /// pack.
12796964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  TemplateParameterList *getExpansionTemplateParameters(unsigned I) const {
12806964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    assert(I < NumExpandedParams && "Out-of-range expansion type index");
12816964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith    return reinterpret_cast<TemplateParameterList *const *>(this + 1)[I];
12826964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith  }
12836964b3f80ce1ba489e7e25e7cd58062699af9b0cRichard Smith
1284127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Determine whether this template parameter has a default
1285127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// argument.
1286d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  bool hasDefaultArgument() const {
1287d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return !DefaultArgument.getArgument().isNull();
1288788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
12897e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
1290127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  /// \brief Retrieve the default argument, if any.
1291d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  const TemplateArgumentLoc &getDefaultArgument() const {
1292d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return DefaultArgument;
1293d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1294d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara
1295d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Retrieve the location of the default argument, if any.
1296d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  SourceLocation getDefaultArgumentLoc() const;
1297d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara
1298d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Determines whether the default argument was inherited
1299d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// from a previous declaration of this template.
1300d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  bool defaultArgumentWasInherited() const {
1301d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    return DefaultArgumentWasInherited;
1302788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
13037e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
1304d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Set the default argument for this template parameter, and
1305d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// whether that default argument was inherited from another
1306d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// declaration.
1307d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  void setDefaultArgument(const TemplateArgumentLoc &DefArg, bool Inherited) {
1308127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor    DefaultArgument = DefArg;
1309d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentWasInherited = Inherited;
1310d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  }
1311d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara
1312d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  /// \brief Removes the default argument of this template parameter.
1313d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara  void removeDefaultArgument() {
1314d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgument = TemplateArgumentLoc();
1315d92f7a297c0ed3f7d0ebcbb557e1d4c1925b8c72Abramo Bagnara    DefaultArgumentWasInherited = false;
1316127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  }
13177e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
1318aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY {
1319fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor    SourceLocation End = getLocation();
1320fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor    if (hasDefaultArgument() && !defaultArgumentWasInherited())
1321fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor      End = getDefaultArgument().getSourceRange().getEnd();
1322fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor    return SourceRange(getTemplateParameters()->getTemplateLoc(), End);
1323fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor  }
1324fe72e9ceeae6cc8669cd8bb722425300190638eaDouglas Gregor
1325127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  // Implement isa/cast/dyncast/etc.
132680cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
1327127102b5196ffe04bdb70fd553fe62c265ab10a9Douglas Gregor  static bool classof(const TemplateTemplateParmDecl *D) { return true; }
132880cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == TemplateTemplateParm; }
1329bfcc92c3476ada55ceeea49e43e6d2e083252830Argyrios Kyrtzidis
1330d527cc06d78fe5afa5f20105b51697637eb02c56Sebastian Redl  friend class ASTDeclReader;
13313397c5570369f19b2d6c52e898f708d75ceede1fSebastian Redl  friend class ASTDeclWriter;
13327e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor};
13337e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor
13343e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// \brief Represents a class template specialization, which refers to
13353e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// a class template with a given set of template arguments.
13363e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor///
13373e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// Class template specializations represent both explicit
13383e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// specialization of class templates, as in the example below, and
13393e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// implicit instantiations of class templates.
13403e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor///
13413e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// \code
13423e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// template<typename T> class array;
13431eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump///
13441eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump/// template<>
13453e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// class array<bool> { }; // class template specialization array<bool>
13463e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// \endcode
13471eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpclass ClassTemplateSpecializationDecl
13483e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  : public CXXRecordDecl, public llvm::FoldingSetNode {
13491eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13501eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  /// \brief Structure that stores information about a class template
135137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// specialization that was instantiated from a class template partial
135237d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// specialization.
135337d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  struct SpecializedPartialSpecialization {
135437d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    /// \brief The class template partial specialization from which this
135537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    /// class template specialization was instantiated.
135637d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    ClassTemplatePartialSpecializationDecl *PartialSpecialization;
13571eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
135837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    /// \brief The template argument list deduced for the class template
135937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    /// partial specialization itself.
136037d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    TemplateArgumentList *TemplateArgs;
136137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  };
13621eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
13633e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  /// \brief The template that this specialization specializes
136437d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  llvm::PointerUnion<ClassTemplateDecl *, SpecializedPartialSpecialization *>
136537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    SpecializedTemplate;
13663e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
1367c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Further info for explicit template specialization/instantiation.
1368c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  struct ExplicitSpecializationInfo {
1369c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    /// \brief The type-as-written.
1370c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    TypeSourceInfo *TypeAsWritten;
1371c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    /// \brief The location of the extern keyword.
1372c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    SourceLocation ExternLoc;
1373c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    /// \brief The location of the template keyword.
1374c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    SourceLocation TemplateKeywordLoc;
1375c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara
1376c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    ExplicitSpecializationInfo()
1377c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara      : TypeAsWritten(0), ExternLoc(), TemplateKeywordLoc() {}
1378c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  };
1379c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara
1380c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Further info for explicit template specialization/instantiation.
13813cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// Does not apply to implicit specializations.
1382c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  ExplicitSpecializationInfo *ExplicitInfo;
13833cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall
13847e06390f8a60440d6fc5f0e633acdc2edd8ee924Douglas Gregor  /// \brief The template arguments used to describe this specialization.
1385910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  TemplateArgumentList *TemplateArgs;
1386cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
13879cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  /// \brief The point where this template was instantiated (if any)
13889cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  SourceLocation PointOfInstantiation;
13899cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall
1390cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  /// \brief The kind of specialization this declaration refers to.
1391cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  /// Really a value of type TemplateSpecializationKind.
1392d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor  unsigned SpecializationKind : 3;
1393cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
1394c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregorprotected:
139513c8577201e4fc0ddac5f09d05fd1778832137d1Douglas Gregor  ClassTemplateSpecializationDecl(ASTContext &Context, Kind DK, TagKind TK,
1396ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara                                  DeclContext *DC, SourceLocation StartLoc,
1397ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara                                  SourceLocation IdLoc,
13983e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor                                  ClassTemplateDecl *SpecializedTemplate,
1399910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                  const TemplateArgument *Args,
1400910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                  unsigned NumArgs,
14018e9e9ef5348bce1a8f0741a5684fac3de9701c28Douglas Gregor                                  ClassTemplateSpecializationDecl *PrevDecl);
14021eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
140394d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  explicit ClassTemplateSpecializationDecl(Kind DK);
140494d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
14053e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregorpublic:
14063e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  static ClassTemplateSpecializationDecl *
1407ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara  Create(ASTContext &Context, TagKind TK, DeclContext *DC,
1408ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara         SourceLocation StartLoc, SourceLocation IdLoc,
14093e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor         ClassTemplateDecl *SpecializedTemplate,
1410910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor         const TemplateArgument *Args,
1411910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor         unsigned NumArgs,
1412cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor         ClassTemplateSpecializationDecl *PrevDecl);
1413b8b03e6df1cc89e701a809c6a47c41f31b7a9e50Argyrios Kyrtzidis  static ClassTemplateSpecializationDecl *
14141e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  CreateDeserialized(ASTContext &C, unsigned ID);
141594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
1416da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor  virtual void getNameForDiagnostic(std::string &S,
1417da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor                                    const PrintingPolicy &Policy,
1418da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor                                    bool Qualified) const;
1419da2142f2e2b3a02ee6eb5de9f9e6ed6f7eb5a0c0Douglas Gregor
1420ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  ClassTemplateSpecializationDecl *getMostRecentDecl() {
1421cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    CXXRecordDecl *Recent
1422ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor        = cast<CXXRecordDecl>(CXXRecordDecl::getMostRecentDecl());
1423cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    if (!isa<ClassTemplateSpecializationDecl>(Recent)) {
1424cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis      // FIXME: Does injected class name need to be in the redeclarations chain?
1425ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor      assert(Recent->isInjectedClassName() && Recent->getPreviousDecl());
1426ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor      Recent = Recent->getPreviousDecl();
1427cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    }
1428cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    return cast<ClassTemplateSpecializationDecl>(Recent);
1429cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  }
1430cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
14313e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  /// \brief Retrieve the template that this specialization specializes.
143237d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  ClassTemplateDecl *getSpecializedTemplate() const;
14333e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
14341eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  /// \brief Retrieve the template arguments of the class template
143537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// specialization.
14361eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  const TemplateArgumentList &getTemplateArgs() const {
1437910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    return *TemplateArgs;
14383e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  }
14393e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
1440cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  /// \brief Determine the kind of specialization that this
1441cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  /// declaration represents.
1442cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  TemplateSpecializationKind getSpecializationKind() const {
1443cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor    return static_cast<TemplateSpecializationKind>(SpecializationKind);
1444cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  }
1445cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
14466ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall  bool isExplicitSpecialization() const {
14476ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall    return getSpecializationKind() == TSK_ExplicitSpecialization;
14486ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall  }
14496ce51ee94bd300c5f30930d96436fd53e4ea89a7John McCall
1450cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  void setSpecializationKind(TemplateSpecializationKind TSK) {
1451cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor    SpecializationKind = TSK;
1452cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor  }
1453cc636688c4fd10b1732ce3e33b2b106024d545caDouglas Gregor
14549cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  /// \brief Get the point of instantiation (if any), or null if none.
14559cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  SourceLocation getPointOfInstantiation() const {
14569cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall    return PointOfInstantiation;
14579cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  }
14589cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall
14599cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  void setPointOfInstantiation(SourceLocation Loc) {
14609cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall    assert(Loc.isValid() && "point of instantiation must be valid!");
14619cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall    PointOfInstantiation = Loc;
14629cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall  }
14639cc7807e1622c2f945b607bdd39dd283df5e7bb5John McCall
146437d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// \brief If this class template specialization is an instantiation of
146537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// a template (rather than an explicit specialization), return the
146637d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// class template or class template partial specialization from which it
146737d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// was instantiated.
14681eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  llvm::PointerUnion<ClassTemplateDecl *,
146937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor                     ClassTemplatePartialSpecializationDecl *>
147037d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  getInstantiatedFrom() const {
147137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    if (getSpecializationKind() != TSK_ImplicitInstantiation &&
1472d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor        getSpecializationKind() != TSK_ExplicitInstantiationDefinition &&
1473d0e3daf2b980b505e535d35b432c938c6d0208efDouglas Gregor        getSpecializationKind() != TSK_ExplicitInstantiationDeclaration)
1474e0329acf5c9437e2086a2fb2bf7a95ae2ac96505Douglas Gregor      return llvm::PointerUnion<ClassTemplateDecl *,
1475e0329acf5c9437e2086a2fb2bf7a95ae2ac96505Douglas Gregor                                ClassTemplatePartialSpecializationDecl *>();
14761eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
14771eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    if (SpecializedPartialSpecialization *PartialSpec
147837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor          = SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
147937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor      return PartialSpec->PartialSpecialization;
14801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
148137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    return const_cast<ClassTemplateDecl*>(
148237d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor                             SpecializedTemplate.get<ClassTemplateDecl*>());
148337d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  }
14841eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
148594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  /// \brief Retrieve the class template or class template partial
148694d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  /// specialization which was specialized by this.
148794d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  llvm::PointerUnion<ClassTemplateDecl *,
148894d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis                     ClassTemplatePartialSpecializationDecl *>
148994d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  getSpecializedTemplateOrPartial() const {
149094d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    if (SpecializedPartialSpecialization *PartialSpec
149194d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis          = SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
149294d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis      return PartialSpec->PartialSpecialization;
149394d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
149494d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    return const_cast<ClassTemplateDecl*>(
149594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis                             SpecializedTemplate.get<ClassTemplateDecl*>());
149694d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  }
149794d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
149837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// \brief Retrieve the set of template arguments that should be used
149937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// to instantiate members of the class template or class template partial
150037d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// specialization from which this class template specialization was
150137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// instantiated.
150237d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  ///
150337d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// \returns For a class template specialization instantiated from the primary
150437d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// template, this function will return the same template arguments as
150537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// getTemplateArgs(). For a class template specialization instantiated from
150637d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// a class template partial specialization, this function will return the
150737d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// deduced template arguments for the class template partial specialization
150837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// itself.
150937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  const TemplateArgumentList &getTemplateInstantiationArgs() const {
15101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    if (SpecializedPartialSpecialization *PartialSpec
151137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor        = SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
151237d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor      return *PartialSpec->TemplateArgs;
15131eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
151437d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    return getTemplateArgs();
151537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  }
15161eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
151737d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// \brief Note that this class template specialization is actually an
151837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// instantiation of the given class template partial specialization whose
151937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  /// template arguments have been deduced.
152037d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  void setInstantiationOf(ClassTemplatePartialSpecializationDecl *PartialSpec,
152137d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor                          TemplateArgumentList *TemplateArgs) {
152294d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    assert(!SpecializedTemplate.is<SpecializedPartialSpecialization*>() &&
152394d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis           "Already set to a class template partial specialization!");
15241eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump    SpecializedPartialSpecialization *PS
152537d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor      = new (getASTContext()) SpecializedPartialSpecialization();
152637d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    PS->PartialSpecialization = PartialSpec;
152737d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    PS->TemplateArgs = TemplateArgs;
152837d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor    SpecializedTemplate = PS;
152937d93e9252026d4fb836d9c05d0122a2d46e56beDouglas Gregor  }
15301eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
153194d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  /// \brief Note that this class template specialization is an instantiation
153294d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  /// of the given class template.
153394d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  void setInstantiationOf(ClassTemplateDecl *TemplDecl) {
153494d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    assert(!SpecializedTemplate.is<SpecializedPartialSpecialization*>() &&
153594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis           "Previously set to a class template partial specialization!");
153694d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    SpecializedTemplate = TemplDecl;
153794d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  }
153894d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
1539fc705b84347e6fb4746a1a7e26949f64c2f2f358Douglas Gregor  /// \brief Sets the type of this specialization as it was written by
1540fc705b84347e6fb4746a1a7e26949f64c2f2f358Douglas Gregor  /// the user. This will be a class template specialization type.
15413cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  void setTypeAsWritten(TypeSourceInfo *T) {
1542db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek    if (!ExplicitInfo)
1543db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek      ExplicitInfo = new (getASTContext()) ExplicitSpecializationInfo;
1544c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    ExplicitInfo->TypeAsWritten = T;
15453cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  }
15463cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// \brief Gets the type of this specialization as it was written by
15473cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// the user, if it was so written.
15483cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  TypeSourceInfo *getTypeAsWritten() const {
1549c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    return ExplicitInfo ? ExplicitInfo->TypeAsWritten : 0;
1550c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  }
1551c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara
1552c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Gets the location of the extern keyword, if present.
1553c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  SourceLocation getExternLoc() const {
1554c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    return ExplicitInfo ? ExplicitInfo->ExternLoc : SourceLocation();
1555c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  }
1556c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Sets the location of the extern keyword.
1557c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  void setExternLoc(SourceLocation Loc) {
1558db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek    if (!ExplicitInfo)
1559db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek      ExplicitInfo = new (getASTContext()) ExplicitSpecializationInfo;
1560c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    ExplicitInfo->ExternLoc = Loc;
1561c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  }
1562c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara
1563c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Sets the location of the template keyword.
1564c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  void setTemplateKeywordLoc(SourceLocation Loc) {
1565db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek    if (!ExplicitInfo)
1566db1423008b6185fc570558cff77d92f94e55b386Ted Kremenek      ExplicitInfo = new (getASTContext()) ExplicitSpecializationInfo;
1567c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    ExplicitInfo->TemplateKeywordLoc = Loc;
1568c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  }
1569c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  /// \brief Gets the location of the template keyword, if present.
1570c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara  SourceLocation getTemplateKeywordLoc() const {
1571c98971d5c994caed9452aeadd0122c855e0f4de1Abramo Bagnara    return ExplicitInfo ? ExplicitInfo->TemplateKeywordLoc : SourceLocation();
1572fc705b84347e6fb4746a1a7e26949f64c2f2f358Douglas Gregor  }
1573fc705b84347e6fb4746a1a7e26949f64c2f2f358Douglas Gregor
1574aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY;
15754a85a73466bfb541cd9c7b57a99292a0b6900b9bAbramo Bagnara
1576c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  void Profile(llvm::FoldingSetNodeID &ID) const {
1577910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    Profile(ID, TemplateArgs->data(), TemplateArgs->size(), getASTContext());
1578c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
1579c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
15801eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  static void
15811eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  Profile(llvm::FoldingSetNodeID &ID, const TemplateArgument *TemplateArgs,
1582828e226ab7ed08b3eb766549e9d3306432137460Douglas Gregor          unsigned NumTemplateArgs, ASTContext &Context) {
15830ceffb51b28b09db67404058c642dcb1f877f6e8Anders Carlsson    ID.AddInteger(NumTemplateArgs);
15843e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor    for (unsigned Arg = 0; Arg != NumTemplateArgs; ++Arg)
1585828e226ab7ed08b3eb766549e9d3306432137460Douglas Gregor      TemplateArgs[Arg].Profile(ID, Context);
15863e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  }
15873e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
158880cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
158980cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) {
15909a55591af3e5506b95a9718e15380129fbfc5ebcSean Hunt    return K >= firstClassTemplateSpecialization &&
15919a55591af3e5506b95a9718e15380129fbfc5ebcSean Hunt           K <= lastClassTemplateSpecialization;
15923e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  }
15933e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
15943e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  static bool classof(const ClassTemplateSpecializationDecl *) {
15953e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor    return true;
15963e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  }
1597c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1598c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  static bool classof(const ClassTemplatePartialSpecializationDecl *) {
1599c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor    return true;
1600c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
1601ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1602586c7156d51039290f100c80d2d8bd263c99addcArgyrios Kyrtzidis  friend class ASTDeclReader;
1603586c7156d51039290f100c80d2d8bd263c99addcArgyrios Kyrtzidis  friend class ASTDeclWriter;
1604c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor};
1605c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
16061eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpclass ClassTemplatePartialSpecializationDecl
16071eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  : public ClassTemplateSpecializationDecl {
160899ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie  virtual void anchor();
160999ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie
16101eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump  /// \brief The list of template parameters
1611c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  TemplateParameterList* TemplateParams;
1612c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1613833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// \brief The source info for the template arguments as written.
16143cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// FIXME: redundant with TypeAsWritten?
1615833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLoc *ArgsAsWritten;
1616833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  unsigned NumArgsAsWritten;
1617833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
1618dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// \brief Sequence number indicating when this class template partial
1619dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// specialization was added to the set of partial specializations for
1620dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// its owning class template.
1621dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  unsigned SequenceNumber;
1622ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1623ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief The class template partial specialization from which this
1624ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// class template partial specialization was instantiated.
1625ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1626ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// The boolean value will be true to indicate that this class template
1627ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// partial specialization was specialized at this level.
1628ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  llvm::PointerIntPair<ClassTemplatePartialSpecializationDecl *, 1, bool>
1629ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      InstantiatedFromMember;
1630ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
163113c8577201e4fc0ddac5f09d05fd1778832137d1Douglas Gregor  ClassTemplatePartialSpecializationDecl(ASTContext &Context, TagKind TK,
1632ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara                                         DeclContext *DC,
1633ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara                                         SourceLocation StartLoc,
1634ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara                                         SourceLocation IdLoc,
1635c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor                                         TemplateParameterList *Params,
1636c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor                                         ClassTemplateDecl *SpecializedTemplate,
1637910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                         const TemplateArgument *Args,
1638910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor                                         unsigned NumArgs,
1639833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall                                         TemplateArgumentLoc *ArgInfos,
1640833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall                                         unsigned NumArgInfos,
1641dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor                               ClassTemplatePartialSpecializationDecl *PrevDecl,
16429a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor                                         unsigned SequenceNumber);
1643ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
164494d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  ClassTemplatePartialSpecializationDecl()
164594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis    : ClassTemplateSpecializationDecl(ClassTemplatePartialSpecialization),
164694d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis      TemplateParams(0), ArgsAsWritten(0),
164794d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis      NumArgsAsWritten(0), SequenceNumber(0),
164894d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis      InstantiatedFromMember(0, false) { }
1649c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1650c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregorpublic:
1651c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  static ClassTemplatePartialSpecializationDecl *
1652ff91d240d431afbec18e25909caaf5c17f26e643Nico Weber  Create(ASTContext &Context, TagKind TK, DeclContext *DC,
1653ba877adeb49ed6dc17f27fa3a3bcd0cca713fd68Abramo Bagnara         SourceLocation StartLoc, SourceLocation IdLoc,
1654c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor         TemplateParameterList *Params,
1655c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor         ClassTemplateDecl *SpecializedTemplate,
1656910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor         const TemplateArgument *Args,
1657910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor         unsigned NumArgs,
1658d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall         const TemplateArgumentListInfo &ArgInfos,
16593cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall         QualType CanonInjectedType,
1660dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor         ClassTemplatePartialSpecializationDecl *PrevDecl,
1661dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor         unsigned SequenceNumber);
1662c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
166394d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis  static ClassTemplatePartialSpecializationDecl *
16641e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  CreateDeserialized(ASTContext &C, unsigned ID);
166594d228d3454a3f6436526d15b2ad7fc90246fe54Argyrios Kyrtzidis
1666ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  ClassTemplatePartialSpecializationDecl *getMostRecentDecl() {
1667cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    return cast<ClassTemplatePartialSpecializationDecl>(
1668ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor                   ClassTemplateSpecializationDecl::getMostRecentDecl());
1669cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  }
1670cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
1671c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  /// Get the list of template parameters
1672c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  TemplateParameterList *getTemplateParameters() const {
1673c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor    return TemplateParams;
1674c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
1675c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1676833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// Get the template arguments as written.
1677833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLoc *getTemplateArgsAsWritten() const {
1678833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    return ArgsAsWritten;
1679833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
1680833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
1681833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  /// Get the number of template arguments as written.
1682833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  unsigned getNumTemplateArgsAsWritten() const {
1683833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    return NumArgsAsWritten;
1684833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
1685833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
1686dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// \brief Get the sequence number for this class template partial
1687dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// specialization.
1688dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  unsigned getSequenceNumber() const { return SequenceNumber; }
16898fed4b4bc93cce4d15bdb79f9e30cc25a93c8143Argyrios Kyrtzidis
1690ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \brief Retrieve the member class template partial specialization from
1691ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// which this particular class template partial specialization was
1692ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// instantiated.
1693ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1694ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \code
1695ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// template<typename T>
1696ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// struct Outer {
1697ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///   template<typename U> struct Inner;
1698ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///   template<typename U> struct Inner<U*> { }; // #1
1699ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// };
1700ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1701ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// Outer<float>::Inner<int*> ii;
1702ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \endcode
1703ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1704ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// In this example, the instantiation of \c Outer<float>::Inner<int*> will
1705ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// end up instantiating the partial specialization
1706ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \c Outer<float>::Inner<U*>, which itself was instantiated from the class
1707ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// template partial specialization \c Outer<T>::Inner<U*>. Given
1708ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \c Outer<float>::Inner<U*>, this function would return
1709ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \c Outer<T>::Inner<U*>.
1710ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ClassTemplatePartialSpecializationDecl *getInstantiatedFromMember() {
1711ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    ClassTemplatePartialSpecializationDecl *First
1712ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      = cast<ClassTemplatePartialSpecializationDecl>(getFirstDeclaration());
1713ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return First->InstantiatedFromMember.getPointer();
1714ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  }
1715ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1716ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  void setInstantiatedFromMember(
1717ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor                          ClassTemplatePartialSpecializationDecl *PartialSpec) {
1718ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    ClassTemplatePartialSpecializationDecl *First
1719ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      = cast<ClassTemplatePartialSpecializationDecl>(getFirstDeclaration());
1720ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    First->InstantiatedFromMember.setPointer(PartialSpec);
1721ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  }
1722ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1723ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie  /// \brief Determines whether this class template partial specialization
1724ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// template was a specialization of a member partial specialization.
1725ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1726ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// In the following example, the member template partial specialization
1727ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \c X<int>::Inner<T*> is a member specialization.
1728ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1729ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \code
1730ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// template<typename T>
1731ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// struct X {
1732ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///   template<typename U> struct Inner;
1733ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///   template<typename U> struct Inner<U*>;
1734ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// };
1735ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  ///
1736ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// template<> template<typename T>
1737ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// struct X<int>::Inner<T*> { /* ... */ };
1738ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \endcode
1739ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  bool isMemberSpecialization() {
1740ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    ClassTemplatePartialSpecializationDecl *First
1741ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      = cast<ClassTemplatePartialSpecializationDecl>(getFirstDeclaration());
1742ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return First->InstantiatedFromMember.getInt();
1743ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  }
1744ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1745ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  /// \brief Note that this member template is a specialization.
1746ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  void setMemberSpecialization() {
1747ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    ClassTemplatePartialSpecializationDecl *First
1748ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor      = cast<ClassTemplatePartialSpecializationDecl>(getFirstDeclaration());
1749ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    assert(First->InstantiatedFromMember.getPointer() &&
1750ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor           "Only member templates can be member template specializations");
1751ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor    return First->InstantiatedFromMember.setInt(true);
1752ed9c0f90b7e0811c209b95e39fe07c211c531285Douglas Gregor  }
175331f17ecbef57b5679c017c375db330546b7b5145John McCall
175431f17ecbef57b5679c017c375db330546b7b5145John McCall  /// Retrieves the injected specialization type for this partial
175531f17ecbef57b5679c017c375db330546b7b5145John McCall  /// specialization.  This is not the same as the type-decl-type for
175631f17ecbef57b5679c017c375db330546b7b5145John McCall  /// this partial specialization, which is an InjectedClassNameType.
175731f17ecbef57b5679c017c375db330546b7b5145John McCall  QualType getInjectedSpecializationType() const {
175831f17ecbef57b5679c017c375db330546b7b5145John McCall    assert(getTypeForDecl() && "partial specialization has no type set!");
175931f17ecbef57b5679c017c375db330546b7b5145John McCall    return cast<InjectedClassNameType>(getTypeForDecl())
176031f17ecbef57b5679c017c375db330546b7b5145John McCall             ->getInjectedSpecializationType();
176131f17ecbef57b5679c017c375db330546b7b5145John McCall  }
1762ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1763c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  // FIXME: Add Profile support!
1764c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
176580cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
176680cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) {
176780cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall    return K == ClassTemplatePartialSpecialization;
1768c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
1769c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1770c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  static bool classof(const ClassTemplatePartialSpecializationDecl *) {
1771c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor    return true;
1772c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
17738fed4b4bc93cce4d15bdb79f9e30cc25a93c8143Argyrios Kyrtzidis
17748fed4b4bc93cce4d15bdb79f9e30cc25a93c8143Argyrios Kyrtzidis  friend class ASTDeclReader;
17758fed4b4bc93cce4d15bdb79f9e30cc25a93c8143Argyrios Kyrtzidis  friend class ASTDeclWriter;
17763e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor};
17773e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
17783e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor/// Declaration of a class template.
17797c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregorclass ClassTemplateDecl : public RedeclarableTemplateDecl {
17800054531488928a424666ac11fcdc6bcc5112de52Douglas Gregor  static void DeallocateCommon(void *Ptr);
1781ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
17823e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregorprotected:
17835953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor  /// \brief Data that is common to all of the declarations of a given
17845953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor  /// class template.
17859eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  struct Common : CommonBase {
1786c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    Common() : LazySpecializations() { }
1787ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
17885953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor    /// \brief The class template specializations for this class
17895953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor    /// template, including explicit specializations and instantiations.
1790d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth    llvm::FoldingSetVector<ClassTemplateSpecializationDecl> Specializations;
17917da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor
1792c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor    /// \brief The class template partial specializations for this class
1793c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor    /// template.
1794d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth    llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl>
1795c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor      PartialSpecializations;
1796c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
17977da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor    /// \brief The injected-class-name type for this class template.
17987da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor    QualType InjectedClassNameType;
1799ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1800c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    /// \brief If non-null, points to an array of specializations (including
1801c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    /// partial specializations) known ownly by their external declaration IDs.
1802c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    ///
1803c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    /// The first value in the array is the number of of specializations/
1804c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    /// partial specializations that follow.
1805c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor    uint32_t *LazySpecializations;
18065953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor  };
18075953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor
1808c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor  /// \brief Load any lazily-loaded specializations from the external source.
1809c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor  void LoadLazySpecializations();
1810ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1811cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Retrieve the set of specializations of this class template.
1812d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  llvm::FoldingSetVector<ClassTemplateSpecializationDecl> &getSpecializations();
1813cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
1814cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Retrieve the set of partial specializations of this class
1815cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// template.
1816d964d6380945e0505b623050fe6a3f428008fc2aChandler Carruth  llvm::FoldingSetVector<ClassTemplatePartialSpecializationDecl> &
1817c8e5cf8f725e111965debb7130ef7466c0c73884Douglas Gregor  getPartialSpecializations();
1818cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
18193e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  ClassTemplateDecl(DeclContext *DC, SourceLocation L, DeclarationName Name,
18208731ca76acf81826df7048bffd0c44c7c0f96c7fArgyrios Kyrtzidis                    TemplateParameterList *Params, NamedDecl *Decl)
18219eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    : RedeclarableTemplateDecl(ClassTemplate, DC, L, Name, Params, Decl) { }
18229eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
18239a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor  ClassTemplateDecl(EmptyShell Empty)
18249a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor    : RedeclarableTemplateDecl(ClassTemplate, 0, SourceLocation(),
18259a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor                               DeclarationName(), 0, 0) { }
18269a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor
18276b5415196327fa8ef00f028ba175fafef1738ae1Argyrios Kyrtzidis  CommonBase *newCommon(ASTContext &C);
18289eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
18299eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  Common *getCommonPtr() {
18309eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne    return static_cast<Common *>(RedeclarableTemplateDecl::getCommonPtr());
18319eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18323e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
18333e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregorpublic:
1834d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Get the underlying class declarations of the template.
18353e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  CXXRecordDecl *getTemplatedDecl() const {
18363e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor    return static_cast<CXXRecordDecl *>(TemplatedDecl);
18373e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  }
18383e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
1839d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Returns whether this template declaration defines the primary
184013fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  /// class pattern.
184113fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  bool isThisDeclarationADefinition() const {
184213fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall    return getTemplatedDecl()->isThisDeclarationADefinition();
184313fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall  }
184413fda8afe2ddd06c12bfb93a054e6b0d6d0d99f1John McCall
1845d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Create a class template node.
18463e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  static ClassTemplateDecl *Create(ASTContext &C, DeclContext *DC,
18473e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor                                   SourceLocation L,
18483e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor                                   DeclarationName Name,
18493e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor                                   TemplateParameterList *Params,
18505953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor                                   NamedDecl *Decl,
18515953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor                                   ClassTemplateDecl *PrevDecl);
18523e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
1853d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Create an empty class template node.
18541e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static ClassTemplateDecl *CreateDeserialized(ASTContext &C, unsigned ID);
18559a299e0575ce235f491014627c7267e2d2cd73deDouglas Gregor
1856cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Return the specialization with the provided arguments if it exists,
1857cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// otherwise return the insertion point.
1858cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  ClassTemplateSpecializationDecl *
1859cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  findSpecialization(const TemplateArgument *Args, unsigned NumArgs,
1860cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis                     void *&InsertPos);
1861cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
1862cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Insert the specified specialization knowing that it is not already
1863cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// in. InsertPos must be obtained from findSpecialization.
1864bef1a7b9c175d37e4a727e6ce68bd05232fa6970Argyrios Kyrtzidis  void AddSpecialization(ClassTemplateSpecializationDecl *D, void *InsertPos);
18653e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
18669eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ClassTemplateDecl *getCanonicalDecl() {
18677c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<ClassTemplateDecl>(
18687c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
18699eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18709eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  const ClassTemplateDecl *getCanonicalDecl() const {
18717c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<ClassTemplateDecl>(
18727c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
18739eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18749eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
18759eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieve the previous declaration of this class template, or
18769eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// NULL if no such declaration exists.
1877ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  ClassTemplateDecl *getPreviousDecl() {
18787c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<ClassTemplateDecl>(
1879ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
18809eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18819eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
18829eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// \brief Retrieve the previous declaration of this class template, or
18839eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  /// NULL if no such declaration exists.
1884ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  const ClassTemplateDecl *getPreviousDecl() const {
18857c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<ClassTemplateDecl>(
1886ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
18879eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18889eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
18899eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  ClassTemplateDecl *getInstantiatedFromMemberTemplate() {
18907c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<ClassTemplateDecl>(
18917c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getInstantiatedFromMemberTemplate());
18929eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne  }
18939eabebafc165a67812eacc184806e7bf34c5f0a5Peter Collingbourne
1894cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Return the partial specialization with the provided arguments if it
1895cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// exists, otherwise return the insertion point.
1896cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  ClassTemplatePartialSpecializationDecl *
1897cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  findPartialSpecialization(const TemplateArgument *Args, unsigned NumArgs,
1898cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis                            void *&InsertPos);
1899cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
1900cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Insert the specified partial specialization knowing that it is not
1901cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// already in. InsertPos must be obtained from findPartialSpecialization.
1902cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  void AddPartialSpecialization(ClassTemplatePartialSpecializationDecl *D,
1903bef1a7b9c175d37e4a727e6ce68bd05232fa6970Argyrios Kyrtzidis                                void *InsertPos);
1904cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis
1905cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Return the next partial specialization sequence number.
1906cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  unsigned getNextPartialSpecSequenceNumber() {
1907cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis    return getPartialSpecializations().size();
1908c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor  }
1909c8ab2563ac8f7dcc4fdc518b5cc7015ecbb2f003Douglas Gregor
1910dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  /// \brief Retrieve the partial specializations as an ordered list.
1911dc60c1eb4acbde6edcec9760de92f9098593d915Douglas Gregor  void getPartialSpecializations(
1912686775deca8b8685eb90801495880e3abdd844c2Chris Lattner          SmallVectorImpl<ClassTemplatePartialSpecializationDecl *> &PS);
1913ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1914b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  /// \brief Find a class template partial specialization with the given
1915b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  /// type T.
1916b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  ///
1917cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \param T a dependent type that names a specialization of this class
1918b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  /// template.
1919b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  ///
1920b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  /// \returns the class template partial specialization that exactly matches
1921b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  /// the type \p T, or NULL if no such partial specialization exists.
1922b88e888404ad0a2bdd9bfae457e8530bb38a87c5Douglas Gregor  ClassTemplatePartialSpecializationDecl *findPartialSpecialization(QualType T);
1923ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
1924cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \brief Find a class template partial specialization which was instantiated
1925cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// from the given member partial specialization.
1926cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  ///
1927cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \param D a member class template partial specialization.
1928cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  ///
1929cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// \returns the class template partial specialization which was instantiated
1930cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// from the given member partial specialization, or NULL if no such partial
1931cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  /// specialization exists.
1932cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  ClassTemplatePartialSpecializationDecl *
1933cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis  findPartialSpecInstantiatedFromMember(
1934cc0b1bc979b650a8a8b34b2032a074fd7724a90dArgyrios Kyrtzidis                                     ClassTemplatePartialSpecializationDecl *D);
19351eb4433ac451dc16f4133a88af2d002ac26c58efMike Stump
19363cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// \brief Retrieve the template specialization type of the
19373cb0ebd5f76abcb776f7cb4062bd79e3268c0dc4John McCall  /// injected-class-name for this class template.
19387da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  ///
19397da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// The injected-class-name for a class template \c X is \c
19407da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// X<template-args>, where \c template-args is formed from the
19417da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// template arguments that correspond to the template parameters of
19427da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// \c X. For example:
19437da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  ///
19447da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// \code
19457da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// template<typename T, int N>
19467da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// struct array {
19477da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  ///   typedef array this_type; // "array" is equivalent to "array<T, N>"
19487da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// };
19497da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor  /// \endcode
195024bae92f08ae098cc50a602d8cf1273b423e14daDouglas Gregor  QualType getInjectedClassNameSpecialization();
19517da97d0f31e1ec16998d3de2cfd2e88fe3736673Douglas Gregor
19529f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  typedef SpecIterator<ClassTemplateSpecializationDecl> spec_iterator;
19539f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19549f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  spec_iterator spec_begin() {
19559f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getSpecializations(), false);
19569f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
19579f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19589f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  spec_iterator spec_end() {
19599f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getSpecializations(), true);
19609f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
19619f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19629f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  typedef SpecIterator<ClassTemplatePartialSpecializationDecl>
19639f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne          partial_spec_iterator;
19649f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19659f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  partial_spec_iterator partial_spec_begin() {
19669f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getPartialSpecializations(), false);
19679f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
19689f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19699f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  partial_spec_iterator partial_spec_end() {
19709f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne    return makeSpecIterator(getPartialSpecializations(), true);
19719f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne  }
19729f339ba5b00256588d0d78786fff6d48ef073015Peter Collingbourne
19733e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor  // Implement isa/cast/dyncast support
197480cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
197580cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const ClassTemplateDecl *D) { return true; }
197680cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == ClassTemplate; }
19775953d8b37f92f0cf548941f617c9b0a7703df33bDouglas Gregor
1978d527cc06d78fe5afa5f20105b51697637eb02c56Sebastian Redl  friend class ASTDeclReader;
19793397c5570369f19b2d6c52e898f708d75ceede1fSebastian Redl  friend class ASTDeclWriter;
19803e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor};
19813e00bad490f1bae8a2c60f934e7eb5dbb9752c5dDouglas Gregor
1982d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Declaration of a friend template.
1983dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall///
1984d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// For example:
1985d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \code
1986d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// template \<typename T> class A {
1987dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall///   friend class MyVector<T>; // not a friend template
1988d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///   template \<typename U> friend class B; // not a friend template
1989d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///   template \<typename U> friend class Foo<T>::Nested; // friend template
1990c6a518a7271bbd6d0f606ba5c1b1b9c668bbdcb0Craig Silverstein/// };
1991d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \endcode
1992d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
1993d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \note This class is not currently in use.  All of the above
1994c6a518a7271bbd6d0f606ba5c1b1b9c668bbdcb0Craig Silverstein/// will yield a FriendDecl, not a FriendTemplateDecl.
1995dd4a3b0065b9a7e7b00073df415a798886c090f3John McCallclass FriendTemplateDecl : public Decl {
199699ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie  virtual void anchor();
1997dd4a3b0065b9a7e7b00073df415a798886c090f3John McCallpublic:
199832f2fb53d9d7c28c94d8569fd0fcf06cccee0c3dJohn McCall  typedef llvm::PointerUnion<NamedDecl*,TypeSourceInfo*> FriendUnion;
1999dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2000dd4a3b0065b9a7e7b00073df415a798886c090f3John McCallprivate:
2001dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  // The number of template parameters;  always non-zero.
2002dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  unsigned NumParams;
2003dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2004dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  // The parameter list.
2005dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  TemplateParameterList **Params;
2006dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2007dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  // The declaration that's a friend of this class.
2008dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  FriendUnion Friend;
2009dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2010dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  // Location of the 'friend' specifier.
2011dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  SourceLocation FriendLoc;
2012dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2013dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2014dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  FriendTemplateDecl(DeclContext *DC, SourceLocation Loc,
2015ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie                     unsigned NParams,
2016dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                     TemplateParameterList **Params,
2017dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                     FriendUnion Friend,
2018dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                     SourceLocation FriendLoc)
2019dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    : Decl(Decl::FriendTemplate, DC, Loc),
2020dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      NumParams(NParams),
2021dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      Params(Params),
2022dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      Friend(Friend),
2023dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall      FriendLoc(FriendLoc)
2024dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  {}
2025dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2026554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis  FriendTemplateDecl(EmptyShell Empty)
2027554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis    : Decl(Decl::FriendTemplate, Empty),
2028554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis      NumParams(0),
2029554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis      Params(0)
2030554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis  {}
2031554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis
2032dd4a3b0065b9a7e7b00073df415a798886c090f3John McCallpublic:
2033dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  static FriendTemplateDecl *Create(ASTContext &Context,
2034dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                                    DeclContext *DC, SourceLocation Loc,
2035ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie                                    unsigned NParams,
2036dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                                    TemplateParameterList **Params,
2037dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                                    FriendUnion Friend,
2038dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall                                    SourceLocation FriendLoc);
2039dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
20401e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static FriendTemplateDecl *CreateDeserialized(ASTContext &C, unsigned ID);
2041554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis
2042dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// If this friend declaration names a templated type (or
2043dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// a dependent member type of a templated type), return that
2044dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// type;  otherwise return null.
204532f2fb53d9d7c28c94d8569fd0fcf06cccee0c3dJohn McCall  TypeSourceInfo *getFriendType() const {
204632f2fb53d9d7c28c94d8569fd0fcf06cccee0c3dJohn McCall    return Friend.dyn_cast<TypeSourceInfo*>();
2047dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  }
2048dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2049dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// If this friend declaration names a templated function (or
2050dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// a member function of a templated type), return that type;
2051dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  /// otherwise return null.
2052dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  NamedDecl *getFriendDecl() const {
2053dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    return Friend.dyn_cast<NamedDecl*>();
2054dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  }
2055dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2056d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett  /// \brief Retrieves the location of the 'friend' keyword.
2057dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  SourceLocation getFriendLoc() const {
2058dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    return FriendLoc;
2059dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  }
2060dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2061dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  TemplateParameterList *getTemplateParameterList(unsigned i) const {
2062dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    assert(i <= NumParams);
2063dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    return Params[i];
2064dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  }
2065dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2066dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  unsigned getNumTemplateParameters() const {
2067dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall    return NumParams;
2068dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  }
2069dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2070dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  // Implement isa/cast/dyncast/etc.
207180cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
207280cd64a8450d8e2c079dc134d9711cd45ba89d63John McCall  static bool classofKind(Kind K) { return K == Decl::FriendTemplate; }
2073dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall  static bool classof(const FriendTemplateDecl *D) { return true; }
2074554e6aa2da082575514607c3639c246c04b3232aArgyrios Kyrtzidis
2075d527cc06d78fe5afa5f20105b51697637eb02c56Sebastian Redl  friend class ASTDeclReader;
2076dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall};
2077dd4a3b0065b9a7e7b00073df415a798886c090f3John McCall
2078d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Declaration of an alias template.
20793e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith///
2080d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// For example:
2081d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \code
2082d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// template \<typename T> using V = std::map<T*, int, MyCompare<T>>;
2083d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \endcode
20847c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregorclass TypeAliasTemplateDecl : public RedeclarableTemplateDecl {
20853e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static void DeallocateCommon(void *Ptr);
20863e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
20873e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smithprotected:
20883e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  typedef CommonBase Common;
20893e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
20903e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  TypeAliasTemplateDecl(DeclContext *DC, SourceLocation L, DeclarationName Name,
20913e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith                        TemplateParameterList *Params, NamedDecl *Decl)
20923e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    : RedeclarableTemplateDecl(TypeAliasTemplate, DC, L, Name, Params, Decl) { }
20933e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
20943e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  CommonBase *newCommon(ASTContext &C);
20953e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
20963e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  Common *getCommonPtr() {
20973e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    return static_cast<Common *>(RedeclarableTemplateDecl::getCommonPtr());
20983e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
20993e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21003e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smithpublic:
21013e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// Get the underlying function declaration of the template.
21023e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  TypeAliasDecl *getTemplatedDecl() const {
21033e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith    return static_cast<TypeAliasDecl*>(TemplatedDecl);
21043e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21053e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21063e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21073e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  TypeAliasTemplateDecl *getCanonicalDecl() {
21087c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<TypeAliasTemplateDecl>(
21097c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
21103e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21113e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  const TypeAliasTemplateDecl *getCanonicalDecl() const {
21127c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast<TypeAliasTemplateDecl>(
21137c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getCanonicalDecl());
21143e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21153e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21163e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// \brief Retrieve the previous declaration of this function template, or
21173e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// NULL if no such declaration exists.
2118ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  TypeAliasTemplateDecl *getPreviousDecl() {
21197c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<TypeAliasTemplateDecl>(
2120ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
21213e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21223e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21233e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// \brief Retrieve the previous declaration of this function template, or
21243e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// NULL if no such declaration exists.
2125ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor  const TypeAliasTemplateDecl *getPreviousDecl() const {
21267c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<TypeAliasTemplateDecl>(
2127ef96ee0be5f100789f451641542a69cd719144d2Douglas Gregor             RedeclarableTemplateDecl::getPreviousDecl());
21283e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21293e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21303e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  TypeAliasTemplateDecl *getInstantiatedFromMemberTemplate() {
21317c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor    return cast_or_null<TypeAliasTemplateDecl>(
21327c99bb5c4901c39460818ff8c00840218c48251fDouglas Gregor             RedeclarableTemplateDecl::getInstantiatedFromMemberTemplate());
21333e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  }
21343e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
2135ba243b59a1074e0962f6abfa3bb9aa984eac1245David Blaikie
21363e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// \brief Create a function template node.
21373e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static TypeAliasTemplateDecl *Create(ASTContext &C, DeclContext *DC,
21383e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith                                       SourceLocation L,
21393e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith                                       DeclarationName Name,
21403e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith                                       TemplateParameterList *Params,
21413e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith                                       NamedDecl *Decl);
21423e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21433e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  /// \brief Create an empty alias template node.
21441e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static TypeAliasTemplateDecl *CreateDeserialized(ASTContext &C, unsigned ID);
21453e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21463e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  // Implement isa/cast/dyncast support
21473e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
21483e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static bool classof(const TypeAliasTemplateDecl *D) { return true; }
21493e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  static bool classofKind(Kind K) { return K == TypeAliasTemplate; }
21503e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
21513e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  friend class ASTDeclReader;
21523e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith  friend class ASTDeclWriter;
21533e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith};
21543e4c6c4c79a03f5cb0c4671d7c282d623c6dc35eRichard Smith
2155d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \brief Declaration of a function specialization at template class scope.
2156d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
2157af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// This is a non standard extension needed to support MSVC.
2158d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett///
2159af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// For example:
2160d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \code
2161af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// template <class T>
2162af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// class A {
2163af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet///    template <class U> void foo(U a) { }
2164af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet///    template<> void foo(int a) { }
2165af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// }
2166d5e26b8933a377893c8043ff6a23aaf6b601d18fJames Dennett/// \endcode
2167af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet///
2168af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// "template<> foo(int a)" will be saved in Specialization as a normal
2169af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// CXXMethodDecl. Then during an instantiation of class A, it will be
2170af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet/// transformed into an actual function specialization.
2171af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichetclass ClassScopeFunctionSpecializationDecl : public Decl {
217299ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie  virtual void anchor();
217399ba9e3bd70671f3441fb974895f226a83ce0e66David Blaikie
2174af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  ClassScopeFunctionSpecializationDecl(DeclContext *DC, SourceLocation Loc,
21756b02009359a462ffe633696a4441313b462e6566Nico Weber                                       CXXMethodDecl *FD, bool Args,
21766b02009359a462ffe633696a4441313b462e6566Nico Weber                                       TemplateArgumentListInfo TemplArgs)
2177af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet    : Decl(Decl::ClassScopeFunctionSpecialization, DC, Loc),
21786b02009359a462ffe633696a4441313b462e6566Nico Weber      Specialization(FD), HasExplicitTemplateArgs(Args),
21796b02009359a462ffe633696a4441313b462e6566Nico Weber      TemplateArgs(TemplArgs) {}
2180af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2181af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  ClassScopeFunctionSpecializationDecl(EmptyShell Empty)
2182af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet    : Decl(Decl::ClassScopeFunctionSpecialization, Empty) {}
2183af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2184af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  CXXMethodDecl *Specialization;
21856b02009359a462ffe633696a4441313b462e6566Nico Weber  bool HasExplicitTemplateArgs;
21866b02009359a462ffe633696a4441313b462e6566Nico Weber  TemplateArgumentListInfo TemplateArgs;
2187af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2188af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichetpublic:
2189af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  CXXMethodDecl *getSpecialization() const { return Specialization; }
21906b02009359a462ffe633696a4441313b462e6566Nico Weber  bool hasExplicitTemplateArgs() const { return HasExplicitTemplateArgs; }
21916b02009359a462ffe633696a4441313b462e6566Nico Weber  const TemplateArgumentListInfo& templateArgs() const { return TemplateArgs; }
2192af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2193af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  static ClassScopeFunctionSpecializationDecl *Create(ASTContext &C,
2194af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet                                                      DeclContext *DC,
2195af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet                                                      SourceLocation Loc,
21966b02009359a462ffe633696a4441313b462e6566Nico Weber                                                      CXXMethodDecl *FD,
21976b02009359a462ffe633696a4441313b462e6566Nico Weber                                                   bool HasExplicitTemplateArgs,
21986b02009359a462ffe633696a4441313b462e6566Nico Weber                                        TemplateArgumentListInfo TemplateArgs) {
21996b02009359a462ffe633696a4441313b462e6566Nico Weber    return new (C) ClassScopeFunctionSpecializationDecl(DC , Loc, FD,
22006b02009359a462ffe633696a4441313b462e6566Nico Weber                                                        HasExplicitTemplateArgs,
22016b02009359a462ffe633696a4441313b462e6566Nico Weber                                                        TemplateArgs);
2202af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  }
2203af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
22041e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  static ClassScopeFunctionSpecializationDecl *
22051e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor  CreateDeserialized(ASTContext &Context, unsigned ID);
22061e68ecc4fcce12f683c4fd38acfd1a004001b04fDouglas Gregor
2207af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  // Implement isa/cast/dyncast/etc.
2208af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  static bool classof(const Decl *D) { return classofKind(D->getKind()); }
2209af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  static bool classofKind(Kind K) {
2210af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet    return K == Decl::ClassScopeFunctionSpecialization;
2211af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  }
2212af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  static bool classof(const ClassScopeFunctionSpecializationDecl *D) {
2213af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet    return true;
2214af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  }
2215af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2216af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  friend class ASTDeclReader;
2217af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet  friend class ASTDeclWriter;
2218af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet};
2219af0f4d0b2e38c810effc8b024ad2fb6604eec5d3Francois Pichet
2220e53060fa78ad7e98352049f72787bdb7543e2a48Douglas Gregor/// Implementation of inline functions that require the template declarations
22211eb4433ac451dc16f4133a88af2d002ac26c58efMike Stumpinline AnyFunctionDecl::AnyFunctionDecl(FunctionTemplateDecl *FTD)
2222e53060fa78ad7e98352049f72787bdb7543e2a48Douglas Gregor  : Function(FTD) { }
2223e53060fa78ad7e98352049f72787bdb7543e2a48Douglas Gregor
2224aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor} /* end of namespace clang */
2225aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor
2226aaba5e346dffdbad5d1c42765a89e4a7afb0da67Douglas Gregor#endif
2227