This is an archive of the discontinued LLVM Phabricator instance.

[ConstantRange] Fix isWrappedSet()
AbandonedPublic

Authored by nikic on Mar 24 2019, 9:45 AM.

Details

Reviewers
lebedev.ri
spatel
Summary

isWrappedSet() currently incorrectly returns true for ranges like i8 [42, 255], also known as i8 [42, 0). While a reasonable person might argue that the current behavior is correct if you interpret "wrapping" relative to the exclusive upper bound, the behavior is inconsistent with isSignWrappedSet() in two ways:

  • While i8 [42, 0) is considered unsigned wrapping, i8 [42, -128) is not considered signed wrapping.
  • The full set is not considered unsigned wrapping, but considered signed wrapping.

This patch changes isWrappedSet() and isSignWrappedSet() to behave consistently: They will both not consider 0/SignedMin upper bound as wrapping, and both not consider full sets as wrapping.

Additionally isUpperWrapped() and isUpperSignWrapped() methods are added which *do* consider 0/SignedMin as wrapping. Both interpretations of wrapping are useful depending on context, so both are provided.

Diff Detail

Event Timeline

nikic created this revision.Mar 24 2019, 9:45 AM
Herald added a project: Restricted Project. · View Herald TranscriptMar 24 2019, 9:45 AM
nikic marked an inline comment as done.Mar 24 2019, 1:41 PM
nikic added inline comments.
llvm/lib/IR/ConstantRange.cpp
463

I should note that the use of isUpperWrapped() in this function is incorrect, I'm just using it to preserve the existing behavior. This function should be using isWrappedSet() and work on an inclusive upper bound. Right now it handles ranges with Upper=0 suboptimally. I will submit a followup for that.

This is a bit too low-level and intrusive than i feel comfortable reviewing..

It is best to split this up:

  1. Rename isWrappedSet() into isUpperWrapped() (including all of it's uses). That would be an obvious, uncontroversial NFC commit.
  2. Rename isSignWrappedSet() to something else like isSignWrappedSetLegacy(). NFC commit.
  3. Introduce these 3 new functions. Also pretty much NFC.
  4. The remaining of the patch

This is a bit too low-level and intrusive than i feel comfortable reviewing..

It is best to split this up:

  1. Rename isWrappedSet() into isUpperWrapped() (including all of it's uses). That would be an obvious, uncontroversial NFC commit.
  2. Rename isSignWrappedSet() to something else like isSignWrappedSetLegacy(). NFC commit.
  3. Introduce these 3 new functions. Also pretty much NFC.
  4. The remaining of the patch

.. or, if isSignWrappedSet() change is NFC, then that can be [yet another] NFC commit after Introduce these new functions diff.

After applying the other changes in rL357039, rL357107 and rL357112 there isn't really much left here. Could change one or two uses of isUpperWrapped() back to isWrappedSet() because it is the same in the used context...

After applying the other changes in rL357039, rL357107 and rL357112

Thanks!
Those three small diffs are oh so much better than this huge monolithic patch.

there isn't really much left here. Could change one or two uses of isUpperWrapped() back to isWrappedSet() because it is the same in the used context...

That sounds like a good cleanup to me, if you feel like it.

lebedev.ri requested changes to this revision.Apr 6 2019, 7:53 AM

there isn't really much left here. Could change one or two uses of isUpperWrapped() back to isWrappedSet() because it is the same in the used context...

That sounds like a good cleanup to me, if you feel like it.

This differential basically fully landed.
Should be either abandoned, or rebased to contain the cleanup part.

This revision now requires changes to proceed.Apr 6 2019, 7:53 AM
nikic abandoned this revision.May 6 2019, 10:56 AM

Abandoning this one, don't think there's anything worthwhile left here.