public inbox for gcc-cvs@sourceware.org
help / color / mirror / Atom feed
* [gcc(refs/users/aoliva/heads/testme)] ipa-modref: merge flags when adding escape
@ 2021-06-18  9:01 Alexandre Oliva
  0 siblings, 0 replies; 4+ messages in thread
From: Alexandre Oliva @ 2021-06-18  9:01 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:e63c790af30fa492031d9b09f0d5186a372dfdbb

commit e63c790af30fa492031d9b09f0d5186a372dfdbb
Author: Alexandre Oliva <oliva@adacore.com>
Date:   Fri Jun 18 05:59:46 2021 -0300

    ipa-modref: merge flags when adding escape
    
    While working on some function splitting changes, I've got a
    miscompilation in stagefeedback that I've tracked down to a
    complicated scenario:
    
    - ipa-modref miscomputes a function parameter as having EAF_DIRECT,
      because it's dereferenced and passed on to another function, but
      add_escape_point does not update the flags for the dereferenced
      SSA_NAME passed as a parameter, and the EAF_UNUSED in the value that
      first initializes it, that remains unchanged throughout, causes
      deref_flags to set EAF_DIRECT, among other flags.
    
    - structalias, seeing the EAF_DIRECT in the parameter for that
      function, refrains from mak[ing]_transitive_closure_constraints for
      a pointer passed in that parameter.
    
    - tree dse2 concludes the initializer of the pointed-to variable is a
      dead store and removes it.
    
    The test depends on gimple passes's processing of functions in a
    certain order to expose parm flag miscomputed by ipa-modref.  A
    different order may enable the non-ipa modref2 pass to compute flags
    differently and avoid the problem.
    
    I've arranged for add_escape_point to merge flags, as the non-ipa path
    does.  I've also caught and fixed an error in the dumping of escaping
    flags.
    
    
    for  gcc/ChangeLog
    
            * ipa-modref.c (modref_lattice::add_escape_point): Merge
            min_flags into flags.
            (modref_lattice::dump): Fix escape_point's min_flags dumping.
    
    for  gcc/testsuite/ChangeLog
    
            * c-c++-common/modref-dse.c: New.

Diff:
---
 gcc/ipa-modref.c                        |  4 ++--
 gcc/testsuite/c-c++-common/modref-dse.c | 38 +++++++++++++++++++++++++++++++++
 2 files changed, 40 insertions(+), 2 deletions(-)

diff --git a/gcc/ipa-modref.c b/gcc/ipa-modref.c
index d5a8332fb55..3b0830cb875 100644
--- a/gcc/ipa-modref.c
+++ b/gcc/ipa-modref.c
@@ -1392,7 +1392,7 @@ modref_lattice::dump (FILE *out, int indent) const
 	  fprintf (out, "%*s  Arg %i (%s) min flags", indent, "",
 		   escape_points[i].arg,
 		   escape_points[i].direct ? "direct" : "indirect");
-	  dump_eaf_flags (out, flags, false);
+	  dump_eaf_flags (out, escape_points[i].min_flags, false);
 	  fprintf (out, " in call ");
 	  print_gimple_stmt (out, escape_points[i].call, 0);
 	}
