Message ID | VI1PR0801MB2127BDEB57F071A0384CC69183CB0@VI1PR0801MB2127.eurprd08.prod.outlook.com |
---|---|
State | New |
Headers | show |
Series | [ARM] Cleanup logical DImode operations | expand |
ping Cleanup the logical DImode operations since the current implementation is way too complicated. Thumb-1, Thumb-2, VFP/Neon and iwMMXt all work differently, resulting in a bewildering number of expansions, patterns and splits across several md files. All this complexity is counterproductive and results in inefficient code. A much simpler approach is to split these operations early in the expander so that optimizations and register allocation are applied on the 32-bit halves. Code generation is unchanged on Thumb-1 and Arm/Thumb-2 without Neon or iwMMXt (which already expand these instructions early). With Neon these changes save ~1000 instructions from the PR77308 testcase, mostly by significantly reducing register pressure and spilling. Bootstrap & regress OK on arm-none-linux-gnueabihf --with-cpu=cortex-a57 OK for commit? ChangeLog: 2019-07-18 Wilco Dijkstra <wdijkstr@arm.com> * config/arm/arm.md (split and/eor/ior): Remove Neon check. (split not): Add DImode not splitter. (anddi3): Remove pattern. (anddi3_insn): Likewise. (anddi_zesidi_di): Likewise. (anddi_sesdi_di): Likewise. (anddi_notdi_di): Likewise. (anddi_notzesidi_di): Likewise. (anddi_notsesidi_di): Likewise. (iordi3): Likewise. (iordi3_insn): Likewise. (iordi_zesidi_di): Likewise. (iordi_sesidi_di): Likewise. (xordi3): Likewise. (xordi3_insn): Likewise. (xordi_sesidi_di): Likewise. (xordi_zesidi_di): Likewise. (one_cmpldi2): Likewise. (one_cmpldi2_insn): Likewise. * config/arm/constraints.md: Remove De, Df, Dg constraints. * config/arm/iwmmxt.md (iwmmxt_iordi3): Remove general register alternative. (iwmmxt_xordi3): Likewise. (iwmmxt_anddi3): Likewise. * config/arm/neon.md (orndi3_neon): Remove pattern. (anddi_notdi_di): Likewise. * config/arm/predicates.md (arm_anddi_operand_neon): Remove. (arm_iordi_operand_neon): Likewise. (arm_xordi_operand_neon): Likewise. * config/arm/thumb2.md(iordi_notdi_di): Remove pattern. (iordi_notzesidi_di): Likewise. (iordi_notdi_zesidi): Likewise. (iordi_notsesidi_di): Likewise. --- diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md index 8f4a4c26ea849a023f2e63d2efbf327423512dfc..cab59c403b777c37c1e412ab9a69db2c2ec533a2 100644 --- a/gcc/config/arm/arm.md +++ b/gcc/config/arm/arm.md @@ -2183,19 +2183,16 @@ (define_expand "divdf3" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -;; Boolean and,ior,xor insns -;; Split up double word logical operations - -;; Split up simple DImode logical operations. Simply perform the logical +;; Split DImode and, ior, xor operations. Simply perform the logical ;; operation on the upper and lower halves of the registers. +;; This is needed for atomic operations in arm_split_atomic_op. (define_split [(set (match_operand:DI 0 "s_register_operand" "") (match_operator:DI 6 "logical_binary_operator" [(match_operand:DI 1 "s_register_operand" "") (match_operand:DI 2 "s_register_operand" "")]))] "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) (set (match_dup 3) (match_op_dup:SI 6 [(match_dup 4) (match_dup 5)]))] @@ -2210,167 +2207,20 @@ (define_split }" ) +;; Split DImode not (needed for atomic operations in arm_split_atomic_op). (define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (match_operator:DI 6 "logical_binary_operator" - [(sign_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")]))] - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) - (set (match_dup 3) (match_op_dup:SI 6 - [(ashiftrt:SI (match_dup 2) (const_int 31)) - (match_dup 4)]))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (ior:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (xor:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -(define_expand "anddi3" - [(set (match_operand:DI 0 "s_register_operand") - (and:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_inv_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*anddi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (and:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_anddi_operand_neon" "w ,DL,r ,r ,De,De,w ,DL")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vand\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vand", &operands[2], - DImode, 1, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: /* fall through */ - return "#"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,\ - multiple,multiple,neon_logic,neon_logic") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*, - avoid_neon_for_64bits,avoid_neon_for_64bits") - (set_attr "length" "*,*,8,8,8,8,*,*") - ] -) - -(define_insn_and_split "*anddi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] + [(set (match_operand:DI 0 "s_register_operand") + (not:DI (match_operand:DI 1 "s_register_operand")))] "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - ; The zero extend of operand 2 clears the high word of the output - ; operand. - [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (const_int 0))] + [(set (match_dup 0) (not:SI (match_dup 1))) + (set (match_dup 2) (not:SI (match_dup 3)))] " { - operands[3] = gen_highpart (SImode, operands[0]); + operands[2] = gen_highpart (SImode, operands[0]); operands[0] = gen_lowpart (SImode, operands[0]); + operands[3] = gen_highpart (SImode, operands[1]); operands[1] = gen_lowpart (SImode, operands[1]); }" - [(set_attr "length" "8") - (set_attr "type" "multiple")] -) - -(define_insn "*anddi_sesdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "type" "multiple")] ) (define_expand "andsi3" @@ -2952,105 +2802,6 @@ (define_insn "insv_t2" (set_attr "type" "bfm")] ) -; constants for op 2 will never be given to these patterns. -(define_insn_and_split "*anddi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) - && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" - [(set (match_dup 0) (and:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - bic%?\\t%Q0, %Q1, %2 - #" - ; (not (zero_extend ...)) allows us to just copy the high word from - ; operand1 to operand0. - "TARGET_32BIT - && reload_completed - && operands[0] != operands[1]" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r"))))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int 0))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (and:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_insn "andsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) @@ -3150,101 +2901,6 @@ (define_insn "*andsi_notsi_si_compare0_scratch" (set_attr "type" "logics_shift_reg")] ) -(define_expand "iordi3" - [(set (match_operand:DI 0 "s_register_operand") - (ior:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*iordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (ior:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_iordi_operand_neon" "w ,Dl,r ,r ,Df,Df,w ,Dl")))] - "TARGET_32BIT && !TARGET_IWMMXT" - { - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vorr\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vorr", &operands[2], - DImode, 0, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: - return "#"; - default: gcc_unreachable (); - } - } - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,multiple,\ - multiple,neon_logic,neon_logic") - (set_attr "length" "*,*,8,8,8,8,*,*") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*,avoid_neon_for_64bits,avoid_neon_for_64bits")] -) - -(define_insn "*iordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - orr%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg,multiple")] -) - -(define_insn "*iordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "iorsi3" [(set (match_operand:SI 0 "s_register_operand") (ior:SI (match_operand:SI 1 "s_register_operand") @@ -3347,103 +3003,6 @@ (define_insn "*iorsi3_compare0_scratch" (set_attr "type" "logics_imm,logics_reg")] ) -(define_expand "xordi3" - [(set (match_operand:DI 0 "s_register_operand") - (xor:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "arm_xordi_operand")))] - "TARGET_32BIT" - { - /* The iWMMXt pattern for xordi3 accepts only register operands but we want - to reuse this expander for all TARGET_32BIT targets so just force the - constants into a register. Unlike for the anddi3 and iordi3 there are - no NEON instructions that take an immediate. */ - if (TARGET_IWMMXT && !REG_P (operands[2])) - operands[2] = force_reg (DImode, operands[2]); - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - } -) - -(define_insn_and_split "*xordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,&r,&r,?w") - (xor:DI (match_operand:DI 1 "s_register_operand" "%w ,0,r ,0 ,r ,w") - (match_operand:DI 2 "arm_xordi_operand" "w ,r ,r ,Dg,Dg,w")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 1: - case 2: - case 3: - case 4: /* fall through */ - return "#"; - case 0: /* fall through */ - case 5: return "veor\t%P0, %P1, %P2"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "length" "*,8,8,8,8,*") - (set_attr "type" "neon_logic,multiple,multiple,multiple,multiple,neon_logic") - (set_attr "arch" "neon_for_64bits,*,*,*,*,avoid_neon_for_64bits")] -) - -(define_insn "*xordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - eor%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg")] -) - -(define_insn "*xordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "xorsi3" [(set (match_operand:SI 0 "s_register_operand") (xor:SI (match_operand:SI 1 "s_register_operand") @@ -5033,56 +4592,6 @@ (define_expand "sqrtdf2" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -(define_expand "one_cmpldi2" - [(set (match_operand:DI 0 "s_register_operand") - (not:DI (match_operand:DI 1 "s_register_operand")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_unary (NOT, SImode, - gen_lowpart (SImode, operands[1]), - SImode); - rtx high = simplify_gen_unary (NOT, SImode, - gen_highpart_mode (SImode, DImode, - operands[1]), - SImode); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*one_cmpldi2_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,?w") - (not:DI (match_operand:DI 1 "s_register_operand" " w, 0, r, w")))] - "TARGET_32BIT" - "@ - vmvn\t%P0, %P1 - # - # - vmvn\t%P0, %P1" - "TARGET_32BIT && reload_completed - && arm_general_register_operand (operands[0], DImode)" - [(set (match_dup 0) (not:SI (match_dup 1))) - (set (match_dup 2) (not:SI (match_dup 3)))] - " - { - operands[2] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[3] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "*,8,8,*") - (set_attr "predicable" "no,yes,yes,no") - (set_attr "type" "neon_move,multiple,multiple,neon_move") - (set_attr "arch" "neon_for_64bits,*,*,avoid_neon_for_64bits")] -) - (define_expand "one_cmplsi2" [(set (match_operand:SI 0 "s_register_operand") (not:SI (match_operand:SI 1 "s_register_operand")))] diff --git a/gcc/config/arm/constraints.md b/gcc/config/arm/constraints.md index d4a4c5967aea09816485d77f9ab90020aa085e73..b76de81b85c8ce7a2ca484a750b908b7ca64600a 100644 --- a/gcc/config/arm/constraints.md +++ b/gcc/config/arm/constraints.md @@ -273,24 +273,6 @@ (define_constraint "Dd" (and (match_code "const_int") (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, PLUS)"))) -(define_constraint "De" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn anddi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, AND)"))) - -(define_constraint "Df" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn iordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, IOR)"))) - -(define_constraint "Dg" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn xordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, XOR)"))) - (define_constraint "Di" "@internal In ARM/Thumb-2 state a const_int or const_double where both the high diff --git a/gcc/config/arm/iwmmxt.md b/gcc/config/arm/iwmmxt.md index 310019aa5ceef98047b310284123f66940430095..86158ea4fd278180d5e2321c66c6c2b5e5c460b0 100644 --- a/gcc/config/arm/iwmmxt.md +++ b/gcc/config/arm/iwmmxt.md @@ -55,45 +55,36 @@ (define_insn "tbcstv2si" ) (define_insn "iwmmxt_iordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (ior:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (ior:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wor%?\\t%0, %1, %2 - # - #" + "wor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wor")] ) (define_insn "iwmmxt_xordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (xor:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (xor:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wxor%?\\t%0, %1, %2 - # - #" + "wxor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wxor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wxor")] ) (define_insn "iwmmxt_anddi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (and:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (and:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wand%?\\t%0, %1, %2 - # - #" + "wand%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wand,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wand")] ) (define_insn "iwmmxt_nanddi3" diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md index 6333e0ea3ea68d73bed1f7c4d8ca090090ad68cc..ef73c77abeeaa02947c70ffa435f7bedc431e3be 100644 --- a/gcc/config/arm/neon.md +++ b/gcc/config/arm/neon.md @@ -838,46 +838,6 @@ (define_insn "orn<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; TODO: investigate whether we should disable -;; this and bicdi3_neon for the A8 in line with the other -;; changes above. -(define_insn_and_split "orndi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r,?&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,0,0,r")) - (match_operand:DI 1 "s_register_operand" "w,r,r,0")))] - "TARGET_NEON" - "@ - vorn\t%P0, %P1, %P2 - # - # - #" - "reload_completed && - (TARGET_NEON && !(IS_VFP_REGNUM (REGNO (operands[0]))))" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - if (TARGET_THUMB2) - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - operands[5] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - } - else - { - emit_insn (gen_one_cmpldi2 (operands[0], operands[2])); - emit_insn (gen_iordi3 (operands[0], operands[1], operands[0])); - DONE; - } - }" - [(set_attr "type" "neon_logic,multiple,multiple,multiple") - (set_attr "length" "*,16,8,8") - (set_attr "arch" "any,a,t2,t2")] -) - (define_insn "bic<mode>3_neon" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (and:VDQ (not:VDQ (match_operand:VDQ 2 "s_register_operand" "w")) @@ -887,20 +847,6 @@ (define_insn "bic<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; Compare to *anddi_notdi_di. -(define_insn "bicdi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,r,0")) - (match_operand:DI 1 "s_register_operand" "w,0,r")))] - "TARGET_NEON" - "@ - vbic\t%P0, %P1, %P2 - # - #" - [(set_attr "type" "neon_logic,multiple,multiple") - (set_attr "length" "*,8,8")] -) - (define_insn "xor<mode>3" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (xor:VDQ (match_operand:VDQ 1 "s_register_operand" "w") diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md index f53378a250edfdd0de467f2abbe08bc933d6d734..af97edd28f27a1d8ab9ac2a63343380236d97603 100644 --- a/gcc/config/arm/predicates.md +++ b/gcc/config/arm/predicates.md @@ -201,23 +201,6 @@ (define_predicate "arm_add_operand" (ior (match_operand 0 "arm_rhs_operand") (match_operand 0 "arm_neg_immediate_operand"))) -(define_predicate "arm_anddi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), AND)")) - (match_operand 0 "neon_inv_logic_op2"))) - -(define_predicate "arm_iordi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), IOR)")) - (match_operand 0 "neon_logic_op2"))) - -(define_predicate "arm_xordi_operand" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), XOR)")))) - (define_predicate "arm_adddi_operand" (ior (match_operand 0 "s_register_operand") (and (match_code "const_int") diff --git a/gcc/config/arm/thumb2.md b/gcc/config/arm/thumb2.md index b283a7b656526d3c4719860d10aa1c0550288ba3..78a6ea0b10dab97ed6651ce62e99cfd7a81722ab 100644 --- a/gcc/config/arm/thumb2.md +++ b/gcc/config/arm/thumb2.md @@ -1478,103 +1478,6 @@ (define_insn "*thumb2_negsi2_short" (set_attr "type" "alu_sreg")] ) -; Constants for op 2 will never be given to these patterns. -(define_insn_and_split "*iordi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_THUMB2" - "#" - ; (not (zero_extend...)) means operand0 will always be 0xffffffff - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int -1))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "0,?r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r,r"))))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (not:SI (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - (define_insn "*orsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (ior:SI (not:SI (match_operand:SI 2 "s_register_operand" "r"))
ping Cleanup the logical DImode operations since the current implementation is way too complicated. Thumb-1, Thumb-2, VFP/Neon and iwMMXt all work differently, resulting in a bewildering number of expansions, patterns and splits across several md files. All this complexity is counterproductive and results in inefficient code. A much simpler approach is to split these operations early in the expander so that optimizations and register allocation are applied on the 32-bit halves. Code generation is unchanged on Thumb-1 and Arm/Thumb-2 without Neon or iwMMXt (which already expand these instructions early). With Neon these changes save ~1000 instructions from the PR77308 testcase, mostly by significantly reducing register pressure and spilling. Bootstrap & regress OK on arm-none-linux-gnueabihf --with-cpu=cortex-a57 OK for commit? ChangeLog: 2019-07-18 Wilco Dijkstra <wdijkstr@arm.com> * config/arm/arm.md (split and/eor/ior): Remove Neon check. (split not): Add DImode not splitter. (anddi3): Remove pattern. (anddi3_insn): Likewise. (anddi_zesidi_di): Likewise. (anddi_sesdi_di): Likewise. (anddi_notdi_di): Likewise. (anddi_notzesidi_di): Likewise. (anddi_notsesidi_di): Likewise. (iordi3): Likewise. (iordi3_insn): Likewise. (iordi_zesidi_di): Likewise. (iordi_sesidi_di): Likewise. (xordi3): Likewise. (xordi3_insn): Likewise. (xordi_sesidi_di): Likewise. (xordi_zesidi_di): Likewise. (one_cmpldi2): Likewise. (one_cmpldi2_insn): Likewise. * config/arm/constraints.md: Remove De, Df, Dg constraints. * config/arm/iwmmxt.md (iwmmxt_iordi3): Remove general register alternative. (iwmmxt_xordi3): Likewise. (iwmmxt_anddi3): Likewise. * config/arm/neon.md (orndi3_neon): Remove pattern. (anddi_notdi_di): Likewise. * config/arm/predicates.md (arm_anddi_operand_neon): Remove. (arm_iordi_operand_neon): Likewise. (arm_xordi_operand_neon): Likewise. * config/arm/thumb2.md(iordi_notdi_di): Remove pattern. (iordi_notzesidi_di): Likewise. (iordi_notdi_zesidi): Likewise. (iordi_notsesidi_di): Likewise. --- diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md index 8f4a4c26ea849a023f2e63d2efbf327423512dfc..cab59c403b777c37c1e412ab9a69db2c2ec533a2 100644 --- a/gcc/config/arm/arm.md +++ b/gcc/config/arm/arm.md @@ -2183,19 +2183,16 @@ (define_expand "divdf3" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -;; Boolean and,ior,xor insns -;; Split up double word logical operations - -;; Split up simple DImode logical operations. Simply perform the logical +;; Split DImode and, ior, xor operations. Simply perform the logical ;; operation on the upper and lower halves of the registers. +;; This is needed for atomic operations in arm_split_atomic_op. (define_split [(set (match_operand:DI 0 "s_register_operand" "") (match_operator:DI 6 "logical_binary_operator" [(match_operand:DI 1 "s_register_operand" "") (match_operand:DI 2 "s_register_operand" "")]))] "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) (set (match_dup 3) (match_op_dup:SI 6 [(match_dup 4) (match_dup 5)]))] @@ -2210,167 +2207,20 @@ (define_split }" ) +;; Split DImode not (needed for atomic operations in arm_split_atomic_op). (define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (match_operator:DI 6 "logical_binary_operator" - [(sign_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")]))] - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) - (set (match_dup 3) (match_op_dup:SI 6 - [(ashiftrt:SI (match_dup 2) (const_int 31)) - (match_dup 4)]))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (ior:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (xor:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -(define_expand "anddi3" - [(set (match_operand:DI 0 "s_register_operand") - (and:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_inv_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*anddi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (and:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_anddi_operand_neon" "w ,DL,r ,r ,De,De,w ,DL")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vand\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vand", &operands[2], - DImode, 1, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: /* fall through */ - return "#"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,\ - multiple,multiple,neon_logic,neon_logic") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*, - avoid_neon_for_64bits,avoid_neon_for_64bits") - (set_attr "length" "*,*,8,8,8,8,*,*") - ] -) - -(define_insn_and_split "*anddi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] + [(set (match_operand:DI 0 "s_register_operand") + (not:DI (match_operand:DI 1 "s_register_operand")))] "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - ; The zero extend of operand 2 clears the high word of the output - ; operand. - [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (const_int 0))] + [(set (match_dup 0) (not:SI (match_dup 1))) + (set (match_dup 2) (not:SI (match_dup 3)))] " { - operands[3] = gen_highpart (SImode, operands[0]); + operands[2] = gen_highpart (SImode, operands[0]); operands[0] = gen_lowpart (SImode, operands[0]); + operands[3] = gen_highpart (SImode, operands[1]); operands[1] = gen_lowpart (SImode, operands[1]); }" - [(set_attr "length" "8") - (set_attr "type" "multiple")] -) - -(define_insn "*anddi_sesdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "type" "multiple")] ) (define_expand "andsi3" @@ -2952,105 +2802,6 @@ (define_insn "insv_t2" (set_attr "type" "bfm")] ) -; constants for op 2 will never be given to these patterns. -(define_insn_and_split "*anddi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) - && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" - [(set (match_dup 0) (and:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - bic%?\\t%Q0, %Q1, %2 - #" - ; (not (zero_extend ...)) allows us to just copy the high word from - ; operand1 to operand0. - "TARGET_32BIT - && reload_completed - && operands[0] != operands[1]" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r"))))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int 0))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (and:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_insn "andsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) @@ -3150,101 +2901,6 @@ (define_insn "*andsi_notsi_si_compare0_scratch" (set_attr "type" "logics_shift_reg")] ) -(define_expand "iordi3" - [(set (match_operand:DI 0 "s_register_operand") - (ior:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*iordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (ior:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_iordi_operand_neon" "w ,Dl,r ,r ,Df,Df,w ,Dl")))] - "TARGET_32BIT && !TARGET_IWMMXT" - { - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vorr\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vorr", &operands[2], - DImode, 0, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: - return "#"; - default: gcc_unreachable (); - } - } - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,multiple,\ - multiple,neon_logic,neon_logic") - (set_attr "length" "*,*,8,8,8,8,*,*") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*,avoid_neon_for_64bits,avoid_neon_for_64bits")] -) - -(define_insn "*iordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - orr%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg,multiple")] -) - -(define_insn "*iordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "iorsi3" [(set (match_operand:SI 0 "s_register_operand") (ior:SI (match_operand:SI 1 "s_register_operand") @@ -3347,103 +3003,6 @@ (define_insn "*iorsi3_compare0_scratch" (set_attr "type" "logics_imm,logics_reg")] ) -(define_expand "xordi3" - [(set (match_operand:DI 0 "s_register_operand") - (xor:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "arm_xordi_operand")))] - "TARGET_32BIT" - { - /* The iWMMXt pattern for xordi3 accepts only register operands but we want - to reuse this expander for all TARGET_32BIT targets so just force the - constants into a register. Unlike for the anddi3 and iordi3 there are - no NEON instructions that take an immediate. */ - if (TARGET_IWMMXT && !REG_P (operands[2])) - operands[2] = force_reg (DImode, operands[2]); - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - } -) - -(define_insn_and_split "*xordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,&r,&r,?w") - (xor:DI (match_operand:DI 1 "s_register_operand" "%w ,0,r ,0 ,r ,w") - (match_operand:DI 2 "arm_xordi_operand" "w ,r ,r ,Dg,Dg,w")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 1: - case 2: - case 3: - case 4: /* fall through */ - return "#"; - case 0: /* fall through */ - case 5: return "veor\t%P0, %P1, %P2"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "length" "*,8,8,8,8,*") - (set_attr "type" "neon_logic,multiple,multiple,multiple,multiple,neon_logic") - (set_attr "arch" "neon_for_64bits,*,*,*,*,avoid_neon_for_64bits")] -) - -(define_insn "*xordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - eor%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg")] -) - -(define_insn "*xordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "xorsi3" [(set (match_operand:SI 0 "s_register_operand") (xor:SI (match_operand:SI 1 "s_register_operand") @@ -5033,56 +4592,6 @@ (define_expand "sqrtdf2" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -(define_expand "one_cmpldi2" - [(set (match_operand:DI 0 "s_register_operand") - (not:DI (match_operand:DI 1 "s_register_operand")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_unary (NOT, SImode, - gen_lowpart (SImode, operands[1]), - SImode); - rtx high = simplify_gen_unary (NOT, SImode, - gen_highpart_mode (SImode, DImode, - operands[1]), - SImode); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*one_cmpldi2_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,?w") - (not:DI (match_operand:DI 1 "s_register_operand" " w, 0, r, w")))] - "TARGET_32BIT" - "@ - vmvn\t%P0, %P1 - # - # - vmvn\t%P0, %P1" - "TARGET_32BIT && reload_completed - && arm_general_register_operand (operands[0], DImode)" - [(set (match_dup 0) (not:SI (match_dup 1))) - (set (match_dup 2) (not:SI (match_dup 3)))] - " - { - operands[2] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[3] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "*,8,8,*") - (set_attr "predicable" "no,yes,yes,no") - (set_attr "type" "neon_move,multiple,multiple,neon_move") - (set_attr "arch" "neon_for_64bits,*,*,avoid_neon_for_64bits")] -) - (define_expand "one_cmplsi2" [(set (match_operand:SI 0 "s_register_operand") (not:SI (match_operand:SI 1 "s_register_operand")))] diff --git a/gcc/config/arm/constraints.md b/gcc/config/arm/constraints.md index d4a4c5967aea09816485d77f9ab90020aa085e73..b76de81b85c8ce7a2ca484a750b908b7ca64600a 100644 --- a/gcc/config/arm/constraints.md +++ b/gcc/config/arm/constraints.md @@ -273,24 +273,6 @@ (define_constraint "Dd" (and (match_code "const_int") (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, PLUS)"))) -(define_constraint "De" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn anddi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, AND)"))) - -(define_constraint "Df" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn iordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, IOR)"))) - -(define_constraint "Dg" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn xordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, XOR)"))) - (define_constraint "Di" "@internal In ARM/Thumb-2 state a const_int or const_double where both the high diff --git a/gcc/config/arm/iwmmxt.md b/gcc/config/arm/iwmmxt.md index 310019aa5ceef98047b310284123f66940430095..86158ea4fd278180d5e2321c66c6c2b5e5c460b0 100644 --- a/gcc/config/arm/iwmmxt.md +++ b/gcc/config/arm/iwmmxt.md @@ -55,45 +55,36 @@ (define_insn "tbcstv2si" ) (define_insn "iwmmxt_iordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (ior:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (ior:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wor%?\\t%0, %1, %2 - # - #" + "wor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wor")] ) (define_insn "iwmmxt_xordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (xor:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (xor:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wxor%?\\t%0, %1, %2 - # - #" + "wxor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wxor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wxor")] ) (define_insn "iwmmxt_anddi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (and:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (and:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wand%?\\t%0, %1, %2 - # - #" + "wand%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wand,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wand")] ) (define_insn "iwmmxt_nanddi3" diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md index 6333e0ea3ea68d73bed1f7c4d8ca090090ad68cc..ef73c77abeeaa02947c70ffa435f7bedc431e3be 100644 --- a/gcc/config/arm/neon.md +++ b/gcc/config/arm/neon.md @@ -838,46 +838,6 @@ (define_insn "orn<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; TODO: investigate whether we should disable -;; this and bicdi3_neon for the A8 in line with the other -;; changes above. -(define_insn_and_split "orndi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r,?&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,0,0,r")) - (match_operand:DI 1 "s_register_operand" "w,r,r,0")))] - "TARGET_NEON" - "@ - vorn\t%P0, %P1, %P2 - # - # - #" - "reload_completed && - (TARGET_NEON && !(IS_VFP_REGNUM (REGNO (operands[0]))))" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - if (TARGET_THUMB2) - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - operands[5] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - } - else - { - emit_insn (gen_one_cmpldi2 (operands[0], operands[2])); - emit_insn (gen_iordi3 (operands[0], operands[1], operands[0])); - DONE; - } - }" - [(set_attr "type" "neon_logic,multiple,multiple,multiple") - (set_attr "length" "*,16,8,8") - (set_attr "arch" "any,a,t2,t2")] -) - (define_insn "bic<mode>3_neon" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (and:VDQ (not:VDQ (match_operand:VDQ 2 "s_register_operand" "w")) @@ -887,20 +847,6 @@ (define_insn "bic<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; Compare to *anddi_notdi_di. -(define_insn "bicdi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,r,0")) - (match_operand:DI 1 "s_register_operand" "w,0,r")))] - "TARGET_NEON" - "@ - vbic\t%P0, %P1, %P2 - # - #" - [(set_attr "type" "neon_logic,multiple,multiple") - (set_attr "length" "*,8,8")] -) - (define_insn "xor<mode>3" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (xor:VDQ (match_operand:VDQ 1 "s_register_operand" "w") diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md index f53378a250edfdd0de467f2abbe08bc933d6d734..af97edd28f27a1d8ab9ac2a63343380236d97603 100644 --- a/gcc/config/arm/predicates.md +++ b/gcc/config/arm/predicates.md @@ -201,23 +201,6 @@ (define_predicate "arm_add_operand" (ior (match_operand 0 "arm_rhs_operand") (match_operand 0 "arm_neg_immediate_operand"))) -(define_predicate "arm_anddi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), AND)")) - (match_operand 0 "neon_inv_logic_op2"))) - -(define_predicate "arm_iordi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), IOR)")) - (match_operand 0 "neon_logic_op2"))) - -(define_predicate "arm_xordi_operand" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), XOR)")))) - (define_predicate "arm_adddi_operand" (ior (match_operand 0 "s_register_operand") (and (match_code "const_int") diff --git a/gcc/config/arm/thumb2.md b/gcc/config/arm/thumb2.md index b283a7b656526d3c4719860d10aa1c0550288ba3..78a6ea0b10dab97ed6651ce62e99cfd7a81722ab 100644 --- a/gcc/config/arm/thumb2.md +++ b/gcc/config/arm/thumb2.md @@ -1478,103 +1478,6 @@ (define_insn "*thumb2_negsi2_short" (set_attr "type" "alu_sreg")] ) -; Constants for op 2 will never be given to these patterns. -(define_insn_and_split "*iordi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_THUMB2" - "#" - ; (not (zero_extend...)) means operand0 will always be 0xffffffff - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int -1))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "0,?r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r,r"))))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (not:SI (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - (define_insn "*orsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (ior:SI (not:SI (match_operand:SI 2 "s_register_operand" "r"))
Hi Wilco, On 7/19/19 12:30 PM, Wilco Dijkstra wrote: > > Cleanup the logical DImode operations since the current implementation > is way > too complicated. Thumb-1, Thumb-2, VFP/Neon and iwMMXt all work > differently, > resulting in a bewildering number of expansions, patterns and splits > across > several md files. All this complexity is counterproductive and results in > inefficient code. > > A much simpler approach is to split these operations early in the expander > so that optimizations and register allocation are applied on the > 32-bit halves. > Code generation is unchanged on Thumb-1 and Arm/Thumb-2 without Neon > or iwMMXt > (which already expand these instructions early). With Neon these > changes save > ~1000 instructions from the PR77308 testcase, mostly by significantly > reducing > register pressure and spilling. > > Bootstrap & regress OK on arm-none-linux-gnueabihf --with-cpu=cortex-a57 > > OK for commit? Ok. Thanks for doing this. Please keep an eye out for fallout after committing. Kyrill > > ChangeLog: > 2019-07-18 Wilco Dijkstra <wdijkstr@arm.com> > > * config/arm/arm.md (split and/eor/ior): Remove Neon check. > (split not): Add DImode not splitter. > (anddi3): Remove pattern. > (anddi3_insn): Likewise. > (anddi_zesidi_di): Likewise. > (anddi_sesdi_di): Likewise. > (anddi_notdi_di): Likewise. > (anddi_notzesidi_di): Likewise. > (anddi_notsesidi_di): Likewise. > (iordi3): Likewise. > (iordi3_insn): Likewise. > (iordi_zesidi_di): Likewise. > (iordi_sesidi_di): Likewise. > (xordi3): Likewise. > (xordi3_insn): Likewise. > (xordi_sesidi_di): Likewise. > (xordi_zesidi_di): Likewise. > (one_cmpldi2): Likewise. > (one_cmpldi2_insn): Likewise. > * config/arm/constraints.md: Remove De, Df, Dg constraints. > * config/arm/iwmmxt.md (iwmmxt_iordi3): Remove general register > alternative. > (iwmmxt_xordi3): Likewise. > (iwmmxt_anddi3): Likewise. > * config/arm/neon.md (orndi3_neon): Remove pattern. > (anddi_notdi_di): Likewise. > * config/arm/predicates.md (arm_anddi_operand_neon): Remove. > (arm_iordi_operand_neon): Likewise. > (arm_xordi_operand_neon): Likewise. > * config/arm/thumb2.md(iordi_notdi_di): Remove pattern. > (iordi_notzesidi_di): Likewise. > (iordi_notdi_zesidi): Likewise. > (iordi_notsesidi_di): Likewise. > > > --- > diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md > index > 8f4a4c26ea849a023f2e63d2efbf327423512dfc..cab59c403b777c37c1e412ab9a69db2c2ec533a2 > 100644 > --- a/gcc/config/arm/arm.md > +++ b/gcc/config/arm/arm.md > @@ -2183,19 +2183,16 @@ (define_expand "divdf3" > "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" > "") > > -;; Boolean and,ior,xor insns > > -;; Split up double word logical operations > - > -;; Split up simple DImode logical operations. Simply perform the logical > +;; Split DImode and, ior, xor operations. Simply perform the logical > ;; operation on the upper and lower halves of the registers. > +;; This is needed for atomic operations in arm_split_atomic_op. > (define_split > [(set (match_operand:DI 0 "s_register_operand" "") > (match_operator:DI 6 "logical_binary_operator" > [(match_operand:DI 1 "s_register_operand" "") > (match_operand:DI 2 "s_register_operand" "")]))] > "TARGET_32BIT && reload_completed > - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) > && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" > [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) > (set (match_dup 3) (match_op_dup:SI 6 [(match_dup 4) (match_dup 5)]))] > @@ -2210,167 +2207,20 @@ (define_split > }" > ) > > +;; Split DImode not (needed for atomic operations in > arm_split_atomic_op). > (define_split > - [(set (match_operand:DI 0 "s_register_operand" "") > -(match_operator:DI 6 "logical_binary_operator" > - [(sign_extend:DI (match_operand:SI 2 "s_register_operand" "")) > - (match_operand:DI 1 "s_register_operand" "")]))] > - "TARGET_32BIT && reload_completed" > - [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) > - (set (match_dup 3) (match_op_dup:SI 6 > -[(ashiftrt:SI (match_dup 2) (const_int 31)) > - (match_dup 4)]))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - operands[5] = gen_highpart (SImode, operands[2]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - }" > -) > - > -;; The zero extend of operand 2 means we can just copy the high part of > -;; operand1 into operand0. > -(define_split > - [(set (match_operand:DI 0 "s_register_operand" "") > -(ior:DI > - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) > - (match_operand:DI 1 "s_register_operand" "")))] > - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" > - [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 2))) > - (set (match_dup 3) (match_dup 4))] > - " > - { > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > -) > - > -;; The zero extend of operand 2 means we can just copy the high part of > -;; operand1 into operand0. > -(define_split > - [(set (match_operand:DI 0 "s_register_operand" "") > -(xor:DI > - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) > - (match_operand:DI 1 "s_register_operand" "")))] > - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" > - [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 2))) > - (set (match_dup 3) (match_dup 4))] > - " > - { > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > -) > - > -(define_expand "anddi3" > - [(set (match_operand:DI 0 "s_register_operand") > -(and:DI (match_operand:DI 1 "s_register_operand") > -(match_operand:DI 2 "neon_inv_logic_op2")))] > - "TARGET_32BIT" > - " > - if (!TARGET_NEON && !TARGET_IWMMXT) > - { > - rtx low = simplify_gen_binary (AND, SImode, > - gen_lowpart (SImode, operands[1]), > - gen_lowpart (SImode, operands[2])); > - rtx high = simplify_gen_binary (AND, SImode, > - gen_highpart (SImode, operands[1]), > - gen_highpart_mode (SImode, DImode, > - operands[2])); > - > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > - > - DONE; > - } > - /* Otherwise expand pattern as above. */ > - " > -) > - > -(define_insn_and_split "*anddi3_insn" > - [(set (match_operand:DI 0 "s_register_operand" "=w,w > ,&r,&r,&r,&r,?w,?w") > - (and:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 > ,r ,0 ,r ,w ,0") > - (match_operand:DI 2 "arm_anddi_operand_neon" "w ,DL,r > ,r ,De,De,w ,DL")))] > - "TARGET_32BIT && !TARGET_IWMMXT" > -{ > - switch (which_alternative) > - { > - case 0: /* fall through */ > - case 6: return "vand\t%P0, %P1, %P2"; > - case 1: /* fall through */ > - case 7: return neon_output_logic_immediate ("vand", &operands[2], > - DImode, 1, VALID_NEON_QREG_MODE (DImode)); > - case 2: > - case 3: > - case 4: > - case 5: /* fall through */ > - return "#"; > - default: gcc_unreachable (); > - } > -} > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > - [(set (match_dup 3) (match_dup 4)) > - (set (match_dup 5) (match_dup 6))] > - " > - { > - operands[3] = gen_lowpart (SImode, operands[0]); > - operands[5] = gen_highpart (SImode, operands[0]); > - > - operands[4] = simplify_gen_binary (AND, SImode, > - gen_lowpart (SImode, operands[1]), > - gen_lowpart (SImode, operands[2])); > - operands[6] = simplify_gen_binary (AND, SImode, > - gen_highpart (SImode, operands[1]), > - gen_highpart_mode (SImode, DImode, operands[2])); > - > - }" > - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,\ > - multiple,multiple,neon_logic,neon_logic") > - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*, > - avoid_neon_for_64bits,avoid_neon_for_64bits") > - (set_attr "length" "*,*,8,8,8,8,*,*") > - ] > -) > - > -(define_insn_and_split "*anddi_zesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(and:DI (zero_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > + [(set (match_operand:DI 0 "s_register_operand") > +(not:DI (match_operand:DI 1 "s_register_operand")))] > "TARGET_32BIT" > - "#" > - "TARGET_32BIT && reload_completed" > - ; The zero extend of operand 2 clears the high word of the output > - ; operand. > - [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 2))) > - (set (match_dup 3) (const_int 0))] > + [(set (match_dup 0) (not:SI (match_dup 1))) > + (set (match_dup 2) (not:SI (match_dup 3)))] > " > { > - operands[3] = gen_highpart (SImode, operands[0]); > + operands[2] = gen_highpart (SImode, operands[0]); > operands[0] = gen_lowpart (SImode, operands[0]); > + operands[3] = gen_highpart (SImode, operands[1]); > operands[1] = gen_lowpart (SImode, operands[1]); > }" > - [(set_attr "length" "8") > - (set_attr "type" "multiple")] > -) > - > -(define_insn "*anddi_sesdi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(and:DI (sign_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > - "TARGET_32BIT" > - "#" > - [(set_attr "length" "8") > - (set_attr "type" "multiple")] > ) > > (define_expand "andsi3" > @@ -2952,105 +2802,6 @@ (define_insn "insv_t2" > (set_attr "type" "bfm")] > ) > > -; constants for op 2 will never be given to these patterns. > -(define_insn_and_split "*anddi_notdi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(and:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) > -(match_operand:DI 2 "s_register_operand" "r,0")))] > - "TARGET_32BIT" > - "#" > - "TARGET_32BIT && reload_completed > - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) > - && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" > - [(set (match_dup 0) (and:SI (not:SI (match_dup 1)) (match_dup 2))) > - (set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - operands[5] = gen_highpart (SImode, operands[2]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*anddi_notzesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(and:DI (not:DI (zero_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r"))) > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > - "TARGET_32BIT" > - "@ > - bic%?\\t%Q0, %Q1, %2 > - #" > - ; (not (zero_extend ...)) allows us to just copy the high word from > - ; operand1 to operand0. > - "TARGET_32BIT > - && reload_completed > - && operands[0] != operands[1]" > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (match_dup 4))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > - [(set_attr "length" "4,8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*anddi_notdi_zesidi" > - [(set (match_operand:DI 0 "s_register_operand" "=r") > - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r")) > - (zero_extend:DI > - (match_operand:SI 1 "s_register_operand" "r"))))] > - "TARGET_32BIT" > - "#" > - "TARGET_32BIT && reload_completed" > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (const_int 0))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*anddi_notsesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(and:DI (not:DI (sign_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r"))) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > - "TARGET_32BIT" > - "#" > - "TARGET_32BIT && reload_completed" > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (and:SI (not:SI > -(ashiftrt:SI (match_dup 2) (const_int 31))) > - (match_dup 4)))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > (define_insn "andsi_notsi_si" > [(set (match_operand:SI 0 "s_register_operand" "=r") > (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) > @@ -3150,101 +2901,6 @@ (define_insn "*andsi_notsi_si_compare0_scratch" > (set_attr "type" "logics_shift_reg")] > ) > > -(define_expand "iordi3" > - [(set (match_operand:DI 0 "s_register_operand") > -(ior:DI (match_operand:DI 1 "s_register_operand") > -(match_operand:DI 2 "neon_logic_op2")))] > - "TARGET_32BIT" > - " > - if (!TARGET_NEON && !TARGET_IWMMXT) > - { > - rtx low = simplify_gen_binary (IOR, SImode, > - gen_lowpart (SImode, operands[1]), > - gen_lowpart (SImode, operands[2])); > - rtx high = simplify_gen_binary (IOR, SImode, > - gen_highpart (SImode, operands[1]), > - gen_highpart_mode (SImode, DImode, > - operands[2])); > - > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > - > - DONE; > - } > - /* Otherwise expand pattern as above. */ > - " > -) > - > -(define_insn_and_split "*iordi3_insn" > - [(set (match_operand:DI 0 "s_register_operand" "=w,w > ,&r,&r,&r,&r,?w,?w") > -(ior:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 > ,r ,w ,0") > -(match_operand:DI 2 "arm_iordi_operand_neon" "w ,Dl,r ,r ,Df,Df,w > ,Dl")))] > - "TARGET_32BIT && !TARGET_IWMMXT" > - { > - switch (which_alternative) > - { > - case 0: /* fall through */ > - case 6: return "vorr\t%P0, %P1, %P2"; > - case 1: /* fall through */ > - case 7: return neon_output_logic_immediate ("vorr", &operands[2], > - DImode, 0, VALID_NEON_QREG_MODE (DImode)); > - case 2: > - case 3: > - case 4: > - case 5: > - return "#"; > - default: gcc_unreachable (); > - } > - } > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > - [(set (match_dup 3) (match_dup 4)) > - (set (match_dup 5) (match_dup 6))] > - " > - { > - operands[3] = gen_lowpart (SImode, operands[0]); > - operands[5] = gen_highpart (SImode, operands[0]); > - > - operands[4] = simplify_gen_binary (IOR, SImode, > - gen_lowpart (SImode, operands[1]), > - gen_lowpart (SImode, operands[2])); > - operands[6] = simplify_gen_binary (IOR, SImode, > - gen_highpart (SImode, operands[1]), > - gen_highpart_mode (SImode, DImode, operands[2])); > - > - }" > - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,multiple,\ > - multiple,neon_logic,neon_logic") > - (set_attr "length" "*,*,8,8,8,8,*,*") > - (set_attr "arch" > "neon_for_64bits,neon_for_64bits,*,*,*,*,avoid_neon_for_64bits,avoid_neon_for_64bits")] > -) > - > -(define_insn "*iordi_zesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (zero_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > - "TARGET_32BIT" > - "@ > - orr%?\\t%Q0, %Q1, %2 > - #" > - [(set_attr "length" "4,8") > - (set_attr "predicable" "yes") > - (set_attr "type" "logic_reg,multiple")] > -) > - > -(define_insn "*iordi_sesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (sign_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > - "TARGET_32BIT" > - "#" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > (define_expand "iorsi3" > [(set (match_operand:SI 0 "s_register_operand") > (ior:SI (match_operand:SI 1 "s_register_operand") > @@ -3347,103 +3003,6 @@ (define_insn "*iorsi3_compare0_scratch" > (set_attr "type" "logics_imm,logics_reg")] > ) > > -(define_expand "xordi3" > - [(set (match_operand:DI 0 "s_register_operand") > -(xor:DI (match_operand:DI 1 "s_register_operand") > -(match_operand:DI 2 "arm_xordi_operand")))] > - "TARGET_32BIT" > - { > - /* The iWMMXt pattern for xordi3 accepts only register operands > but we want > - to reuse this expander for all TARGET_32BIT targets so just > force the > - constants into a register. Unlike for the anddi3 and iordi3 > there are > - no NEON instructions that take an immediate. */ > - if (TARGET_IWMMXT && !REG_P (operands[2])) > - operands[2] = force_reg (DImode, operands[2]); > - if (!TARGET_NEON && !TARGET_IWMMXT) > - { > -rtx low = simplify_gen_binary (XOR, SImode, > -gen_lowpart (SImode, operands[1]), > -gen_lowpart (SImode, operands[2])); > -rtx high = simplify_gen_binary (XOR, SImode, > -gen_highpart (SImode, operands[1]), > -gen_highpart_mode (SImode, DImode, > - operands[2])); > - > -emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > -emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > - > -DONE; > - } > - /* Otherwise expand pattern as above. */ > - } > -) > - > -(define_insn_and_split "*xordi3_insn" > - [(set (match_operand:DI 0 "s_register_operand" > "=w,&r,&r,&r,&r,?w") > -(xor:DI (match_operand:DI 1 "s_register_operand" "%w ,0,r ,0 ,r ,w") > -(match_operand:DI 2 "arm_xordi_operand" "w ,r ,r ,Dg,Dg,w")))] > - "TARGET_32BIT && !TARGET_IWMMXT" > -{ > - switch (which_alternative) > - { > - case 1: > - case 2: > - case 3: > - case 4: /* fall through */ > - return "#"; > - case 0: /* fall through */ > - case 5: return "veor\t%P0, %P1, %P2"; > - default: gcc_unreachable (); > - } > -} > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > - [(set (match_dup 3) (match_dup 4)) > - (set (match_dup 5) (match_dup 6))] > - " > - { > - operands[3] = gen_lowpart (SImode, operands[0]); > - operands[5] = gen_highpart (SImode, operands[0]); > - > - operands[4] = simplify_gen_binary (XOR, SImode, > - gen_lowpart (SImode, operands[1]), > - gen_lowpart (SImode, operands[2])); > - operands[6] = simplify_gen_binary (XOR, SImode, > - gen_highpart (SImode, operands[1]), > - gen_highpart_mode (SImode, DImode, operands[2])); > - > - }" > - [(set_attr "length" "*,8,8,8,8,*") > - (set_attr "type" > "neon_logic,multiple,multiple,multiple,multiple,neon_logic") > - (set_attr "arch" "neon_for_64bits,*,*,*,*,avoid_neon_for_64bits")] > -) > - > -(define_insn "*xordi_zesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(xor:DI (zero_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > - "TARGET_32BIT" > - "@ > - eor%?\\t%Q0, %Q1, %2 > - #" > - [(set_attr "length" "4,8") > - (set_attr "predicable" "yes") > - (set_attr "type" "logic_reg")] > -) > - > -(define_insn "*xordi_sesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(xor:DI (sign_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r")) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > - "TARGET_32BIT" > - "#" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "type" "multiple")] > -) > - > (define_expand "xorsi3" > [(set (match_operand:SI 0 "s_register_operand") > (xor:SI (match_operand:SI 1 "s_register_operand") > @@ -5033,56 +4592,6 @@ (define_expand "sqrtdf2" > "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" > "") > > -(define_expand "one_cmpldi2" > - [(set (match_operand:DI 0 "s_register_operand") > -(not:DI (match_operand:DI 1 "s_register_operand")))] > - "TARGET_32BIT" > - " > - if (!TARGET_NEON && !TARGET_IWMMXT) > - { > - rtx low = simplify_gen_unary (NOT, SImode, > - gen_lowpart (SImode, operands[1]), > - SImode); > - rtx high = simplify_gen_unary (NOT, SImode, > - gen_highpart_mode (SImode, DImode, > -operands[1]), > - SImode); > - > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > - > - DONE; > - } > - /* Otherwise expand pattern as above. */ > - " > -) > - > -(define_insn_and_split "*one_cmpldi2_insn" > - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,?w") > -(not:DI (match_operand:DI 1 "s_register_operand" " w, 0, r, w")))] > - "TARGET_32BIT" > - "@ > - vmvn\t%P0, %P1 > - # > - # > - vmvn\t%P0, %P1" > - "TARGET_32BIT && reload_completed > - && arm_general_register_operand (operands[0], DImode)" > - [(set (match_dup 0) (not:SI (match_dup 1))) > - (set (match_dup 2) (not:SI (match_dup 3)))] > - " > - { > - operands[2] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[3] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > - [(set_attr "length" "*,8,8,*") > - (set_attr "predicable" "no,yes,yes,no") > - (set_attr "type" "neon_move,multiple,multiple,neon_move") > - (set_attr "arch" "neon_for_64bits,*,*,avoid_neon_for_64bits")] > -) > - > (define_expand "one_cmplsi2" > [(set (match_operand:SI 0 "s_register_operand") > (not:SI (match_operand:SI 1 "s_register_operand")))] > diff --git a/gcc/config/arm/constraints.md b/gcc/config/arm/constraints.md > index > d4a4c5967aea09816485d77f9ab90020aa085e73..b76de81b85c8ce7a2ca484a750b908b7ca64600a > 100644 > --- a/gcc/config/arm/constraints.md > +++ b/gcc/config/arm/constraints.md > @@ -273,24 +273,6 @@ (define_constraint "Dd" > (and (match_code "const_int") > (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, > PLUS)"))) > > -(define_constraint "De" > - "@internal > - In ARM/Thumb-2 state a const_int that can be used by insn anddi." > - (and (match_code "const_int") > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, AND)"))) > - > -(define_constraint "Df" > - "@internal > - In ARM/Thumb-2 state a const_int that can be used by insn iordi." > - (and (match_code "const_int") > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, IOR)"))) > - > -(define_constraint "Dg" > - "@internal > - In ARM/Thumb-2 state a const_int that can be used by insn xordi." > - (and (match_code "const_int") > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, XOR)"))) > - > (define_constraint "Di" > "@internal > In ARM/Thumb-2 state a const_int or const_double where both the high > diff --git a/gcc/config/arm/iwmmxt.md b/gcc/config/arm/iwmmxt.md > index > 310019aa5ceef98047b310284123f66940430095..86158ea4fd278180d5e2321c66c6c2b5e5c460b0 > 100644 > --- a/gcc/config/arm/iwmmxt.md > +++ b/gcc/config/arm/iwmmxt.md > @@ -55,45 +55,36 @@ (define_insn "tbcstv2si" > ) > > (define_insn "iwmmxt_iordi3" > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > - (ior:DI (match_operand:DI 1 "register_operand" "%y,0,r") > -(match_operand:DI 2 "register_operand" "y,r,r")))] > + [(set (match_operand:DI 0 "register_operand" "=y") > + (ior:DI (match_operand:DI 1 "register_operand" "%y") > +(match_operand:DI 2 "register_operand" "y")))] > "TARGET_REALLY_IWMMXT" > - "@ > - wor%?\\t%0, %1, %2 > - # > - #" > + "wor%?\\t%0, %1, %2" > [(set_attr "predicable" "yes") > - (set_attr "length" "4,8,8") > - (set_attr "type" "wmmx_wor,*,*")] > + (set_attr "length" "4") > + (set_attr "type" "wmmx_wor")] > ) > > (define_insn "iwmmxt_xordi3" > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > - (xor:DI (match_operand:DI 1 "register_operand" "%y,0,r") > -(match_operand:DI 2 "register_operand" "y,r,r")))] > + [(set (match_operand:DI 0 "register_operand" "=y") > + (xor:DI (match_operand:DI 1 "register_operand" "%y") > +(match_operand:DI 2 "register_operand" "y")))] > "TARGET_REALLY_IWMMXT" > - "@ > - wxor%?\\t%0, %1, %2 > - # > - #" > + "wxor%?\\t%0, %1, %2" > [(set_attr "predicable" "yes") > - (set_attr "length" "4,8,8") > - (set_attr "type" "wmmx_wxor,*,*")] > + (set_attr "length" "4") > + (set_attr "type" "wmmx_wxor")] > ) > > (define_insn "iwmmxt_anddi3" > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > - (and:DI (match_operand:DI 1 "register_operand" "%y,0,r") > -(match_operand:DI 2 "register_operand" "y,r,r")))] > + [(set (match_operand:DI 0 "register_operand" "=y") > + (and:DI (match_operand:DI 1 "register_operand" "%y") > +(match_operand:DI 2 "register_operand" "y")))] > "TARGET_REALLY_IWMMXT" > - "@ > - wand%?\\t%0, %1, %2 > - # > - #" > + "wand%?\\t%0, %1, %2" > [(set_attr "predicable" "yes") > - (set_attr "length" "4,8,8") > - (set_attr "type" "wmmx_wand,*,*")] > + (set_attr "length" "4") > + (set_attr "type" "wmmx_wand")] > ) > > (define_insn "iwmmxt_nanddi3" > diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md > index > 6333e0ea3ea68d73bed1f7c4d8ca090090ad68cc..ef73c77abeeaa02947c70ffa435f7bedc431e3be > 100644 > --- a/gcc/config/arm/neon.md > +++ b/gcc/config/arm/neon.md > @@ -838,46 +838,6 @@ (define_insn "orn<mode>3_neon" > [(set_attr "type" "neon_logic<q>")] > ) > > -;; TODO: investigate whether we should disable > -;; this and bicdi3_neon for the A8 in line with the other > -;; changes above. > -(define_insn_and_split "orndi3_neon" > - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r,?&r") > -(ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,0,0,r")) > -(match_operand:DI 1 "s_register_operand" "w,r,r,0")))] > - "TARGET_NEON" > - "@ > - vorn\t%P0, %P1, %P2 > - # > - # > - #" > - "reload_completed && > - (TARGET_NEON && !(IS_VFP_REGNUM (REGNO (operands[0]))))" > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] > - " > - { > - if (TARGET_THUMB2) > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[2]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - operands[5] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - } > - else > - { > - emit_insn (gen_one_cmpldi2 (operands[0], operands[2])); > - emit_insn (gen_iordi3 (operands[0], operands[1], operands[0])); > - DONE; > - } > - }" > - [(set_attr "type" "neon_logic,multiple,multiple,multiple") > - (set_attr "length" "*,16,8,8") > - (set_attr "arch" "any,a,t2,t2")] > -) > - > (define_insn "bic<mode>3_neon" > [(set (match_operand:VDQ 0 "s_register_operand" "=w") > (and:VDQ (not:VDQ (match_operand:VDQ 2 "s_register_operand" "w")) > @@ -887,20 +847,6 @@ (define_insn "bic<mode>3_neon" > [(set_attr "type" "neon_logic<q>")] > ) > > -;; Compare to *anddi_notdi_di. > -(define_insn "bicdi3_neon" > - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r") > - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" > "w,r,0")) > -(match_operand:DI 1 "s_register_operand" "w,0,r")))] > - "TARGET_NEON" > - "@ > - vbic\t%P0, %P1, %P2 > - # > - #" > - [(set_attr "type" "neon_logic,multiple,multiple") > - (set_attr "length" "*,8,8")] > -) > - > (define_insn "xor<mode>3" > [(set (match_operand:VDQ 0 "s_register_operand" "=w") > (xor:VDQ (match_operand:VDQ 1 "s_register_operand" "w") > diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md > index > f53378a250edfdd0de467f2abbe08bc933d6d734..af97edd28f27a1d8ab9ac2a63343380236d97603 > 100644 > --- a/gcc/config/arm/predicates.md > +++ b/gcc/config/arm/predicates.md > @@ -201,23 +201,6 @@ (define_predicate "arm_add_operand" > (ior (match_operand 0 "arm_rhs_operand") > (match_operand 0 "arm_neg_immediate_operand"))) > > -(define_predicate "arm_anddi_operand_neon" > - (ior (match_operand 0 "s_register_operand") > - (and (match_code "const_int") > - (match_test "const_ok_for_dimode_op (INTVAL (op), AND)")) > - (match_operand 0 "neon_inv_logic_op2"))) > - > -(define_predicate "arm_iordi_operand_neon" > - (ior (match_operand 0 "s_register_operand") > - (and (match_code "const_int") > - (match_test "const_ok_for_dimode_op (INTVAL (op), IOR)")) > - (match_operand 0 "neon_logic_op2"))) > - > -(define_predicate "arm_xordi_operand" > - (ior (match_operand 0 "s_register_operand") > - (and (match_code "const_int") > - (match_test "const_ok_for_dimode_op (INTVAL (op), XOR)")))) > - > (define_predicate "arm_adddi_operand" > (ior (match_operand 0 "s_register_operand") > (and (match_code "const_int") > diff --git a/gcc/config/arm/thumb2.md b/gcc/config/arm/thumb2.md > index > b283a7b656526d3c4719860d10aa1c0550288ba3..78a6ea0b10dab97ed6651ce62e99cfd7a81722ab > 100644 > --- a/gcc/config/arm/thumb2.md > +++ b/gcc/config/arm/thumb2.md > @@ -1478,103 +1478,6 @@ (define_insn "*thumb2_negsi2_short" > (set_attr "type" "alu_sreg")] > ) > > -; Constants for op 2 will never be given to these patterns. > -(define_insn_and_split "*iordi_notdi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) > -(match_operand:DI 2 "s_register_operand" "r,0")))] > - "TARGET_THUMB2" > - "#" > - "TARGET_THUMB2 && reload_completed" > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 1)) (match_dup 2))) > - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - operands[5] = gen_highpart (SImode, operands[2]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "predicable_short_it" "no") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*iordi_notzesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (not:DI (zero_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r"))) > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > - "TARGET_THUMB2" > - "#" > - ; (not (zero_extend...)) means operand0 will always be 0xffffffff > - "TARGET_THUMB2 && reload_completed" > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (const_int -1))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > - [(set_attr "length" "4,8") > - (set_attr "predicable" "yes") > - (set_attr "predicable_short_it" "no") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*iordi_notdi_zesidi" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "0,?r")) > -(zero_extend:DI > - (match_operand:SI 1 "s_register_operand" "r,r"))))] > - "TARGET_THUMB2" > - "#" > - "TARGET_THUMB2 && reload_completed" > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (not:SI (match_dup 4)))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - operands[4] = gen_highpart (SImode, operands[2]); > - operands[2] = gen_lowpart (SImode, operands[2]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "predicable_short_it" "no") > - (set_attr "type" "multiple")] > -) > - > -(define_insn_and_split "*iordi_notsesidi_di" > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > -(ior:DI (not:DI (sign_extend:DI > - (match_operand:SI 2 "s_register_operand" "r,r"))) > -(match_operand:DI 1 "s_register_operand" "0,r")))] > - "TARGET_THUMB2" > - "#" > - "TARGET_THUMB2 && reload_completed" > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > - (set (match_dup 3) (ior:SI (not:SI > -(ashiftrt:SI (match_dup 2) (const_int 31))) > - (match_dup 4)))] > - " > - { > - operands[3] = gen_highpart (SImode, operands[0]); > - operands[0] = gen_lowpart (SImode, operands[0]); > - operands[4] = gen_highpart (SImode, operands[1]); > - operands[1] = gen_lowpart (SImode, operands[1]); > - }" > - [(set_attr "length" "8") > - (set_attr "predicable" "yes") > - (set_attr "predicable_short_it" "no") > - (set_attr "type" "multiple")] > -) > - > (define_insn "*orsi_notsi_si" > [(set (match_operand:SI 0 "s_register_operand" "=r") > (ior:SI (not:SI (match_operand:SI 2 "s_register_operand" "r"))
On Thu, 22 Aug 2019 at 14:03, Kyrill Tkachov <kyrylo.tkachov@foss.arm.com> wrote: > > Hi Wilco, > > On 7/19/19 12:30 PM, Wilco Dijkstra wrote: > > > > Cleanup the logical DImode operations since the current implementation > > is way > > too complicated. Thumb-1, Thumb-2, VFP/Neon and iwMMXt all work > > differently, > > resulting in a bewildering number of expansions, patterns and splits > > across > > several md files. All this complexity is counterproductive and results in > > inefficient code. > > > > A much simpler approach is to split these operations early in the expander > > so that optimizations and register allocation are applied on the > > 32-bit halves. > > Code generation is unchanged on Thumb-1 and Arm/Thumb-2 without Neon > > or iwMMXt > > (which already expand these instructions early). With Neon these > > changes save > > ~1000 instructions from the PR77308 testcase, mostly by significantly > > reducing > > register pressure and spilling. > > > > Bootstrap & regress OK on arm-none-linux-gnueabihf --with-cpu=cortex-a57 > > > > OK for commit? Hi Wilco, After this was committed (r274823), I've noticed 2 regressions on arm*: FAIL: gcc.target/arm/pr53447-5.c scan-assembler-times (ldrd|vldr\\.64) 20 FAIL: gcc.target/arm/pr53447-5.c scan-assembler-times (strd|vstr\\.64) 18 Does this test still pass for you? Thanks, Christophe > > Ok. Thanks for doing this. > > Please keep an eye out for fallout after committing. > > Kyrill > > > > > > ChangeLog: > > 2019-07-18 Wilco Dijkstra <wdijkstr@arm.com> > > > > * config/arm/arm.md (split and/eor/ior): Remove Neon check. > > (split not): Add DImode not splitter. > > (anddi3): Remove pattern. > > (anddi3_insn): Likewise. > > (anddi_zesidi_di): Likewise. > > (anddi_sesdi_di): Likewise. > > (anddi_notdi_di): Likewise. > > (anddi_notzesidi_di): Likewise. > > (anddi_notsesidi_di): Likewise. > > (iordi3): Likewise. > > (iordi3_insn): Likewise. > > (iordi_zesidi_di): Likewise. > > (iordi_sesidi_di): Likewise. > > (xordi3): Likewise. > > (xordi3_insn): Likewise. > > (xordi_sesidi_di): Likewise. > > (xordi_zesidi_di): Likewise. > > (one_cmpldi2): Likewise. > > (one_cmpldi2_insn): Likewise. > > * config/arm/constraints.md: Remove De, Df, Dg constraints. > > * config/arm/iwmmxt.md (iwmmxt_iordi3): Remove general register > > alternative. > > (iwmmxt_xordi3): Likewise. > > (iwmmxt_anddi3): Likewise. > > * config/arm/neon.md (orndi3_neon): Remove pattern. > > (anddi_notdi_di): Likewise. > > * config/arm/predicates.md (arm_anddi_operand_neon): Remove. > > (arm_iordi_operand_neon): Likewise. > > (arm_xordi_operand_neon): Likewise. > > * config/arm/thumb2.md(iordi_notdi_di): Remove pattern. > > (iordi_notzesidi_di): Likewise. > > (iordi_notdi_zesidi): Likewise. > > (iordi_notsesidi_di): Likewise. > > > > > > --- > > diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md > > index > > 8f4a4c26ea849a023f2e63d2efbf327423512dfc..cab59c403b777c37c1e412ab9a69db2c2ec533a2 > > 100644 > > --- a/gcc/config/arm/arm.md > > +++ b/gcc/config/arm/arm.md > > @@ -2183,19 +2183,16 @@ (define_expand "divdf3" > > "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" > > "") > > > > -;; Boolean and,ior,xor insns > > > > -;; Split up double word logical operations > > - > > -;; Split up simple DImode logical operations. Simply perform the logical > > +;; Split DImode and, ior, xor operations. Simply perform the logical > > ;; operation on the upper and lower halves of the registers. > > +;; This is needed for atomic operations in arm_split_atomic_op. > > (define_split > > [(set (match_operand:DI 0 "s_register_operand" "") > > (match_operator:DI 6 "logical_binary_operator" > > [(match_operand:DI 1 "s_register_operand" "") > > (match_operand:DI 2 "s_register_operand" "")]))] > > "TARGET_32BIT && reload_completed > > - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) > > && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" > > [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) > > (set (match_dup 3) (match_op_dup:SI 6 [(match_dup 4) (match_dup 5)]))] > > @@ -2210,167 +2207,20 @@ (define_split > > }" > > ) > > > > +;; Split DImode not (needed for atomic operations in > > arm_split_atomic_op). > > (define_split > > - [(set (match_operand:DI 0 "s_register_operand" "") > > -(match_operator:DI 6 "logical_binary_operator" > > - [(sign_extend:DI (match_operand:SI 2 "s_register_operand" "")) > > - (match_operand:DI 1 "s_register_operand" "")]))] > > - "TARGET_32BIT && reload_completed" > > - [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) > > - (set (match_dup 3) (match_op_dup:SI 6 > > -[(ashiftrt:SI (match_dup 2) (const_int 31)) > > - (match_dup 4)]))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - operands[5] = gen_highpart (SImode, operands[2]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - }" > > -) > > - > > -;; The zero extend of operand 2 means we can just copy the high part of > > -;; operand1 into operand0. > > -(define_split > > - [(set (match_operand:DI 0 "s_register_operand" "") > > -(ior:DI > > - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) > > - (match_operand:DI 1 "s_register_operand" "")))] > > - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" > > - [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 2))) > > - (set (match_dup 3) (match_dup 4))] > > - " > > - { > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > -) > > - > > -;; The zero extend of operand 2 means we can just copy the high part of > > -;; operand1 into operand0. > > -(define_split > > - [(set (match_operand:DI 0 "s_register_operand" "") > > -(xor:DI > > - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) > > - (match_operand:DI 1 "s_register_operand" "")))] > > - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" > > - [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 2))) > > - (set (match_dup 3) (match_dup 4))] > > - " > > - { > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > -) > > - > > -(define_expand "anddi3" > > - [(set (match_operand:DI 0 "s_register_operand") > > -(and:DI (match_operand:DI 1 "s_register_operand") > > -(match_operand:DI 2 "neon_inv_logic_op2")))] > > - "TARGET_32BIT" > > - " > > - if (!TARGET_NEON && !TARGET_IWMMXT) > > - { > > - rtx low = simplify_gen_binary (AND, SImode, > > - gen_lowpart (SImode, operands[1]), > > - gen_lowpart (SImode, operands[2])); > > - rtx high = simplify_gen_binary (AND, SImode, > > - gen_highpart (SImode, operands[1]), > > - gen_highpart_mode (SImode, DImode, > > - operands[2])); > > - > > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > > - > > - DONE; > > - } > > - /* Otherwise expand pattern as above. */ > > - " > > -) > > - > > -(define_insn_and_split "*anddi3_insn" > > - [(set (match_operand:DI 0 "s_register_operand" "=w,w > > ,&r,&r,&r,&r,?w,?w") > > - (and:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 > > ,r ,0 ,r ,w ,0") > > - (match_operand:DI 2 "arm_anddi_operand_neon" "w ,DL,r > > ,r ,De,De,w ,DL")))] > > - "TARGET_32BIT && !TARGET_IWMMXT" > > -{ > > - switch (which_alternative) > > - { > > - case 0: /* fall through */ > > - case 6: return "vand\t%P0, %P1, %P2"; > > - case 1: /* fall through */ > > - case 7: return neon_output_logic_immediate ("vand", &operands[2], > > - DImode, 1, VALID_NEON_QREG_MODE (DImode)); > > - case 2: > > - case 3: > > - case 4: > > - case 5: /* fall through */ > > - return "#"; > > - default: gcc_unreachable (); > > - } > > -} > > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > > - [(set (match_dup 3) (match_dup 4)) > > - (set (match_dup 5) (match_dup 6))] > > - " > > - { > > - operands[3] = gen_lowpart (SImode, operands[0]); > > - operands[5] = gen_highpart (SImode, operands[0]); > > - > > - operands[4] = simplify_gen_binary (AND, SImode, > > - gen_lowpart (SImode, operands[1]), > > - gen_lowpart (SImode, operands[2])); > > - operands[6] = simplify_gen_binary (AND, SImode, > > - gen_highpart (SImode, operands[1]), > > - gen_highpart_mode (SImode, DImode, operands[2])); > > - > > - }" > > - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,\ > > - multiple,multiple,neon_logic,neon_logic") > > - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*, > > - avoid_neon_for_64bits,avoid_neon_for_64bits") > > - (set_attr "length" "*,*,8,8,8,8,*,*") > > - ] > > -) > > - > > -(define_insn_and_split "*anddi_zesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(and:DI (zero_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > + [(set (match_operand:DI 0 "s_register_operand") > > +(not:DI (match_operand:DI 1 "s_register_operand")))] > > "TARGET_32BIT" > > - "#" > > - "TARGET_32BIT && reload_completed" > > - ; The zero extend of operand 2 clears the high word of the output > > - ; operand. > > - [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 2))) > > - (set (match_dup 3) (const_int 0))] > > + [(set (match_dup 0) (not:SI (match_dup 1))) > > + (set (match_dup 2) (not:SI (match_dup 3)))] > > " > > { > > - operands[3] = gen_highpart (SImode, operands[0]); > > + operands[2] = gen_highpart (SImode, operands[0]); > > operands[0] = gen_lowpart (SImode, operands[0]); > > + operands[3] = gen_highpart (SImode, operands[1]); > > operands[1] = gen_lowpart (SImode, operands[1]); > > }" > > - [(set_attr "length" "8") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn "*anddi_sesdi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(and:DI (sign_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > - "TARGET_32BIT" > > - "#" > > - [(set_attr "length" "8") > > - (set_attr "type" "multiple")] > > ) > > > > (define_expand "andsi3" > > @@ -2952,105 +2802,6 @@ (define_insn "insv_t2" > > (set_attr "type" "bfm")] > > ) > > > > -; constants for op 2 will never be given to these patterns. > > -(define_insn_and_split "*anddi_notdi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(and:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) > > -(match_operand:DI 2 "s_register_operand" "r,0")))] > > - "TARGET_32BIT" > > - "#" > > - "TARGET_32BIT && reload_completed > > - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) > > - && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" > > - [(set (match_dup 0) (and:SI (not:SI (match_dup 1)) (match_dup 2))) > > - (set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - operands[5] = gen_highpart (SImode, operands[2]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*anddi_notzesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(and:DI (not:DI (zero_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r"))) > > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > > - "TARGET_32BIT" > > - "@ > > - bic%?\\t%Q0, %Q1, %2 > > - #" > > - ; (not (zero_extend ...)) allows us to just copy the high word from > > - ; operand1 to operand0. > > - "TARGET_32BIT > > - && reload_completed > > - && operands[0] != operands[1]" > > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (match_dup 4))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > - [(set_attr "length" "4,8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*anddi_notdi_zesidi" > > - [(set (match_operand:DI 0 "s_register_operand" "=r") > > - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r")) > > - (zero_extend:DI > > - (match_operand:SI 1 "s_register_operand" "r"))))] > > - "TARGET_32BIT" > > - "#" > > - "TARGET_32BIT && reload_completed" > > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (const_int 0))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*anddi_notsesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(and:DI (not:DI (sign_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r"))) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > - "TARGET_32BIT" > > - "#" > > - "TARGET_32BIT && reload_completed" > > - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (and:SI (not:SI > > -(ashiftrt:SI (match_dup 2) (const_int 31))) > > - (match_dup 4)))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > (define_insn "andsi_notsi_si" > > [(set (match_operand:SI 0 "s_register_operand" "=r") > > (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) > > @@ -3150,101 +2901,6 @@ (define_insn "*andsi_notsi_si_compare0_scratch" > > (set_attr "type" "logics_shift_reg")] > > ) > > > > -(define_expand "iordi3" > > - [(set (match_operand:DI 0 "s_register_operand") > > -(ior:DI (match_operand:DI 1 "s_register_operand") > > -(match_operand:DI 2 "neon_logic_op2")))] > > - "TARGET_32BIT" > > - " > > - if (!TARGET_NEON && !TARGET_IWMMXT) > > - { > > - rtx low = simplify_gen_binary (IOR, SImode, > > - gen_lowpart (SImode, operands[1]), > > - gen_lowpart (SImode, operands[2])); > > - rtx high = simplify_gen_binary (IOR, SImode, > > - gen_highpart (SImode, operands[1]), > > - gen_highpart_mode (SImode, DImode, > > - operands[2])); > > - > > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > > - > > - DONE; > > - } > > - /* Otherwise expand pattern as above. */ > > - " > > -) > > - > > -(define_insn_and_split "*iordi3_insn" > > - [(set (match_operand:DI 0 "s_register_operand" "=w,w > > ,&r,&r,&r,&r,?w,?w") > > -(ior:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 > > ,r ,w ,0") > > -(match_operand:DI 2 "arm_iordi_operand_neon" "w ,Dl,r ,r ,Df,Df,w > > ,Dl")))] > > - "TARGET_32BIT && !TARGET_IWMMXT" > > - { > > - switch (which_alternative) > > - { > > - case 0: /* fall through */ > > - case 6: return "vorr\t%P0, %P1, %P2"; > > - case 1: /* fall through */ > > - case 7: return neon_output_logic_immediate ("vorr", &operands[2], > > - DImode, 0, VALID_NEON_QREG_MODE (DImode)); > > - case 2: > > - case 3: > > - case 4: > > - case 5: > > - return "#"; > > - default: gcc_unreachable (); > > - } > > - } > > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > > - [(set (match_dup 3) (match_dup 4)) > > - (set (match_dup 5) (match_dup 6))] > > - " > > - { > > - operands[3] = gen_lowpart (SImode, operands[0]); > > - operands[5] = gen_highpart (SImode, operands[0]); > > - > > - operands[4] = simplify_gen_binary (IOR, SImode, > > - gen_lowpart (SImode, operands[1]), > > - gen_lowpart (SImode, operands[2])); > > - operands[6] = simplify_gen_binary (IOR, SImode, > > - gen_highpart (SImode, operands[1]), > > - gen_highpart_mode (SImode, DImode, operands[2])); > > - > > - }" > > - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,multiple,\ > > - multiple,neon_logic,neon_logic") > > - (set_attr "length" "*,*,8,8,8,8,*,*") > > - (set_attr "arch" > > "neon_for_64bits,neon_for_64bits,*,*,*,*,avoid_neon_for_64bits,avoid_neon_for_64bits")] > > -) > > - > > -(define_insn "*iordi_zesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (zero_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > > - "TARGET_32BIT" > > - "@ > > - orr%?\\t%Q0, %Q1, %2 > > - #" > > - [(set_attr "length" "4,8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "logic_reg,multiple")] > > -) > > - > > -(define_insn "*iordi_sesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (sign_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > - "TARGET_32BIT" > > - "#" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > (define_expand "iorsi3" > > [(set (match_operand:SI 0 "s_register_operand") > > (ior:SI (match_operand:SI 1 "s_register_operand") > > @@ -3347,103 +3003,6 @@ (define_insn "*iorsi3_compare0_scratch" > > (set_attr "type" "logics_imm,logics_reg")] > > ) > > > > -(define_expand "xordi3" > > - [(set (match_operand:DI 0 "s_register_operand") > > -(xor:DI (match_operand:DI 1 "s_register_operand") > > -(match_operand:DI 2 "arm_xordi_operand")))] > > - "TARGET_32BIT" > > - { > > - /* The iWMMXt pattern for xordi3 accepts only register operands > > but we want > > - to reuse this expander for all TARGET_32BIT targets so just > > force the > > - constants into a register. Unlike for the anddi3 and iordi3 > > there are > > - no NEON instructions that take an immediate. */ > > - if (TARGET_IWMMXT && !REG_P (operands[2])) > > - operands[2] = force_reg (DImode, operands[2]); > > - if (!TARGET_NEON && !TARGET_IWMMXT) > > - { > > -rtx low = simplify_gen_binary (XOR, SImode, > > -gen_lowpart (SImode, operands[1]), > > -gen_lowpart (SImode, operands[2])); > > -rtx high = simplify_gen_binary (XOR, SImode, > > -gen_highpart (SImode, operands[1]), > > -gen_highpart_mode (SImode, DImode, > > - operands[2])); > > - > > -emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > > -emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > > - > > -DONE; > > - } > > - /* Otherwise expand pattern as above. */ > > - } > > -) > > - > > -(define_insn_and_split "*xordi3_insn" > > - [(set (match_operand:DI 0 "s_register_operand" > > "=w,&r,&r,&r,&r,?w") > > -(xor:DI (match_operand:DI 1 "s_register_operand" "%w ,0,r ,0 ,r ,w") > > -(match_operand:DI 2 "arm_xordi_operand" "w ,r ,r ,Dg,Dg,w")))] > > - "TARGET_32BIT && !TARGET_IWMMXT" > > -{ > > - switch (which_alternative) > > - { > > - case 1: > > - case 2: > > - case 3: > > - case 4: /* fall through */ > > - return "#"; > > - case 0: /* fall through */ > > - case 5: return "veor\t%P0, %P1, %P2"; > > - default: gcc_unreachable (); > > - } > > -} > > - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed > > - && !(IS_VFP_REGNUM (REGNO (operands[0])))" > > - [(set (match_dup 3) (match_dup 4)) > > - (set (match_dup 5) (match_dup 6))] > > - " > > - { > > - operands[3] = gen_lowpart (SImode, operands[0]); > > - operands[5] = gen_highpart (SImode, operands[0]); > > - > > - operands[4] = simplify_gen_binary (XOR, SImode, > > - gen_lowpart (SImode, operands[1]), > > - gen_lowpart (SImode, operands[2])); > > - operands[6] = simplify_gen_binary (XOR, SImode, > > - gen_highpart (SImode, operands[1]), > > - gen_highpart_mode (SImode, DImode, operands[2])); > > - > > - }" > > - [(set_attr "length" "*,8,8,8,8,*") > > - (set_attr "type" > > "neon_logic,multiple,multiple,multiple,multiple,neon_logic") > > - (set_attr "arch" "neon_for_64bits,*,*,*,*,avoid_neon_for_64bits")] > > -) > > - > > -(define_insn "*xordi_zesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(xor:DI (zero_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > > - "TARGET_32BIT" > > - "@ > > - eor%?\\t%Q0, %Q1, %2 > > - #" > > - [(set_attr "length" "4,8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "logic_reg")] > > -) > > - > > -(define_insn "*xordi_sesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(xor:DI (sign_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r")) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > - "TARGET_32BIT" > > - "#" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "type" "multiple")] > > -) > > - > > (define_expand "xorsi3" > > [(set (match_operand:SI 0 "s_register_operand") > > (xor:SI (match_operand:SI 1 "s_register_operand") > > @@ -5033,56 +4592,6 @@ (define_expand "sqrtdf2" > > "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" > > "") > > > > -(define_expand "one_cmpldi2" > > - [(set (match_operand:DI 0 "s_register_operand") > > -(not:DI (match_operand:DI 1 "s_register_operand")))] > > - "TARGET_32BIT" > > - " > > - if (!TARGET_NEON && !TARGET_IWMMXT) > > - { > > - rtx low = simplify_gen_unary (NOT, SImode, > > - gen_lowpart (SImode, operands[1]), > > - SImode); > > - rtx high = simplify_gen_unary (NOT, SImode, > > - gen_highpart_mode (SImode, DImode, > > -operands[1]), > > - SImode); > > - > > - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); > > - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); > > - > > - DONE; > > - } > > - /* Otherwise expand pattern as above. */ > > - " > > -) > > - > > -(define_insn_and_split "*one_cmpldi2_insn" > > - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,?w") > > -(not:DI (match_operand:DI 1 "s_register_operand" " w, 0, r, w")))] > > - "TARGET_32BIT" > > - "@ > > - vmvn\t%P0, %P1 > > - # > > - # > > - vmvn\t%P0, %P1" > > - "TARGET_32BIT && reload_completed > > - && arm_general_register_operand (operands[0], DImode)" > > - [(set (match_dup 0) (not:SI (match_dup 1))) > > - (set (match_dup 2) (not:SI (match_dup 3)))] > > - " > > - { > > - operands[2] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[3] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > - [(set_attr "length" "*,8,8,*") > > - (set_attr "predicable" "no,yes,yes,no") > > - (set_attr "type" "neon_move,multiple,multiple,neon_move") > > - (set_attr "arch" "neon_for_64bits,*,*,avoid_neon_for_64bits")] > > -) > > - > > (define_expand "one_cmplsi2" > > [(set (match_operand:SI 0 "s_register_operand") > > (not:SI (match_operand:SI 1 "s_register_operand")))] > > diff --git a/gcc/config/arm/constraints.md b/gcc/config/arm/constraints.md > > index > > d4a4c5967aea09816485d77f9ab90020aa085e73..b76de81b85c8ce7a2ca484a750b908b7ca64600a > > 100644 > > --- a/gcc/config/arm/constraints.md > > +++ b/gcc/config/arm/constraints.md > > @@ -273,24 +273,6 @@ (define_constraint "Dd" > > (and (match_code "const_int") > > (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, > > PLUS)"))) > > > > -(define_constraint "De" > > - "@internal > > - In ARM/Thumb-2 state a const_int that can be used by insn anddi." > > - (and (match_code "const_int") > > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, AND)"))) > > - > > -(define_constraint "Df" > > - "@internal > > - In ARM/Thumb-2 state a const_int that can be used by insn iordi." > > - (and (match_code "const_int") > > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, IOR)"))) > > - > > -(define_constraint "Dg" > > - "@internal > > - In ARM/Thumb-2 state a const_int that can be used by insn xordi." > > - (and (match_code "const_int") > > - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, XOR)"))) > > - > > (define_constraint "Di" > > "@internal > > In ARM/Thumb-2 state a const_int or const_double where both the high > > diff --git a/gcc/config/arm/iwmmxt.md b/gcc/config/arm/iwmmxt.md > > index > > 310019aa5ceef98047b310284123f66940430095..86158ea4fd278180d5e2321c66c6c2b5e5c460b0 > > 100644 > > --- a/gcc/config/arm/iwmmxt.md > > +++ b/gcc/config/arm/iwmmxt.md > > @@ -55,45 +55,36 @@ (define_insn "tbcstv2si" > > ) > > > > (define_insn "iwmmxt_iordi3" > > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > > - (ior:DI (match_operand:DI 1 "register_operand" "%y,0,r") > > -(match_operand:DI 2 "register_operand" "y,r,r")))] > > + [(set (match_operand:DI 0 "register_operand" "=y") > > + (ior:DI (match_operand:DI 1 "register_operand" "%y") > > +(match_operand:DI 2 "register_operand" "y")))] > > "TARGET_REALLY_IWMMXT" > > - "@ > > - wor%?\\t%0, %1, %2 > > - # > > - #" > > + "wor%?\\t%0, %1, %2" > > [(set_attr "predicable" "yes") > > - (set_attr "length" "4,8,8") > > - (set_attr "type" "wmmx_wor,*,*")] > > + (set_attr "length" "4") > > + (set_attr "type" "wmmx_wor")] > > ) > > > > (define_insn "iwmmxt_xordi3" > > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > > - (xor:DI (match_operand:DI 1 "register_operand" "%y,0,r") > > -(match_operand:DI 2 "register_operand" "y,r,r")))] > > + [(set (match_operand:DI 0 "register_operand" "=y") > > + (xor:DI (match_operand:DI 1 "register_operand" "%y") > > +(match_operand:DI 2 "register_operand" "y")))] > > "TARGET_REALLY_IWMMXT" > > - "@ > > - wxor%?\\t%0, %1, %2 > > - # > > - #" > > + "wxor%?\\t%0, %1, %2" > > [(set_attr "predicable" "yes") > > - (set_attr "length" "4,8,8") > > - (set_attr "type" "wmmx_wxor,*,*")] > > + (set_attr "length" "4") > > + (set_attr "type" "wmmx_wxor")] > > ) > > > > (define_insn "iwmmxt_anddi3" > > - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") > > - (and:DI (match_operand:DI 1 "register_operand" "%y,0,r") > > -(match_operand:DI 2 "register_operand" "y,r,r")))] > > + [(set (match_operand:DI 0 "register_operand" "=y") > > + (and:DI (match_operand:DI 1 "register_operand" "%y") > > +(match_operand:DI 2 "register_operand" "y")))] > > "TARGET_REALLY_IWMMXT" > > - "@ > > - wand%?\\t%0, %1, %2 > > - # > > - #" > > + "wand%?\\t%0, %1, %2" > > [(set_attr "predicable" "yes") > > - (set_attr "length" "4,8,8") > > - (set_attr "type" "wmmx_wand,*,*")] > > + (set_attr "length" "4") > > + (set_attr "type" "wmmx_wand")] > > ) > > > > (define_insn "iwmmxt_nanddi3" > > diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md > > index > > 6333e0ea3ea68d73bed1f7c4d8ca090090ad68cc..ef73c77abeeaa02947c70ffa435f7bedc431e3be > > 100644 > > --- a/gcc/config/arm/neon.md > > +++ b/gcc/config/arm/neon.md > > @@ -838,46 +838,6 @@ (define_insn "orn<mode>3_neon" > > [(set_attr "type" "neon_logic<q>")] > > ) > > > > -;; TODO: investigate whether we should disable > > -;; this and bicdi3_neon for the A8 in line with the other > > -;; changes above. > > -(define_insn_and_split "orndi3_neon" > > - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r,?&r") > > -(ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,0,0,r")) > > -(match_operand:DI 1 "s_register_operand" "w,r,r,0")))] > > - "TARGET_NEON" > > - "@ > > - vorn\t%P0, %P1, %P2 > > - # > > - # > > - #" > > - "reload_completed && > > - (TARGET_NEON && !(IS_VFP_REGNUM (REGNO (operands[0]))))" > > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] > > - " > > - { > > - if (TARGET_THUMB2) > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[2]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - operands[5] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - } > > - else > > - { > > - emit_insn (gen_one_cmpldi2 (operands[0], operands[2])); > > - emit_insn (gen_iordi3 (operands[0], operands[1], operands[0])); > > - DONE; > > - } > > - }" > > - [(set_attr "type" "neon_logic,multiple,multiple,multiple") > > - (set_attr "length" "*,16,8,8") > > - (set_attr "arch" "any,a,t2,t2")] > > -) > > - > > (define_insn "bic<mode>3_neon" > > [(set (match_operand:VDQ 0 "s_register_operand" "=w") > > (and:VDQ (not:VDQ (match_operand:VDQ 2 "s_register_operand" "w")) > > @@ -887,20 +847,6 @@ (define_insn "bic<mode>3_neon" > > [(set_attr "type" "neon_logic<q>")] > > ) > > > > -;; Compare to *anddi_notdi_di. > > -(define_insn "bicdi3_neon" > > - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r") > > - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" > > "w,r,0")) > > -(match_operand:DI 1 "s_register_operand" "w,0,r")))] > > - "TARGET_NEON" > > - "@ > > - vbic\t%P0, %P1, %P2 > > - # > > - #" > > - [(set_attr "type" "neon_logic,multiple,multiple") > > - (set_attr "length" "*,8,8")] > > -) > > - > > (define_insn "xor<mode>3" > > [(set (match_operand:VDQ 0 "s_register_operand" "=w") > > (xor:VDQ (match_operand:VDQ 1 "s_register_operand" "w") > > diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md > > index > > f53378a250edfdd0de467f2abbe08bc933d6d734..af97edd28f27a1d8ab9ac2a63343380236d97603 > > 100644 > > --- a/gcc/config/arm/predicates.md > > +++ b/gcc/config/arm/predicates.md > > @@ -201,23 +201,6 @@ (define_predicate "arm_add_operand" > > (ior (match_operand 0 "arm_rhs_operand") > > (match_operand 0 "arm_neg_immediate_operand"))) > > > > -(define_predicate "arm_anddi_operand_neon" > > - (ior (match_operand 0 "s_register_operand") > > - (and (match_code "const_int") > > - (match_test "const_ok_for_dimode_op (INTVAL (op), AND)")) > > - (match_operand 0 "neon_inv_logic_op2"))) > > - > > -(define_predicate "arm_iordi_operand_neon" > > - (ior (match_operand 0 "s_register_operand") > > - (and (match_code "const_int") > > - (match_test "const_ok_for_dimode_op (INTVAL (op), IOR)")) > > - (match_operand 0 "neon_logic_op2"))) > > - > > -(define_predicate "arm_xordi_operand" > > - (ior (match_operand 0 "s_register_operand") > > - (and (match_code "const_int") > > - (match_test "const_ok_for_dimode_op (INTVAL (op), XOR)")))) > > - > > (define_predicate "arm_adddi_operand" > > (ior (match_operand 0 "s_register_operand") > > (and (match_code "const_int") > > diff --git a/gcc/config/arm/thumb2.md b/gcc/config/arm/thumb2.md > > index > > b283a7b656526d3c4719860d10aa1c0550288ba3..78a6ea0b10dab97ed6651ce62e99cfd7a81722ab > > 100644 > > --- a/gcc/config/arm/thumb2.md > > +++ b/gcc/config/arm/thumb2.md > > @@ -1478,103 +1478,6 @@ (define_insn "*thumb2_negsi2_short" > > (set_attr "type" "alu_sreg")] > > ) > > > > -; Constants for op 2 will never be given to these patterns. > > -(define_insn_and_split "*iordi_notdi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) > > -(match_operand:DI 2 "s_register_operand" "r,0")))] > > - "TARGET_THUMB2" > > - "#" > > - "TARGET_THUMB2 && reload_completed" > > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 1)) (match_dup 2))) > > - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - operands[5] = gen_highpart (SImode, operands[2]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "predicable_short_it" "no") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*iordi_notzesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (not:DI (zero_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r"))) > > -(match_operand:DI 1 "s_register_operand" "0,?r")))] > > - "TARGET_THUMB2" > > - "#" > > - ; (not (zero_extend...)) means operand0 will always be 0xffffffff > > - "TARGET_THUMB2 && reload_completed" > > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (const_int -1))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > - [(set_attr "length" "4,8") > > - (set_attr "predicable" "yes") > > - (set_attr "predicable_short_it" "no") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*iordi_notdi_zesidi" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "0,?r")) > > -(zero_extend:DI > > - (match_operand:SI 1 "s_register_operand" "r,r"))))] > > - "TARGET_THUMB2" > > - "#" > > - "TARGET_THUMB2 && reload_completed" > > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (not:SI (match_dup 4)))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - operands[4] = gen_highpart (SImode, operands[2]); > > - operands[2] = gen_lowpart (SImode, operands[2]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "predicable_short_it" "no") > > - (set_attr "type" "multiple")] > > -) > > - > > -(define_insn_and_split "*iordi_notsesidi_di" > > - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") > > -(ior:DI (not:DI (sign_extend:DI > > - (match_operand:SI 2 "s_register_operand" "r,r"))) > > -(match_operand:DI 1 "s_register_operand" "0,r")))] > > - "TARGET_THUMB2" > > - "#" > > - "TARGET_THUMB2 && reload_completed" > > - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) > > - (set (match_dup 3) (ior:SI (not:SI > > -(ashiftrt:SI (match_dup 2) (const_int 31))) > > - (match_dup 4)))] > > - " > > - { > > - operands[3] = gen_highpart (SImode, operands[0]); > > - operands[0] = gen_lowpart (SImode, operands[0]); > > - operands[4] = gen_highpart (SImode, operands[1]); > > - operands[1] = gen_lowpart (SImode, operands[1]); > > - }" > > - [(set_attr "length" "8") > > - (set_attr "predicable" "yes") > > - (set_attr "predicable_short_it" "no") > > - (set_attr "type" "multiple")] > > -) > > - > > (define_insn "*orsi_notsi_si" > > [(set (match_operand:SI 0 "s_register_operand" "=r") > > (ior:SI (not:SI (match_operand:SI 2 "s_register_operand" "r"))
Hi Christophe, > After this was committed (r274823), I've noticed 2 regressions on arm*: > FAIL: gcc.target/arm/pr53447-5.c scan-assembler-times (ldrd|vldr\\.64) 20 > FAIL: gcc.target/arm/pr53447-5.c scan-assembler-times (strd|vstr\\.64) 18 > > Does this test still pass for you? You're right, this fails for me too when I configure GCC for armv7-a or higher. It looks like a latent issue in that the Arm backend isn't able to recombine separate loads/stores into LDRD/STRD - eventhough it should really do that. There is a workaround - I can add back the logical DImode expanders which split off all memory operands before the DImode split (rather than the other way around). Cheers, Wilco
diff --git a/gcc/config/arm/arm.md b/gcc/config/arm/arm.md index 8f4a4c26ea849a023f2e63d2efbf327423512dfc..cab59c403b777c37c1e412ab9a69db2c2ec533a2 100644 --- a/gcc/config/arm/arm.md +++ b/gcc/config/arm/arm.md @@ -2183,19 +2183,16 @@ (define_expand "divdf3" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -;; Boolean and,ior,xor insns -;; Split up double word logical operations - -;; Split up simple DImode logical operations. Simply perform the logical +;; Split DImode and, ior, xor operations. Simply perform the logical ;; operation on the upper and lower halves of the registers. +;; This is needed for atomic operations in arm_split_atomic_op. (define_split [(set (match_operand:DI 0 "s_register_operand" "") (match_operator:DI 6 "logical_binary_operator" [(match_operand:DI 1 "s_register_operand" "") (match_operand:DI 2 "s_register_operand" "")]))] "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) (set (match_dup 3) (match_op_dup:SI 6 [(match_dup 4) (match_dup 5)]))] @@ -2210,167 +2207,20 @@ (define_split }" ) +;; Split DImode not (needed for atomic operations in arm_split_atomic_op). (define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (match_operator:DI 6 "logical_binary_operator" - [(sign_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")]))] - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (match_op_dup:SI 6 [(match_dup 1) (match_dup 2)])) - (set (match_dup 3) (match_op_dup:SI 6 - [(ashiftrt:SI (match_dup 2) (const_int 31)) - (match_dup 4)]))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (ior:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (ior:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -;; The zero extend of operand 2 means we can just copy the high part of -;; operand1 into operand0. -(define_split - [(set (match_operand:DI 0 "s_register_operand" "") - (xor:DI - (zero_extend:DI (match_operand:SI 2 "s_register_operand" "")) - (match_operand:DI 1 "s_register_operand" "")))] - "TARGET_32BIT && operands[0] != operands[1] && reload_completed" - [(set (match_dup 0) (xor:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[4] = gen_highpart (SImode, operands[1]); - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" -) - -(define_expand "anddi3" - [(set (match_operand:DI 0 "s_register_operand") - (and:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_inv_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*anddi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (and:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_anddi_operand_neon" "w ,DL,r ,r ,De,De,w ,DL")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vand\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vand", &operands[2], - DImode, 1, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: /* fall through */ - return "#"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (AND, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (AND, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,\ - multiple,multiple,neon_logic,neon_logic") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*, - avoid_neon_for_64bits,avoid_neon_for_64bits") - (set_attr "length" "*,*,8,8,8,8,*,*") - ] -) - -(define_insn_and_split "*anddi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] + [(set (match_operand:DI 0 "s_register_operand") + (not:DI (match_operand:DI 1 "s_register_operand")))] "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - ; The zero extend of operand 2 clears the high word of the output - ; operand. - [(set (match_dup 0) (and:SI (match_dup 1) (match_dup 2))) - (set (match_dup 3) (const_int 0))] + [(set (match_dup 0) (not:SI (match_dup 1))) + (set (match_dup 2) (not:SI (match_dup 3)))] " { - operands[3] = gen_highpart (SImode, operands[0]); + operands[2] = gen_highpart (SImode, operands[0]); operands[0] = gen_lowpart (SImode, operands[0]); + operands[3] = gen_highpart (SImode, operands[1]); operands[1] = gen_lowpart (SImode, operands[1]); }" - [(set_attr "length" "8") - (set_attr "type" "multiple")] -) - -(define_insn "*anddi_sesdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "type" "multiple")] ) (define_expand "andsi3" @@ -2952,105 +2802,6 @@ (define_insn "insv_t2" (set_attr "type" "bfm")] ) -; constants for op 2 will never be given to these patterns. -(define_insn_and_split "*anddi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed - && ! (TARGET_NEON && IS_VFP_REGNUM (REGNO (operands[0]))) - && ! IS_IWMMXT_REGNUM (REGNO (operands[0]))" - [(set (match_dup 0) (and:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (and:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - bic%?\\t%Q0, %Q1, %2 - #" - ; (not (zero_extend ...)) allows us to just copy the high word from - ; operand1 to operand0. - "TARGET_32BIT - && reload_completed - && operands[0] != operands[1]" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (match_dup 4))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r"))))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int 0))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*anddi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (and:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - "TARGET_32BIT && reload_completed" - [(set (match_dup 0) (and:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (and:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_insn "andsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (and:SI (not:SI (match_operand:SI 2 "s_register_operand" "r")) @@ -3150,101 +2901,6 @@ (define_insn "*andsi_notsi_si_compare0_scratch" (set_attr "type" "logics_shift_reg")] ) -(define_expand "iordi3" - [(set (match_operand:DI 0 "s_register_operand") - (ior:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "neon_logic_op2")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*iordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,w ,&r,&r,&r,&r,?w,?w") - (ior:DI (match_operand:DI 1 "s_register_operand" "%w,0 ,0 ,r ,0 ,r ,w ,0") - (match_operand:DI 2 "arm_iordi_operand_neon" "w ,Dl,r ,r ,Df,Df,w ,Dl")))] - "TARGET_32BIT && !TARGET_IWMMXT" - { - switch (which_alternative) - { - case 0: /* fall through */ - case 6: return "vorr\t%P0, %P1, %P2"; - case 1: /* fall through */ - case 7: return neon_output_logic_immediate ("vorr", &operands[2], - DImode, 0, VALID_NEON_QREG_MODE (DImode)); - case 2: - case 3: - case 4: - case 5: - return "#"; - default: gcc_unreachable (); - } - } - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (IOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (IOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "type" "neon_logic,neon_logic,multiple,multiple,multiple,\ - multiple,neon_logic,neon_logic") - (set_attr "length" "*,*,8,8,8,8,*,*") - (set_attr "arch" "neon_for_64bits,neon_for_64bits,*,*,*,*,avoid_neon_for_64bits,avoid_neon_for_64bits")] -) - -(define_insn "*iordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - orr%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg,multiple")] -) - -(define_insn "*iordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "iorsi3" [(set (match_operand:SI 0 "s_register_operand") (ior:SI (match_operand:SI 1 "s_register_operand") @@ -3347,103 +3003,6 @@ (define_insn "*iorsi3_compare0_scratch" (set_attr "type" "logics_imm,logics_reg")] ) -(define_expand "xordi3" - [(set (match_operand:DI 0 "s_register_operand") - (xor:DI (match_operand:DI 1 "s_register_operand") - (match_operand:DI 2 "arm_xordi_operand")))] - "TARGET_32BIT" - { - /* The iWMMXt pattern for xordi3 accepts only register operands but we want - to reuse this expander for all TARGET_32BIT targets so just force the - constants into a register. Unlike for the anddi3 and iordi3 there are - no NEON instructions that take an immediate. */ - if (TARGET_IWMMXT && !REG_P (operands[2])) - operands[2] = force_reg (DImode, operands[2]); - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - rtx high = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, - operands[2])); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - } -) - -(define_insn_and_split "*xordi3_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,&r,&r,?w") - (xor:DI (match_operand:DI 1 "s_register_operand" "%w ,0,r ,0 ,r ,w") - (match_operand:DI 2 "arm_xordi_operand" "w ,r ,r ,Dg,Dg,w")))] - "TARGET_32BIT && !TARGET_IWMMXT" -{ - switch (which_alternative) - { - case 1: - case 2: - case 3: - case 4: /* fall through */ - return "#"; - case 0: /* fall through */ - case 5: return "veor\t%P0, %P1, %P2"; - default: gcc_unreachable (); - } -} - "TARGET_32BIT && !TARGET_IWMMXT && reload_completed - && !(IS_VFP_REGNUM (REGNO (operands[0])))" - [(set (match_dup 3) (match_dup 4)) - (set (match_dup 5) (match_dup 6))] - " - { - operands[3] = gen_lowpart (SImode, operands[0]); - operands[5] = gen_highpart (SImode, operands[0]); - - operands[4] = simplify_gen_binary (XOR, SImode, - gen_lowpart (SImode, operands[1]), - gen_lowpart (SImode, operands[2])); - operands[6] = simplify_gen_binary (XOR, SImode, - gen_highpart (SImode, operands[1]), - gen_highpart_mode (SImode, DImode, operands[2])); - - }" - [(set_attr "length" "*,8,8,8,8,*") - (set_attr "type" "neon_logic,multiple,multiple,multiple,multiple,neon_logic") - (set_attr "arch" "neon_for_64bits,*,*,*,*,avoid_neon_for_64bits")] -) - -(define_insn "*xordi_zesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_32BIT" - "@ - eor%?\\t%Q0, %Q1, %2 - #" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "type" "logic_reg")] -) - -(define_insn "*xordi_sesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (xor:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r")) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_32BIT" - "#" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "type" "multiple")] -) - (define_expand "xorsi3" [(set (match_operand:SI 0 "s_register_operand") (xor:SI (match_operand:SI 1 "s_register_operand") @@ -5033,56 +4592,6 @@ (define_expand "sqrtdf2" "TARGET_32BIT && TARGET_HARD_FLOAT && TARGET_VFP_DOUBLE" "") -(define_expand "one_cmpldi2" - [(set (match_operand:DI 0 "s_register_operand") - (not:DI (match_operand:DI 1 "s_register_operand")))] - "TARGET_32BIT" - " - if (!TARGET_NEON && !TARGET_IWMMXT) - { - rtx low = simplify_gen_unary (NOT, SImode, - gen_lowpart (SImode, operands[1]), - SImode); - rtx high = simplify_gen_unary (NOT, SImode, - gen_highpart_mode (SImode, DImode, - operands[1]), - SImode); - - emit_insn (gen_rtx_SET (gen_lowpart (SImode, operands[0]), low)); - emit_insn (gen_rtx_SET (gen_highpart (SImode, operands[0]), high)); - - DONE; - } - /* Otherwise expand pattern as above. */ - " -) - -(define_insn_and_split "*one_cmpldi2_insn" - [(set (match_operand:DI 0 "s_register_operand" "=w,&r,&r,?w") - (not:DI (match_operand:DI 1 "s_register_operand" " w, 0, r, w")))] - "TARGET_32BIT" - "@ - vmvn\t%P0, %P1 - # - # - vmvn\t%P0, %P1" - "TARGET_32BIT && reload_completed - && arm_general_register_operand (operands[0], DImode)" - [(set (match_dup 0) (not:SI (match_dup 1))) - (set (match_dup 2) (not:SI (match_dup 3)))] - " - { - operands[2] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[3] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "*,8,8,*") - (set_attr "predicable" "no,yes,yes,no") - (set_attr "type" "neon_move,multiple,multiple,neon_move") - (set_attr "arch" "neon_for_64bits,*,*,avoid_neon_for_64bits")] -) - (define_expand "one_cmplsi2" [(set (match_operand:SI 0 "s_register_operand") (not:SI (match_operand:SI 1 "s_register_operand")))] diff --git a/gcc/config/arm/constraints.md b/gcc/config/arm/constraints.md index d4a4c5967aea09816485d77f9ab90020aa085e73..b76de81b85c8ce7a2ca484a750b908b7ca64600a 100644 --- a/gcc/config/arm/constraints.md +++ b/gcc/config/arm/constraints.md @@ -273,24 +273,6 @@ (define_constraint "Dd" (and (match_code "const_int") (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, PLUS)"))) -(define_constraint "De" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn anddi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, AND)"))) - -(define_constraint "Df" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn iordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, IOR)"))) - -(define_constraint "Dg" - "@internal - In ARM/Thumb-2 state a const_int that can be used by insn xordi." - (and (match_code "const_int") - (match_test "TARGET_32BIT && const_ok_for_dimode_op (ival, XOR)"))) - (define_constraint "Di" "@internal In ARM/Thumb-2 state a const_int or const_double where both the high diff --git a/gcc/config/arm/iwmmxt.md b/gcc/config/arm/iwmmxt.md index 310019aa5ceef98047b310284123f66940430095..86158ea4fd278180d5e2321c66c6c2b5e5c460b0 100644 --- a/gcc/config/arm/iwmmxt.md +++ b/gcc/config/arm/iwmmxt.md @@ -55,45 +55,36 @@ (define_insn "tbcstv2si" ) (define_insn "iwmmxt_iordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (ior:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (ior:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wor%?\\t%0, %1, %2 - # - #" + "wor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wor")] ) (define_insn "iwmmxt_xordi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (xor:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (xor:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wxor%?\\t%0, %1, %2 - # - #" + "wxor%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wxor,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wxor")] ) (define_insn "iwmmxt_anddi3" - [(set (match_operand:DI 0 "register_operand" "=y,?&r,?&r") - (and:DI (match_operand:DI 1 "register_operand" "%y,0,r") - (match_operand:DI 2 "register_operand" "y,r,r")))] + [(set (match_operand:DI 0 "register_operand" "=y") + (and:DI (match_operand:DI 1 "register_operand" "%y") + (match_operand:DI 2 "register_operand" "y")))] "TARGET_REALLY_IWMMXT" - "@ - wand%?\\t%0, %1, %2 - # - #" + "wand%?\\t%0, %1, %2" [(set_attr "predicable" "yes") - (set_attr "length" "4,8,8") - (set_attr "type" "wmmx_wand,*,*")] + (set_attr "length" "4") + (set_attr "type" "wmmx_wand")] ) (define_insn "iwmmxt_nanddi3" diff --git a/gcc/config/arm/neon.md b/gcc/config/arm/neon.md index 6333e0ea3ea68d73bed1f7c4d8ca090090ad68cc..ef73c77abeeaa02947c70ffa435f7bedc431e3be 100644 --- a/gcc/config/arm/neon.md +++ b/gcc/config/arm/neon.md @@ -838,46 +838,6 @@ (define_insn "orn<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; TODO: investigate whether we should disable -;; this and bicdi3_neon for the A8 in line with the other -;; changes above. -(define_insn_and_split "orndi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r,?&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,0,0,r")) - (match_operand:DI 1 "s_register_operand" "w,r,r,0")))] - "TARGET_NEON" - "@ - vorn\t%P0, %P1, %P2 - # - # - #" - "reload_completed && - (TARGET_NEON && !(IS_VFP_REGNUM (REGNO (operands[0]))))" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - if (TARGET_THUMB2) - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - operands[5] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - } - else - { - emit_insn (gen_one_cmpldi2 (operands[0], operands[2])); - emit_insn (gen_iordi3 (operands[0], operands[1], operands[0])); - DONE; - } - }" - [(set_attr "type" "neon_logic,multiple,multiple,multiple") - (set_attr "length" "*,16,8,8") - (set_attr "arch" "any,a,t2,t2")] -) - (define_insn "bic<mode>3_neon" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (and:VDQ (not:VDQ (match_operand:VDQ 2 "s_register_operand" "w")) @@ -887,20 +847,6 @@ (define_insn "bic<mode>3_neon" [(set_attr "type" "neon_logic<q>")] ) -;; Compare to *anddi_notdi_di. -(define_insn "bicdi3_neon" - [(set (match_operand:DI 0 "s_register_operand" "=w,?&r,?&r") - (and:DI (not:DI (match_operand:DI 2 "s_register_operand" "w,r,0")) - (match_operand:DI 1 "s_register_operand" "w,0,r")))] - "TARGET_NEON" - "@ - vbic\t%P0, %P1, %P2 - # - #" - [(set_attr "type" "neon_logic,multiple,multiple") - (set_attr "length" "*,8,8")] -) - (define_insn "xor<mode>3" [(set (match_operand:VDQ 0 "s_register_operand" "=w") (xor:VDQ (match_operand:VDQ 1 "s_register_operand" "w") diff --git a/gcc/config/arm/predicates.md b/gcc/config/arm/predicates.md index f53378a250edfdd0de467f2abbe08bc933d6d734..af97edd28f27a1d8ab9ac2a63343380236d97603 100644 --- a/gcc/config/arm/predicates.md +++ b/gcc/config/arm/predicates.md @@ -201,23 +201,6 @@ (define_predicate "arm_add_operand" (ior (match_operand 0 "arm_rhs_operand") (match_operand 0 "arm_neg_immediate_operand"))) -(define_predicate "arm_anddi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), AND)")) - (match_operand 0 "neon_inv_logic_op2"))) - -(define_predicate "arm_iordi_operand_neon" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), IOR)")) - (match_operand 0 "neon_logic_op2"))) - -(define_predicate "arm_xordi_operand" - (ior (match_operand 0 "s_register_operand") - (and (match_code "const_int") - (match_test "const_ok_for_dimode_op (INTVAL (op), XOR)")))) - (define_predicate "arm_adddi_operand" (ior (match_operand 0 "s_register_operand") (and (match_code "const_int") diff --git a/gcc/config/arm/thumb2.md b/gcc/config/arm/thumb2.md index b283a7b656526d3c4719860d10aa1c0550288ba3..78a6ea0b10dab97ed6651ce62e99cfd7a81722ab 100644 --- a/gcc/config/arm/thumb2.md +++ b/gcc/config/arm/thumb2.md @@ -1478,103 +1478,6 @@ (define_insn "*thumb2_negsi2_short" (set_attr "type" "alu_sreg")] ) -; Constants for op 2 will never be given to these patterns. -(define_insn_and_split "*iordi_notdi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 1 "s_register_operand" "0,r")) - (match_operand:DI 2 "s_register_operand" "r,0")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 1)) (match_dup 2))) - (set (match_dup 3) (ior:SI (not:SI (match_dup 4)) (match_dup 5)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[5] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notzesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (zero_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,?r")))] - "TARGET_THUMB2" - "#" - ; (not (zero_extend...)) means operand0 will always be 0xffffffff - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (const_int -1))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "4,8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notdi_zesidi" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (match_operand:DI 2 "s_register_operand" "0,?r")) - (zero_extend:DI - (match_operand:SI 1 "s_register_operand" "r,r"))))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (not:SI (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[1] = gen_lowpart (SImode, operands[1]); - operands[4] = gen_highpart (SImode, operands[2]); - operands[2] = gen_lowpart (SImode, operands[2]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - -(define_insn_and_split "*iordi_notsesidi_di" - [(set (match_operand:DI 0 "s_register_operand" "=&r,&r") - (ior:DI (not:DI (sign_extend:DI - (match_operand:SI 2 "s_register_operand" "r,r"))) - (match_operand:DI 1 "s_register_operand" "0,r")))] - "TARGET_THUMB2" - "#" - "TARGET_THUMB2 && reload_completed" - [(set (match_dup 0) (ior:SI (not:SI (match_dup 2)) (match_dup 1))) - (set (match_dup 3) (ior:SI (not:SI - (ashiftrt:SI (match_dup 2) (const_int 31))) - (match_dup 4)))] - " - { - operands[3] = gen_highpart (SImode, operands[0]); - operands[0] = gen_lowpart (SImode, operands[0]); - operands[4] = gen_highpart (SImode, operands[1]); - operands[1] = gen_lowpart (SImode, operands[1]); - }" - [(set_attr "length" "8") - (set_attr "predicable" "yes") - (set_attr "predicable_short_it" "no") - (set_attr "type" "multiple")] -) - (define_insn "*orsi_notsi_si" [(set (match_operand:SI 0 "s_register_operand" "=r") (ior:SI (not:SI (match_operand:SI 2 "s_register_operand" "r"))