From e95395926a84a2406faefe0995295d199d595440 Mon Sep 17 00:00:00 2001 From: Uros Bizjak Date: Thu, 18 Jun 2020 20:12:48 +0200 Subject: [PATCH] i386: Fix mode of ZERO_EXTRACT RTXes, remove ext_register_operand predicate. MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit The mode of ZERO_EXTRACT RTX should match the mode of its LOC register operand. The mode should be HI, SI or DImode to enable combine to synthesize extractions from HImode and DImode operands, in addition to existing SImode. Further, these changes tighten allowed modes for extv, extzv and insv named patterns and finally enable removal of ext_register_operand special predicate. 2020-18-06 Uroš Bizjak gcc/ChangeLog: * config/i386/i386.md (*cmpqi_ext_1): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. Rename from *cmpqi_ext_1. (*cmpqi_ext_2): Ditto. Rename from *cmpqi_ext_2. (*cmpqi_ext_3): Ditto. Rename from *cmpqi_ext_3. (*cmpqi_ext_4): Ditto. Rename from *cmpqi_ext_4. (cmpi_ext_3): Use HImode instead of SImode for ZERO_EXTRACT RTX. (*extv): Use SWI24 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (*extzv): Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (*extzvqi): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (*extzvqi_mem_rex64 and corresponding peephole2): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (@insv_1): Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (*insvqi_1): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (*insvqi_2): Ditto. (*insvqi_3): Ditto. (*insvqi_1_mem_rex64 and corresponding peephole2): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. (addqi_ext_1): New expander. (*addqi_ext_1): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. Rename from *addqi_ext_1. (*addqi_ext_2): Ditto. Rename from *addqi_ext_2. (divmodqi4): Use HImode instead of SImode for ZERO_EXTRACT RTX. (udivmodqi4): Ditto. (testqi_ext_1): Use HImode instead of SImode for ZERO_EXTRACT RTX. (*testqi_ext_1): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. Rename from *testqi_ext_1. (*testqi_ext_2): Ditto. Rename from *testqi_ext_2. (andqi_ext_1): New expander. (*andqi_ext_1): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. Rename from andqi_ext_1. (*andqi_ext_1_cc): Ditto. Rename from *andqi_ext_1_cc. (*andqi_ext_2): Ditto. Rename from *andqi_ext_2. (*qi_ext_1): Ditto. Rename from *qi_ext_1. (*qi_ext_2): Ditto. Rename from *qi_ext_2. (xorqi_ext_1_cc): Use HImode instead of SImode for ZERO_EXTRACT RTX. (*xorqi_ext_1_cc): Use SWI248 mode iterator instead of SImode for ZERO_EXTRACT RTX. Use SWI248 mode iterator for the first operand of ZERO_EXTRACT RTX. Change ext_register_operand predicate to register_operand. Rename from *xorqi_ext_1_cc. * config/i386/i386-expand.c (ix86_split_idivmod): Emit ZERO_EXTRACT in mode, matching its first operand. (promote_duplicated_reg): Update for renamed insv_1. * config/i386/predicates.md (ext_register_operand): Remove predicate. gcc/testsuite/ChangeLog: * gcc.target/i386/pr78904-1a.c: New test. * gcc.target/i386/pr78904-1b.c: Ditto. * gcc.target/i386/pr78904-2a.c: Ditto. * gcc.target/i386/pr78904-2b.c: Ditto. * gcc.target/i386/pr78904-3a.c: Ditto. * gcc.target/i386/pr78904-3b.c: Ditto. * gcc.target/i386/pr78904-4a.c: Ditto. * gcc.target/i386/pr78904-4b.c: Ditto. * gcc.target/i386/pr78904-5a.c: Ditto. * gcc.target/i386/pr78904-5b.c: Ditto. * gcc.target/i386/pr78904-6a.c: Ditto. * gcc.target/i386/pr78904-6b.c: Ditto. * gcc.target/i386/pr78967-1a.c: Ditto. * gcc.target/i386/pr78967-1b.c: Ditto. * gcc.target/i386/pr78967-2a.c: Ditto. * gcc.target/i386/pr78967-2b.c: Ditto. --- gcc/config/i386/i386-expand.c | 26 +- gcc/config/i386/i386.md | 450 ++++++++++++--------- gcc/config/i386/predicates.md | 8 - gcc/testsuite/gcc.target/i386/pr78904-1a.c | 47 +++ gcc/testsuite/gcc.target/i386/pr78904-1b.c | 49 +++ gcc/testsuite/gcc.target/i386/pr78904-2a.c | 48 +++ gcc/testsuite/gcc.target/i386/pr78904-2b.c | 50 +++ gcc/testsuite/gcc.target/i386/pr78904-3a.c | 42 ++ gcc/testsuite/gcc.target/i386/pr78904-3b.c | 43 ++ gcc/testsuite/gcc.target/i386/pr78904-4a.c | 21 + gcc/testsuite/gcc.target/i386/pr78904-4b.c | 23 ++ gcc/testsuite/gcc.target/i386/pr78904-5a.c | 21 + gcc/testsuite/gcc.target/i386/pr78904-5b.c | 23 ++ gcc/testsuite/gcc.target/i386/pr78904-6a.c | 21 + gcc/testsuite/gcc.target/i386/pr78904-6b.c | 23 ++ gcc/testsuite/gcc.target/i386/pr78967-1a.c | 20 + gcc/testsuite/gcc.target/i386/pr78967-1b.c | 21 + gcc/testsuite/gcc.target/i386/pr78967-2a.c | 24 ++ gcc/testsuite/gcc.target/i386/pr78967-2b.c | 26 ++ 19 files changed, 765 insertions(+), 221 deletions(-) create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-1a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-1b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-2a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-2b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-3a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-3b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-4a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-4b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-5a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-5b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-6a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78904-6b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78967-1a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78967-1b.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78967-2a.c create mode 100644 gcc/testsuite/gcc.target/i386/pr78967-2b.c diff --git a/gcc/config/i386/i386-expand.c b/gcc/config/i386/i386-expand.c index d7077980f9b..d81dd73f034 100644 --- a/gcc/config/i386/i386-expand.c +++ b/gcc/config/i386/i386-expand.c @@ -1179,9 +1179,8 @@ ix86_split_idivmod (machine_mode mode, rtx operands[], JUMP_LABEL (insn) = qimode_label; /* Generate original signed/unsigned divimod. */ - div = gen_divmod4_1 (operands[0], operands[1], - operands[2], operands[3]); - emit_insn (div); + emit_insn (gen_divmod4_1 (operands[0], operands[1], + operands[2], operands[3])); /* Branch to the end. */ emit_jump_insn (gen_jump (end_label)); @@ -1215,18 +1214,10 @@ ix86_split_idivmod (machine_mode mode, rtx operands[], } /* Extract remainder from AH. */ - tmp1 = gen_rtx_ZERO_EXTRACT (GET_MODE (operands[1]), - tmp0, GEN_INT (8), GEN_INT (8)); - if (REG_P (operands[1])) - insn = emit_move_insn (operands[1], tmp1); - else - { - /* Need a new scratch register since the old one has result - of 8bit divide. */ - scratch = gen_reg_rtx (GET_MODE (operands[1])); - emit_move_insn (scratch, tmp1); - insn = emit_move_insn (operands[1], scratch); - } + scratch = gen_lowpart (GET_MODE (operands[1]), scratch); + tmp1 = gen_rtx_ZERO_EXTRACT (GET_MODE (operands[1]), scratch, + GEN_INT (8), GEN_INT (8)); + insn = emit_move_insn (operands[1], tmp1); set_unique_reg_note (insn, REG_EQUAL, mod); /* Zero extend quotient from AL. */ @@ -7060,10 +7051,7 @@ promote_duplicated_reg (machine_mode mode, rtx val) rtx reg = convert_modes (mode, QImode, val, true); if (!TARGET_PARTIAL_REG_STALL) - if (mode == SImode) - emit_insn (gen_insvsi_1 (reg, reg)); - else - emit_insn (gen_insvdi_1 (reg, reg)); + emit_insn (gen_insv_1 (mode, reg, reg)); else { tmp = expand_simple_binop (mode, ASHIFT, reg, GEN_INT (8), diff --git a/gcc/config/i386/i386.md b/gcc/config/i386/i386.md index 4d455584f09..d0ecd9eb6cf 100644 --- a/gcc/config/i386/i386.md +++ b/gcc/config/i386/i386.md @@ -1355,13 +1355,13 @@ [(set_attr "type" "icmp") (set_attr "mode" "")]) -(define_insn "*cmpqi_ext_1" +(define_insn "*cmpqi_ext_1" [(set (reg FLAGS_REG) (compare (match_operand:QI 0 "nonimmediate_operand" "QBc,m") (subreg:QI - (zero_extract:SI - (match_operand 1 "ext_register_operand" "Q,Q") + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q,Q") (const_int 8) (const_int 8)) 0)))] "ix86_match_ccmode (insn, CCmode)" @@ -1370,12 +1370,12 @@ (set_attr "type" "icmp") (set_attr "mode" "QI")]) -(define_insn "*cmpqi_ext_2" +(define_insn "*cmpqi_ext_2" [(set (reg FLAGS_REG) (compare (subreg:QI - (zero_extract:SI - (match_operand 0 "ext_register_operand" "Q") + (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "Q") (const_int 8) (const_int 8)) 0) (match_operand:QI 1 "const0_operand")))] @@ -1389,18 +1389,18 @@ [(set (reg:CC FLAGS_REG) (compare:CC (subreg:QI - (zero_extract:SI - (match_operand 0 "ext_register_operand") + (zero_extract:HI + (match_operand:HI 0 "register_operand") (const_int 8) (const_int 8)) 0) (match_operand:QI 1 "const_int_operand")))]) -(define_insn "*cmpqi_ext_3" +(define_insn "*cmpqi_ext_3" [(set (reg FLAGS_REG) (compare (subreg:QI - (zero_extract:SI - (match_operand 0 "ext_register_operand" "Q,Q") + (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "Q,Q") (const_int 8) (const_int 8)) 0) (match_operand:QI 1 "general_operand" "QnBc,m")))] @@ -1410,17 +1410,17 @@ (set_attr "type" "icmp") (set_attr "mode" "QI")]) -(define_insn "*cmpqi_ext_4" +(define_insn "*cmpqi_ext_4" [(set (reg FLAGS_REG) (compare (subreg:QI - (zero_extract:SI - (match_operand 0 "ext_register_operand" "Q") + (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "Q") (const_int 8) (const_int 8)) 0) (subreg:QI - (zero_extract:SI - (match_operand 1 "ext_register_operand" "Q") + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q") (const_int 8) (const_int 8)) 0)))] "ix86_match_ccmode (insn, CCmode)" @@ -2775,7 +2775,7 @@ (define_insn "*extv" [(set (match_operand:SWI24 0 "register_operand" "=R") - (sign_extract:SWI24 (match_operand 1 "ext_register_operand" "Q") + (sign_extract:SWI24 (match_operand:SWI24 1 "register_operand" "Q") (const_int 8) (const_int 8)))] "" @@ -2807,9 +2807,10 @@ (define_insn "*extzvqi_mem_rex64" [(set (match_operand:QI 0 "norex_memory_operand" "=Bn") (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0))] + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0))] "TARGET_64BIT && reload_completed" "mov{b}\t{%h1, %0|%0, %h1}" [(set_attr "type" "imov") @@ -2817,7 +2818,7 @@ (define_insn "*extzv" [(set (match_operand:SWI248 0 "register_operand" "=R") - (zero_extract:SWI248 (match_operand 1 "ext_register_operand" "Q") + (zero_extract:SWI248 (match_operand:SWI248 1 "register_operand" "Q") (const_int 8) (const_int 8)))] "" @@ -2828,9 +2829,10 @@ (define_insn "*extzvqi" [(set (match_operand:QI 0 "nonimmediate_operand" "=QBc,?R,m") (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "Q,Q,Q") - (const_int 8) - (const_int 8)) 0))] + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q,Q,Q") + (const_int 8) + (const_int 8)) 0))] "" { switch (get_attr_type (insn)) @@ -2856,17 +2858,17 @@ (define_peephole2 [(set (match_operand:QI 0 "register_operand") (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand") - (const_int 8) - (const_int 8)) 0)) + (zero_extract:SWI248 (match_operand:SWI248 1 "register_operand") + (const_int 8) + (const_int 8)) 0)) (set (match_operand:QI 2 "norex_memory_operand") (match_dup 0))] "TARGET_64BIT && peep2_reg_dead_p (2, operands[0])" [(set (match_dup 2) (subreg:QI - (zero_extract:SI (match_dup 1) - (const_int 8) - (const_int 8)) 0))]) + (zero_extract:SWI248 (match_dup 1) + (const_int 8) + (const_int 8)) 0))]) (define_expand "insv" [(set (zero_extract:SWI248 (match_operand:SWI248 0 "register_operand") @@ -2892,7 +2894,7 @@ else dst = operands[0]; - emit_insn (gen_insv_1 (dst, operands[3])); + emit_insn (gen_insv_1 (mode, dst, operands[3])); /* Fix up the destination if needed. */ if (dst != operands[0]) @@ -2902,20 +2904,22 @@ }) (define_insn "*insvqi_1_mem_rex64" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (subreg:SI + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (match_operand:QI 1 "norex_memory_operand" "Bn") 0))] "TARGET_64BIT && reload_completed" "mov{b}\t{%1, %h0|%h0, %1}" [(set_attr "type" "imov") (set_attr "mode" "QI")]) -(define_insn "insv_1" - [(set (zero_extract:SWI248 (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) +(define_insn "@insv_1" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) (match_operand:SWI248 1 "general_operand" "QnBc,m"))] "" { @@ -2928,10 +2932,11 @@ (set_attr "mode" "QI")]) (define_insn "*insvqi_1" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (match_operand:QI 1 "general_operand" "QnBc,m") 0))] "" "mov{b}\t{%1, %h0|%h0, %1}" @@ -2942,37 +2947,41 @@ (define_peephole2 [(set (match_operand:QI 0 "register_operand") (match_operand:QI 1 "norex_memory_operand")) - (set (zero_extract:SI (match_operand 2 "ext_register_operand") - (const_int 8) - (const_int 8)) - (subreg:SI (match_dup 0) 0))] + (set (zero_extract:SWI248 (match_operand:SWI248 2 "register_operand") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (match_dup 0) 0))] "TARGET_64BIT && peep2_reg_dead_p (2, operands[0])" - [(set (zero_extract:SI (match_dup 2) - (const_int 8) - (const_int 8)) - (subreg:SI (match_dup 1) 0))]) + [(set (zero_extract:SWI248 (match_dup 2) + (const_int 8) + (const_int 8)) + (subreg:SWI248 (match_dup 1) 0))]) (define_code_iterator any_extract [sign_extract zero_extract]) (define_insn "*insvqi_2" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (any_extract:SI (match_operand 1 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)))] + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (any_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q") + (const_int 8) + (const_int 8)))] "" "mov{b}\t{%h1, %h0|%h0, %h1}" [(set_attr "type" "imov") (set_attr "mode" "QI")]) (define_insn "*insvqi_3" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (any_shiftrt:SI (match_operand:SI 1 "register_operand" "Q") - (const_int 8)))] + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (any_shiftrt:SWI248 + (match_operand:SWI248 1 "register_operand" "Q") + (const_int 8)))] "" "mov{b}\t{%h1, %h0|%h0, %h1}" [(set_attr "type" "imov") @@ -5835,16 +5844,32 @@ (const_string "*"))) (set_attr "mode" "")]) -(define_insn "addqi_ext_1" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_expand "addqi_ext_1" + [(parallel + [(set (zero_extract:HI (match_operand:HI 0 "register_operand") + (const_int 8) + (const_int 8)) + (subreg:HI + (plus:QI + (subreg:QI + (zero_extract:HI (match_operand:HI 1 "register_operand") + (const_int 8) + (const_int 8)) 0) + (match_operand:QI 2 "const_int_operand")) 0)) + (clobber (reg:CC FLAGS_REG))])]) + +(define_insn "*addqi_ext_1" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (plus:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "0,0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "0,0") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 2 "general_operand" "QnBc,m")) 0)) (clobber (reg:CC FLAGS_REG))] "/* FIXME: without this LRA can't reload this pattern, see PR82524. */ @@ -5872,20 +5897,23 @@ (const_string "alu"))) (set_attr "mode" "QI")]) -(define_insn "*addqi_ext_2" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_insn "*addqi_ext_2" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (plus:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "%0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "%0") + (const_int 8) + (const_int 8)) 0) (subreg:QI - (zero_extract:SI (match_operand 2 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0)) 0)) + (zero_extract:SWI248 + (match_operand:SWI248 2 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0)) 0)) (clobber (reg:CC FLAGS_REG))] "/* FIXME: without this LRA can't reload this pattern, see PR82524. */ rtx_equal_p (operands[0], operands[1]) @@ -8556,8 +8584,8 @@ emit_insn (gen_divmodhiqi3 (tmp0, tmp1, operands[2])); /* Extract remainder from AH. */ - tmp1 = gen_rtx_ZERO_EXTRACT (SImode, tmp0, GEN_INT (8), GEN_INT (8)); - tmp1 = lowpart_subreg (QImode, tmp1, SImode); + tmp1 = gen_rtx_ZERO_EXTRACT (HImode, tmp0, GEN_INT (8), GEN_INT (8)); + tmp1 = lowpart_subreg (QImode, tmp1, HImode); rtx_insn *insn = emit_move_insn (operands[3], tmp1); mod = gen_rtx_MOD (QImode, operands[1], operands[2]); @@ -8593,8 +8621,8 @@ emit_insn (gen_udivmodhiqi3 (tmp0, tmp1, operands[2])); /* Extract remainder from AH. */ - tmp1 = gen_rtx_ZERO_EXTRACT (SImode, tmp0, GEN_INT (8), GEN_INT (8)); - tmp1 = lowpart_subreg (QImode, tmp1, SImode); + tmp1 = gen_rtx_ZERO_EXTRACT (HImode, tmp0, GEN_INT (8), GEN_INT (8)); + tmp1 = lowpart_subreg (QImode, tmp1, HImode); rtx_insn *insn = emit_move_insn (operands[3], tmp1); mod = gen_rtx_UMOD (QImode, operands[1], operands[2]); @@ -8740,20 +8768,22 @@ (compare:CCNO (and:QI (subreg:QI - (zero_extract:SI (match_operand 0 "ext_register_operand") - (const_int 8) - (const_int 8)) 0) - (match_operand 1 "const_int_operand")) + (zero_extract:HI + (match_operand:HI 0 "register_operand") + (const_int 8) + (const_int 8)) 0) + (match_operand:QI 1 "const_int_operand")) (const_int 0)))]) -(define_insn "*testqi_ext_1" +(define_insn "*testqi_ext_1" [(set (reg FLAGS_REG) (compare (and:QI (subreg:QI - (zero_extract:SI (match_operand 0 "ext_register_operand" "Q,Q") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "Q,Q") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 1 "general_operand" "QnBc,m")) (const_int 0)))] "ix86_match_ccmode (insn, CCNOmode)" @@ -8762,18 +8792,20 @@ (set_attr "type" "test") (set_attr "mode" "QI")]) -(define_insn "*testqi_ext_2" +(define_insn "*testqi_ext_2" [(set (reg FLAGS_REG) (compare (and:QI (subreg:QI - (zero_extract:SI (match_operand 0 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0) (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0)) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0)) (const_int 0)))] "ix86_match_ccmode (insn, CCNOmode)" "test{b}\t{%h1, %h0|%h0, %h1}" @@ -9312,16 +9344,32 @@ [(set_attr "type" "alu") (set_attr "mode" "")]) -(define_insn "andqi_ext_1" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_expand "andqi_ext_1" + [(parallel + [(set (zero_extract:HI (match_operand:HI 0 "register_operand") + (const_int 8) + (const_int 8)) + (subreg:HI + (and:QI + (subreg:QI + (zero_extract:HI (match_operand:HI 1 "register_operand") + (const_int 8) + (const_int 8)) 0) + (match_operand:QI 2 "const_int_operand")) 0)) + (clobber (reg:CC FLAGS_REG))])]) + +(define_insn "*andqi_ext_1" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (and:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "0,0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "0,0") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 2 "general_operand" "QnBc,m")) 0)) (clobber (reg:CC FLAGS_REG))] "/* FIXME: without this LRA can't reload this pattern, see PR82524. */ @@ -9333,25 +9381,28 @@ ;; Generated by peephole translating test to and. This shows up ;; often in fp comparisons. -(define_insn "*andqi_ext_1_cc" +(define_insn "*andqi_ext_1_cc" [(set (reg FLAGS_REG) (compare (and:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "0,0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "0,0") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 2 "general_operand" "QnBc,m")) (const_int 0))) - (set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI + (set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (and:QI (subreg:QI - (zero_extract:SI (match_dup 1) - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_dup 1) + (const_int 8) + (const_int 8)) 0) (match_dup 2)) 0))] "ix86_match_ccmode (insn, CCNOmode) /* FIXME: without this LRA can't reload this pattern, see PR82524. */ @@ -9361,20 +9412,23 @@ (set_attr "type" "alu") (set_attr "mode" "QI")]) -(define_insn "*andqi_ext_2" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_insn "*andqi_ext_2" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (and:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "%0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "%0") + (const_int 8) + (const_int 8)) 0) (subreg:QI - (zero_extract:SI (match_operand 2 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0)) 0)) + (zero_extract:SWI248 + (match_operand:SWI248 2 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0)) 0)) (clobber (reg:CC FLAGS_REG))] "/* FIXME: without this LRA can't reload this pattern, see PR82524. */ rtx_equal_p (operands[0], operands[1]) @@ -9743,16 +9797,18 @@ [(set_attr "type" "alu") (set_attr "mode" "")]) -(define_insn "*qi_ext_1" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_insn "*qi_ext_1" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (any_or:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "0,0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "0,0") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 2 "general_operand" "QnBc,m")) 0)) (clobber (reg:CC FLAGS_REG))] "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)) @@ -9763,20 +9819,23 @@ (set_attr "type" "alu") (set_attr "mode" "QI")]) -(define_insn "*qi_ext_2" - [(set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q") - (const_int 8) - (const_int 8)) - (subreg:SI +(define_insn "*qi_ext_2" + [(set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (any_or:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "%0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "%0") + (const_int 8) + (const_int 8)) 0) (subreg:QI - (zero_extract:SI (match_operand 2 "ext_register_operand" "Q") - (const_int 8) - (const_int 8)) 0)) 0)) + (zero_extract:SWI248 + (match_operand:SWI248 2 "register_operand" "Q") + (const_int 8) + (const_int 8)) 0)) 0)) (clobber (reg:CC FLAGS_REG))] "(!TARGET_PARTIAL_REG_STALL || optimize_function_for_size_p (cfun)) /* FIXME: without this LRA can't reload this pattern, see PR82524. */ @@ -9839,46 +9898,49 @@ }) (define_expand "xorqi_ext_1_cc" - [(parallel [ - (set (reg:CCNO FLAGS_REG) - (compare:CCNO - (xor:QI - (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand") - (const_int 8) - (const_int 8)) 0) - (match_operand 2 "const_int_operand")) - (const_int 0))) - (set (zero_extract:SI (match_operand 0 "ext_register_operand") - (const_int 8) - (const_int 8)) - (subreg:SI - (xor:QI - (subreg:QI - (zero_extract:SI (match_dup 1) - (const_int 8) - (const_int 8)) 0) - (match_dup 2)) 0))])]) - -(define_insn "*xorqi_ext_1_cc" + [(parallel + [(set (reg:CCNO FLAGS_REG) + (compare:CCNO + (xor:QI + (subreg:QI + (zero_extract:HI (match_operand:HI 1 "register_operand") + (const_int 8) + (const_int 8)) 0) + (match_operand:QI 2 "const_int_operand")) + (const_int 0))) + (set (zero_extract:HI (match_operand:HI 0 "register_operand") + (const_int 8) + (const_int 8)) + (subreg:HI + (xor:QI + (subreg:QI + (zero_extract:HI (match_dup 1) + (const_int 8) + (const_int 8)) 0) + (match_dup 2)) 0))])]) + +(define_insn "*xorqi_ext_1_cc" [(set (reg FLAGS_REG) (compare (xor:QI (subreg:QI - (zero_extract:SI (match_operand 1 "ext_register_operand" "0,0") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_operand:SWI248 1 "register_operand" "0,0") + (const_int 8) + (const_int 8)) 0) (match_operand:QI 2 "general_operand" "QnBc,m")) (const_int 0))) - (set (zero_extract:SI (match_operand 0 "ext_register_operand" "+Q,Q") - (const_int 8) - (const_int 8)) - (subreg:SI + (set (zero_extract:SWI248 + (match_operand:SWI248 0 "register_operand" "+Q,Q") + (const_int 8) + (const_int 8)) + (subreg:SWI248 (xor:QI (subreg:QI - (zero_extract:SI (match_dup 1) - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 + (match_dup 1) + (const_int 8) + (const_int 8)) 0) (match_dup 2)) 0))] "ix86_match_ccmode (insn, CCNOmode) /* FIXME: without this LRA can't reload this pattern, see PR82524. */ @@ -19409,9 +19471,9 @@ (match_operator 1 "compare_operator" [(and:QI (subreg:QI - (zero_extract:SI (match_operand 2 "QIreg_operand") - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 (match_operand:SWI248 2 "QIreg_operand") + (const_int 8) + (const_int 8)) 0) (match_operand 3 "const_int_operand")) (const_int 0)]))] "! TARGET_PARTIAL_REG_STALL @@ -19423,20 +19485,20 @@ (match_op_dup 1 [(and:QI (subreg:QI - (zero_extract:SI (match_dup 2) - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 (match_dup 2) + (const_int 8) + (const_int 8)) 0) (match_dup 3)) (const_int 0)])) - (set (zero_extract:SI (match_dup 2) - (const_int 8) - (const_int 8)) - (subreg:SI + (set (zero_extract:SWI248 (match_dup 2) + (const_int 8) + (const_int 8)) + (subreg:SWI248 (and:QI (subreg:QI - (zero_extract:SI (match_dup 2) - (const_int 8) - (const_int 8)) 0) + (zero_extract:SWI248 (match_dup 2) + (const_int 8) + (const_int 8)) 0) (match_dup 3)) 0))])]) ;; Don't do logical operations with memory inputs. diff --git a/gcc/config/i386/predicates.md b/gcc/config/i386/predicates.md index 8d8bcb1a765..07e69d555c0 100644 --- a/gcc/config/i386/predicates.md +++ b/gcc/config/i386/predicates.md @@ -87,14 +87,6 @@ (and (match_code "reg") (match_test "REGNO (op) == FLAGS_REG"))) -;; Match a DI, SI or HImode register for a zero_extract. -(define_special_predicate "ext_register_operand" - (and (match_operand 0 "register_operand") - (ior (and (match_test "TARGET_64BIT") - (match_test "GET_MODE (op) == DImode")) - (match_test "GET_MODE (op) == SImode") - (match_test "GET_MODE (op) == HImode")))) - ;; Match a DI, SI, HI or QImode nonimmediate_operand. (define_special_predicate "int_nonimmediate_operand" (and (match_operand 0 "nonimmediate_operand") diff --git a/gcc/testsuite/gcc.target/i386/pr78904-1a.c b/gcc/testsuite/gcc.target/i386/pr78904-1a.c new file mode 100644 index 00000000000..7746477d745 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-1a.c @@ -0,0 +1,47 @@ +/* PR target/78904 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ +/* { dg-final { scan-assembler-not "movb" } } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +struct S1 test_and (struct S1 a, struct S1 b) +{ + a.val &= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]andb" } } */ + +struct S1 test_or (struct S1 a, struct S1 b) +{ + a.val |= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]orb" } } */ + +struct S1 test_xor (struct S1 a, struct S1 b) +{ + a.val ^= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]xorb" } } */ + +struct S1 test_add (struct S1 a, struct S1 b) +{ + a.val += b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]addb" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-1b.c b/gcc/testsuite/gcc.target/i386/pr78904-1b.c new file mode 100644 index 00000000000..20b677252ab --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-1b.c @@ -0,0 +1,49 @@ +/* PR target/78904 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ +/* { dg-final { scan-assembler-not "movb" } } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +struct S1 test_and (struct S1 a, struct S1 b) +{ + a.val &= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]andb" } } */ + +struct S1 test_or (struct S1 a, struct S1 b) +{ + a.val |= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]orb" } } */ + +struct S1 test_xor (struct S1 a, struct S1 b) +{ + a.val ^= b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]xorb" } } */ + +struct S1 test_add (struct S1 a, struct S1 b) +{ + a.val += b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]addb" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-2a.c b/gcc/testsuite/gcc.target/i386/pr78904-2a.c new file mode 100644 index 00000000000..41eaa259158 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-2a.c @@ -0,0 +1,48 @@ +/* PR target/78904 */ +/* { dg-do compile } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +extern struct S1 t; + +struct S1 test_and (struct S1 a) +{ + a.val &= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]andb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_or (struct S1 a) +{ + a.val |= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]orb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_xor (struct S1 a) +{ + a.val ^= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]xorb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_add (struct S1 a) +{ + a.val += t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]addb\[ \t\]+t\[^\n\r]*, %.h" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-2b.c b/gcc/testsuite/gcc.target/i386/pr78904-2b.c new file mode 100644 index 00000000000..23e975ac93e --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-2b.c @@ -0,0 +1,50 @@ +/* PR target/78904 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +extern struct S1 t; + +struct S1 test_and (struct S1 a) +{ + a.val &= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]andb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_or (struct S1 a) +{ + a.val |= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]orb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_xor (struct S1 a) +{ + a.val ^= t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]xorb\[ \t\]+t\[^\n\r]*, %.h" } } */ + +struct S1 test_add (struct S1 a) +{ + a.val += t.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]addb\[ \t\]+t\[^\n\r]*, %.h" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-3a.c b/gcc/testsuite/gcc.target/i386/pr78904-3a.c new file mode 100644 index 00000000000..2827b380b6c --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-3a.c @@ -0,0 +1,42 @@ +/* PR target/78904 */ +/* { dg-do assemble } */ +/* { dg-options "-O2" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; +}; + +extern struct S1 t[256]; + +struct S1 test_and (struct S1 a, size_t i) +{ + a.val &= t[i].val; + + return a; +} + +struct S1 test_or (struct S1 a, size_t i) +{ + a.val |= t[i].val; + + return a; +} + +struct S1 test_xor (struct S1 a, size_t i) +{ + a.val ^= t[i].val; + + return a; +} + +struct S1 test_add (struct S1 a, size_t i) +{ + a.val += t[i].val; + + return a; +} diff --git a/gcc/testsuite/gcc.target/i386/pr78904-3b.c b/gcc/testsuite/gcc.target/i386/pr78904-3b.c new file mode 100644 index 00000000000..0c73cbc2ec9 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-3b.c @@ -0,0 +1,43 @@ +/* PR target/78904 */ +/* { dg-do assemble { target { ! ia32 } } } */ +/* { dg-options "-O2" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +extern struct S1 t[256]; + +struct S1 test_and (struct S1 a, size_t i) +{ + a.val &= t[i].val; + + return a; +} + +struct S1 test_or (struct S1 a, size_t i) +{ + a.val |= t[i].val; + + return a; +} + +struct S1 test_xor (struct S1 a, size_t i) +{ + a.val ^= t[i].val; + + return a; +} + +struct S1 test_add (struct S1 a, size_t i) +{ + a.val += t[i].val; + + return a; +} diff --git a/gcc/testsuite/gcc.target/i386/pr78904-4a.c b/gcc/testsuite/gcc.target/i386/pr78904-4a.c new file mode 100644 index 00000000000..5e6159a7648 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-4a.c @@ -0,0 +1,21 @@ +/* PR target/78904 */ +/* { dg-do compile } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +extern unsigned char t[256]; + +void foo (struct S1 a, size_t i) +{ + t[i] = a.val; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[\t \]+%.h, t" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-4b.c b/gcc/testsuite/gcc.target/i386/pr78904-4b.c new file mode 100644 index 00000000000..ab7434f3de4 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-4b.c @@ -0,0 +1,23 @@ +/* PR target/78904 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +extern unsigned char t[256]; + +void foo (struct S1 a, size_t i) +{ + t[i] = a.val; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[\t \]+%.h, t" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-5a.c b/gcc/testsuite/gcc.target/i386/pr78904-5a.c new file mode 100644 index 00000000000..d078d79b73a --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-5a.c @@ -0,0 +1,21 @@ +/* PR target/78904 */ +/* { dg-do assemble { target { ! ia32 } } } */ +/* { dg-options "-O2" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +extern unsigned char t[256]; + +void foo (struct S1 a, size_t i) +{ + register size_t _i __asm ("r10") = i; + + asm volatile ("" : "+r" (_i)); + t[_i] = a.val; +} diff --git a/gcc/testsuite/gcc.target/i386/pr78904-5b.c b/gcc/testsuite/gcc.target/i386/pr78904-5b.c new file mode 100644 index 00000000000..9490030d772 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-5b.c @@ -0,0 +1,23 @@ +/* PR target/78904 */ +/* { dg-do assemble { target { ! ia32 } } } */ +/* { dg-options "-O2" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +extern unsigned char t[256]; + +void foo (struct S1 a, size_t i) +{ + register size_t _i __asm ("r10") = i; + + asm volatile ("" : "+r" (_i)); + t[_i] = a.val; +} diff --git a/gcc/testsuite/gcc.target/i386/pr78904-6a.c b/gcc/testsuite/gcc.target/i386/pr78904-6a.c new file mode 100644 index 00000000000..ab296a2e173 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-6a.c @@ -0,0 +1,21 @@ +/* PR target/78904 */ +/* { dg-do compile } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + char pad1; + char val; +}; + +extern char t[256]; + +void foo (struct S1 a, size_t i) +{ + t[i] = a.val; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[\t \]*%.h, t" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78904-6b.c b/gcc/testsuite/gcc.target/i386/pr78904-6b.c new file mode 100644 index 00000000000..235bfe7d042 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78904-6b.c @@ -0,0 +1,23 @@ +/* PR target/78904 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-options "-O2 -masm=att" } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + char pad1; + char val; + short pad2; + int pad3; +}; + +extern char t[256]; + +void foo (struct S1 a, size_t i) +{ + t[i] = a.val; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[\t \]*%.h, t" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78967-1a.c b/gcc/testsuite/gcc.target/i386/pr78967-1a.c new file mode 100644 index 00000000000..007c50646b6 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78967-1a.c @@ -0,0 +1,20 @@ +/* PR target/78967 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-additional-options "-mregparm=3" { target ia32 } } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +struct S1 foo (struct S1 a, struct S1 b) +{ + a.val = b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[ \t\]+%.h, %.h" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78967-1b.c b/gcc/testsuite/gcc.target/i386/pr78967-1b.c new file mode 100644 index 00000000000..7e7144379f3 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78967-1b.c @@ -0,0 +1,21 @@ +/* PR target/78967 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +struct S1 foo (struct S1 a, struct S1 b) +{ + a.val = b.val; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[ \t\]+%.h, %.h" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78967-2a.c b/gcc/testsuite/gcc.target/i386/pr78967-2a.c new file mode 100644 index 00000000000..ce61cabf414 --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78967-2a.c @@ -0,0 +1,24 @@ +/* PR target/78967 */ +/* { dg-do compile } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; +}; + +extern unsigned char t[256]; + +struct S1 foo (struct S1 a, size_t i) +{ + a.val = t[i]; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[ \t\]+t\[^\n\r]*, %.h" } } */ diff --git a/gcc/testsuite/gcc.target/i386/pr78967-2b.c b/gcc/testsuite/gcc.target/i386/pr78967-2b.c new file mode 100644 index 00000000000..ce38ac4d0bf --- /dev/null +++ b/gcc/testsuite/gcc.target/i386/pr78967-2b.c @@ -0,0 +1,26 @@ +/* PR target/78967 */ +/* { dg-do compile { target { ! ia32 } } } */ +/* { dg-options "-O2 -masm=att" } */ +/* { dg-require-effective-target nonpic } */ +/* { dg-final { scan-assembler-not "movzbl" } } */ + +typedef __SIZE_TYPE__ size_t; + +struct S1 +{ + unsigned char pad1; + unsigned char val; + unsigned short pad2; + unsigned int pad3; +}; + +extern unsigned char t[256]; + +struct S1 foo (struct S1 a, size_t i) +{ + a.val = t[i]; + + return a; +} + +/* { dg-final { scan-assembler "\[ \t\]movb\[ \t\]+t\[^\n\r]*, %.h" } } */ -- 2.30.2