re PR rtl-optimization/87817 (gcc.target/i386/bmi2-bzhi-2.c execution test)
authorJakub Jelinek <jakub@redhat.com>
Wed, 21 Nov 2018 10:45:58 +0000 (11:45 +0100)
committerJakub Jelinek <jakub@gcc.gnu.org>
Wed, 21 Nov 2018 10:45:58 +0000 (11:45 +0100)
PR rtl-optimization/87817
* config/i386/i386.md (bmi2_bzhi_<mode>3, *bmi2_bzhi_<mode>3,
*bmi2_bzhi_<mode>3_1, *bmi2_bzhi_<mode>3_1_ccz): Use IF_THEN_ELSE
in the pattern to avoid triggering UB when operands[2] is zero.
(tbm_bextri_<mode>): New expander.  Renamed the old define_insn to ...
(*tbm_bextri_<mode>): ... this.

From-SVN: r266340

gcc/ChangeLog
gcc/config/i386/i386.md

index bff4dfb..005ce0f 100644 (file)
@@ -1,3 +1,12 @@
+2018-11-21  Jakub Jelinek  <jakub@redhat.com>
+
+       PR rtl-optimization/87817
+       * config/i386/i386.md (bmi2_bzhi_<mode>3, *bmi2_bzhi_<mode>3,
+       *bmi2_bzhi_<mode>3_1, *bmi2_bzhi_<mode>3_1_ccz): Use IF_THEN_ELSE
+       in the pattern to avoid triggering UB when operands[2] is zero.
+       (tbm_bextri_<mode>): New expander.  Renamed the old define_insn to ...
+       (*tbm_bextri_<mode>): ... this.
+
 2018-11-21  Tom de Vries  <tdevries@suse.de>
 
        PR driver/79855
index 1a3a179..2231204 100644 (file)
 (define_expand "bmi2_bzhi_<mode>3"
   [(parallel
     [(set (match_operand:SWI48 0 "register_operand")
-         (zero_extract:SWI48
-           (match_operand:SWI48 1 "nonimmediate_operand")
-           (umin:SWI48
-             (and:SWI48 (match_operand:SWI48 2 "register_operand")
-                        (const_int 255))
-             (match_dup 3))
+         (if_then_else:SWI48
+           (ne:QI (and:SWI48 (match_operand:SWI48 2 "register_operand")
+                             (const_int 255))
+                  (const_int 0))
+           (zero_extract:SWI48
+             (match_operand:SWI48 1 "nonimmediate_operand")
+             (umin:SWI48 (and:SWI48 (match_dup 2) (const_int 255))
+                         (match_dup 3))
+             (const_int 0))
            (const_int 0)))
      (clobber (reg:CC FLAGS_REG))])]
   "TARGET_BMI2"
 
 (define_insn "*bmi2_bzhi_<mode>3"
   [(set (match_operand:SWI48 0 "register_operand" "=r")
-       (zero_extract:SWI48
-         (match_operand:SWI48 1 "nonimmediate_operand" "rm")
-         (umin:SWI48
-           (and:SWI48 (match_operand:SWI48 2 "register_operand" "r")
-                      (const_int 255))
-           (match_operand:SWI48 3 "const_int_operand" "n"))
+       (if_then_else:SWI48
+         (ne:QI (and:SWI48 (match_operand:SWI48 2 "register_operand" "r")
+                           (const_int 255))
+                (const_int 0))
+         (zero_extract:SWI48
+           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
+           (umin:SWI48 (and:SWI48 (match_dup 2) (const_int 255))
+                       (match_operand:SWI48 3 "const_int_operand" "n"))
+           (const_int 0))
          (const_int 0)))
    (clobber (reg:CC FLAGS_REG))]
   "TARGET_BMI2 && INTVAL (operands[3]) == <MODE_SIZE> * BITS_PER_UNIT"
 
 (define_insn "*bmi2_bzhi_<mode>3_1"
   [(set (match_operand:SWI48 0 "register_operand" "=r")
-       (zero_extract:SWI48
-         (match_operand:SWI48 1 "nonimmediate_operand" "rm")
-         (umin:SWI48
-           (zero_extend:SWI48 (match_operand:QI 2 "register_operand" "r"))
-           (match_operand:SWI48 3 "const_int_operand" "n"))
+       (if_then_else:SWI48
+         (ne:QI (match_operand:QI 2 "register_operand" "r") (const_int 0))
+         (zero_extract:SWI48
+           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
+           (umin:SWI48 (zero_extend:SWI48 (match_dup 2))
+                       (match_operand:SWI48 3 "const_int_operand" "n"))
+           (const_int 0))
          (const_int 0)))
    (clobber (reg:CC FLAGS_REG))]
   "TARGET_BMI2 && INTVAL (operands[3]) == <MODE_SIZE> * BITS_PER_UNIT"
 (define_insn "*bmi2_bzhi_<mode>3_1_ccz"
   [(set (reg:CCZ FLAGS_REG)
        (compare:CCZ
-         (zero_extract:SWI48
-           (match_operand:SWI48 1 "nonimmediate_operand" "rm")
-           (umin:SWI48
-             (zero_extend:SWI48 (match_operand:QI 2 "register_operand" "r"))
-             (match_operand:SWI48 3 "const_int_operand" "n"))
+         (if_then_else:SWI48
+           (ne:QI (match_operand:QI 2 "register_operand" "r") (const_int 0))
+           (zero_extract:SWI48
+             (match_operand:SWI48 1 "nonimmediate_operand" "rm")
+             (umin:SWI48 (zero_extend:SWI48 (match_dup 2))
+                         (match_operand:SWI48 3 "const_int_operand" "n"))
+             (const_int 0))
            (const_int 0))
        (const_int 0)))
    (clobber (match_scratch:SWI48 0 "=r"))]
    (set_attr "mode" "<MODE>")])
 
 ;; TBM instructions.
-(define_insn "tbm_bextri_<mode>"
+(define_expand "tbm_bextri_<mode>"
+  [(parallel
+    [(set (match_operand:SWI48 0 "register_operand")
+         (zero_extract:SWI48
+           (match_operand:SWI48 1 "nonimmediate_operand")
+           (match_operand 2 "const_0_to_255_operand" "N")
+           (match_operand 3 "const_0_to_255_operand" "N")))
+     (clobber (reg:CC FLAGS_REG))])]
+  "TARGET_TBM"
+{
+  if (operands[2] == const0_rtx
+      || INTVAL (operands[3]) >= <MODE_SIZE> * BITS_PER_UNIT)
+    {
+      emit_move_insn (operands[0], const0_rtx);
+      DONE;
+    }
+  if (INTVAL (operands[2]) + INTVAL (operands[3])
+      > <MODE_SIZE> * BITS_PER_UNIT)
+    operands[2] = GEN_INT (<MODE_SIZE> * BITS_PER_UNIT - INTVAL (operands[3]));
+})
+
+(define_insn "*tbm_bextri_<mode>"
   [(set (match_operand:SWI48 0 "register_operand" "=r")
         (zero_extract:SWI48
           (match_operand:SWI48 1 "nonimmediate_operand" "rm")