OSDN Git Service

Remove cast-as-lvalue extension.
authormmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 4 Sep 2003 07:16:43 +0000 (07:16 +0000)
committermmitchel <mmitchel@138bc75d-0d04-0410-961f-82ee72b054a4>
Thu, 4 Sep 2003 07:16:43 +0000 (07:16 +0000)
* call.c (build_conditional_expr): Correct formatting.
(convert_like_real): Use lvalue_p, not non_cast_lvalue_p.
(initialize_real): Use real_lvalue_p, not real_non_cast_lvalue_p.
* cp-tree.h (non_cast_lvalue_p): Remove.
(real_non_cast_lvalue_p): Remove.
(non_cast_lvalue_or_else): Remove.
* tree.c (lvalue_p_1): Remove allow_cast_as_lvalue parameter.
(real_lvalue_p): Adjust call to lvalue_p_1.
(non_cast_lvalue_p): Remove.
(non_cast_lvalue_or_else): Remove.
(lvalue_p): Adjust call to lvalue_p_1.
(lvalue_or_else): Simplify.
* typeck.c (build_unary_op): Use lvalue_or_else, not
non_cast_lvalue_or_else.
(build_static_cast): Use real_lvalue_p, not real_non_cast_lvalue_p.

* doc/extend.texi: Document removal of cast-as-lvalue extension in
C++.

* g++.dg/expr/lval1.C: New test.
* g++.dg/ext/lvcast.C: Remove.

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

gcc/ChangeLog
gcc/cp/ChangeLog
gcc/cp/call.c
gcc/cp/cp-tree.h
gcc/cp/tree.c
gcc/cp/typeck.c
gcc/doc/extend.texi
gcc/testsuite/ChangeLog
gcc/testsuite/g++.dg/expr/lval1.C [new file with mode: 0644]
gcc/testsuite/g++.dg/ext/lvcast.C [deleted file]

index acbd799..f078ad4 100644 (file)
@@ -1,3 +1,8 @@
+2003-09-04  Mark Mitchell  <mark@codesourcery.com>
+
+       * doc/extend.texi: Document removal of cast-as-lvalue extension in
+       C++.
+
 2003-09-04  Nicolas Roche  <roche@act-europe.fr>
 
        * gcc.c (process_command): Fix typo.
 2003-09-04  Nicolas Roche  <roche@act-europe.fr>
 
        * gcc.c (process_command): Fix typo.
index dafa9c5..50fe265 100644 (file)
@@ -1,3 +1,22 @@
+2003-09-04  Mark Mitchell  <mark@codesourcery.com>
+
+       Remove cast-as-lvalue extension.
+       * call.c (build_conditional_expr): Correct formatting.
+       (convert_like_real): Use lvalue_p, not non_cast_lvalue_p.
+       (initialize_real): Use real_lvalue_p, not real_non_cast_lvalue_p.
+       * cp-tree.h (non_cast_lvalue_p): Remove.
+       (real_non_cast_lvalue_p): Remove.
+       (non_cast_lvalue_or_else): Remove.
+       * tree.c (lvalue_p_1): Remove allow_cast_as_lvalue parameter.
+       (real_lvalue_p): Adjust call to lvalue_p_1.
+       (non_cast_lvalue_p): Remove.
+       (non_cast_lvalue_or_else): Remove.
+       (lvalue_p): Adjust call to lvalue_p_1.
+       (lvalue_or_else): Simplify.
+       * typeck.c (build_unary_op): Use lvalue_or_else, not
+       non_cast_lvalue_or_else.
+       (build_static_cast): Use real_lvalue_p, not real_non_cast_lvalue_p.
+
 2003-09-03  DJ Delorie  <dj@redhat.com>
 
        * decl.c (finish_function): Pass fndecl to aggregate_value_p.
 2003-09-03  DJ Delorie  <dj@redhat.com>
 
        * decl.c (finish_function): Pass fndecl to aggregate_value_p.
