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]

[PATCH] Add UNARY_PLUS_EXPR to C++ front-end (take 2)


Many thanks to both Mark and Giovanni for suggesting that appropriate
fix was to fold the new UNARY_PLUS_EXPR in fold_if_not_in_template.
This indeed fixes the g++ regression.  I also took the opportunity
to go through and audit all of the uses of CONVERT_EXPR in the cp/
directory.  I believe I've now caught all the relevant cases and the
12 remaining uses of CONVERT_EXPR appear to treat it as a synonym
for NOP_EXPR.

The following revised patch has been tested on x86_64-unknown-linux-gnu
with a full "make bootstrap", all default languages, and regression
tested with a top-level "make -k check" with no new failures.

Ok for mainline?



2005-05-26  Roger Sayle  <roger@eyesopen.com>
	    Giovanni Bajo  <giovannibajo@gcc.gnu.org>

	* cp-tree.def (UNARY_PLUS_EXPR): New C++ unary tree code.
	* parser.c (cp_parser_unary_expression): Use UNARY_PLUS_EXPR instead
	of CONVERT_EXPR.
	(cp_parser_unary_expression): Likewise.
	* typeck.c (build_unary_op): Likewise.
	* call.c (add_builtin_candidate, build_new_op): Likewise.
	* error.c (dump_expr): Likewise.
	* pt.c (tsubst_copy, tsubst_copy_and_build): Likewise.
	* decl.c (ambi_op_p, grok_op_properties): Likewise.
	* dump.c (dump_op): Likewise.
	* lex.c (init_operators): Likewise.
	* operators.def ("+"): Likewise.
	* cp-gimplify.c (cp_gimplify_expr): Handle UNARY_PLUS_EXPR like a
	conversion, if the result and argument types differ.
	* tree.c (fold_if_not_in_template): Fold UNARY_PLUS_EXPR much
	like a NOP_EXPR when !processing_template_decl.


