Bug 1259911: Only add predecessors to the join block once; r=sunfish
authorBenjamin Bouvier <benj@benj.me>
Tue, 29 Mar 2016 18:41:39 +0200
changeset 291248 f53dbc1c638a131bff1b5b49ce08d71a8f0a56c9
parent 291247 ef04d22a4de586d67193e7011bd37aaecdf90164
child 291249 9839c4bda97608c9fc2dcecb6e767386a4c9215d
push id19656
push usergwagner@mozilla.com
push dateMon, 04 Apr 2016 13:43:23 +0000
treeherderb2g-inbound@e99061fde28a [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerssunfish
bugs1259911
milestone48.0a1
Bug 1259911: Only add predecessors to the join block once; r=sunfish MozReview-Commit-ID: A660ASYGb4l
js/src/asmjs/WasmIonCompile.cpp
js/src/jit-test/tests/wasm/random-control-flow.js
--- a/js/src/asmjs/WasmIonCompile.cpp
+++ b/js/src/asmjs/WasmIonCompile.cpp
@@ -1346,28 +1346,40 @@ class FunctionCompiler
             if (i < patches.length())
                 return patches[i].ins->block();
             return curBlock_;
         };
         ensurePushInvariants(getBlock, patches.length() + !!curBlock_);
 
         MBasicBlock* join = nullptr;
         MControlInstruction* ins = patches[0].ins;
-        if (!newBlock(ins->block(), &join))
+        MBasicBlock* pred = ins->block();
+        if (!newBlock(pred, &join))
             return false;
 
+        pred->mark();
         ins->replaceSuccessor(patches[0].index, join);
 
         for (size_t i = 1; i < patches.length(); i++) {
             ins = patches[i].ins;
-            if (!join->addPredecessor(alloc(), ins->block()))
-                return false;
+
+            pred = ins->block();
+            if (!pred->isMarked()) {
+                if (!join->addPredecessor(alloc(), pred))
+                    return false;
+                pred->mark();
+            }
+
             ins->replaceSuccessor(patches[i].index, join);
         }
 
+        MOZ_ASSERT_IF(curBlock_, !curBlock_->isMarked());
+        for (uint32_t i = 0; i < join->numPredecessors(); i++)
+            join->getPredecessor(i)->unmark();
+
         if (curBlock_ && !goToExistingBlock(curBlock_, join))
             return false;
         curBlock_ = join;
 
         *def = hasPushed(curBlock_) ? curBlock_->pop() : nullptr;
 
         patches.clear();
         return true;
--- a/js/src/jit-test/tests/wasm/random-control-flow.js
+++ b/js/src/jit-test/tests/wasm/random-control-flow.js
@@ -7,16 +7,21 @@ assertEq(wasmEvalText(`(module
 )`)(42), 42);
 
 wasmEvalText(`(module (func $func$0
       (block (if (i32.const 1) (loop (br_table 0 (br 0)))))
   )
 )`);
 
 wasmEvalText(`(module (func
+      (loop $out $in (br_table $out $out $in (i32.const 0)))
+  )
+)`);
+
+wasmEvalText(`(module (func
   (select
     (block
       (block
         (br_table
          1
          0
          (i32.const 1)
         )