[pypy-commit] pypy vecopt: rewriting parts of the guard strength reduction to eliminate array bound checks
plan_rich
noreply at buildbot.pypy.org
Wed Jul 15 17:32:04 CEST 2015
Author: Richard Plangger <rich at pasra.at>
Branch: vecopt
Changeset: r78555:961725ecb559
Date: 2015-07-15 17:32 +0200
http://bitbucket.org/pypy/pypy/changeset/961725ecb559/
Log: rewriting parts of the guard strength reduction to eliminate array
bound checks
diff --git a/rpython/jit/metainterp/optimizeopt/guard.py b/rpython/jit/metainterp/optimizeopt/guard.py
--- a/rpython/jit/metainterp/optimizeopt/guard.py
+++ b/rpython/jit/metainterp/optimizeopt/guard.py
@@ -9,34 +9,34 @@
MemoryRef, Node, IndexVar)
from rpython.jit.metainterp.resoperation import (rop, ResOperation, GuardResOp)
from rpython.jit.metainterp.history import (ConstInt, BoxVector,
- BoxFloat, BoxInt, ConstFloat, Box)
+ BoxFloat, BoxInt, ConstFloat, Box, Const)
+from rpython.rlib.objectmodel import we_are_translated
class Guard(object):
""" An object wrapper around a guard. Helps to determine
if one guard implies another
"""
- def __init__(self, index, op, cmp_op, lhs, lhs_arg, rhs, rhs_arg):
+ def __init__(self, index, op, cmp_op, lhs_arg, rhs_arg):
self.index = index
self.op = op
self.cmp_op = cmp_op
- self.lhs = lhs
- self.rhs = rhs
self.lhs_arg = lhs_arg
self.rhs_arg = rhs_arg
- self.implied = False
- self.stronger = False
+ self.lhs_key = None
+ self.rhs_key = None
def implies(self, guard, opt):
if self.op.getopnum() != guard.op.getopnum():
return False
- my_key = opt._get_key(self.cmp_op)
- ot_key = opt._get_key(guard.cmp_op)
-
- if my_key[1] == ot_key[1]:
+ if self.lhs_key == guard.lhs_key:
# same operation
- lc = self.compare(self.lhs, guard.lhs)
- rc = self.compare(self.rhs, guard.rhs)
+ valid, lc = self.compare(self.lhs, guard.lhs)
+ if not valid:
+ return False
+ valid, rc = self.compare(self.rhs, guard.rhs)
+ if not valid:
+ return False
opnum = self.get_compare_opnum()
if opnum == -1:
return False
@@ -65,40 +65,43 @@
otherop = other.op
assert isinstance(otherop, GuardResOp)
assert isinstance(myop, GuardResOp)
- self.stronger = True
self.index = other.index
descr = myop.getdescr()
- descr.copy_all_attributes_from(other.op.getdescr())
- myop.rd_frame_info_list = otherop.rd_frame_info_list
- myop.rd_snapshot = otherop.rd_snapshot
- myop.setfailargs(otherop.getfailargs())
+ if we_are_translated():
+ descr.copy_all_attributes_from(other.op.getdescr())
+ myop.rd_frame_info_list = otherop.rd_frame_info_list
+ myop.rd_snapshot = otherop.rd_snapshot
+ myop.setfailargs(otherop.getfailargs())
def compare(self, key1, key2):
if isinstance(key1, Box):
- assert isinstance(key2, Box)
- assert key1 is key2 # key of hash enforces this
- return 0
+ if isinstance(key2, Box) and key1 is key2:
+ return True, 0
+ return False, 0
#
if isinstance(key1, ConstInt):
- assert isinstance(key2, ConstInt)
+ if not isinstance(key2, ConstInt):
+ return False, 0
v1 = key1.value
v2 = key2.value
if v1 == v2:
- return 0
+ return True, 0
elif v1 < v2:
- return -1
+ return True, -1
else:
- return 1
+ return True, 1
#
if isinstance(key1, IndexVar):
assert isinstance(key2, IndexVar)
- return key1.compare(key2)
+ return True, key1.compare(key2)
#
raise AssertionError("cannot compare: " + str(key1) + " <=> " + str(key2))
def emit_varops(self, opt, var, old_arg):
if isinstance(var, IndexVar):
+ if var.is_identity():
+ return var.var
box = var.emit_operations(opt)
opt.renamer.start_renaming(old_arg, box)
return box
@@ -117,105 +120,122 @@
guard.setarg(0, box_result)
opt.emit_operation(guard)
-class GuardStrengthenOpt(object):
- def __init__(self, index_vars):
- self.index_vars = index_vars
- self._newoperations = []
- self._same_as = {}
- self.strength_reduced = 0 # how many guards could be removed?
+ def update_keys(self, index_vars):
+ self.lhs = index_vars.get(self.lhs_arg, self.lhs_arg)
+ if isinstance(self.lhs, IndexVar):
+ self.lhs = self.lhs.var
+ self.lhs_key = self.lhs
+ #
+ self.rhs = index_vars.get(self.rhs_arg, self.rhs_arg)
+ if isinstance(self.rhs, IndexVar):
+ self.rhs = self.rhs.var
+ self.rhs_key = self.rhs
- def find_compare_guard_bool(self, boolarg, operations, index):
+ @staticmethod
+ def of(boolarg, operations, index):
+ guard_op = operations[index]
i = index - 1
# most likely hit in the first iteration
while i > 0:
op = operations[i]
if op.result and op.result == boolarg:
- return op
+ if rop.INT_LT <= op.getopnum() <= rop.INT_GE:
+ cmp_op = op
+ break
+ return None
i -= 1
+ else:
+ raise AssertionError("guard_true/false first arg not defined")
+ #
+ lhs_arg = cmp_op.getarg(0)
+ rhs_arg = cmp_op.getarg(1)
+ return Guard(i, guard_op, cmp_op, lhs_arg, rhs_arg)
- raise AssertionError("guard_true/false first arg not defined")
+class GuardStrengthenOpt(object):
+ def __init__(self, index_vars):
+ self.index_vars = index_vars
+ self._newoperations = []
+ self.strength_reduced = 0 # how many guards could be removed?
+ self.strongest_guards = {}
+ self.guards = {}
- def _get_key(self, cmp_op):
- if cmp_op and rop.INT_LT <= cmp_op.getopnum() <= rop.INT_GE:
- lhs_arg = cmp_op.getarg(0)
- rhs_arg = cmp_op.getarg(1)
- lhs_index_var = self.index_vars.get(lhs_arg, None)
- rhs_index_var = self.index_vars.get(rhs_arg, None)
+ #def _get_key(self, cmp_op):
+ # assert cmp_op
+ # lhs_arg = cmp_op.getarg(0)
+ # rhs_arg = cmp_op.getarg(1)
+ # lhs_index_var = self.index_vars.get(lhs_arg, None)
+ # rhs_index_var = self.index_vars.get(rhs_arg, None)
- cmp_opnum = cmp_op.getopnum()
- # get the key, this identifies the guarded operation
- if lhs_index_var and rhs_index_var:
- key = (lhs_index_var.getvariable(), cmp_opnum, rhs_index_var.getvariable())
- elif lhs_index_var:
- key = (lhs_index_var.getvariable(), cmp_opnum, rhs_arg)
- elif rhs_index_var:
- key = (lhs_arg, cmp_opnum, rhs_index_var)
- else:
- key = (lhs_arg, cmp_opnum, rhs_arg)
- return key
- return (None, 0, None)
+ # cmp_opnum = cmp_op.getopnum()
+ # # get the key, this identifies the guarded operation
+ # if lhs_index_var and rhs_index_var:
+ # return (lhs_index_var.getvariable(), cmp_opnum, rhs_index_var.getvariable())
+ # elif lhs_index_var:
+ # return (lhs_index_var.getvariable(), cmp_opnum, None)
+ # elif rhs_index_var:
+ # return (None, cmp_opnum, rhs_index_var)
+ # else:
+ # return (None, cmp_opnum, None)
+ # return key
- def get_key(self, guard_bool, operations, i):
- cmp_op = self.find_compare_guard_bool(guard_bool.getarg(0), operations, i)
- return self._get_key(cmp_op)
-
- def propagate_all_forward(self, loop):
- """ strengthens the guards that protect an integral value """
- strongest_guards = {}
- guards = {}
- # the guards are ordered. guards[i] is before guards[j] iff i < j
+ def collect_guard_information(self, loop):
operations = loop.operations
last_guard = None
for i,op in enumerate(operations):
op = operations[i]
- if op.is_guard() and op.getopnum() in (rop.GUARD_TRUE, rop.GUARD_FALSE):
- cmp_op = self.find_compare_guard_bool(op.getarg(0), operations, i)
- key = self._get_key(cmp_op)
- if key[0] is not None:
- lhs_arg = cmp_op.getarg(0)
- lhs = self.index_vars.get(lhs_arg, lhs_arg)
- rhs_arg = cmp_op.getarg(1)
- rhs = self.index_vars.get(rhs_arg, rhs_arg)
- other = strongest_guards.get(key, None)
- if not other:
- guard = Guard(i, op, cmp_op,
- lhs, lhs_arg,
- rhs, rhs_arg)
- strongest_guards[key] = guard
- # nothing known, at this position emit the guard
- guards[i] = guard
- else: # implicit index(strongest) < index(current)
- guard = Guard(i, op, cmp_op,
- lhs, lhs_arg, rhs, rhs_arg)
- if guard.implies(other, self):
- guard.inhert_attributes(other)
+ if not op.is_guard():
+ continue
+ if op.getopnum() in (rop.GUARD_TRUE, rop.GUARD_FALSE):
+ guard = Guard.of(op.getarg(0), operations, i)
+ if guard is None:
+ continue
+ guard.update_keys(self.index_vars)
+ self.record_guard(guard.lhs_key, guard)
+ self.record_guard(guard.rhs_key, guard)
- strongest_guards[key] = guard
- guards[other.index] = guard
- # do not mark as emit
- continue
- elif other.implies(guard, self):
- guard.implied = True
- # mark as emit
- guards[i] = guard
- else:
- # emit non guard_true/false guards
- guards[i] = Guard(i, op, None, None, None, None, None)
+ def record_guard(self, key, guard):
+ if key is None:
+ return
+ # the operations are processed from 1..n (forward),
+ # thus if the key is not present (1), the guard is saved
+ # (2) guard(s) with this key is/are already present,
+ # thus each of is seen as possible candidate to strengthen
+ # or imply the current. in both cases the current guard is
+ # not emitted and the original is replaced with the current
+ others = self.strongest_guards.setdefault(key, [])
+ if len(others) > 0: # (2)
+ for i,other in enumerate(others):
+ if guard.implies(other, self):
+ # strengthend
+ guard.inhert_attributes(other)
+ others[i] = guard
+ self.guards[other.index] = guard
+ self.guards[guard.index] = None # mark as 'do not emit'
+ continue
+ elif other.implies(guard, self):
+ # implied
+ self.guards[guard.index] = None # mark as 'do not emit'
+ continue
+ else: # (2)
+ others.append(guard)
- strongest_guards = None
- #
+ def eliminate_guards(self, loop):
self.renamer = Renamer()
- last_op_idx = len(operations)-1
- for i,op in enumerate(operations):
- op = operations[i]
- if op.is_guard() and op.getopnum() in (rop.GUARD_TRUE, rop.GUARD_FALSE):
- guard = guards.get(i, None)
- if not guard or guard.implied:
+ for i,op in enumerate(loop.operations):
+ op = loop.operations[i]
+ if op.is_guard():
+ if i in self.guards:
+ # either a stronger guard has been saved
+ # or it should not be emitted
+ guard = self.guards[i]
# this guard is implied or marked as not emitted (= None)
self.strength_reduced += 1
+ if guard is None:
+ continue
+ guard.emit_operations(self)
continue
- if guard.stronger:
- guard.emit_operations(self)
+ else:
+ self.emit_operation(op)
continue
if op.result:
index_var = self.index_vars.get(op.result, None)
@@ -224,8 +244,15 @@
index_var.emit_operations(self, op.result)
continue
self.emit_operation(op)
+ #
+ loop.operations = self._newoperations[:]
- loop.operations = self._newoperations[:]
+ def propagate_all_forward(self, loop):
+ """ strengthens the guards that protect an integral value """
+ # the guards are ordered. guards[i] is before guards[j] iff i < j
+ self.collect_guard_information(loop)
+ #
+ self.eliminate_guards(loop)
def emit_operation(self, op):
self.renamer.rename(op)
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_guard.py b/rpython/jit/metainterp/optimizeopt/test/test_guard.py
new file mode 100644
--- /dev/null
+++ b/rpython/jit/metainterp/optimizeopt/test/test_guard.py
@@ -0,0 +1,159 @@
+import py
+
+from rpython.jit.metainterp.history import TargetToken, JitCellToken, TreeLoop
+from rpython.jit.metainterp.optimizeopt.util import equaloplists
+from rpython.jit.metainterp.optimizeopt.vectorize import (VecScheduleData,
+ Pack, NotAProfitableLoop, VectorizingOptimizer)
+from rpython.jit.metainterp.optimizeopt.dependency import Node, DependencyGraph
+from rpython.jit.metainterp.optimizeopt.guard import GuardStrengthenOpt
+from rpython.jit.metainterp.optimizeopt.test.test_util import LLtypeMixin
+from rpython.jit.metainterp.optimizeopt.test.test_schedule import SchedulerBaseTest
+from rpython.jit.metainterp.optimizeopt.test.test_vectorize import (FakeMetaInterpStaticData,
+ FakeJitDriverStaticData)
+from rpython.jit.metainterp.resoperation import rop, ResOperation
+from rpython.jit.tool.oparser_model import get_model
+
+class FakeMemoryRef(object):
+ def __init__(self, array, iv):
+ self.index_var = iv
+ self.array = array
+
+ def is_adjacent_to(self, other):
+ if self.array is not other.array:
+ return False
+ iv = self.index_var
+ ov = other.index_var
+ val = (int(str(ov.var)[1:]) - int(str(iv.var)[1:]))
+ # i0 and i1 are adjacent
+ # i1 and i0 ...
+ # but not i0, i2
+ # ...
+ return abs(val) == 1
+
+class GuardBaseTest(SchedulerBaseTest):
+ def optguards(self, loop):
+ dep = DependencyGraph(loop)
+ opt = GuardStrengthenOpt(dep.index_vars)
+ opt.propagate_all_forward(loop)
+ return opt
+
+ def assert_guard_count(self, loop, count):
+ guard = 0
+ for op in loop.operations:
+ if op.is_guard():
+ guard += 1
+ if guard != count:
+ self.debug_print_operations(loop)
+ assert guard == count
+
+ def assert_contains_sequence(self, loop, instr):
+ class Glob(object):
+ def __repr__(self):
+ return '*'
+ from rpython.jit.tool.oparser import OpParser, default_fail_descr
+ parser = OpParser(instr, self.cpu, self.namespace(), 'lltype', None, default_fail_descr, True, None)
+ operations = []
+ last_glob = None
+ prev_op = None
+ for line in instr.splitlines():
+ line = line.strip()
+ if line.startswith("#") or \
+ line == "":
+ continue
+ if line.startswith("..."):
+ last_glob = Glob()
+ last_glob.prev = prev_op
+ operations.append(last_glob)
+ continue
+ op = parser.parse_next_op(line)
+ if last_glob is not None:
+ last_glob.next = op
+ last_glob = None
+ operations.append(op)
+ prev_op = op
+
+ def check(op, candidate, rename):
+ if isinstance(candidate, Glob):
+ if candidate.next is None:
+ return 0 # consumes the rest
+ if op.getopnum() != candidate.next.getopnum():
+ return 0
+ candidate = candidate.next
+ if op.getopnum() == candidate.getopnum():
+ for i,arg in enumerate(op.getarglist()):
+ oarg = candidate.getarg(i)
+ if arg in rename:
+ assert rename[arg] is oarg
+ else:
+ rename[arg] = oarg
+
+ if op.result:
+ rename[op.result] = candidate.result
+ return 1
+ return 0
+ j = 0
+ rename = {}
+ for i, op in enumerate(loop.operations):
+ candidate = operations[j]
+ j += check(op, candidate, rename)
+ if isinstance(operations[0], Glob):
+ assert j == len(operations)-2
+ else:
+ assert j == len(operations)-1
+
+ def test_basic(self):
+ loop1 = self.parse("""
+ i10 = int_lt(i1, 42)
+ guard_true(i10) []
+ i11 = int_add(i1, 1)
+ i12 = int_lt(i11, 42)
+ guard_true(i12) []
+ """)
+ opt = self.optguards(loop1)
+ self.assert_guard_count(loop1, 1)
+ self.assert_contains_sequence(loop1, """
+ ...
+ i11 = int_add(i1, 1)
+ i12 = int_lt(i11, 42)
+ guard_true(i12) []
+ ...
+ """)
+
+ def test_basic_sub(self):
+ loop1 = self.parse("""
+ i10 = int_gt(i1, 42)
+ guard_true(i10) []
+ i11 = int_sub(i1, 1)
+ i12 = int_gt(i11, 42)
+ guard_true(i12) []
+ """)
+ opt = self.optguards(loop1)
+ self.assert_guard_count(loop1, 1)
+ self.assert_contains_sequence(loop1, """
+ ...
+ i11 = int_sub(i1, 1)
+ i12 = int_gt(i11, 42)
+ guard_true(i12) []
+ ...
+ """)
+
+ def test_collapse(self):
+ loop1 = self.parse("""
+ i10 = int_gt(i1, 42)
+ guard_true(i10) []
+ i11 = int_sub(i1, 1)
+ i12 = int_gt(i11, 42)
+ guard_true(i12) []
+ """)
+ opt = self.optguards(loop1)
+ self.assert_guard_count(loop1, 1)
+ self.assert_contains_sequence(loop1, """
+ ...
+ i11 = int_sub(i1, 1)
+ i12 = int_gt(i11, 42)
+ guard_true(i12) []
+ ...
+ """)
+
+class Test(GuardBaseTest, LLtypeMixin):
+ pass
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_schedule.py b/rpython/jit/metainterp/optimizeopt/test/test_schedule.py
--- a/rpython/jit/metainterp/optimizeopt/test/test_schedule.py
+++ b/rpython/jit/metainterp/optimizeopt/test/test_schedule.py
@@ -25,13 +25,8 @@
class SchedulerBaseTest(DependencyBaseTest):
- def parse(self, source, inc_label_jump=True,
- pargs=2,
- iargs=10,
- fargs=6,
- additional_args=None,
- replace_args=None):
- ns = {
+ def namespace(self):
+ return {
'double': self.floatarraydescr,
'float': self.singlefloatarraydescr,
'long': self.intarraydescr,
@@ -39,6 +34,13 @@
'short': self.int16arraydescr,
'char': self.chararraydescr,
}
+
+ def parse(self, source, inc_label_jump=True,
+ pargs=2,
+ iargs=10,
+ fargs=6,
+ additional_args=None,
+ replace_args=None):
args = []
for prefix, rang in [('p',range(pargs)), ('i',range(iargs)), ('f',range(fargs))]:
for i in rang:
@@ -56,7 +58,7 @@
joinedargs = ','.join(args)
fmt = (indent, joinedargs, source, indent, joinedargs)
src = "%s[%s]\n%s\n%sjump(%s)" % fmt
- loop = opparse(src, cpu=self.cpu, namespace=ns)
+ loop = opparse(src, cpu=self.cpu, namespace=self.namespace())
if inc_label_jump:
token = JitCellToken()
loop.operations = \
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py b/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
--- a/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
+++ b/rpython/jit/metainterp/optimizeopt/test/test_vectorize.py
@@ -1360,19 +1360,47 @@
def test_abc(self):
trace="""
- [i16, i17, i18, i5, p6, p7, f19, p9, p10, p11, p12, p13, p14, p15, i20, i21]
+ [p0, p1, p5, p6, p7, p12, p13, i14, i15, i16, i17, i18, i19, i20]
guard_early_exit() []
- f22 = raw_load(i20, i18, descr=<ArrayF 8>)
- guard_not_invalidated(descr=<rpython.jit.metainterp.compile.ResumeGuardNotInvalidated object at 0x7fc428762410>) [i5, i18, i17, i16, p15, p14, p13, p12, p11, p10, p9, p7, p6, f22, f19]
- f23 = raw_load(i21, i17, descr=<ArrayF 8>)
- f24 = float_mul(f22, f23)
- f25 = float_add(f19, f24)
- i27 = int_add(i18, 8)
- i29 = int_add(i17, 8)
- i30 = int_lt(i16, i5)
- guard_true(i30, descr=<rpython.jit.metainterp.compile.ResumeGuardTrueDescr object at 0x7fc4287689d0>) [i5, i27, i29, i16, p15, p14, p13, p12, p11, p10, p9, p7, p6, f25, None]
- i33 = int_add(i16, 1)
- jump(i33, i29, i27, i5, p6, p7, f25, p9, p10, p11, p12, p13, p14, p15, i20, i21)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #117 LOAD_NAME')
+ guard_not_invalidated(descr=<ResumeGuardNotInvalidated object at 0x7fc657d7be20>) [p1, p0, p5, p6, p7, p12, p13]
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #120 LOAD_CONST')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #123 COMPARE_OP')
+ i22 = int_lt(i14, 2024)
+ guard_true(i22, descr=<ResumeGuardTrueDescr object at 0x7fc657d7bdc0>) [p1, p0, p5, p6, p7, p12, p13, i14]
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #126 POP_JUMP_IF_FALSE')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #129 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #132 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #135 BINARY_SUBSCR')
+ i23 = int_lt(i14, i15)
+ guard_true(i23, descr=<ResumeGuardTrueDescr object at 0x7fc657d7bd60>) [p1, p0, i14, p5, p6, p7, p12, p13, None]
+ f25 = getarrayitem_raw(i16, i14, descr=floatarraydescr)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #136 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #139 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #142 BINARY_SUBSCR')
+ i26 = int_lt(i14, i17)
+ guard_true(i26, descr=<ResumeGuardTrueDescr object at 0x7fc657d7bca0>) [p1, p0, i14, p5, p6, p7, p12, p13, f25, None]
+ f27 = getarrayitem_raw(i18, i14, descr=floatarraydescr)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #143 BINARY_ADD')
+ f28 = float_add(f25, f27)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #144 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #147 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #150 STORE_SUBSCR')
+ i29 = int_lt(i14, i19)
+ guard_true(i29, descr=<ResumeGuardTrueDescr object at 0x7fc657d7bc40>) [p1, p0, i14, p5, p6, p7, p12, p13, f28, None, None]
+ setarrayitem_raw(i20, i14, f28, descr=floatarraydescr)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #151 LOAD_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #154 LOAD_CONST')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #157 INPLACE_ADD')
+ i31 = int_add(i14, 1)
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #158 STORE_NAME')
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #161 JUMP_ABSOLUTE')
+ i33 = getfield_raw(140489852409120, descr=<FieldS pypysig_long_struct.c_value 0>)
+ setfield_gc(1234, i31, descr=<FieldS pypy.objspace.std.typeobject.IntMutableCell.inst_intvalue 8>)
+ i36 = int_lt(i33, 0)
+ guard_false(i36, descr=<ResumeGuardFalseDescr object at 0x7fc657d7be80>) [p1, p0, p5, p6, p7, p12, p13, None, None, None]
+ debug_merge_point(0, 0, '<code object <module>. file '/home/rich/proj/da/thesis/bench/user1.py'. line 2> #117 LOAD_NAME')
+ jump(p0, p1, p5, p6, p7, p12, p13, i31, i15, i16, i17, i18, i19, i20)
"""
# schedule 885 -> ptype is non for raw_load?
opt = self.vectorize(self.parse_loop(trace))
More information about the pypy-commit
mailing list