Skip to content
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

[release/8.0] Check if loop body occured before loopTop and if so unmark alignment #91918

Merged
merged 4 commits into from
Sep 18, 2023
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 31 additions & 3 deletions src/coreclr/jit/compiler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5282,6 +5282,13 @@ PhaseStatus Compiler::placeLoopAlignInstructions()
weight_t minBlockSoFar = BB_MAX_WEIGHT;
BasicBlock* bbHavingAlign = nullptr;
BasicBlock::loopNumber currentAlignedLoopNum = BasicBlock::NOT_IN_LOOP;
bool visitedLoopNum[BasicBlock::MAX_LOOP_NUM];
memset(visitedLoopNum, false, sizeof(visitedLoopNum));

#ifdef DEBUG
unsigned visitedBlockForLoopNum[BasicBlock::MAX_LOOP_NUM];
memset(visitedBlockForLoopNum, 0, sizeof(visitedBlockForLoopNum));
#endif

if ((fgFirstBB != nullptr) && fgFirstBB->isLoopAlign())
{
Expand All @@ -5304,7 +5311,7 @@ PhaseStatus Compiler::placeLoopAlignInstructions()
}
}

// If there is a unconditional jump (which is not part of callf/always pair)
// If there is an unconditional jump (which is not part of callf/always pair)
if (opts.compJitHideAlignBehindJmp && (block->bbJumpKind == BBJ_ALWAYS) && !block->isBBCallAlwaysPairTail())
{
// Track the lower weight blocks
Expand Down Expand Up @@ -5358,12 +5365,19 @@ PhaseStatus Compiler::placeLoopAlignInstructions()
madeChanges = true;
unmarkedLoopAlign = true;
}
else if ((block->bbNatLoopNum != BasicBlock::NOT_IN_LOOP) && (block->bbNatLoopNum == loopTop->bbNatLoopNum))
else if ((loopTop->bbNatLoopNum != BasicBlock::NOT_IN_LOOP) && visitedLoopNum[loopTop->bbNatLoopNum])
{
#ifdef DEBUG
char buffer[100];
sprintf_s(buffer, 100, "loop block " FMT_BB " appears before top of loop",
visitedBlockForLoopNum[loopTop->bbNatLoopNum]);
#endif

// In some odd cases we may see blocks within the loop before we see the
// top block of the loop. Just bail on aligning such loops.
//
loopTop->unmarkLoopAlign(this DEBUG_ARG("loop block appears before top of loop"));

loopTop->unmarkLoopAlign(this DEBUG_ARG(buffer));
madeChanges = true;
unmarkedLoopAlign = true;
}
Expand Down Expand Up @@ -5398,6 +5412,20 @@ PhaseStatus Compiler::placeLoopAlignInstructions()
break;
}
}

if (block->bbNatLoopNum != BasicBlock::NOT_IN_LOOP)
{
#ifdef DEBUG
if (!visitedLoopNum[block->bbNatLoopNum])
{
// Record the first block for which bbNatLoopNum was seen for
// debugging purpose.
visitedBlockForLoopNum[block->bbNatLoopNum] = block->bbNum;
}
#endif
// If this block is part of loop, mark the loopNum as visited.
visitedLoopNum[block->bbNatLoopNum] = true;
}
}

assert(loopsToProcess == 0);
Expand Down