This is the mail archive of the
gcc-patches@gcc.gnu.org
mailing list for the GCC project.
[csl-arm] Thumb-2 rotate bugs
- From: Paul Brook <paul at codesourcery dot com>
- To: gcc-patches at gcc dot gnu dot org
- Date: Thu, 30 Mar 2006 01:39:33 +0100
- Subject: [csl-arm] Thumb-2 rotate bugs
The attached patch fixes a couple of bugs in the Thumb-2 rotate instructions.
- The pattern for thumb2_shiftsi3_short was using %I, which doesn't handle
ROTATE. Changed to use arm_output_shift.
- arm_output_shift wasn't using the correct shift amount after changing ROTATE
to ROTATERT.
Tested with cross to arm-none-eabi.
Applied to branches/csl/arm-4_1.
Paul
2006-03-30 Paul Brook <paul@codesourcery.com>
* gcc/config/arm/arm.c (arm_output_shift): Change set_flags to
tristate option. Use modified shift value.
* gcc/config/arm/arm-protos.h (arm_output_shift): Update prototype.
* gcc/config/arm/thumb2.md (thumb2_shiftsi3_short): Use
arm_output_shift.
* gcc/config/arm/arm.md (arm_shiftsi3, shiftsi3_compare0,
shiftsi3_compare0_scratch): Adjust arguments to arm_output_shift.
Index: gcc/config/arm/arm.c
===================================================================
--- gcc/config/arm/arm.c (revision 112511)
+++ gcc/config/arm/arm.c (working copy)
@@ -16193,26 +16193,29 @@ arm_output_addr_const_extra (FILE *fp, r
return FALSE;
}
-/* Output assembly for a shift instruction. SET_FLAGS is TRUE if the
- instruction modifies the condition codes. */
+/* Output assembly for a shift instruction.
+ SET_FLAGS determines how the instruction modifies the condition codes.
+ 0 - Do not set conditiona codes.
+ 1 - Set condition codes.
+ 2 - Use smallest instruction. */
const char *
-arm_output_shift(rtx * operands, bool set_flags)
+arm_output_shift(rtx * operands, int set_flags)
{
char pattern[100];
+ static const char flag_chars[3] = {'.', '?', '!'};
const char *shift;
HOST_WIDE_INT val;
char c;
- if (set_flags)
- c = '.';
- else
- c = '?';
-
+ c = flag_chars[set_flags];
if (TARGET_UNIFIED_ASM)
{
shift = shift_op(operands[3], &val);
if (shift)
- sprintf (pattern, "%s%%%c\t%%0, %%1, %%2", shift, c);
+ {
+ operands[2] = GEN_INT(val);
+ sprintf (pattern, "%s%%%c\t%%0, %%1, %%2", shift, c);
+ }
else
sprintf (pattern, "mov%%%c\t%%0, %%1", c);
}
Index: gcc/config/arm/thumb2.md
===================================================================
--- gcc/config/arm/thumb2.md (revision 112511)
+++ gcc/config/arm/thumb2.md (working copy)
@@ -1020,7 +1020,7 @@ (define_insn "*thumb2_shiftsi3_short"
(match_operand:SI 2 "low_reg_or_int_operand" "lM")]))
(clobber (reg:CC CC_REGNUM))]
"TARGET_THUMB2 && reload_completed"
- "%I3%!\\t%0, %1, %2"
+ "* return arm_output_shift(operands, 2);"
[(set_attr "predicable" "yes")
(set_attr "shift" "1")
(set_attr "length" "2")
Index: gcc/config/arm/arm-protos.h
===================================================================
--- gcc/config/arm/arm-protos.h (revision 112511)
+++ gcc/config/arm/arm-protos.h (working copy)
@@ -125,7 +125,7 @@ extern const char * arm_output_load_gr (
extern const char *vfp_output_fstmx (rtx *);
extern void arm_set_return_address (rtx, rtx);
extern int arm_eliminable_register (rtx);
-extern const char *arm_output_shift(rtx *, bool);
+extern const char *arm_output_shift(rtx *, int);
extern bool arm_output_addr_const_extra (FILE *, rtx);
Index: gcc/config/arm/arm.md
===================================================================
--- gcc/config/arm/arm.md (revision 112511)
+++ gcc/config/arm/arm.md (working copy)
@@ -2903,7 +2903,7 @@ (define_insn "*arm_shiftsi3"
[(match_operand:SI 1 "s_register_operand" "r")
(match_operand:SI 2 "reg_or_int_operand" "rM")]))]
"TARGET_32BIT"
- "* return arm_output_shift(operands, false);"
+ "* return arm_output_shift(operands, 0);"
[(set_attr "predicable" "yes")
(set_attr "shift" "1")
(set (attr "type") (if_then_else (match_operand 2 "const_int_operand" "")
@@ -2920,7 +2920,7 @@ (define_insn "*shiftsi3_compare0"
(set (match_operand:SI 0 "s_register_operand" "=r")
(match_op_dup 3 [(match_dup 1) (match_dup 2)]))]
"TARGET_32BIT"
- "* return arm_output_shift(operands, true);"
+ "* return arm_output_shift(operands, 1);"
[(set_attr "conds" "set")
(set_attr "shift" "1")
(set (attr "type") (if_then_else (match_operand 2 "const_int_operand" "")
@@ -2936,7 +2936,7 @@ (define_insn "*shiftsi3_compare0_scratch
(const_int 0)))
(clobber (match_scratch:SI 0 "=r"))]
"TARGET_32BIT"
- "* return arm_output_shift(operands, true);"
+ "* return arm_output_shift(operands, 1);"
[(set_attr "conds" "set")
(set_attr "shift" "1")]
)