[LTO][PATCH] Workround for ipcp ltrans clones issue

Simon Baldwin simonb@google.com
Thu Feb 19 19:33:00 GMT 2009


This patch addresses (somewhat inelegantly, for the moment) the issue described
in http://gcc.gnu.org/ml/gcc/2009-02/msg00297.html.  It removes nodes from
consideration for ipcp cloning if they have a clone caller.


gcc/ChangeLog.lto
2009-02-19  Simon Baldwin  <simonb@google.com>

	* cgraph.h (cgraph_is_clone_node): New function declaration.
	* cgraph.c (cgraph_is_clone_node): Definition.
	* ipa-cp.c (ipcp_ltrans_cloning_candidate_p): New function,
	applies extra candidate check for ltrans.
	(ipcp_cloning_candidate_p): Call it.

gcc/testsuite/ChangeLog.lto
2009-02-19  Simon Baldwin  <simonb@google.com>

	* gcc.dg/lto/20090219_0.c: New.


Index: gcc/cgraph.c
===================================================================
--- gcc/cgraph.c	(revision 144301)
+++ gcc/cgraph.c	(working copy)
@@ -1422,6 +1422,13 @@ cgraph_clone_input_node (struct cgraph_n
   return new_node;
 }
 
+/* Return true if N is a cloned node.  */
+
+bool
+cgraph_is_clone_node (struct cgraph_node *n)
+{
+  return n->next_clone || n->prev_clone;
+}
 
 /* Return true if N is an master_clone, (see cgraph_master_clone).  */
 
Index: gcc/cgraph.h
===================================================================
--- gcc/cgraph.h	(revision 144301)
+++ gcc/cgraph.h	(working copy)
@@ -407,6 +407,7 @@ bool cgraph_function_possibly_inlined_p 
 void cgraph_unnest_node (struct cgraph_node *);
 
 enum availability cgraph_function_body_availability (struct cgraph_node *);
+bool cgraph_is_clone_node (struct cgraph_node *);
 bool cgraph_is_master_clone (struct cgraph_node *, bool);
 struct cgraph_node *cgraph_master_clone (struct cgraph_node *, bool);
 void cgraph_add_new_function (tree, bool);
Index: gcc/ipa-cp.c
===================================================================
--- gcc/ipa-cp.c	(revision 144301)
+++ gcc/ipa-cp.c	(working copy)
@@ -379,6 +379,32 @@ ipcp_print_all_lattices (FILE * f)
     }
 }
 
+/* Return true if this NODE may be cloned in ltrans.
+
+   FIXME: returns false if any caller of NODE is a clone, reason described
+   in http://gcc.gnu.org/ml/gcc/2009-02/msg00297.html; this extra check
+   should be deleted if the underlying issue is resolved.  */
+static bool
+ipcp_ltrans_cloning_candidate_p (struct cgraph_node *node)
+{
+  struct cgraph_edge *e;
+
+  /* Check callers of this node to see if any is a clone.  */
+  for (e = node->callers; e; e = e->next_caller)
+    {
+      if (cgraph_is_clone_node (e->caller))
+	break;
+    }
+  if (e)
+    {
+      if (dump_file)
+        fprintf (dump_file, "Not considering %s for cloning; has a clone caller.\n",
+ 	         cgraph_node_name (node));
+      return false;
+    }
+  return true;
+}
+
 /* Return true if this NODE is viable candidate for cloning.  */
 static bool
 ipcp_cloning_candidate_p (struct cgraph_node *node)
@@ -395,6 +421,11 @@ ipcp_cloning_candidate_p (struct cgraph_
   if (!node->needed || !node->analyzed)
     return false;
 
+  /* If reading ltrans, we want an extra check here.
+     FIXME: see ipcp_ltrans_cloning_candidate_p above for details.  */
+  if (flag_ltrans && !ipcp_ltrans_cloning_candidate_p (node))
+    return false;
+
   if (cgraph_function_body_availability (node) <= AVAIL_OVERWRITABLE)
     {
       if (dump_file)
Index: gcc/testsuite/gcc.dg/lto/20090219_0.c
===================================================================
--- gcc/testsuite/gcc.dg/lto/20090219_0.c	(revision 0)
+++ gcc/testsuite/gcc.dg/lto/20090219_0.c	(revision 0)
@@ -0,0 +1,28 @@
+/* { dg-do link } */
+/* { dg-options "{-O3 -fwhopr -shared}" } */
+
+struct Foo { int f1, f2, f3, f4, f5; };
+
+int x = 0;
+struct Foo *foo;
+
+inline void Bar(int n){
+  foo[x].f1 = 0;
+  foo[x].f2 = 0;
+  foo[x].f3 = 0;
+  foo[x].f4 = 0;
+  foo[x].f5 = n;
+}
+
+int ei[1];
+inline void Baz(int n) {
+  if (ei[n] == 1)
+    Bar (0);
+  else if (ei[n] == 0)
+    Bar (1);
+}
+
+void mumble(void) {
+  for (;;)
+    Baz (0);
+}



More information about the Gcc-patches mailing list