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

Unmark loop align regardless if we found block to align or not #86198

Merged
merged 2 commits into from
May 16, 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
102 changes: 51 additions & 51 deletions src/coreclr/jit/compiler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5311,66 +5311,66 @@ PhaseStatus Compiler::placeLoopAlignInstructions()
{
// Loop alignment is disabled for cold blocks
assert((block->bbFlags & BBF_COLD) == 0);
BasicBlock* const loopTop = block->bbNext;

// If jmp was not found, then block before the loop start is where align instruction will be added.
// There are two special cases:
// 1. If the block before the loop start is a retless BBJ_CALLFINALLY with
// FEATURE_EH_CALLFINALLY_THUNKS, we can't add alignment because it will affect reported EH
// region range.
// 2. If the previous block is the BBJ_ALWAYS of a BBJ_CALLFINALLY/BBJ_ALWAYS pair, then we
// can't add alignment because we can't add instructions in that block. In the
// FEATURE_EH_CALLFINALLY_THUNKS case, it would affect the reported EH, as above.
//
// Currently, we don't align loops for these cases.
//
if (bbHavingAlign == nullptr)
{
bool isSpecialCallFinally = block->isBBCallAlwaysPairTail();
BasicBlock* const loopTop = block->bbNext;
bool isSpecialCallFinally = block->isBBCallAlwaysPairTail();
bool unmarkedLoopAlign = false;

#if FEATURE_EH_CALLFINALLY_THUNKS
if (block->bbJumpKind == BBJ_CALLFINALLY)
{
// It must be a retless BBJ_CALLFINALLY if we get here.
assert(!block->isBBCallAlwaysPair());

// In the case of FEATURE_EH_CALLFINALLY_THUNKS, we can't put the align instruction in a retless
// BBJ_CALLFINALLY either, because it alters the "cloned finally" region reported to the VM.
// In the x86 case (the only !FEATURE_EH_CALLFINALLY_THUNKS that supports retless
// BBJ_CALLFINALLY), we allow it.
isSpecialCallFinally = true;
}
if (block->bbJumpKind == BBJ_CALLFINALLY)
{
// It must be a retless BBJ_CALLFINALLY if we get here.
assert(!block->isBBCallAlwaysPair());

// In the case of FEATURE_EH_CALLFINALLY_THUNKS, we can't put the align instruction in a retless
// BBJ_CALLFINALLY either, because it alters the "cloned finally" region reported to the VM.
// In the x86 case (the only !FEATURE_EH_CALLFINALLY_THUNKS that supports retless
// BBJ_CALLFINALLY), we allow it.
isSpecialCallFinally = true;
}
#endif // FEATURE_EH_CALLFINALLY_THUNKS

if (isSpecialCallFinally)
{
loopTop->unmarkLoopAlign(this DEBUG_ARG("block before loop is special callfinally/always block"));
madeChanges = true;
}
else if ((block->bbNatLoopNum != BasicBlock::NOT_IN_LOOP) &&
(block->bbNatLoopNum == loopTop->bbNatLoopNum))
{
// 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"));
madeChanges = true;
}
else
if (isSpecialCallFinally)
{
// There are two special cases:
// 1. If the block before the loop start is a retless BBJ_CALLFINALLY with
// FEATURE_EH_CALLFINALLY_THUNKS, we can't add alignment because it will affect reported EH
// region range.
// 2. If the previous block is the BBJ_ALWAYS of a BBJ_CALLFINALLY/BBJ_ALWAYS pair, then we
// can't add alignment because we can't add instructions in that block. In the
// FEATURE_EH_CALLFINALLY_THUNKS case, it would affect the reported EH, as above.
// Currently, we don't align loops for these cases.

loopTop->unmarkLoopAlign(this DEBUG_ARG("block before loop is special callfinally/always block"));
madeChanges = true;
unmarkedLoopAlign = true;
}
else if ((block->bbNatLoopNum != BasicBlock::NOT_IN_LOOP) && (block->bbNatLoopNum == loopTop->bbNatLoopNum))
{
// 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"));
madeChanges = true;
unmarkedLoopAlign = true;
}

if (!unmarkedLoopAlign)
{
if (bbHavingAlign == nullptr)
{
// If jmp was not found, then block before the loop start is where align instruction will be added.

bbHavingAlign = block;
JITDUMP("Marking " FMT_BB " before the loop with BBF_HAS_ALIGN for loop at " FMT_BB "\n",
block->bbNum, loopTop->bbNum);
}
}
else
{
JITDUMP("Marking " FMT_BB " that ends with unconditional jump with BBF_HAS_ALIGN for loop at " FMT_BB
"\n",
bbHavingAlign->bbNum, loopTop->bbNum);
}
else
{
JITDUMP("Marking " FMT_BB
" that ends with unconditional jump with BBF_HAS_ALIGN for loop at " FMT_BB "\n",
bbHavingAlign->bbNum, loopTop->bbNum);
}

if (bbHavingAlign != nullptr)
{
madeChanges = true;
bbHavingAlign->bbFlags |= BBF_HAS_ALIGN;
}
Expand Down