-
Notifications
You must be signed in to change notification settings - Fork 4.9k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Fix problem with scaling general loop blocks; add dumpers #99742
Fix problem with scaling general loop blocks; add dumpers #99742
Conversation
1. Fix a problem where scaling block weights of a range of basic blocks that compose a general loop could encounter a block that is unreachable. This can happen for various kinds of blocks that the JIT doesn't like to remove even if unreachable. Simply skip scaling those blocks. 2. Add dumpers for `FlowGraphDfsTree` and `BlockToNaturalLoopMap`. These can be called from the debugger (perhaps they should be called to output these things to the JitDump). 3. Update `fgDfsBlocksAndRemove()` to dump any blocks that it did not remove, even if they were unreachable. This was found as part of fixing JitOptRepeat: dotnet#94250
@jakobbotsch PTAL |
Tagging subscribers to this area: @JulieLeeMSFT, @jakobbotsch |
This includes various fixes that are being separately PR'ed: 1. dotnet#99744: Introduce HandleKindDataIsInvariant helper 2. dotnet#99743: Add basic support for TYP_MASK constants 3. dotnet#99742: Fix problem with scaling general loop blocks; add dumpers 4. dotnet#99740: Add edge likelihood dumping; fix one edge likelihood update case Also: 1. Add support for running JitOptRepeat under JitStress. This is still over-written by JitOptRepeat being forced on at 4 iterations.
printf("%02u %02u -> " FMT_BB "[%u, %u]\n", i, rpoNum, block->bbNum, block->bbPreorderNum, | ||
block->bbPostorderNum); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i
and block->bbPostorderNum
is the same thing here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Well, this is a dumper, so this can help verify that in the output.
|
||
// Should we call this using the phase method: | ||
// DoPhase(this, PHASE_SET_BLOCK_WEIGHTS, &Compiler::optSetBlockWeights); | ||
// ? It could be called multiple times. | ||
optSetBlockWeights(); | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hopefully we'll just end up removing optSetBlockWeights
entirely in favor of some profile maintenance that means that this call will just go away at some point.
#ifdef DEBUG | ||
// Did we actually remove all the blocks we said we were going to? | ||
if (verbose) | ||
{ | ||
if (m_dfsTree->GetPostOrderCount() != fgBBcount) | ||
{ | ||
printf("%u unreachable blocks were not removed:\n", fgBBcount - m_dfsTree->GetPostOrderCount()); | ||
for (BasicBlock* block : Blocks()) | ||
{ | ||
if (!m_dfsTree->Contains(block)) | ||
{ | ||
printf(" " FMT_BB "\n", block->bbNum); | ||
} | ||
} | ||
} | ||
} | ||
#endif // DEBUG |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Luckily the blocks are still removed in the "graph" sense -- they don't have any preds/succs left anymore, so they don't interact with reachable blocks in any way. I.e. asserts like these are ok:
runtime/src/coreclr/jit/morph.cpp
Lines 13833 to 13835 in b60a541
for (BasicBlock* const pred : block->PredBlocks()) | |
{ | |
assert(m_dfsTree->Contains(pred)); // We should have removed dead blocks before this. |
But yeah, we still have this annoying case to check for when iterating the block list.
Co-authored-by: Jakob Botsch Nielsen <[email protected]>
Fix a problem where scaling block weights of a range of basic blocks that compose a general loop could encounter a block that is unreachable. This can happen for various kinds of blocks that the JIT doesn't like to remove even if unreachable. Simply skip scaling those blocks.
Add dumpers for
FlowGraphDfsTree
andBlockToNaturalLoopMap
. These can be called from the debugger (perhaps they should be called to output these things to the JitDump).Update
fgDfsBlocksAndRemove()
to dump any blocks that it did not remove, even if they were unreachable.This was found as part of fixing JitOptRepeat: #94250