//===-- DeclTemplate.h - Classes for representing C++ templates -*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file defines the C++ template declaration subclasses.
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_CLANG_AST_DECLTEMPLATE_H
#define LLVM_CLANG_AST_DECLTEMPLATE_H
#include "clang/AST/DeclCXX.h"
#include "llvm/ADT/APSInt.h"
#include "llvm/ADT/FoldingSet.h"
#include "llvm/ADT/PointerUnion.h"
#include <limits>
namespace clang {
class TemplateParameterList;
class TemplateDecl;
class FunctionTemplateDecl;
class ClassTemplateDecl;
class ClassTemplatePartialSpecializationDecl;
class TemplateTypeParmDecl;
class NonTypeTemplateParmDecl;
class TemplateTemplateParmDecl;
/// \brief Stores a template parameter of any kind.
typedef llvm::PointerUnion3<TemplateTypeParmDecl*, NonTypeTemplateParmDecl*,
TemplateTemplateParmDecl*> TemplateParameter;
/// TemplateParameterList - Stores a list of template parameters for a
/// TemplateDecl and its derived classes.
class TemplateParameterList {
/// The location of the 'template' keyword.
SourceLocation TemplateLoc;
/// The locations of the '<' and '>' angle brackets.
SourceLocation LAngleLoc, RAngleLoc;
/// The number of template parameters in this template
/// parameter list.
unsigned NumParams;
TemplateParameterList(SourceLocation TemplateLoc, SourceLocation LAngleLoc,
Decl **Params, unsigned NumParams,
SourceLocation RAngleLoc);
public:
static TemplateParameterList *Create(ASTContext &C,
SourceLocation TemplateLoc,
SourceLocation LAngleLoc,
Decl **Params,
unsigned NumParams,
SourceLocation RAngleLoc);
/// iterator - Iterates through the template parameters in this list.
typedef Decl** iterator;
/// const_iterator - Iterates through the template parameters in this list.
typedef Decl* const* const_iterator;
iterator begin() { return reinterpret_cast<Decl **>(this + 1); }
const_iterator begin() const {
return reinterpret_cast<Decl * const *>(this + 1);
}
iterator end() { return begin() + NumParams; }
const_iterator end() const { return begin() + NumParams; }
unsigned size() const { return NumParams; }
Decl* getParam(unsigned Idx) {
assert(Idx < size() && "Template parameter index out-of-range");
return begin()[Idx];
}
const Decl* getParam(unsigned Idx) const {
assert(Idx < size() && "Template parameter index out-of-range");
return begin()[Idx];
}
/// \btief Returns the minimum number of arguments needed to form a
/// template specialization. This may be fewer than the number of
/// template parameters, if some of the parameters have default
/// arguments or if there is a parameter pack.
unsigned getMinRequiredArguments() const;
SourceLocation getTemplateLoc() const { return TemplateLoc; }
SourceLocation getLAngleLoc() const { return LAngleLoc; }
SourceLocation getRAngleLoc() const { return RAngleLoc; }
SourceRange getSourceRange() const {
return SourceRange(TemplateLoc, RAngleLoc);
}
};
/// \brief Represents a template argument within a class template
/// specialization.
class TemplateArgument {
union {
uintptr_t TypeOrValue;
struct {
char Value[sizeof(llvm::APSInt)];
void *Type;
} Integer;
struct {
TemplateArgument *Args;
unsigned NumArgs;
bool CopyArgs;
} Args;
};
/// \brief Location of the beginning of this template argument.
SourceLocation StartLoc;
public:
/// \brief The type of template argument we're storing.
enum ArgKind {
Null = 0,
/// The template argument is a type. Its value is stored in the
/// TypeOrValue field.
Type = 1,
/// The template argument is a declaration
Declaration = 2,
/// The template argument is an integral value stored in an llvm::APSInt.
Integral = 3,
/// The template argument is a value- or type-dependent expression
/// stored in an Expr*.
Expression = 4,
/// The template argument is actually a parameter pack. Arguments are stored
/// in the Args struct.
Pack =