[pypy-commit] pypy jit-leaner-frontend: progress, pass the first snapshot test

fijal pypy.commits at gmail.com
Wed Mar 2 10:35:15 EST 2016


Author: fijal
Branch: jit-leaner-frontend
Changeset: r82660:0077f0c7f4ec
Date: 2016-03-02 16:33 +0100
http://bitbucket.org/pypy/pypy/changeset/0077f0c7f4ec/

Log:	progress, pass the first snapshot test

diff --git a/rpython/jit/metainterp/opencoder.py b/rpython/jit/metainterp/opencoder.py
--- a/rpython/jit/metainterp/opencoder.py
+++ b/rpython/jit/metainterp/opencoder.py
@@ -5,12 +5,16 @@
     ResOperation, oparity, opname, rop, ResOperation, opwithdescr
 from rpython.rlib.rarithmetic import intmask
 from rpython.jit.metainterp import resume
+from rpython.rlib.objectmodel import we_are_translated
 
 TAGINT, TAGCONST, TAGBOX = range(3)
 TAGMASK = 0x3
 TAGSHIFT = 2
 MAXINT = 65536
 
+class Sentinel(object):
+    pass
+
 class TraceIterator(object):
     def __init__(self, trace, end):
         self.trace = trace
@@ -47,18 +51,10 @@
         else:
             yyyy
 
-    def read_resume(self, op):
-        jc_index = self._next()
-        pc = self._next()
-        f = resume.FrameInfo(None, jc_index, pc)
-        op.rd_frame_info_list = f
-        lgt = self._next()
-        box_list = []
-        for i in range(lgt):
-            box = self._get(self._next())
-            assert box
-            box_list.append(box)
-        op.rd_snapshot = resume.TopSnapshot(resume.Snapshot(None, box_list), [], [])
+    def skip_resume_data(self):
+        pos = self.pos
+        self.pos = self._next()
+        return pos
 
     def next(self):
         opnum = self._next()
@@ -79,7 +75,7 @@
             descr = None
         res = ResOperation(opnum, args, -1, descr=descr)
         if rop.is_guard(opnum):
-            self.read_resume(res)
+            res.rd_snapshot_position = self.skip_resume_data()
         self._cache[self._count] = res
         self._count += 1
         return res
@@ -145,6 +141,9 @@
         index = op._pos
         self._ops[index] = -newtag - 1
 
+    def record_snapshot_link(self, pos):
+        self._ops.append(-pos - 1)
+
     def record_op(self, opnum, argboxes, descr=None):
         # return an ResOperation instance, ideally die in hell
         pos = self._record_op(opnum, argboxes, descr)
@@ -154,12 +153,29 @@
         return tag(TAGBOX, self._record_raw(opnum, tagged_args, descr))
 
     def record_snapshot(self, jitcode, pc, active_boxes):
+        pos = len(self._ops)
+        self._ops.append(len(active_boxes)) # unnecessary, can be read from
         self._ops.append(jitcode.index)
         self._ops.append(pc)
-        self._ops.append(len(active_boxes)) # unnecessary, can be read from
-        # jitcode
         for box in active_boxes:
             self._ops.append(box.position) # not tagged, as it must be boxes
+        return pos
+
+    def get_patchable_position(self):
+        p = len(self._ops)
+        if not we_are_translated():
+            self._ops.append(Sentinel())
+        else:
+            self._ops.append(-1)
+        return p
+
+    def patch_position_to_current(self, p):
+        prev = self._ops[p]
+        if we_are_translated():
+            assert prev == -1
+        else:
+            assert isinstance(prev, Sentinel)
+        self._ops[p] = len(self._ops)
 
     def get_iter(self):
         return TraceIterator(self, len(self._ops))
diff --git a/rpython/jit/metainterp/optimizeopt/test/test_util.py b/rpython/jit/metainterp/optimizeopt/test/test_util.py
--- a/rpython/jit/metainterp/optimizeopt/test/test_util.py
+++ b/rpython/jit/metainterp/optimizeopt/test/test_util.py
@@ -502,13 +502,10 @@
         return self.oparse.parse()
 
     def postprocess(self, op):
