On 01/14/2016 12:49 AM, Jakub Jelinek wrote:
On Thu, Jan 14, 2016 at 08:46:43AM +0100, Jakub Jelinek wrote:
On Thu, Jan 14, 2016 at 12:38:52AM -0700, Jeff Law wrote:
+ /* An integral type with more precision, but the object
+ only takes on values [0..1] as determined by VRP
+ analysis. */
+ wide_int min, max;
+ if (INTEGRAL_TYPE_P (TREE_TYPE (op))
+ && get_range_info (op, &min, &max) == VR_RANGE
+ && wi::eq_p (min, 0)
+ && wi::eq_p (max, 1))
+ return true;
You could use and/or:
if (INTEGRAL_TYPE_P (TREE_TYPE (op)) && wi::eq_p (get_nonzero_bits (op), 1))
set_range_info for VR_RANGE should usually update also the non-zero bits, but
set_nonzero_bits does not update the recorded range.
Though, that would need to be limited to TYPE_PRECISION (TREE_TYPE (op)) > 1
or TYPE_UNSIGNED.
Quite surprisingly, this does seem to do better fairly often. Usually
it's just getting more constants into the PHI nodes without further
improvements. However occasionally I see a PHI that turns into a
constant, which is then propagated to a use where we're able to simplify
some arithmetic/logical.
Unfortunately it doesn't make a bit of difference in the final output,
so something post DOM was picking up these anyway (most likely VRP2).
But I'm a fan of getting stuff optimized earlier in the pipeline when
it's reasonable to do so, and this seems reasonable.
Limiting to TYPE_PRECISION > 1 or TYPE_UNSIGNED ought to be trivial.
BTW,
+ /* An integral type with a single bit of precision. */
+ if (INTEGRAL_TYPE_P (TREE_TYPE (op))
+ && TYPE_PRECISION (TREE_TYPE (op)) == 1)
+ return true;
does not guarantee values 0, 1, it can mean either 0, 1 or -1, 0. So, if
-1, 0 is unacceptable, you need to use TYPE_UNSIGNED (TREE_TYPE (op)) too.
Hmm, then I think we've got other places that likely need updating. I
remember adding similar code elsewhere in the past couple years. I'll
have to do a little auditing.
jeff