[prev in list] [next in list] [prev in thread] [next in thread] 

List:       binutils
Subject:    Re: [patch] GAS supports for MIPS32 MT ASE
From:       "Chao-ying Fu" <fu () mips ! com>
Date:       2005-08-31 0:47:53
Message-ID: 000b01c5adc5$9f59c430$a914a8c0 () MIPS ! COM
[Download RAW message or body]

Hello,

  Here is the latest patch with the change: -mmt/-mno-mt.
Also, "mips32-mt.d" is changed to use "-mmt".
I built and tested for mipsisa32-elf and mipsisa64-elf.  No
new regression.  Any comments?  Thanks!

Regards,
Chao-ying

include/opcode/ChangeLog
2005-08-30  Chao-ying Fu  <fu@mips.com>

    * mips.h (OP_SH_MT_U, OP_MASK_MT_U, OP_SH_MT_H, OP_MASK_MT_H,
    OP_SH_MTACC_T, OP_MASK_MTACC_T, OP_SH_MTACC_D, OP_MASK_MTACC_D): New
    define.
    Document !, $, *, &, g, +t, +T operand formats for MT instructions.
    (INSN_ASE_MASK): Update to include INSN_MT.
    (INSN_MT): New define for MT ASE.

opcodes/ChangeLog
2005-08-30  Chao-ying Fu  <fu@mips.com>

    * mips-opc.c (MT32): New define.
    (mips_builtin_opcodes): Move "bc0f", "bc0fl", "bc0t", "bc0tl" to the
    bottom to avoid opcode collision with "mftr" and "mttr".
    Add MT instructions.
    * mips-dis.c (mips_arch_choices): Enable INSN_MT for mips32r2.
    (print_insn_args): Add supports for +t, +T, !, $, *, &, g operand
    formats.

gas/ChangeLog
2005-08-30  Chao-ying Fu  <fu@mips.com>

    * config/tc-mips.c (mips_set_options): Add ase_mt for MT instructions.
    (mips_opts): Add -1 to initialize ase_mt.
    (file_ase_mt): New variable for -mmt.
    (CPU_HAS_MT): New define.
    (validate_mips_insn): Add supports for +t, +T, !, $, *, &, g operand
    formats.
    (mips_ip): Check ase_mt to enable MT instructions.
    Handle !, $, *, &, +T, +t, g operand formats.
    For "mftc1", "mfthc1", "cftc1", "mttc1", "mtthc1", "cttc1", we allow
    odd float registers.
    (OPTION_MT, OPTION_NO_MT): New define.
    (OPTION_COMPAT_ARCH_BASE): Change because of inserting MT define.
    (md_parse_option): Parse OPTION_MT and OPTION_NO_MT.
    (mips_after_parse_args): Set ase_mt based on CPU.
    (s_mipsset): Handle ".set mt" and ".set nomt".
    (mips_elf_final_processing): Remind of adding new flag for MT ASE.
    (md_show_usage): Show usage of -mmt and -mno-mt.

gas/testsuite/ChangeLog
2005-08-30  Chao-ying Fu  <fu@mips.com>

    * gas/mips/mips.exp: Run MT test for mips32r2 only.
    * gas/mips/mips32-mt.[sdl]: New test.

----- Original Message ----- 
From: "Eric Christopher" <echristo@apple.com>
To: "Daniel Jacobowitz" <drow@false.org>
Cc: "Chao-ying Fu" <fu@mips.com>; "Thiemo Seufer" <ths@networkno.de>;
"Maciej W. Rozycki" <macro@linux-mips.org>; "Thekkath, Radhika"
<radhika@mips.com>; <binutils@sourceware.org>
Sent: Tuesday, August 30, 2005 5:25 PM
Subject: Re: [patch] GAS supports for MIPS32 MT ASE


> >
> > ... please don't.  The other options should be fixed and only
> > compatibility aliases kept, IMO.
>
> OK. :)
>
> I didn't have a strong opinion either way.
>
> -eric
>

["src.diff" (application/octet-stream)]

Index: include/opcode/mips.h
===================================================================
RCS file: /cvs/src/src/include/opcode/mips.h,v
retrieving revision 1.44
diff -c -3 -p -r1.44 mips.h
*** include/opcode/mips.h	25 Aug 2005 18:09:24 -0000	1.44
--- include/opcode/mips.h	31 Aug 2005 00:10:28 -0000
*************** Software Foundation, 51 Franklin Street 
*** 170,175 ****
--- 170,185 ----
  #define OP_SH_RDDSP		16
  #define OP_MASK_RDDSP		0x3f
  
+ /* MIPS MT ASE */
+ #define OP_SH_MT_U		5
+ #define OP_MASK_MT_U		0x1
+ #define OP_SH_MT_H		4
+ #define OP_MASK_MT_H		0x1
+ #define OP_SH_MTACC_T		18
+ #define OP_MASK_MTACC_T		0x3
+ #define OP_SH_MTACC_D		13
+ #define OP_MASK_MTACC_D		0x3
+ 
  #define	OP_OP_COP0		0x10
  #define	OP_OP_COP1		0x11
  #define	OP_OP_COP2		0x12
*************** struct mips_opcode
*** 331,336 ****
--- 341,355 ----
     "'" 6 bit unsigned immediate (OP_*_RDDSP)
     "@" 10 bit signed immediate (OP_*_IMM10)
  