-        class FakeJitCode(object):
-            index = 0
-
         if OpHelpers.is_guard(op.getopnum()):
-            op.rd_snapshot = resume.TopSnapshot(None,
+            op.rd_snapshot = resume.TopSnapshot(
                 resume.Snapshot(None, op.getfailargs()), [], [])
-            op.rd_frame_info_list = resume.FrameInfo(None, FakeJitCode(), 11)
+            op.rd_frame_info_list = resume.FrameInfo(None, 0, 11)
 
     def add_guard_future_condition(self, res):
         # invent a GUARD_FUTURE_CONDITION to not have to change all tests
diff --git a/rpython/jit/metainterp/pyjitpl.py b/rpython/jit/metainterp/pyjitpl.py
--- a/rpython/jit/metainterp/pyjitpl.py
+++ b/rpython/jit/metainterp/pyjitpl.py
@@ -70,8 +70,7 @@
         self.copy_constants(self.registers_f, jitcode.constants_f, ConstFloat)
         self._result_argcode = 'v'
         # for resume.py operation
-        self.parent_resumedata_snapshot = None
-        self.parent_resumedata_frame_info_list = None
+        self.parent_resumedata_position = -1
         # counter for unrolling inlined loops
         self.unroll_iterations = 1
 
@@ -2061,7 +2060,8 @@
         else:
             guard_op = self.history.record(opnum, moreargs, None)            
         assert isinstance(guard_op, GuardResOp)
-        self.capture_resumedata(resumepc) # <- records extra to history
+        self.capture_resumedata(resumepc)
+        # ^^^ records extra to history
         self.staticdata.profiler.count_ops(opnum, Counters.GUARDS)
         # count
         self.attach_debug_info(guard_op)
diff --git a/rpython/jit/metainterp/resume.py b/rpython/jit/metainterp/resume.py
--- a/rpython/jit/metainterp/resume.py
+++ b/rpython/jit/metainterp/resume.py
@@ -112,23 +112,20 @@
                                               self.variable,
                                               self.location)
 
-def _ensure_parent_resumedata(framestack, n):
-    target = framestack[n]
+def _ensure_parent_resumedata(framestack, n, t):
     if n == 0:
         return
+    target = framestack[n]
     back = framestack[n - 1]
-    if target.parent_resumedata_frame_info_list is not None:
-        _, pc = unpack_uint(target.parent_resumedata_frame_info_list.packed_jitcode_pc)
-        assert pc == back.pc
+    if target.parent_resumedata_position != -1:
+        t.check_snapshot_jitcode_pc(back.jitcode, back.pc,
+            target.parent_resumedata_position)
+        t.record_snapshot_link(target.parent_resumedata_position)
         return
-    _ensure_parent_resumedata(framestack, n - 1)
-    target.parent_resumedata_frame_info_list = FrameInfo(
-                                         back.parent_resumedata_frame_info_list,
-                                         back.jitcode,
-                                         back.pc)
-    target.parent_resumedata_snapshot = Snapshot(
-                                         back.parent_resumedata_snapshot,
-                                         back.get_list_of_active_boxes(True))
+    pos = t.record_snapshot(back.jitcode, back.pc,
+                            back.get_list_of_active_boxes(True))
+    _ensure_parent_resumedata(framestack, n - 1, t)
+    target.parent_resumedata_position = pos
 
 def capture_resumedata(framestack, virtualizable_boxes, virtualref_boxes, t):
     n = len(framestack) - 1
@@ -140,16 +137,11 @@
     virtualref_boxes = virtualref_boxes[:]
     if n >= 0:
         top = framestack[n]
+        pos = t.get_patchable_position()
         t.record_snapshot(top.jitcode, top.pc,
                           top.get_list_of_active_boxes(False))
