diff options
Diffstat (limited to 'gcc/config')
| -rw-r--r-- | gcc/config/arc/arc.md | 60 |
1 files changed, 35 insertions, 25 deletions
diff --git a/gcc/config/arc/arc.md b/gcc/config/arc/arc.md index 55be6ce74da..2b16ac5f2c7 100644 --- a/gcc/config/arc/arc.md +++ b/gcc/config/arc/arc.md @@ -3555,7 +3555,14 @@ archs4x, archs4xd" [(set (match_operand:SI 0 "dest_reg_operand" "") (ANY_SHIFT_ROTATE:SI (match_operand:SI 1 "register_operand" "") (match_operand:SI 2 "nonmemory_operand" "")))] - "") + "" +{ + if (!TARGET_BARREL_SHIFTER && operands[2] != const1_rtx) + { + emit_insn (gen_<insn>si3_loop (operands[0], operands[1], operands[2])); + DONE; + } +}) ; asl, asr, lsr patterns: ; There is no point in including an 'I' alternative since only the lowest 5 @@ -3654,35 +3661,23 @@ archs4x, archs4xd" [(set_attr "type" "shift") (set_attr "length" "8")]) -(define_insn_and_split "*<insn>si3_nobs" - [(set (match_operand:SI 0 "dest_reg_operand") - (ANY_SHIFT_ROTATE:SI (match_operand:SI 1 "register_operand") - (match_operand:SI 2 "nonmemory_operand")))] +(define_insn_and_split "<insn>si3_loop" + [(set (match_operand:SI 0 "dest_reg_operand" "=r,r") + (ANY_SHIFT_ROTATE:SI (match_operand:SI 1 "register_operand" "0,0") + (match_operand:SI 2 "nonmemory_operand" "rn,Cal"))) + (clobber (reg:SI LP_COUNT)) + (clobber (reg:CC CC_REG))] "!TARGET_BARREL_SHIFTER - && operands[2] != const1_rtx - && arc_pre_reload_split ()" - "#" - "&& 1" + && operands[2] != const1_rtx" + "* return output_shift_loop (<CODE>, operands);" + "&& arc_pre_reload_split ()" [(const_int 0)] { arc_split_<insn> (operands); DONE; -}) - -;; <ANY_SHIFT_ROTATE>si3_loop appears after <ANY_SHIFT_ROTATE>si3_nobs -(define_insn "<insn>si3_loop" - [(set (match_operand:SI 0 "dest_reg_operand" "=r,r") - (ANY_SHIFT_ROTATE:SI - (match_operand:SI 1 "register_operand" "0,0") - (match_operand:SI 2 "nonmemory_operand" "rn,Cal"))) - (clobber (reg:SI LP_COUNT)) - (clobber (reg:CC CC_REG)) - ] - "!TARGET_BARREL_SHIFTER - && operands[2] != const1_rtx" - "* return output_shift_loop (<CODE>, operands);" - [(set_attr "type" "shift") - (set_attr "length" "16,20")]) +} +[(set_attr "type" "shift") + (set_attr "length" "16,20")]) ;; DImode shifts @@ -6414,6 +6409,21 @@ archs4x, archs4xd" (set_attr "length" "4") (set_attr "predicable" "no")]) +;; Match <insn>si3_loop pattern if operand 2 has become const_int 1 in the meantime +(define_insn_and_split "<insn>si3_cnt1_clobber" + [(set (match_operand:SI 0 "dest_reg_operand") + (ANY_SHIFT_ROTATE:SI (match_operand:SI 1 "register_operand") + (const_int 1))) + (clobber (reg:SI LP_COUNT)) + (clobber (reg:CC CC_REG))] + "!TARGET_BARREL_SHIFTER" + "#" + "&& arc_pre_reload_split ()" + [(set (match_dup 0) (ANY_SHIFT_ROTATE:SI (match_dup 1) (const_int 1)))] + "" +[(set_attr "type" "shift") + (set_attr "length" "4")]) + (define_peephole2 [(set (match_operand:SI 0 "register_operand" "") (zero_extract:SI (match_dup 0) |
