public inbox for gcc-patches@gcc.gnu.org
 help / color / mirror / Atom feed
* [patch] Fix PR rtl-optimization/54870
@ 2012-10-14 21:01 Eric Botcazou
  2012-10-15 10:02 ` Richard Biener
  0 siblings, 1 reply; 8+ messages in thread
From: Eric Botcazou @ 2012-10-14 21:01 UTC (permalink / raw)
  To: gcc-patches

[-- Attachment #1: Type: text/plain, Size: 2173 bytes --]

Hi,

This is the execution failure of gfortran.dg/array_constructor_4.f90 in 64-bit
mode on SPARC/Solaris at -O3.  The dse2 dump for the reduced testcase reads:

dse: local deletions = 0, global deletions = 1, spill deletions = 0
starting the processing of deferred insns
deleting insn with uid = 25.
ending the processing of deferred insns

but the memory location stored to:

(insn 25 27 154 2 (set (mem/c:SI (plus:DI (reg/f:DI 30 %fp)
                (const_int 2039 [0x7f7])) [6 A.1+16 S4 A64])
        (reg:SI 1 %g1 [136])) array_constructor_4.f90:4 61 {*movsi_insn}
     (nil))

is read by a subsequent call to memcpy.

It turns out that this memcpy call is generated for an aggregate assignment:

  MEM[(c_char * {ref-all})&i] = MEM[(c_char * {ref-all})&A.17];

Note the A.1 in the store and the A.17 in the load. A.1 and A.17 are aggregate
variables sharing the same stack slot.  A.17 is correcty marked as addressable
because of the call to memcpy, but A.1 isn't since its address isn't taken, 
and DSE can optimize away (since 4.7) stores if their MEM_EXPR doesn't escape.

The store is reaching the load because an intermediate store into A.17:

(insn 78 76 82 6 (set (mem/c:SI (plus:DI (reg/f:DI 30 %fp)
                (const_int 2039 [0x7f7])) [6 A.17+16 S4 A64])
        (reg:SI 1 %g1 [136])) array_constructor_4.f90:14 61 {*movsi_insn}
     (nil))

has been deleted by postreload as no-op (because redundant), thus making A.1
partially escape without marking it as addressable.

The attached patch uses cfun->gimple_df->escaped.vars to plug the hole: when 
mark_addressable is called during RTL expansion and the decl is partitioned, 
all the variables in the partition are added to the bitmap.  Then can_escape 
is changed to additionally test cfun->gimple_df->escaped.vars.

Tested on x86-64/Linux and SPARC64/Solaris, OK for mainline and 4.7 branch?


2012-10-14  Eric Botcazou  <ebotcazou@adacore.com>

	PR rtl-optimization/54870
	* dse.c (can_escape): Test cfun->gimple_df->escaped.vars as well.
	* gimplify.c (mark_addressable): If this is a partition decl, add
	all the variables in the partition to cfun->gimple_df->escaped.vars.


-- 
Eric Botcazou

[-- Attachment #2: pr54870.diff --]
[-- Type: text/x-patch, Size: 1813 bytes --]

Index: dse.c
===================================================================
--- dse.c	(revision 192353)
+++ dse.c	(working copy)
@@ -990,6 +990,7 @@ delete_dead_store_insn (insn_info_t insn
 }
 
 /* Check if EXPR can possibly escape the current function scope.  */
+
 static bool
 can_escape (tree expr)
 {
@@ -998,7 +999,10 @@ can_escape (tree expr)
     return true;
   base = get_base_address (expr);
   if (DECL_P (base)
-      && !may_be_aliased (base))
+      && !may_be_aliased (base)
+      && !(cfun->gimple_df->escaped.vars
+	   && bitmap_bit_p (cfun->gimple_df->escaped.vars,
+			    DECL_PT_UID (base))))
     return false;
   return true;
 }
Index: gimplify.c
===================================================================
--- gimplify.c	(revision 192353)
+++ gimplify.c	(working copy)
@@ -116,6 +116,26 @@ mark_addressable (tree x)
       && TREE_CODE (x) != RESULT_DECL)
     return;
   TREE_ADDRESSABLE (x) = 1;
+
+  /* If this is a partitioned decl, we need to mark all the variables in the
+     partition as escaped.  This is needed because a store into one of them
+     can be replaced with a store into another, and this may not change the
+     outcome of the escape analysis for DSE to work properly.  */
+  if (TREE_CODE (x) == VAR_DECL
+      && !TREE_STATIC (x)
+      && cfun->gimple_df != NULL
+      && cfun->gimple_df->decls_to_pointers != NULL)
+    {
+      void *namep
+	= pointer_map_contains (cfun->gimple_df->decls_to_pointers, x);
+      if (namep)
+	{
+	  struct ptr_info_def *pi = get_ptr_info (*(tree *)namep);
+	  if (cfun->gimple_df->escaped.vars == NULL)
+	    cfun->gimple_df->escaped.vars = BITMAP_GGC_ALLOC ();
+	  bitmap_ior_into (cfun->gimple_df->escaped.vars, pi->pt.vars);
+	}
+    }
 }
 
 /* Return a hash value for a formal temporary table entry.  */

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

end of thread, other threads:[~2012-10-16 11:42 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2012-10-14 21:01 [patch] Fix PR rtl-optimization/54870 Eric Botcazou
2012-10-15 10:02 ` Richard Biener
2012-10-15 10:20   ` Eric Botcazou
2012-10-15 10:37     ` Richard Biener
2012-10-15 11:03       ` Eric Botcazou
2012-10-15 11:33         ` Richard Biener
2012-10-16 10:13           ` Eric Botcazou
2012-10-16 13:19             ` Richard Biener

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).