This is the mail archive of the
`gcc-patches@gcc.gnu.org`
mailing list for the GCC project.

# Re: [PATCH] Optimize (CST1 << A) == CST2 (PR tree-optimization/66299)

*From*: Jakub Jelinek <jakub at redhat dot com>
*To*: Marek Polacek <polacek at redhat dot com>
*Cc*: GCC Patches <gcc-patches at gcc dot gnu dot org>
*Date*: Thu, 28 May 2015 14:34:36 +0200
*Subject*: Re: [PATCH] Optimize (CST1 << A) == CST2 (PR tree-optimization/66299)
*Authentication-results*: sourceware.org; auth=none
*References*: <20150528121545 dot GE27320 at redhat dot com>
*Reply-to*: Jakub Jelinek <jakub at redhat dot com>

On Thu, May 28, 2015 at 02:15:45PM +0200, Marek Polacek wrote:
> This PR points out that we weren't able to optimize 1 << x == 2 to just
> x == 1. This is my attempt to fix that: if we see (CST1 << A) == CST2
> and CST2 is a multiple of CST1, use log2 to get rid of the shift, but
> only if the result of the shift is a natural number (including zero).
Is CST2 a multiple of CST1 the best test though?
I mean say in
(0x8001U << x) == 0x20000U
0x20000U isn't a multiple of 0x8001U, yet there is only one
valid value of x for which it holds (17), so we could very well
optimize that to x == 17.
If popcount of the CST1 is 1, then multiple_of_p is supposedly sufficient
(have you checked if CST1 is negative that it still works?), for others
supposedly we could have a helper function that would just try
in a loop all shift counts from 0 to precision - 1, and note when
(CST1 << b) == CST2 - if for no b, then it should fold regardless of
has_single_use to false or true, if for exactly one shift count, then
use a comparison against that shift count, otherwise give up?
Supposedly (CST1 >> A) == CST2 can be handled similarly.
> If CST2 is not a multiple of CST1, then the whole expression can be
> discarded, but I'd like to do that as a follow-up.
> (It would help if our current match.pd grammar allowed us to use "else",
> any plans on doing that?)
Jakub