index 9e46282..35a8226 100644 (file)
@@ -3193,8 +3193,9 @@ build_conditional_expr (tree arg1, tree arg2, tree arg3)
 
      If the second and third operands are lvalues and have the same
      type, the result is of that type and is an lvalue.  */
 
      If the second and third operands are lvalues and have the same
      type, the result is of that type and is an lvalue.  */
-  if (real_lvalue_p (arg2) && real_lvalue_p (arg3) && 
-      same_type_p (arg2_type, arg3_type))
+  if (real_lvalue_p (arg2) 
+      && real_lvalue_p (arg3) 
+      && same_type_p (arg2_type, arg3_type))
     {
       result_type = arg2_type;
       goto valid_operands;
     {
       result_type = arg2_type;
       goto valid_operands;
@@ -4126,7 +4127,7 @@ convert_like_real (tree convs, tree expr, tree fn, int argnum, int inner,
        tree ref_type = totype;
 
        /* If necessary, create a temporary.  */
        tree ref_type = totype;
 
        /* If necessary, create a temporary.  */
-       if (NEED_TEMPORARY_P (convs) || !non_cast_lvalue_p (expr))
+       if (NEED_TEMPORARY_P (convs) || !lvalue_p (expr))
          {
            tree type = TREE_TYPE (TREE_OPERAND (convs, 0));
 
          {
            tree type = TREE_TYPE (TREE_OPERAND (convs, 0));
 
@@ -6089,7 +6090,7 @@ initialize_reference (tree type, tree expr, tree decl, tree *cleanup)
        base_conv_type = NULL_TREE;
       /* Perform the remainder of the conversion.  */
       expr = convert_like (conv, expr);
        base_conv_type = NULL_TREE;
       /* Perform the remainder of the conversion.  */
       expr = convert_like (conv, expr);
-      if (!real_non_cast_lvalue_p (expr))
+      if (!real_lvalue_p (expr))
        {
          tree init;
          tree type;
        {
          tree init;
          tree type;
index cf4b8ce..50228e2 100644 (file)
@@ -4167,10 +4167,7 @@ extern int zero_init_p                           (tree);
 extern tree canonical_type_variant              (tree);
 extern tree copy_base_binfos                   (tree, tree, tree);
 extern int member_p                            (tree);
 extern tree canonical_type_variant              (tree);
 extern tree copy_base_binfos                   (tree, tree, tree);
 extern int member_p                            (tree);
-extern cp_lvalue_kind real_lvalue_p            (tree);
-extern int non_cast_lvalue_p                   (tree);
-extern cp_lvalue_kind real_non_cast_lvalue_p    (tree);
-extern int non_cast_lvalue_or_else             (tree, const char *);
+extern cp_lvalue_kind real_lvalue_p             (tree);
 extern tree build_min                          (enum tree_code, tree,
                                                         ...);
 extern tree build_min_nt                       (enum tree_code, ...);
 extern tree build_min                          (enum tree_code, tree,
                                                         ...);
 extern tree build_min_nt                       (enum tree_code, ...);
index 532d8b9..71742a7 100644 (file)
@@ -41,7 +41,7 @@ static tree build_cplus_array_type_1 (tree, tree);
 static int list_hash_eq (const void *, const void *);
 static hashval_t list_hash_pieces (tree, tree, tree);
 static hashval_t list_hash (const void *);
 static int list_hash_eq (const void *, const void *);
 static hashval_t list_hash_pieces (tree, tree, tree);
 static hashval_t list_hash (const void *);
-static cp_lvalue_kind lvalue_p_1 (tree, int, int);
+static cp_lvalue_kind lvalue_p_1 (tree, int);
 static tree no_linkage_helper (tree *, int *, void *);
 static tree mark_local_for_remap_r (tree *, int *, void *);
 static tree cp_unsave_r (tree *, int *, void *);
 static tree no_linkage_helper (tree *, int *, void *);
 static tree mark_local_for_remap_r (tree *, int *, void *);
 static tree cp_unsave_r (tree *, int *, void *);
@@ -60,8 +60,7 @@ static tree handle_init_priority_attribute (tree *, tree, tree, int, bool *);
 
 static cp_lvalue_kind
 lvalue_p_1 (tree ref, 
 
 static cp_lvalue_kind
 lvalue_p_1 (tree ref, 
-            int treat_class_rvalues_as_lvalues, 
-            int allow_cast_as_lvalue)
+            int treat_class_rvalues_as_lvalues)
 {
   cp_lvalue_kind op1_lvalue_kind = clk_none;
   cp_lvalue_kind op2_lvalue_kind = clk_none;
 {
   cp_lvalue_kind op1_lvalue_kind = clk_none;
   cp_lvalue_kind op2_lvalue_kind = clk_none;
@@ -85,21 +84,11 @@ lvalue_p_1 (tree ref,
     case REALPART_EXPR:
     case IMAGPART_EXPR:
       return lvalue_p_1 (TREE_OPERAND (ref, 0),
     case REALPART_EXPR:
     case IMAGPART_EXPR:
       return lvalue_p_1 (TREE_OPERAND (ref, 0),
-                        treat_class_rvalues_as_lvalues,
-                        allow_cast_as_lvalue);
-
-    case NOP_EXPR:
-      if (allow_cast_as_lvalue)
-       return lvalue_p_1 (TREE_OPERAND (ref, 0),
-                          treat_class_rvalues_as_lvalues,
-                          allow_cast_as_lvalue);
-      else
-       return clk_none;
+                        treat_class_rvalues_as_lvalues);
 
     case COMPONENT_REF:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 0),
 
     case COMPONENT_REF:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 0),
-                                   treat_class_rvalues_as_lvalues,
-                                   allow_cast_as_lvalue);
+                                   treat_class_rvalues_as_lvalues);
       if (!op1_lvalue_kind 
          /* The "field" can be a FUNCTION_DECL or an OVERLOAD in some  
             situations.  */
       if (!op1_lvalue_kind 
          /* The "field" can be a FUNCTION_DECL or an OVERLOAD in some  
             situations.  */
@@ -140,20 +129,16 @@ lvalue_p_1 (tree ref,
     case MAX_EXPR:
     case MIN_EXPR:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 0),
     case MAX_EXPR:
     case MIN_EXPR:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 0),
-                                   treat_class_rvalues_as_lvalues,
-                                   allow_cast_as_lvalue);
+                                   treat_class_rvalues_as_lvalues);
       op2_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 1),
       op2_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 1),
-                                   treat_class_rvalues_as_lvalues,
-                                   allow_cast_as_lvalue);
+                                   treat_class_rvalues_as_lvalues);
       break;
 
     case COND_EXPR:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 1),
       break;
 
     case COND_EXPR:
       op1_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 1),
