浏览代码

Limit work done in SINK pass.

Reported by XmiliaH.
Mike Pall 3 年之前
父节点
当前提交
a01602a826
共有 1 个文件被更改,包括 12 次插入4 次删除
  1. 12 4
      src/lj_opt_sink.c

+ 12 - 4
src/lj_opt_sink.c

@@ -36,12 +36,14 @@ static IRIns *sink_checkalloc(jit_State *J, IRIns *irs)
 }
 }
 
 
 /* Recursively check whether a value depends on a PHI. */
 /* Recursively check whether a value depends on a PHI. */
-static int sink_phidep(jit_State *J, IRRef ref)
+static int sink_phidep(jit_State *J, IRRef ref, int *workp)
 {
 {
   IRIns *ir = IR(ref);
   IRIns *ir = IR(ref);
+  if (!*workp) return 1;  /* Give up and pretend it does. */
+  (*workp)--;
   if (irt_isphi(ir->t)) return 1;
   if (irt_isphi(ir->t)) return 1;
-  if (ir->op1 >= REF_FIRST && sink_phidep(J, ir->op1)) return 1;
-  if (ir->op2 >= REF_FIRST && sink_phidep(J, ir->op2)) return 1;
+  if (ir->op1 >= REF_FIRST && sink_phidep(J, ir->op1, workp)) return 1;
+  if (ir->op2 >= REF_FIRST && sink_phidep(J, ir->op2, workp)) return 1;
   return 0;
   return 0;
 }
 }
 
 
@@ -56,7 +58,13 @@ static int sink_checkphi(jit_State *J, IRIns *ira, IRRef ref)
       return 1;  /* Sinkable PHI. */
       return 1;  /* Sinkable PHI. */
     }
     }
     /* Otherwise the value must be loop-invariant. */
     /* Otherwise the value must be loop-invariant. */
-    return ref < J->loopref && !sink_phidep(J, ref);
+    if (ref < J->loopref) {
+      /* Check for PHI dependencies, but give up after reasonable effort. */
+      int work = 64;
+      return !sink_phidep(J, ref, &work);
+    } else {
+      return 0;  /* Loop-variant. */
+    }
   }
   }
   return 1;  /* Constant (non-PHI). */
   return 1;  /* Constant (non-PHI). */
 }
 }