aboutsummaryrefslogtreecommitdiff
path: root/gcc
diff options
context:
space:
mode:
authorJan Hubicka <hubicka@ucw.cz>2015-01-12 10:24:18 +0100
committerJan Hubicka <hubicka@gcc.gnu.org>2015-01-12 09:24:18 +0000
commitd8d5aef10080e5c96414ba48fa31e41e823a95f7 (patch)
tree993913a7158e643f48bf7e882b92891566a2049e /gcc
parent0d2dd460fe627cf460536b80b99f56682775fe78 (diff)
downloadgcc-d8d5aef10080e5c96414ba48fa31e41e823a95f7.zip
gcc-d8d5aef10080e5c96414ba48fa31e41e823a95f7.tar.gz
gcc-d8d5aef10080e5c96414ba48fa31e41e823a95f7.tar.bz2
re PR ipa/63470 (internal compiler error: in estimate_edge_growth, at ipa-inline.h:308)
PR ipa/63470 * ipa-inline-analysis.c (inline_edge_duplication_hook): Adjust cost when edge becomes direct. * ipa-prop.c (make_edge_direct): Do not adjust when speculation is resolved or when introducing new speculation. * testsuite/g++.dg/ipa/pr63470.C: New testcase. From-SVN: r219451
Diffstat (limited to 'gcc')
-rw-r--r--gcc/ChangeLog8
-rw-r--r--gcc/ipa-inline-analysis.c7
-rw-r--r--gcc/ipa-prop.c21
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/g++.dg/ipa/pr63470.C54
5 files changed, 89 insertions, 6 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 5331044..29dab90 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,11 @@
+2015-01-12 Jan Hubicka <hubicka@ucw.cz>
+
+ PR ipa/63470
+ * ipa-inline-analysis.c (inline_edge_duplication_hook): Adjust
+ cost when edge becomes direct.
+ * ipa-prop.c (make_edge_direct): Do not adjust when speculation
+ is resolved or when introducing new speculation.
+
2015-01-12 Chen Gang <gang.chen.5i5j@gmail.com>
PR ipa/64551
diff --git a/gcc/ipa-inline-analysis.c b/gcc/ipa-inline-analysis.c
index 92858da..ec91d8e 100644
--- a/gcc/ipa-inline-analysis.c
+++ b/gcc/ipa-inline-analysis.c
@@ -1312,6 +1312,13 @@ inline_edge_duplication_hook (struct cgraph_edge *src,
info->predicate = NULL;
edge_set_predicate (dst, srcinfo->predicate);
info->param = srcinfo->param.copy ();
+ if (!dst->indirect_unknown_callee && src->indirect_unknown_callee)
+ {
+ info->call_stmt_size -= (eni_size_weights.indirect_call_cost
+ - eni_size_weights.call_cost);
+ info->call_stmt_time -= (eni_time_weights.indirect_call_cost
+ - eni_time_weights.call_cost);
+ }
}
diff --git a/gcc/ipa-prop.c b/gcc/ipa-prop.c
index a96b2be..01f4111 100644
--- a/gcc/ipa-prop.c
+++ b/gcc/ipa-prop.c
@@ -2737,7 +2737,20 @@ ipa_make_edge_direct_to_target (struct cgraph_edge *ie, tree target,
ie->caller->name (), callee->name ());
}
if (!speculative)
- ie = ie->make_direct (callee);
+ {
+ struct cgraph_edge *orig = ie;
+ ie = ie->make_direct (callee);
+ /* If we resolved speculative edge the cost is already up to date
+ for direct call (adjusted by inline_edge_duplication_hook). */
+ if (ie == orig)
+ {
+ es = inline_edge_summary (ie);
+ es->call_stmt_size -= (eni_size_weights.indirect_call_cost
+ - eni_size_weights.call_cost);
+ es->call_stmt_time -= (eni_time_weights.indirect_call_cost
+ - eni_time_weights.call_cost);
+ }
+ }
else
{
if (!callee->can_be_discarded_p ())
@@ -2747,14 +2760,10 @@ ipa_make_edge_direct_to_target (struct cgraph_edge *ie, tree target,
if (alias)
callee = alias;
}
+ /* make_speculative will update ie's cost to direct call cost. */
ie = ie->make_speculative
(callee, ie->count * 8 / 10, ie->frequency * 8 / 10);
}
- es = inline_edge_summary (ie);
- es->call_stmt_size -= (eni_size_weights.indirect_call_cost
- - eni_size_weights.call_cost);
- es->call_stmt_time -= (eni_time_weights.indirect_call_cost
- - eni_time_weights.call_cost);
return ie;
}
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index b3b6b59..9378266 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2015-01-12 Jan Hubicka <hubicka@ucw.cz>
+
+ PR ipa/63470
+ * testsuite/g++.dg/ipa/pr63470.C: New testcase.
+
2015-01-11 Janus Weil <janus@gcc.gnu.org>
PR fortran/63733
diff --git a/gcc/testsuite/g++.dg/ipa/pr63470.C b/gcc/testsuite/g++.dg/ipa/pr63470.C
new file mode 100644
index 0000000..e6fa73b
--- /dev/null
+++ b/gcc/testsuite/g++.dg/ipa/pr63470.C
@@ -0,0 +1,54 @@
+/* PR ipa/63470.C */
+/* { dg-do compile } */
+/* { dg-options "-O2 -finline-functions" } */
+
+class A
+{
+public:
+ virtual bool m_fn1 ();
+ virtual const char **m_fn2 (int);
+ virtual int m_fn3 ();
+};
+class FTjackSupport : A
+{
+ ~FTjackSupport ();
+ bool m_fn1 ();
+ bool m_fn4 ();
+ const char **
+ m_fn2 (int)
+ {
+ }
+ int _inited;
+ int *_jackClient;
+ int _activePathCount;
+}
+
+* a;
+void fn1 (...);
+void fn2 (void *);
+int fn3 (int *);
+FTjackSupport::~FTjackSupport () { m_fn4 (); }
+
+bool
+FTjackSupport::m_fn1 ()
+{
+ if (!_jackClient)
+ return 0;
+ for (int i=0; _activePathCount; ++i)
+ if (m_fn2 (i))
+ fn2 (a);
+ if (m_fn3 ())
+ fn2 (a);
+ if (fn3 (_jackClient))
+ fn1 (0);
+}
+
+bool
+FTjackSupport::m_fn4 ()
+{
+ if (_inited && _jackClient)
+ {
+ m_fn1 ();
+ return 0;
+ }
+}