c++: unexpanded pack in var tmpl partial spec [PR100652]
Commit Message
Here we're not spotting a bare parameter pack appearing in the argument
list of a variable template partial specialization because we only look
for them within the decl's TREE_TYPE, which is sufficient for class
templates but not for variable templates.
Bootstrapped and regtested on x86_64-pc-linux-gnu, does this look OK for
trunk?
PR c++/100652
gcc/cp/ChangeLog:
* pt.c (push_template_decl): Check for bare parameter packs in
the argument list of a variable template partial specialization.
gcc/testsuite/ChangeLog:
* g++.dg/cpp1y/var-templ69.C: New test.
---
gcc/cp/pt.c | 17 ++++++++++++-----
gcc/testsuite/g++.dg/cpp1y/var-templ69.C | 5 +++++
2 files changed, 17 insertions(+), 5 deletions(-)
create mode 100644 gcc/testsuite/g++.dg/cpp1y/var-templ69.C
Comments
On 11/8/21 09:45, Patrick Palka wrote:
> Here we're not spotting a bare parameter pack appearing in the argument
> list of a variable template partial specialization because we only look
> for them within the decl's TREE_TYPE, which is sufficient for class
> templates but not for variable templates.
>
> Bootstrapped and regtested on x86_64-pc-linux-gnu, does this look OK for
> trunk?
OK.
> PR c++/100652
>
> gcc/cp/ChangeLog:
>
> * pt.c (push_template_decl): Check for bare parameter packs in
> the argument list of a variable template partial specialization.
>
> gcc/testsuite/ChangeLog:
>
> * g++.dg/cpp1y/var-templ69.C: New test.
> ---
> gcc/cp/pt.c | 17 ++++++++++++-----
> gcc/testsuite/g++.dg/cpp1y/var-templ69.C | 5 +++++
> 2 files changed, 17 insertions(+), 5 deletions(-)
> create mode 100644 gcc/testsuite/g++.dg/cpp1y/var-templ69.C
>
> diff --git a/gcc/cp/pt.c b/gcc/cp/pt.c
> index b82b9cc3cd2..991a20a85d4 100644
> --- a/gcc/cp/pt.c
> +++ b/gcc/cp/pt.c
> @@ -5877,12 +5877,19 @@ push_template_decl (tree decl, bool is_friend)
> if (check_for_bare_parameter_packs (TYPE_RAISES_EXCEPTIONS (type)))
> TYPE_RAISES_EXCEPTIONS (type) = NULL_TREE;
> }
> - else if (check_for_bare_parameter_packs (is_typedef_decl (decl)
> - ? DECL_ORIGINAL_TYPE (decl)
> - : TREE_TYPE (decl)))
> + else
> {
> - TREE_TYPE (decl) = error_mark_node;
> - return error_mark_node;
> + if (check_for_bare_parameter_packs (is_typedef_decl (decl)
> + ? DECL_ORIGINAL_TYPE (decl)
> + : TREE_TYPE (decl)))
> + {
> + TREE_TYPE (decl) = error_mark_node;
> + return error_mark_node;
> + }
> +
> + if (is_partial && VAR_P (decl)
> + && check_for_bare_parameter_packs (DECL_TI_ARGS (decl)))
> + return error_mark_node;
> }
>
> if (is_partial)
> diff --git a/gcc/testsuite/g++.dg/cpp1y/var-templ69.C b/gcc/testsuite/g++.dg/cpp1y/var-templ69.C
> new file mode 100644
> index 00000000000..420d617368c
> --- /dev/null
> +++ b/gcc/testsuite/g++.dg/cpp1y/var-templ69.C
> @@ -0,0 +1,5 @@
> +// PR c++/100652
> +// { dg-do compile { target c++14 } }
> +
> +template<class...> int var;
> +template<class... Ts> char var<bool, Ts>; // { dg-error "parameter packs not expanded" }
>
@@ -5877,12 +5877,19 @@ push_template_decl (tree decl, bool is_friend)
if (check_for_bare_parameter_packs (TYPE_RAISES_EXCEPTIONS (type)))
TYPE_RAISES_EXCEPTIONS (type) = NULL_TREE;
}
- else if (check_for_bare_parameter_packs (is_typedef_decl (decl)
- ? DECL_ORIGINAL_TYPE (decl)
- : TREE_TYPE (decl)))
+ else
{
- TREE_TYPE (decl) = error_mark_node;
- return error_mark_node;
+ if (check_for_bare_parameter_packs (is_typedef_decl (decl)
+ ? DECL_ORIGINAL_TYPE (decl)
+ : TREE_TYPE (decl)))
+ {
+ TREE_TYPE (decl) = error_mark_node;
+ return error_mark_node;
+ }
+
+ if (is_partial && VAR_P (decl)
+ && check_for_bare_parameter_packs (DECL_TI_ARGS (decl)))
+ return error_mark_node;
}
if (is_partial)
new file mode 100644
@@ -0,0 +1,5 @@
+// PR c++/100652
+// { dg-do compile { target c++14 } }
+
+template<class...> int var;
+template<class... Ts> char var<bool, Ts>; // { dg-error "parameter packs not expanded" }