On Tue, Mar 22, 2011 at 08:30:47AM +0100, Andreas Krebbel wrote:
> Index: gcc/config/s390/s390.c
> ===================================================================
> *** gcc/config/s390/s390.c.orig
> --- gcc/config/s390/s390.c
> *************** s390_delegitimize_address (rtx orig_x)
> *** 5019,5025 ****
> /* Extract the symbol ref from:
> (plus:SI (reg:SI 12 %r12)
> (const:SI (unspec:SI [(symbol_ref/f:SI ("*.LC0"))]
> ! UNSPEC_GOTOFF))) */
> if (GET_CODE (x) == PLUS
> && REG_P (XEXP (x, 0))
> && REGNO (XEXP (x, 0)) == PIC_OFFSET_TABLE_REGNUM
> --- 5019,5030 ----
> /* Extract the symbol ref from:
> (plus:SI (reg:SI 12 %r12)
> (const:SI (unspec:SI [(symbol_ref/f:SI ("*.LC0"))]
> ! UNSPEC_GOTOFF/PLTOFF)))
> ! and
> ! (plus:SI (reg:SI 12 %r12)
> ! (const:SI (plus:SI (unspec:SI [(symbol_ref:SI ("L"))]
> ! UNSPEC_GOTOFF/PLTOFF)
> ! (const_int 4 [0x4])))) */
> if (GET_CODE (x) == PLUS
> && REG_P (XEXP (x, 0))
> && REGNO (XEXP (x, 0)) == PIC_OFFSET_TABLE_REGNUM
> *************** s390_delegitimize_address (rtx orig_x)
> *** 5027,5034 ****
> {
> /* The const operand. */
> y = XEXP (XEXP (x, 1), 0);
> if (GET_CODE (y) == UNSPEC
> ! && XINT (y, 1) == UNSPEC_GOTOFF)
> return XVECEXP (y, 0, 0);
> }
>
> --- 5032,5045 ----
> {
> /* The const operand. */
> y = XEXP (XEXP (x, 1), 0);
> +
> + if (GET_CODE (y) == PLUS
> + && GET_CODE (XEXP (y, 1)) == CONST_INT)
> + y = XEXP (y, 0);
This surprises me, you accept there arbitrary
offsets and throw them away. If it behaves like i?86 GOTOFF,
then I'd expect you want to remember the offset and
> +
> if (GET_CODE (y) == UNSPEC
> ! && (XINT (y, 1) == UNSPEC_GOTOFF
> ! || XINT (y, 1) == UNSPEC_PLTOFF))
> return XVECEXP (y, 0, 0);
return plus_constant (XVECEXP (y, 0, 0), offset);
here... Not sure what exactly PLTOFF with a constant
offset means though.
Jakub