-        #_ensure_parent_resumedata(framestack, n)
-        #frame_info_list = FrameInfo(top.parent_resumedata_frame_info_list,
-        #                            top.jitcode, top.pc)
-        #snapshot_storage.rd_frame_info_list = frame_info_list
-        #snapshot = Snapshot(top.parent_resumedata_snapshot,
-        #                    top.get_list_of_active_boxes(False))
-        #snapshot = TopSnapshot(snapshot, virtualref_boxes, virtualizable_boxes)
-        #snapshot_storage.rd_snapshot = snapshot
+        _ensure_parent_resumedata(framestack, n, t)
+        t.patch_position_to_current(pos)
     else:
         yyy
         snapshot_storage.rd_frame_info_list = None
diff --git a/rpython/jit/metainterp/test/test_opencoder.py b/rpython/jit/metainterp/test/test_opencoder.py
--- a/rpython/jit/metainterp/test/test_opencoder.py
+++ b/rpython/jit/metainterp/test/test_opencoder.py
@@ -11,14 +11,14 @@
         l = []
         while not iter.done():
             l.append(iter.next())
-        return iter.inputargs, l
+        return iter.inputargs, l, iter
 
     def test_simple_iterator(self):
         i0, i1 = InputArgInt(), InputArgInt()
         t = Trace([i0, i1])
         add = t.record_op(rop.INT_ADD, [i0, i1])
         t.record_op(rop.INT_ADD, [add, ConstInt(1)])
-        (i0, i1), l = self.unpack(t)
+        (i0, i1), l, _ = self.unpack(t)
         assert len(l) == 2
         assert l[0].opnum == rop.INT_ADD
         assert l[1].opnum == rop.INT_ADD
@@ -27,14 +27,26 @@
         assert l[0].getarg(0) is i0
         assert l[0].getarg(1) is i1
 
+    def unpack_snapshot(self, t, pos):
+        trace = t.trace
+        first = trace._ops[pos] # this is the size
+        pos += 1
+        boxes = []
+        while first > pos + 1:
+            snapshot_size = trace._ops[pos]
+            # 2 for jitcode and pc
+            pos += 1 + 2
+            boxes += [t._get(trace._ops[i + pos]) for i in range(snapshot_size)]
+            pos += len(boxes)
+        return boxes
+
     def test_rd_snapshot(self):
         class JitCode(object):
             def __init__(self, index):
                 self.index = index
 
         class FakeFrame(object):
-            parent_resumedata_frame_info_list = None
-            parent_resumedata_snapshot = None
+            parent_resumedata_position = -1
 
             def __init__(self, pc, jitcode, boxes):
                 self.pc = pc
@@ -49,11 +61,20 @@
         add = t.record_op(rop.INT_ADD, [i0, i1])
         t.record_op(rop.GUARD_FALSE, [add])
         # now we write rd_snapshot and friends
-        virtualizable_boxes = None
-        virutalref_boxes = []
-        framestack = [FakeFrame(1, JitCode(2), [i0, i1])]
-        resume.capture_resumedata(framestack, virtualizable_boxes,
-                                  virutalref_boxes, t)
-        (i0, i1), l = self.unpack(t)
+        frame0 = FakeFrame(1, JitCode(2), [i0, i1])
+        frame1 = FakeFrame(3, JitCode(4), [i0, i0, add])
+        framestack = [frame0]
+        resume.capture_resumedata(framestack, None, [], t)
+        (i0, i1), l, iter = self.unpack(t)
         assert l[1].opnum == rop.GUARD_FALSE
-        assert l[1].rd_snapshot.prev.boxes == [i0, i1]
+        boxes = self.unpack_snapshot(iter, l[1].rd_snapshot_position)
+        assert boxes == [i0, i1]
+        t.record_op(rop.GUARD_FALSE, [add])
+        resume.capture_resumedata([frame0, frame1], None, [], t)
+        (i0, i1), l, iter = self.unpack(t)
+        assert l[1].opnum == rop.GUARD_FALSE
+        boxes = self.unpack_snapshot(iter, l[1].rd_snapshot_position)
+        assert boxes == [i0, i1]
+        assert l[2].opnum == rop.GUARD_FALSE
+        boxes = self.unpack_snapshot(iter, l[2].rd_snapshot_position)
+        assert boxes == [i0, i0, l[0], i0, i1]


More information about the pypy-commit mailing list