https://github.com/ilya-biryukov updated https://github.com/llvm/llvm-project/pull/99880
>From ad2d2f42282d5493761fa0af13b77dc7aab73bba Mon Sep 17 00:00:00 2001 From: Ilya Biryukov <ibiryu...@google.com> Date: Mon, 22 Jul 2024 15:19:07 +0200 Subject: [PATCH 1/5] [Sema] Default arguments for template parameters affect ContainsUnexpandedPacks This addresses the FIXME in the code. There are tests for the new behavior in a follow up fix for #99877, which also addresses other bugs that prevent exposing the wrong results of `ContainsUnexpandedPacks` in the outputs of the compiler without crashes. --- clang/lib/AST/DeclTemplate.cpp | 38 ++++++++++++++++++++++++---------- 1 file changed, 27 insertions(+), 11 deletions(-) diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index 722c7fcf0b0df..f95be88e6c087 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -61,27 +61,43 @@ TemplateParameterList::TemplateParameterList(const ASTContext& C, bool IsPack = P->isTemplateParameterPack(); if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P)) { - if (!IsPack && NTTP->getType()->containsUnexpandedParameterPack()) - ContainsUnexpandedParameterPack = true; + if (!IsPack) { + if (NTTP->getType()->containsUnexpandedParameterPack()) + ContainsUnexpandedParameterPack = true; + else if (NTTP->hasDefaultArgument() && + NTTP->getDefaultArgument() + .getArgument() + .containsUnexpandedParameterPack()) + ContainsUnexpandedParameterPack = true; + } if (NTTP->hasPlaceholderTypeConstraint()) HasConstrainedParameters = true; } else if (const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(P)) { - if (!IsPack && - TTP->getTemplateParameters()->containsUnexpandedParameterPack()) - ContainsUnexpandedParameterPack = true; - } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) { - if (const TypeConstraint *TC = TTP->getTypeConstraint()) { - if (TC->getImmediatelyDeclaredConstraint() - ->containsUnexpandedParameterPack()) + if (!IsPack) { + if (TTP->getTemplateParameters()->containsUnexpandedParameterPack()) ContainsUnexpandedParameterPack = true; + else if (TTP->hasDefaultArgument() && + TTP->getDefaultArgument() + .getArgument() + .containsUnexpandedParameterPack()) + ContainsUnexpandedParameterPack = true; + } + } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) { + if (!IsPack && TTP->hasDefaultArgument() && + TTP->getDefaultArgument() + .getArgument() + .containsUnexpandedParameterPack()) { + ContainsUnexpandedParameterPack = true; + } else if (const TypeConstraint *TC = TTP->getTypeConstraint(); + TC && TC->getImmediatelyDeclaredConstraint() + ->containsUnexpandedParameterPack()) { + ContainsUnexpandedParameterPack = true; } if (TTP->hasTypeConstraint()) HasConstrainedParameters = true; } else { llvm_unreachable("unexpected template parameter type"); } - // FIXME: If a default argument contains an unexpanded parameter pack, the - // template parameter list does too. } if (HasRequiresClause) { >From 34a18e0c78c2915df201aea368f6c2763f885fbe Mon Sep 17 00:00:00 2001 From: Ilya Biryukov <ibiryu...@google.com> Date: Tue, 23 Jul 2024 13:01:10 +0200 Subject: [PATCH 2/5] fixup! [Sema] Default arguments for template parameters affect ContainsUnexpandedPacks Add a helper function to avoid code duplication. --- clang/lib/AST/DeclTemplate.cpp | 23 +++++++++++------------ 1 file changed, 11 insertions(+), 12 deletions(-) diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index f95be88e6c087..5d207cfbecb97 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -45,6 +45,14 @@ using namespace clang; //===----------------------------------------------------------------------===// +namespace { +template<class TemplateParam> +bool DefaultArgumentContainsUnexpandedPack(const TemplateParam& P) { + return P.hasDefaultArgument() && + P.getDefaultArgument().getArgument().containsUnexpandedParameterPack(); +} +} + TemplateParameterList::TemplateParameterList(const ASTContext& C, SourceLocation TemplateLoc, SourceLocation LAngleLoc, @@ -64,10 +72,7 @@ TemplateParameterList::TemplateParameterList(const ASTContext& C, if (!IsPack) { if (NTTP->getType()->containsUnexpandedParameterPack()) ContainsUnexpandedParameterPack = true; - else if (NTTP->hasDefaultArgument() && - NTTP->getDefaultArgument() - .getArgument() - .containsUnexpandedParameterPack()) + else if (DefaultArgumentContainsUnexpandedPack(*NTTP)) ContainsUnexpandedParameterPack = true; } if (NTTP->hasPlaceholderTypeConstraint()) @@ -76,17 +81,11 @@ TemplateParameterList::TemplateParameterList(const ASTContext& C, if (!IsPack) { if (TTP->getTemplateParameters()->containsUnexpandedParameterPack()) ContainsUnexpandedParameterPack = true; - else if (TTP->hasDefaultArgument() && - TTP->getDefaultArgument() - .getArgument() - .containsUnexpandedParameterPack()) + else if (DefaultArgumentContainsUnexpandedPack(*TTP)) ContainsUnexpandedParameterPack = true; } } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) { - if (!IsPack && TTP->hasDefaultArgument() && - TTP->getDefaultArgument() - .getArgument() - .containsUnexpandedParameterPack()) { + if (!IsPack && DefaultArgumentContainsUnexpandedPack(*TTP)) { ContainsUnexpandedParameterPack = true; } else if (const TypeConstraint *TC = TTP->getTypeConstraint(); TC && TC->getImmediatelyDeclaredConstraint() >From d8e2db25421c459e6f2a19baf5e387ab377378ee Mon Sep 17 00:00:00 2001 From: Ilya Biryukov <ibiryu...@google.com> Date: Tue, 23 Jul 2024 13:07:26 +0200 Subject: [PATCH 3/5] fixup! [Sema] Default arguments for template parameters affect ContainsUnexpandedPacks reformat the code --- clang/lib/AST/DeclTemplate.cpp | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index 5d207cfbecb97..c1a4181d9b6e2 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -44,14 +44,13 @@ using namespace clang; // TemplateParameterList Implementation //===----------------------------------------------------------------------===// - namespace { -template<class TemplateParam> -bool DefaultArgumentContainsUnexpandedPack(const TemplateParam& P) { +template <class TemplateParam> +bool DefaultArgumentContainsUnexpandedPack(const TemplateParam &P) { return P.hasDefaultArgument() && P.getDefaultArgument().getArgument().containsUnexpandedParameterPack(); } -} +} // namespace TemplateParameterList::TemplateParameterList(const ASTContext& C, SourceLocation TemplateLoc, >From ae4021d31bf71622765221ac68b7ff1a316fe670 Mon Sep 17 00:00:00 2001 From: Ilya Biryukov <ibiryu...@google.com> Date: Tue, 23 Jul 2024 15:51:04 +0200 Subject: [PATCH 4/5] fixup! [Sema] Default arguments for template parameters affect ContainsUnexpandedPacks Simplify the code and reduce nesting --- clang/lib/AST/DeclTemplate.cpp | 18 +++++++----------- 1 file changed, 7 insertions(+), 11 deletions(-) diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index c1a4181d9b6e2..5a47b4e646355 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -68,20 +68,16 @@ TemplateParameterList::TemplateParameterList(const ASTContext& C, bool IsPack = P->isTemplateParameterPack(); if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P)) { - if (!IsPack) { - if (NTTP->getType()->containsUnexpandedParameterPack()) - ContainsUnexpandedParameterPack = true; - else if (DefaultArgumentContainsUnexpandedPack(*NTTP)) - ContainsUnexpandedParameterPack = true; - } + if (!IsPack && (NTTP->getType()->containsUnexpandedParameterPack() || + DefaultArgumentContainsUnexpandedPack(*NTTP))) + ContainsUnexpandedParameterPack = true; if (NTTP->hasPlaceholderTypeConstraint()) HasConstrainedParameters = true; } else if (const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(P)) { - if (!IsPack) { - if (TTP->getTemplateParameters()->containsUnexpandedParameterPack()) - ContainsUnexpandedParameterPack = true; - else if (DefaultArgumentContainsUnexpandedPack(*TTP)) - ContainsUnexpandedParameterPack = true; + if (!IsPack && + (TTP->getTemplateParameters()->containsUnexpandedParameterPack() || + DefaultArgumentContainsUnexpandedPack(*TTP))) { + ContainsUnexpandedParameterPack = true; } } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) { if (!IsPack && DefaultArgumentContainsUnexpandedPack(*TTP)) { >From d64b95c8df6d0a287fb1924d1ced090d33d76ce3 Mon Sep 17 00:00:00 2001 From: Ilya Biryukov <ibiryu...@google.com> Date: Tue, 23 Jul 2024 19:11:46 +0200 Subject: [PATCH 5/5] fixup! [Sema] Default arguments for template parameters affect ContainsUnexpandedPacks - Rename function - Use static instead of anonymous namespace --- clang/lib/AST/DeclTemplate.cpp | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/clang/lib/AST/DeclTemplate.cpp b/clang/lib/AST/DeclTemplate.cpp index 5a47b4e646355..976b3a3e1eced 100644 --- a/clang/lib/AST/DeclTemplate.cpp +++ b/clang/lib/AST/DeclTemplate.cpp @@ -44,13 +44,12 @@ using namespace clang; // TemplateParameterList Implementation //===----------------------------------------------------------------------===// -namespace { template <class TemplateParam> -bool DefaultArgumentContainsUnexpandedPack(const TemplateParam &P) { +static bool +DefaultTemplateArgumentContainsUnexpandedPack(const TemplateParam &P) { return P.hasDefaultArgument() && P.getDefaultArgument().getArgument().containsUnexpandedParameterPack(); } -} // namespace TemplateParameterList::TemplateParameterList(const ASTContext& C, SourceLocation TemplateLoc, @@ -69,18 +68,18 @@ TemplateParameterList::TemplateParameterList(const ASTContext& C, bool IsPack = P->isTemplateParameterPack(); if (const auto *NTTP = dyn_cast<NonTypeTemplateParmDecl>(P)) { if (!IsPack && (NTTP->getType()->containsUnexpandedParameterPack() || - DefaultArgumentContainsUnexpandedPack(*NTTP))) + DefaultTemplateArgumentContainsUnexpandedPack(*NTTP))) ContainsUnexpandedParameterPack = true; if (NTTP->hasPlaceholderTypeConstraint()) HasConstrainedParameters = true; } else if (const auto *TTP = dyn_cast<TemplateTemplateParmDecl>(P)) { if (!IsPack && (TTP->getTemplateParameters()->containsUnexpandedParameterPack() || - DefaultArgumentContainsUnexpandedPack(*TTP))) { + DefaultTemplateArgumentContainsUnexpandedPack(*TTP))) { ContainsUnexpandedParameterPack = true; } } else if (const auto *TTP = dyn_cast<TemplateTypeParmDecl>(P)) { - if (!IsPack && DefaultArgumentContainsUnexpandedPack(*TTP)) { + if (!IsPack && DefaultTemplateArgumentContainsUnexpandedPack(*TTP)) { ContainsUnexpandedParameterPack = true; } else if (const TypeConstraint *TC = TTP->getTypeConstraint(); TC && TC->getImmediatelyDeclaredConstraint() _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits