This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
Re: [PATCH] [MIPS] Fix operands for microMIPS SW16, SH16 and SB16
- From: Richard Sandiford <rdsandiford at googlemail dot com>
- To: Matthew Fortune <Matthew dot Fortune at imgtec dot com>
- Cc: "Moore\, Catherine" <Catherine_Moore at mentor dot com>, "gcc-patches\ at gcc dot gnu dot org" <gcc-patches at gcc dot gnu dot org>, rguenther at suse dot de, jakub at redhat dot com
- Date: Sat, 12 Apr 2014 11:40:45 +0100
- Subject: Re: [PATCH] [MIPS] Fix operands for microMIPS SW16, SH16 and SB16
- Authentication-results: sourceware.org; auth=none
- References: <FD3DCEAC5B03E9408544A1E416F1124201497ED8A4 at NA-MBX-04 dot mgc dot mentorg dot com> <6D39441BF12EF246A7ABCE6654B023534E17E5 at LEMAIL01 dot le dot imgtec dot org> <87zjjrxb11 dot fsf at talisman dot default>
Richard Sandiford <rdsandiford@googlemail.com> writes:
> Matthew Fortune <Matthew.Fortune@imgtec.com> writes:
>> Hi Catherine/Richard,
>>
>> I think there may be some impact on register move costs by introducing
>> this class.
>
> Yeah, I was worried about that too. I'm going to do some code comparison
> tests for SE and MIPS16 to see what happens.
OK, I compared the .s testsuite output for -O, -O2, -O3, -Os,
"-O -mips16 -mabi=32" and "-Os -mips16 -mabi=32" on mips64-linux-gnu.
I also tried CSiBE with -O2 and "-Os -mips16 -mabi=32". The code was
identical in all cases so I think we should be OK.
I went ahead and applied the adjusted version of the patch to trunk
as below (because I wanted to add a testcase too).
Adding a new register class is definitely a bit invasive for this stage
of 4.9. OTOH microMIPS is a new feature and it would be good to have
it working in 4.9.0. Since the testing suggests that the patch really
doesn't affect non-microMIPS code, I'd like it to go in 4.9 now.
Richard, Jakub, would that be OK?
Thanks,
Richard
gcc/
2014-04-12 Catherine Moore <clm@codesourcery.com>
* config/mips/constraints.md: Add new register constraint "kb".
* config/mips/mips.md (*mov<mode>_internal): Use constraint "kb".
(*movhi_internal): Likewise.
(*movqi_internal): Likewise.
* config/mips/mips.h (M16_STORE_REGS): New register class.
(REG_CLASS_NAMES): Add M16_STORE_REGS.
(REG_CLASS_CONTENTS): Likewise.
* config/mips/mips.c (mips_regno_to_class): Add M16_STORE_REGS.
gcc/testsuite/
* gcc.target/mips/umips-store16-1.c: New test.
Index: gcc/config/mips/constraints.md
===================================================================
--- gcc/config/mips/constraints.md 2014-04-12 10:36:09.105788710 +0100
+++ gcc/config/mips/constraints.md 2014-04-12 10:38:48.895224932 +0100
@@ -92,6 +92,9 @@ (define_register_constraint "D" "COP3_RE
;; but the DSP version allows any accumulator target.
(define_register_constraint "ka" "ISA_HAS_DSP_MULT ? ACC_REGS : MD_REGS")
+(define_register_constraint "kb" "M16_STORE_REGS"
+ "@internal")
+
(define_constraint "kf"
"@internal"
(match_operand 0 "force_to_mem_operand"))
Index: gcc/config/mips/mips.md
===================================================================
--- gcc/config/mips/mips.md 2014-04-12 10:36:09.105788710 +0100
+++ gcc/config/mips/mips.md 2014-04-12 10:38:48.925225200 +0100
@@ -4437,7 +4437,7 @@ (define_expand "mov<mode>"
(define_insn "*mov<mode>_internal"
[(set (match_operand:IMOVE32 0 "nonimmediate_operand" "=d,!u,!u,d,e,!u,!ks,d,ZS,ZT,m,*f,*f,*d,*m,*d,*z,*a,*d,*B*C*D,*B*C*D,*d,*m")
- (match_operand:IMOVE32 1 "move_operand" "d,J,Udb7,Yd,Yf,ZT,ZS,m,!ks,!u,dJ,*d*J,*m,*f,*f,*z,*d,*J*d,*a,*d,*m,*B*C*D,*B*C*D"))]
+ (match_operand:IMOVE32 1 "move_operand" "d,J,Udb7,Yd,Yf,ZT,ZS,m,!ks,!kb,dJ,*d*J,*m,*f,*f,*z,*d,*J*d,*a,*d,*m,*B*C*D,*B*C*D"))]
"!TARGET_MIPS16
&& (register_operand (operands[0], <MODE>mode)
|| reg_or_0_operand (operands[1], <MODE>mode))"
@@ -4578,7 +4578,7 @@ (define_expand "movhi"
(define_insn "*movhi_internal"
[(set (match_operand:HI 0 "nonimmediate_operand" "=d,!u,d,!u,d,ZU,m,*a,*d")
- (match_operand:HI 1 "move_operand" "d,J,I,ZU,m,!u,dJ,*d*J,*a"))]
+ (match_operand:HI 1 "move_operand" "d,J,I,ZU,m,!kb,dJ,*d*J,*a"))]
"!TARGET_MIPS16
&& (register_operand (operands[0], HImode)
|| reg_or_0_operand (operands[1], HImode))"
@@ -4654,7 +4654,7 @@ (define_expand "movqi"
(define_insn "*movqi_internal"
[(set (match_operand:QI 0 "nonimmediate_operand" "=d,!u,d,!u,d,ZV,m,*a,*d")
- (match_operand:QI 1 "move_operand" "d,J,I,ZW,m,!u,dJ,*d*J,*a"))]
+ (match_operand:QI 1 "move_operand" "d,J,I,ZW,m,!kb,dJ,*d*J,*a"))]
"!TARGET_MIPS16
&& (register_operand (operands[0], QImode)
|| reg_or_0_operand (operands[1], QImode))"
Index: gcc/config/mips/mips.h
===================================================================
--- gcc/config/mips/mips.h 2014-04-12 10:36:09.105788710 +0100
+++ gcc/config/mips/mips.h 2014-04-12 10:38:48.924225191 +0100
@@ -1870,6 +1870,7 @@ #define PIC_OFFSET_TABLE_REGNUM \
enum reg_class
{
NO_REGS, /* no registers in set */
+ M16_STORE_REGS, /* microMIPS store registers */
M16_REGS, /* mips16 directly accessible registers */
T_REG, /* mips16 T register ($24) */
M16_T_REGS, /* mips16 registers plus T register */
@@ -1907,6 +1908,7 @@ #define GENERAL_REGS GR_REGS
#define REG_CLASS_NAMES \
{ \
"NO_REGS", \
+ "M16_STORE_REGS", \
"M16_REGS", \
"T_REG", \
"M16_T_REGS", \
@@ -1947,6 +1949,7 @@ #define REG_CLASS_NAMES \
#define REG_CLASS_CONTENTS \
{ \
{ 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, /* NO_REGS */ \
+ { 0x000200fc, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, /* M16_STORE_REGS */ \
{ 0x000300fc, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, /* M16_REGS */ \
{ 0x01000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, /* T_REG */ \
{ 0x010300fc, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, /* M16_T_REGS */ \
Index: gcc/config/mips/mips.c
===================================================================
--- gcc/config/mips/mips.c 2014-04-12 10:36:09.105788710 +0100
+++ gcc/config/mips/mips.c 2014-04-12 10:38:48.923225182 +0100
@@ -648,14 +648,15 @@ struct target_globals *mips16_globals;
/* Index R is the smallest register class that contains register R. */
const enum reg_class mips_regno_to_class[FIRST_PSEUDO_REGISTER] = {
- LEA_REGS, LEA_REGS, M16_REGS, V1_REG,
- M16_REGS, M16_REGS, M16_REGS, M16_REGS,
- LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
- LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
- M16_REGS, M16_REGS, LEA_REGS, LEA_REGS,
- LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
- T_REG, PIC_FN_ADDR_REG, LEA_REGS, LEA_REGS,
- LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
+ LEA_REGS, LEA_REGS, M16_STORE_REGS, V1_REG,
+ M16_STORE_REGS, M16_STORE_REGS, M16_STORE_REGS, M16_STORE_REGS,
+ LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
+ LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
+ M16_REGS, M16_STORE_REGS, LEA_REGS, LEA_REGS,
+ LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
+ T_REG, PIC_FN_ADDR_REG, LEA_REGS, LEA_REGS,
+ LEA_REGS, LEA_REGS, LEA_REGS, LEA_REGS,
+
FP_REGS, FP_REGS, FP_REGS, FP_REGS,
FP_REGS, FP_REGS, FP_REGS, FP_REGS,
FP_REGS, FP_REGS, FP_REGS, FP_REGS,
Index: gcc/testsuite/gcc.target/mips/umips-store16-1.c
===================================================================
--- /dev/null 2014-04-11 11:50:02.034263237 +0100
+++ gcc/testsuite/gcc.target/mips/umips-store16-1.c 2014-04-12 10:38:48.926225209 +0100
@@ -0,0 +1,30 @@
+/* { dg-options "(-mmicromips)" } */
+/* { dg-do assemble } */
+
+register unsigned int global asm ("$16");
+
+extern void exit (int) __attribute__((noreturn));
+
+MICROMIPS void
+test_sb (unsigned char *ptr, void (*f) (void))
+{
+ ptr[0] = global;
+ f ();
+ exit (0);
+}
+
+MICROMIPS void
+test_sh (unsigned short *ptr, void (*f) (void))
+{
+ ptr[0] = global;
+ f ();
+ exit (0);
+}
+
+MICROMIPS void
+test_sw (unsigned int *ptr, void (*f) (void))
+{
+ ptr[0] = global;
+ f ();
+ exit (0);
+}