This is an archive of the discontinued LLVM Phabricator instance.

Generalize getExtendAddRecStart to work with both sign and zero extensions.
ClosedPublic

Authored by sanjoy on Feb 14 2015, 1:01 PM.

Details

Summary

This change also removes DEBUG(dbgs() << "SCEV: untested prestart overflow check\n"); because that case has a unit test now.

Diff Detail

Repository
rL LLVM

Event Timeline

sanjoy updated this revision to Diff 19971.Feb 14 2015, 1:01 PM
sanjoy retitled this revision from to Generalize getExtendAddRecStart to work with both sign and zero extensions..
sanjoy updated this object.
sanjoy edited the test plan for this revision. (Show Details)
sanjoy added reviewers: atrick, hfinkel, majnemer.
sanjoy added a subscriber: Unknown Object (MLST).
atrick accepted this revision.Feb 17 2015, 12:42 AM
atrick edited edge metadata.

Thanks for generalizing this. It would seem simpler to define an ExtendOpTraits base class parameterized on ExtendOp instead of triplicating the typedef. Otherwise LGTM.

I can't remember if there are other places we've tried to generalize SCEV extension ops. I don't see anything off hand.

This revision is now accepted and ready to land.Feb 17 2015, 12:42 AM
This revision was automatically updated to reflect the committed changes.

I can see how my comment about duplicating the typedef would seem silly. I was actually thinking about bringing the members defined by that type into the base, as shown below. But I didn't think it through because now that I write it out, the out-of-line static definitions are utterly horrid:

template <SCEV::NoWrapFlags W, GetExtendExprTy ExtendF,

GetOverflowLimitForStepTy OverflowF>

struct ExtendOpTraitsBase {

static const SCEV::NoWrapFlags WrapType = W;
static const GetExtendExprTy GetExtendExpr;
static const GetOverflowLimitForStepTy GetOverflowLimitForStep;

};

template <SCEV::NoWrapFlags W, GetExtendExprTy ExtendF,

GetOverflowLimitForStepTy OverflowF>

const GetExtendExprTy ExtendOpTraitsBase<W, ExtendF, OverflowF>::
GetExtendExpr = ExtendF;

template <SCEV::NoWrapFlags W, GetExtendExprTy ExtendF,

GetOverflowLimitForStepTy OverflowF>

const GetOverflowLimitForStepTy ExtendOpTraitsBase<W, ExtendF, OverflowF>::
GetOverflowLimitForStep = OverflowF;

template <typename ExtendOp> struct ExtendOpTraits {};

template <>
struct ExtendOpTraits<SCEVSignExtendExpr>

: public ExtendOpTraitsBase<SCEV::FlagNSW, getSignExtendExpr,
                            getSignedOverflowLimitForStep>

{};

template <>
struct ExtendOpTraits<SCEVZeroExtendExpr>

: public ExtendOpTraitsBase<SCEV::FlagNUW, getZeroExtendExpr,
                            getUnsignedOverflowLimitForStep>

{};

Oh well, at any rate, you shouldn't need to refer to the type like this anymore:
ExtendOpTraits<SCEVSignExtendExpr>::GetExtendExprTy

Looks like I misinterpreted your review comment. :) Does what I
checked in look okay though?

  • Sanjoy
spatel added a subscriber: spatel.Feb 20 2015, 3:44 PM

Hi all -
This patch appears to be responsible for a new miscompile detailed in:
http://llvm.org/bugs/show_bug.cgi?id=22641