* config/tc-mips.c (append_insn): In a compound relocation, take the

field width from the final (outermost) operator.
This commit is contained in:
Richard Sandiford 2003-06-12 05:45:50 +00:00
parent 7282305265
commit 34ce925ee0
6 changed files with 55 additions and 73 deletions

View File

@ -1,3 +1,8 @@
2003-06-12 Richard Sandiford <rsandifo@redhat.com>
* config/tc-mips.c (append_insn): In a compound relocation, take the
field width from the final (outermost) operator.
2003-06-11 Richard Henderson <rth@redhat.com>
* dw2gencfi.c (struct cfi_escape_data): New.

View File

@ -2154,13 +2154,20 @@ append_insn (place, ip, address_expr, reloc_type)
}
else
{
reloc_howto_type *howto;
need_reloc:
/* Don't generate a reloc if we are writing into a variant frag. */
if (place == NULL)
{
howto = bfd_reloc_type_lookup (stdoutput, reloc_type[0]);
reloc_howto_type *howto;
int i;
/* In a compound relocation, it is the final (outermost)
operator that determines the relocated field. */
for (i = 1; i < 3; i++)
if (reloc_type[i] == BFD_RELOC_UNUSED)
break;
howto = bfd_reloc_type_lookup (stdoutput, reloc_type[i - 1]);
fixp[0] = fix_new_exp (frag_now, f - frag_now->fr_literal,
bfd_get_reloc_size(howto),
address_expr,
@ -2207,77 +2214,22 @@ append_insn (place, ip, address_expr, reloc_type)
hi_fixup->seg = now_seg;
}
if (reloc_type[1] != BFD_RELOC_UNUSED)
{
/* FIXME: This symbol can be one of
RSS_UNDEF, RSS_GP, RSS_GP0, RSS_LOC. */
address_expr->X_op = O_absent;
address_expr->X_add_symbol = 0;
address_expr->X_add_number = 0;
/* Add fixups for the second and third relocations, if given.
Note that the ABI allows the second relocation to be
against RSS_UNDEF, RSS_GP, RSS_GP0 or RSS_LOC. At the
moment we only use RSS_UNDEF, but we could add support
for the others if it ever becomes necessary. */
for (i = 1; i < 3; i++)
if (reloc_type[i] != BFD_RELOC_UNUSED)
{
address_expr->X_op = O_absent;
address_expr->X_add_symbol = 0;
address_expr->X_add_number = 0;
howto = bfd_reloc_type_lookup (stdoutput, reloc_type[1]);
fixp[1] = fix_new_exp (frag_now, f - frag_now->fr_literal,
bfd_get_reloc_size(howto),
address_expr, FALSE, reloc_type[1]);
/* These relocations can have an addend that won't fit in
4 octets for 64bit assembly. */
if (HAVE_64BIT_GPRS
&& ! howto->partial_inplace
&& (reloc_type[1] == BFD_RELOC_16
|| reloc_type[1] == BFD_RELOC_32
|| reloc_type[1] == BFD_RELOC_MIPS_JMP
|| reloc_type[1] == BFD_RELOC_HI16_S
|| reloc_type[1] == BFD_RELOC_LO16
|| reloc_type[1] == BFD_RELOC_GPREL16
|| reloc_type[1] == BFD_RELOC_MIPS_LITERAL
|| reloc_type[1] == BFD_RELOC_GPREL32
|| reloc_type[1] == BFD_RELOC_64
|| reloc_type[1] == BFD_RELOC_CTOR
|| reloc_type[1] == BFD_RELOC_MIPS_SUB
|| reloc_type[1] == BFD_RELOC_MIPS_HIGHEST
|| reloc_type[1] == BFD_RELOC_MIPS_HIGHER
|| reloc_type[1] == BFD_RELOC_MIPS_SCN_DISP
|| reloc_type[1] == BFD_RELOC_MIPS_REL16
|| reloc_type[1] == BFD_RELOC_MIPS_RELGOT))
fixp[1]->fx_no_overflow = 1;
if (reloc_type[2] != BFD_RELOC_UNUSED)
{
address_expr->X_op = O_absent;
address_expr->X_add_symbol = 0;
address_expr->X_add_number = 0;
howto = bfd_reloc_type_lookup (stdoutput, reloc_type[2]);
fixp[2] = fix_new_exp (frag_now,
f - frag_now->fr_literal,
bfd_get_reloc_size(howto),
address_expr, FALSE,
reloc_type[2]);
/* These relocations can have an addend that won't fit in
4 octets for 64bit assembly. */
if (HAVE_64BIT_GPRS
&& ! howto->partial_inplace
&& (reloc_type[2] == BFD_RELOC_16
|| reloc_type[2] == BFD_RELOC_32
|| reloc_type[2] == BFD_RELOC_MIPS_JMP
|| reloc_type[2] == BFD_RELOC_HI16_S
|| reloc_type[2] == BFD_RELOC_LO16
|| reloc_type[2] == BFD_RELOC_GPREL16
|| reloc_type[2] == BFD_RELOC_MIPS_LITERAL
|| reloc_type[2] == BFD_RELOC_GPREL32
|| reloc_type[2] == BFD_RELOC_64
|| reloc_type[2] == BFD_RELOC_CTOR
|| reloc_type[2] == BFD_RELOC_MIPS_SUB
|| reloc_type[2] == BFD_RELOC_MIPS_HIGHEST
|| reloc_type[2] == BFD_RELOC_MIPS_HIGHER
|| reloc_type[2] == BFD_RELOC_MIPS_SCN_DISP
|| reloc_type[2] == BFD_RELOC_MIPS_REL16
|| reloc_type[2] == BFD_RELOC_MIPS_RELGOT))
fixp[2]->fx_no_overflow = 1;
}
}
fixp[i] = fix_new_exp (frag_now, fixp[0]->fx_where,
fixp[0]->fx_size, address_expr,
FALSE, reloc_type[i]);
}
}
}
}

View File

@ -1,3 +1,8 @@
2003-06-12 Richard Sandiford <rsandifo@redhat.com>
* gas/mips/elf-rel15.[sd]: New test.
* gas/mips/mips.exp: Run it.
2003-06-11 Richard Henderson <rth@redhat.com>
* gas/cfi/cfi-common-3.[ds]: New.

View File

@ -0,0 +1,14 @@
#objdump: -dr
#as: -mabi=n32 -mips3
.*: file format .*
Disassembly of section \.text:
00000000 <foo>:
0: 3c020000 lui v0,0x0
0: R_MIPS_GPREL16 \.text
0: R_MIPS_SUB \*ABS\*
0: R_MIPS_HI16 \*ABS\*
4: 23bdffe4 addi sp,sp,-28
...

View File

@ -0,0 +1,4 @@
foo:
lui $2,%hi(%neg(%gp_rel(foo)))
sub $sp,$sp,28
.space 16

View File

@ -645,6 +645,8 @@ if { [istarget mips*-*-*] } then {
run_dump_test "elf-rel14"
if $has_newabi {
run_dump_test "elf-rel15"
run_dump_test "elf-rel-got-n32"
run_dump_test "elf-rel-xgot-n32"
run_dump_test "elf-rel-got-n64"