aboutsummaryrefslogtreecommitdiff
path: root/include/opcode/mips.h
diff options
context:
space:
mode:
authorRichard Sandiford <rdsandiford@googlemail.com>2013-08-03 10:49:48 +0000
committerRichard Sandiford <rdsandiford@googlemail.com>2013-08-03 10:49:48 +0000
commit3ccad066ac853353fb20d9bf2993107dda242801 (patch)
tree50222c01bc5d4e226cc9b32442b1be3215278165 /include/opcode/mips.h
parent0acfaea6cd192fce727369cdcede034410a5a1da (diff)
downloadgdb-3ccad066ac853353fb20d9bf2993107dda242801.zip
gdb-3ccad066ac853353fb20d9bf2993107dda242801.tar.gz
gdb-3ccad066ac853353fb20d9bf2993107dda242801.tar.bz2
include/opcode/
* mips.h (mips_pcrel_operand): Inherit from mips_int_operand. (mips_int_operand_min, mips_int_operand_max): New functions. (mips_decode_pcrel_operand): Use mips_decode_int_operand. opcodes/ * mips-formats.h (PCREL): Reorder parameters and update the definition to match new mips_pcrel_operand layout. (JUMP, JALX, BRANCH): Update accordingly. * mips16-opc.c (decode_mips16_operand): Likewise. gas/ * config/tc-mips.c (match_int_operand): Use mips_int_operand_min and mips_int_operand_max. (mips16_immed_operand, mips16_immed_operands, MIPS16_NUM_IMMED): Delete. (mips16_immed_operand, mips16_immed_in_range_p): New functions. (mips16_immed, mips16_extended_frag): Use them. Use mips_int_operand instead of mips16_immed_operand.
Diffstat (limited to 'include/opcode/mips.h')
-rw-r--r--include/opcode/mips.h35
1 files changed, 24 insertions, 11 deletions
diff --git a/include/opcode/mips.h b/include/opcode/mips.h
index b299bd8..e82e4c2 100644
--- a/include/opcode/mips.h
+++ b/include/opcode/mips.h
@@ -537,16 +537,13 @@ struct mips_reg_pair_operand
but the rules for MIPS16 instructions like ADDIUPC are more complicated. */
struct mips_pcrel_operand
{
- struct mips_operand root;
+ /* Encodes the offset. */
+ struct mips_int_operand root;
- /* The low ALIGN_LOG2 bits of the base PC are cleared to give PC'. */
+ /* The low ALIGN_LOG2 bits of the base PC are cleared to give PC',
+ which is then added to the offset encoded by ROOT. */
unsigned int align_log2 : 8;
- /* The operand is shifted left SHIFT places and added to PC'.
- The operand is signed if IS_SIGNED. */
- unsigned int shift : 8;
- unsigned int is_signed : 1;
-
/* If INCLUDE_ISA_BIT, the ISA bit of the original base PC is then
reinstated. This is true for jumps and branches and false for
PC-relative data instructions. */
@@ -604,6 +601,25 @@ mips_decode_int_operand (const struct mips_int_operand *operand,
return uval;
}
+/* Return the maximum value that can be encoded by OPERAND. */
+
+static inline int
+mips_int_operand_max (const struct mips_int_operand *operand)
+{
+ return (operand->max_val + operand->bias) << operand->shift;
+}
+
+/* Return the minimum value that can be encoded by OPERAND. */
+
+static inline int
+mips_int_operand_min (const struct mips_int_operand *operand)
+{
+ unsigned int mask;
+
+ mask = (1 << operand->root.size) - 1;
+ return mips_int_operand_max (operand) - (mask << operand->shift);
+}
+
/* Return the register that OPERAND encodes as UVAL. */
static inline int
@@ -625,10 +641,7 @@ mips_decode_pcrel_operand (const struct mips_pcrel_operand *operand,
bfd_vma addr;
addr = base_pc & -(1 << operand->align_log2);
- if (operand->is_signed)
- addr += mips_signed_operand (&operand->root, uval) * (1 << operand->shift);
- else
- addr += uval << operand->shift;
+ addr += mips_decode_int_operand (&operand->root, uval);
if (operand->include_isa_bit)
addr |= base_pc & 1;
if (operand->flip_isa_bit)