OSDN Git Service

* init.c (perform_member_init): Use build_vec_init_expr for
authorjason <jason@138bc75d-0d04-0410-961f-82ee72b054a4>
Sun, 7 Nov 2010 00:46:45 +0000 (00:46 +0000)
committerjason <jason@138bc75d-0d04-0410-961f-82ee72b054a4>
Sun, 7 Nov 2010 00:46:45 +0000 (00:46 +0000)
value-init of arrays, too.
* cp-gimplify.c (cp_gimplify_expr): Use VEC_INIT_EXPR_VALUE_INIT.
* cp-tree.h (VEC_INIT_EXPR_IS_CONSTEXPR): New macro.
(VEC_INIT_EXPR_VALUE_INIT): New macro.
* semantics.c (potential_constant_expression): No longer static.
Check VEC_INIT_EXPR_IS_CONSTEXPR.
* tree.c (build_vec_init_expr): Handle value-init.  Set
VEC_INIT_EXPR_IS_CONSTEXPR and VEC_INIT_EXPR_VALUE_INIT.

git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@166413 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/ChangeLog
gcc/cp/cp-gimplify.c
gcc/cp/cp-tree.h
gcc/cp/init.c
gcc/cp/semantics.c
gcc/cp/tree.c
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/cpp0x/constexpr-ctor3.C [new file with mode: 0644]

index 784f3aa..3f3a8ee 100644 (file)
@@ -1,3 +1,15 @@
+2010-11-06  Jason Merrill  <jason@redhat.com>
+
+       * init.c (perform_member_init): Use build_vec_init_expr for
+       value-init of arrays, too.
+       * cp-gimplify.c (cp_gimplify_expr): Use VEC_INIT_EXPR_VALUE_INIT.
+       * cp-tree.h (VEC_INIT_EXPR_IS_CONSTEXPR): New macro.
+       (VEC_INIT_EXPR_VALUE_INIT): New macro.
+       * semantics.c (potential_constant_expression): No longer static.
+       Check VEC_INIT_EXPR_IS_CONSTEXPR.
+       * tree.c (build_vec_init_expr): Handle value-init.  Set
+       VEC_INIT_EXPR_IS_CONSTEXPR and VEC_INIT_EXPR_VALUE_INIT.
+
 2010-11-06  Nathan Froyd  <froydnj@codesourcery.com>
 
        PR c++/45332
index 705979d..557430d 100644 (file)
@@ -535,7 +535,7 @@ cp_gimplify_expr (tree *expr_p, gimple_seq *pre_p, gimple_seq *post_p)
        gcc_assert (EXPR_HAS_LOCATION (*expr_p));
        input_location = EXPR_LOCATION (*expr_p);
        *expr_p = build_vec_init (VEC_INIT_EXPR_SLOT (*expr_p), NULL_TREE,
-                                 init, /*explicit_value_init_p*/false,
+                                 init, VEC_INIT_EXPR_VALUE_INIT (*expr_p),
                                  from_array,
                                  tf_warning_or_error);
        ret = GS_OK;
index 8f52278..241805c 100644 (file)
@@ -72,6 +72,7 @@ c-common.h, not after.
       CONSTRUCTOR_IS_DIRECT_INIT (in CONSTRUCTOR)
       LAMBDA_EXPR_CAPTURES_THIS_P (in LAMBDA_EXPR)
       DECLTYPE_FOR_LAMBDA_CAPTURE (in DECLTYPE_TYPE)
+      VEC_INIT_EXPR_IS_CONSTEXPR (in VEC_INIT_EXPR)
    1: IDENTIFIER_VIRTUAL_P (in IDENTIFIER_NODE)
       TI_PENDING_TEMPLATE_FLAG.
       TEMPLATE_PARMS_FOR_INLINE.
@@ -2898,6 +2899,15 @@ more_aggr_init_expr_args_p (const aggr_init_expr_arg_iterator *iter)
 #define VEC_INIT_EXPR_SLOT(NODE) TREE_OPERAND (NODE, 0)
 #define VEC_INIT_EXPR_INIT(NODE) TREE_OPERAND (NODE, 1)
 
+/* Indicates that a VEC_INIT_EXPR is a potential constant expression.
+   Only set when the current function is constexpr.  */
+#define VEC_INIT_EXPR_IS_CONSTEXPR(NODE) \
+  TREE_LANG_FLAG_0 (VEC_INIT_EXPR_CHECK (NODE))
+
+/* Indicates that a VEC_INIT_EXPR is expressing value-initialization.  */
+#define VEC_INIT_EXPR_VALUE_INIT(NODE) \
+  TREE_LANG_FLAG_1 (VEC_INIT_EXPR_CHECK (NODE))
+
 /* The TYPE_MAIN_DECL for a class template type is a TYPE_DECL, not a
    TEMPLATE_DECL.  This macro determines whether or not a given class
    type is really a template type, as opposed to an instantiation or
@@ -5240,6 +5250,7 @@ extern bool literal_type_p (tree);
 extern tree validate_constexpr_fundecl (tree);
 extern tree register_constexpr_fundef (tree, tree);
 extern tree ensure_literal_type_for_constexpr_object (tree);
+extern bool potential_constant_expression (tree, tsubst_flags_t);
 extern tree cxx_constant_value (tree);
 extern tree maybe_constant_value (tree);
 extern tree maybe_constant_init (tree);
index ab834bf..0ecd61d 100644 (file)
@@ -453,10 +453,8 @@ perform_member_init (tree member, tree init)
       /* mem() means value-initialization.  */
       if (TREE_CODE (type) == ARRAY_TYPE)
        {
-         init = build_vec_init (decl, NULL_TREE, NULL_TREE,
-                                /*explicit_value_init_p=*/true,
-                                /* from_array=*/0,
-                                tf_warning_or_error);
+         init = build_vec_init_expr (type, init);
+         init = build2 (INIT_EXPR, type, decl, init);
          finish_expr_stmt (init);
        }
       else
