@@ -3312,8 +3312,8 @@
(define_expand "extv<mode>"
[(set (match_operand:SWI24 0 "register_operand")
(sign_extract:SWI24 (match_operand:SWI24 1 "register_operand")
- (match_operand:SI 2 "const_int_operand")
- (match_operand:SI 3 "const_int_operand")))]
+ (match_operand:QI 2 "const_int_operand")
+ (match_operand:QI 3 "const_int_operand")))]
""
{
/* Handle extractions from %ah et al. */
@@ -3340,8 +3340,8 @@
(define_expand "extzv<mode>"
[(set (match_operand:SWI248 0 "register_operand")
(zero_extract:SWI248 (match_operand:SWI248 1 "register_operand")
- (match_operand:SI 2 "const_int_operand")
- (match_operand:SI 3 "const_int_operand")))]
+ (match_operand:QI 2 "const_int_operand")
+ (match_operand:QI 3 "const_int_operand")))]
""
{
if (ix86_expand_pextr (operands))
@@ -3428,8 +3428,8 @@
(define_expand "insv<mode>"
[(set (zero_extract:SWI248 (match_operand:SWI248 0 "register_operand")
- (match_operand:SI 1 "const_int_operand")
- (match_operand:SI 2 "const_int_operand"))
+ (match_operand:QI 1 "const_int_operand")
+ (match_operand:QI 2 "const_int_operand"))
(match_operand:SWI248 3 "register_operand"))]
""
{
@@ -10788,8 +10788,8 @@
(match_operator 1 "compare_operator"
[(zero_extract:SWI248
(match_operand 2 "int_nonimmediate_operand" "rm")
- (match_operand 3 "const_int_operand")
- (match_operand 4 "const_int_operand"))
+ (match_operand:QI 3 "const_int_operand")
+ (match_operand:QI 4 "const_int_operand"))
(const_int 0)]))]
"/* Ensure that resulting mask is zero or sign extended operand. */
INTVAL (operands[4]) >= 0
@@ -15965,7 +15965,7 @@
[(set (zero_extract:HI
(match_operand:SWI12 0 "nonimmediate_operand")
(const_int 1)
- (zero_extend:SI (match_operand:QI 1 "register_operand")))
+ (match_operand:QI 1 "register_operand"))
(const_int 0))
(clobber (reg:CC FLAGS_REG))]
"TARGET_USE_BT && ix86_pre_reload_split ()"
@@ -15989,7 +15989,7 @@
[(set (zero_extract:HI
(match_operand:SWI12 0 "register_operand")
(const_int 1)
- (zero_extend:SI (match_operand:QI 1 "register_operand")))
+ (match_operand:QI 1 "register_operand"))
(const_int 0))
(clobber (reg:CC FLAGS_REG))]
"TARGET_USE_BT && ix86_pre_reload_split ()"
@@ -16016,7 +16016,7 @@
(define_insn "*btsq_imm"
[(set (zero_extract:DI (match_operand:DI 0 "nonimmediate_operand" "+rm")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(const_int 1))
(clobber (reg:CC FLAGS_REG))]
"TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
@@ -16029,7 +16029,7 @@
(define_insn "*btrq_imm"
[(set (zero_extract:DI (match_operand:DI 0 "nonimmediate_operand" "+rm")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(const_int 0))
(clobber (reg:CC FLAGS_REG))]
"TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
@@ -16042,7 +16042,7 @@
(define_insn "*btcq_imm"
[(set (zero_extract:DI (match_operand:DI 0 "nonimmediate_operand" "+rm")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(not:DI (zero_extract:DI (match_dup 0) (const_int 1) (match_dup 1))))
(clobber (reg:CC FLAGS_REG))]
"TARGET_64BIT && (TARGET_USE_BT || reload_completed)"
@@ -16059,7 +16059,7 @@
(parallel [(set (zero_extract:DI
(match_operand:DI 0 "nonimmediate_operand")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(const_int 1))
(clobber (reg:CC FLAGS_REG))])]
"TARGET_64BIT && !TARGET_USE_BT"
@@ -16083,7 +16083,7 @@
(parallel [(set (zero_extract:DI
(match_operand:DI 0 "nonimmediate_operand")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(const_int 0))
(clobber (reg:CC FLAGS_REG))])]
"TARGET_64BIT && !TARGET_USE_BT"
@@ -16107,7 +16107,7 @@
(parallel [(set (zero_extract:DI
(match_operand:DI 0 "nonimmediate_operand")
(const_int 1)
- (match_operand 1 "const_0_to_63_operand"))
+ (match_operand:QI 1 "const_0_to_63_operand"))
(not:DI (zero_extract:DI
(match_dup 0) (const_int 1) (match_dup 1))))
(clobber (reg:CC FLAGS_REG))])]
@@ -16135,14 +16135,14 @@
(zero_extract:SWI48
(match_operand:SWI48 0 "nonimmediate_operand" "r,m")
(const_int 1)
- (match_operand:SI 1 "nonmemory_operand" "r<S>,<S>"))
+ (match_operand:QI 1 "nonmemory_operand" "q<S>,<S>"))
(const_int 0)))]
""
{
switch (get_attr_mode (insn))
{
case MODE_SI:
- return "bt{l}\t{%1, %k0|%k0, %1}";
+ return "bt{l}\t{%k1, %k0|%k0, %k1}";
case MODE_DI:
return "bt{q}\t{%q1, %0|%0, %q1}";
@@ -16160,13 +16160,36 @@
(const_string "SI")
(const_string "<MODE>")))])
+(define_insn_and_split "*bt<SWI48:mode>_mask"
+ [(set (reg:CCC FLAGS_REG)
+ (compare:CCC
+ (zero_extract:SWI48
+ (match_operand:SWI48 0 "nonimmediate_operand" "r,m")
+ (const_int 1)
+ (subreg:QI
+ (and:SWI248
+ (match_operand:SWI248 1 "register_operand")
+ (match_operand 2 "const_int_operand")) 0))
+ (const_int 0)))]
+ "TARGET_USE_BT
+ && (INTVAL (operands[2]) & (GET_MODE_BITSIZE (<SWI48:MODE>mode)-1))
+ == GET_MODE_BITSIZE (<SWI48:MODE>mode)-1
+ && ix86_pre_reload_split ()"
+ "#"
+ "&& 1"
+ [(set (reg:CCC FLAGS_REG)
+ (compare:CCC
+ (zero_extract:SWI48 (match_dup 0) (const_int 1) (match_dup 1))
+ (const_int 0)))]
+ "operands[1] = gen_lowpart (QImode, operands[1]);")
+
(define_insn_and_split "*jcc_bt<mode>"
[(set (pc)
(if_then_else (match_operator 0 "bt_comparison_operator"
[(zero_extract:SWI48
(match_operand:SWI48 1 "nonimmediate_operand")
(const_int 1)
- (match_operand:SI 2 "nonmemory_operand"))
+ (match_operand:QI 2 "nonmemory_operand"))
(const_int 0)])
(label_ref (match_operand 3))
(pc)))
@@ -16196,39 +16219,6 @@
PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
})
-(define_insn_and_split "*jcc_bt<mode>_1"
- [(set (pc)
- (if_then_else (match_operator 0 "bt_comparison_operator"
- [(zero_extract:SWI48
- (match_operand:SWI48 1 "register_operand")
- (const_int 1)
- (zero_extend:SI
- (match_operand:QI 2 "register_operand")))
- (const_int 0)])
- (label_ref (match_operand 3))
- (pc)))
- (clobber (reg:CC FLAGS_REG))]
- "(TARGET_USE_BT || optimize_function_for_size_p (cfun))
- && ix86_pre_reload_split ()"
- "#"
- "&& 1"
- [(set (reg:CCC FLAGS_REG)
- (compare:CCC
- (zero_extract:SWI48
- (match_dup 1)
- (const_int 1)
- (match_dup 2))
- (const_int 0)))
- (set (pc)
- (if_then_else (match_op_dup 0 [(reg:CCC FLAGS_REG) (const_int 0)])
- (label_ref (match_dup 3))
- (pc)))]
-{
- operands[2] = lowpart_subreg (SImode, operands[2], QImode);
- operands[0] = shallow_copy_rtx (operands[0]);
- PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
-})
-
;; Avoid useless masking of bit offset operand.
(define_insn_and_split "*jcc_bt<mode>_mask"
[(set (pc)
@@ -16236,8 +16226,8 @@
[(zero_extract:SWI48
(match_operand:SWI48 1 "register_operand")
(const_int 1)
- (and:SI
- (match_operand:SI 2 "register_operand")
+ (and:QI
+ (match_operand:QI 2 "register_operand")
(match_operand 3 "const_int_operand")))])
(label_ref (match_operand 4))
(pc)))
@@ -16264,23 +16254,23 @@
PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
})
-(define_insn_and_split "*jcc_bt<mode>_mask_1"
+;; Avoid useless masking of bit offset operand.
+(define_insn_and_split "*jcc_bt<SWI48:mode>_mask_1"
[(set (pc)
- (if_then_else (match_operator 0 "bt_comparison_operator"
+ (if_then_else (match_operator 0 "bt_comparison_operator"
[(zero_extract:SWI48
(match_operand:SWI48 1 "register_operand")
(const_int 1)
- (zero_extend:SI
- (subreg:QI
- (and
- (match_operand 2 "int248_register_operand")
- (match_operand 3 "const_int_operand")) 0)))])
+ (subreg:QI
+ (and:SWI248
+ (match_operand:SWI248 2 "register_operand")
+ (match_operand 3 "const_int_operand")) 0))])
(label_ref (match_operand 4))
(pc)))
(clobber (reg:CC FLAGS_REG))]
"(TARGET_USE_BT || optimize_function_for_size_p (cfun))
- && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
- == GET_MODE_BITSIZE (<MODE>mode)-1
+ && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<SWI48:MODE>mode)-1))
+ == GET_MODE_BITSIZE (<SWI48:MODE>mode)-1
&& ix86_pre_reload_split ()"
"#"
"&& 1"
@@ -16296,10 +16286,9 @@
(label_ref (match_dup 4))
(pc)))]
{
- operands[2] = force_reg (GET_MODE (operands[2]), operands[2]);
- operands[2] = gen_lowpart (SImode, operands[2]);
operands[0] = shallow_copy_rtx (operands[0]);
PUT_CODE (operands[0], reverse_condition (GET_CODE (operands[0])));
+ operands[2] = gen_lowpart (QImode, operands[2]);
})
;; Help combine recognize bt followed by cmov
@@ -16310,7 +16299,7 @@
[(zero_extract:SWI48
(match_operand:SWI48 1 "register_operand")
(const_int 1)
- (zero_extend:SI (match_operand:QI 2 "register_operand")))
+ (match_operand:QI 2 "register_operand"))
(const_int 0)])
(match_operand:SWI248 3 "nonimmediate_operand")
(match_operand:SWI248 4 "nonimmediate_operand")))]
@@ -16328,7 +16317,6 @@
{
if (GET_CODE (operands[5]) == EQ)
std::swap (operands[3], operands[4]);
- operands[2] = lowpart_subreg (SImode, operands[2], QImode);
})
;; Help combine recognize bt followed by setc
@@ -16337,7 +16325,7 @@
(zero_extract:SWI48
(match_operand:SWI48 1 "register_operand")
(const_int 1)
- (zero_extend:SI (match_operand:QI 2 "register_operand"))))
+ (match_operand:QI 2 "register_operand")))
(clobber (reg:CC FLAGS_REG))]
"TARGET_USE_BT && ix86_pre_reload_split ()"
"#"
@@ -16347,8 +16335,7 @@
(zero_extract:SWI48 (match_dup 1) (const_int 1) (match_dup 2))
(const_int 0)))
(set (match_dup 0)
- (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))]
- "operands[2] = lowpart_subreg (SImode, operands[2], QImode);")
+ (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))])
;; Help combine recognize bt followed by setnc
(define_insn_and_split "*bt<mode>_setncqi"
@@ -16368,8 +16355,7 @@
(zero_extract:SWI48 (match_dup 1) (const_int 1) (match_dup 2))
(const_int 0)))
(set (match_dup 0)
- (ne:QI (reg:CCC FLAGS_REG) (const_int 0)))]
- "operands[2] = lowpart_subreg (SImode, operands[2], QImode);")
+ (ne:QI (reg:CCC FLAGS_REG) (const_int 0)))])
(define_insn_and_split "*bt<mode>_setnc<mode>"
[(set (match_operand:SWI48 0 "register_operand")
@@ -16389,10 +16375,7 @@
(set (match_dup 3)
(ne:QI (reg:CCC FLAGS_REG) (const_int 0)))
(set (match_dup 0) (zero_extend:SWI48 (match_dup 3)))]
-{
- operands[2] = lowpart_subreg (SImode, operands[2], QImode);
- operands[3] = gen_reg_rtx (QImode);
-})
+ "operands[3] = gen_reg_rtx (QImode);")
;; Help combine recognize bt followed by setnc (PR target/110588)
(define_insn_and_split "*bt<mode>_setncqi_2"
@@ -16401,7 +16384,7 @@
(zero_extract:SWI48
(match_operand:SWI48 1 "register_operand")
(const_int 1)
- (zero_extend:SI (match_operand:QI 2 "register_operand")))
+ (match_operand:QI 2 "register_operand"))
(const_int 0)))
(clobber (reg:CC FLAGS_REG))]
"TARGET_USE_BT && ix86_pre_reload_split ()"
@@ -16412,8 +16395,36 @@
(zero_extract:SWI48 (match_dup 1) (const_int 1) (match_dup 2))
(const_int 0)))
(set (match_dup 0)
- (ne:QI (reg:CCC FLAGS_REG) (const_int 0)))]
- "operands[2] = lowpart_subreg (SImode, operands[2], QImode);")
+ (ne:QI (reg:CCC FLAGS_REG) (const_int 0)))])
+
+;; Help combine recognize bt followed by setc
+(define_insn_and_split "*bt<mode>_setc<mode>_mask"
+ [(set (match_operand:SWI48 0 "register_operand")
+ (zero_extract:SWI48
+ (match_operand:SWI48 1 "register_operand")
+ (const_int 1)
+ (subreg:QI
+ (and:SWI48
+ (match_operand:SWI48 2 "register_operand")
+ (match_operand 3 "const_int_operand")) 0)))
+ (clobber (reg:CC FLAGS_REG))]
+ "TARGET_USE_BT
+ && (INTVAL (operands[3]) & (GET_MODE_BITSIZE (<MODE>mode)-1))
+ == GET_MODE_BITSIZE (<MODE>mode)-1
+ && ix86_pre_reload_split ()"
+ "#"
+ "&& 1"
+ [(set (reg:CCC FLAGS_REG)
+ (compare:CCC
+ (zero_extract:SWI48 (match_dup 1) (const_int 1) (match_dup 2))
+ (const_int 0)))
+ (set (match_dup 3)
+ (eq:QI (reg:CCC FLAGS_REG) (const_int 0)))
+ (set (match_dup 0) (zero_extend:SWI48 (match_dup 3)))]
+{
+ operands[2] = gen_lowpart (QImode, operands[2]);
+ operands[3] = gen_reg_rtx (QImode);
+})
;; Store-flag instructions.
@@ -18708,46 +18719,29 @@
[(parallel
[(set (match_operand:SWI48 0 "register_operand")
(if_then_else:SWI48
- (ne:QI (and:SWI48 (match_operand:SWI48 2 "register_operand")
- (const_int 255))
+ (ne:QI (match_operand:QI 2 "register_operand")
(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))
+ (umin:QI (match_dup 2) (match_dup 3))
(const_int 0))
(const_int 0)))
(clobber (reg:CC FLAGS_REG))])]
"TARGET_BMI2"
- "operands[3] = GEN_INT (<MODE_SIZE> * BITS_PER_UNIT);")
+{
+ operands[2] = gen_lowpart (QImode, operands[2]);
+ operands[3] = GEN_INT (<MODE_SIZE> * BITS_PER_UNIT);
+})
(define_insn "*bmi2_bzhi_<mode>3"
[(set (match_operand:SWI48 0 "register_operand" "=r")
(if_then_else:SWI48
- (ne:QI (and:SWI48 (match_operand:SWI48 2 "register_operand" "r")
- (const_int 255))
+ (ne:QI (match_operand:QI 2 "register_operand" "q")
(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"))
- (const_int 0))
- (const_int 0)))
- (clobber (reg:CC FLAGS_REG))]
- "TARGET_BMI2 && INTVAL (operands[3]) == <MODE_SIZE> * BITS_PER_UNIT"
- "bzhi\t{%2, %1, %0|%0, %1, %2}"
- [(set_attr "type" "bitmanip")
- (set_attr "prefix" "vex")
- (set_attr "mode" "<MODE>")])
-
-(define_insn "*bmi2_bzhi_<mode>3_1"
- [(set (match_operand:SWI48 0 "register_operand" "=r")
- (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"))
+ (umin:QI (match_dup 2)
+ (match_operand:QI 3 "const_int_operand"))
(const_int 0))
(const_int 0)))
(clobber (reg:CC FLAGS_REG))]
@@ -18764,8 +18758,8 @@
(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"))
+ (umin:QI (match_dup 2)
+ (match_operand:QI 3 "const_int_operand"))
(const_int 0))
(const_int 0))
(const_int 0)))
@@ -18864,8 +18858,8 @@
[(set (match_operand:SWI48 0 "register_operand" "=r")
(zero_extract:SWI48
(match_operand:SWI48 1 "nonimmediate_operand" "rm")
- (match_operand 2 "const_0_to_255_operand")
- (match_operand 3 "const_0_to_255_operand")))
+ (match_operand:QI 2 "const_0_to_255_operand")
+ (match_operand:QI 3 "const_0_to_255_operand")))
(clobber (reg:CC FLAGS_REG))]
"TARGET_TBM"
{
new file mode 100644
@@ -0,0 +1,33 @@
+/* { dg-do run } */
+/* { dg-options "-O2" } */
+typedef unsigned long int mp_limb_t;
+typedef const mp_limb_t * mp_srcptr;
+
+__attribute__((noipa))
+int
+refmpn_tstbit_bad (mp_srcptr ptr, unsigned long bit)
+{
+ return (((ptr)[(bit)/(32 - 0)] & (((mp_limb_t) 1L) << ((bit)%(32 - 0)))) != 0);
+}
+
+__attribute__((noipa, optimize(0)))
+int
+refmpn_tstbit_good (mp_srcptr ptr, unsigned long bit)
+{
+ return (((ptr)[(bit)/(32 - 0)] & (((mp_limb_t) 1L) << ((bit)%(32 - 0)))) != 0);
+}
+
+__attribute__((noipa))
+int
+refmpn_tstbit (mp_srcptr ptr, unsigned long bit)
+{
+ if (refmpn_tstbit_bad (ptr, bit) != refmpn_tstbit_good (ptr, bit)) {
+ __builtin_trap();
+ }
+ return refmpn_tstbit_bad (ptr, bit);
+}
+
+int main(){
+ unsigned long num[] = { 0x3801ff9f, 0x0, 0x0, 0x0 };
+ refmpn_tstbit(num, 0);
+}
new file mode 100644
@@ -0,0 +1,13 @@
+/* { dg-do compile } */
+/* { dg-options "-O2" } */
+typedef unsigned long int mp_limb_t;
+typedef const mp_limb_t * mp_srcptr;
+
+int
+refmpn_tstbit_bad (mp_srcptr ptr, unsigned long bit)
+{
+ return (((ptr)[(bit)/(32 - 0)] & (((mp_limb_t) 1L) << ((bit)%(32 - 0)))) != 0);
+}
+
+/* { dg-final { scan-assembler "bt\[ql\]" } } */
+/* { dg-final { scan-assembler "setc" } } */