aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--gcc/ChangeLog7
-rw-r--r--gcc/ipa-prop.c18
-rw-r--r--gcc/testsuite/ChangeLog5
-rw-r--r--gcc/testsuite/gcc.dg/ipa/pr58106.c50
4 files changed, 72 insertions, 8 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 9009612..ab141db 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,10 @@
+2013-09-02 Martin Jambor <mjambor@suse.cz>
+
+ PR ipa/58106
+ * ipa-prop.c (ipa_edge_duplication_hook): Always put new rdesc to the
+ linked list. When finding the correct duplicate, also consider also
+ the caller in additon to its inlined_to node.
+
2013-09-02 James Greenhalgh <james.greenhalgh@arm.com>
* config/aarch64/aarch64-simd-builtins.def
diff --git a/gcc/ipa-prop.c b/gcc/ipa-prop.c
index fee5d18..177283c 100644
--- a/gcc/ipa-prop.c
+++ b/gcc/ipa-prop.c
@@ -3015,11 +3015,8 @@ ipa_edge_duplication_hook (struct cgraph_edge *src, struct cgraph_edge *dst,
= (struct ipa_cst_ref_desc *) pool_alloc (ipa_refdesc_pool);
dst_rdesc->cs = dst;
dst_rdesc->refcount = src_rdesc->refcount;
- if (dst->caller->global.inlined_to)
- {
- dst_rdesc->next_duplicate = src_rdesc->next_duplicate;
- src_rdesc->next_duplicate = dst_rdesc;
- }
+ dst_rdesc->next_duplicate = src_rdesc->next_duplicate;
+ src_rdesc->next_duplicate = dst_rdesc;
dst_jf->value.constant.rdesc = dst_rdesc;
}
else
@@ -3034,9 +3031,14 @@ ipa_edge_duplication_hook (struct cgraph_edge *src, struct cgraph_edge *dst,
for (dst_rdesc = src_rdesc->next_duplicate;
dst_rdesc;
dst_rdesc = dst_rdesc->next_duplicate)
- if (dst_rdesc->cs->caller->global.inlined_to
- == dst->caller->global.inlined_to)
- break;
+ {
+ struct cgraph_node *top;
+ top = dst_rdesc->cs->caller->global.inlined_to
+ ? dst_rdesc->cs->caller->global.inlined_to
+ : dst_rdesc->cs->caller;
+ if (dst->caller->global.inlined_to == top)
+ break;
+ }
gcc_assert (dst_rdesc);
dst_jf->value.constant.rdesc = dst_rdesc;
}
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index d3892f6..dd53ef6 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2013-09-02 Martin Jambor <mjambor@suse.cz>
+
+ PR ipa/58106
+ * gcc.dg/ipa/pr58106.c: New test.
+
2013-09-02 James Greenhalgh <james.greenhalgh@arm.com>
* gcc.target/aarch64/scalar_intrinsics.c
diff --git a/gcc/testsuite/gcc.dg/ipa/pr58106.c b/gcc/testsuite/gcc.dg/ipa/pr58106.c
new file mode 100644
index 0000000..b83353c
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/ipa/pr58106.c
@@ -0,0 +1,50 @@
+/* PR 58106 testcase. Verify that rdesc chain creating and lookup works with
+ recursive inlining and master clone creation. */
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+typedef struct rtx_def *rtx;
+enum rtx_code {
+ LAST_AND_UNUSED_RTX_CODE};
+extern const char * const rtx_format[((int) LAST_AND_UNUSED_RTX_CODE)];
+struct rtx_def {
+ enum rtx_code code;
+};
+typedef int (*rtx_function) (rtx *, void *);
+extern int for_each_rtx (rtx *, rtx_function, void *);
+int
+replace_label (rtx *x, void *data)
+{
+ rtx l = *x;
+ if (l == (rtx) 0)
+ {
+ {
+ rtx new_c, new_l;
+ for_each_rtx (&new_c, replace_label, data);
+ }
+ }
+}
+static int
+for_each_rtx_1 (rtx exp, int n, rtx_function f, void *data)
+{
+ int result, i, j;
+ const char *format = (rtx_format[(int) (((enum rtx_code) (exp)->code))]);
+ rtx *x;
+ for (; format[n] != '\0'; n++)
+ {
+ switch (format[n])
+ {
+ case 'e':
+ result = (*f) (x, data);
+ {
+ result = for_each_rtx_1 (*x, i, f, data);
+ }
+ }
+ }
+}
+int
+for_each_rtx (rtx *x, rtx_function f, void *data)
+{
+ int i;
+ return for_each_rtx_1 (*x, i, f, data);
+}