-                                   treat_class_rvalues_as_lvalues,
-                                   allow_cast_as_lvalue);
+                                   treat_class_rvalues_as_lvalues);
       op2_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 2),
       op2_lvalue_kind = lvalue_p_1 (TREE_OPERAND (ref, 2),
-                                   treat_class_rvalues_as_lvalues,
-                                   allow_cast_as_lvalue);
+                                   treat_class_rvalues_as_lvalues);
       break;
 
     case MODIFY_EXPR:
       break;
 
     case MODIFY_EXPR:
@@ -161,8 +146,7 @@ lvalue_p_1 (tree ref,
 
     case COMPOUND_EXPR:
       return lvalue_p_1 (TREE_OPERAND (ref, 1),
 
     case COMPOUND_EXPR:
       return lvalue_p_1 (TREE_OPERAND (ref, 1),
-                        treat_class_rvalues_as_lvalues,
-                        allow_cast_as_lvalue);
+                        treat_class_rvalues_as_lvalues);
 
     case TARGET_EXPR:
       return treat_class_rvalues_as_lvalues ? clk_class : clk_none;
 
     case TARGET_EXPR:
       return treat_class_rvalues_as_lvalues ? clk_class : clk_none;
@@ -205,27 +189,15 @@ lvalue_p_1 (tree ref,
   return op1_lvalue_kind;
 }
 
   return op1_lvalue_kind;
 }
 
