===================================================================
@@ -5650,52 +5650,14 @@
(set_attr "mode" "SI")])
(define_insn "*addhi_1"
- [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
- (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0")
- (match_operand:HI 2 "general_operand" "rn,rm")))
+ [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r,r,Yp")
+ (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r,Yp")
+ (match_operand:HI 2 "general_operand" "rn,rm,0,ln")))
(clobber (reg:CC FLAGS_REG))]
- "TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (PLUS, HImode, operands)"
+ "ix86_binary_operator_ok (PLUS, HImode, operands)"
{
switch (get_attr_type (insn))
{
- case TYPE_INCDEC:
- if (operands[2] == const1_rtx)
- return "inc{w}\t%0";
- else
- {
- gcc_assert (operands[2] == constm1_rtx);
- return "dec{w}\t%0";
- }
-
- default:
- if (x86_maybe_negate_const_int (&operands[2], HImode))
- return "sub{w}\t{%2, %0|%0, %2}";
-
- return "add{w}\t{%2, %0|%0, %2}";
- }
-}
- [(set (attr "type")
- (if_then_else (match_operand:HI 2 "incdec_operand" "")
- (const_string "incdec")
- (const_string "alu")))
- (set (attr "length_immediate")
- (if_then_else
- (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
- (const_string "1")
- (const_string "*")))
- (set_attr "mode" "HI")])
-
-(define_insn "*addhi_1_lea"
- [(set (match_operand:HI 0 "nonimmediate_operand" "=r,rm,r,r")
- (plus:HI (match_operand:HI 1 "nonimmediate_operand" "%0,0,r,r")
- (match_operand:HI 2 "general_operand" "rmn,rn,0,ln")))
- (clobber (reg:CC FLAGS_REG))]
- "!TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (PLUS, HImode, operands)"
-{
- switch (get_attr_type (insn))
- {
case TYPE_LEA:
return "#";
@@ -5739,63 +5701,16 @@
(const_string "*")))
(set_attr "mode" "HI,HI,HI,SI")])
-;; %%% Potential partial reg stall on alternative 2. What to do?
+;; %%% Potential partial reg stall on alternatives 3 and 4. What to do?
(define_insn "*addqi_1"
- [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,r")
- (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,0")
- (match_operand:QI 2 "general_operand" "qn,qmn,rn")))
+ [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,q,q,r,r,Yp")
+ (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,q,0,r,Yp")
+ (match_operand:QI 2 "general_operand" "qn,qm,0,rn,0,ln")))
(clobber (reg:CC FLAGS_REG))]
- "TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (PLUS, QImode, operands)"
+ "ix86_binary_operator_ok (PLUS, QImode, operands)"
{
- int widen = (which_alternative == 2);
- switch (get_attr_type (insn))
- {
- case TYPE_INCDEC:
- if (operands[2] == const1_rtx)
- return widen ? "inc{l}\t%k0" : "inc{b}\t%0";
- else
- {
- gcc_assert (operands[2] == constm1_rtx);
- return widen ? "dec{l}\t%k0" : "dec{b}\t%0";
- }
+ bool widen = (which_alternative == 3 || which_alternative == 4);
- default:
- if (x86_maybe_negate_const_int (&operands[2], QImode))
- {
- if (widen)
- return "sub{l}\t{%2, %k0|%k0, %2}";
- else
- return "sub{b}\t{%2, %0|%0, %2}";
- }
- if (widen)
- return "add{l}\t{%k2, %k0|%k0, %k2}";
- else
- return "add{b}\t{%2, %0|%0, %2}";
- }
-}
- [(set (attr "type")
- (if_then_else (match_operand:QI 2 "incdec_operand" "")
- (const_string "incdec")
- (const_string "alu")))
- (set (attr "length_immediate")
- (if_then_else
- (and (eq_attr "type" "alu") (match_operand 2 "const128_operand" ""))
- (const_string "1")
- (const_string "*")))
- (set_attr "mode" "QI,QI,SI")])
-
-;; %%% Potential partial reg stall on alternatives 3 and 4. What to do?
-(define_insn "*addqi_1_lea"
- [(set (match_operand:QI 0 "nonimmediate_operand" "=q,qm,q,r,r,r")
- (plus:QI (match_operand:QI 1 "nonimmediate_operand" "%0,0,q,0,r,r")
- (match_operand:QI 2 "general_operand" "qmn,qn,0,rn,0,ln")))
- (clobber (reg:CC FLAGS_REG))]
- "!TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (PLUS, QImode, operands)"
-{
- int widen = (which_alternative == 3 || which_alternative == 4);
-
switch (get_attr_type (insn))
{
case TYPE_LEA:
@@ -9294,53 +9209,11 @@
"operands[2] = gen_lowpart (SImode, operands[2]);")
(define_insn "*ashlhi3_1"
- [(set (match_operand:HI 0 "nonimmediate_operand" "=rm")
- (ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0")
- (match_operand:QI 2 "nonmemory_operand" "cI")))
- (clobber (reg:CC FLAGS_REG))]
- "TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
-{
- switch (get_attr_type (insn))
- {
- case TYPE_ALU:
- gcc_assert (operands[2] == const1_rtx);
- return "add{w}\t%0, %0";
-
- default:
- if (operands[2] == const1_rtx
- && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
- return "sal{w}\t%0";
- else
- return "sal{w}\t{%2, %0|%0, %2}";
- }
-}
- [(set (attr "type")
- (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
- (const_int 0))
- (match_operand 0 "register_operand" ""))
- (match_operand 2 "const1_operand" ""))
- (const_string "alu")
- ]
- (const_string "ishift")))
- (set (attr "length_immediate")
- (if_then_else
- (ior (eq_attr "type" "alu")
- (and (eq_attr "type" "ishift")
- (and (match_operand 2 "const1_operand" "")
- (ne (symbol_ref "TARGET_SHIFT1 || optimize_function_for_size_p (cfun)")
- (const_int 0)))))
- (const_string "0")
- (const_string "*")))
- (set_attr "mode" "HI")])
-
-(define_insn "*ashlhi3_1_lea"
- [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,r")
+ [(set (match_operand:HI 0 "nonimmediate_operand" "=rm,Yp")
(ashift:HI (match_operand:HI 1 "nonimmediate_operand" "0,l")
(match_operand:QI 2 "nonmemory_operand" "cI,M")))
(clobber (reg:CC FLAGS_REG))]
- "!TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (ASHIFT, HImode, operands)"
+ "ix86_binary_operator_ok (ASHIFT, HImode, operands)"
{
switch (get_attr_type (insn))
{
@@ -9380,68 +9253,13 @@
(const_string "*")))
(set_attr "mode" "HI,SI")])
+;; %%% Potential partial reg stall on alternative 1. What to do?
(define_insn "*ashlqi3_1"
- [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r")
- (ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0")
- (match_operand:QI 2 "nonmemory_operand" "cI,cI")))
- (clobber (reg:CC FLAGS_REG))]
- "TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
-{
- switch (get_attr_type (insn))
- {
- case TYPE_ALU:
- gcc_assert (operands[2] == const1_rtx);
- if (REG_P (operands[1]) && !ANY_QI_REG_P (operands[1]))
- return "add{l}\t%k0, %k0";
- else
- return "add{b}\t%0, %0";
-
- default:
- if (operands[2] == const1_rtx
- && (TARGET_SHIFT1 || optimize_function_for_size_p (cfun)))
- {
- if (get_attr_mode (insn) == MODE_SI)
- return "sal{l}\t%k0";
- else
- return "sal{b}\t%0";
- }
- else
- {
- if (get_attr_mode (insn) == MODE_SI)
- return "sal{l}\t{%2, %k0|%k0, %2}";
- else
- return "sal{b}\t{%2, %0|%0, %2}";
- }
- }
-}
- [(set (attr "type")
- (cond [(and (and (ne (symbol_ref "TARGET_DOUBLE_WITH_ADD")
- (const_int 0))
- (match_operand 0 "register_operand" ""))
- (match_operand 2 "const1_operand" ""))
- (const_string "alu")
- ]
- (const_string "ishift")))
- (set (attr "length_immediate")
- (if_then_else
- (ior (eq_attr "type" "alu")
- (and (eq_attr "type" "ishift")
- (and (match_operand 2 "const1_operand" "")
- (ne (symbol_ref "TARGET_SHIFT1 || optimize_function_for_size_p (cfun)")
- (const_int 0)))))
- (const_string "0")
- (const_string "*")))
- (set_attr "mode" "QI,SI")])
-
-;; %%% Potential partial reg stall on alternative 2. What to do?
-(define_insn "*ashlqi3_1_lea"
- [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,r")
+ [(set (match_operand:QI 0 "nonimmediate_operand" "=qm,r,Yp")
(ashift:QI (match_operand:QI 1 "nonimmediate_operand" "0,0,l")
(match_operand:QI 2 "nonmemory_operand" "cI,cI,M")))
(clobber (reg:CC FLAGS_REG))]
- "!TARGET_PARTIAL_REG_STALL
- && ix86_binary_operator_ok (ASHIFT, QImode, operands)"
+ "ix86_binary_operator_ok (ASHIFT, QImode, operands)"
{
switch (get_attr_type (insn))
{
===================================================================
@@ -88,8 +88,11 @@
;; We use the Y prefix to denote any number of conditional register sets:
;; z First SSE register.
;; 2 SSE2 enabled
+;; 3 SSE3 enabled
+;; 4 SSE4_1 enabled
;; i SSE2 inter-unit moves enabled
;; m MMX inter-unit moves enabled
+;; p Integer register when TARGET_PARTIAL_REG_STALL is disabled
;; d Integer register when integer DFmode moves are enabled
;; x Integer register when integer XFmode moves are enabled
@@ -113,6 +116,10 @@
"TARGET_MMX && TARGET_INTER_UNIT_MOVES ? MMX_REGS : NO_REGS"
"@internal Any MMX register, when inter-unit moves are enabled.")
+(define_register_constraint "Yp"
+ "TARGET_PARTIAL_REG_STALL ? NO_REGS : GENERAL_REGS"
+ "@internal Any integer register when TARGET_PARTIAL_REG_STALL is disabled.")
+
(define_register_constraint "Yd"
"(TARGET_64BIT
|| (TARGET_INTEGER_DFMODE_MOVES && optimize_function_for_speed_p (cfun)))
Hello! Attached patch introduces Yp register constraint, conditionalized on TARGET_PARTIAL_REG_STALL. Using this constraint, several *_lea patterns can be merged with their base patterns, resulting in many removed lines of code. No functional changes otherwise. 2011-08-23 Uros Bizjak <ubizjak@gmail.com> * config/i386/constraints.md (Yp): New register constraint. * config/i386/i386.md (*addhi_1): Merge with *addhi_1_lea using Yp register constraint. (*addqi_1): Merge with *addqi_1_lea using Yp register constraint. (*ashlhi3_1): Merge with *ashlhi3_1_lea using Yp register constraint. (*ashlqi3_1): Merge with *ashlqi3_1_lea using Yp register constraint. Patch was bootstrapped and regression tested on x86_64-pc-linux-gnu {,-m32}, committed to mainline SVN. URos.