@@ -1411,7 +1411,7 @@ modref_lattice::add_escape_point (gcall *call, int arg, int min_flags,
 
   /* If we already determined flags to be bad enough,
    * we do not need to record.  */
-  if ((flags & min_flags) == flags)
+  if (!merge (min_flags))
     return false;
 
   FOR_EACH_VEC_ELT (escape_points, i, ep)
diff --git a/gcc/testsuite/c-c++-common/modref-dse.c b/gcc/testsuite/c-c++-common/modref-dse.c
new file mode 100644
index 00000000000..5f64e8f4b59
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/modref-dse.c
@@ -0,0 +1,38 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-dse2-details" } */
+/* { dg-final { scan-tree-dump-not "Deleted dead store" "dse2" } } */
+
+struct foo { unsigned long bar; };
+
+unsigned y;
+
+static int __attribute__ ((__noinline__, __noclone__))
+wrapped (struct foo *p, int i);
+
+static int wrapper (struct foo *p);
+
+static int __attribute__ ((__noclone__))
+wrapper (struct foo *p) {
+  return wrapped (p, 1);
+}
+
+static int __attribute__ ((__noinline__, __noclone__))
+dind (struct foo **pp);
+
+int __attribute__ ((__noclone__, __no_reorder__))
+xfn () {
+  struct foo x = { 0xBADC0FFE };
+  struct foo *p = &x;
+  return dind (&p);
+}
+
+static int __attribute__ ((__noinline__, __no_reorder__))
+wrapped (struct foo *p, int i) {
+  return p->bar + i == y++;
+}
+
+static int __attribute__ ((__noinline__, __noclone__, __no_reorder__))
+dind (struct foo **pp) {
+  wrapper (*pp);
+  return 0;
+}


^ permalink raw reply	[flat|nested] 4+ messages in thread

* [gcc(refs/users/aoliva/heads/testme)] ipa-modref: merge flags when adding escape
@ 2021-07-10  9:43 Alexandre Oliva
  0 siblings, 0 replies; 4+ messages in thread
From: Alexandre Oliva @ 2021-07-10  9:43 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:21f072ecb6a8a492a2f6f621341ad588281d1701

commit 21f072ecb6a8a492a2f6f621341ad588281d1701
Author: Alexandre Oliva <oliva@adacore.com>
Date:   Fri Jul 9 19:54:41 2021 -0300

    ipa-modref: merge flags when adding escape
    
    While working on some function splitting changes, I've got a
    miscompilation in stagefeedback that I've tracked down to a
    complicated scenario:
    
    - ipa-modref miscomputes a function parameter as having EAF_DIRECT,
      because it's dereferenced and passed on to another function, but
      add_escape_point does not update the flags for the dereferenced
      SSA_NAME passed as a parameter, and the EAF_UNUSED in the value that
      first initializes it, that remains unchanged throughout, causes
      deref_flags to set EAF_DIRECT, among other flags.
    
    - structalias, seeing the EAF_DIRECT in the parameter for that
      function, refrains from mak[ing]_transitive_closure_constraints for
      a pointer passed in that parameter.
    
    - tree dse2 concludes the initializer of the pointed-to variable is a
      dead store and removes it.
    
    The test depends on gimple passes's processing of functions in a
    certain order to expose parm flag miscomputed by ipa-modref.  A
    different order may enable the non-ipa modref2 pass to compute flags
    differently and avoid the problem.
    
    I've arranged for add_escape_point to merge flags, as the non-ipa path
    does.  I've also caught and fixed an error in the dumping of escaping
    flags.
    
    
    for  gcc/ChangeLog
    
            * ipa-modref.c (modref_lattice::add_escape_point): Merge
            min_flags into flags.
            (modref_lattice::dump): Fix escape_point's min_flags dumping.
    
    for  gcc/testsuite/ChangeLog
    
            * c-c++-common/modref-dse.c: New.

Diff:
---
 gcc/ipa-modref.c                        |  4 ++--
 gcc/testsuite/c-c++-common/modref-dse.c | 38 +++++++++++++++++++++++++++++++++
 2 files changed, 40 insertions(+), 2 deletions(-)

diff --git a/gcc/ipa-modref.c b/gcc/ipa-modref.c
index d5a8332fb55..3b0830cb875 100644
--- a/gcc/ipa-modref.c
+++ b/gcc/ipa-modref.c
@@ -1392,7 +1392,7 @@ modref_lattice::dump (FILE *out, int indent) const
 	  fprintf (out, "%*s  Arg %i (%s) min flags", indent, "",
 		   escape_points[i].arg,
 		   escape_points[i].direct ? "direct" : "indirect");
-	  dump_eaf_flags (out, flags, false);
+	  dump_eaf_flags (out, escape_points[i].min_flags, false);
 	  fprintf (out, " in call ");
 	  print_gimple_stmt (out, escape_points[i].call, 0);
 	}
