[PATCH] D39345: SCEV: preserve debug information attached to PHI nodes.

Adrian Prantl via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Fri Oct 27 10:42:03 PDT 2017


aprantl added inline comments.


================
Comment at: lib/Analysis/ScalarEvolutionExpander.cpp:1215
+  // Save the original PHI node so we can copy over its debug info.
+  PHINode *OldPN = L->getCanonicalInductionVariable();
+ 
----------------
aprantl wrote:
> hfinkel wrote:
> > aprantl wrote:
> > > hfinkel wrote:
> > > > How do you know that the AddRec being expanded here is equivalent to a canonical induction variable? That's only true if we're expanding '{0,+,1}', right?
> > > > 
> > > > Does calling SE.getSCEVValues(Normalized) also find the original PHI node?
> > > > 
> > > Thanks, that is a good point! I could either constrain it to just handle this special case or attempt to generalize it. Unfortunately I don't know enough about SCEV yet:
> > > Can SCEV also modify the trip count of the loop?
> > > Is there a way I can reconstruct a function (that I then could translate into a DWARF expression) that transforms the value of the new induction variable into the original one for the current iteration?
> > > Thanks, that is a good point! I could either constrain it to just handle this special case or attempt > to generalize it. Unfortunately I don't know enough about SCEV yet:
> > 
> > If `SE.getSCEVValues(Normalized)` will give you the original PHI for a given SCEV, then that should be fully general (at least for cases where there is an existing PHI for a particular).
> > 
> > > Can SCEV also modify the trip count of the loop?
> > 
> > SCEV is an analysis, so this is really a question about what transformations might do. A transformation can change the trip count of a loop (generally by reducing it; peeling for example).
> > 
> > > Is there a way I can reconstruct a function (that I then could translate into a DWARF expression) that transforms the value of the new induction variable into the original one for the current iteration?
> > 
> > If I have the SCEV of the original induction variable, OrigIVAddRec, and the new induction variable, NewIVAddRec, then you can subtract them:
> > 
> >   IVDiff = SE->getMinusSCEV(NewIVAddRec, OrigIVAddRec);
> > 
> > Now, in each iteration, IVDiff is what you need to add to the current induction variable, NewIV, in order to get the value of the existing one, OldIV. So you can construct a DWARF expression that adds IVDiff to NewIV. In some cases, IVDiff will actually just be an SCEVConstant, but it could be a more general expression.
> > 
> > To handle the more-general case, a SCEV -> DWARF utility can be created. One way to do this would be to write an SCEVVisitor that builds up a DWARF expression as it recurses through an SCEV. When you reach an SCEVUnknown, that's just a wrapper around a Value*. And you might be able to short-circuit the evaluation at any SCEV,moreover, if SE.getSCEVValues on that SCEV returns a useful Value*.
> > 
> > I suspect this is most of what you need to do to adjust for what IndVarSimplify does as well (although it also sometimes changes the bitwidth of induction variables, so there's a little more to do there I suspect for those cases).
> Thanks, I have a couple more questions!
> 
> > Does calling SE.getSCEVValues(Normalized) also find the original PHI node?
> `SE.getSCEVValues(Normalized)` returns a nullptr unfortunately.
> 
> Is the problem with  `L->getCanonicalInductionVariable()` that multiple transformations might be applied on top of another and that the IV from the Loop object might be out of date?
> 
> I guess I'm also slightly confused at what the SCEV of the original induction variable is. Does the `SCEVAddRecExpr *Normalized` represent the induction variable or the loop itself?
> 
> `Normalized->dump()` says: `{0,+,1}<nuw><nsw><%for.cond>`
> so this appears to represent the recurrence representing one step in the loop. Is that the "SCEV of the induction variable" or is that different from the SCEVAddRecExpr and how do I get to it?
> 
> Does the notation '{0,+,1}' mean start=0, increment_operator=+, increment=1?
> 
> That said, the part with the SCEVVisitor ->DWARF translator sounds fairly straightforward and fun to do!
Based on this snippet from the top of SCEVExpander::getAddRecExprPHILiterally() it looks like `PhiSCEV` is the SCEV for the original induction variable.

```
 for (auto &I : *L->getHeader()) {
      auto *PN = dyn_cast<PHINode>(&I);
      if (!PN || !SE.isSCEVable(PN->getType()))
        continue;

      const SCEVAddRecExpr *PhiSCEV = dyn_cast<SCEVAddRecExpr>(SE.getSCEV(PN));
      if (!PhiSCEV)
        continue;
```


https://reviews.llvm.org/D39345





More information about the llvm-commits mailing list