1275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//===-- TemplateBase.h - Core classes for C++ templates ---------*- C++ -*-===//
2275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//
3275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//                     The LLVM Compiler Infrastructure
4275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//
5275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall// This file is distributed under the University of Illinois Open Source
6275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall// License. See LICENSE.TXT for details.
7275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//
8275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//===----------------------------------------------------------------------===//
9275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//
10275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//  This file provides definitions which are common for all kinds of
11275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//  template representation.
12275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//
13275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall//===----------------------------------------------------------------------===//
14275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
15275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall#ifndef LLVM_CLANG_AST_TEMPLATEBASE_H
16275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall#define LLVM_CLANG_AST_TEMPLATEBASE_H
17275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
18aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar#include "clang/AST/TemplateName.h"
1930a2e16f6c27f888dd11eba6bbbae1e980078fcbChandler Carruth#include "clang/AST/Type.h"
20275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall#include "llvm/ADT/APSInt.h"
21d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall#include "llvm/ADT/SmallVector.h"
22aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar#include "llvm/Support/Compiler.h"
23833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall#include "llvm/Support/ErrorHandling.h"
24275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
25275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCallnamespace llvm {
26275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  class FoldingSetNodeID;
27275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall}
28275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
29275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCallnamespace clang {
30275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
31a933319ebf754396623165f9dc0a29c2a48879f5Douglas Gregorclass DiagnosticBuilder;
32275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCallclass Expr;
3387dd697dcc8ecb64df73ae64d61b8c80ff0c157cDouglas Gregorstruct PrintingPolicy;
34a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCallclass TypeSourceInfo;
35d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedmanclass ValueDecl;
36275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
37275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall/// \brief Represents a template argument within a class template
38275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall/// specialization.
39275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCallclass TemplateArgument {
40275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCallpublic:
412bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  /// \brief The kind of template argument we're storing.
42275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  enum ArgKind {
43788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// \brief Represents an empty template argument, e.g., one that has not
44788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// been deduced.
45275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    Null = 0,
46d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    /// The template argument is a type.
47788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Type,
48d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    /// The template argument is a declaration that was provided for a pointer,
49d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    /// reference, or pointer to member non-type template parameter.
50788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Declaration,
51d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    /// The template argument is a null pointer or null pointer to member that
52d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    /// was provided for a non-type template parameter.
53d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    NullPtr,
54788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// The template argument is an integral value stored in an llvm::APSInt
55788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// that was provided for an integral non-type template parameter.
56788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Integral,
57788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// The template argument is a template name that was provided for a
58788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    /// template template parameter.
59788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Template,
60a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    /// The template argument is a pack expansion of a template name that was
61a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    /// provided for a template template parameter.
62a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    TemplateExpansion,
63275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    /// The template argument is a value- or type-dependent expression
64275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    /// stored in an Expr*.
65788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Expression,
66275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    /// The template argument is actually a parameter pack. Arguments are stored
67275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    /// in the Args struct.
68788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Pack
692bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  };
702bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor
712bde8273eb5730324f823945d0c2389badf325e6Douglas Gregorprivate:
722bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  /// \brief The kind of template argument we're storing.
732bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  unsigned Kind;
74275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
75e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  struct DA {
76e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    ValueDecl *D;
77e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    bool ForRefParam;
78e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  };
79e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  struct I {
80e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    // We store a decomposed APSInt with the data allocated by ASTContext if
81e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    // BitWidth > 64. The memory may be shared between multiple
82e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    // TemplateArgument instances.
83e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    union {
84e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher      uint64_t VAL;          ///< Used to store the <= 64 bits integer value.
85e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher      const uint64_t *pVal;  ///< Used to store the >64 bits integer value.
86e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    };
87e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned BitWidth : 31;
88e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned IsUnsigned : 1;
89e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    void *Type;
90e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  };
91e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  struct A {
92e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    const TemplateArgument *Args;
93e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned NumArgs;
94e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  };
95e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  struct TA {
96e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    void *Name;
97e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned NumExpansions;
98e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  };
992bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  union {
100e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    struct DA DeclArg;
101e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    struct I Integer;
102e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    struct A Args;
103e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    struct TA TemplateArg;
1042bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor    uintptr_t TypeOrValue;
1052bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  };
1062bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor
107e2e1fa27e2533410f744137b0db1bc9491543392David Blaikie  TemplateArgument(TemplateName, bool) LLVM_DELETED_FUNCTION;
1082be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor
1092bde8273eb5730324f823945d0c2389badf325e6Douglas Gregorpublic:
110275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Construct an empty, invalid template argument.
111854fc56c95845660fccb1cb165fbf33fb9ae09a8Bill Wendling  TemplateArgument() : Kind(Null), TypeOrValue(0) { }
112275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
113275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Construct a template type argument.
114d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  TemplateArgument(QualType T, bool isNullPtr = false)
115d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    : Kind(isNullPtr ? NullPtr : Type) {
116275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    TypeOrValue = reinterpret_cast<uintptr_t>(T.getAsOpaquePtr());
117275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
118275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
119275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Construct a template argument that refers to a
120275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// declaration, which is either an external declaration or a
121275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// template declaration.
122d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  TemplateArgument(ValueDecl *D, bool ForRefParam) : Kind(Declaration) {
123d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(D && "Expected decl");
124d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    DeclArg.D = D;
125d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    DeclArg.ForRefParam = ForRefParam;
126275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
127275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
128855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  /// \brief Construct an integral constant template argument. The memory to
129855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  /// store the value is allocated with Ctx.
130855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  TemplateArgument(ASTContext &Ctx, const llvm::APSInt &Value, QualType Type);
131855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer
132855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  /// \brief Construct an integral constant template argument with the same
133855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  /// value as Other but a different type.
134855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  TemplateArgument(const TemplateArgument &Other, QualType Type)
135855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer    : Kind(Integral) {
136855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer    Integer = Other.Integer;
137275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    Integer.Type = Type.getAsOpaquePtr();
138275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
139275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
1402be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// \brief Construct a template argument that is a template.
141788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  ///
142788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  /// This form of template argument is generally used for template template
143788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  /// parameters. However, the template name could be a dependent template
144788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  /// name that ends up being instantiated to a function template whose address
145788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  /// is taken.
146ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  ///
147ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  /// \param Name The template name.
1482be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  TemplateArgument(TemplateName Name) : Kind(Template)
149ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  {
1502be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    TemplateArg.Name = Name.getAsVoidPointer();
1512be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    TemplateArg.NumExpansions = 0;
152788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
1532be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor
1542be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// \brief Construct a template argument that is a template pack expansion.
1552be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  ///
1562be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// This form of template argument is generally used for template template
1572be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// parameters. However, the template name could be a dependent template
1582be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// name that ends up being instantiated to a function template whose address
1592be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// is taken.
1602be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  ///
1612be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// \param Name The template name.
1622be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  ///
1632be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// \param NumExpansions The number of expansions that will be generated by
1642be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// instantiating
165dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie  TemplateArgument(TemplateName Name, Optional<unsigned> NumExpansions)
1662be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    : Kind(TemplateExpansion)
1672be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  {
1682be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    TemplateArg.Name = Name.getAsVoidPointer();
1692be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    if (NumExpansions)
1702be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor      TemplateArg.NumExpansions = *NumExpansions + 1;
1712be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    else
1722be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor      TemplateArg.NumExpansions = 0;
1732be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  }
1742be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor
175275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Construct a template argument that is an expression.
176275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  ///
177275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// This form of template argument only occurs in template argument
178275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// lists used for dependent types and for expression; it will not
179275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// occur in a non-dependent, canonical template argument list.
180833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgument(Expr *E) : Kind(Expression) {
181833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    TypeOrValue = reinterpret_cast<uintptr_t>(E);
182833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
183275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
184910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// \brief Construct a template argument that is a template argument pack.
185910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  ///
186910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// We assume that storage for the template arguments provided
187910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  /// outlives the TemplateArgument itself.
188d3731198193eee92796ddeb493973b7a598b003eDouglas Gregor  TemplateArgument(const TemplateArgument *Args, unsigned NumArgs) : Kind(Pack){
189910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    this->Args.Args = Args;
190910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor    this->Args.NumArgs = NumArgs;
191910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor  }
192910f8008fea79120489a53593fe971b0b8a4a740Douglas Gregor
193d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  static TemplateArgument getEmptyPack() {
194d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return TemplateArgument((TemplateArgument*)0, 0);
195d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  }
196d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
197203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor  /// \brief Create a new template argument pack by copying the given set of
198203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor  /// template arguments.
199203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor  static TemplateArgument CreatePackCopy(ASTContext &Context,
200203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor                                         const TemplateArgument *Args,
201203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor                                         unsigned NumArgs);
202203e6a322ae29d577acafcb1572a57ec16e1e730Douglas Gregor
203275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Return the kind of stored template argument.
2042bde8273eb5730324f823945d0c2389badf325e6Douglas Gregor  ArgKind getKind() const { return (ArgKind)Kind; }
205275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
206275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Determine whether this template argument has no value.
207275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  bool isNull() const { return Kind == Null; }
208275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
209bebbe0d9b7568ce43a464286bee49429489ef483Douglas Gregor  /// \brief Whether this template argument is dependent on a template
210561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor  /// parameter such that its result can change from one instantiation to
211561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor  /// another.
212bebbe0d9b7568ce43a464286bee49429489ef483Douglas Gregor  bool isDependent() const;
213bebbe0d9b7568ce43a464286bee49429489ef483Douglas Gregor
214561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor  /// \brief Whether this template argument is dependent on a template
215561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor  /// parameter.
216561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor  bool isInstantiationDependent() const;
217561f81243f665cf2001caadc45df505f826b72d6Douglas Gregor
218d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// \brief Whether this template argument contains an unexpanded
219d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  /// parameter pack.
220d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor  bool containsUnexpandedParameterPack() const;
221d0937224f383c7cc72c947119380f9713a070c73Douglas Gregor
2228491ffe86c50241b47c6d7ef8cd9ee00f5e675daDouglas Gregor  /// \brief Determine whether this template argument is a pack expansion.
2238491ffe86c50241b47c6d7ef8cd9ee00f5e675daDouglas Gregor  bool isPackExpansion() const;
2248491ffe86c50241b47c6d7ef8cd9ee00f5e675daDouglas Gregor
225d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// \brief Retrieve the type for a type template argument.
226275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  QualType getAsType() const {
227d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Type && "Unexpected kind");
228275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return QualType::getFromOpaquePtr(reinterpret_cast<void*>(TypeOrValue));
229275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
230275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
231d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// \brief Retrieve the declaration for a declaration non-type
232d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// template argument.
233d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  ValueDecl *getAsDecl() const {
234d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Declaration && "Unexpected kind");
235d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return DeclArg.D;
236d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  }
237d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
238d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// \brief Retrieve whether a declaration is binding to a
239d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// reference parameter in a declaration non-type template argument.
240d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  bool isDeclForReferenceParam() const {
241d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Declaration && "Unexpected kind");
242d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return DeclArg.ForRefParam;
243275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
244275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
245d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// \brief Retrieve the type for null non-type template argument.
246d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  QualType getNullPtrType() const {
247d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == NullPtr && "Unexpected kind");
248d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return QualType::getFromOpaquePtr(reinterpret_cast<void*>(TypeOrValue));
249d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  }
250d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
251d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  /// \brief Retrieve the template name for a template name argument.
252788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  TemplateName getAsTemplate() const {
253d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Template && "Unexpected kind");
2542be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    return TemplateName::getFromVoidPointer(TemplateArg.Name);
255788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
256a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor
257a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor  /// \brief Retrieve the template argument as a template name; if the argument
258a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor  /// is a pack expansion, return the pattern as a template name.
259a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor  TemplateName getAsTemplateOrTemplatePattern() const {
260d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert((Kind == Template || Kind == TemplateExpansion) &&
261d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman           "Unexpected kind");
262a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor
2632be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor    return TemplateName::getFromVoidPointer(TemplateArg.Name);
264a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor  }
265a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor
2662be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// \brief Retrieve the number of expansions that a template template argument
2672be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor  /// expansion will produce, if known.
268dc84cd5efdd3430efb22546b4ac656aa0540b210David Blaikie  Optional<unsigned> getNumTemplateExpansions() const;
2692be29f423acad3bbe39099a78db2805acb5bdf17Douglas Gregor
270275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Retrieve the template argument as an integral value.
271855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  // FIXME: Provide a way to read the integral data without copying the value.
272855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer  llvm::APSInt getAsIntegral() const {
273d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Integral && "Unexpected kind");
274b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer    using namespace llvm;
275855243789cb44799c03f4c7216d3d6308805f549Benjamin Kramer    if (Integer.BitWidth <= 64)
276b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer      return APSInt(APInt(Integer.BitWidth, Integer.VAL), Integer.IsUnsigned);
277b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer
278b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer    unsigned NumWords = APInt::getNumWords(Integer.BitWidth);
279b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer    return APSInt(APInt(Integer.BitWidth, makeArrayRef(Integer.pVal, NumWords)),
280b8e54cd26cc71075456a74be054a95fa1f2e28adBenjamin Kramer                  Integer.IsUnsigned);
281275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
282275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
283275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Retrieve the type of the integral value.
284275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  QualType getIntegralType() const {
285d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Integral && "Unexpected kind");
286275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return QualType::getFromOpaquePtr(Integer.Type);
287275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
288275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
289275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  void setIntegralType(QualType T) {
290d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Integral && "Unexpected kind");
291275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    Integer.Type = T.getAsOpaquePtr();
2927177dee8aee4b432911c91f1b788963bec0cac9fDaniel Dunbar  }
293275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
294275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Retrieve the template argument as an expression.
295275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  Expr *getAsExpr() const {
296d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Kind == Expression && "Unexpected kind");
297275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return reinterpret_cast<Expr *>(TypeOrValue);
298275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
299275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
300275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Iterator that traverses the elements of a template argument pack.
301275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  typedef const TemplateArgument * pack_iterator;
302275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
303275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Iterator referencing the first argument of a template argument
304275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// pack.
305275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  pack_iterator pack_begin() const {
306275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    assert(Kind == Pack);
307275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return Args.Args;
308275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
309275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
310275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Iterator referencing one past the last argument of a template
311275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// argument pack.
312275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  pack_iterator pack_end() const {
313275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    assert(Kind == Pack);
314275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return Args.Args + Args.NumArgs;
315275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
316275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
317275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief The number of template arguments in the given template argument
318275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// pack.
319275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  unsigned pack_size() const {
320275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    assert(Kind == Pack);
321275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall    return Args.NumArgs;
322275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  }
323275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
3245a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall  /// \brief Return the array of arguments in this template argument pack.
3255a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall  llvm::ArrayRef<TemplateArgument> getPackAsArray() const {
3265a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall    assert(Kind == Pack);
3275a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall    return llvm::ArrayRef<TemplateArgument>(Args.Args, Args.NumArgs);
3285a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall  }
3295a758de93fa2a28a84eb0d918a31d9522472990cJohn McCall
330efce31f51d6e7e31e125f96c20f6cdab3ead0a47James Dennett  /// \brief Determines whether two template arguments are superficially the
33133500955d731c73717af52088b7fc0e7a85681e7John McCall  /// same.
33233500955d731c73717af52088b7fc0e7a85681e7John McCall  bool structurallyEquals(const TemplateArgument &Other) const;
33333500955d731c73717af52088b7fc0e7a85681e7John McCall
334efce31f51d6e7e31e125f96c20f6cdab3ead0a47James Dennett  /// \brief When the template argument is a pack expansion, returns
335e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor  /// the pattern of the pack expansion.
336e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor  TemplateArgument getPackExpansionPattern() const;
337e02e26293cf8e3bad1059b39cea75c6582896da6Douglas Gregor
33887dd697dcc8ecb64df73ae64d61b8c80ff0c157cDouglas Gregor  /// \brief Print this template argument to the given output stream.
3398cc488fefb2fb04bc8d5398da29f0182f97934cfChris Lattner  void print(const PrintingPolicy &Policy, raw_ostream &Out) const;
34087dd697dcc8ecb64df73ae64d61b8c80ff0c157cDouglas Gregor
341275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall  /// \brief Used to insert TemplateArguments into FoldingSets.
3424ba2a17694148e16eaa8d3917f657ffcd3667be4Jay Foad  void Profile(llvm::FoldingSetNodeID &ID, const ASTContext &Context) const;
343275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall};
344275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
345833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall/// Location information for a TemplateArgument.
346833ca991c1bfc967f0995974ca86f66ba1f666b5John McCallstruct TemplateArgumentLocInfo {
347833ca991c1bfc967f0995974ca86f66ba1f666b5John McCallprivate:
348e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher
349e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  struct T {
350e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    // FIXME: We'd like to just use the qualifier in the TemplateName,
351e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    // but template arguments get canonicalized too quickly.
352e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    NestedNameSpecifier *Qualifier;
353e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    void *QualifierLocData;
354e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned TemplateNameLoc;
355e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    unsigned EllipsisLoc;
356e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher  };
357e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher
358828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  union {
359e462c60ac3365d3302b7d0a566c5cb7dbe0e5ae3Eric Christopher    struct T Template;
360828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    Expr *Expression;
361a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall    TypeSourceInfo *Declarator;
362828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  };
363833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
364833ca991c1bfc967f0995974ca86f66ba1f666b5John McCallpublic:
365b0ddf3aeb2f119cac42468b029584e8839b354ccDouglas Gregor  TemplateArgumentLocInfo();
3668de39b431d3775cd46584080beec3a75d019bd28Douglas Gregor
3676939fff69a3dfff2552261a1d7f1f609380fe6b0Douglas Gregor  TemplateArgumentLocInfo(TypeSourceInfo *TInfo) : Declarator(TInfo) {}
3688de39b431d3775cd46584080beec3a75d019bd28Douglas Gregor
3696939fff69a3dfff2552261a1d7f1f609380fe6b0Douglas Gregor  TemplateArgumentLocInfo(Expr *E) : Expression(E) {}
370788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor
371b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor  TemplateArgumentLocInfo(NestedNameSpecifierLoc QualifierLoc,
372ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor                          SourceLocation TemplateNameLoc,
373ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor                          SourceLocation EllipsisLoc)
374788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  {
375b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor    Template.Qualifier = QualifierLoc.getNestedNameSpecifier();
376b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor    Template.QualifierLocData = QualifierLoc.getOpaqueData();
377788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    Template.TemplateNameLoc = TemplateNameLoc.getRawEncoding();
378ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor    Template.EllipsisLoc = EllipsisLoc.getRawEncoding();
379788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
380833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
381a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  TypeSourceInfo *getAsTypeSourceInfo() const {
382828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    return Declarator;
383833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
384833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
385833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  Expr *getAsExpr() const {
386828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    return Expression;
387833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
388833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
389b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor  NestedNameSpecifierLoc getTemplateQualifierLoc() const {
390b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor    return NestedNameSpecifierLoc(Template.Qualifier,
391b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor                                  Template.QualifierLocData);
392788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
393788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor
394788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  SourceLocation getTemplateNameLoc() const {
395788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    return SourceLocation::getFromRawEncoding(Template.TemplateNameLoc);
396788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
397ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor
398ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  SourceLocation getTemplateEllipsisLoc() const {
399ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor    return SourceLocation::getFromRawEncoding(Template.EllipsisLoc);
400ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  }
401833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall};
402833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
403833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall/// Location wrapper for a TemplateArgument.  TemplateArgument is to
404833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall/// TemplateArgumentLoc as Type is to TypeLoc.
405833ca991c1bfc967f0995974ca86f66ba1f666b5John McCallclass TemplateArgumentLoc {
406833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgument Argument;
407833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLocInfo LocInfo;
408833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
409828bff2079b6a91ecd7ed5b842c59527d7682789John McCallpublic:
410828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  TemplateArgumentLoc() {}
411828bff2079b6a91ecd7ed5b842c59527d7682789John McCall
412833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLoc(const TemplateArgument &Argument,
413833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall                      TemplateArgumentLocInfo Opaque)
414833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    : Argument(Argument), LocInfo(Opaque) {
415833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
416833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
417a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  TemplateArgumentLoc(const TemplateArgument &Argument, TypeSourceInfo *TInfo)
418a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall    : Argument(Argument), LocInfo(TInfo) {
419833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    assert(Argument.getKind() == TemplateArgument::Type);
420833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
421833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
422833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLoc(const TemplateArgument &Argument, Expr *E)
423833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    : Argument(Argument), LocInfo(E) {
424833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    assert(Argument.getKind() == TemplateArgument::Expression);
425833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
426833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
427788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  TemplateArgumentLoc(const TemplateArgument &Argument,
428b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor                      NestedNameSpecifierLoc QualifierLoc,
429ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor                      SourceLocation TemplateNameLoc,
430ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor                      SourceLocation EllipsisLoc = SourceLocation())
431b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor    : Argument(Argument), LocInfo(QualifierLoc, TemplateNameLoc, EllipsisLoc) {
432a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    assert(Argument.getKind() == TemplateArgument::Template ||
433a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor           Argument.getKind() == TemplateArgument::TemplateExpansion);
434788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
435788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor
436788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  /// \brief - Fetches the primary location of the argument.
437828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  SourceLocation getLocation() const {
438a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    if (Argument.getKind() == TemplateArgument::Template ||
439a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor        Argument.getKind() == TemplateArgument::TemplateExpansion)
440788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor      return getTemplateNameLoc();
441788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor
442828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    return getSourceRange().getBegin();
443833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
444833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
445828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  /// \brief - Fetches the full source range of the argument.
446aa49a7d70e58dac2aeb40664ba16d2ea571b8c95Daniel Dunbar  SourceRange getSourceRange() const LLVM_READONLY;
447833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
448833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  const TemplateArgument &getArgument() const {
449833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    return Argument;
450833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
451833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
452833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  TemplateArgumentLocInfo getLocInfo() const {
453833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    return LocInfo;
454833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
455833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
456a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall  TypeSourceInfo *getTypeSourceInfo() const {
457833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    assert(Argument.getKind() == TemplateArgument::Type);
458a93c934af4fbf97cbe8e649d82e68ccacfe57c95John McCall    return LocInfo.getAsTypeSourceInfo();
459833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
460833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
461833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  Expr *getSourceExpression() const {
462833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    assert(Argument.getKind() == TemplateArgument::Expression);
463828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    return LocInfo.getAsExpr();
464828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  }
465828bff2079b6a91ecd7ed5b842c59527d7682789John McCall
466828bff2079b6a91ecd7ed5b842c59527d7682789John McCall  Expr *getSourceDeclExpression() const {
467828bff2079b6a91ecd7ed5b842c59527d7682789John McCall    assert(Argument.getKind() == TemplateArgument::Declaration);
468833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall    return LocInfo.getAsExpr();
469833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall  }
470d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
471d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  Expr *getSourceNullPtrExpression() const {
472d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Argument.getKind() == TemplateArgument::NullPtr);
473d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return LocInfo.getAsExpr();
474d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  }
475d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
476d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  Expr *getSourceIntegralExpression() const {
477d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    assert(Argument.getKind() == TemplateArgument::Integral);
478d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman    return LocInfo.getAsExpr();
479d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman  }
480d7a6b1640e565487d163023a6a2e83f55476ae96Eli Friedman
481b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor  NestedNameSpecifierLoc getTemplateQualifierLoc() const {
482a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    assert(Argument.getKind() == TemplateArgument::Template ||
483a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor           Argument.getKind() == TemplateArgument::TemplateExpansion);
484b6744efecba58792cce20d2d7b9ee39927c5422eDouglas Gregor    return LocInfo.getTemplateQualifierLoc();
485788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
486788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor
487788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  SourceLocation getTemplateNameLoc() const {
488a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    assert(Argument.getKind() == TemplateArgument::Template ||
489a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor           Argument.getKind() == TemplateArgument::TemplateExpansion);
490788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor    return LocInfo.getTemplateNameLoc();
491788cd06cf8e868a67158aafec5de3a1f408d14f3Douglas Gregor  }
4928491ffe86c50241b47c6d7ef8cd9ee00f5e675daDouglas Gregor
493ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  SourceLocation getTemplateEllipsisLoc() const {
494a7fc901a2e39bfe55bfcff5934b2d9fdf9656491Douglas Gregor    assert(Argument.getKind() == TemplateArgument::TemplateExpansion);
495ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor    return LocInfo.getTemplateEllipsisLoc();
496ba68eca7582a62e3e2ff4b0eba1b2b73a6b80895Douglas Gregor  }
497833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall};
498833ca991c1bfc967f0995974ca86f66ba1f666b5John McCall
499d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall/// A convenient class for passing around template argument
500d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall/// information.  Designed to be passed by reference.
501d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCallclass TemplateArgumentListInfo {
502686775deca8b8685eb90801495880e3abdd844c2Chris Lattner  SmallVector<TemplateArgumentLoc, 8> Arguments;
503d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  SourceLocation LAngleLoc;
504d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  SourceLocation RAngleLoc;
505d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
50671a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  // This can leak if used in an AST node, use ASTTemplateArgumentListInfo
50771a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  // instead.
50871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  void* operator new(size_t bytes, ASTContext& C);
50971a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
510d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCallpublic:
511d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  TemplateArgumentListInfo() {}
512d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
513d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  TemplateArgumentListInfo(SourceLocation LAngleLoc,
514d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall                           SourceLocation RAngleLoc)
515d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall    : LAngleLoc(LAngleLoc), RAngleLoc(RAngleLoc) {}
516d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
517d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  SourceLocation getLAngleLoc() const { return LAngleLoc; }
518d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  SourceLocation getRAngleLoc() const { return RAngleLoc; }
519d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
520d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  void setLAngleLoc(SourceLocation Loc) { LAngleLoc = Loc; }
521d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  void setRAngleLoc(SourceLocation Loc) { RAngleLoc = Loc; }
522d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
523d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  unsigned size() const { return Arguments.size(); }
524d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
525d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  const TemplateArgumentLoc *getArgumentArray() const {
526d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall    return Arguments.data();
527d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  }
528d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
529d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  const TemplateArgumentLoc &operator[](unsigned I) const {
530d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall    return Arguments[I];
531d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  }
532d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
533d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  void addArgument(const TemplateArgumentLoc &Loc) {
534d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall    Arguments.push_back(Loc);
535d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall  }
536d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall};
537d5532b6cfff2977e0c59fa6ead7f7973984a620dJohn McCall
53871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis/// \brief Represents an explicit template argument list in C++, e.g.,
53971a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis/// the "<int>" in "sort<int>".
54071a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis/// This is safe to be used inside an AST node, in contrast with
54171a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis/// TemplateArgumentListInfo.
54271a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidisstruct ASTTemplateArgumentListInfo {
54397f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith  /// \brief The source location of the left angle bracket ('<').
54471a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  SourceLocation LAngleLoc;
54571a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
54697f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith  /// \brief The source location of the right angle bracket ('>').
54771a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  SourceLocation RAngleLoc;
54871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
54997f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith  union {
55097f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    /// \brief The number of template arguments in TemplateArgs.
55197f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    /// The actual template arguments (if any) are stored after the
55297f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    /// ExplicitTemplateArgumentList structure.
55397f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    unsigned NumTemplateArgs;
55497f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith
55597f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    /// Force ASTTemplateArgumentListInfo to the right alignment
55697f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    /// for the following array of TemplateArgumentLocs.
55797f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith    void *Aligner;
55897f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith  };
55997f6026f460c3aaa250fc9dcd7c2b8b6c1f3ba69Richard Smith
56071a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  /// \brief Retrieve the template arguments
56171a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  TemplateArgumentLoc *getTemplateArgs() {
56271a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis    return reinterpret_cast<TemplateArgumentLoc *> (this + 1);
56371a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  }
56471a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
56571a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  /// \brief Retrieve the template arguments
56671a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  const TemplateArgumentLoc *getTemplateArgs() const {
56771a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis    return reinterpret_cast<const TemplateArgumentLoc *> (this + 1);
56871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  }
56971a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
57071a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  const TemplateArgumentLoc &operator[](unsigned I) const {
57171a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis    return getTemplateArgs()[I];
57271a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  }
57371a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
57471a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  static const ASTTemplateArgumentListInfo *Create(ASTContext &C,
57571a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis                                          const TemplateArgumentListInfo &List);
57671a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
57771a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  void initializeFrom(const TemplateArgumentListInfo &List);
57871a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  void initializeFrom(const TemplateArgumentListInfo &List,
57971a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis                      bool &Dependent, bool &InstantiationDependent,
58071a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis                      bool &ContainsUnexpandedParameterPack);
58171a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  void copyInto(TemplateArgumentListInfo &List) const;
58271a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis  static std::size_t sizeFor(unsigned NumTemplateArgs);
583e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara};
584e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
585e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara/// \brief Extends ASTTemplateArgumentListInfo with the source location
586e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara/// information for the template keyword; this is used as part of the
587e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara/// representation of qualified identifiers, such as S<T>::template apply<T>.
588e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnarastruct ASTTemplateKWAndArgsInfo : public ASTTemplateArgumentListInfo {
589e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  typedef ASTTemplateArgumentListInfo Base;
590e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
591e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  // NOTE: the source location of the (optional) template keyword is
592e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  // stored after all template arguments.
593e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
594e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  /// \brief Get the source location of the template keyword.
595e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  SourceLocation getTemplateKeywordLoc() const {
596e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara    return *reinterpret_cast<const SourceLocation*>
597e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara      (getTemplateArgs() + NumTemplateArgs);
598e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  }
599e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
600e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  /// \brief Sets the source location of the template keyword.
601e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  void setTemplateKeywordLoc(SourceLocation TemplateKWLoc) {
602e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara    *reinterpret_cast<SourceLocation*>
603e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara      (getTemplateArgs() + NumTemplateArgs) = TemplateKWLoc;
604e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  }
605e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
606e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  static const ASTTemplateKWAndArgsInfo*
607e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  Create(ASTContext &C, SourceLocation TemplateKWLoc,
608e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara         const TemplateArgumentListInfo &List);
609e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
610e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  void initializeFrom(SourceLocation TemplateKWLoc,
611e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara                      const TemplateArgumentListInfo &List);
612e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  void initializeFrom(SourceLocation TemplateKWLoc,
613e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara                      const TemplateArgumentListInfo &List,
614e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara                      bool &Dependent, bool &InstantiationDependent,
615e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara                      bool &ContainsUnexpandedParameterPack);
616e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  void initializeFrom(SourceLocation TemplateKWLoc);
617e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara
618e4b92761b43ced611c417ae478568610f1ad7b1eAbramo Bagnara  static std::size_t sizeFor(unsigned NumTemplateArgs);
61971a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis};
62071a7605977113c795edd44fcbd2302ad49506653Argyrios Kyrtzidis
621a933319ebf754396623165f9dc0a29c2a48879f5Douglas Gregorconst DiagnosticBuilder &operator<<(const DiagnosticBuilder &DB,
622a933319ebf754396623165f9dc0a29c2a48879f5Douglas Gregor                                    const TemplateArgument &Arg);
62333500955d731c73717af52088b7fc0e7a85681e7John McCall
62433500955d731c73717af52088b7fc0e7a85681e7John McCallinline TemplateSpecializationType::iterator
62533500955d731c73717af52088b7fc0e7a85681e7John McCall    TemplateSpecializationType::end() const {
62633500955d731c73717af52088b7fc0e7a85681e7John McCall  return getArgs() + getNumArgs();
62733500955d731c73717af52088b7fc0e7a85681e7John McCall}
62833500955d731c73717af52088b7fc0e7a85681e7John McCall
62933500955d731c73717af52088b7fc0e7a85681e7John McCallinline DependentTemplateSpecializationType::iterator
63033500955d731c73717af52088b7fc0e7a85681e7John McCall    DependentTemplateSpecializationType::end() const {
63133500955d731c73717af52088b7fc0e7a85681e7John McCall  return getArgs() + getNumArgs();
63233500955d731c73717af52088b7fc0e7a85681e7John McCall}
63333500955d731c73717af52088b7fc0e7a85681e7John McCall
63433500955d731c73717af52088b7fc0e7a85681e7John McCallinline const TemplateArgument &
63533500955d731c73717af52088b7fc0e7a85681e7John McCall    TemplateSpecializationType::getArg(unsigned Idx) const {
63633500955d731c73717af52088b7fc0e7a85681e7John McCall  assert(Idx < getNumArgs() && "Template argument out of range");
63733500955d731c73717af52088b7fc0e7a85681e7John McCall  return getArgs()[Idx];
63833500955d731c73717af52088b7fc0e7a85681e7John McCall}
63933500955d731c73717af52088b7fc0e7a85681e7John McCall
64033500955d731c73717af52088b7fc0e7a85681e7John McCallinline const TemplateArgument &
64133500955d731c73717af52088b7fc0e7a85681e7John McCall    DependentTemplateSpecializationType::getArg(unsigned Idx) const {
64233500955d731c73717af52088b7fc0e7a85681e7John McCall  assert(Idx < getNumArgs() && "Template argument out of range");
64333500955d731c73717af52088b7fc0e7a85681e7John McCall  return getArgs()[Idx];
64433500955d731c73717af52088b7fc0e7a85681e7John McCall}
645a933319ebf754396623165f9dc0a29c2a48879f5Douglas Gregor
646a933319ebf754396623165f9dc0a29c2a48879f5Douglas Gregor} // end namespace clang
647275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall
648275c10a8a4a43219f67d8d2c912ec6294d9d9af2John McCall#endif
649