diff --git a/src/coreclr/jit/fgbasic.cpp b/src/coreclr/jit/fgbasic.cpp index aac4b48732fe6..49ba08c98eb6e 100644 --- a/src/coreclr/jit/fgbasic.cpp +++ b/src/coreclr/jit/fgbasic.cpp @@ -654,7 +654,8 @@ void Compiler::fgReplaceJumpTarget(BasicBlock* block, BasicBlock* oldTarget, Bas if (block->FalseEdgeIs(oldEdge)) { - // fgRemoveRefPred returns nullptr for BBJ_COND blocks with two flow edges to target + // Branch was degenerate, simplify it first + // fgRemoveConditionalJump(block); assert(block->KindIs(BBJ_ALWAYS)); assert(block->TargetIs(oldTarget)); @@ -663,10 +664,7 @@ void Compiler::fgReplaceJumpTarget(BasicBlock* block, BasicBlock* oldTarget, Bas // fgRemoveRefPred should have removed the flow edge fgRemoveRefPred(oldEdge); assert(oldEdge->getDupCount() == 0); - - // TODO-NoFallThrough: Proliferate weight from oldEdge - // (as a quirk, we avoid doing so for the true target to reduce diffs for now) - FlowEdge* const newEdge = fgAddRefPred(newTarget, block); + FlowEdge* const newEdge = fgAddRefPred(newTarget, block, oldEdge); if (block->KindIs(BBJ_ALWAYS)) { @@ -676,11 +674,6 @@ void Compiler::fgReplaceJumpTarget(BasicBlock* block, BasicBlock* oldTarget, Bas { assert(block->KindIs(BBJ_COND)); block->SetTrueEdge(newEdge); - - if (oldEdge->hasLikelihood()) - { - newEdge->setLikelihood(oldEdge->getLikelihood()); - } } } else @@ -688,12 +681,34 @@ void Compiler::fgReplaceJumpTarget(BasicBlock* block, BasicBlock* oldTarget, Bas assert(block->FalseTargetIs(oldTarget)); FlowEdge* const oldEdge = block->GetFalseEdge(); + // Already degenerate cases should have taken the true path above. + assert(!block->TrueEdgeIs(oldEdge)); + // fgRemoveRefPred should have removed the flow edge fgRemoveRefPred(oldEdge); assert(oldEdge->getDupCount() == 0); FlowEdge* const newEdge = fgAddRefPred(newTarget, block, oldEdge); - block->SetFalseEdge(newEdge); + + if (block->KindIs(BBJ_ALWAYS)) + { + block->SetTargetEdge(newEdge); + } + else + { + assert(block->KindIs(BBJ_COND)); + block->SetFalseEdge(newEdge); + } } + + if (block->KindIs(BBJ_COND) && (block->GetFalseEdge() == block->GetTrueEdge())) + { + // Block became degenerate, simplify + // + fgRemoveConditionalJump(block); + assert(block->KindIs(BBJ_ALWAYS)); + assert(block->TargetIs(newTarget)); + } + break; case BBJ_SWITCH: