From b015e599c772eeb5f818d710119ee43e7df0feff Mon Sep 17 00:00:00 2001 From: Andrew Pinski Date: Fri, 10 May 2013 01:08:48 +0000 Subject: binutils/ChangeLog: * doc/binutils.texi: Document -Mvirt disassembler option. gas/ChangeLog: * config/tc-mips.c (struct mips_set_options): New ase_virt field. (mips_opts): Update for the new field. (file_ase_virt): New variable. (ISA_SUPPORTS_VIRT_ASE): New macro. (ISA_SUPPORTS_VIRT64_ASE): New macro. (MIPS_CPU_ASE_VIRT): New define. (is_opcode_valid): Handle ase_virt. (macro_build): Handle "+J". (validate_mips_insn): Likewise. (mips_ip): Likewise. (enum options): Add OPTION_VIRT and OPTION_NO_VIRT. (md_longopts): Add mvirt and mnovirt (md_parse_option): Handle OPTION_VIRT and OPTION_NO_VIRT. (mips_after_parse_args): Handle ase_virt field. (s_mipsset): Handle "virt" and "novirt". (mips_elf_final_processing): Add a comment about virt ASE might need a new flag. (md_show_usage): Print out the usage of -mvirt and mno-virt options. * doc/c-mips.texi: Document -mvirt and -mno-virt. Document ".set virt" and ".set novirt". gas/testsuite/ChangeLog: * gas/mips/mips.exp: Run virt and virt64 testcases. * gas/mips/virt.d: New file. * gas/mips/virt.s: New file. * gas/mips/virt64.d: New file. * gas/mips/virt64.s: New file. include/opcode/ChangeLog: * mips.h (OP_MASK_CODE10): Correct definition. (OP_SH_CODE10): Likewise. Add a comment that "+J" is used now for OP_*CODE10. (INSN_ASE_MASK): Update. (INSN_VIRT): New macro. (INSN_VIRT64): New macro opcodes/ChangeLog: * mips-dis.c (mips_arch_choices): Add INSN_VIRT to mips32r2 . Add INSN_VIRT and INSN_VIRT64 to mips64r2. (parse_mips_dis_option): Handle the virt option. (print_insn_args): Handle "+J". (print_mips_disassembler_options): Print out message about virt64. * mips-opc.c (IVIRT): New define. (IVIRT64): New define. (mips_builtin_opcodes): Add dmfgc0, dmtgc0, hypcall, mfgc0, mtgc0, tlbgr, tlbgwi, tlbginv, tlbginvf, tlbgwr, tlbgp VIRT instructions. Move rfe to the bottom as it conflicts with tlbgp. --- binutils/ChangeLog | 4 ++ binutils/doc/binutils.texi | 3 ++ gas/ChangeLog | 23 +++++++++++ gas/config/tc-mips.c | 86 ++++++++++++++++++++++++++++++++++++----- gas/doc/c-mips.texi | 14 +++++++ gas/testsuite/ChangeLog | 8 ++++ gas/testsuite/gas/mips/mips.exp | 3 ++ gas/testsuite/gas/mips/virt.d | 20 ++++++++++ gas/testsuite/gas/mips/virt.s | 22 +++++++++++ gas/testsuite/gas/mips/virt64.d | 12 ++++++ gas/testsuite/gas/mips/virt64.s | 12 ++++++ include/opcode/ChangeLog | 9 +++++ include/opcode/mips.h | 17 ++++++-- opcodes/ChangeLog | 13 +++++++ opcodes/mips-dis.c | 19 ++++++++- opcodes/mips-opc.c | 26 ++++++++++++- 16 files changed, 274 insertions(+), 17 deletions(-) create mode 100644 gas/testsuite/gas/mips/virt.d create mode 100644 gas/testsuite/gas/mips/virt.s create mode 100644 gas/testsuite/gas/mips/virt64.d create mode 100644 gas/testsuite/gas/mips/virt64.s diff --git a/binutils/ChangeLog b/binutils/ChangeLog index 63f0910..6859005 100644 --- a/binutils/ChangeLog +++ b/binutils/ChangeLog @@ -1,3 +1,7 @@ +2013-05-09 Andrew Pinski + + * doc/binutils.texi: Document -Mvirt disassembler option. + 2013-05-02 Nick Clifton * readelf.c: Add support for MSP430X architecture. diff --git a/binutils/doc/binutils.texi b/binutils/doc/binutils.texi index 0bb1d92..aaa0bdb 100644 --- a/binutils/doc/binutils.texi +++ b/binutils/doc/binutils.texi @@ -2113,6 +2113,9 @@ Print the 'raw' instruction mnemonic instead of some pseudo instruction mnemonic. I.e., print 'daddu' or 'or' instead of 'move', 'sll' instead of 'nop', etc. +@item virt +Disassemble the virtualization ASE instructions. + @item gpr-names=@var{ABI} Print GPR (general-purpose register) names as appropriate for the specified ABI. By default, GPR names are selected according to diff --git a/gas/ChangeLog b/gas/ChangeLog index b32779d..e35c821 100644 --- a/gas/ChangeLog +++ b/gas/ChangeLog @@ -1,3 +1,26 @@ +2013-05-09 Andrew Pinski + + * config/tc-mips.c (struct mips_set_options): New ase_virt field. + (mips_opts): Update for the new field. + (file_ase_virt): New variable. + (ISA_SUPPORTS_VIRT_ASE): New macro. + (ISA_SUPPORTS_VIRT64_ASE): New macro. + (MIPS_CPU_ASE_VIRT): New define. + (is_opcode_valid): Handle ase_virt. + (macro_build): Handle "+J". + (validate_mips_insn): Likewise. + (mips_ip): Likewise. + (enum options): Add OPTION_VIRT and OPTION_NO_VIRT. + (md_longopts): Add mvirt and mnovirt + (md_parse_option): Handle OPTION_VIRT and OPTION_NO_VIRT. + (mips_after_parse_args): Handle ase_virt field. + (s_mipsset): Handle "virt" and "novirt". + (mips_elf_final_processing): Add a comment about virt ASE might need + a new flag. + (md_show_usage): Print out the usage of -mvirt and mno-virt options. + * doc/c-mips.texi: Document -mvirt and -mno-virt. + Document ".set virt" and ".set novirt". + 2013-05-09 Alan Modra * config/tc-ppc.c (md_apply_fix): Sign extend fieldval under diff --git a/gas/config/tc-mips.c b/gas/config/tc-mips.c index 6eff836..b234795 100644 --- a/gas/config/tc-mips.c +++ b/gas/config/tc-mips.c @@ -218,6 +218,7 @@ struct mips_set_options int ase_dspr2; int ase_mt; int ase_mcu; + int ase_virt; /* Whether we are assembling for the mips16 processor. 0 if we are not, 1 if we are, and -1 if the value has not been initialized. Changed by `.set mips16' and `.set nomips16', and the -mips16 and @@ -292,10 +293,11 @@ static struct mips_set_options mips_opts = { /* isa */ ISA_UNKNOWN, /* ase_mips3d */ -1, /* ase_mdmx */ -1, /* ase_smartmips */ 0, /* ase_dsp */ -1, /* ase_dspr2 */ -1, /* ase_mt */ -1, - /* ase_mcu */ -1, /* mips16 */ -1, /* micromips */ -1, /* noreorder */ 0, - /* at */ ATREG, /* warn_about_macros */ 0, /* nomove */ 0, /* nobopt */ 0, - /* noautoextend */ 0, /* gp32 */ 0, /* fp32 */ 0, /* arch */ CPU_UNKNOWN, - /* sym32 */ FALSE, /* soft_float */ FALSE, /* single_float */ FALSE + /* ase_mcu */ -1, /* ase_virt */ -1, /* mips16 */ -1,/* micromips */ -1, + /* noreorder */ 0, /* at */ ATREG, /* warn_about_macros */ 0, + /* nomove */ 0, /* nobopt */ 0, /* noautoextend */ 0, /* gp32 */ 0, + /* fp32 */ 0, /* arch */ CPU_UNKNOWN, /* sym32 */ FALSE, + /* soft_float */ FALSE, /* single_float */ FALSE }; /* These variables are filled in with the masks of registers used. @@ -374,6 +376,15 @@ static int file_ase_mt; || mips_opts.isa == ISA_MIPS64R2 \ || mips_opts.micromips) +/* True if -mvirt was passed or implied by arguments passed on the + command line (e.g., by -march). */ +static int file_ase_virt; + +#define ISA_SUPPORTS_VIRT_ASE (mips_opts.isa == ISA_MIPS32R2 \ + || mips_opts.isa == ISA_MIPS64R2) + +#define ISA_SUPPORTS_VIRT64_ASE (mips_opts.isa == ISA_MIPS64R2) + /* The argument of the -march= flag. The architecture we are assembling. */ static int file_mips_arch = CPU_UNKNOWN; static const char *mips_arch_string; @@ -1395,6 +1406,7 @@ struct mips_cpu_info #define MIPS_CPU_ASE_MDMX 0x0020 /* CPU implements MDMX ASE */ #define MIPS_CPU_ASE_DSPR2 0x0040 /* CPU implements DSP R2 ASE */ #define MIPS_CPU_ASE_MCU 0x0080 /* CPU implements MCU ASE */ +#define MIPS_CPU_ASE_VIRT 0x0100 /* CPU implements Virtualization ASE */ static const struct mips_cpu_info *mips_parse_cpu (const char *, const char *); static const struct mips_cpu_info *mips_cpu_info_from_isa (int); @@ -2258,6 +2270,10 @@ is_opcode_valid (const struct mips_opcode *mo) isa |= INSN_SMARTMIPS; if (mips_opts.ase_mcu) isa |= INSN_MCU; + if (mips_opts.ase_virt) + isa |= INSN_VIRT; + if (mips_opts.ase_virt && ISA_SUPPORTS_VIRT64_ASE) + isa |= INSN_VIRT64; if (!opcode_is_member (mo, isa, mips_opts.arch)) return FALSE; @@ -5036,6 +5052,11 @@ macro_build (expressionS *ep, const char *name, const char *fmt, ...) INSMSB, insn, va_arg (args, int)); continue; + case 'J': + gas_assert (!mips_opts.micromips); + INSERT_OPERAND (0, CODE10, insn, va_arg (args, int)); + continue; + case 'C': case 'G': case 'H': @@ -10416,6 +10437,7 @@ validate_mips_insn (const struct mips_opcode *opc) case 'G': USE_BITS (OP_MASK_EXTMSBD, OP_SH_EXTMSBD); break; case 'H': USE_BITS (OP_MASK_EXTMSBD, OP_SH_EXTMSBD); break; case 'I': break; + case 'J': USE_BITS (OP_MASK_CODE10, OP_SH_CODE10); break; case 't': USE_BITS (OP_MASK_RT, OP_SH_RT); break; case 'T': USE_BITS (OP_MASK_RT, OP_SH_RT); USE_BITS (OP_MASK_SEL, OP_SH_SEL); break; @@ -11339,6 +11361,23 @@ mips_ip (char *str, struct mips_cl_insn *ip) } continue; + case 'J': /* 10-bit hypcall code. */ + gas_assert (!mips_opts.micromips); + { + unsigned long mask = OP_MASK_CODE10; + + my_getExpression (&imm_expr, s); + check_absolute_expr (ip, &imm_expr); + if ((unsigned long) imm_expr.X_add_number > mask) + as_warn (_("Code for %s not in range 0..%lu (%lu)"), + ip->insn_mo->name, + mask, (unsigned long) imm_expr.X_add_number); + INSERT_OPERAND (0, CODE10, *ip, imm_expr.X_add_number); + imm_expr.X_op = O_absent; + s = expr_end; + } + continue; + case 'A': /* ins/ext position, becomes LSB. */ limlo = 0; limhi = 31; @@ -14496,6 +14535,8 @@ enum options OPTION_NO_DSP, OPTION_MT, OPTION_NO_MT, + OPTION_VIRT, + OPTION_NO_VIRT, OPTION_SMARTMIPS, OPTION_NO_SMARTMIPS, OPTION_DSPR2, @@ -14600,6 +14641,8 @@ struct option md_longopts[] = {"mno-micromips", no_argument, NULL, OPTION_NO_MICROMIPS}, {"mmcu", no_argument, NULL, OPTION_MCU}, {"mno-mcu", no_argument, NULL, OPTION_NO_MCU}, + {"mvirt", no_argument, NULL, OPTION_VIRT}, + {"mno-virt", no_argument, NULL, OPTION_NO_VIRT}, /* Old-style architecture options. Don't add more of these. */ {"m4650", no_argument, NULL, OPTION_M4650}, @@ -14877,6 +14920,14 @@ md_parse_option (int c, char *arg) mips_no_prev_insn (); break; + case OPTION_VIRT: + mips_opts.ase_virt = 1; + break; + + case OPTION_NO_VIRT: + mips_opts.ase_virt = 0; + break; + case OPTION_MIPS16: if (mips_opts.micromips == 1) { @@ -15370,6 +15421,12 @@ mips_after_parse_args (void) as_warn (_("%s ISA does not support MCU ASE"), mips_cpu_info_from_isa (mips_opts.isa)->name); + if (mips_opts.ase_virt == -1) + mips_opts.ase_virt = (arch_info->flags & MIPS_CPU_ASE_VIRT) ? 1 : 0; + if (mips_opts.ase_virt && !ISA_SUPPORTS_VIRT_ASE) + as_warn (_("%s ISA does not support Virtualization ASE"), + mips_cpu_info_from_isa (mips_opts.isa)->name); + file_mips_isa = mips_opts.isa; file_ase_mips3d = mips_opts.ase_mips3d; file_ase_mdmx = mips_opts.ase_mdmx; @@ -15377,6 +15434,7 @@ mips_after_parse_args (void) file_ase_dsp = mips_opts.ase_dsp; file_ase_dspr2 = mips_opts.ase_dspr2; file_ase_mt = mips_opts.ase_mt; + file_ase_virt = mips_opts.ase_virt; mips_opts.gp32 = file_mips_gp32; mips_opts.fp32 = file_mips_fp32; mips_opts.soft_float = file_mips_soft_float; @@ -16446,6 +16504,15 @@ s_mipsset (int x ATTRIBUTE_UNUSED) mips_opts.ase_mcu = 1; else if (strcmp (name, "nomcu") == 0) mips_opts.ase_mcu = 0; + else if (strcmp (name, "virt") == 0) + { + if (!ISA_SUPPORTS_VIRT_ASE) + as_warn (_("%s ISA does not support Virtualization ASE"), + mips_cpu_info_from_isa (mips_opts.isa)->name); + mips_opts.ase_virt = 1; + } + else if (strcmp (name, "novirt") == 0) + mips_opts.ase_virt = 0; else if (strncmp (name, "mips", 4) == 0 || strncmp (name, "arch=", 5) == 0) { int reset = 0; @@ -18718,12 +18785,8 @@ mips_elf_final_processing (void) if (mips_abicalls) elf_elfheader (stdoutput)->e_flags |= EF_MIPS_CPIC; - /* Set MIPS ELF flags for ASEs. */ - /* We may need to define a new flag for DSP ASE, and set this flag when - file_ase_dsp is true. */ - /* Same for DSP R2. */ - /* We may need to define a new flag for MT ASE, and set this flag when - file_ase_mt is true. */ + /* Set MIPS ELF flags for ASEs. Note that not all ASEs have flags + defined at present; this might need to change in future. */ if (file_ase_mips16) elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ARCH_ASE_M16; if (file_ase_micromips) @@ -19594,6 +19657,9 @@ MIPS options:\n\ -mmcu generate MCU instructions\n\ -mno-mcu do not generate MCU instructions\n")); fprintf (stream, _("\ +-mvirt generate Virtualization instructions\n\ +-mno-virt do not generate Virtualization instructions\n")); + fprintf (stream, _("\ -mfix-loongson2f-jump work around Loongson2F JUMP instructions\n\ -mfix-loongson2f-nop work around Loongson2F NOP errata\n\ -mfix-vr4120 work around certain VR4120 errata\n\ diff --git a/gas/doc/c-mips.texi b/gas/doc/c-mips.texi index 7df5f79..b8953be 100644 --- a/gas/doc/c-mips.texi +++ b/gas/doc/c-mips.texi @@ -181,6 +181,12 @@ Generate code for the MCU Application Specific Extension. This tells the assembler to accept MCU instructions. @samp{-mno-mcu} turns off this option. +@item -mvirt +@itemx -mno-virt +Generate code for the Virtualization Application Specific Extension. +This tells the assembler to accept Virtualization instructions. +@samp{-mno-virt} turns off this option. + @item -mfix7000 @itemx -mno-fix7000 Cause nops to be inserted if the read of the destination register @@ -684,6 +690,14 @@ from the MCU Application Specific Extension from that point on in the assembly. The @code{.set nomcu} directive prevents MCU instructions from being accepted. +@cindex Virtualization instruction generation override +@kindex @code{.set virt} +@kindex @code{.set novirt} +The directive @code{.set virt} makes the assembler accept instructions +from the Virtualization Application Specific Extension from that point +on in the assembly. The @code{.set novirt} directive prevents Virtualization +instructions from being accepted. + Traditional @sc{mips} assemblers do not support these directives. @node MIPS floating-point diff --git a/gas/testsuite/ChangeLog b/gas/testsuite/ChangeLog index b853d8b..dbaed95 100644 --- a/gas/testsuite/ChangeLog +++ b/gas/testsuite/ChangeLog @@ -1,3 +1,11 @@ +2013-05-09 Andrew Pinski + + * gas/mips/mips.exp: Run virt and virt64 testcases. + * gas/mips/virt.d: New file. + * gas/mips/virt.s: New file. + * gas/mips/virt64.d: New file. + * gas/mips/virt64.s: New file. + 2013-05-04 Richard Sandiford * gas/mips/micromips-warn-branch-delay.d: Use numeric registers. diff --git a/gas/testsuite/gas/mips/mips.exp b/gas/testsuite/gas/mips/mips.exp index 48bd33e..d338e53 100644 --- a/gas/testsuite/gas/mips/mips.exp +++ b/gas/testsuite/gas/mips/mips.exp @@ -786,6 +786,9 @@ if { [istarget mips*-*-vxworks*] } { run_dump_test "lineno" run_dump_test "sync" + run_dump_test_arches "virt" [mips_arch_list_matching mips32r2 !micromips] + run_dump_test_arches "virt64" [mips_arch_list_matching mips64r2 !micromips] + run_dump_test_arches "mips32" [mips_arch_list_matching mips32] run_dump_test_arches "mips32-imm" [mips_arch_list_matching mips32] diff --git a/gas/testsuite/gas/mips/virt.d b/gas/testsuite/gas/mips/virt.d new file mode 100644 index 0000000..c22f867 --- /dev/null +++ b/gas/testsuite/gas/mips/virt.d @@ -0,0 +1,20 @@ +#objdump: -dr --prefix-addresses --show-raw-insn -Mvirt,cp0-names=mips32r2 +#name: virt instructions +#as: -32 -mvirt + +.*: +file format .*mips.* + +Disassembly of section \.text: +[0-9a-f]+ <[^>]*> 4063e800 mfgc0 v1,c0_taghi +[0-9a-f]+ <[^>]*> 406ba005 mfgc0 t3,\$20,5 +[0-9a-f]+ <[^>]*> 40771200 mtgc0 s7,c0_entrylo0 +[0-9a-f]+ <[^>]*> 40677202 mtgc0 a3,\$14,2 +[0-9a-f]+ <[^>]*> 42000028 hypcall +[0-9a-f]+ <[^>]*> 4212b028 hypcall 0x256 +[0-9a-f]+ <[^>]*> 4200000b tlbginv +[0-9a-f]+ <[^>]*> 4200000c tlbginvf +[0-9a-f]+ <[^>]*> 42000010 tlbgp +[0-9a-f]+ <[^>]*> 42000009 tlbgr +[0-9a-f]+ <[^>]*> 4200000a tlbgwi +[0-9a-f]+ <[^>]*> 4200000e tlbgwr + ... diff --git a/gas/testsuite/gas/mips/virt.s b/gas/testsuite/gas/mips/virt.s new file mode 100644 index 0000000..eca5e02 --- /dev/null +++ b/gas/testsuite/gas/mips/virt.s @@ -0,0 +1,22 @@ + .text + .set noreorder + +foo: + mfgc0 $3,$29 + mfgc0 $11,$20,5 + mtgc0 $23,$2 + mtgc0 $7,$14,2 + + hypcall + hypcall 0x256 + + tlbginv + tlbginvf + tlbgp + tlbgr + tlbgwi + tlbgwr + +# Force at least 8 (non-delay-slot) zero bytes, to make 'objdump' print ... + .align 2 + .space 8 diff --git a/gas/testsuite/gas/mips/virt64.d b/gas/testsuite/gas/mips/virt64.d new file mode 100644 index 0000000..7a86ff9 --- /dev/null +++ b/gas/testsuite/gas/mips/virt64.d @@ -0,0 +1,12 @@ +#objdump: -dr --prefix-addresses --show-raw-insn -Mvirt,cp0-names=mips64r2 +#name: virt64 instructions +#as: -64 -mvirt + +.*: +file format .*mips.* + +Disassembly of section \.text: +[0-9a-f]+ <[^>]*> 4063e900 dmfgc0 v1,c0_taghi +[0-9a-f]+ <[^>]*> 406ba105 dmfgc0 a7,\$20,5 +[0-9a-f]+ <[^>]*> 40771300 dmtgc0 s7,c0_entrylo0 +[0-9a-f]+ <[^>]*> 40677302 dmtgc0 a3,\$14,2 + ... diff --git a/gas/testsuite/gas/mips/virt64.s b/gas/testsuite/gas/mips/virt64.s new file mode 100644 index 0000000..f3cd7b5 --- /dev/null +++ b/gas/testsuite/gas/mips/virt64.s @@ -0,0 +1,12 @@ + .text + .set noreorder + +foo: + dmfgc0 $3,$29 + dmfgc0 $11,$20,5 + dmtgc0 $23,$2 + dmtgc0 $7,$14,2 + +# Force at least 8 (non-delay-slot) zero bytes, to make 'objdump' print ... + .align 2 + .space 8 diff --git a/include/opcode/ChangeLog b/include/opcode/ChangeLog index 2b76a36..773fa58 100644 --- a/include/opcode/ChangeLog +++ b/include/opcode/ChangeLog @@ -1,3 +1,12 @@ +2013-05-09 Andrew Pinski + + * mips.h (OP_MASK_CODE10): Correct definition. + (OP_SH_CODE10): Likewise. + Add a comment that "+J" is used now for OP_*CODE10. + (INSN_ASE_MASK): Update. + (INSN_VIRT): New macro. + (INSN_VIRT64): New macro + 2013-05-02 Nick Clifton * msp430.h: Add patterns for MSP430X instructions. diff --git a/include/opcode/mips.h b/include/opcode/mips.h index ef81bbe..bf0f115 100644 --- a/include/opcode/mips.h +++ b/include/opcode/mips.h @@ -212,6 +212,10 @@ #define OP_OP_SDC2 0x3e #define OP_OP_SDC3 0x3f /* a.k.a. sd */ +/* MIPS VIRT ASE */ +#define OP_MASK_CODE10 0x3ff +#define OP_SH_CODE10 11 + /* Values in the 'VSEL' field. */ #define MDMX_FMTSEL_IMM_QH 0x1d #define MDMX_FMTSEL_IMM_OB 0x1e @@ -255,8 +259,6 @@ of the operand handling in GAS. The fields below only exist in the microMIPS encoding, so define each one to have an empty range. */ -#define OP_MASK_CODE10 0 -#define OP_SH_CODE10 0 #define OP_MASK_TRAP 0 #define OP_SH_TRAP 0 #define OP_MASK_OFFSET10 0 @@ -486,6 +488,9 @@ struct mips_opcode "~" 12 bit offset (OP_*_OFFSET12) "\" 3 bit position for aset and aclr (OP_*_3BITPOS) + VIRT ASE usage: + "+J" 10-bit hypcall code (OP_*CODE10) + UDI immediates: "+1" UDI immediate bits 6-10 "+2" UDI immediate bits 6-15 @@ -528,7 +533,7 @@ struct mips_opcode Extension character sequences used so far ("+" followed by the following), for quick reference when adding more: "1234" - "ABCDEFGHIPQSTXZ" + "ABCDEFGHIJPQSTXZ" "abcpstxz" */ @@ -726,7 +731,7 @@ static const unsigned int mips_isa_table[] = #define INSN_OCTEON2 0x00000100 /* Masks used for MIPS-defined ASEs. */ -#define INSN_ASE_MASK 0x3c00f010 +#define INSN_ASE_MASK 0x3c00f0d0 /* DSP ASE */ #define INSN_DSP 0x00001000 @@ -735,6 +740,10 @@ static const unsigned int mips_isa_table[] = /* MIPS R5900 instruction */ #define INSN_5900 0x00004000 +/* Virtualization ASE */ +#define INSN_VIRT 0x00000080 +#define INSN_VIRT64 0x00000040 + /* MIPS-3D ASE */ #define INSN_MIPS3D 0x00008000 diff --git a/opcodes/ChangeLog b/opcodes/ChangeLog index e918abc..9a80d04 100644 --- a/opcodes/ChangeLog +++ b/opcodes/ChangeLog @@ -1,3 +1,16 @@ +2013-05-09 Andrew Pinski + + * mips-dis.c (mips_arch_choices): Add INSN_VIRT to mips32r2. + Add INSN_VIRT and INSN_VIRT64 to mips64r2. + (parse_mips_dis_option): Handle the virt option. + (print_insn_args): Handle "+J". + (print_mips_disassembler_options): Print out message about virt64. + * mips-opc.c (IVIRT): New define. + (IVIRT64): New define. + (mips_builtin_opcodes): Add dmfgc0, dmtgc0, hypcall, mfgc0, mtgc0, + tlbgr, tlbgwi, tlbginv, tlbginvf, tlbgwr, tlbgp VIRT instructions. + Move rfe to the bottom as it conflicts with tlbgp. + 2013-05-09 Alan Modra * ppc-opc.c (extract_vlesi): Properly sign extend. diff --git a/opcodes/mips-dis.c b/opcodes/mips-dis.c index 018ac94..834fd5c 100644 --- a/opcodes/mips-dis.c +++ b/opcodes/mips-dis.c @@ -590,7 +590,7 @@ const struct mips_arch_choice mips_arch_choices[] = { "mips32r2", 1, bfd_mach_mipsisa32r2, CPU_MIPS32R2, (ISA_MIPS32R2 | INSN_SMARTMIPS | INSN_DSP | INSN_DSPR2 - | INSN_MIPS3D | INSN_MT | INSN_MCU), + | INSN_MIPS3D | INSN_MT | INSN_MCU | INSN_VIRT), mips_cp0_names_mips3264r2, mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2), mips_hwr_names_mips3264r2 }, @@ -604,7 +604,7 @@ const struct mips_arch_choice mips_arch_choices[] = { "mips64r2", 1, bfd_mach_mipsisa64r2, CPU_MIPS64R2, (ISA_MIPS64R2 | INSN_MIPS3D | INSN_DSP | INSN_DSPR2 - | INSN_DSP64 | INSN_MT | INSN_MDMX | INSN_MCU), + | INSN_DSP64 | INSN_MT | INSN_MDMX | INSN_MCU | INSN_VIRT | INSN_VIRT64), mips_cp0_names_mips3264r2, mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2), mips_hwr_names_mips3264r2 }, @@ -824,6 +824,14 @@ parse_mips_dis_option (const char *option, unsigned int len) no_aliases = 1; return; } + + if (CONST_STRNEQ (option, "virt")) + { + mips_isa |= INSN_VIRT; + if (mips_isa & ISA_MIPS64R2) + mips_isa |= INSN_VIRT64; + return; + } /* Look for the = that delimits the end of the option name. */ for (i = 0; i < len; i++) @@ -1066,6 +1074,10 @@ print_insn_args (const char *d, infprintf (is, "0x%x", msbd + 1); break; + case 'J': /* hypcall operand */ + infprintf (is, "0x%x", GET_OP (l, CODE10)); + break; + case 't': /* Coprocessor 0 reg name */ infprintf (is, "%s", mips_cp0_names[GET_OP (l, RT)]); break; @@ -3034,6 +3046,9 @@ The following MIPS specific disassembler options are supported for use\n\ with the -M switch (multiple options should be separated by commas):\n")); fprintf (stream, _("\n\ + virt Recognize the virtualization ASE instructions.\n")); + + fprintf (stream, _("\n\ gpr-names=ABI Print GPR names according to specified ABI.\n\ Default: based on binary being disassembled.\n")); diff --git a/opcodes/mips-opc.c b/opcodes/mips-opc.c index ee189c2..0c43d0a 100644 --- a/opcodes/mips-opc.c +++ b/opcodes/mips-opc.c @@ -128,6 +128,8 @@ #define IOCTP (INSN_OCTEONP | INSN_OCTEON2) #define IOCT2 INSN_OCTEON2 #define XLR INSN_XLR +#define IVIRT INSN_VIRT +#define IVIRT64 INSN_VIRT64 #define G1 (T3 \ |EE \ @@ -718,11 +720,17 @@ const struct mips_opcode mips_builtin_opcodes[] = {"dmfc0", "t,G", 0x40200000, 0xffe007ff, LCD|WR_t|RD_C0, 0, I3, EE }, {"dmfc0", "t,+D", 0x40200000, 0xffe007f8, LCD|WR_t|RD_C0, 0, I64 }, {"dmfc0", "t,G,H", 0x40200000, 0xffe007f8, LCD|WR_t|RD_C0, 0, I64 }, +{"dmfgc0", "t,G", 0x40600100, 0xffe007ff, LCD|WR_t|RD_C0, 0, IVIRT64 }, +{"dmfgc0", "t,+D", 0x40600100, 0xffe007f8, LCD|WR_t|RD_C0, 0, IVIRT64 }, +{"dmfgc0", "t,G,H", 0x40600100, 0xffe007f8, LCD|WR_t|RD_C0, 0, IVIRT64 }, {"dmt", "", 0x41600bc1, 0xffffffff, TRAP, 0, MT32 }, {"dmt", "t", 0x41600bc1, 0xffe0ffff, TRAP|WR_t, 0, MT32 }, {"dmtc0", "t,G", 0x40a00000, 0xffe007ff, COD|RD_t|WR_C0|WR_CC, 0, I3, EE }, {"dmtc0", "t,+D", 0x40a00000, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, I64 }, {"dmtc0", "t,G,H", 0x40a00000, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, I64 }, +{"dmtgc0", "t,G", 0x40600300, 0xffe007ff, COD|RD_t|WR_C0|WR_CC, 0, IVIRT64 }, +{"dmtgc0", "t,+D", 0x40600300, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, IVIRT64 }, +{"dmtgc0", "t,G,H", 0x40600300, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, IVIRT64 }, {"dmfc1", "t,S", 0x44200000, 0xffe007ff, LCD|WR_t|RD_S|FP_D, 0, I3, SF }, {"dmfc1", "t,G", 0x44200000, 0xffe007ff, LCD|WR_t|RD_S|FP_D, 0, I3, SF }, {"dmtc1", "t,S", 0x44a00000, 0xffe007ff, COD|RD_t|WR_S|FP_D, 0, I3, SF }, @@ -811,6 +819,8 @@ const struct mips_opcode mips_builtin_opcodes[] = {"floor.w.d", "D,S", 0x4620000f, 0xffff003f, WR_D|RD_S|FP_S|FP_D, 0, I2, SF }, {"floor.w.s", "D,S", 0x4600000f, 0xffff003f, WR_D|RD_S|FP_S, 0, I2 }, {"hibernate","", 0x42000023, 0xffffffff, 0, 0, V1 }, +{"hypcall", "", 0x42000028, 0xffffffff, TRAP, 0, IVIRT }, +{"hypcall", "+J", 0x42000028, 0xffe007ff, TRAP, 0, IVIRT }, {"ins", "t,r,+A,+B", 0x7c000004, 0xfc00003f, WR_t|RD_s, 0, I33 }, {"iret", "", 0x42000038, 0xffffffff, NODS, 0, MC }, {"jr", "s", 0x00000008, 0xfc1fffff, UBD|RD_s, 0, I1 }, @@ -1010,6 +1020,9 @@ const struct mips_opcode mips_builtin_opcodes[] = {"mfc0", "t,G", 0x40000000, 0xffe007ff, LCD|WR_t|RD_C0, 0, I1 }, {"mfc0", "t,+D",0x40000000, 0xffe007f8, LCD|WR_t|RD_C0, 0, I32 }, {"mfc0", "t,G,H", 0x40000000, 0xffe007f8, LCD|WR_t|RD_C0, 0, I32 }, +{"mfgc0", "t,G", 0x40600000, 0xffe007ff, LCD|WR_t|RD_C0, 0, IVIRT }, +{"mfgc0", "t,+D", 0x40600000, 0xffe007f8, LCD|WR_t|RD_C0, 0, IVIRT }, +{"mfgc0", "t,G,H", 0x40600000, 0xffe007f8, LCD|WR_t|RD_C0, 0, IVIRT }, {"mfc1", "t,S", 0x44000000, 0xffe007ff, LCD|WR_t|RD_S|FP_S, 0, I1 }, {"mfc1", "t,G", 0x44000000, 0xffe007ff, LCD|WR_t|RD_S|FP_S, 0, I1 }, {"mfhc1", "t,S", 0x44600000, 0xffe007ff, LCD|WR_t|RD_S|FP_D, 0, I33 }, @@ -1104,6 +1117,9 @@ const struct mips_opcode mips_builtin_opcodes[] = {"mtc0", "t,G", 0x40800000, 0xffe007ff, COD|RD_t|WR_C0|WR_CC, 0, I1 }, {"mtc0", "t,+D", 0x40800000, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, I32 }, {"mtc0", "t,G,H", 0x40800000, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, I32 }, +{"mtgc0", "t,G", 0x40600200, 0xffe007ff, COD|RD_t|WR_C0|WR_CC, 0, IVIRT }, +{"mtgc0", "t,+D", 0x40600200, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, IVIRT }, +{"mtgc0", "t,G,H", 0x40600200, 0xffe007f8, COD|RD_t|WR_C0|WR_CC, 0, IVIRT }, {"mtc1", "t,S", 0x44800000, 0xffe007ff, COD|RD_t|WR_S|FP_S, 0, I1 }, {"mtc1", "t,G", 0x44800000, 0xffe007ff, COD|RD_t|WR_S|FP_S, 0, I1 }, {"mthc1", "t,S", 0x44e00000, 0xffe007ff, COD|RD_t|WR_S|FP_D, 0, I33 }, @@ -1379,7 +1395,7 @@ const struct mips_opcode mips_builtin_opcodes[] = {"remu", "d,v,I", 0, (int) M_REMU_3I, INSN_MACRO, 0, I1 }, {"rdhwr", "t,K", 0x7c00003b, 0xffe007ff, WR_t, 0, I33 }, {"rdpgpr", "d,w", 0x41400000, 0xffe007ff, WR_d, 0, I33 }, -{"rfe", "", 0x42000010, 0xffffffff, 0, 0, I1|T3 }, +/* rfe is moved below as it now conflicts with tlbgp */ {"rnas.qh", "X,Q", 0x78200025, 0xfc20f83f, WR_D|RD_T|FP_D, RD_MACC, MX }, {"rnau.ob", "X,Q", 0x78000021, 0xfc20f83f, WR_D|RD_T|FP_D, RD_MACC, MX|SB1 }, {"rnau.qh", "X,Q", 0x78200021, 0xfc20f83f, WR_D|RD_T|FP_D, RD_MACC, MX }, @@ -1624,6 +1640,12 @@ const struct mips_opcode mips_builtin_opcodes[] = {"tlbr", "", 0x42000001, 0xffffffff, INSN_TLB, 0, I1 }, {"tlbwi", "", 0x42000002, 0xffffffff, INSN_TLB, 0, I1 }, {"tlbwr", "", 0x42000006, 0xffffffff, INSN_TLB, 0, I1 }, +{"tlbgr", "", 0x42000009, 0xffffffff, INSN_TLB, 0, IVIRT }, +{"tlbgwi", "", 0x4200000a, 0xffffffff, INSN_TLB, 0, IVIRT }, +{"tlbginv", "", 0x4200000b, 0xffffffff, INSN_TLB, 0, IVIRT }, +{"tlbginvf","", 0x4200000c, 0xffffffff, INSN_TLB, 0, IVIRT }, +{"tlbgwr", "", 0x4200000e, 0xffffffff, INSN_TLB, 0, IVIRT }, +{"tlbgp", "", 0x42000010, 0xffffffff, INSN_TLB, 0, IVIRT }, {"tlti", "s,j", 0x040a0000, 0xfc1f0000, RD_s|TRAP, 0, I2 }, {"tlt", "s,t", 0x00000032, 0xfc00ffff, RD_s|RD_t|TRAP, 0, I2 }, {"tlt", "s,t,q", 0x00000032, 0xfc00003f, RD_s|RD_t|TRAP, 0, I2 }, @@ -2273,6 +2295,8 @@ const struct mips_opcode mips_builtin_opcodes[] = {"cop1", "C", 0, (int) M_COP1, INSN_MACRO, INSN2_M_FP_S, I1 }, {"cop2", "C", 0, (int) M_COP2, INSN_MACRO, 0, I1, IOCT|IOCTP|IOCT2 }, {"cop3", "C", 0, (int) M_COP3, INSN_MACRO, 0, I1, IOCT|IOCTP|IOCT2 }, +/* RFE conflicts with the new Virt spec instruction tlbgp. */ +{"rfe", "", 0x42000010, 0xffffffff, 0, 0, I1|T3 }, }; #define MIPS_NUM_OPCODES \ -- cgit v1.1