aboutsummaryrefslogtreecommitdiff
path: root/gas
diff options
context:
space:
mode:
authorIan Lance Taylor <ian@airs.com>1993-08-12 15:52:57 +0000
committerIan Lance Taylor <ian@airs.com>1993-08-12 15:52:57 +0000
commit0aa07269cfb496dd99f9d7d0c8bb052cfdda922d (patch)
tree13826e5b6c4c0038c1fec1858218ba220d16713e /gas
parent8e2184bda0fbf5b64a76478a12192ba7f131dbe6 (diff)
downloadgdb-0aa07269cfb496dd99f9d7d0c8bb052cfdda922d.zip
gdb-0aa07269cfb496dd99f9d7d0c8bb052cfdda922d.tar.gz
gdb-0aa07269cfb496dd99f9d7d0c8bb052cfdda922d.tar.bz2
* config/tc-mips.c (mips_ip): Suggested by
davidj@ICSI.Berkeley.EDU (David Johnson): Don't accept symbolic names for 'E' and 'G' argument types (coprocessor registers) and don't warn if $1 is used on the coprocessor.
Diffstat (limited to 'gas')
-rw-r--r--gas/ChangeLog14
-rw-r--r--gas/config/tc-mips.c128
2 files changed, 96 insertions, 46 deletions
diff --git a/gas/ChangeLog b/gas/ChangeLog
index 92e1086..a33ac42 100644
--- a/gas/ChangeLog
+++ b/gas/ChangeLog
@@ -1,3 +1,17 @@
+Thu Aug 12 11:47:58 1993 Ian Lance Taylor (ian@tweedledumb.cygnus.com)
+
+ * config/tc-mips.c (mips_ip): Suggested by
+ davidj@ICSI.Berkeley.EDU (David Johnson): Don't accept symbolic
+ names for 'E' and 'G' argument types (coprocessor registers) and
+ don't warn if $1 is used on the coprocessor.
+
+Mon Aug 9 12:09:14 1993 Doug Evans (dje@canuck.cygnus.com)
+
+ * read.c (emit_expr): Use BFD_RELOC_16 for 2-byte values.
+ * config/tc-sparc.c (md_apply_fix, tc_gen_reloc): Handle
+ BFD_RELOC_16.
+ * config/tc-sparc.h (WORKING_DOT_WORD): Define.
+
Mon Aug 9 13:36:22 1993 Ken Raeburn (raeburn@cambridge.cygnus.com)
* write.c (merge_data_into_text): Define only if BFD_ASSEMBLER is
diff --git a/gas/config/tc-mips.c b/gas/config/tc-mips.c
index bb4c48e..e0cc5d4 100644
--- a/gas/config/tc-mips.c
+++ b/gas/config/tc-mips.c
@@ -102,10 +102,11 @@ static symbolS *insn_label;
/* To output NOP instructions correctly, we need to keep information
about the previous two instructions. */
-/* Whether we are optimizing. We always optimize unless -O0 is given.
- For the very simple optimizations we do, this is compatible with
- the MIPS assembler. */
-static int mips_optimize = 1;
+/* Whether we are optimizing. The default value of 2 means to remove
+ unneeded NOPs and swap branch instructions when possible. A value
+ of 1 means to not swap branches. A value of 0 means to always
+ insert NOPs. */
+static int mips_optimize = 2;
/* The previous instruction. */
static struct mips_cl_insn prev_insn;
@@ -460,9 +461,11 @@ append_insn (ip, address_expr, reloc_type)
/* A load delay. All load delays delay the use of general
register rt for one instruction. */
know (prev_insn.insn_mo->pinfo & INSN_WRITE_GPR_T);
- if (insn_uses_reg (ip,
- (prev_insn.insn_opcode >> OP_SH_RT) & OP_MASK_RT,
- 0))
+ if (mips_optimize == 0
+ || insn_uses_reg (ip,
+ ((prev_insn.insn_opcode >> OP_SH_RT)
+ & OP_MASK_RT),
+ 0))
++nops;
}
else if (prev_insn.insn_mo->pinfo & INSN_COPROC_DELAY)
@@ -480,18 +483,20 @@ append_insn (ip, address_expr, reloc_type)
all. */
if (prev_insn.insn_mo->pinfo & INSN_WRITE_FPR_T)
{
- if (insn_uses_reg (ip,
- ((prev_insn.insn_opcode >> OP_SH_RT)
- & OP_MASK_RT),
- 1))
+ if (mips_optimize == 0
+ || insn_uses_reg (ip,
+ ((prev_insn.insn_opcode >> OP_SH_RT)
+ & OP_MASK_RT),
+ 1))
++nops;
}
else if (prev_insn.insn_mo->pinfo & INSN_WRITE_FPR_D)
{
- if (insn_uses_reg (ip,
- ((prev_insn.insn_opcode >> OP_SH_RD)
- & OP_MASK_RD),
- 1))
+ if (mips_optimize == 0
+ || insn_uses_reg (ip,
+ ((prev_insn.insn_opcode >> OP_SH_RD)
+ & OP_MASK_RD),
+ 1))
++nops;
}
else
@@ -502,8 +507,9 @@ append_insn (ip, address_expr, reloc_type)
instruction may set the condition codes, and the
current instruction uses them, we must insert two
NOPS. */
- if ((prev_insn.insn_mo->pinfo & INSN_WRITE_COND_CODE)
- && (ip->insn_mo->pinfo & INSN_READ_COND_CODE))
+ if (mips_optimize == 0
+ || ((prev_insn.insn_mo->pinfo & INSN_WRITE_COND_CODE)
+ && (ip->insn_mo->pinfo & INSN_READ_COND_CODE)))
nops += 2;
else if (ip->insn_mo->pinfo & INSN_COP)
++nops;
@@ -516,7 +522,8 @@ append_insn (ip, address_expr, reloc_type)
(this means it is a floating point comparison
instruction). If this instruction uses the condition
codes, we need to insert a single NOP. */
- if (ip->insn_mo->pinfo & INSN_READ_COND_CODE)
+ if (mips_optimize == 0
+ || ip->insn_mo->pinfo & INSN_READ_COND_CODE)
++nops;
}
else if (prev_insn.insn_mo->pinfo & INSN_READ_LO)
@@ -524,7 +531,8 @@ append_insn (ip, address_expr, reloc_type)
/* The previous instruction reads the LO register; if the
current instruction writes to the LO register, we must
insert two NOPS. */
- if (ip->insn_mo->pinfo & INSN_WRITE_LO)
+ if (mips_optimize == 0
+ || ip->insn_mo->pinfo & INSN_WRITE_LO)
nops += 2;
}
else if (prev_insn.insn_mo->pinfo & INSN_READ_HI)
@@ -532,7 +540,8 @@ append_insn (ip, address_expr, reloc_type)
/* The previous instruction reads the HI register; if the
current instruction writes to the HI register, we must
insert a NOP. */
- if (ip->insn_mo->pinfo & INSN_WRITE_HI)
+ if (mips_optimize == 0
+ || ip->insn_mo->pinfo & INSN_WRITE_HI)
nops += 2;
}
@@ -625,7 +634,7 @@ append_insn (ip, address_expr, reloc_type)
if ((ip->insn_mo->pinfo & INSN_UNCOND_BRANCH_DELAY)
|| (ip->insn_mo->pinfo & INSN_COND_BRANCH_DELAY))
{
- if (! mips_optimize
+ if (mips_optimize < 2
/* If we had to emit any NOP instructions, then we
already know we can not swap. */
|| nops != 0
@@ -2469,6 +2478,20 @@ mips_ip (str, ip)
s = expr_end;
continue;
+ case 'C': /* Coprocessor code */
+ my_getExpression (&imm_expr, s);
+ check_absolute_expr (ip, &imm_expr);
+ if ((unsigned long) imm_expr.X_add_number >= (1<<25))
+ {
+ as_warn ("Coproccesor code > 25 bits (%d)",
+ imm_expr.X_add_number);
+ imm_expr.X_add_number &= ((1<<25) - 1);
+ }
+ ip->insn_opcode |= imm_expr.X_add_number;
+ imm_expr.X_op = O_absent;
+ s = expr_end;
+ continue;
+
case 'b': /* base register */
case 'd': /* destination register */
case 's': /* source register */
@@ -2492,33 +2515,36 @@ mips_ip (str, ip)
++s;
}
while (isdigit (*s));
+ if (regno > 31)
+ as_bad ("Invalid register number (%d)", regno);
}
- else if (s[1] == 'f' && s[2] == 'p')
- {
- s += 3;
- regno = 30;
- }
- else if (s[1] == 's' && s[2] == 'p')
- {
- s += 3;
- regno = 29;
- }
- else if (s[1] == 'g' && s[2] == 'p')
- {
- s += 3;
- regno = 28;
- }
- else if (s[1] == 'a' && s[2] == 't')
+ else if (*args != 'E' && *args != 'G')
{
- s += 3;
- regno = 1;
+ if (s[1] == 'f' && s[2] == 'p')
+ {
+ s += 3;
+ regno = 30;
+ }
+ else if (s[1] == 's' && s[2] == 'p')
+ {
+ s += 3;
+ regno = 29;
+ }
+ else if (s[1] == 'g' && s[2] == 'p')
+ {
+ s += 3;
+ regno = 28;
+ }
+ else if (s[1] == 'a' && s[2] == 't')
+ {
+ s += 3;
+ regno = 1;
+ }
+ else
+ goto notreg;
+ if (regno == AT && ! mips_noat)
+ as_warn ("Used $at without \".set noat\"");
}
- else
- goto notreg;
- if (regno > 31)
- as_bad ("Invalid register number (%d)", regno);
- if (regno == AT && !mips_noat)
- as_warn ("Used $at without \".set noat\"");
c = *args;
if (*s == ' ')
s++;
@@ -3001,7 +3027,17 @@ md_parse_option (argP, cntP, vecP)
if (**argP == 'O')
{
- mips_optimize = (*argP)[1] != '0';
+ if ((*argP)[1] == '0')
+ mips_optimize = 1;
+ else
+ mips_optimize = 2;
+ return 1;
+ }
+
+ if (**argP == 'g')
+ {
+ if ((*argP)[1] == '\0' || (*argP)[1] == '2')
+ mips_optimize = 0;
return 1;
}