This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
Re: Validity of SUBREG+AND-imm transformations
- From: Kyrill Tkachov <kyrylo dot tkachov at foss dot arm dot com>
- To: Segher Boessenkool <segher at kernel dot crashing dot org>
- Cc: Jeff Law <law at redhat dot com>, "gcc at gcc dot gnu dot org" <gcc at gcc dot gnu dot org>
- Date: Fri, 04 Mar 2016 15:30:33 +0000
- Subject: Re: Validity of SUBREG+AND-imm transformations
- Authentication-results: sourceware.org; auth=none
- References: <56D055C6 dot 6040800 at foss dot arm dot com> <56D0C2A1 dot 1070501 at redhat dot com> <56D422AC dot 2000703 at foss dot arm dot com> <20160304115946 dot GA20650 at gate dot crashing dot org> <56D99E93 dot 70209 at foss dot arm dot com> <56D9A035 dot 2010902 at foss dot arm dot com> <20160304150718 dot GA31234 at gate dot crashing dot org> <56D9A5F2 dot 4050807 at foss dot arm dot com>
On 04/03/16 15:12, Kyrill Tkachov wrote:
On 04/03/16 15:07, Segher Boessenkool wrote:
On Fri, Mar 04, 2016 at 02:48:21PM +0000, Kyrill Tkachov wrote:
Although there are case where we hit the same problem:
unsigned long
f3 (unsigned long bit_addr)
{
unsigned long bitnumb = bit_addr & 63;
return (1L << bitnumb);
}
combine will try to match:
(set (reg:DI 78)
(ashift:DI (reg:DI 80)
(subreg:SI (and:DI (reg:DI 0 x0 [ bit_addr ])
(const_int 63 [0x3f])) 0)))
does that mean that the shift amount should be DImode?
Heh. Maybe? Try it out, see which works best.
My point was that you do not have QI anywhere else. Registers are
always SI or DI (I think? Not totally familiar with the aarch64 code).
Yeah, registers can be accessed either in SImode (w-form) or DImode (x-form)
and if an instruction writes the SImode form the top 32 bits are implicitly
zeroed out.
Making DImode performs worst of all...
For code:
unsigned long
foo (unsigned long a, unsigned int b)
{
return a << b;
}
If we represent the shift amount as DImode then the SImode register for 'b' is wrapped
into a zero-extend to DImode during expand, so we'd need all of the arith+shift patterns
to match a zero_extend form. When the shift amount is QImode we don't have any of that
because we just take the QImode subreg in the ashift RTX. I suspect that's the original
reason why it was not made DImode.
Seems like a more flexible approach would be for the midend to be able to
handle these things...
Of course. OTOH, there is no reason to make it harder than necessary
for the compiler to do a reasonable job ;-)
I'll do some more investigations. Last time I looked at changing the mode I recall
having various zero_extends being introduced that hurt matching...
Kyrill
Segher