-/* If REF is an lvalue, returns the kind of lvalue that REF is.
-   Otherwise, returns clk_none.  Lvalues can be assigned, unless they
-   have TREE_READONLY, or unless they are FUNCTION_DECLs.  Lvalues can
-   have their address taken, unless they have DECL_REGISTER.  */
-
-cp_lvalue_kind
-real_lvalue_p (tree ref)
-{
-  return lvalue_p_1 (ref, /*treat_class_rvalues_as_lvalues=*/ 0, /*cast*/ 1);
-}
-
 /* Returns the kind of lvalue that REF is, in the sense of
    [basic.lval].  This function should really be named lvalue_p; it
    computes the C++ definition of lvalue.  */
 
 cp_lvalue_kind
 /* Returns the kind of lvalue that REF is, in the sense of
    [basic.lval].  This function should really be named lvalue_p; it
    computes the C++ definition of lvalue.  */
 
 cp_lvalue_kind
-real_non_cast_lvalue_p (tree ref)
+real_lvalue_p (tree ref)
 {
   return lvalue_p_1 (ref, 
 {
   return lvalue_p_1 (ref, 
-                    /*treat_class_rvalues_as_lvalues=*/0, 
-                    /*allow_cast_as_lvalue=*/0);
+                    /*treat_class_rvalues_as_lvalues=*/0);
 }
 
 /* This differs from real_lvalue_p in that class rvalues are
 }
 
 /* This differs from real_lvalue_p in that class rvalues are
@@ -235,14 +207,7 @@ int
 lvalue_p (tree ref)
 {
   return 
 lvalue_p (tree ref)
 {
   return 
-    (lvalue_p_1 (ref, /*class rvalue ok*/ 1, /*cast*/ 1) != clk_none);
-}
-
-int
-non_cast_lvalue_p (tree ref)
-{
-  return 
-    (lvalue_p_1 (ref, /*class rvalue ok*/ 1, /*cast*/ 0) != clk_none);
+    (lvalue_p_1 (ref, /*class rvalue ok*/ 1) != clk_none);
 }
 
 /* Return nonzero if REF is an lvalue valid for this language;
 }
 
 /* Return nonzero if REF is an lvalue valid for this language;
@@ -251,21 +216,12 @@ non_cast_lvalue_p (tree ref)
 int
 lvalue_or_else (tree ref, const char* string)
 {
 int
 lvalue_or_else (tree ref, const char* string)
 {
-  int ret = lvalue_p_1 (ref, /* class rvalue ok */ 1, /* cast ok */ 1);
-  int win = (ret != clk_none);
-  if (! win)
-    error ("non-lvalue in %s", string);
-  return win;
-}
-
-int
-non_cast_lvalue_or_else (tree ref, const char* string)
-{
-  int ret = lvalue_p_1 (ref, /* class rvalue ok */ 1, /* cast ok */ 0);
-  int win = (ret != clk_none);
-  if (! win)
-    error ("non-lvalue in %s", string);
-  return win;
+  if (!lvalue_p (ref))
+    {
+      error ("non-lvalue in %s", string);
+      return 0;
+    }
+  return 1;
 }
 
 /* Build a TARGET_EXPR, initializing the DECL with the VALUE.  */
 }
 
 /* Build a TARGET_EXPR, initializing the DECL with the VALUE.  */
