diff options
author | Douglas Gregor <dgregor@apple.com> | 2009-10-15 14:05:49 +0000 |
---|---|---|
committer | Douglas Gregor <dgregor@apple.com> | 2009-10-15 14:05:49 +0000 |
commit | e2d3a3de71b2fa35614cb732a6da95a41fa38ad9 (patch) | |
tree | f59f0a8f3395319bf7cf5e2e065bc4e71ac8cc76 /lib/Sema/SemaTemplateInstantiateDecl.cpp | |
parent | bf7643e7966cd9acd797a84870018034112e49d3 (diff) |
Diagnose explicit instantiations of function templates and member
functions/static data members of class template specializations that
do not have definitions. This is the latter part of [temp.explicit]p4;
the former part still needs more testing.
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@84182 91177308-0d34-0410-b5e6-96231b3b80d8
Diffstat (limited to 'lib/Sema/SemaTemplateInstantiateDecl.cpp')
-rw-r--r-- | lib/Sema/SemaTemplateInstantiateDecl.cpp | 39 |
1 files changed, 36 insertions, 3 deletions
diff --git a/lib/Sema/SemaTemplateInstantiateDecl.cpp b/lib/Sema/SemaTemplateInstantiateDecl.cpp index 060cc55983..ca05d59aba 100644 --- a/lib/Sema/SemaTemplateInstantiateDecl.cpp +++ b/lib/Sema/SemaTemplateInstantiateDecl.cpp @@ -1044,9 +1044,14 @@ TemplateDeclInstantiator::InitMethodInstantiation(CXXMethodDecl *New, /// /// \param Recursive if true, recursively instantiates any functions that /// are required by this instantiation. +/// +/// \param DefinitionRequired if true, then we are performing an explicit +/// instantiation where the body of the function is required. Complain if +/// there is no such body. void Sema::InstantiateFunctionDefinition(SourceLocation PointOfInstantiation, FunctionDecl *Function, - bool Recursive) { + bool Recursive, + bool DefinitionRequired) { if (Function->isInvalidDecl()) return; @@ -1075,8 +1080,24 @@ void Sema::InstantiateFunctionDefinition(SourceLocation PointOfInstantiation, if (PatternDecl) Pattern = PatternDecl->getBody(PatternDecl); - if (!Pattern) + if (!Pattern) { + if (DefinitionRequired) { + if (Function->getPrimaryTemplate()) + Diag(PointOfInstantiation, + diag::err_explicit_instantiation_undefined_func_template) + << Function->getPrimaryTemplate(); + else + Diag(PointOfInstantiation, + diag::err_explicit_instantiation_undefined_member) + << 1 << Function->getDeclName() << Function->getDeclContext(); + + if (PatternDecl) + Diag(PatternDecl->getLocation(), + diag::note_explicit_instantiation_here); + } + return; + } // C++0x [temp.explicit]p9: // Except for inline functions, other explicit instantiation declarations @@ -1161,10 +1182,15 @@ void Sema::InstantiateFunctionDefinition(SourceLocation PointOfInstantiation, /// /// \param Recursive if true, recursively instantiates any functions that /// are required by this instantiation. +/// +/// \param DefinitionRequired if true, then we are performing an explicit +/// instantiation where an out-of-line definition of the member variable +/// is required. Complain if there is no such definition. void Sema::InstantiateStaticDataMemberDefinition( SourceLocation PointOfInstantiation, VarDecl *Var, - bool Recursive) { + bool Recursive, + bool DefinitionRequired) { if (Var->isInvalidDecl()) return; @@ -1187,6 +1213,13 @@ void Sema::InstantiateStaticDataMemberDefinition( // so we won't perform any instantiation. Rather, we rely on the user to // instantiate this definition (or provide a specialization for it) in // another translation unit. + if (DefinitionRequired) { + Diag(PointOfInstantiation, + diag::err_explicit_instantiation_undefined_member) + << 2 << Var->getDeclName() << Var->getDeclContext(); + Diag(Def->getLocation(), diag::note_explicit_instantiation_here); + } + return; } |