Index: cp-tree.def
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/cp-tree.def,v
retrieving revision 1.101
diff -c -3 -p -r1.101 cp-tree.def
*** cp-tree.def	25 Apr 2005 19:03:36 -0000	1.101
--- cp-tree.def	26 May 2005 21:33:12 -0000
*************** DEFTREECODE (ALIGNOF_EXPR, "alignof_expr
*** 340,345 ****
--- 340,349 ----
     STMT_EXPR_STMT is the statement given by the expression.  */
  DEFTREECODE (STMT_EXPR, "stmt_expr", tcc_expression, 1)

+ /* Unary plus. Operand 0 is the expression to which the unary plus
+    is applied.  */
+ DEFTREECODE (UNARY_PLUS_EXPR, "unary_plus_expr", tcc_unary, 1)
+
  /*
  Local variables:
  mode:c
Index: parser.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/parser.c,v
retrieving revision 1.333
diff -c -3 -p -r1.333 parser.c
*** parser.c	25 May 2005 04:17:38 -0000	1.333
--- parser.c	26 May 2005 21:33:16 -0000
*************** cp_parser_unary_expression (cp_parser *p
*** 4873,4879 ****
  	  non_constant_p = (unary_operator == PREINCREMENT_EXPR
  			    ? "`++'" : "`--'");
  	  /* Fall through.  */
! 	case CONVERT_EXPR:
  	case NEGATE_EXPR:
  	case TRUTH_NOT_EXPR:
  	  expression = finish_unary_op_expr (unary_operator, cast_expression);
--- 4873,4879 ----
  	  non_constant_p = (unary_operator == PREINCREMENT_EXPR
  			    ? "`++'" : "`--'");
  	  /* Fall through.  */
! 	case UNARY_PLUS_EXPR:
  	case NEGATE_EXPR:
  	case TRUTH_NOT_EXPR:
  	  expression = finish_unary_op_expr (unary_operator, cast_expression);
*************** cp_parser_unary_operator (cp_token* toke
*** 4909,4915 ****
        return ADDR_EXPR;

      case CPP_PLUS:
!       return CONVERT_EXPR;

      case CPP_MINUS:
        return NEGATE_EXPR;
--- 4909,4915 ----
        return ADDR_EXPR;

      case CPP_PLUS:
!       return UNARY_PLUS_EXPR;

      case CPP_MINUS:
        return NEGATE_EXPR;
Index: typeck.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/typeck.c,v
retrieving revision 1.629
diff -c -3 -p -r1.629 typeck.c
*** typeck.c	24 May 2005 22:22:33 -0000	1.629
--- typeck.c	26 May 2005 21:33:17 -0000
*************** build_unary_op (enum tree_code code, tre
*** 3692,3704 ****

    switch (code)
      {
!     /* CONVERT_EXPR stands for unary plus in this context.  */
!     case CONVERT_EXPR:
      case NEGATE_EXPR:
        {
  	int flags = WANT_ARITH | WANT_ENUM;
  	/* Unary plus (but not unary minus) is allowed on pointers.  */
! 	if (code == CONVERT_EXPR)
  	  flags |= WANT_POINTER;
  	arg = build_expr_type_conversion (flags, arg, true);
  	if (!arg)
--- 3692,3703 ----

    switch (code)
      {
!     case UNARY_PLUS_EXPR:
      case NEGATE_EXPR:
        {
  	int flags = WANT_ARITH | WANT_ENUM;
  	/* Unary plus (but not unary minus) is allowed on pointers.  */
! 	if (code == UNARY_PLUS_EXPR)
  	  flags |= WANT_POINTER;
  	arg = build_expr_type_conversion (flags, arg, true);
  	if (!arg)
Index: call.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/call.c,v
retrieving revision 1.535
diff -c -3 -p -r1.535 call.c
*** call.c	23 Apr 2005 21:28:47 -0000	1.535
--- call.c	26 May 2005 21:33:18 -0000
*************** add_builtin_candidate (struct z_candidat
*** 1652,1658 ****
  	     T       operator+(T);
  	     T       operator-(T);  */

!     case CONVERT_EXPR: /* unary + */
        if (TREE_CODE (type1) == POINTER_TYPE)
  	break;
      case NEGATE_EXPR:
--- 1652,1658 ----
  	     T       operator+(T);
  	     T       operator-(T);  */

!     case UNARY_PLUS_EXPR: /* unary + */
        if (TREE_CODE (type1) == POINTER_TYPE)
  	break;
      case NEGATE_EXPR:
*************** build_new_op (enum tree_code code, int f
*** 3848,3854 ****
      case TRUTH_ORIF_EXPR:
        return cp_build_binary_op (code, arg1, arg2);

!     case CONVERT_EXPR:
      case NEGATE_EXPR:
      case BIT_NOT_EXPR:
      case TRUTH_NOT_EXPR:
--- 3848,3854 ----
      case TRUTH_ORIF_EXPR:
        return cp_build_binary_op (code, arg1, arg2);

!     case UNARY_PLUS_EXPR:
      case NEGATE_EXPR:
      case BIT_NOT_EXPR:
      case TRUTH_NOT_EXPR:
Index: error.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/error.c,v
retrieving revision 1.280
diff -c -3 -p -r1.280 error.c
*** error.c	24 Mar 2005 07:20:33 -0000	1.280
--- error.c	26 May 2005 21:33:19 -0000
*************** dump_expr (tree t, int flags)
*** 1511,1517 ****
        pp_cxx_right_bracket (cxx_pp);
        break;

!     case CONVERT_EXPR:
        if (TREE_TYPE (t) && VOID_TYPE_P (TREE_TYPE (t)))
  	{
  	  pp_cxx_left_paren (cxx_pp);
--- 1511,1517 ----
        pp_cxx_right_bracket (cxx_pp);
        break;

!     case UNARY_PLUS_EXPR:
        if (TREE_TYPE (t) && VOID_TYPE_P (TREE_TYPE (t)))
  	{
  	  pp_cxx_left_paren (cxx_pp);
Index: pt.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/pt.c,v
retrieving revision 1.998
diff -c -3 -p -r1.998 pt.c
*** pt.c	24 May 2005 22:22:27 -0000	1.998
--- pt.c	26 May 2005 21:33:22 -0000
*************** tsubst_copy (tree t, tree args, tsubst_f
*** 7785,7791 ****
      case TRUTH_NOT_EXPR:
      case BIT_NOT_EXPR:
      case ADDR_EXPR:
!     case CONVERT_EXPR:      /* Unary + */
      case SIZEOF_EXPR:
      case ALIGNOF_EXPR:
      case ARROW_EXPR:
--- 7785,7791 ----
      case TRUTH_NOT_EXPR:
      case BIT_NOT_EXPR:
      case ADDR_EXPR:
!     case UNARY_PLUS_EXPR:      /* Unary + */
      case SIZEOF_EXPR:
      case ALIGNOF_EXPR:
      case ARROW_EXPR:
*************** tsubst_copy_and_build (tree t,
*** 8466,8472 ****
      case BIT_NOT_EXPR:
      case ABS_EXPR:
      case TRUTH_NOT_EXPR:
!     case CONVERT_EXPR:  /* Unary + */
      case REALPART_EXPR:
      case IMAGPART_EXPR:
        return build_x_unary_op (TREE_CODE (t), RECUR (TREE_OPERAND (t, 0)));
--- 8466,8472 ----
      case BIT_NOT_EXPR:
      case ABS_EXPR:
      case TRUTH_NOT_EXPR:
!     case UNARY_PLUS_EXPR:  /* Unary + */
      case REALPART_EXPR:
      case IMAGPART_EXPR:
        return build_x_unary_op (TREE_CODE (t), RECUR (TREE_OPERAND (t, 0)));
Index: decl.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/decl.c,v
retrieving revision 1.1398
diff -c -3 -p -r1.1398 decl.c
*** decl.c	25 May 2005 04:17:29 -0000	1.1398
--- decl.c	26 May 2005 21:33:24 -0000
*************** ambi_op_p (enum tree_code code)
*** 8586,8592 ****
  {
    return (code == INDIRECT_REF
  	  || code == ADDR_EXPR
! 	  || code == CONVERT_EXPR
  	  || code == NEGATE_EXPR
  	  || code == PREINCREMENT_EXPR
  	  || code == PREDECREMENT_EXPR);
--- 8586,8592 ----
  {
    return (code == INDIRECT_REF
  	  || code == ADDR_EXPR
! 	  || code == UNARY_PLUS_EXPR
  	  || code == NEGATE_EXPR
  	  || code == PREINCREMENT_EXPR
  	  || code == PREDECREMENT_EXPR);
*************** grok_op_properties (tree decl, int frien
*** 8806,8812 ****
  		  operator_code = BIT_AND_EXPR;
  		  break;

! 		case CONVERT_EXPR:
  		  operator_code = PLUS_EXPR;
  		  break;

--- 8806,8812 ----
  		  operator_code = BIT_AND_EXPR;
  		  break;

! 		case UNARY_PLUS_EXPR:
  		  operator_code = PLUS_EXPR;
  		  break;

Index: dump.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/dump.c,v
retrieving revision 1.84
diff -c -3 -p -r1.84 dump.c
*** dump.c	25 Apr 2005 19:03:40 -0000	1.84
--- dump.c	26 May 2005 21:33:24 -0000
*************** dump_op (dump_info_p di, tree t)
*** 65,71 ****
      case VEC_DELETE_EXPR:
        dump_string (di, "vecdelete");
        break;
!     case CONVERT_EXPR:
        dump_string (di, "pos");
        break;
      case NEGATE_EXPR:
--- 65,71 ----
      case VEC_DELETE_EXPR:
        dump_string (di, "vecdelete");
        break;
!     case UNARY_PLUS_EXPR:
        dump_string (di, "pos");
        break;
      case NEGATE_EXPR:
Index: cp-gimplify.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/cp-gimplify.c,v
retrieving revision 1.19
diff -c -3 -p -r1.19 cp-gimplify.c
*** cp-gimplify.c	25 Apr 2005 19:03:36 -0000	1.19
--- cp-gimplify.c	26 May 2005 21:33:24 -0000
*************** cp_gimplify_expr (tree *expr_p, tree *pr
*** 557,562 ****
--- 557,572 ----
        ret = GS_OK;
        break;

+     case UNARY_PLUS_EXPR:
+       {
+ 	tree arg = TREE_OPERAND (*expr_p, 0);
+ 	tree type = TREE_TYPE (*expr_p);
+ 	*expr_p = (TREE_TYPE (arg) != type) ? fold_convert (type, arg)
+ 					    : arg;
+ 	ret = GS_OK;
+       }
+       break;
+
      default:
        ret = c_gimplify_expr (expr_p, pre_p, post_p);
        break;
Index: tree.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/tree.c,v
retrieving revision 1.434
diff -c -3 -p -r1.434 tree.c
*** tree.c	25 May 2005 04:17:45 -0000	1.434
--- tree.c	26 May 2005 21:33:24 -0000
*************** fold_if_not_in_template (tree expr)
*** 2268,2274 ****
       "fold".  We will call fold later when actually instantiating the
       template.  Integral constant expressions in templates will be
       evaluated via fold_non_dependent_expr, as necessary.  */
!   return (processing_template_decl ? expr : fold (expr));
  }


--- 2268,2281 ----
       "fold".  We will call fold later when actually instantiating the
       template.  Integral constant expressions in templates will be
       evaluated via fold_non_dependent_expr, as necessary.  */
!   if (processing_template_decl)
!     return expr;
!
!   /* Fold C++ front-end specific tree codes.  */
!   if (TREE_CODE (expr) == UNARY_PLUS_EXPR)
!     return fold_convert (TREE_TYPE (expr), TREE_OPERAND (expr, 0));
!
!   return fold (expr);
  }


Index: lex.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/lex.c,v
retrieving revision 1.359
diff -c -3 -p -r1.359 lex.c
*** lex.c	17 May 2005 20:05:11 -0000	1.359
--- lex.c	26 May 2005 21:33:25 -0000
*************** init_operators (void)
*** 145,151 ****
    operator_name_info [(int) TRUTH_AND_EXPR].name = "strict &&";
    operator_name_info [(int) TRUTH_OR_EXPR].name = "strict ||";
    operator_name_info [(int) RANGE_EXPR].name = "...";
!   operator_name_info [(int) CONVERT_EXPR].name = "+";

    assignment_operator_name_info [(int) EXACT_DIV_EXPR].name
      = "(exact /=)";
--- 145,151 ----
    operator_name_info [(int) TRUTH_AND_EXPR].name = "strict &&";
    operator_name_info [(int) TRUTH_OR_EXPR].name = "strict ||";
    operator_name_info [(int) RANGE_EXPR].name = "...";
!   operator_name_info [(int) UNARY_PLUS_EXPR].name = "+";

    assignment_operator_name_info [(int) EXACT_DIV_EXPR].name
      = "(exact /=)";
Index: operators.def
===================================================================
RCS file: /cvs/gcc/gcc/gcc/cp/operators.def,v
retrieving revision 1.15
diff -c -3 -p -r1.15 operators.def
*** operators.def	11 Jul 2003 23:01:53 -0000	1.15
--- operators.def	26 May 2005 21:33:25 -0000
*************** DEF_SIMPLE_OPERATOR ("delete", DELETE_EX
*** 84,90 ****
  DEF_SIMPLE_OPERATOR ("delete []", VEC_DELETE_EXPR, "da", -1)

  /* Unary operators.  */
! DEF_SIMPLE_OPERATOR ("+", CONVERT_EXPR, "ps", 1)
  DEF_SIMPLE_OPERATOR ("-", NEGATE_EXPR, "ng", 1)
  DEF_SIMPLE_OPERATOR ("&", ADDR_EXPR, "ad", 1)
  DEF_SIMPLE_OPERATOR ("*", INDIRECT_REF, "de", 1)
--- 84,90 ----
  DEF_SIMPLE_OPERATOR ("delete []", VEC_DELETE_EXPR, "da", -1)

  /* Unary operators.  */
! DEF_SIMPLE_OPERATOR ("+", UNARY_PLUS_EXPR, "ps", 1)
  DEF_SIMPLE_OPERATOR ("-", NEGATE_EXPR, "ng", 1)
  DEF_SIMPLE_OPERATOR ("&", ADDR_EXPR, "ad", 1)
  DEF_SIMPLE_OPERATOR ("*", INDIRECT_REF, "de", 1)


Roger
--
Roger Sayle,                         E-mail: roger@eyesopen.com
OpenEye Scientific Software,         WWW: http://www.eyesopen.com/
Suite 1107, 3600 Cerrillos Road,     Tel: (+1) 505-473-7385
Santa Fe, New Mexico, 87507.         Fax: (+1) 505-473-0833


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