index 558be88..fd7da34 100644 (file)
@@ -5324,8 +5324,6 @@ typedef struct GTY(()) constexpr_fundef {
 
 static GTY ((param_is (constexpr_fundef))) htab_t constexpr_fundef_table;
 
-static bool potential_constant_expression (tree, tsubst_flags_t);
-
 /* Utility function used for managing the constexpr function table.
    Return true if the entries pointed to by P and Q are for the
    same constexpr function.  */
@@ -7066,7 +7064,7 @@ morally_constexpr_builtin_function_p (tree decl)
       logical OR (5.15), and conditional (5.16) operations that are
       not evaluated are not considered.   */
 
-static bool
+bool
 potential_constant_expression (tree t, tsubst_flags_t flags)
 {
   int i;
@@ -7451,11 +7449,7 @@ potential_constant_expression (tree t, tsubst_flags_t flags)
       return false;
 
     case VEC_INIT_EXPR:
-      /* We should only see this in a defaulted constructor for a class
-        with a non-static data member of array type; if we get here we
-        know this is a potential constant expression.  */
-      gcc_assert (DECL_DEFAULTED_FN (current_function_decl));
-      return true;
+      return VEC_INIT_EXPR_IS_CONSTEXPR (t);
 
     default:
       sorry ("unexpected ast of kind %s", tree_code_name[TREE_CODE (t)]);
index d1d306e..5440e10 100644 (file)
@@ -462,34 +462,54 @@ build_vec_init_expr (tree type, tree init)
 {
   tree slot;
   tree inner_type = strip_array_types (type);
-
-  gcc_assert (init == NULL_TREE
-             || (same_type_ignoring_top_level_qualifiers_p
-                 (type, TREE_TYPE (init))));
+  tree elt_init = integer_zero_node;
+  bool value_init = false;
 
   /* Since we're deferring building the actual constructor calls until
      gimplification time, we need to build one now and throw it away so
      that the relevant constructor gets mark_used before cgraph decides
      what functions are needed.  Here we assume that init is either
-     NULL_TREE or another array to copy.  */
-  if (CLASS_TYPE_P (inner_type))
+     NULL_TREE, void_type_node (indicating value-initialization), or
+     another array to copy.  */
+  if (init == void_type_node)
     {
-      VEC(tree,gc) *argvec = make_tree_vector ();
-      if (init)
+      elt_init = build_value_init (inner_type, tf_warning_or_error);
+      value_init = true;
+      init = NULL_TREE;
+    }
+  else
+    {
+      gcc_assert (init == NULL_TREE
+                 || (same_type_ignoring_top_level_qualifiers_p
+                     (type, TREE_TYPE (init))));
+
+      if (CLASS_TYPE_P (inner_type))
        {
-         tree dummy = build_dummy_object (inner_type);
-         if (!real_lvalue_p (init))
-           dummy = move (dummy);
-         VEC_quick_push (tree, argvec, dummy);
+         VEC(tree,gc) *argvec = make_tree_vector ();
+         if (init)
+           {
+             tree dummy = build_dummy_object (inner_type);
+             if (!real_lvalue_p (init))
+               dummy = move (dummy);
+             VEC_quick_push (tree, argvec, dummy);
+           }
+         elt_init
+           = build_special_member_call (NULL_TREE, complete_ctor_identifier,
+                                        &argvec, inner_type, LOOKUP_NORMAL,
+                                        tf_warning_or_error);
        }
-      build_special_member_call (NULL_TREE, complete_ctor_identifier,
-                                &argvec, inner_type, LOOKUP_NORMAL,
-                                tf_warning_or_error);
     }
 
   slot = build_local_temp (type);
   init = build2 (VEC_INIT_EXPR, type, slot, init);
   SET_EXPR_LOCATION (init, input_location);
+
+  if (current_function_decl
+      && DECL_DECLARED_CONSTEXPR_P (current_function_decl)
+      && potential_constant_expression (elt_init, tf_warning_or_error))
+    VEC_INIT_EXPR_IS_CONSTEXPR (init) = true;
+  VEC_INIT_EXPR_VALUE_INIT (init) = value_init;
+
   init = build_target_expr (slot, init);
   TARGET_EXPR_IMPLICIT_P (init) = 1;
 
index 98a866b..c5ccdb8 100644 (file)
@@ -1,3 +1,7 @@
+2010-11-06  Jason Merrill  <jason@redhat.com>
+
+       * g++.dg/cpp0x/constexpr-ctor3.C: New.
+
 2010-11-06  Simon Martin  <simartin@users.sourceforge.net>
 
        PR c/43384
diff --git a/gcc/testsuite/g++.dg/cpp0x/constexpr-ctor3.C b/gcc/testsuite/g++.dg/cpp0x/constexpr-ctor3.C
new file mode 100644 (file)
index 0000000..50d4d85
--- /dev/null
@@ -0,0 +1,9 @@
+// { dg-options -std=c++0x }
+
+struct A
+{
+  int arr[1];
+
+  constexpr A()
+  : arr() { }
+};