2
0
mirror of git://gcc.gnu.org/git/gcc.git synced 2025-03-24 12:31:25 +08:00

re PR target/36133 (GCC creates suboptimal ASM : Code includes unneeded TST instructions)

2008-11-19  Andrew Stubbs  <ams@codesourcery.com>

	gcc/
	PR target/36133
	* config/m68k/m68k.h (CC_OVERFLOW_UNUSABLE, CC_NO_CARRY): New defines.
	* config/m68k/m68k.c (notice_update_cc): Set cc_status properly for
	shift instructions.
	* config/m68k/m68k.md: Adjust all conditional branches that use the
	carry and overflow flags so they understand CC_OVERFLOW_UNUSABLE.

	gcc/testsuite/
	PR target/36133
	* gcc.target/m68k/pr36133.c: New test.

From-SVN: r141999
This commit is contained in:
Andrew Stubbs 2008-11-19 11:23:28 +00:00 committed by Andrew Stubbs
parent 681afbeab6
commit 1afac9a69f
6 changed files with 159 additions and 11 deletions
gcc
ChangeLog
config/m68k
testsuite
ChangeLog
gcc.target/m68k

@ -1,3 +1,12 @@
2008-11-19 Andrew Stubbs <ams@codesourcery.com>
PR target/36133
* config/m68k/m68k.h (CC_OVERFLOW_UNUSABLE, CC_NO_CARRY): New defines.
* config/m68k/m68k.c (notice_update_cc): Set cc_status properly for
shift instructions.
* config/m68k/m68k.md: Adjust all conditional branches that use the
carry and overflow flags so they understand CC_OVERFLOW_UNUSABLE.
2008-11-18 Uros Bizjak <ubizjak@gmail.com>
PR target/37362

@ -3605,9 +3605,7 @@ notice_update_cc (rtx exp, rtx insn)
case ROTATE: case ROTATERT:
/* These instructions always clear the overflow bit, and set
the carry to the bit shifted out. */
/* ??? We don't currently have a way to signal carry not valid,
nor do we check for it in the branch insns. */
CC_STATUS_INIT;
cc_status.flags |= CC_OVERFLOW_UNUSABLE | CC_NO_CARRY;
break;
case PLUS: case MINUS: case MULT:

@ -855,6 +855,14 @@ __transfer_from_trampoline () \
some or all of the saved cc's so they won't be used. */
#define NOTICE_UPDATE_CC(EXP,INSN) notice_update_cc (EXP, INSN)
/* The shift instructions always clear the overflow bit. */
#define CC_OVERFLOW_UNUSABLE 01000
/* The shift instructions use the carry bit in a way not compatible with
conditional branches. conditions.h uses CC_NO_OVERFLOW for this purpose.
Rename it to something more understandable. */
#define CC_NO_CARRY CC_NO_OVERFLOW
#define OUTPUT_JUMP(NORMAL, FLOAT, NO_OV) \
do { if (cc_prev_status.flags & CC_IN_68881) \
return FLOAT; \

@ -6371,6 +6371,12 @@
(pc)))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jgt %l0", "fjgt %l0", 0);
}
[(set (attr "type") (symbol_ref "m68k_sched_branch_type (insn)"))])
@ -6382,7 +6388,15 @@
(label_ref (match_operand 0 "" ""))
(pc)))]
""
"jhi %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jhi %l0";
}
[(set_attr "type" "bcc")])
(define_insn "blt"
@ -6393,6 +6407,12 @@
(pc)))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jlt %l0", "fjlt %l0", "jmi %l0");
}
[(set (attr "type") (symbol_ref "m68k_sched_branch_type (insn)"))])
@ -6404,7 +6424,15 @@
(label_ref (match_operand 0 "" ""))
(pc)))]
""
"jcs %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jcs %l0";
}
[(set_attr "type" "bcc")])
(define_insn "bge"
@ -6415,6 +6443,12 @@
(pc)))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jge %l0", "fjge %l0", "jpl %l0");
})
@ -6425,7 +6459,15 @@
(label_ref (match_operand 0 "" ""))
(pc)))]
""
"jcc %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jcc %l0";
}
[(set_attr "type" "bcc")])
(define_insn "ble"
@ -6436,6 +6478,12 @@
(pc)))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jle %l0", "fjle %l0", 0);
}
[(set_attr "type" "bcc")])
@ -6447,7 +6495,15 @@
(label_ref (match_operand 0 "" ""))
(pc)))]
""
"jls %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jls %l0";
}
[(set_attr "type" "bcc")])
(define_insn "bordered"
@ -6580,6 +6636,12 @@
(label_ref (match_operand 0 "" ""))))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jle %l0", "fjngt %l0", 0);
}
[(set_attr "type" "bcc")])
@ -6591,7 +6653,15 @@
(pc)
(label_ref (match_operand 0 "" ""))))]
""
"jls %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jls %l0";
}
[(set_attr "type" "bcc")])
(define_insn "*blt_rev"
@ -6602,6 +6672,12 @@
(label_ref (match_operand 0 "" ""))))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jge %l0", "fjnlt %l0", "jpl %l0");
}
[(set_attr "type" "bcc")])
@ -6613,7 +6689,15 @@
(pc)
(label_ref (match_operand 0 "" ""))))]
""
"jcc %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jcc %l0";
}
[(set_attr "type" "bcc")])
(define_insn "*bge_rev"
@ -6624,6 +6708,12 @@
(label_ref (match_operand 0 "" ""))))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jlt %l0", "fjnge %l0", "jmi %l0");
}
[(set_attr "type" "bcc")])
@ -6635,7 +6725,15 @@
(pc)
(label_ref (match_operand 0 "" ""))))]
""
"jcs %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jcs %l0";
}
[(set_attr "type" "bcc")])
(define_insn "*ble_rev"
@ -6646,6 +6744,12 @@
(label_ref (match_operand 0 "" ""))))]
""
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
OUTPUT_JUMP ("jgt %l0", "fjnle %l0", 0);
}
[(set_attr "type" "bcc")])
@ -6657,7 +6761,15 @@
(pc)
(label_ref (match_operand 0 "" ""))))]
""
"jhi %l0"
{
if ((cc_status.flags & CC_OVERFLOW_UNUSABLE) != 0)
{
cc_status.flags &= ~CC_OVERFLOW_UNUSABLE;
return 0;
}
return "jhi %l0";
}
[(set_attr "type" "bcc")])
(define_insn "*bordered_rev"

@ -1,3 +1,8 @@
2008-11-19 Andrew Stubbs <ams@codesourcery.com>
PR target/36133
* gcc.target/m68k/pr36133.c: New test.
2008-11-19 Maxim Kuvyrkov <maxim@codesourcery.com>
* gcc.gd/struct/wo_prof_global_var.c: Use uninitialized integer

@ -0,0 +1,16 @@
/* pr36133.c
This test ensures that conditional branches can use the condition codes
written by shift instructions, without the need for an extra TST. */
/* { dg-do compile } */
/* { dg-options "-O2" } */
/* { dg-final { scan-assembler-not "tst" } } */
void
f (unsigned int a)
{
if (a >> 4)
asm volatile ("nop");
asm volatile ("nop");
}