diff mbox

Fix invalid GIMPLE out of SRA

Message ID 201103232154.28597.ebotcazou@adacore.com
State New
Headers show

Commit Message

Eric Botcazou March 23, 2011, 8:54 p.m. UTC
Hi,

this is a fallout of one of my gimplifier changes.  For the attached testcase, 
the compiler generates invalid GIMPLE at -O1 or above:

p.adb: In function 'P.F':
p.adb:24:1: error: invalid operand in unary operation
D.2361_107 = (integer[1:1] *) &*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4};

  if (!is_gimple_val (rhs1))
    {
      error ("invalid operand in unary operation");
      return true;
    }

(gdb) p rhs_code
$6 = NOP_EXPR
(gdb) p debug_generic_expr(rhs1)
&*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4}

i.e ADDR_EXPR of ARRAY_RANGE_REF with non-constant operand #1.

The invalid statement is generated by the early SRA pass:

  integer a1[1:1];

  VIEW_CONVERT_EXPR<integer[1:1]>(*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4}) = 
a1;

is rewritten into:

  Created a replacement for a1 offset: 0, size: 32: a1$1

  D.2361_107 = (integer[1:1] *) &*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4};
  MEM[(integer[1:D.2312] *)D.2361_107] = a1$1_92;


It turns out that the problematic NOP_EXPR is a useless type conversion emitted 
by build_fold_addr_expr: if you add a call to force_gimple_operand at the hot 
spot, it ends up removing the NOP_EXPR and nothing else.  So the proposed fix 
is just to add a call to STRIP_USELESS_TYPE_CONVERSION there.

Tested on i586-suse-linux, OK for the mainline?


2011-03-23  Eric Botcazou  <ebotcazou@adacore.com>

	* tree-sra.c (build_ref_for_offset): Call STRIP_USELESS_TYPE_CONVERSION
	on the address built for a reference with variable offset.


2011-03-23  Eric Botcazou  <ebotcazou@adacore.com>

	* gnat.dg/array15.ad[sb]: New test.
	* gnat.dg/array15_pkg.ads: New helper.

Comments

Richard Biener March 24, 2011, 10:05 a.m. UTC | #1
On Wed, Mar 23, 2011 at 9:54 PM, Eric Botcazou <ebotcazou@adacore.com> wrote:
> Hi,
>
> this is a fallout of one of my gimplifier changes.  For the attached testcase,
> the compiler generates invalid GIMPLE at -O1 or above:
>
> p.adb: In function 'P.F':
> p.adb:24:1: error: invalid operand in unary operation
> D.2361_107 = (integer[1:1] *) &*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4};
>
>  if (!is_gimple_val (rhs1))
>    {
>      error ("invalid operand in unary operation");
>      return true;
>    }
>
> (gdb) p rhs_code
> $6 = NOP_EXPR
> (gdb) p debug_generic_expr(rhs1)
> &*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4}
>
> i.e ADDR_EXPR of ARRAY_RANGE_REF with non-constant operand #1.
>
> The invalid statement is generated by the early SRA pass:
>
>  integer a1[1:1];
>
>  VIEW_CONVERT_EXPR<integer[1:1]>(*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4}) =
> a1;
>
> is rewritten into:
>
>  Created a replacement for a1 offset: 0, size: 32: a1$1
>
>  D.2361_107 = (integer[1:1] *) &*S15b.16_56[D.2327_91 ...]{lb: 1 sz: 4};
>  MEM[(integer[1:D.2312] *)D.2361_107] = a1$1_92;
>
>
> It turns out that the problematic NOP_EXPR is a useless type conversion emitted
> by build_fold_addr_expr: if you add a call to force_gimple_operand at the hot
> spot, it ends up removing the NOP_EXPR and nothing else.  So the proposed fix
> is just to add a call to STRIP_USELESS_TYPE_CONVERSION there.
>
> Tested on i586-suse-linux, OK for the mainline?

Ok.

At some point I hope we get gimple variants for most of the tree
building helpers (that build_fold_addr_expr, and also fold_convert).

Thanks,
Richard.

>
> 2011-03-23  Eric Botcazou  <ebotcazou@adacore.com>
>
>        * tree-sra.c (build_ref_for_offset): Call STRIP_USELESS_TYPE_CONVERSION
>        on the address built for a reference with variable offset.
>
>
> 2011-03-23  Eric Botcazou  <ebotcazou@adacore.com>
>
>        * gnat.dg/array15.ad[sb]: New test.
>        * gnat.dg/array15_pkg.ads: New helper.
>
>
> --
> Eric Botcazou
>
diff mbox

Patch

Index: tree-sra.c
===================================================================
--- tree-sra.c	(revision 171345)
+++ tree-sra.c	(working copy)
@@ -1376,6 +1376,7 @@  build_ref_for_offset (location_t loc, tr
       add_referenced_var (tmp);
       tmp = make_ssa_name (tmp, NULL);
       addr = build_fold_addr_expr (unshare_expr (prev_base));
+      STRIP_USELESS_TYPE_CONVERSION (addr);
       stmt = gimple_build_assign (tmp, addr);
       gimple_set_location (stmt, loc);
       SSA_NAME_DEF_STMT (tmp) = stmt;