summaryrefslogtreecommitdiff
path: root/src/jit/flowgraph.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/jit/flowgraph.cpp')
-rw-r--r--src/jit/flowgraph.cpp55
1 files changed, 22 insertions, 33 deletions
diff --git a/src/jit/flowgraph.cpp b/src/jit/flowgraph.cpp
index 0c57862768..f11d55622d 100644
--- a/src/jit/flowgraph.cpp
+++ b/src/jit/flowgraph.cpp
@@ -1815,9 +1815,9 @@ void Compiler::fgComputeReachabilitySets()
for (block = fgFirstBB; block != nullptr; block = block->bbNext)
{
- // Initialize the per-block bbReach sets. (Note that we can't just call BlockSetOps::ClearD()
- // when re-running this computation, because if the epoch changes, the size and representation of the
- // sets might change).
+ // Initialize the per-block bbReach sets. It creates a new empty set,
+ // because the block epoch could change since the previous initialization
+ // and the old set could have wrong size.
block->bbReach = BlockSetOps::MakeEmpty(this);
/* Mark block as reaching itself */
@@ -4335,7 +4335,7 @@ void Compiler::fgFindJumpTargets(const BYTE* codeAddr, IL_OFFSET codeSize, BYTE*
DECODE_OPCODE:
- if (opcode >= CEE_COUNT)
+ if ((unsigned)opcode >= CEE_COUNT)
{
BADCODE3("Illegal opcode", ": %02X", (int)opcode);
}
@@ -5231,7 +5231,7 @@ unsigned Compiler::fgMakeBasicBlocks(const BYTE* codeAddr, IL_OFFSET codeSize, B
/* Get the size of additional parameters */
- noway_assert(opcode < CEE_COUNT);
+ noway_assert((unsigned)opcode < CEE_COUNT);
sz = opcodeSizes[opcode];
@@ -10011,7 +10011,7 @@ void Compiler::fgCompactBlocks(BasicBlock* block, BasicBlock* bNext)
if (fgDomsComputed && block->bbNum > fgDomBBcount)
{
BlockSetOps::Assign(this, block->bbReach, bNext->bbReach);
- BlockSetOps::ClearD(this, bNext->bbReach);
+ BlockSetOps::OldStyleClearD(this, bNext->bbReach);
block->bbIDom = bNext->bbIDom;
bNext->bbIDom = nullptr;
@@ -17055,8 +17055,8 @@ bool Compiler::fgCheckEHCanInsertAfterBlock(BasicBlock* blk, unsigned regionInde
//
// Return Value:
// A block with the desired characteristics, so the new block will be inserted after this one.
-// If there is no suitable location, return nullptr. This should basically never happen except in the case of
-// single-block filters.
+// If there is no suitable location, return nullptr. This should basically never happen.
+//
BasicBlock* Compiler::fgFindInsertPoint(unsigned regionIndex,
bool putInTryRegion,
BasicBlock* startBlk,
@@ -17284,19 +17284,21 @@ BasicBlock* Compiler::fgFindInsertPoint(unsigned regionIndex,
DONE:
+#if defined(JIT32_GCENCODER)
// If we are inserting into a filter and the best block is the end of the filter region, we need to
- // insert after its predecessor instead: the CLR ABI states that the terminal block of a filter region
- // is its exit block. If the filter region consists of a single block, a new block cannot be inserted
- // without either splitting the single block before inserting a new block or inserting the new block
- // before the single block and updating the filter description such that the inserted block is marked
- // as the entry block for the filter. This work must be done by the caller; this function returns
- // `nullptr` to indicate this case.
- if (insertingIntoFilter && (bestBlk == endBlk->bbPrev) && (bestBlk == startBlk))
+ // insert after its predecessor instead: the JIT32 GC encoding used by the x86 CLR ABI states that the
+ // terminal block of a filter region is its exit block. If the filter region consists of a single block,
+ // a new block cannot be inserted without either splitting the single block before inserting a new block
+ // or inserting the new block before the single block and updating the filter description such that the
+ // inserted block is marked as the entry block for the filter. Becuase this sort of split can be complex
+ // (especially given that it must ensure that the liveness of the exception object is properly tracked),
+ // we avoid this situation by never generating single-block filters on x86 (see impPushCatchArgOnStack).
+ if (insertingIntoFilter && (bestBlk == endBlk->bbPrev))
{
- assert(bestBlk != nullptr);
- assert(bestBlk->bbJumpKind == BBJ_EHFILTERRET);
- bestBlk = nullptr;
+ assert(bestBlk != startBlk);
+ bestBlk = bestBlk->bbPrev;
}
+#endif // defined(JIT32_GCENCODER)
return bestBlk;
}
@@ -17475,21 +17477,6 @@ BasicBlock* Compiler::fgNewBBinRegion(BBjumpKinds jumpKind,
// Now find the insertion point.
afterBlk = fgFindInsertPoint(regionIndex, putInTryRegion, startBlk, endBlk, nearBlk, nullptr, runRarely);
- // If afterBlk is nullptr, we must be inserting into a single-block filter region. Because the CLR ABI requires
- // that control exits a filter via the last instruction in the filter range, this situation requires logically
- // splitting the single block. In practice, we simply insert a new block at the beginning of the filter region
- // that transfers control flow to the existing single block.
- if (afterBlk == nullptr)
- {
- assert(putInFilter);
-
- BasicBlock* newFilterEntryBlock = fgNewBBbefore(BBJ_ALWAYS, startBlk, true);
- newFilterEntryBlock->bbJumpDest = startBlk;
- fgAddRefPred(startBlk, newFilterEntryBlock);
-
- afterBlk = newFilterEntryBlock;
- }
-
_FoundAfterBlk:;
/* We have decided to insert the block after 'afterBlk'. */
@@ -17788,10 +17775,12 @@ BasicBlock* Compiler::fgAddCodeRef(BasicBlock* srcBlk, unsigned refData, Special
#if defined(UNIX_X86_ABI)
codeGen->setFrameRequired(true);
+ codeGen->setFramePointerRequiredGCInfo(true);
#else // !defined(UNIX_X86_ABI)
if (add->acdStkLvl != stkDepth)
{
codeGen->setFrameRequired(true);
+ codeGen->setFramePointerRequiredGCInfo(true);
}
#endif // !defined(UNIX_X86_ABI)
#endif // _TARGET_X86_