@@ -1411,7 +1411,7 @@ modref_lattice::add_escape_point (gcall *call, int arg, int min_flags,
 
   /* If we already determined flags to be bad enough,
    * we do not need to record.  */
-  if ((flags & min_flags) == flags)
+  if (!merge (min_flags))
     return false;
 
   FOR_EACH_VEC_ELT (escape_points, i, ep)
diff --git a/gcc/testsuite/c-c++-common/modref-dse.c b/gcc/testsuite/c-c++-common/modref-dse.c
new file mode 100644
index 00000000000..5f64e8f4b59
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/modref-dse.c
@@ -0,0 +1,38 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-dse2-details" } */
+/* { dg-final { scan-tree-dump-not "Deleted dead store" "dse2" } } */
+
+struct foo { unsigned long bar; };
+
+unsigned y;
+
+static int __attribute__ ((__noinline__, __noclone__))
+wrapped (struct foo *p, int i);
+
+static int wrapper (struct foo *p);
+
+static int __attribute__ ((__noclone__))
+wrapper (struct foo *p) {
+  return wrapped (p, 1);
+}
+
+static int __attribute__ ((__noinline__, __noclone__))
+dind (struct foo **pp);
+
+int __attribute__ ((__noclone__, __no_reorder__))
+xfn () {
+  struct foo x = { 0xBADC0FFE };
+  struct foo *p = &x;
+  return dind (&p);
+}
+
+static int __attribute__ ((__noinline__, __no_reorder__))
+wrapped (struct foo *p, int i) {
+  return p->bar + i == y++;
+}
+
+static int __attribute__ ((__noinline__, __noclone__, __no_reorder__))
+dind (struct foo **pp) {
+  wrapper (*pp);
+  return 0;
+}


^ permalink raw reply	[flat|nested] 4+ messages in thread

* [gcc(refs/users/aoliva/heads/testme)] ipa-modref: merge flags when adding escape
@ 2021-07-10  0:08 Alexandre Oliva
  0 siblings, 0 replies; 4+ messages in thread
From: Alexandre Oliva @ 2021-07-10  0:08 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:2d2ed7112da23701877d055b340cbe333dfeb4a4

commit 2d2ed7112da23701877d055b340cbe333dfeb4a4
Author: Alexandre Oliva <oliva@adacore.com>
Date:   Fri Jul 9 19:54:41 2021 -0300

    ipa-modref: merge flags when adding escape
    
    While working on some function splitting changes, I've got a
    miscompilation in stagefeedback that I've tracked down to a
    complicated scenario:
    
    - ipa-modref miscomputes a function parameter as having EAF_DIRECT,
      because it's dereferenced and passed on to another function, but
      add_escape_point does not update the flags for the dereferenced
      SSA_NAME passed as a parameter, and the EAF_UNUSED in the value that
      first initializes it, that remains unchanged throughout, causes
      deref_flags to set EAF_DIRECT, among other flags.
    
    - structalias, seeing the EAF_DIRECT in the parameter for that
      function, refrains from mak[ing]_transitive_closure_constraints for
      a pointer passed in that parameter.
    
    - tree dse2 concludes the initializer of the pointed-to variable is a
      dead store and removes it.
    
    The test depends on gimple passes's processing of functions in a
    certain order to expose parm flag miscomputed by ipa-modref.  A
    different order may enable the non-ipa modref2 pass to compute flags
    differently and avoid the problem.
    
    I've arranged for add_escape_point to merge flags, as the non-ipa path
    does.  I've also caught and fixed an error in the dumping of escaping
    flags.
    
    
    for  gcc/ChangeLog
    
            * ipa-modref.c (modref_lattice::add_escape_point): Merge
            min_flags into flags.
            (modref_lattice::dump): Fix escape_point's min_flags dumping.
    
    for  gcc/testsuite/ChangeLog
    
            * c-c++-common/modref-dse.c: New.

Diff:
---
 gcc/ipa-modref.c                        |  4 ++--
 gcc/testsuite/c-c++-common/modref-dse.c | 38 +++++++++++++++++++++++++++++++++
 2 files changed, 40 insertions(+), 2 deletions(-)

diff --git a/gcc/ipa-modref.c b/gcc/ipa-modref.c
index d5a8332fb55..3b0830cb875 100644
--- a/gcc/ipa-modref.c
+++ b/gcc/ipa-modref.c
@@ -1392,7 +1392,7 @@ modref_lattice::dump (FILE *out, int indent) const
 	  fprintf (out, "%*s  Arg %i (%s) min flags", indent, "",
 		   escape_points[i].arg,
 		   escape_points[i].direct ? "direct" : "indirect");
-	  dump_eaf_flags (out, flags, false);
+	  dump_eaf_flags (out, escape_points[i].min_flags, false);
 	  fprintf (out, " in call ");
 	  print_gimple_stmt (out, escape_points[i].call, 0);
 	}
