mirror of
https://sourceware.org/git/binutils-gdb.git
synced 2025-01-19 06:23:36 +08:00
gas/
* config/tc-mips.c (enum small_ex_type): Remove. (imm_unmatched_hi): Remove. (md_assemble): Remove use of imm_unmatched_hi. Remove the last argument from calls to append_insn. (append_insn): Remove unmatched_hi parameter; check reloc_type[0] instead. (macro_build): Update append_insn calls. (mips16_macro_build, macro_build_lui): Likewise. (mips_ip): Rework handling of small expressions. Move explicit relocation handling into my_getSmallExpression. Assume that the value of 'o' operands is zero if there is only one bracketed expression left. (percent_op): Make constant. Record the BFD relocation code associated with each operator. (my_getSmallParser, my_getPercentOp): Remove. (parse_relocation): New function. (my_getSamllExpression): Rework. Fill in relocations here rather than in mips_ip. gas/testsuite * gas/mips/elf-rel8.[sd], gas/mips/elf-rel9.[sd], gas/mips/elf-rel10.[sd], gas/mips/elf-rel11.[sd]: New tests. * gas/mips/mips.exp: Run elf-rel8 and elf-rel9 for all elf targets. Run elf-rel10 and elf-rel11 for NewABI targets.
This commit is contained in:
parent
5f601589e1
commit
5e0116d519
@ -1,3 +1,24 @@
|
||||
2003-02-02 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* config/tc-mips.c (enum small_ex_type): Remove.
|
||||
(imm_unmatched_hi): Remove.
|
||||
(md_assemble): Remove use of imm_unmatched_hi. Remove the last
|
||||
argument from calls to append_insn.
|
||||
(append_insn): Remove unmatched_hi parameter; check reloc_type[0]
|
||||
instead.
|
||||
(macro_build): Update append_insn calls.
|
||||
(mips16_macro_build, macro_build_lui): Likewise.
|
||||
(mips_ip): Rework handling of small expressions. Move explicit
|
||||
relocation handling into my_getSmallExpression. Assume that the
|
||||
value of 'o' operands is zero if there is only one bracketed
|
||||
expression left.
|
||||
(percent_op): Make constant. Record the BFD relocation code
|
||||
associated with each operator.
|
||||
(my_getSmallParser, my_getPercentOp): Remove.
|
||||
(parse_relocation): New function.
|
||||
(my_getSamllExpression): Rework. Fill in relocations here
|
||||
rather than in mips_ip.
|
||||
|
||||
2003-01-29 Nick Clifton <nickc@redhat.com>
|
||||
|
||||
* config/tc-i386.c (line_comment_chars): Add '#'. This makes the
|
||||
|
@ -810,7 +810,7 @@ static void mips16_mark_labels
|
||||
PARAMS ((void));
|
||||
static void append_insn
|
||||
PARAMS ((char *place, struct mips_cl_insn * ip, expressionS * p,
|
||||
bfd_reloc_code_real_type *r, bfd_boolean));
|
||||
bfd_reloc_code_real_type *r));
|
||||
static void mips_no_prev_insn
|
||||
PARAMS ((int));
|
||||
static void mips_emit_delays
|
||||
@ -856,12 +856,10 @@ static void mips16_ip
|
||||
static void mips16_immed
|
||||
PARAMS ((char *, unsigned int, int, offsetT, bfd_boolean, bfd_boolean,
|
||||
bfd_boolean, unsigned long *, bfd_boolean *, unsigned short *));
|
||||
static int my_getPercentOp
|
||||
PARAMS ((char **, unsigned int *, int *));
|
||||
static int my_getSmallParser
|
||||
PARAMS ((char **, unsigned int *, int *));
|
||||
static int my_getSmallExpression
|
||||
PARAMS ((expressionS *, char *));
|
||||
static bfd_boolean parse_relocation
|
||||
PARAMS ((char **, bfd_reloc_code_real_type *));
|
||||
static size_t my_getSmallExpression
|
||||
PARAMS ((expressionS *, bfd_reloc_code_real_type *, char *));
|
||||
static void my_getExpression
|
||||
PARAMS ((expressionS *, char *));
|
||||
#ifdef OBJ_ELF
|
||||
@ -946,32 +944,6 @@ static int mips_need_elf_addend_fixup
|
||||
PARAMS ((fixS *));
|
||||
#endif
|
||||
|
||||
/* Return values of my_getSmallExpression(). */
|
||||
|
||||
enum small_ex_type
|
||||
{
|
||||
S_EX_NONE = 0,
|
||||
S_EX_REGISTER,
|
||||
|
||||
/* Direct relocation creation by %percent_op(). */
|
||||
S_EX_HALF,
|
||||
S_EX_HI,
|
||||
S_EX_LO,
|
||||
S_EX_GP_REL,
|
||||
S_EX_GOT,
|
||||
S_EX_CALL16,
|
||||
S_EX_GOT_DISP,
|
||||
S_EX_GOT_PAGE,
|
||||
S_EX_GOT_OFST,
|
||||
S_EX_GOT_HI,
|
||||
S_EX_GOT_LO,
|
||||
S_EX_NEG,
|
||||
S_EX_HIGHER,
|
||||
S_EX_HIGHEST,
|
||||
S_EX_CALL_HI,
|
||||
S_EX_CALL_LO
|
||||
};
|
||||
|
||||
/* Table and functions used to map between CPU/ISA names, and
|
||||
ISA levels, and CPU numbers. */
|
||||
|
||||
@ -1136,10 +1108,6 @@ static bfd_reloc_code_real_type imm_reloc[3]
|
||||
static bfd_reloc_code_real_type offset_reloc[3]
|
||||
= {BFD_RELOC_UNUSED, BFD_RELOC_UNUSED, BFD_RELOC_UNUSED};
|
||||
|
||||
/* This is set by mips_ip if imm_reloc is an unmatched HI16_S reloc. */
|
||||
|
||||
static bfd_boolean imm_unmatched_hi;
|
||||
|
||||
/* These are set by mips16_ip if an explicit extension is used. */
|
||||
|
||||
static bfd_boolean mips16_small, mips16_ext;
|
||||
@ -1430,7 +1398,6 @@ md_assemble (str)
|
||||
= {BFD_RELOC_UNUSED, BFD_RELOC_UNUSED, BFD_RELOC_UNUSED};
|
||||
|
||||
imm_expr.X_op = O_absent;
|
||||
imm_unmatched_hi = FALSE;
|
||||
offset_expr.X_op = O_absent;
|
||||
imm_reloc[0] = BFD_RELOC_UNUSED;
|
||||
imm_reloc[1] = BFD_RELOC_UNUSED;
|
||||
@ -1464,11 +1431,11 @@ md_assemble (str)
|
||||
else
|
||||
{
|
||||
if (imm_expr.X_op != O_absent)
|
||||
append_insn (NULL, &insn, &imm_expr, imm_reloc, imm_unmatched_hi);
|
||||
append_insn (NULL, &insn, &imm_expr, imm_reloc);
|
||||
else if (offset_expr.X_op != O_absent)
|
||||
append_insn (NULL, &insn, &offset_expr, offset_reloc, FALSE);
|
||||
append_insn (NULL, &insn, &offset_expr, offset_reloc);
|
||||
else
|
||||
append_insn (NULL, &insn, NULL, unused_reloc, FALSE);
|
||||
append_insn (NULL, &insn, NULL, unused_reloc);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1616,23 +1583,24 @@ mips16_mark_labels ()
|
||||
used with RELOC_TYPE. */
|
||||
|
||||
static void
|
||||
append_insn (place, ip, address_expr, reloc_type, unmatched_hi)
|
||||
append_insn (place, ip, address_expr, reloc_type)
|
||||
char *place;
|
||||
struct mips_cl_insn *ip;
|
||||
expressionS *address_expr;
|
||||
bfd_reloc_code_real_type *reloc_type;
|
||||
bfd_boolean unmatched_hi;
|
||||
{
|
||||
register unsigned long prev_pinfo, pinfo;
|
||||
char *f;
|
||||
fixS *fixp[3];
|
||||
int nops = 0;
|
||||
bfd_boolean unmatched_reloc_p;
|
||||
|
||||
/* Mark instruction labels in mips16 mode. */
|
||||
mips16_mark_labels ();
|
||||
|
||||
prev_pinfo = prev_insn.insn_mo->pinfo;
|
||||
pinfo = ip->insn_mo->pinfo;
|
||||
unmatched_reloc_p = FALSE;
|
||||
|
||||
if (place == NULL && (! mips_opts.noreorder || prev_nop_frag != NULL))
|
||||
{
|
||||
@ -2176,17 +2144,17 @@ append_insn (place, ip, address_expr, reloc_type, unmatched_hi)
|
||||
|| *reloc_type == BFD_RELOC_MIPS_RELGOT))
|
||||
fixp[0]->fx_no_overflow = 1;
|
||||
|
||||
if (unmatched_hi)
|
||||
if (reloc_type[0] == BFD_RELOC_HI16_S)
|
||||
{
|
||||
struct mips_hi_fixup *hi_fixup;
|
||||
|
||||
assert (*reloc_type == BFD_RELOC_HI16_S);
|
||||
hi_fixup = ((struct mips_hi_fixup *)
|
||||
xmalloc (sizeof (struct mips_hi_fixup)));
|
||||
hi_fixup->fixp = fixp[0];
|
||||
hi_fixup->seg = now_seg;
|
||||
hi_fixup->next = mips_hi_fixup_list;
|
||||
mips_hi_fixup_list = hi_fixup;
|
||||
unmatched_reloc_p = TRUE;
|
||||
}
|
||||
|
||||
if (reloc_type[1] != BFD_RELOC_UNUSED)
|
||||
@ -2743,7 +2711,7 @@ append_insn (place, ip, address_expr, reloc_type, unmatched_hi)
|
||||
reloc does not become a variant frag. Otherwise, the
|
||||
rearrangement of %hi relocs in frob_file may confuse
|
||||
tc_gen_reloc. */
|
||||
if (unmatched_hi)
|
||||
if (unmatched_reloc_p)
|
||||
{
|
||||
frag_wane (frag_now);
|
||||
frag_new (0);
|
||||
@ -3140,7 +3108,7 @@ macro_build (place, counter, ep, name, fmt, va_alist)
|
||||
va_end (args);
|
||||
assert (*r == BFD_RELOC_UNUSED ? ep == NULL : ep != NULL);
|
||||
|
||||
append_insn (place, &insn, ep, r, FALSE);
|
||||
append_insn (place, &insn, ep, r);
|
||||
}
|
||||
|
||||
static void
|
||||
@ -3266,7 +3234,7 @@ mips16_macro_build (place, counter, ep, name, fmt, args)
|
||||
|
||||
assert (*r == BFD_RELOC_UNUSED ? ep == NULL : ep != NULL);
|
||||
|
||||
append_insn (place, &insn, ep, r, FALSE);
|
||||
append_insn (place, &insn, ep, r);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -3356,10 +3324,10 @@ macro_build_lui (place, counter, ep, regnum)
|
||||
if (*r == BFD_RELOC_UNUSED)
|
||||
{
|
||||
insn.insn_opcode |= high_expr.X_add_number;
|
||||
append_insn (place, &insn, NULL, r, FALSE);
|
||||
append_insn (place, &insn, NULL, r);
|
||||
}
|
||||
else
|
||||
append_insn (place, &insn, &high_expr, r, FALSE);
|
||||
append_insn (place, &insn, &high_expr, r);
|
||||
}
|
||||
|
||||
/* Generate a sequence of instructions to do a load or store from a constant
|
||||
@ -9065,122 +9033,70 @@ mips_ip (str, ip)
|
||||
case 'i': /* 16 bit unsigned immediate */
|
||||
case 'j': /* 16 bit signed immediate */
|
||||
*imm_reloc = BFD_RELOC_LO16;
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
if (c != S_EX_NONE)
|
||||
{
|
||||
if (c != S_EX_LO)
|
||||
{
|
||||
if (c == S_EX_HI)
|
||||
{
|
||||
*imm_reloc = BFD_RELOC_HI16_S;
|
||||
imm_unmatched_hi = TRUE;
|
||||
}
|
||||
#ifdef OBJ_ELF
|
||||
else if (c == S_EX_HIGHEST)
|
||||
*imm_reloc = BFD_RELOC_MIPS_HIGHEST;
|
||||
else if (c == S_EX_HIGHER)
|
||||
*imm_reloc = BFD_RELOC_MIPS_HIGHER;
|
||||
else if (c == S_EX_GP_REL)
|
||||
{
|
||||
/* This occurs in NewABI only. */
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
if (c != S_EX_NEG)
|
||||
as_bad (_("bad composition of relocations"));
|
||||
else
|
||||
{
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
if (c != S_EX_LO)
|
||||
as_bad (_("bad composition of relocations"));
|
||||
else
|
||||
{
|
||||
imm_reloc[0] = BFD_RELOC_GPREL16;
|
||||
imm_reloc[1] = BFD_RELOC_MIPS_SUB;
|
||||
imm_reloc[2] = BFD_RELOC_LO16;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
else
|
||||
*imm_reloc = BFD_RELOC_HI16;
|
||||
}
|
||||
else if (imm_expr.X_op == O_constant)
|
||||
imm_expr.X_add_number &= 0xffff;
|
||||
}
|
||||
if (*args == 'i')
|
||||
{
|
||||
if ((c == S_EX_NONE && imm_expr.X_op != O_constant)
|
||||
|| ((imm_expr.X_add_number < 0
|
||||
|| imm_expr.X_add_number >= 0x10000)
|
||||
&& imm_expr.X_op == O_constant))
|
||||
{
|
||||
if (insn + 1 < &mips_opcodes[NUMOPCODES] &&
|
||||
!strcmp (insn->name, insn[1].name))
|
||||
break;
|
||||
if (imm_expr.X_op == O_constant
|
||||
|| imm_expr.X_op == O_big)
|
||||
as_bad (_("16 bit expression not in range 0..65535"));
|
||||
}
|
||||
}
|
||||
else
|
||||
if (my_getSmallExpression (&imm_expr, imm_reloc, s) == 0)
|
||||
{
|
||||
int more;
|
||||
offsetT max;
|
||||
offsetT minval, maxval;
|
||||
|
||||
/* The upper bound should be 0x8000, but
|
||||
unfortunately the MIPS assembler accepts numbers
|
||||
from 0x8000 to 0xffff and sign extends them, and
|
||||
we want to be compatible. We only permit this
|
||||
extended range for an instruction which does not
|
||||
provide any further alternates, since those
|
||||
alternates may handle other cases. People should
|
||||
use the numbers they mean, rather than relying on
|
||||
a mysterious sign extension. */
|
||||
more = (insn + 1 < &mips_opcodes[NUMOPCODES] &&
|
||||
strcmp (insn->name, insn[1].name) == 0);
|
||||
if (more)
|
||||
max = 0x8000;
|
||||
more = (insn + 1 < &mips_opcodes[NUMOPCODES]
|
||||
&& strcmp (insn->name, insn[1].name) == 0);
|
||||
|
||||
/* If the expression was written as an unsigned number,
|
||||
only treat it as signed if there are no more
|
||||
alternatives. */
|
||||
if (more
|
||||
&& *args == 'j'
|
||||
&& sizeof (imm_expr.X_add_number) <= 4
|
||||
&& imm_expr.X_op == O_constant
|
||||
&& imm_expr.X_add_number < 0
|
||||
&& imm_expr.X_unsigned
|
||||
&& HAVE_64BIT_GPRS)
|
||||
break;
|
||||
|
||||
/* For compatibility with older assemblers, we accept
|
||||
0x8000-0xffff as signed 16-bit numbers when only
|
||||
signed numbers are allowed. */
|
||||
if (*args == 'i')
|
||||
minval = 0, maxval = 0xffff;
|
||||
else if (more)
|
||||
minval = -0x8000, maxval = 0x7fff;
|
||||
else
|
||||
max = 0x10000;
|
||||
if ((c == S_EX_NONE && imm_expr.X_op != O_constant)
|
||||
|| ((imm_expr.X_add_number < -0x8000
|
||||
|| imm_expr.X_add_number >= max)
|
||||
&& imm_expr.X_op == O_constant)
|
||||
|| (more
|
||||
&& imm_expr.X_add_number < 0
|
||||
&& HAVE_64BIT_GPRS
|
||||
&& imm_expr.X_unsigned
|
||||
&& sizeof (imm_expr.X_add_number) <= 4))
|
||||
minval = -0x8000, maxval = 0xffff;
|
||||
|
||||
if (imm_expr.X_op != O_constant
|
||||
|| imm_expr.X_add_number < minval
|
||||
|| imm_expr.X_add_number > maxval)
|
||||
{
|
||||
if (more)
|
||||
break;
|
||||
if (imm_expr.X_op == O_constant
|
||||
|| imm_expr.X_op == O_big)
|
||||
as_bad (_("16 bit expression not in range -32768..32767"));
|
||||
as_bad (_("expression out of range"));
|
||||
}
|
||||
}
|
||||
s = expr_end;
|
||||
continue;
|
||||
|
||||
case 'o': /* 16 bit offset */
|
||||
c = my_getSmallExpression (&offset_expr, s);
|
||||
/* Check whether there is only a single bracketed expression
|
||||
left. If so, it must be the base register and the
|
||||
constant must be zero. */
|
||||
if (*s == '(' && strchr (s + 1, '(') == 0)
|
||||
{
|
||||
offset_expr.X_op = O_constant;
|
||||
offset_expr.X_add_number = 0;
|
||||
continue;
|
||||
}
|
||||
|
||||
/* If this value won't fit into a 16 bit offset, then go
|
||||
find a macro that will generate the 32 bit offset
|
||||
code pattern. */
|
||||
if (c == S_EX_NONE
|
||||
if (my_getSmallExpression (&offset_expr, offset_reloc, s) == 0
|
||||
&& (offset_expr.X_op != O_constant
|
||||
|| offset_expr.X_add_number >= 0x8000
|
||||
|| offset_expr.X_add_number < -0x8000))
|
||||
break;
|
||||
|
||||
if (c == S_EX_HI)
|
||||
{
|
||||
if (offset_expr.X_op != O_constant)
|
||||
break;
|
||||
offset_expr.X_add_number =
|
||||
(offset_expr.X_add_number >> 16) & 0xffff;
|
||||
}
|
||||
*offset_reloc = BFD_RELOC_LO16;
|
||||
s = expr_end;
|
||||
continue;
|
||||
|
||||
@ -9191,49 +9107,10 @@ mips_ip (str, ip)
|
||||
continue;
|
||||
|
||||
case 'u': /* upper 16 bits */
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
*imm_reloc = BFD_RELOC_LO16;
|
||||
if (c != S_EX_NONE)
|
||||
{
|
||||
if (c != S_EX_LO)
|
||||
{
|
||||
if (c == S_EX_HI)
|
||||
{
|
||||
*imm_reloc = BFD_RELOC_HI16_S;
|
||||
imm_unmatched_hi = TRUE;
|
||||
}
|
||||
#ifdef OBJ_ELF
|
||||
else if (c == S_EX_HIGHEST)
|
||||
*imm_reloc = BFD_RELOC_MIPS_HIGHEST;
|
||||
else if (c == S_EX_GP_REL)
|
||||
{
|
||||
/* This occurs in NewABI only. */
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
if (c != S_EX_NEG)
|
||||
as_bad (_("bad composition of relocations"));
|
||||
else
|
||||
{
|
||||
c = my_getSmallExpression (&imm_expr, s);
|
||||
if (c != S_EX_HI)
|
||||
as_bad (_("bad composition of relocations"));
|
||||
else
|
||||
{
|
||||
imm_reloc[0] = BFD_RELOC_GPREL16;
|
||||
imm_reloc[1] = BFD_RELOC_MIPS_SUB;
|
||||
imm_reloc[2] = BFD_RELOC_HI16_S;
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
else
|
||||
*imm_reloc = BFD_RELOC_HI16;
|
||||
}
|
||||
else if (imm_expr.X_op == O_constant)
|
||||
imm_expr.X_add_number &= 0xffff;
|
||||
}
|
||||
else if (imm_expr.X_op == O_constant
|
||||
&& (imm_expr.X_add_number < 0
|
||||
|| imm_expr.X_add_number >= 0x10000))
|
||||
if (my_getSmallExpression (&imm_expr, imm_reloc, s) == 0
|
||||
&& imm_expr.X_op == O_constant
|
||||
&& (imm_expr.X_add_number < 0
|
||||
|| imm_expr.X_add_number >= 0x10000))
|
||||
as_bad (_("lui expression not in range 0..65535"));
|
||||
s = expr_end;
|
||||
continue;
|
||||
@ -10070,222 +9947,118 @@ mips16_immed (file, line, type, val, warn, small, ext, insn, use_extend,
|
||||
}
|
||||
}
|
||||
|
||||
static struct percent_op_match
|
||||
static const struct percent_op_match
|
||||
{
|
||||
const char *str;
|
||||
const enum small_ex_type type;
|
||||
const char *str;
|
||||
bfd_reloc_code_real_type reloc;
|
||||
} percent_op[] =
|
||||
{
|
||||
{"%lo", S_EX_LO},
|
||||
{"%lo", BFD_RELOC_LO16},
|
||||
#ifdef OBJ_ELF
|
||||
{"%call_hi", S_EX_CALL_HI},
|
||||
{"%call_lo", S_EX_CALL_LO},
|
||||
{"%call16", S_EX_CALL16},
|
||||
{"%got_disp", S_EX_GOT_DISP},
|
||||
{"%got_page", S_EX_GOT_PAGE},
|
||||
{"%got_ofst", S_EX_GOT_OFST},
|
||||
{"%got_hi", S_EX_GOT_HI},
|
||||
{"%got_lo", S_EX_GOT_LO},
|
||||
{"%got", S_EX_GOT},
|
||||
{"%gp_rel", S_EX_GP_REL},
|
||||
{"%half", S_EX_HALF},
|
||||
{"%highest", S_EX_HIGHEST},
|
||||
{"%higher", S_EX_HIGHER},
|
||||
{"%neg", S_EX_NEG},
|
||||
{"%call_hi", BFD_RELOC_MIPS_CALL_HI16},
|
||||
{"%call_lo", BFD_RELOC_MIPS_CALL_LO16},
|
||||
{"%call16", BFD_RELOC_MIPS_CALL16},
|
||||
{"%got_disp", BFD_RELOC_MIPS_GOT_DISP},
|
||||
{"%got_page", BFD_RELOC_MIPS_GOT_PAGE},
|
||||
{"%got_ofst", BFD_RELOC_MIPS_GOT_OFST},
|
||||
{"%got_hi", BFD_RELOC_MIPS_GOT_HI16},
|
||||
{"%got_lo", BFD_RELOC_MIPS_GOT_LO16},
|
||||
{"%got", BFD_RELOC_MIPS_GOT16},
|
||||
{"%gp_rel", BFD_RELOC_GPREL16},
|
||||
{"%half", BFD_RELOC_16},
|
||||
{"%highest", BFD_RELOC_MIPS_HIGHEST},
|
||||
{"%higher", BFD_RELOC_MIPS_HIGHER},
|
||||
{"%neg", BFD_RELOC_MIPS_SUB},
|
||||
#endif
|
||||
{"%hi", S_EX_HI}
|
||||
{"%hi", BFD_RELOC_HI16_S}
|
||||
};
|
||||
|
||||
/* Parse small expression input. STR gets adjusted to eat up whitespace.
|
||||
It detects valid "%percent_op(...)" and "($reg)" strings. Percent_op's
|
||||
can be nested, this is handled by blanking the innermost, parsing the
|
||||
rest by subsequent calls. */
|
||||
|
||||
static int
|
||||
my_getSmallParser (str, len, nestlevel)
|
||||
/* Return true if *STR points to a relocation operator. When returning true,
|
||||
move *STR over the operator and store its relocation code in *RELOC.
|
||||
Leave both *STR and *RELOC alone when returning false. */
|
||||
|
||||
static bfd_boolean
|
||||
parse_relocation (str, reloc)
|
||||
char **str;
|
||||
unsigned int *len;
|
||||
int *nestlevel;
|
||||
bfd_reloc_code_real_type *reloc;
|
||||
{
|
||||
*len = 0;
|
||||
*str += strspn (*str, " \t");
|
||||
/* Check for expression in parentheses. */
|
||||
if (**str == '(')
|
||||
{
|
||||
char *b = *str + 1 + strspn (*str + 1, " \t");
|
||||
char *e;
|
||||
size_t i;
|
||||
|
||||
/* Check for base register. */
|
||||
if (b[0] == '$')
|
||||
{
|
||||
if (strchr (b, ')')
|
||||
&& (e = b + strcspn (b, ") \t"))
|
||||
&& e - b > 1 && e - b < 4)
|
||||
{
|
||||
if ((e - b == 3
|
||||
&& ((b[1] == 'f' && b[2] == 'p')
|
||||
|| (b[1] == 's' && b[2] == 'p')
|
||||
|| (b[1] == 'g' && b[2] == 'p')
|
||||
|| (b[1] == 'a' && b[2] == 't')
|
||||
|| (ISDIGIT (b[1])
|
||||
&& ISDIGIT (b[2]))))
|
||||
|| (ISDIGIT (b[1])))
|
||||
{
|
||||
*len = strcspn (*str, ")") + 1;
|
||||
return S_EX_REGISTER;
|
||||
}
|
||||
}
|
||||
}
|
||||
/* Check for percent_op (in parentheses). */
|
||||
else if (b[0] == '%')
|
||||
{
|
||||
*str = b;
|
||||
return my_getPercentOp (str, len, nestlevel);
|
||||
}
|
||||
|
||||
/* Some other expression in the parentheses, which can contain
|
||||
parentheses itself. Attempt to find the matching one. */
|
||||
for (i = 0; i < ARRAY_SIZE (percent_op); i++)
|
||||
if (strncasecmp (*str, percent_op[i].str, strlen (percent_op[i].str)) == 0)
|
||||
{
|
||||
int pcnt = 1;
|
||||
char *s;
|
||||
*str += strlen (percent_op[i].str);
|
||||
*reloc = percent_op[i].reloc;
|
||||
|
||||
*len = 1;
|
||||
for (s = *str + 1; *s && pcnt; s++, (*len)++)
|
||||
/* Check whether the output BFD supports this relocation.
|
||||
If not, issue an error and fall back on something safe. */
|
||||
if (!bfd_reloc_type_lookup (stdoutput, percent_op[i].reloc))
|
||||
{
|
||||
if (*s == '(')
|
||||
++pcnt;
|
||||
else if (*s == ')')
|
||||
--pcnt;
|
||||
as_bad ("relocation %s isn't supported by the current ABI",
|
||||
percent_op[i].str);
|
||||
*reloc = BFD_RELOC_LO16;
|
||||
}
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
/* Check for percent_op (outside of parentheses). */
|
||||
else if (*str[0] == '%')
|
||||
return my_getPercentOp (str, len, nestlevel);
|
||||
|
||||
/* Any other expression. */
|
||||
return S_EX_NONE;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
static int
|
||||
my_getPercentOp (str, len, nestlevel)
|
||||
char **str;
|
||||
unsigned int *len;
|
||||
int *nestlevel;
|
||||
{
|
||||
char *tmp = *str + 1;
|
||||
unsigned int i = 0;
|
||||
|
||||
while (ISALPHA (*tmp) || *tmp == '_')
|
||||
{
|
||||
*tmp = TOLOWER (*tmp);
|
||||
tmp++;
|
||||
}
|
||||
while (i < (sizeof (percent_op) / sizeof (struct percent_op_match)))
|
||||
{
|
||||
if (strncmp (*str, percent_op[i].str, strlen (percent_op[i].str)))
|
||||
i++;
|
||||
else
|
||||
{
|
||||
int type = percent_op[i].type;
|
||||
/* Parse string STR as a 16-bit relocatable operand. Store the
|
||||
expression in *EP and the relocations in the array starting
|
||||
at RELOC. Return the number of relocation operators used.
|
||||
|
||||
/* Only %hi and %lo are allowed for OldABI. */
|
||||
if (! HAVE_NEWABI && type != S_EX_HI && type != S_EX_LO)
|
||||
return S_EX_NONE;
|
||||
On exit, EXPR_END points to the first character after the expression.
|
||||
If no relocation operators are used, RELOC[0] is set to BFD_RELOC_LO16. */
|
||||
|
||||
*len = strlen (percent_op[i].str);
|
||||
++(*nestlevel);
|
||||
return type;
|
||||
}
|
||||
}
|
||||
return S_EX_NONE;
|
||||
}
|
||||
|
||||
static int
|
||||
my_getSmallExpression (ep, str)
|
||||
static size_t
|
||||
my_getSmallExpression (ep, reloc, str)
|
||||
expressionS *ep;
|
||||
bfd_reloc_code_real_type *reloc;
|
||||
char *str;
|
||||
{
|
||||
static char *oldstr = NULL;
|
||||
int c = S_EX_NONE;
|
||||
int oldc;
|
||||
int nestlevel = -1;
|
||||
unsigned int len;
|
||||
bfd_reloc_code_real_type reversed_reloc[3];
|
||||
size_t reloc_index, i;
|
||||
int bracket_depth;
|
||||
|
||||
/* Don't update oldstr if the last call had nested percent_op's. We need
|
||||
it to parse the outer ones later. */
|
||||
if (! oldstr)
|
||||
oldstr = str;
|
||||
reloc_index = 0;
|
||||
bracket_depth = 0;
|
||||
|
||||
do
|
||||
/* Search for the start of the main expression, recoding relocations
|
||||
in REVERSED_RELOC. */
|
||||
for (;;)
|
||||
{
|
||||
oldc = c;
|
||||
c = my_getSmallParser (&str, &len, &nestlevel);
|
||||
if (c != S_EX_NONE && c != S_EX_REGISTER)
|
||||
str += len;
|
||||
}
|
||||
while (c != S_EX_NONE && c != S_EX_REGISTER);
|
||||
|
||||
if (nestlevel >= 0)
|
||||
{
|
||||
/* A percent_op was encountered. Don't try to get an expression if
|
||||
it is already blanked out. */
|
||||
if (*(str + strspn (str + 1, " )")) != ')')
|
||||
{
|
||||
char save;
|
||||
|
||||
/* Let my_getExpression() stop at the closing parenthesis. */
|
||||
save = *(str + len);
|
||||
*(str + len) = '\0';
|
||||
my_getExpression (ep, str);
|
||||
*(str + len) = save;
|
||||
}
|
||||
if (nestlevel > 0)
|
||||
{
|
||||
/* Blank out including the % sign and the proper matching
|
||||
parenthesis. */
|
||||
int pcnt = 1;
|
||||
char *s = strrchr (oldstr, '%');
|
||||
char *end;
|
||||
|
||||
for (end = strchr (s, '(') + 1; *end && pcnt; end++)
|
||||
{
|
||||
if (*end == '(')
|
||||
++pcnt;
|
||||
else if (*end == ')')
|
||||
--pcnt;
|
||||
}
|
||||
|
||||
memset (s, ' ', end - s);
|
||||
str = oldstr;
|
||||
}
|
||||
if (*str == '(')
|
||||
bracket_depth++, str++;
|
||||
else if (*str == ' ' || *str == '\t')
|
||||
str++;
|
||||
else if (*str == '%'
|
||||
&& reloc_index < (HAVE_NEWABI ? 3 : 1)
|
||||
&& parse_relocation (&str, &reversed_reloc[reloc_index]))
|
||||
reloc_index++;
|
||||
else
|
||||
expr_end = str + len;
|
||||
|
||||
c = oldc;
|
||||
}
|
||||
else if (c == S_EX_NONE)
|
||||
{
|
||||
my_getExpression (ep, str);
|
||||
}
|
||||
else if (c == S_EX_REGISTER)
|
||||
{
|
||||
ep->X_op = O_constant;
|
||||
expr_end = str;
|
||||
ep->X_add_symbol = NULL;
|
||||
ep->X_op_symbol = NULL;
|
||||
ep->X_add_number = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
as_fatal (_("internal error"));
|
||||
break;
|
||||
}
|
||||
|
||||
if (nestlevel <= 0)
|
||||
/* All percent_op's have been handled. */
|
||||
oldstr = NULL;
|
||||
my_getExpression (ep, str);
|
||||
str = expr_end;
|
||||
|
||||
return c;
|
||||
/* Match every open bracket. */
|
||||
while (bracket_depth > 0 && (*str == ')' || *str == ' ' || *str == '\t'))
|
||||
if (*str++ == ')')
|
||||
bracket_depth--;
|
||||
|
||||
if (bracket_depth > 0)
|
||||
as_bad ("unclosed '('");
|
||||
|
||||
expr_end = str;
|
||||
|
||||
reloc[0] = BFD_RELOC_LO16;
|
||||
for (i = 0; i < reloc_index; i++)
|
||||
reloc[i] = reversed_reloc[reloc_index - 1 - i];
|
||||
|
||||
return reloc_index;
|
||||
}
|
||||
|
||||
static void
|
||||
|
@ -1,3 +1,10 @@
|
||||
2003-02-02 Richard Sandiford <rsandifo@redhat.com>
|
||||
|
||||
* gas/mips/elf-rel8.[sd], gas/mips/elf-rel9.[sd],
|
||||
gas/mips/elf-rel10.[sd], gas/mips/elf-rel11.[sd]: New tests.
|
||||
* gas/mips/mips.exp: Run elf-rel8 and elf-rel9 for all elf
|
||||
targets. Run elf-rel10 and elf-rel11 for NewABI targets.
|
||||
|
||||
2003-01-27 Alexandre Oliva <aoliva@redhat.com>
|
||||
|
||||
* gas/mips/n32-consec.d: New.
|
||||
|
29
gas/testsuite/gas/mips/elf-rel10.d
Normal file
29
gas/testsuite/gas/mips/elf-rel10.d
Normal file
@ -0,0 +1,29 @@
|
||||
#as: -march=mips3 -mabi=n32 -KPIC
|
||||
#readelf: --relocs
|
||||
#name: MIPS ELF reloc 10
|
||||
|
||||
Relocation section '\.rela\.text' at offset .* contains 22 entries:
|
||||
*Offset * Info * Type * Sym\.Value * Sym\. Name \+ Addend
|
||||
0+0000 * 0+..07 * R_MIPS_GPREL16 * 0+0000 * foo \+ 0
|
||||
0+0000 * 0+0018 * R_MIPS_SUB * 0+0000
|
||||
0+0000 * 0+0005 * R_MIPS_HI16 * 0+0000
|
||||
0+0004 * 0+..07 * R_MIPS_GPREL16 * 0+0000 * foo \+ 0
|
||||
0+0004 * 0+0018 * R_MIPS_SUB * 0+0000
|
||||
0+0004 * 0+0006 * R_MIPS_LO16 * 0+0000
|
||||
0+000c * 0+..07 * R_MIPS_GPREL16 * 0+0000 * \.text \+ c
|
||||
0+000c * 0+0018 * R_MIPS_SUB * 0+0000
|
||||
0+000c * 0+0005 * R_MIPS_HI16 * 0+0000
|
||||
0+0010 * 0+..07 * R_MIPS_GPREL16 * 0+0000 * \.text \+ c
|
||||
0+0010 * 0+0018 * R_MIPS_SUB * 0+0000
|
||||
0+0010 * 0+0006 * R_MIPS_LO16 * 0+0000
|
||||
0+0018 * 0+..14 * R_MIPS_GOT_PAGE * 0+0000 * foo \+ 0
|
||||
0+001c * 0+..15 * R_MIPS_GOT_OFST * 0+0000 * foo \+ 0
|
||||
0+0020 * 0+..14 * R_MIPS_GOT_PAGE * 0+0000 * foo \+ 1234
|
||||
0+0024 * 0+..15 * R_MIPS_GOT_OFST * 0+0000 * foo \+ 1234
|
||||
0+0028 * 0+..14 * R_MIPS_GOT_PAGE * 0+0000 * \.text \+ c
|
||||
0+002c * 0+..15 * R_MIPS_GOT_OFST * 0+0000 * \.text \+ c
|
||||
0+0030 * 0+..14 * R_MIPS_GOT_PAGE * 0+0000 * \.text \+ 33221d
|
||||
0+0034 * 0+..15 * R_MIPS_GOT_OFST * 0+0000 * \.text \+ 33221d
|
||||
0+0038 * 0+..14 * R_MIPS_GOT_PAGE * 0+0000 * frob \+ 0
|
||||
0+003c * 0+..15 * R_MIPS_GOT_OFST * 0+0000 * frob \+ 0
|
||||
#pass
|
31
gas/testsuite/gas/mips/elf-rel10.s
Normal file
31
gas/testsuite/gas/mips/elf-rel10.s
Normal file
@ -0,0 +1,31 @@
|
||||
.globl foo
|
||||
.ent foo
|
||||
foo:
|
||||
lui $gp,%hi(%neg(%gp_rel(foo)))
|
||||
addiu $gp,$gp,%lo(%neg(%gp_rel(foo)))
|
||||
daddu $gp,$gp,$25
|
||||
.end foo
|
||||
|
||||
.ent bar
|
||||
bar:
|
||||
lui $gp,%hi(%neg(%gp_rel(bar)))
|
||||
addiu $gp,$gp,%lo(%neg(%gp_rel(bar)))
|
||||
daddu $gp,$gp,$25
|
||||
.end bar
|
||||
|
||||
.ent frob
|
||||
lw $4,%got_page(foo)($gp)
|
||||
addiu $4,$4,%got_ofst(foo)
|
||||
|
||||
lw $4,%got_page(foo + 0x1234)($gp)
|
||||
addiu $4,$4,%got_ofst(foo + 0x1234)
|
||||
|
||||
lw $4,%got_page(bar)($gp)
|
||||
addiu $4,$4,%got_ofst(bar)
|
||||
|
||||
lw $4,%got_page(bar + 0x332211)($gp)
|
||||
addiu $4,$4,%got_ofst(bar + 0x332211)
|
||||
|
||||
lw $4,%got_page(frob)($gp)
|
||||
addiu $4,$4,%got_ofst(frob)
|
||||
.end frob
|
43
gas/testsuite/gas/mips/elf-rel11.d
Normal file
43
gas/testsuite/gas/mips/elf-rel11.d
Normal file
@ -0,0 +1,43 @@
|
||||
#as: -march=mips3 -mabi=64
|
||||
#readelf: --relocs
|
||||
#name: MIPS ELF reloc 11
|
||||
|
||||
Relocation section '\.rela\.text' at offset .* contains 12 entries:
|
||||
*Offset * Info * Type * Sym\. Value * Sym\. Name \+ Addend
|
||||
0+0000 * 0+..0000001d * R_MIPS_HIGHEST * 0+0000 * bar \+ 0
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0008 * 0+..0000001c * R_MIPS_HIGHER * 0+0000 * bar \+ 0
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0004 * 0+..00000005 * R_MIPS_HI16 * 0+0000 * bar \+ 0
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+000c * 0+..00000006 * R_MIPS_LO16 * 0+0000 * bar \+ 0
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0018 * 0+..0000001d * R_MIPS_HIGHEST * 0+0000 * bar \+ 12345678
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0020 * 0+..0000001c * R_MIPS_HIGHER * 0+0000 * bar \+ 12345678
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+001c * 0+..00000005 * R_MIPS_HI16 * 0+0000 * bar \+ 12345678
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0024 * 0+..00000006 * R_MIPS_LO16 * 0+0000 * bar \+ 12345678
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0030 * 0+..0000001d * R_MIPS_HIGHEST * 0+0000 * \.data \+ 10
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0034 * 0+..0000001c * R_MIPS_HIGHER * 0+0000 * \.data \+ 10
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+003c * 0+..00000005 * R_MIPS_HI16 * 0+0000 * \.data \+ 10
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
0+0044 * 0+..00000006 * R_MIPS_LO16 * 0+0000 * \.data \+ 10
|
||||
* Type2: R_MIPS_NONE *
|
||||
* Type3: R_MIPS_NONE *
|
||||
#pass
|
27
gas/testsuite/gas/mips/elf-rel11.s
Normal file
27
gas/testsuite/gas/mips/elf-rel11.s
Normal file
@ -0,0 +1,27 @@
|
||||
.ent foo
|
||||
foo:
|
||||
lui $4,%highest(bar)
|
||||
lui $5,%hi(bar)
|
||||
daddiu $4,$4,%higher(bar)
|
||||
daddiu $5,$5,%lo(bar)
|
||||
dsll32 $4,$4,0
|
||||
daddu $4,$4,$5
|
||||
|
||||
lui $4,%highest(bar + 0x12345678)
|
||||
lui $5,%hi(bar + 0x12345678)
|
||||
daddiu $4,$4,%higher(bar + 0x12345678)
|
||||
daddiu $5,$5,%lo(bar + 0x12345678)
|
||||
dsll32 $4,$4,0
|
||||
daddu $4,$4,$5
|
||||
|
||||
lui $4,%highest(l1)
|
||||
daddiu $4,$4,%higher(l1)
|
||||
dsll $4,$4,16
|
||||
daddiu $4,$4,%hi(l1)
|
||||
dsll $4,$4,16
|
||||
lw $4,%lo(l1)($4)
|
||||
.end foo
|
||||
|
||||
.data
|
||||
.word 1,2,3,4
|
||||
l1: .word 4,5
|
57
gas/testsuite/gas/mips/elf-rel8.d
Normal file
57
gas/testsuite/gas/mips/elf-rel8.d
Normal file
@ -0,0 +1,57 @@
|
||||
#as: -march=mips2 -mabi=32
|
||||
#objdump: -M gpr-names=numeric -dr
|
||||
#name: MIPS ELF reloc 8
|
||||
|
||||
.*: file format .*
|
||||
|
||||
Disassembly of section \.text:
|
||||
|
||||
0+00 <foo>:
|
||||
0: 3c040000 lui \$4,0x0
|
||||
0: R_MIPS_HI16 gvar
|
||||
4: 24840000 addiu \$4,\$4,0
|
||||
4: R_MIPS_LO16 gvar
|
||||
8: 8ca40000 lw \$4,0\(\$5\)
|
||||
8: R_MIPS_LO16 gvar
|
||||
c: 8fc40002 lw \$4,2\(\$30\)
|
||||
10: 3c040000 lui \$4,0x0
|
||||
10: R_MIPS_CALL_HI16 gfunc
|
||||
14: 009c2021 addu \$4,\$4,\$28
|
||||
18: 8c990000 lw \$25,0\(\$4\)
|
||||
18: R_MIPS_CALL_LO16 gfunc
|
||||
1c: 3c040000 lui \$4,0x0
|
||||
1c: R_MIPS_GOT_HI16 gvar
|
||||
20: 009c2021 addu \$4,\$4,\$28
|
||||
24: 8c850000 lw \$5,0\(\$4\)
|
||||
24: R_MIPS_GOT_LO16 gvar
|
||||
28: 8f840000 lw \$4,0\(\$28\)
|
||||
28: R_MIPS_GOT16 \.data
|
||||
2c: a0850000 sb \$5,0\(\$4\)
|
||||
2c: R_MIPS_LO16 \.data
|
||||
30: 3c040000 lui \$4,0x0
|
||||
30: R_MIPS_CALL_HI16 gfunc
|
||||
34: 24840000 addiu \$4,\$4,0
|
||||
34: R_MIPS_CALL_LO16 gfunc
|
||||
38: 3c040000 lui \$4,0x0
|
||||
38: R_MIPS_GOT_HI16 gvar
|
||||
3c: 24840000 addiu \$4,\$4,0
|
||||
3c: R_MIPS_GOT_LO16 gvar
|
||||
40: 8f840000 lw \$4,0\(\$28\)
|
||||
40: R_MIPS_GOT16 \.data
|
||||
44: 24840000 addiu \$4,\$4,0
|
||||
44: R_MIPS_LO16 \.data
|
||||
48: 8f990000 lw \$25,0\(\$28\)
|
||||
48: R_MIPS_CALL16 gfunc
|
||||
4c: 27840000 addiu \$4,\$28,0
|
||||
4c: R_MIPS_CALL16 gfunc
|
||||
50: 8f840000 lw \$4,0\(\$28\)
|
||||
50: R_MIPS_GOT_DISP gvar
|
||||
54: 27840000 addiu \$4,\$28,0
|
||||
54: R_MIPS_GOT_DISP gvar
|
||||
58: 8f840000 lw \$4,0\(\$28\)
|
||||
58: R_MIPS_GPREL16 gvar
|
||||
5c: af840000 sw \$4,0\(\$28\)
|
||||
5c: R_MIPS_GPREL16 gvar
|
||||
60: 27840000 addiu \$4,\$28,0
|
||||
60: R_MIPS_GPREL16 gvar
|
||||
\.\.\.
|
53
gas/testsuite/gas/mips/elf-rel8.s
Normal file
53
gas/testsuite/gas/mips/elf-rel8.s
Normal file
@ -0,0 +1,53 @@
|
||||
.equ $fprel, 2
|
||||
|
||||
.ent foo
|
||||
foo:
|
||||
# Test various forms of relocation syntax.
|
||||
|
||||
lui $4,(%hi gvar)
|
||||
addiu $4,$4,(%lo (gvar))
|
||||
lw $4,%lo gvar($5)
|
||||
|
||||
# Check that registers aren't confused with $ identifiers.
|
||||
|
||||
lw $4,($fprel)($fp)
|
||||
|
||||
# Check various forms of paired relocations.
|
||||
|
||||
lui $4,%call_hi(gfunc)
|
||||
addu $4,$4,$gp
|
||||
lw $25,%call_lo(gfunc)($4)
|
||||
|
||||
lui $4,%got_hi(gvar)
|
||||
addu $4,$4,$gp
|
||||
lw $5,%got_lo(gvar)($4)
|
||||
|
||||
lw $4,%got(lvar)($28)
|
||||
sb $5,%lo(lvar)($4)
|
||||
|
||||
lui $4,%call_hi(gfunc)
|
||||
addiu $4,$4,%call_lo(gfunc)
|
||||
|
||||
lui $4,%got_hi(gvar)
|
||||
addiu $4,$4,%got_lo(gvar)
|
||||
|
||||
lw $4,%got(lvar)($28)
|
||||
addiu $4,$4,%lo(lvar)
|
||||
|
||||
# Check individual relocations.
|
||||
|
||||
lw $25,%call16(gfunc)($28)
|
||||
addiu $4,$28,%call16(gfunc)
|
||||
|
||||
lw $4,%got_disp(gvar)($28)
|
||||
addiu $4,$28,%got_disp(gvar)
|
||||
|
||||
lw $4,%gp_rel(gvar)($28)
|
||||
sw $4,%gp_rel(gvar)($28)
|
||||
addiu $4,$28,%gp_rel(gvar)
|
||||
|
||||
.space 64
|
||||
.end foo
|
||||
|
||||
.data
|
||||
lvar: .word 1,2
|
68
gas/testsuite/gas/mips/elf-rel9.d
Normal file
68
gas/testsuite/gas/mips/elf-rel9.d
Normal file
@ -0,0 +1,68 @@
|
||||
#as: -march=mips2 -mabi=32
|
||||
#objdump: -M gpr-names=numeric -dr
|
||||
#name: MIPS ELF reloc 9
|
||||
|
||||
.*: file format .*
|
||||
|
||||
Disassembly of section \.text:
|
||||
|
||||
0+00 <foo>:
|
||||
0: 8f840000 lw \$4,0\(\$28\)
|
||||
0: R_MIPS_GOT16 \.data
|
||||
4: 24840010 addiu \$4,\$4,16
|
||||
4: R_MIPS_LO16 \.data
|
||||
8: 8f840000 lw \$4,0\(\$28\)
|
||||
8: R_MIPS_GOT16 \.data
|
||||
c: 24840020 addiu \$4,\$4,32
|
||||
c: R_MIPS_LO16 \.data
|
||||
10: 8f840000 lw \$4,0\(\$28\)
|
||||
10: R_MIPS_GOT16 \.data
|
||||
14: 24847ffc addiu \$4,\$4,32764
|
||||
14: R_MIPS_LO16 \.data
|
||||
18: 8f840001 lw \$4,1\(\$28\)
|
||||
18: R_MIPS_GOT16 \.data
|
||||
1c: 24848000 addiu \$4,\$4,-32768
|
||||
1c: R_MIPS_LO16 \.data
|
||||
20: 8f840001 lw \$4,1\(\$28\)
|
||||
20: R_MIPS_GOT16 \.data
|
||||
24: 2484fffc addiu \$4,\$4,-4
|
||||
24: R_MIPS_LO16 \.data
|
||||
28: 8f840001 lw \$4,1\(\$28\)
|
||||
28: R_MIPS_GOT16 \.data
|
||||
2c: 24840000 addiu \$4,\$4,0
|
||||
2c: R_MIPS_LO16 \.data
|
||||
30: 8f840002 lw \$4,2\(\$28\)
|
||||
30: R_MIPS_GOT16 \.data
|
||||
34: 24848010 addiu \$4,\$4,-32752
|
||||
34: R_MIPS_LO16 \.data
|
||||
38: 8f840002 lw \$4,2\(\$28\)
|
||||
38: R_MIPS_GOT16 \.data
|
||||
3c: 2484f000 addiu \$4,\$4,-4096
|
||||
3c: R_MIPS_LO16 \.data
|
||||
40: 8f840002 lw \$4,2\(\$28\)
|
||||
40: R_MIPS_GOT16 \.data
|
||||
44: 2484ffff addiu \$4,\$4,-1
|
||||
44: R_MIPS_LO16 \.data
|
||||
48: 8f840002 lw \$4,2\(\$28\)
|
||||
48: R_MIPS_GOT16 \.data
|
||||
4c: 2484f100 addiu \$4,\$4,-3840
|
||||
4c: R_MIPS_LO16 \.data
|
||||
50: 8f840003 lw \$4,3\(\$28\)
|
||||
50: R_MIPS_GOT16 \.data
|
||||
54: 24841345 addiu \$4,\$4,4933
|
||||
54: R_MIPS_LO16 \.data
|
||||
58: 8f84c000 lw \$4,-16384\(\$28\)
|
||||
58: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
5c: 8f84c004 lw \$4,-16380\(\$28\)
|
||||
5c: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
60: 8f84c004 lw \$4,-16380\(\$28\)
|
||||
60: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
64: 8f84c008 lw \$4,-16376\(\$28\)
|
||||
64: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
68: 8f84c00c lw \$4,-16372\(\$28\)
|
||||
68: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
6c: 8f84c014 lw \$4,-16364\(\$28\)
|
||||
6c: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
70: 8f84c018 lw \$4,-16360\(\$28\)
|
||||
70: R_MIPS_GPREL16 \.sdata\+0x4000
|
||||
\.\.\.
|
57
gas/testsuite/gas/mips/elf-rel9.s
Normal file
57
gas/testsuite/gas/mips/elf-rel9.s
Normal file
@ -0,0 +1,57 @@
|
||||
.ent foo
|
||||
foo:
|
||||
lw $4,%got(l1)($28)
|
||||
addiu $4,$4,%lo(l1)
|
||||
|
||||
lw $4,%got(l1 + 16)($28)
|
||||
addiu $4,$4,%lo(l1 + 16)
|
||||
|
||||
lw $4,%got(l1 + 0x7fec)($28)
|
||||
addiu $4,$4,%lo(l1 + 0x7fec)
|
||||
|
||||
lw $4,%got(l1 + 0x7ff0)($28)
|
||||
addiu $4,$4,%lo(l1 + 0x7ff0)
|
||||
|
||||
lw $4,%got(l1 + 0xffec)($28)
|
||||
addiu $4,$4,%lo(l1 + 0xffec)
|
||||
|
||||
lw $4,%got(l1 + 0xfff0)($28)
|
||||
addiu $4,$4,%lo(l1 + 0xfff0)
|
||||
|
||||
lw $4,%got(l1 + 0x18000)($28)
|
||||
addiu $4,$4,%lo(l1 + 0x18000)
|
||||
|
||||
lw $4,%got(l2)($28)
|
||||
addiu $4,$4,%lo(l2)
|
||||
|
||||
lw $4,%got(l2 + 0xfff)($28)
|
||||
addiu $4,$4,%lo(l2 + 0xfff)
|
||||
|
||||
lw $4,%got(l2 + 0x1000)($28)
|
||||
addiu $4,$4,%lo(l2 + 0x100)
|
||||
|
||||
lw $4,%got(l2 + 0x12345)($28)
|
||||
addiu $4,$4,%lo(l2 + 0x12345)
|
||||
|
||||
lw $4,%gp_rel(l3)($28)
|
||||
lw $4,%gp_rel(l3 + 4)($28)
|
||||
lw $4,%gp_rel(l4)($28)
|
||||
lw $4,%gp_rel(l4 + 4)($28)
|
||||
lw $4,%gp_rel(l5)($28)
|
||||
lw $4,%gp_rel(l5 + 8)($28)
|
||||
lw $4,%gp_rel(l5 + 12)($28)
|
||||
|
||||
.space 64
|
||||
.end foo
|
||||
|
||||
.data
|
||||
.word 1,2,3,4
|
||||
l1: .word 4,5
|
||||
.space 0x1f000 - 24
|
||||
l2: .word 7,8
|
||||
|
||||
.sdata
|
||||
l3: .word 1
|
||||
l4: .word 2
|
||||
.word 3
|
||||
l5: .word 4
|
@ -376,7 +376,7 @@ if { [istarget mips*-*-*] } then {
|
||||
set ilocks [istarget mipstx39*-*-*]
|
||||
set gpr_ilocks [expr [istarget mipstx39*-*-*]]
|
||||
set addr32 [expr [istarget mipstx39*-*-*]]
|
||||
set hasn32 [expr [istarget *-*-irix6*] || [istarget mips64*-*-linux*]]
|
||||
set has_newabi [expr [istarget *-*-irix6*] || [istarget mips64*-*-linux*]]
|
||||
|
||||
if { [istarget "mips*-*-*linux*"] } then {
|
||||
set tmips "t"
|
||||
@ -602,6 +602,12 @@ if { [istarget mips*-*-*] } then {
|
||||
run_dump_test "elf-rel5"
|
||||
run_dump_test "elf-rel6"
|
||||
run_dump_test "elf-rel7"
|
||||
run_dump_test "elf-rel8"
|
||||
run_dump_test "elf-rel9"
|
||||
if $has_newabi {
|
||||
run_dump_test "elf-rel10"
|
||||
run_dump_test "elf-rel11"
|
||||
}
|
||||
run_dump_test "${tmips}${el}empic"
|
||||
run_dump_test "empic2"
|
||||
run_dump_test "empic3_e"
|
||||
@ -614,7 +620,7 @@ if { [istarget mips*-*-*] } then {
|
||||
run_dump_test "elf-consthilo"
|
||||
}
|
||||
|
||||
if $hasn32 {
|
||||
if $has_newabi {
|
||||
run_dump_test "n32-consec"
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user