Currently, for self-recursive call, we never use value originated from 
non-passthrough
jump function as source to avoid propagation explosion, but self-dependent 
value is
missed. This patch is made to fix the bug.

Bootstrapped/regtested on x86_64-linux and aarch64-linux.

Feng
---
2020-02-18  Feng Xue  <f...@os.amperecomputing.com>

        PR ipa/93763
        * ipa-cp.c (self_recursively_generated_p): Mark self-dependent value as
        self-recursively generated.
From 1ff803f33de0fe86d526deb23af2d08c15028ff9 Mon Sep 17 00:00:00 2001
From: Feng Xue <f...@os.amperecomputing.com>
Date: Mon, 17 Feb 2020 17:07:04 +0800
Subject: [PATCH] Do not propagate self-dependent value (PR ipa/93763)

---
 gcc/ipa-cp.c                       | 10 ++++---
 gcc/testsuite/g++.dg/ipa/pr93763.C | 15 ++++++++++
 gcc/testsuite/gcc.dg/ipa/pr93763.c | 46 ++++++++++++++++++++++++++++++
 3 files changed, 67 insertions(+), 4 deletions(-)
 create mode 100644 gcc/testsuite/g++.dg/ipa/pr93763.C
 create mode 100644 gcc/testsuite/gcc.dg/ipa/pr93763.c

diff --git a/gcc/ipa-cp.c b/gcc/ipa-cp.c
index 4f5b72e6994..1d0c1ac0f35 100644
--- a/gcc/ipa-cp.c
+++ b/gcc/ipa-cp.c
@@ -1897,8 +1897,8 @@ ipcp_lattice<valtype>::add_value (valtype newval, cgraph_edge *cs,
 }
 
 /* Return true, if a ipcp_value VAL is orginated from parameter value of
-   self-feeding recursive function by applying non-passthrough arithmetic
-   transformation.  */
+   self-feeding recursive function via some kind of pass-through jump
+   function.  */
 
 static bool
 self_recursively_generated_p (ipcp_value<tree> *val)
@@ -1909,10 +1909,12 @@ self_recursively_generated_p (ipcp_value<tree> *val)
     {
       cgraph_edge *cs = src->cs;
 
-      if (!src->val || cs->caller != cs->callee->function_symbol ()
-	  || src->val == val)
+      if (!src->val || cs->caller != cs->callee->function_symbol ())
 	return false;
 
+      if (src->val == val)
+	continue;
+
       if (!info)
 	info = IPA_NODE_REF (cs->caller);
 
diff --git a/gcc/testsuite/g++.dg/ipa/pr93763.C b/gcc/testsuite/g++.dg/ipa/pr93763.C
new file mode 100644
index 00000000000..61117108ecd
--- /dev/null
+++ b/gcc/testsuite/g++.dg/ipa/pr93763.C
@@ -0,0 +1,15 @@
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+struct search_param {
+  int total;
+};
+void search_trivial(search_param error_left) {
+  search_trivial(error_left);
+  search_param error_left2{error_left};
+  error_left2.total--;
+  search_trivial(error_left2);
+}
+void search_algo_uni(search_param error_left) { search_trivial(error_left); }
+void search_algo(search_param error_left) { search_algo_uni(error_left); }
+int main() { search_algo({}); return 0; }
diff --git a/gcc/testsuite/gcc.dg/ipa/pr93763.c b/gcc/testsuite/gcc.dg/ipa/pr93763.c
new file mode 100644
index 00000000000..d11705932b6
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/ipa/pr93763.c
@@ -0,0 +1,46 @@
+/* { dg-do compile } */
+/* { dg-options "-O3" } */
+
+typedef struct a a;
+struct a {
+  a *b
+} d;
+e, k, ah, al;
+f(aa) {
+  if (aa & 1)
+    goto g;
+  f(aa | 2);
+g:
+  h();
+}
+l() {
+  {
+    f(072);
+    i(e, d, 92);
+  }
+}
+ag() {
+  { i(e, d, 36); }
+}
+ai(a *m, a *n, unsigned aa) {
+  f(aa);
+  j(k, l, ah, 1);
+}
+j(int c, a m, int aj, int aa) {
+  int ak = aa;
+  { i(e, d, ak); }
+}
+i(int c, a *m, unsigned aa) {
+  {
+    {             i(c, (*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(
+*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(
+*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*(*m).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b)
+.b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b)
+.b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b)
+.b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b)
+.b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b).b, 0);
+    }
+  }
+  int am = aa;
+  ai(ag, al, am);
+}
-- 
2.17.1

Reply via email to