This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
reload displacement optimization
- To: egcs at cygnus dot com
- Subject: reload displacement optimization
- From: Richard Henderson <rth at cygnus dot com>
- Date: Tue, 10 Mar 1998 00:04:21 -0800
- Reply-To: Richard Henderson <rth at cygnus dot com>
While looking into some problems in reload this evening (which I could
not reproduce, annoyingly), I noticed that reload would produce, when
a displacement off of a base register is out of range,
lda $6,-31856
ldah $6,1($6)
addq $6,$30,$6
ldq $12,0($6)
when
ldah $6,1($30)
ldq $12,-31856($6)
is sufficient.
The solution, I believe, is to teach find_reloads_address about
this new way to break up an address. The following patch does this,
but in a blatently machine dependent way.
Can anyone think of a way to properly conditionalize this, and
to break up the address?
r~
Index: reload.c
===================================================================
RCS file: /egcs/carton/cvsfiles/egcs/gcc/reload.c,v
retrieving revision 1.16
diff -c -p -d -r1.16 reload.c
*** reload.c 1998/03/05 02:42:22 1.16
--- reload.c 1998/03/10 07:46:35
*************** find_reloads_address (mode, memrefloc, a
*** 4490,4495 ****
--- 4490,4513 ----
reload_address_index_reg_class,
GET_MODE (ad), opnum, type, ind_levels);
}
+ else if (1)
+ {
+ HOST_WIDE_INT val = INTVAL (XEXP (ad, 1));
+ HOST_WIDE_INT low = (val & 0xffff) - 2 * (val & 0x8000);
+ HOST_WIDE_INT rest = val - low;
+
+ /* Reload the high part into a base reg; leave the low part
+ in the mem directly. */
+
+ *loc = ad = gen_rtx_PLUS (GET_MODE (ad),
+ gen_rtx_PLUS (GET_MODE (ad), XEXP (ad, 0),
+ GEN_INT (rest)),
+ GEN_INT (low));
+
+ find_reloads_address_part (XEXP (ad, 0), &XEXP (ad, 0),
+ reload_address_base_reg_class,
+ GET_MODE (ad), opnum, type, ind_levels);
+ }
else
{
/* If the sum of two regs is not necessarily valid,