This is an archive of the discontinued LLVM Phabricator instance.

[SimplifyCFG] Add early bailout if Use is not in same BB.
ClosedPublic

Authored by fhahn on Nov 5 2021, 9:32 AM.

Details

Summary

Without this patch, passingValueIsAlwaysUndefined will iterate over all
instructions from I to the end of the basic block, even if the use is
outside the block.

This patch adds an early bail out, if the use instruction is outside I's
BB. This can greatly reduce compile-time in cases where very large basic
blocks are involved, with a large number of PHI nodes and incoming
values.

Note that the refactoring makes the handling of the case where I is a
phi and Use is in PHI more explicit as well: for phi nodes, we can also
directly bail out. In the existing code, we would iterate until we reach
the end and return false.

I could add a test case that shows the compile-time improvement, but it
would be quite large.

Based on an earlier patch by Matt Wala.

Diff Detail

Event Timeline

fhahn created this revision.Nov 5 2021, 9:32 AM
fhahn requested review of this revision.Nov 5 2021, 9:32 AM
Herald added a project: Restricted Project. · View Herald TranscriptNov 5 2021, 9:32 AM
fhahn updated this revision to Diff 385103.Nov 5 2021, 9:40 AM

Remove UseI variable, use Use instead.

RKSimon added a comment.EditedNov 6 2021, 2:41 AM

SGTM - might an alternative to a test be to run it on https://llvm-compile-time-tracker.com ?

I don't understand the old code. Why does it look at one user? I thought the order of uses is undefined, and whatever checks are done for just one user and not done for the others may be a source of non-determinism.

nikic added a subscriber: nikic.Nov 8 2021, 12:21 AM

I don't understand the old code. Why does it look at one user? I thought the order of uses is undefined, and whatever checks are done for just one user and not done for the others may be a source of non-determinism.

The order is deterministic, but usually arbitrary (see uselistorder in IR and -preserve-(bc|ll)-uselistorder).

llvm/lib/Transforms/Utils/SimplifyCFG.cpp
6530–6535

Can be cast, user of instruction is always instruction.

6543

We have isGuaranteedToTransferExecutionToSuccessor() variants that accept iterators in ValueTracking, and also enforce a ScanLimit (default 32). That should ensure that there are no pathological cases even if they are in the same block.

fhahn updated this revision to Diff 385750.Nov 9 2021, 2:32 AM

Updated to use cast instead of dyn_cast.

SGTM - might an alternative to a test be to run it on https://llvm-compile-time-tracker.com ?

Done: http://llvm-compile-time-tracker.com/compare.php?from=e3bfb6a14646fd3b344c491a5f46aaebd43090a7&to=2ea682d8c75956531a894e38af397caf627b3882&stat=instructions

There are a few small but notable improvements:

NewPM-O3:

ClamAV	71699M	71567M (-0.18%)

NewPM-ReleaseLTO-g:

kimwitu++	85293M	85171M (-0.14%)
fhahn marked an inline comment as done.Nov 9 2021, 2:34 AM
fhahn added inline comments.
llvm/lib/Transforms/Utils/SimplifyCFG.cpp
6530–6535

updated, thanks!

6543

I did that with the following results: http://llvm-compile-time-tracker.com/compare.php?from=29c1c85c4e1dfe663bd9e7424d021283f9dc3254&to=2c6b1eed0c7f8e933e7666bc50eb390bbfccc039&stat=instructions

I'd like to keep this out of the current change though, as this may impact the generated code (there are a few binary changes even for CTMark), while the current patch should be NFC with respect to codegen.

This revision is now accepted and ready to land.Nov 9 2021, 2:35 AM
nikic added inline comments.Nov 9 2021, 2:43 AM
llvm/lib/Transforms/Utils/SimplifyCFG.cpp
6530–6535

Can also drop the !Use check.

This revision was automatically updated to reflect the committed changes.
fhahn marked an inline comment as done.
fhahn marked 2 inline comments as done.Nov 9 2021, 4:58 AM
fhahn added inline comments.
llvm/lib/Transforms/Utils/SimplifyCFG.cpp
6530–6535

Done in the committed version, thanks!