+    MT ASE usage:
+    "!" 1 bit immediate at bit 5
+    "$" 1 bit immediate at bit 4
+    "*" 2 bit dsp/smartmips accumulator register (OP_*_MTACC_T)
+    "&" 2 bit dsp/smartmips accumulator register (OP_*_MTACC_D)
+    "g" 5 bit coprocessor 1 and 2 destination register (OP_*_RD)
+    "+t" 5 bit coprocessor 0 destination register (OP_*_RT)
+    "+T" 5 bit coprocessor 0 destination register (OP_*_RT) - disassembly only
+ 
     Other:
     "()" parens surrounding optional value
     ","  separates operands
*************** struct mips_opcode
*** 339,351 ****
  
     Characters used so far, for quick reference when adding more:
     "34567890"
!    "%[]<>(),+:'@"
     "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
!    "abcdefhijklopqrstuvwxz"
  
     Extension character sequences used so far ("+" followed by the
     following), for quick reference when adding more:
!    "ABCDEFGHI"
  */
  
  /* These are the bits which may be set in the pinfo field of an
--- 358,371 ----
  
     Characters used so far, for quick reference when adding more:
     "34567890"
!    "%[]<>(),+:'@!$*&"
     "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
!    "abcdefghijklopqrstuvwxz"
  
     Extension character sequences used so far ("+" followed by the
     following), for quick reference when adding more:
!    "ABCDEFGHIT"
!    "t"
  */
  
  /* These are the bits which may be set in the pinfo field of an
*************** struct mips_opcode
*** 447,453 ****
  #define INSN_ISA64R2              0x00000100
  
  /* Masks used for MIPS-defined ASEs.  */
! #define INSN_ASE_MASK		  0x0000f000
  
  /* DSP ASE */ 
  #define INSN_DSP                  0x00001000
--- 467,473 ----
  #define INSN_ISA64R2              0x00000100
  
  /* Masks used for MIPS-defined ASEs.  */
! #define INSN_ASE_MASK		  0x0400f000
  
  /* DSP ASE */ 
  #define INSN_DSP                  0x00001000
*************** struct mips_opcode
*** 480,485 ****
--- 500,507 ----
  #define INSN_5400		  0x01000000
  /* NEC VR5500 instruction.  */
  #define INSN_5500		  0x02000000
+ /* MT ASE */
+ #define INSN_MT                   0x04000000
  
  /* MIPS ISA defines, use instead of hardcoding ISA level.  */
  
Index: opcodes/mips-opc.c
===================================================================
RCS file: /cvs/src/src/opcodes/mips-opc.c,v
retrieving revision 1.52
diff -c -3 -p -r1.52 mips-opc.c
*** opcodes/mips-opc.c	25 Aug 2005 18:12:43 -0000	1.52
--- opcodes/mips-opc.c	31 Aug 2005 00:10:29 -0000
*************** Software Foundation, 51 Franklin Street 
*** 146,151 ****
--- 146,154 ----
  #define DSP_VOLA	INSN_TRAP
  #define D32	(INSN_DSP)
  
+ /* MIPS MT ASE support.  */
+ #define MT32	(INSN_MT)
+ 
  /* The order of overloaded instructions matters.  Label arguments and
     register arguments look the same. Instructions that can have either
     for arguments must apear in the correct order in this table for the
*************** const struct mips_opcode mips_builtin_op
*** 220,229 ****
  {"andi",    "t,r,i",	0x30000000, 0xfc000000,	WR_t|RD_s,		0,		I1	},
  /* b is at the top of the table.  */
  /* bal is at the top of the table.  */
