Patchwork Fix ICE on conditional expression in Ada

login
register
mail settings
Submitter Eric Botcazou
Date July 3, 2010, 1:11 p.m.
Message ID <201007031511.13007.ebotcazou@adacore.com>
Download mbox | patch
Permalink /patch/57806/
State New
Headers show

Comments

Eric Botcazou - July 3, 2010, 1:11 p.m.
This new Ada 2012 feature is going to stretch the middle-end support for 
statement expressions because the front-end can insert arbitrarily complex 
statements within the arms of conditional expressions.

The attached testcase triggers an ICE in the tree unsharing phase because we 
have a BIND_EXPR under a SAVE_EXPR and we unshare subtrees of SAVE_EXPRs in 
Ada (deep unsharing).  Fixed by handling BIND_EXPR like SAVE_EXPR/TARGET_EXPR 
i.e stopping the unsharing instead of aborting, except with deep unsharing.

This doesn't change anything except for Ada.  Tested on i586-suse-linux and 
applied on the mainline as obvious.


2010-07-03  Eric Botcazou  <ebotcazou@adacore.com>

	* gimplify.c (mostly_copy_tree_r): Deal with BIND_EXPR.


2010-07-03  Eric Botcazou  <ebotcazou@adacore.com>

	* gnat.dg/cond_expr1.adb: New test.

Patch

Index: gimplify.c
===================================================================
--- gimplify.c	(revision 161767)
+++ gimplify.c	(working copy)
@@ -868,9 +868,9 @@  mostly_copy_tree_r (tree *tp, int *walk_
   tree t = *tp;
   enum tree_code code = TREE_CODE (t);
 
-  /* Do not copy SAVE_EXPR or TARGET_EXPR nodes themselves, but copy
-     their subtrees if we can make sure to do it only once.  */
-  if (code == SAVE_EXPR || code == TARGET_EXPR)
+  /* Do not copy SAVE_EXPR, TARGET_EXPR or BIND_EXPR nodes themselves, but
+     copy their subtrees if we can make sure to do it only once.  */
+  if (code == SAVE_EXPR || code == TARGET_EXPR || code == BIND_EXPR)
     {
       if (data && !pointer_set_insert ((struct pointer_set_t *)data, t))
 	;
@@ -895,10 +895,7 @@  mostly_copy_tree_r (tree *tp, int *walk_
 
   /* Leave the bulk of the work to copy_tree_r itself.  */
   else
-    {
-      gcc_assert (code != BIND_EXPR);
-      copy_tree_r (tp, walk_subtrees, NULL);
-    }
+    copy_tree_r (tp, walk_subtrees, NULL);
 
   return NULL_TREE;
 }