https://gcc.gnu.org/bugzilla/show_bug.cgi?id=80960
Richard Biener <rguenth at gcc dot gnu.org> changed:
What |Removed |Added
----------------------------------------------------------------------------
Status|NEW |ASSIGNED
Assignee|unassigned at gcc dot gnu.org |rguenth at gcc dot
gnu.org
--- Comment #25 from Richard Biener <rguenth at gcc dot gnu.org> ---
Oh, so it's not actually that plus_constant calls but the ones called via
get_addr from true_dependence_1 which is called 60 million times from
check_mem_read_use. That does:
/* Convert the address X into something we can use. This is done by returning
it unchanged unless it is a VALUE or VALUE +/- constant; for VALUE
we call cselib to get a more useful rtx. */
rtx
get_addr (rtx x)
{
cselib_val *v;
struct elt_loc_list *l;
if (GET_CODE (x) != VALUE)
{
if ((GET_CODE (x) == PLUS || GET_CODE (x) == MINUS)
&& GET_CODE (XEXP (x, 0)) == VALUE
&& CONST_SCALAR_INT_P (XEXP (x, 1)))
{
rtx op0 = get_addr (XEXP (x, 0));
if (op0 != XEXP (x, 0))
{
poly_int64 c;
if (GET_CODE (x) == PLUS
&& poly_int_rtx_p (XEXP (x, 1), &c))
return plus_constant (GET_MODE (x), op0, c);
thus undoing the valueization DSE does. Since it unconditionally does
this I guess DSE could do it itself instead. That helps tremendously:
dead store elim2 : 6.34 ( 11%) 0.02 ( 7%) 6.38 ( 11%)
170M ( 45%)
TOTAL : 56.96 0.27 57.26
381M
56.96user 0.29system 0:57.27elapsed 99%CPU (0avgtext+0avgdata
825148maxresident)k
0inputs+0outputs (0major+210372minor)pagefaults 0swaps
diff --git a/gcc/dse.c b/gcc/dse.c
index c88587e7d94..da0df54a2dd 100644
--- a/gcc/dse.c
+++ b/gcc/dse.c
@@ -2219,6 +2219,11 @@ check_mem_read_rtx (rtx *loc, bb_info_t bb_info)
}
if (maybe_ne (offset, 0))
mem_addr = plus_constant (get_address_mode (mem), mem_addr, offset);
+ /* Avoid passing VALUE RTXen as mem_addr to canon_true_dependence
+ which will over and over re-create proper RTL and re-apply the
+ offset above. See PR80960 where we almost allocate 1.6GB of PLUS
+ RTXen that way. */
+ mem_addr = get_addr (mem_addr);
if (group_id >= 0)
{