@@ -1411,7 +1411,7 @@ modref_lattice::add_escape_point (gcall *call, int arg, int min_flags,
 
   /* If we already determined flags to be bad enough,
    * we do not need to record.  */
-  if ((flags & min_flags) == flags)
+  if (!merge (min_flags))
     return false;
 
   FOR_EACH_VEC_ELT (escape_points, i, ep)
diff --git a/gcc/testsuite/c-c++-common/modref-dse.c b/gcc/testsuite/c-c++-common/modref-dse.c
new file mode 100644
index 00000000000..5f64e8f4b59
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/modref-dse.c
@@ -0,0 +1,38 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-dse2-details" } */
+/* { dg-final { scan-tree-dump-not "Deleted dead store" "dse2" } } */
+
+struct foo { unsigned long bar; };
+
+unsigned y;
+
+static int __attribute__ ((__noinline__, __noclone__))
+wrapped (struct foo *p, int i);
+
+static int wrapper (struct foo *p);
+
+static int __attribute__ ((__noclone__))
+wrapper (struct foo *p) {
+  return wrapped (p, 1);
+}
+
+static int __attribute__ ((__noinline__, __noclone__))
+dind (struct foo **pp);
+
+int __attribute__ ((__noclone__, __no_reorder__))
+xfn () {
+  struct foo x = { 0xBADC0FFE };
+  struct foo *p = &x;
+  return dind (&p);
+}
+
+static int __attribute__ ((__noinline__, __no_reorder__))
+wrapped (struct foo *p, int i) {
+  return p->bar + i == y++;
+}
+
+static int __attribute__ ((__noinline__, __noclone__, __no_reorder__))
+dind (struct foo **pp) {
+  wrapper (*pp);
+  return 0;
+}


^ permalink raw reply	[flat|nested] 4+ messages in thread

* [gcc(refs/users/aoliva/heads/testme)] ipa-modref: merge flags when adding escape
@ 2021-06-28 15:42 Alexandre Oliva
  0 siblings, 0 replies; 4+ messages in thread
From: Alexandre Oliva @ 2021-06-28 15:42 UTC (permalink / raw)
  To: gcc-cvs

https://gcc.gnu.org/g:b54230f5409463ba380a83a7569ec1de7b88cb35

commit b54230f5409463ba380a83a7569ec1de7b88cb35
Author: Alexandre Oliva <oliva@adacore.com>
Date:   Mon Jun 28 12:40:30 2021 -0300

    ipa-modref: merge flags when adding escape
    
    While working on some function splitting changes, I've got a
    miscompilation in stagefeedback that I've tracked down to a
    complicated scenario:
    
    - ipa-modref miscomputes a function parameter as having EAF_DIRECT,
      because it's dereferenced and passed on to another function, but
      add_escape_point does not update the flags for the dereferenced
      SSA_NAME passed as a parameter, and the EAF_UNUSED in the value that
      first initializes it, that remains unchanged throughout, causes
      deref_flags to set EAF_DIRECT, among other flags.
    
    - structalias, seeing the EAF_DIRECT in the parameter for that
      function, refrains from mak[ing]_transitive_closure_constraints for
      a pointer passed in that parameter.
    
    - tree dse2 concludes the initializer of the pointed-to variable is a
      dead store and removes it.
    
    The test depends on gimple passes's processing of functions in a
    certain order to expose parm flag miscomputed by ipa-modref.  A
    different order may enable the non-ipa modref2 pass to compute flags
    differently and avoid the problem.
    
    I've arranged for add_escape_point to merge flags, as the non-ipa path
    does.  I've also caught and fixed an error in the dumping of escaping
    flags.
    
    
    for  gcc/ChangeLog
    
            * ipa-modref.c (modref_lattice::add_escape_point): Merge
            min_flags into flags.
            (modref_lattice::dump): Fix escape_point's min_flags dumping.
    
    for  gcc/testsuite/ChangeLog
    
            * c-c++-common/modref-dse.c: New.

Diff:
---
 gcc/ipa-modref.c                        |  4 ++--
 gcc/testsuite/c-c++-common/modref-dse.c | 38 +++++++++++++++++++++++++++++++++
 2 files changed, 40 insertions(+), 2 deletions(-)

diff --git a/gcc/ipa-modref.c b/gcc/ipa-modref.c
index d5a8332fb55..3b0830cb875 100644
--- a/gcc/ipa-modref.c
+++ b/gcc/ipa-modref.c
@@ -1392,7 +1392,7 @@ modref_lattice::dump (FILE *out, int indent) const
 	  fprintf (out, "%*s  Arg %i (%s) min flags", indent, "",
 		   escape_points[i].arg,
 		   escape_points[i].direct ? "direct" : "indirect");
-	  dump_eaf_flags (out, flags, false);
+	  dump_eaf_flags (out, escape_points[i].min_flags, false);
 	  fprintf (out, " in call ");
 	  print_gimple_stmt (out, escape_points[i].call, 0);
 	}
