/// TemplateArgumentList - It copies the template arguments into a locally
/// new[]'d array.
TemplateArgumentList(ASTContext &Context,
- unsigned NumArgs, const TemplateArgument *Args);
+ const TemplateArgument *Args, unsigned NumArgs);
/// Produces a shallow copy of the given template argument list. This
/// assumes that the input argument list outlives it. This takes the list as
/// a pointer to avoid looking like a copy constructor, since this really
/// really isn't safe to use that way.
explicit TemplateArgumentList(const TemplateArgumentList *Other);
-
+
+ TemplateArgumentList() : NumFlatArguments(0), NumStructuredArguments(0) { }
+
/// Used to release the memory associated with a TemplateArgumentList
/// object. FIXME: This is currently not called anywhere, but the
/// memory will still be freed when using a BumpPtrAllocator.
void Destroy(ASTContext &C);
~TemplateArgumentList();
+
+ /// \brief Copies the template arguments into a locally new[]'d array.
+ void init(ASTContext &Context,
+ const TemplateArgument *Args, unsigned NumArgs);
/// \brief Retrieve the template argument at a given index.
const TemplateArgument &get(unsigned Idx) const {
TemplateArgumentListBuilder &Builder,
ClassTemplateSpecializationDecl *PrevDecl);
+ explicit ClassTemplateSpecializationDecl(Kind DK);
+
public:
static ClassTemplateSpecializationDecl *
Create(ASTContext &Context, TagKind TK, DeclContext *DC, SourceLocation L,
TemplateArgumentListBuilder &Builder,
ClassTemplateSpecializationDecl *PrevDecl);
+ static ClassTemplateSpecializationDecl *CreateEmpty(ASTContext &Context);
+
virtual void Destroy(ASTContext& C);
virtual void getNameForDiagnostic(std::string &S,
return TemplateArgs;
}
+ /// \brief Initialize the template arguments of the class template
+ /// specialization.
+ void initTemplateArgs(TemplateArgument *Args, unsigned NumArgs) {
+ assert(TemplateArgs.flat_size() == 0 &&
+ "Template arguments already initialized!");
+ TemplateArgs.init(getASTContext(), Args, NumArgs);
+ }
+
/// \brief Determine the kind of specialization that this
/// declaration represents.
TemplateSpecializationKind getSpecializationKind() const {
SpecializedTemplate.get<ClassTemplateDecl*>());
}
+ /// \brief Retrieve the class template or class template partial
+ /// specialization which was specialized by this.
+ llvm::PointerUnion<ClassTemplateDecl *,
+ ClassTemplatePartialSpecializationDecl *>
+ getSpecializedTemplateOrPartial() const {
+ if (SpecializedPartialSpecialization *PartialSpec
+ = SpecializedTemplate.dyn_cast<SpecializedPartialSpecialization*>())
+ return PartialSpec->PartialSpecialization;
+
+ return const_cast<ClassTemplateDecl*>(
+ SpecializedTemplate.get<ClassTemplateDecl*>());
+ }
+
/// \brief Retrieve the set of template arguments that should be used
/// to instantiate members of the class template or class template partial
/// specialization from which this class template specialization was
/// template arguments have been deduced.
void setInstantiationOf(ClassTemplatePartialSpecializationDecl *PartialSpec,
TemplateArgumentList *TemplateArgs) {
+ assert(!SpecializedTemplate.is<SpecializedPartialSpecialization*>() &&
+ "Already set to a class template partial specialization!");
SpecializedPartialSpecialization *PS
= new (getASTContext()) SpecializedPartialSpecialization();
PS->PartialSpecialization = PartialSpec;
SpecializedTemplate = PS;
}
+ /// \brief Note that this class template specialization is actually an
+ /// instantiation of the given class template partial specialization whose
+ /// template arguments have been deduced.
+ void setInstantiationOf(ClassTemplatePartialSpecializationDecl *PartialSpec,
+ TemplateArgument *TemplateArgs,
+ unsigned NumTemplateArgs) {
+ ASTContext &Ctx = getASTContext();
+ setInstantiationOf(PartialSpec,
+ new (Ctx) TemplateArgumentList(Ctx, TemplateArgs,
+ NumTemplateArgs));
+ }
+
+ /// \brief Note that this class template specialization is an instantiation
+ /// of the given class template.
+ void setInstantiationOf(ClassTemplateDecl *TemplDecl) {
+ assert(!SpecializedTemplate.is<SpecializedPartialSpecialization*>() &&
+ "Previously set to a class template partial specialization!");
+ SpecializedTemplate = TemplDecl;
+ }
+
/// \brief Sets the type of this specialization as it was written by
/// the user. This will be a class template specialization type.
void setTypeAsWritten(TypeSourceInfo *T) {
TemplateParams(Params), ArgsAsWritten(ArgInfos),
NumArgsAsWritten(NumArgInfos), SequenceNumber(SequenceNumber),
InstantiatedFromMember(0, false) { }
+
+ ClassTemplatePartialSpecializationDecl()
+ : ClassTemplateSpecializationDecl(ClassTemplatePartialSpecialization),
+ TemplateParams(0), ArgsAsWritten(0),
+ NumArgsAsWritten(0), SequenceNumber(0),
+ InstantiatedFromMember(0, false) { }
public:
static ClassTemplatePartialSpecializationDecl *
ClassTemplatePartialSpecializationDecl *PrevDecl,
unsigned SequenceNumber);
+ static ClassTemplatePartialSpecializationDecl *
+ CreateEmpty(ASTContext &Context);
+
/// Get the list of template parameters
TemplateParameterList *getTemplateParameters() const {
return TemplateParams;
}
+ void initTemplateParameters(TemplateParameterList *Params) {
+ assert(TemplateParams == 0 && "TemplateParams already set");
+ TemplateParams = Params;
+ }
+
/// Get the template arguments as written.
TemplateArgumentLoc *getTemplateArgsAsWritten() const {
return ArgsAsWritten;
}
+ void initTemplateArgsAsWritten(const TemplateArgumentListInfo &ArgInfos);
+
/// Get the number of template arguments as written.
unsigned getNumTemplateArgsAsWritten() const {
return NumArgsAsWritten;
/// \brief Get the sequence number for this class template partial
/// specialization.
unsigned getSequenceNumber() const { return SequenceNumber; }
+ void setSequenceNumber(unsigned N) { SequenceNumber = N; }
/// \brief Retrieve the member class template partial specialization from
/// which this particular class template partial specialization was
}
TemplateArgumentList::TemplateArgumentList(ASTContext &Context,
- unsigned NumArgs,
- const TemplateArgument *Args)
- : NumFlatArguments(NumArgs),
- NumStructuredArguments(NumArgs) {
-
- TemplateArgument *NewArgs = new (Context) TemplateArgument[NumArgs];
- std::copy(Args, Args+NumArgs, NewArgs);
- FlatArguments.setPointer(NewArgs);
- FlatArguments.setInt(1); // Owns the pointer.
-
- // Just reuse the flat arguments array.
- StructuredArguments.setPointer(NewArgs);
- StructuredArguments.setInt(0); // Doesn't own the pointer.
+ const TemplateArgument *Args,
+ unsigned NumArgs) {
+ init(Context, Args, NumArgs);
}
/// Produces a shallow copy of the given template argument list. This
StructuredArguments(Other->StructuredArguments.getPointer(), false),
NumStructuredArguments(Other->NumStructuredArguments) { }
+void TemplateArgumentList::init(ASTContext &Context,
+ const TemplateArgument *Args,
+ unsigned NumArgs) {
+assert(NumFlatArguments == 0 && NumStructuredArguments == 0 &&
+ "Already initialized!");
+
+NumFlatArguments = NumStructuredArguments = NumArgs;
+TemplateArgument *NewArgs = new (Context) TemplateArgument[NumArgs];
+std::copy(Args, Args+NumArgs, NewArgs);
+FlatArguments.setPointer(NewArgs);
+FlatArguments.setInt(1); // Owns the pointer.
+
+// Just reuse the flat arguments array.
+StructuredArguments.setPointer(NewArgs);
+StructuredArguments.setInt(0); // Doesn't own the pointer.
+}
+
void TemplateArgumentList::Destroy(ASTContext &C) {
if (FlatArguments.getInt())
C.Deallocate((void*)FlatArguments.getPointer());
SpecializationKind(TSK_Undeclared) {
}
+ClassTemplateSpecializationDecl::ClassTemplateSpecializationDecl(Kind DK)
+ : CXXRecordDecl(DK, TTK_Struct, 0, SourceLocation(), 0, 0),
+ ExplicitInfo(0),
+ SpecializationKind(TSK_Undeclared) {
+}
+
ClassTemplateSpecializationDecl *
ClassTemplateSpecializationDecl::Create(ASTContext &Context, TagKind TK,
DeclContext *DC, SourceLocation L,
return Result;
}
+ClassTemplateSpecializationDecl *
+ClassTemplateSpecializationDecl::CreateEmpty(ASTContext &Context) {
+ return
+ new (Context)ClassTemplateSpecializationDecl(ClassTemplateSpecialization);
+}
+
void ClassTemplateSpecializationDecl::Destroy(ASTContext &C) {
delete ExplicitInfo;
return Result;
}
+ClassTemplatePartialSpecializationDecl *
+ClassTemplatePartialSpecializationDecl::CreateEmpty(ASTContext &Context) {
+ return new (Context)ClassTemplatePartialSpecializationDecl();
+}
+
+void ClassTemplatePartialSpecializationDecl::
+initTemplateArgsAsWritten(const TemplateArgumentListInfo &ArgInfos) {
+ assert(ArgsAsWritten == 0 && "ArgsAsWritten already set");
+ unsigned N = ArgInfos.size();
+ TemplateArgumentLoc *ClonedArgs
+ = new (getASTContext()) TemplateArgumentLoc[N];
+ for (unsigned I = 0; I != N; ++I)
+ ClonedArgs[I] = ArgInfos[I];
+
+ ArgsAsWritten = ClonedArgs;
+ NumArgsAsWritten = N;
+}
+
//===----------------------------------------------------------------------===//
// FriendTemplateDecl Implementation
//===----------------------------------------------------------------------===//