On 08/28/2013 11:38 AM, Kirill Yukhin wrote:
>> When combine puts the AND and the NOT together, we don't know what registers
>> we
>> want the data in. If we do not supply the general register alternative, with
>> the clobber, then we will be FORCED to implement the operation in the mask
>> registers, even if this operation had nothing to do with actual vector masks.
>> And it ought to come as no surprise that X & ~Y is a fairly common operation.
> I agree with all of that. But why to put in BMI alternative as well? Without
> it
> me may have this pattern w/o clobber and add it when doing split for GPR
> constraint.
Uh, no, you can't just add it when doing the split. You could be adding it in
a place that the flags register is live. You must ALWAYS have the clobber on
the whole pattern when gprs are possible.
> @@ -4219,8 +4225,13 @@ ix86_conditional_register_usage (void)
>
> /* If AVX512F is disabled, squash the registers. */
> if (! TARGET_AVX512F)
> + {
> for (i = FIRST_EXT_REX_SSE_REG; i < LAST_EXT_REX_SSE_REG; i++)
> fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
> +
> + for (i = FIRST_MASK_REG; i < LAST_MASK_REG; i++)
> + fixed_regs[i] = call_used_regs[i] = 1, reg_names[i] = "";
> + }
Fix the indentation.
> @@ -1429,7 +1450,7 @@ enum reg_class
>
> /* Get_secondary_mem widens integral modes to BITS_PER_WORD.
> There is no need to emit full 64 bit move on 64 bit targets
> - for integral modes that can be moved using 32 bit move. */
> + for integral modes that can be moved using 8 bit move. */
> #define SECONDARY_MEMORY_NEEDED_MODE(MODE) \
> (GET_MODE_BITSIZE (MODE) < 32 && INTEGRAL_MODE_P (MODE) \
> ? mode_for_size (32, GET_MODE_CLASS (MODE), 0) \
Spurious comment change.
> +(define_insn "kandn<mode>"
> + [(set (match_operand:SWI12 0 "register_operand" "=r,&r,!k")
> + (and:SWI12
> + (not:SWI12
> + (match_operand:SWI12 1 "register_operand" "r,0,k"))
> + (match_operand:SWI12 2 "register_operand" "r,r,k")))
> + (clobber (reg:CC FLAGS_REG))]
Yk not k?
> +(define_insn "kxnor<mode>"
> + [(set (match_operand:SWI12 0 "register_operand" "=r,!k")
> + (not:SWI12
> + (xor:SWI12
> + (match_operand:SWI12 1 "register_operand" "0,k")
> + (match_operand:SWI12 2 "register_operand" "r,k"))))]
> + "TARGET_AVX512F"
> + "@
> + #
> + kxnorw\t{%2, %1, %0|%0, %1, %2}"
> + [(set_attr "type" "*,msklog")
> + (set_attr "prefix" "*,vex")
> + (set_attr "mode" "<MODE>")])
Likewise.
> +(define_split
> + [(set (match_operand:SWI12 0 "register_operand")
> + (not:SWI12
> + (xor:SWI12
> + (match_dup 0)
> + (match_operand:SWI12 1 "register_operand"))))]
> + "TARGET_AVX512F && !ANY_MASK_REG_P (operands [0])"
> + [(parallel [(set (match_dup 0)
> + (xor:HI (match_dup 0)
> + (match_dup 1)))
> + (clobber (reg:CC FLAGS_REG))])
> + (set (match_dup 0)
> + (not:HI (match_dup 0)))]
> + "")
general_reg_operand.
> +(define_insn "kortestzhi"
> + [(set (reg:CCZ FLAGS_REG)
> + (compare:CCZ
> + (ior:HI
> + (match_operand:HI 0 "register_operand" "%Yk")
> + (match_operand:HI 1 "register_operand" "Yk"))
Omit the %; the two operands are identical.
> +(define_insn "kortestchi"
> + [(set (reg:CCC FLAGS_REG)
> + (compare:CCC
> + (ior:HI
> + (match_operand:HI 0 "register_operand" "%Yk")
> + (match_operand:HI 1 "register_operand" "Yk"))
Likewise.
> +;; Do not split instructions with mask regs.
> (define_split
> [(set (match_operand 0 "register_operand")
> (not (match_operand 1 "register_operand")))]
> @@ -16486,7 +16683,9 @@
> && (GET_MODE (operands[0]) == HImode
> || (GET_MODE (operands[0]) == QImode
> && (TARGET_PROMOTE_QImode
> - || optimize_insn_for_size_p ())))"
> + || optimize_insn_for_size_p ())))
> + && (! ANY_MASK_REG_P (operands[0])
> + || ! ANY_MASK_REG_P (operands[1]))"
> [(set (match_dup 0)
> (not:SI (match_dup 1)))]
general_reg_operand.
r~