diff mbox

PR ipa/59831 (ipa-cp devirt issues)

Message ID 20140204172723.GH9877@kam.mff.cuni.cz
State New
Headers show

Commit Message

Jan Hubicka Feb. 4, 2014, 5:27 p.m. UTC
Hi,
I went ahead and comitted Markus' patch. I updated the testcase to use hidden visibility.
With default visibility the gimple-fold change will enable devirtualization.

Honza
diff mbox

Patch

Index: ChangeLog
===================================================================
--- ChangeLog	(revision 207477)
+++ ChangeLog	(working copy)
@@ -1,3 +1,9 @@ 
+2014-02-04  Markus Trippelsdorf  <markus@trippelsdorf.de>
+
+	PR ipa/60058
+	* ipa-cp.c (ipa_get_indirect_edge_target_1): Check that target
+	is non-null.
+
 2014-02-04  Jan Hubicka  <hubicka@ucw.cz>
 
 	* gimple-fold.c (can_refer_decl_in_current_unit_p): Default visibility is safe.
Index: ipa-cp.c
===================================================================
--- ipa-cp.c	(revision 207451)
+++ ipa-cp.c	(working copy)
@@ -1573,20 +1573,23 @@  ipa_get_indirect_edge_target_1 (struct c
 	{
 	  target = gimple_get_virt_method_for_vtable (ie->indirect_info->otr_token,
 						      vtable, offset);
-	  if ((TREE_CODE (TREE_TYPE (target)) == FUNCTION_TYPE
-	       && DECL_FUNCTION_CODE (target) == BUILT_IN_UNREACHABLE)
-	      || !possible_polymorphic_call_target_p
-		   (ie, cgraph_get_node (target)))
+	  if (target)
 	    {
-	      if (dump_file)
-		fprintf (dump_file,
-			 "Type inconsident devirtualization: %s/%i->%s\n",
-			 ie->caller->name (), ie->caller->order,
-			 IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (target)));
-	      target = builtin_decl_implicit (BUILT_IN_UNREACHABLE);
-	      cgraph_get_create_node (target);
+	      if ((TREE_CODE (TREE_TYPE (target)) == FUNCTION_TYPE
+		   && DECL_FUNCTION_CODE (target) == BUILT_IN_UNREACHABLE)
+		  || !possible_polymorphic_call_target_p
+		       (ie, cgraph_get_node (target)))
+		{
+		  if (dump_file)
+		    fprintf (dump_file,
+			     "Type inconsident devirtualization: %s/%i->%s\n",
+			     ie->caller->name (), ie->caller->order,
+			     IDENTIFIER_POINTER (DECL_ASSEMBLER_NAME (target)));
+		  target = builtin_decl_implicit (BUILT_IN_UNREACHABLE);
+		  cgraph_get_create_node (target);
+		}
+	      return target;
 	    }
-	  return target;
 	}
     }
 
Index: testsuite/ChangeLog
===================================================================
--- testsuite/ChangeLog	(revision 207451)
+++ testsuite/ChangeLog	(working copy)
@@ -1,3 +1,8 @@ 
+2014-02-04  Markus Trippelsdorf  <markus@trippelsdorf.de>
+
+	PR ipa/60058
+	* g++.dg/torture/pr60058.C: New testcase.
+
 2014-02-03  Jan Hubicka  <hubicka@ucw.cz>
 
 	PR ipa/59882
Index: testsuite/g++.dg/torture/pr60058.C
===================================================================
--- testsuite/g++.dg/torture/pr60058.C	(revision 0)
+++ testsuite/g++.dg/torture/pr60058.C	(revision 0)
@@ -0,0 +1,30 @@ 
+/* { dg-do compile } */
+/* { dg-require-visibility "" } */
+
+typedef enum {} UErrorCode;
+class A {
+public:
+  virtual A &m_fn1(A &, const A &, UErrorCode &) const;
+  void m_fn2();
+  A();
+  A(int);
+};
+class __attribute__((visibility("hidden"))) B : public A {
+public:
+  B(A &p1) : norm2(p1), set(0) {}
+  A &m_fn1(A &, const A &, UErrorCode &) const;
+  A &norm2;
+  const int &set;
+};
+
+UErrorCode a;
+A c;
+void fn1(A *p1) {
+  A b;
+  p1->m_fn1(b, 0, a).m_fn2();
+}
+
+void fn2() {
+  B d(c);
+  fn1(&d);
+}