зеркало из https://github.com/mozilla/gecko-dev.git
Bug 1209515 part 10 - Prevent PruneUnusedBranches from being greedy while removing branches which have only be visited a few times. r=bhackett
This commit is contained in:
Родитель
d11cd0d832
Коммит
bf49183eb3
|
@ -7,8 +7,8 @@
|
|||
// Ion eager fails the test below because we have not yet created any
|
||||
// template object in baseline before running the content of the top-level
|
||||
// function.
|
||||
if (getJitCompilerOptions()["ion.warmup.trigger"] <= 30)
|
||||
setJitCompilerOption("ion.warmup.trigger", 30);
|
||||
if (getJitCompilerOptions()["ion.warmup.trigger"] <= 90)
|
||||
setJitCompilerOption("ion.warmup.trigger", 90);
|
||||
|
||||
// This test checks that we are able to remove the getelem & setelem with scalar
|
||||
// replacement, so we should not force inline caches, as this would skip the
|
||||
|
|
|
@ -296,6 +296,43 @@ jit::PruneUnusedBranches(MIRGenerator* mir, MIRGraph& graph)
|
|||
block->getHitState() == MBasicBlock::HitState::Count &&
|
||||
block->getHitCount() == 0;
|
||||
|
||||
// Check if the predecessors got accessed a large number of times in
|
||||
// comparisons of the current block, in order to know if our attempt at
|
||||
// removing this block is not premature.
|
||||
if (shouldBailout) {
|
||||
size_t p = numPred;
|
||||
size_t predCount = 0;
|
||||
bool isLoopExit = false;
|
||||
while (p--) {
|
||||
MBasicBlock* pred = block->getPredecessor(p);
|
||||
if (pred->getHitState() == MBasicBlock::HitState::Count)
|
||||
predCount += pred->getHitCount();
|
||||
isLoopExit |= pred->isLoopHeader() && pred->backedge() != *block;
|
||||
}
|
||||
|
||||
// This assumes that instructions are numbered in sequence, which is
|
||||
// the case after IonBuilder creation of basic blocks.
|
||||
size_t numInst = block->rbegin()->id() - block->begin()->id();
|
||||
|
||||
// This sum is not homogeneous but gives good results on benchmarks
|
||||
// like Kraken and Octane. The current block has not been executed
|
||||
// yet, and ...
|
||||
//
|
||||
// 1. If the number of times the predecessor got executed is
|
||||
// larger, then we are less likely to hit this block.
|
||||
//
|
||||
// 2. If the block is large, then this is likely a corner case,
|
||||
// and thus we are less likely to hit this block.
|
||||
if (predCount + numInst < 75)
|
||||
shouldBailout = false;
|
||||
|
||||
// If this is the exit block of a loop, then keep this basic
|
||||
// block. This heuristic is useful as a bailout is often much more
|
||||
// costly than a simple exit sequence.
|
||||
if (isLoopExit)
|
||||
shouldBailout = false;
|
||||
}
|
||||
|
||||
// Continue to the next basic block if the current basic block can
|
||||
// remain unchanged.
|
||||
if (!isUnreachable && !shouldBailout)
|
||||
|
|
Загрузка…
Ссылка в новой задаче