@@ -1411,7 +1411,7 @@ modref_lattice::add_escape_point (gcall *call, int arg, int min_flags,
 
   /* If we already determined flags to be bad enough,
    * we do not need to record.  */
-  if ((flags & min_flags) == flags)
+  if (!merge (min_flags))
     return false;
 
   FOR_EACH_VEC_ELT (escape_points, i, ep)
diff --git a/gcc/testsuite/c-c++-common/modref-dse.c b/gcc/testsuite/c-c++-common/modref-dse.c
new file mode 100644
index 00000000000..5f64e8f4b59
--- /dev/null
+++ b/gcc/testsuite/c-c++-common/modref-dse.c
@@ -0,0 +1,38 @@
+/* { dg-do compile } */
+/* { dg-options "-O2 -fdump-tree-dse2-details" } */
+/* { dg-final { scan-tree-dump-not "Deleted dead store" "dse2" } } */
+
+struct foo { unsigned long bar; };
+
+unsigned y;
+
+static int __attribute__ ((__noinline__, __noclone__))
+wrapped (struct foo *p, int i);
+
+static int wrapper (struct foo *p);
+
+static int __attribute__ ((__noclone__))
+wrapper (struct foo *p) {
+  return wrapped (p, 1);
+}
+
+static int __attribute__ ((__noinline__, __noclone__))
+dind (struct foo **pp);
+
+int __attribute__ ((__noclone__, __no_reorder__))
+xfn () {
+  struct foo x = { 0xBADC0FFE };
+  struct foo *p = &x;
+  return dind (&p);
+}
+
+static int __attribute__ ((__noinline__, __no_reorder__))
+wrapped (struct foo *p, int i) {
+  return p->bar + i == y++;
+}
+
+static int __attribute__ ((__noinline__, __noclone__, __no_reorder__))
+dind (struct foo **pp) {
+  wrapper (*pp);
+  return 0;
+}


^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2021-07-10  9:43 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2021-06-18  9:01 [gcc(refs/users/aoliva/heads/testme)] ipa-modref: merge flags when adding escape Alexandre Oliva
2021-06-28 15:42 Alexandre Oliva
2021-07-10  0:08 Alexandre Oliva
2021-07-10  9:43 Alexandre Oliva

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).