This is the mail archive of the
mailing list for the GCC project.
Re: [PATCH][AArch64] Use CC_Z and CC_NZ with csinc and similar instructions
- From: Kyrill Tkachov <kyrylo dot tkachov at arm dot com>
- To: Richard Henderson <rth at redhat dot com>, GCC Patches <gcc-patches at gcc dot gnu dot org>
- Cc: Richard Earnshaw <Richard dot Earnshaw at arm dot com>, Marcus Shawcroft <Marcus dot Shawcroft at arm dot com>
- Date: Tue, 19 Aug 2014 17:50:42 +0100
- Subject: Re: [PATCH][AArch64] Use CC_Z and CC_NZ with csinc and similar instructions
- Authentication-results: sourceware.org; auth=none
- References: <53F1F068 dot 4070708 at arm dot com> <53F24B7D dot 1010200 at redhat dot com> <53F35128 dot 9010801 at arm dot com> <53F36C67 dot 4080803 at redhat dot com> <53F376D2 dot 8080505 at redhat dot com>
On 19/08/14 17:09, Richard Henderson wrote:
return (REGNO (op) == CC_REGNUM
&& (GET_MODE (op) == CCmode
|| GET_MODE (op) == CC_Zmode
|| GET_MODE (op) == CC_NZmode));
... and now that I read the backend more closely, I see "_zero" was a bad name.
But more importantly, I see no connection between the comparison used and the
CCmode being accepted. And if we fix that, why are you restricting to just Z
and NZ? What's wrong with e.g. CFPmode?
In the i386 backend, we check comparison+mode correspondence like
(match_operator 4 "ix86_carry_flag_operator"
[(match_operand 3 "flags_reg_operand") (const_int 0)])
I think you'll want something similar. In the case of CSINC, we can accept all
conditions, so let's start with the most general:
(match_operator:GPI 2 "aarch64_comparison_operation"
[(reg CC_REGNUM) (const_int 0)]
(match_operand:GPI 2 "aarch64_comparison_operation" "")
if (XEXP (op, 1) != const0_rtx)
rtx op0 = XEXP (op, 0);
if (!REG_P (op0) || REGNO (op0) != CC_REGNUM)
return aarch64_get_condition_code (op) >= 0;
where aarch64_get_condition_code is
(2) adjusted to return "int" not "unsigned"
(3) adjusted to not abort, but return -1 for invalid combinations.
and the two existing users of aarch64_get_condition_code are adjusted to
gcc_assert that the return value is valid.
Hmm, when I do that combine refuses to match the csinc patterns:
Failed to match this instruction:
(set (reg:SI 73 [ D.2564 ])
(if_then_else:SI (ne (reg:CC 66 cc)
(const_int 0 ))
(plus:SI (reg:SI 74 [ D.2565 ])
(const_int 1 [0x1]))
(const_int 0 )))
I probably mistyped something, I'll look into it...
Thanks for the help,