This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

Re: Patch for constexpr variable templates


This patch prevents the initializer from being checked when it is
dependent. It also sets the type of a dependent template-id referring
to a variable template to be unknown, making such expressions type
dependent.

2014-08-07  Andrew Sutton  <andrew.n.sutton@gmail.com>

        * pt.c (lookup_template_variable): Make the type unspecified if
        any template arguments are dependent.
        * decl.c (cp_finish_decl): Don't check the initializer if it is
        value-dependent.

New test included.

Andrew Sutton


On Wed, Aug 6, 2014 at 9:34 PM, Jason Merrill <jason@redhat.com> wrote:
> On 08/05/2014 04:06 PM, Paolo Carlini wrote:
>>
>> Great. I will double check but var-templ4.C fails for me with an ICE.
>
>
> Hunh, I wonder how I missed that.
>
> Here's what I'm checking in; we want to unset DECL_COMDAT for variable
> templates, too.
>
>
Index: gcc/testsuite/g++.dg/cpp1y/var-templ6.C
===================================================================
--- gcc/testsuite/g++.dg/cpp1y/var-templ6.C	(revision 0)
+++ gcc/testsuite/g++.dg/cpp1y/var-templ6.C	(revision 0)
@@ -0,0 +1,12 @@
+// { dg-options "-std=c++1y" }
+
+template<typename T>
+  constexpr bool Class = __is_class(T);
+
+template<typename T>
+  constexpr bool Test = Class<T>;
+
+struct S { };
+
+static_assert(!Test<int>, "");
+static_assert(Test<S>, "");
Index: gcc/cp/decl.c
===================================================================
--- gcc/cp/decl.c	(revision 213667)
+++ gcc/cp/decl.c	(working copy)
@@ -6417,19 +6417,20 @@ cp_finish_decl (tree decl, tree init, bo
 	  DECL_INITIAL (decl) = NULL_TREE;
 	}
 
+      bool value_dependent_p = init && value_dependent_init_p (init);
+
       /* Generally, initializers in templates are expanded when the
 	 template is instantiated.  But, if DECL is a variable constant
 	 then it can be used in future constant expressions, so its value
 	 must be available. */
-
-      if (!VAR_P (decl) || dependent_type_p (type))
+      if (!VAR_P (decl) || type_dependent_p || value_dependent_p)
 	/* We can't do anything if the decl has dependent type.  */;
       else if (init
 	       && init_const_expr_p
 	       && !type_dependent_p
 	       && decl_maybe_constant_var_p (decl)
 	       && !type_dependent_init_p (init)
-	       && !value_dependent_init_p (init))
+	       && !value_dependent_p)
 	{
 	  /* This variable seems to be a non-dependent constant, so process
 	     its initializer.  If check_initializer returns non-null the
Index: gcc/cp/pt.c
===================================================================
--- gcc/cp/pt.c	(revision 213667)
+++ gcc/cp/pt.c	(working copy)
@@ -8260,13 +8260,23 @@ lookup_template_class (tree d1, tree arg
   return ret;
 }
 
-/* Return a TEMPLATE_ID_EXPR for the given variable template and ARGLIST. */
+/* Return a TEMPLATE_ID_EXPR for the given variable template and ARGLIST. 
+   If the ARGLIST refers to any template parameters, the type of the
+   expression is the unknown_type_node since the template-id could
+   refer to an explicit or partial specialization.
+*/
 
 tree
 lookup_template_variable (tree templ, tree arglist)
 {
-  return build2 (TEMPLATE_ID_EXPR, TREE_TYPE (templ), templ, arglist);
+  tree type;
+  if (uses_template_parms (arglist))
+    type = unknown_type_node;
+  else
+    type = TREE_TYPE (templ);
+  return build2 (TEMPLATE_ID_EXPR, type, templ, arglist);
 }
+
 
 struct pair_fn_data
 {

Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]