This is an archive of the discontinued LLVM Phabricator instance.

[DebugInfo] Make children iterator bidirectional
ClosedPublic

Authored by JDevlieghere on Jul 11 2018, 3:35 AM.

Details

Summary

Make the DIE iterator bidirectional so we can move to the previous sibling of a DIE.

Diff Detail

Repository
rL LLVM

Event Timeline

JDevlieghere created this revision.Jul 11 2018, 3:35 AM
JDevlieghere retitled this revision from DebugInfo] Make children iterator bidirectional to [DebugInfo] Make children iterator bidirectional.Jul 11 2018, 3:47 AM
  • Remove null check so we can iterate backwards from the end iterator.
  • Update comments
dblaikie added inline comments.Jul 11 2018, 8:48 AM
llvm/include/llvm/DebugInfo/DWARF/DWARFDie.h
354 ↗(On Diff #155005)

Why was this change needed?

llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp
595–599 ↗(On Diff #155005)

Unlike get(Next)Sibling, this loop may need to check for "<= Depth" and then return DWARFDie() if it's the < case.

When going forwards, there's always a null die sibling to break this loop (well, I guess a null die is returned from getSibling - and then no caller tries to call getSibling on the null die) - because it has the same depth.

But going backwards there's no null die to break the loop - oh, well, kind of.

So if you've got this arrangement: Unit{A{B,NULL},C{D,NULL},NULL}

And at D you "get previous" then you'll return the NULL child of A... which is still a null child, and that works I suppose. But you could've stopped searching once you saw C - because you've stepped out of C's children list by going to a shallower depth than the depth of D who's sibling you were searching for.

Oh... and it's undefined to dereference a begin iterator anyway, so none of that really matters, I suppose? :)

JDevlieghere marked 2 inline comments as done.
  • Address review feedback Dave
JDevlieghere added inline comments.Jul 11 2018, 9:29 AM
llvm/include/llvm/DebugInfo/DWARF/DWARFDie.h
354 ↗(On Diff #155005)

For a bidirectional iterator you should be able to start iterating from end(), right? (so long you don't dereference it)

llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp
595–599 ↗(On Diff #155005)

Indeed. I added the check at some point but looks like it didn't make it into the patch. Even if it doesn't matter for the iterator (I assume you mean dereferencing the end iterator?) the check is cheap so we might as well make the interface behave as you'd expect.

dblaikie accepted this revision.Jul 11 2018, 9:49 AM
dblaikie added inline comments.
llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp
595–599 ↗(On Diff #155005)

Yeah - if it were just the iterator API I'd say maybe make it an assert - but since this is a "getPrevSibling" it makes sense to me that it's not UB to call it on the first child, and for it to be symmetric with "get(Next)Sibling" in terms of returning null on the first/last element.

626 ↗(On Diff #155021)

Maybe assert that DieArray[I].getDepth() > Depth - to ensure it didn't some how jump out of the children?

This revision is now accepted and ready to land.Jul 11 2018, 9:49 AM
JDevlieghere marked an inline comment as done.Jul 11 2018, 10:01 AM

Thanks for the review!

llvm/lib/DebugInfo/DWARF/DWARFUnit.cpp
626 ↗(On Diff #155021)

Good idea, I'll add that before committing.

This revision was automatically updated to reflect the committed changes.
JDevlieghere marked an inline comment as done.