index 564b337..2a21a00 100644 (file)
@@ -3967,7 +3967,7 @@ build_unary_op (enum tree_code code, tree xarg, int noconvert)
         is an error.  */
       else if (TREE_CODE (argtype) != FUNCTION_TYPE
               && TREE_CODE (argtype) != METHOD_TYPE
         is an error.  */
       else if (TREE_CODE (argtype) != FUNCTION_TYPE
               && TREE_CODE (argtype) != METHOD_TYPE
-              && !non_cast_lvalue_or_else (arg, "unary `&'"))
+              && !lvalue_or_else (arg, "unary `&'"))
        return error_mark_node;
 
       if (argtype != error_mark_node)
        return error_mark_node;
 
       if (argtype != error_mark_node)
@@ -4391,7 +4391,7 @@ build_static_cast (tree type, tree expr)
   if (TREE_CODE (type) == REFERENCE_TYPE
       && CLASS_TYPE_P (TREE_TYPE (type))
       && CLASS_TYPE_P (intype)
   if (TREE_CODE (type) == REFERENCE_TYPE
       && CLASS_TYPE_P (TREE_TYPE (type))
       && CLASS_TYPE_P (intype)
-      && real_non_cast_lvalue_p (expr)
+      && real_lvalue_p (expr)
       && DERIVED_FROM_P (intype, TREE_TYPE (type))
       && can_convert (build_pointer_type (TYPE_MAIN_VARIANT (intype)),
                      build_pointer_type (TYPE_MAIN_VARIANT 
       && DERIVED_FROM_P (intype, TREE_TYPE (type))
       && can_convert (build_pointer_type (TYPE_MAIN_VARIANT (intype)),
                      build_pointer_type (TYPE_MAIN_VARIANT 
index 0edf2cf..6664e1c 100644 (file)
@@ -1071,9 +1071,9 @@ Compound expressions, conditional expressions and casts are allowed as
 lvalues provided their operands are lvalues.  This means that you can take
 their addresses or store values into them.
 
 lvalues provided their operands are lvalues.  This means that you can take
 their addresses or store values into them.
 
-Standard C++ allows compound expressions and conditional expressions as
-lvalues, and permits casts to reference type, so use of this extension
-is deprecated for C++ code.
+Standard C++ allows compound expressions and conditional expressions
+as lvalues, and permits casts to reference type, so use of this
+extension is not supported for C++ code.
 
 For example, a compound expression can be assigned, provided the last
 expression in the sequence is an lvalue.  These two expressions are
 
 For example, a compound expression can be assigned, provided the last
 expression in the sequence is an lvalue.  These two expressions are
index d417f83..562ed09 100644 (file)
@@ -1,3 +1,8 @@
+2003-09-04  Mark Mitchell  <mark@codesourcery.com>
+
+       * g++.dg/expr/lval1.C: New test.
+       * g++.dg/ext/lvcast.C: Remove.
+
 2003-09-03  Roger Sayle  <roger@eyesopen.com>
 
        PR optimization/11700.
 2003-09-03  Roger Sayle  <roger@eyesopen.com>
 
        PR optimization/11700.
diff --git a/gcc/testsuite/g++.dg/expr/lval1.C b/gcc/testsuite/g++.dg/expr/lval1.C
new file mode 100644 (file)
index 0000000..bed47d8
--- /dev/null
@@ -0,0 +1,7 @@
+// Contributed by Matt Austern <austern@apple.com>
+
+void f ()
+{
+  int n;
+  (char) n = 1; // { dg-error "" }
+}
diff --git a/gcc/testsuite/g++.dg/ext/lvcast.C b/gcc/testsuite/g++.dg/ext/lvcast.C
deleted file mode 100644 (file)
index efff04e..0000000
+++ /dev/null
@@ -1,11 +0,0 @@
-// Copyright (C) 2002 Free Software Foundation
-// Contributed by Matt Austern <austern@apple.com>
-
-// { dg-do compile }
-// { dg-options -fpermissive }
-
-void f ()
-{
-  int n;
-  (char) n = 1;
-}