! {"bc0f",    "p",	0x41000000, 0xffff0000,	CBD|RD_CC,		0,		I1	},
! {"bc0fl",   "p",	0x41020000, 0xffff0000,	CBL|RD_CC,		0,		I2|T3	},
! {"bc0t",    "p",	0x41010000, 0xffff0000,	CBD|RD_CC,		0,		I1	},
! {"bc0tl",   "p",	0x41030000, 0xffff0000,	CBL|RD_CC,		0,		I2|T3	},
  {"bc1any2f", "N,p",	0x45200000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
  {"bc1any2t", "N,p",	0x45210000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
  {"bc1any4f", "N,p",	0x45400000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
--- 223,229 ----
  {"andi",    "t,r,i",	0x30000000, 0xfc000000,	WR_t|RD_s,		0,		I1	},
  /* b is at the top of the table.  */
  /* bal is at the top of the table.  */
! /* bc0[tf]l? are at the bottom of the table.  */
  {"bc1any2f", "N,p",	0x45200000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
  {"bc1any2t", "N,p",	0x45210000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
  {"bc1any4f", "N,p",	0x45400000, 0xffe30000,	CBD|RD_CC|FP_S,		0,		M3D	},
*************** const struct mips_opcode mips_builtin_op
*** 469,474 ****
--- 469,477 ----
  {"cfc1",    "t,S",	0x44400000, 0xffe007ff,	LCD|WR_t|RD_C1|FP_S,	0,		I1	},
  /* cfc2 is at the bottom of the table.  */
  {"cfc3",    "t,G",	0x4c400000, 0xffe007ff,	LCD|WR_t|RD_C3,		0,		I1	},
+ {"cftc1",   "d,E",	0x41000023, 0xffe007ff, TRAP|LCD|WR_d|RD_C1|FP_S, 0,		MT32	},
+ {"cftc1",   "d,T",	0x41000023, 0xffe007ff, TRAP|LCD|WR_d|RD_C1|FP_S, 0,		MT32	},
+ {"cftc2",   "d,E",	0x41000025, 0xffe007ff, TRAP|LCD|WR_d|RD_C2,	0,		MT32	},
  {"clo",     "U,s",      0x70000021, 0xfc0007ff, WR_d|WR_t|RD_s, 	0,		I32|N55 },
  {"clz",     "U,s",      0x70000020, 0xfc0007ff, WR_d|WR_t|RD_s, 	0,		I32|N55 },
  {"ctc0",    "t,G",	0x40c00000, 0xffe007ff,	COD|RD_t|WR_CC,		0,		I1	},
*************** const struct mips_opcode mips_builtin_op
*** 476,481 ****
--- 479,487 ----
  {"ctc1",    "t,S",	0x44c00000, 0xffe007ff,	COD|RD_t|WR_CC|FP_S,	0,		I1	},
  /* ctc2 is at the bottom of the table.  */
  {"ctc3",    "t,G",	0x4cc00000, 0xffe007ff,	COD|RD_t|WR_CC,		0,		I1	},
+ {"cttc1",   "t,g",	0x41800023, 0xffe007ff, TRAP|COD|RD_t|WR_CC|FP_S, 0,		MT32	},
+ {"cttc1",   "t,S",	0x41800023, 0xffe007ff, TRAP|COD|RD_t|WR_CC|FP_S, 0,		MT32	},
+ {"cttc2",   "t,g",	0x41800025, 0xffe007ff, TRAP|COD|RD_t|WR_CC,	0,		MT32	},
  {"cvt.d.l", "D,S",	0x46a00021, 0xffff003f,	WR_D|RD_S|FP_D,		0,		I3	},
  {"cvt.d.s", "D,S",	0x46000021, 0xffff003f,	WR_D|RD_S|FP_D|FP_S,	0,		I1	},
  {"cvt.d.w", "D,S",	0x46800021, 0xffff003f,	WR_D|RD_S|FP_D,		0,		I1	},
*************** const struct mips_opcode mips_builtin_op
*** 556,561 ****
--- 562,569 ----
  {"dmfc0",   "t,G",	0x40200000, 0xffe007ff, LCD|WR_t|RD_C0,		0,		I3	},
  {"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     },
+ {"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	},
  {"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     },
*************** const struct mips_opcode mips_builtin_op
*** 620,628 ****
--- 628,642 ----
  {"dsub",    "d,v,I",	0,    (int) M_DSUB_I,	INSN_MACRO,		0,		I3	},
  {"dsubu",   "d,v,t",	0x0000002f, 0xfc0007ff,	WR_d|RD_s|RD_t,		0,		I3	},
  {"dsubu",   "d,v,I",	0,    (int) M_DSUBU_I,	INSN_MACRO,		0,		I3	},
+ {"dvpe",    "",		0x41600001, 0xffffffff, TRAP,			0,		MT32	},
+ {"dvpe",    "t",	0x41600001, 0xffe0ffff, TRAP|WR_t,		0,		MT32	},
  {"ei",      "",		0x41606020, 0xffffffff,	WR_t|WR_C0,		0,		I33	},
  {"ei",      "t",	0x41606020, 0xffe0ffff,	WR_t|WR_C0,		0,		I33	},
+ {"emt",     "",		0x41600be1, 0xffffffff, TRAP,			0,		MT32	},
+ {"emt",     "t",	0x41600be1, 0xffe0ffff, TRAP|WR_t,		0,		MT32	},
  {"eret",    "",         0x42000018, 0xffffffff, 0,      		0,		I3|I32	},
+ {"evpe",    "",		0x41600021, 0xffffffff, TRAP,			0,		MT32	},
+ {"evpe",    "t",	0x41600021, 0xffe0ffff, TRAP|WR_t,		0,		MT32	},
  {"ext",     "t,r,+A,+C", 0x7c000000, 0xfc00003f, WR_t|RD_s,    		0,		I33	},
  {"floor.l.d", "D,S",	0x4620000b, 0xffff003f, WR_D|RD_S|FP_D,		0,		I3	},
  {"floor.l.s", "D,S",	0x4600000b, 0xffff003f, WR_D|RD_S|FP_S,		0,		I3	},
*************** const struct mips_opcode mips_builtin_op
*** 719,724 ****
--- 733,739 ----
  {"lwr",     "t,A(b)",	0,    (int) M_LWR_AB,	INSN_MACRO,		0,		I1	},
  {"flush",   "t,o(b)",	0x98000000, 0xfc000000,	LDD|RD_b|WR_t,		0,		I2	}, /* same */
  {"flush",   "t,A(b)",	0,    (int) M_LWR_AB,	INSN_MACRO,		0,		I2	}, /* as lwr */
+ {"fork",    "d,s,t",	0x7c000008, 0xfc0007ff, TRAP|WR_d|RD_s|RD_t,	0,		MT32	},
  {"lwu",     "t,o(b)",	0x9c000000, 0xfc000000,	LDD|RD_b|WR_t,		0,		I3	},
  {"lwu",     "t,A(b)",	0,    (int) M_LWU_AB,	INSN_MACRO,		0,		I3	},
  {"lwxc1",   "D,t(b)",	0x4c000000, 0xfc00f83f, LDD|WR_D|RD_t|RD_b,	0,		I4	},
*************** const struct mips_opcode mips_builtin_op
*** 755,760 ****
--- 770,793 ----
  {"max.qh",  "X,Y,Q",	0x78200007, 0xfc20003f,	WR_D|RD_S|RD_T|FP_D,	0,		MX	},
  {"mfpc",    "t,P",	0x4000c801, 0xffe0ffc1,	LCD|WR_t|RD_C0,		0,		M1|N5	},
  {"mfps",    "t,P",	0x4000c800, 0xffe0ffc1,	LCD|WR_t|RD_C0,		0,		M1|N5	},
+ {"mftacx",  "d",	0x41020021, 0xffff07ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mftacx",  "d,*",	0x41020021, 0xfff307ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mftc0",   "d,+t",	0x41000000, 0xffe007ff, TRAP|LCD|WR_d|RD_C0,	0,		MT32	},
+ {"mftc0",   "d,+T",	0x41000000, 0xffe007f8, TRAP|LCD|WR_d|RD_C0,	0,		MT32	},
+ {"mftc0",   "d,E,H",	0x41000000, 0xffe007f8, TRAP|LCD|WR_d|RD_C0,	0,		MT32	},
+ {"mftc1",   "d,T",	0x41000022, 0xffe007ff, TRAP|LCD|WR_d|RD_T|FP_S, 0,		MT32	},
+ {"mftc1",   "d,E",	0x41000022, 0xffe007ff, TRAP|LCD|WR_d|RD_T|FP_S, 0,		MT32	},
+ {"mftc2",   "d,E",	0x41000024, 0xffe007ff, TRAP|LCD|WR_d|RD_C2,	0,		MT32	},
+ {"mftdsp",  "d",	0x41100021, 0xffff07ff, TRAP|WR_d,		0,		MT32	},
+ {"mftgpr",  "d,t",	0x41000020, 0xffe007ff, TRAP|WR_d|RD_t,		0,		MT32	},
+ {"mfthc1",  "d,T",	0x41000032, 0xffe007ff, TRAP|LCD|WR_d|RD_T|FP_D, 0,		MT32	},
+ {"mfthc1",  "d,E",	0x41000032, 0xffe007ff, TRAP|LCD|WR_d|RD_T|FP_D, 0,		MT32	},
+ {"mfthc2",  "d,E",	0x41000034, 0xffe007ff, TRAP|LCD|WR_d|RD_C2,	0,		MT32	},
+ {"mfthi",   "d",	0x41010021, 0xffff07ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mfthi",   "d,*",	0x41010021, 0xfff307ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mftlo",   "d",	0x41000021, 0xffff07ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mftlo",   "d,*",	0x41000021, 0xfff307ff, TRAP|WR_d|RD_a,		0,		MT32	},
+ {"mftr",    "t,d,!,H,$", 0x41000000, 0xffe007c8, TRAP|WR_d,		0,		MT32	},
  {"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     },
*************** const struct mips_opcode mips_builtin_op
*** 836,841 ****
--- 869,892 ----
  {"mthi",    "s,7",	0x00000011, 0xfc1fe7ff, RD_s|WR_HI,		0,		D32	},
  {"mtlo",    "s",	0x00000013, 0xfc1fffff,	RD_s|WR_LO,		0,		I1	},
  {"mtlo",    "s,7",	0x00000013, 0xfc1fe7ff, RD_s|WR_LO,		0,		D32	},
+ {"mttc0",   "t,G",	0x41800000, 0xffe007ff, TRAP|COD|RD_t|WR_C0|WR_CC, 0,		MT32	},
+ {"mttc0",   "t,+D",	0x41800000, 0xffe007f8, TRAP|COD|RD_t|WR_C0|WR_CC, 0,		MT32	},
+ {"mttc0",   "t,G,H",	0x41800000, 0xffe007f8, TRAP|COD|RD_t|WR_C0|WR_CC, 0,		MT32	},
+ {"mttc1",   "t,S",	0x41800022, 0xffe007ff, TRAP|COD|RD_t|WR_S|FP_S, 0,		MT32	},
+ {"mttc1",   "t,G",	0x41800022, 0xffe007ff, TRAP|COD|RD_t|WR_S|FP_S, 0,		MT32	},
+ {"mttc2",   "t,g",	0x41800024, 0xffe007ff, TRAP|COD|RD_t|WR_C2|WR_CC, 0,		MT32	},
+ {"mttacx",  "t",	0x41801021, 0xffe0ffff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mttacx",  "t,&",	0x41801021, 0xffe09fff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mttdsp",  "t",	0x41808021, 0xffe0ffff, TRAP|RD_t,		0,		MT32	},
+ {"mttgpr",  "t,d",	0x41800020, 0xffe007ff, TRAP|WR_d|RD_t,		0,		MT32	},
+ {"mtthc1",  "t,S",	0x41800032, 0xffe007ff, TRAP|COD|RD_t|WR_S|FP_D, 0,		MT32	},
+ {"mtthc1",  "t,G",	0x41800032, 0xffe007ff, TRAP|COD|RD_t|WR_S|FP_D, 0,		MT32	},
+ {"mtthc2",  "t,g",	0x41800034, 0xffe007ff, TRAP|COD|RD_t|WR_C2|WR_CC, 0,		MT32	},
+ {"mtthi",   "t",	0x41800821, 0xffe0ffff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mtthi",   "t,&",	0x41800821, 0xffe09fff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mttlo",   "t",	0x41800021, 0xffe0ffff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mttlo",   "t,&",	0x41800021, 0xffe09fff, TRAP|WR_a|RD_t,		0,		MT32	},
+ {"mttr",    "t,d,!,H,$", 0x41800000, 0xffe007c8, TRAP|RD_t,		0,		MT32	},
  {"mul.d",   "D,V,T",	0x46200002, 0xffe0003f,	WR_D|RD_S|RD_T|FP_D,	0,		I1	},
  {"mul.s",   "D,V,T",	0x46000002, 0xffe0003f,	WR_D|RD_S|RD_T|FP_S,	0,		I1	},
  {"mul.ob",  "X,Y,Q",	0x78000030, 0xfc20003f,	WR_D|RD_S|RD_T|FP_D,	0,		MX|SB1	},
*************** const struct mips_opcode mips_builtin_op
*** 1209,1214 ****
--- 1260,1267 ----
  {"xor.ob",  "D,S,k",	0x4bc0000d, 0xffe0003f,	WR_D|RD_S|RD_T,		0,		N54	},
  {"xor.qh",  "X,Y,Q",	0x7820000d, 0xfc20003f,	WR_D|RD_S|RD_T|FP_D,	0,		MX	},
  {"xori",    "t,r,i",	0x38000000, 0xfc000000,	WR_t|RD_s,		0,		I1	},
+ {"yield",   "s",	0x7c000009, 0xfc1fffff, TRAP|RD_s,		0,		MT32	},
+ {"yield",   "d,s",	0x7c000009, 0xfc1f07ff, TRAP|WR_d|RD_s,		0,		MT32	},
  
  /* Coprocessor 2 move/branch operations overlap with VR5400 .ob format
     instructions so they are here for the latters to take precedence.  */
*************** const struct mips_opcode mips_builtin_op
*** 1352,1357 ****
--- 1405,1415 ----
  {"subu_s.qb", "d,s,t",	0x7c000150, 0xfc0007ff, WR_d|RD_s|RD_t,		0,		D32	},
  {"wrdsp",   "s",	0x7c1ffcf8, 0xfc1fffff, RD_s|DSP_VOLA,		0,		D32	},
  {"wrdsp",   "s,8",	0x7c0004f8, 0xfc1e07ff, RD_s|DSP_VOLA,		0,		D32	},
+ /* Move bc0* after mftr and mttr to avoid opcode collision.  */
+ {"bc0f",    "p",	0x41000000, 0xffff0000,	CBD|RD_CC,		0,		I1	},
+ {"bc0fl",   "p",	0x41020000, 0xffff0000,	CBL|RD_CC,		0,		I2|T3	},
+ {"bc0t",    "p",	0x41010000, 0xffff0000,	CBD|RD_CC,		0,		I1	},
+ {"bc0tl",   "p",	0x41030000, 0xffff0000,	CBL|RD_CC,		0,		I2|T3	},
  };
  
  #define MIPS_NUM_OPCODES \
Index: opcodes/mips-dis.c
===================================================================
RCS file: /cvs/src/src/opcodes/mips-dis.c,v
retrieving revision 1.53
diff -c -3 -p -r1.53 mips-dis.c
*** opcodes/mips-dis.c	25 Aug 2005 18:12:44 -0000	1.53
--- opcodes/mips-dis.c	31 Aug 2005 00:10:29 -0000
*************** const struct mips_arch_choice mips_arch_
*** 376,382 ****
      mips_hwr_names_numeric },
  
    { "mips32r2",	1, bfd_mach_mipsisa32r2, CPU_MIPS32R2,
!     ISA_MIPS32R2 | INSN_MIPS16 | INSN_DSP,
      mips_cp0_names_mips3264r2,
      mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
      mips_hwr_names_mips3264r2 },
--- 376,382 ----
      mips_hwr_names_numeric },
  
    { "mips32r2",	1, bfd_mach_mipsisa32r2, CPU_MIPS32R2,
!     ISA_MIPS32R2 | INSN_MIPS16 | INSN_DSP | INSN_MT,
      mips_cp0_names_mips3264r2,
      mips_cp0sel_names_mips3264r2, ARRAY_SIZE (mips_cp0sel_names_mips3264r2),
      mips_hwr_names_mips3264r2 },
*************** print_insn_args (const char *d,
*** 771,776 ****
--- 771,804 ----
  	      (*info->fprintf_func) (info->stream, "0x%x", msbd + 1);
  	      break;
  
+ 	    case 't': /* Coprocessor 0 reg name */
+ 	      (*info->fprintf_func) (info->stream, "%s",
+ 				     mips_cp0_names[(l >> OP_SH_RT) &
+ 						     OP_MASK_RT]);
+ 	      break;
+ 
+ 	    case 'T': /* Coprocessor 0 reg name */
+ 	      {
+ 		const struct mips_cp0sel_name *n;
+ 		unsigned int cp0reg, sel;
+ 
+ 		cp0reg = (l >> OP_SH_RT) & OP_MASK_RT;
+ 		sel = (l >> OP_SH_SEL) & OP_MASK_SEL;
+ 
+ 		/* CP0 register including 'sel' code for mftc0, to be
+ 		   printed textually if known.  If not known, print both
+ 		   CP0 register name and sel numerically since CP0 register
+ 		   with sel 0 may have a name unrelated to register being
+ 		   printed.  */
+ 		n = lookup_mips_cp0sel_name(mips_cp0sel_names,
+ 					    mips_cp0sel_names_len, cp0reg, sel);
+ 		if (n != NULL)
+ 		  (*info->fprintf_func) (info->stream, "%s", n->name);
+ 		else
+ 		  (*info->fprintf_func) (info->stream, "$%d,%d", cp0reg, sel);
+ 		break;
+ 	      }
+ 
  	    default:
  	      /* xgettext:c-format */
  	      (*info->fprintf_func) (info->stream,
*************** print_insn_args (const char *d,
*** 841,846 ****
--- 869,900 ----
  	  (*info->fprintf_func) (info->stream, "%d", delta);
  	  break;
  
+ 	case '!':
+ 	  (*info->fprintf_func) (info->stream, "%ld",
+ 				 (l >> OP_SH_MT_U) & OP_MASK_MT_U);
+ 	  break;
+ 
+ 	case '$':
+ 	  (*info->fprintf_func) (info->stream, "%ld",
+ 				 (l >> OP_SH_MT_H) & OP_MASK_MT_H);
+ 	  break;
+ 
+ 	case '*':
+ 	  (*info->fprintf_func) (info->stream, "$ac%ld",
+ 				 (l >> OP_SH_MTACC_T) & OP_MASK_MTACC_T);
+ 	  break;
+ 
+ 	case '&':
+ 	  (*info->fprintf_func) (info->stream, "$ac%ld",
+ 				 (l >> OP_SH_MTACC_D) & OP_MASK_MTACC_D);
+ 	  break;
+ 
+ 	case 'g':
+ 	  /* Coprocessor register for CTTC1, MTTC2, MTHC2, CTTC2.  */
+ 	  (*info->fprintf_func) (info->stream, "$%ld",
+ 				 (l >> OP_SH_RD) & OP_MASK_RD);
+ 	  break;
+ 
  	case 's':
  	case 'b':
  	case 'r':
Index: gas/config/tc-mips.c
===================================================================
RCS file: /cvs/src/src/gas/config/tc-mips.c,v
retrieving revision 1.318
diff -c -3 -p -r1.318 tc-mips.c
*** gas/config/tc-mips.c	25 Aug 2005 18:17:36 -0000	1.318
--- gas/config/tc-mips.c	31 Aug 2005 00:10:31 -0000
*************** struct mips_set_options
*** 194,199 ****
--- 194,200 ----
    int ase_mips3d;
    int ase_mdmx;
    int ase_dsp;
+   int ase_mt;
    /* 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
*************** static int file_mips_fp32 = -1;
*** 244,250 ****
  
  static struct mips_set_options mips_opts =
  {
!   ISA_UNKNOWN, -1, -1, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, CPU_UNKNOWN, FALSE
  };
  
  /* These variables are filled in with the masks of registers used.
--- 245,251 ----
  
  static struct mips_set_options mips_opts =
  {
!   ISA_UNKNOWN, -1, -1, -1, -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, CPU_UNKNOWN, FALSE
  };
  
  /* These variables are filled in with the masks of registers used.
*************** static int file_ase_mdmx;
*** 272,277 ****
--- 273,282 ----
     command line (e.g., by -march).  */
  static int file_ase_dsp;
  
+ /* True if -mmt was passed or implied by arguments passed on the
+    command line (e.g., by -march).  */
+ static int file_ase_mt;
+ 
  /* The argument of the -march= flag.  The architecture we are assembling.  */
  static int file_mips_arch = CPU_UNKNOWN;
  static const char *mips_arch_string;
*************** static int mips_32bitmode = 0;
*** 374,379 ****
--- 379,388 ----
  #define CPU_HAS_DSP(cpu)	(FALSE                 \
  				 )
  
+ /* Return true if the given CPU supports the MT ASE.  */
+ #define CPU_HAS_MT(cpu)		(FALSE                 \
+ 				 )
+ 
  /* True if CPU has a dror instruction.  */
  #define CPU_HAS_DROR(CPU)	((CPU) == CPU_VR5400 || (CPU) == CPU_VR5500)
  
*************** validate_mips_insn (const struct mips_op
*** 7765,7770 ****
--- 7774,7782 ----
  	  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 '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;
  	  default:
  	    as_bad (_("internal: bad mips opcode (unknown extension operand type `+%c'): %s %s"),
  		    c, opc->name, opc->args);
*************** validate_mips_insn (const struct mips_op
*** 7837,7842 ****
--- 7849,7859 ----
        case '\'': USE_BITS (OP_MASK_RDDSP,	OP_SH_RDDSP);	break;
        case ':': USE_BITS (OP_MASK_DSPSFT_7,	OP_SH_DSPSFT_7);break;
        case '@': USE_BITS (OP_MASK_IMM10,	OP_SH_IMM10);	break;
+       case '!': USE_BITS (OP_MASK_MT_U,		OP_SH_MT_U);	break;
+       case '$': USE_BITS (OP_MASK_MT_H,		OP_SH_MT_H);	break;
+       case '*': USE_BITS (OP_MASK_MTACC_T,	OP_SH_MTACC_T);	break;
+       case '&': USE_BITS (OP_MASK_MTACC_D,	OP_SH_MTACC_D);	break;
+       case 'g':	USE_BITS (OP_MASK_RD,		OP_SH_RD);	break;
        default:
  	as_bad (_("internal: bad mips opcode (unknown operand type `%c'): %s %s"),
  		c, opc->name, opc->args);
*************** mips_ip (char *str, struct mips_cl_insn 
*** 7935,7940 ****
--- 7952,7958 ----
  			     | (file_ase_mips16 ? INSN_MIPS16 : 0)
  	      		     | (mips_opts.ase_mdmx ? INSN_MDMX : 0)
  	      		     | (mips_opts.ase_dsp ? INSN_DSP : 0)
+ 	      		     | (mips_opts.ase_mt ? INSN_MT : 0)
  			     | (mips_opts.ase_mips3d ? INSN_MIPS3D : 0)),
  			    mips_opts.arch))
  	ok = TRUE;
*************** mips_ip (char *str, struct mips_cl_insn 
*** 8156,8161 ****
--- 8174,8233 ----
  	      s = expr_end;
  	      continue;
  
+             case '!': /* mt 1-bit unsigned immediate in bit 5 */
+ 	      my_getExpression (&imm_expr, s);
+ 	      check_absolute_expr (ip, &imm_expr);
+ 	      if (imm_expr.X_add_number & ~OP_MASK_MT_U)
+ 		{
+ 		  as_warn (_("MT immediate not in range 0..%d (%lu)"),
+ 			   OP_MASK_MT_U, (unsigned long) imm_expr.X_add_number);
+ 		  imm_expr.X_add_number &= OP_MASK_MT_U;
+ 		}
+ 	      ip->insn_opcode |= imm_expr.X_add_number << OP_SH_MT_U;
+ 	      imm_expr.X_op = O_absent;
+ 	      s = expr_end;
+ 	      continue;
+ 
+             case '$': /* mt 1-bit unsigned immediate in bit 4 */
+ 	      my_getExpression (&imm_expr, s);
+ 	      check_absolute_expr (ip, &imm_expr);
+ 	      if (imm_expr.X_add_number & ~OP_MASK_MT_H)
+ 		{
+ 		  as_warn (_("MT immediate not in range 0..%d (%lu)"),
+ 			   OP_MASK_MT_H, (unsigned long) imm_expr.X_add_number);
+ 		  imm_expr.X_add_number &= OP_MASK_MT_H;
+ 		}
+ 	      ip->insn_opcode |= imm_expr.X_add_number << OP_SH_MT_H;
+ 	      imm_expr.X_op = O_absent;
+ 	      s = expr_end;
+ 	      continue;
+ 
+ 	    case '*': /* four dsp accumulators in bits 18,19 */ 
+ 	      if (s[0] == '$' && s[1] == 'a' && s[2] == 'c' &&
+ 		  s[3] >= '0' && s[3] <= '3')
+ 		{
+ 		  regno = s[3] - '0';
+ 		  s += 4;
+ 		  ip->insn_opcode |= regno << OP_SH_MTACC_T;
+ 		  continue;
+ 		}
+ 	      else
+ 		as_bad (_("Invalid dsp/smartmips acc register"));
+ 	      break;
+ 
+ 	    case '&': /* four dsp accumulators in bits 13,14 */ 
+ 	      if (s[0] == '$' && s[1] == 'a' && s[2] == 'c' &&
+ 		  s[3] >= '0' && s[3] <= '3')
+ 		{
+ 		  regno = s[3] - '0';
+ 		  s += 4;
+ 		  ip->insn_opcode |= regno << OP_SH_MTACC_D;
+ 		  continue;
+ 		}
+ 	      else
+ 		as_bad (_("Invalid dsp/smartmips acc register"));
+ 	      break;
+ 
  	    case ',':
  	      if (*s++ == *args)
  		continue;
*************** do_msbd:
*** 8308,8313 ****
--- 8380,8413 ----
  		  s = expr_end;
  		  continue;
  
+ 		case 'T': /* Coprocessor register */
+ 		  /* +T is for disassembly only; never match.  */
+ 		  break;
+ 
+ 		case 't': /* Coprocessor register number */
+ 		  if (s[0] == '$' && ISDIGIT (s[1]))
+ 		    {
+ 		      ++s;
+ 		      regno = 0;
+ 		      do
+ 		        {
+ 			  regno *= 10;
+ 			  regno += *s - '0';
+ 			  ++s;
+ 			}
+ 		      while (ISDIGIT (*s));
+ 		      if (regno > 31)
+ 			as_bad (_("Invalid register number (%d)"), regno);
+ 		      else
+ 			{
+ 			  ip->insn_opcode |= regno << OP_SH_RT;
+ 			  continue;
+ 			}
+ 		    }
+ 		  else
+ 		    as_bad (_("Invalid coprocessor 0 register number"));
+ 		  break;
+ 
  		default:
  		  as_bad (_("internal: bad mips opcode (unknown extension operand type `+%c'): %s %s"),
  		    *args, insn->name, insn->args);
*************** do_msbd:
*** 8442,8447 ****
--- 8542,8548 ----
  	    case 'x':		/* ignore register name */
  	    case 'z':		/* must be zero register */
  	    case 'U':           /* destination register (clo/clz).  */
+ 	    case 'g':		/* coprocessor destination register */
  	      s_reset = s;
  	      if (s[0] == '$')
  		{
*************** do_msbd:
*** 8566,8571 ****
--- 8667,8673 ----
  		    case 'd':
  		    case 'G':
  		    case 'K':
+ 		    case 'g':
  		      INSERT_OPERAND (RD, *ip, regno);
  		      break;
  		    case 'U':
*************** do_msbd:
*** 8681,8687 ****
  			    || strcmp (str, "lwc1") == 0
  			    || strcmp (str, "swc1") == 0
  			    || strcmp (str, "l.s") == 0
! 			    || strcmp (str, "s.s") == 0))
  		    as_warn (_("Float register should be even, was %d"),
  			     regno);
  
--- 8783,8795 ----
  			    || strcmp (str, "lwc1") == 0
  			    || strcmp (str, "swc1") == 0
  			    || strcmp (str, "l.s") == 0
! 			    || strcmp (str, "s.s") == 0
! 			    || strcmp (str, "mftc1") == 0
! 			    || strcmp (str, "mfthc1") == 0
! 			    || strcmp (str, "cftc1") == 0
! 			    || strcmp (str, "mttc1") == 0
! 			    || strcmp (str, "mtthc1") == 0
! 			    || strcmp (str, "cttc1") == 0))
  		    as_warn (_("Float register should be even, was %d"),
  			     regno);
  
*************** struct option md_longopts[] =
*** 10222,10230 ****
    {"mdsp", no_argument, NULL, OPTION_DSP},
  #define OPTION_NO_DSP (OPTION_ASE_BASE + 7)
    {"mno-dsp", no_argument, NULL, OPTION_NO_DSP},
  
    /* Old-style architecture options.  Don't add more of these.  */
! #define OPTION_COMPAT_ARCH_BASE (OPTION_ASE_BASE + 8)
  #define OPTION_M4650 (OPTION_COMPAT_ARCH_BASE + 0)
    {"m4650", no_argument, NULL, OPTION_M4650},
  #define OPTION_NO_M4650 (OPTION_COMPAT_ARCH_BASE + 1)
--- 10330,10342 ----
    {"mdsp", no_argument, NULL, OPTION_DSP},
  #define OPTION_NO_DSP (OPTION_ASE_BASE + 7)
    {"mno-dsp", no_argument, NULL, OPTION_NO_DSP},
+ #define OPTION_MT (OPTION_ASE_BASE + 8)
+   {"mmt", no_argument, NULL, OPTION_MT},
+ #define OPTION_NO_MT (OPTION_ASE_BASE + 9)
+   {"mno-mt", no_argument, NULL, OPTION_NO_MT},
  
    /* Old-style architecture options.  Don't add more of these.  */
! #define OPTION_COMPAT_ARCH_BASE (OPTION_ASE_BASE + 10)
  #define OPTION_M4650 (OPTION_COMPAT_ARCH_BASE + 0)
    {"m4650", no_argument, NULL, OPTION_M4650},
  #define OPTION_NO_M4650 (OPTION_COMPAT_ARCH_BASE + 1)
*************** md_parse_option (int c, char *arg)
*** 10484,10489 ****
--- 10596,10609 ----
        mips_opts.ase_dsp = 0;
        break;
  
+     case OPTION_MT:
+       mips_opts.ase_mt = 1;
+       break;
+ 
+     case OPTION_NO_MT:
+       mips_opts.ase_mt = 0;
+       break;
+ 
      case OPTION_MIPS16:
        mips_opts.mips16 = 1;
        mips_no_prev_insn ();
*************** mips_after_parse_args (void)
*** 10840,10851 ****
--- 10960,10974 ----
      mips_opts.ase_mdmx = (CPU_HAS_MDMX (file_mips_arch)) ? 1 : 0;
    if (mips_opts.ase_dsp == -1)
      mips_opts.ase_dsp = (CPU_HAS_DSP (file_mips_arch)) ? 1 : 0;
+   if (mips_opts.ase_mt == -1)
+     mips_opts.ase_mt = (CPU_HAS_MT (file_mips_arch)) ? 1 : 0;
  
    file_mips_isa = mips_opts.isa;
    file_ase_mips16 = mips_opts.mips16;
    file_ase_mips3d = mips_opts.ase_mips3d;
    file_ase_mdmx = mips_opts.ase_mdmx;
    file_ase_dsp = mips_opts.ase_dsp;
+   file_ase_mt = mips_opts.ase_mt;
    mips_opts.gp32 = file_mips_gp32;
    mips_opts.fp32 = file_mips_fp32;
  
*************** s_mipsset (int x ATTRIBUTE_UNUSED)
*** 11787,11792 ****
--- 11910,11919 ----
      mips_opts.ase_dsp = 1;
    else if (strcmp (name, "nodsp") == 0)
      mips_opts.ase_dsp = 0;
+   else if (strcmp (name, "mt") == 0)
+     mips_opts.ase_mt = 1;
+   else if (strcmp (name, "nomt") == 0)
+     mips_opts.ase_mt = 0;
    else if (strncmp (name, "mips", 4) == 0 || strncmp (name, "arch=", 5) == 0)
      {
        int reset = 0;
*************** mips_elf_final_processing (void)
*** 13523,13528 ****
--- 13650,13657 ----
    /* 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.  */
+   /* We may need to define a new flag for MT ASE, and set this flag when
+      file_ase_mt is true.  */
    if (file_ase_mips16)
      elf_elfheader (stdoutput)->e_flags |= EF_MIPS_ARCH_ASE_M16;
  #if 0 /* XXX FIXME */
*************** MIPS options:\n\
*** 14230,14235 ****
--- 14359,14367 ----
  -mdsp			generate DSP instructions\n\
  -mno-dsp		do not generate DSP instructions\n"));
    fprintf (stream, _("\
+ -mmt			generate MT instructions\n\
+ -mno-mt			do not generate MT instructions\n"));
+   fprintf (stream, _("\
  -mfix-vr4120		work around certain VR4120 errata\n\
  -mfix-vr4130		work around VR4130 mflo/mfhi errata\n\
  -mgp32			use 32-bit GPRs, regardless of the chosen ISA\n\
Index: gas/testsuite/gas/mips/mips.exp
===================================================================
RCS file: /cvs/src/src/gas/testsuite/gas/mips/mips.exp,v
retrieving revision 1.108
diff -c -3 -p -r1.108 mips.exp
*** gas/testsuite/gas/mips/mips.exp	25 Aug 2005 18:21:47 -0000	1.108
--- gas/testsuite/gas/mips/mips.exp	31 Aug 2005 00:10:31 -0000
*************** if { [istarget mips*-*-*] } then {
*** 763,768 ****
--- 763,769 ----
      run_list_test "noat-7" ""
  
      run_dump_test_arches "mips32-dsp"	[mips_arch_list_matching mips32 !sb1]
+     run_dump_test_arches "mips32-mt"	[mips_arch_list_matching mips32r2 !gpr64]
  
      if { $elf && !$no_mips16 } {
  	run_dump_test "mips16-dwarf2"

["mips32-mt.s" (application/octet-stream)]
["mips32-mt.l" (application/octet-stream)]
["mips32-mt.d" (application/octet-stream)]

[prev in list] [next in list] [prev in thread] [next in thread] 

Configure | About | News | Add a list | Sponsored by KoreLogic