Author: Maciej Fijalkowski <fij...@gmail.com>
Branch: jitframe-on-heap
Changeset: r60541:cf0aed3ee46e
Date: 2013-01-27 22:21 +0200
http://bitbucket.org/pypy/pypy/changeset/cf0aed3ee46e/

Log:    implement rewriting of frame malloc

diff --git a/rpython/jit/backend/llsupport/gc.py 
b/rpython/jit/backend/llsupport/gc.py
--- a/rpython/jit/backend/llsupport/gc.py
+++ b/rpython/jit/backend/llsupport/gc.py
@@ -122,6 +122,8 @@
         for name in ['jf_descr', 'jf_guard_exc', 'jf_force_descr',
                      'jf_frame_info', 'jf_gcmap']:
             setattr(descrs, name, cpu.fielddescrof(jitframe.JITFRAME, name))
+        descrs.jfi_frame_size = cpu.fielddescrof(jitframe.JITFRAMEINFO,
+                                                  'jfi_frame_size')
         descrs.jfi_frame_depth = cpu.fielddescrof(jitframe.JITFRAMEINFO,
                                                   'jfi_frame_depth')
         return descrs
diff --git a/rpython/jit/backend/llsupport/jitframe.py 
b/rpython/jit/backend/llsupport/jitframe.py
--- a/rpython/jit/backend/llsupport/jitframe.py
+++ b/rpython/jit/backend/llsupport/jitframe.py
@@ -14,10 +14,19 @@
 GCMAP = lltype.GcArray(lltype.Unsigned)
 NULLGCMAP = lltype.nullptr(GCMAP)
 
+def jitframeinfo_set_depth(jfi, new_depth):
+    jfi.jfi_frame_depth = new_depth
+    jfi.jfi_frame_size = STATICSIZE + new_depth * SIZEOFSIGNED
+
 JITFRAMEINFO = lltype.GcStruct(
     'JITFRAMEINFO',
-    # the depth of frame
+    # the depth of the frame
     ('jfi_frame_depth', lltype.Signed),
+    # the total size of the frame, in bytes
+    ('jfi_frame_size', lltype.Signed),
+    adtmeths = {
+        'set_frame_depth': jitframeinfo_set_depth,
+    },
 )
 
 NULLFRAMEINFO = lltype.nullptr(JITFRAMEINFO)
diff --git a/rpython/jit/backend/llsupport/rewrite.py 
b/rpython/jit/backend/llsupport/rewrite.py
--- a/rpython/jit/backend/llsupport/rewrite.py
+++ b/rpython/jit/backend/llsupport/rewrite.py
@@ -137,22 +137,42 @@
             else:
                 raise NotImplementedError(op.getopname())
 
+    def gen_malloc_frame(self, frame_info, frame, size_box):
+        descrs = self.gc_ll_descr.getframedescrs(self.cpu)
+        if self.gc_ll_descr.kind == 'boehm':
+            op0 = ResOperation(rop.GETFIELD_GC, [history.ConstPtr(frame_info)],
+                               size_box,
+                               descr=descrs.jfi_frame_depth)
+            self.newops.append(op0)
+            op1 = ResOperation(rop.NEW_ARRAY, [size_box], frame,
+                               descr=descrs.arraydescr)
+            self.handle_new_array(descrs.arraydescr, op1)
+        else:
+            # we read size in bytes here, not the length
+            op0 = ResOperation(rop.GETFIELD_GC, [history.ConstPtr(frame_info)],
+                               size_box,
+                               descr=descrs.jfi_frame_size)
+            self.newops.append(op0)
+            self.gen_malloc_nursery_varsize(size_box, frame, is_small=True)
+            self.gen_initialize_tid(frame, descrs.arraydescr.tid)
+            length_box = history.BoxInt()
+            op1 = ResOperation(rop.GETFIELD_GC, [history.ConstPtr(frame_info)],
+                               length_box,
+                               descr=descrs.jfi_frame_depth)
+            self.newops.append(op1)
+            self.gen_initialize_len(frame, length_box,
+                                    descrs.arraydescr.lendescr)
+
     def handle_call_assembler(self, op):
         descrs = self.gc_ll_descr.getframedescrs(self.cpu)
         loop_token = op.getdescr()
         assert isinstance(loop_token, history.JitCellToken)
-        lgt_box = history.BoxInt()
-        frame = history.BoxPtr()
         jfi = loop_token.compiled_loop_token.frame_info
         llref = lltype.cast_opaque_ptr(llmemory.GCREF, jfi)
         rgc._make_sure_does_not_move(llref)
-        op0 = ResOperation(rop.GETFIELD_GC, [history.ConstPtr(llref)], lgt_box,
-                           descr=descrs.jfi_frame_depth)
-        self.newops.append(op0)
-
-        op1 = ResOperation(rop.NEW_ARRAY, [lgt_box], frame,
-                           descr=descrs.arraydescr)
-        self.handle_new_array(descrs.arraydescr, op1)
+        size_box = history.BoxInt()
+        frame = history.BoxPtr()
+        self.gen_malloc_frame(llref, frame, size_box)
         op2 = ResOperation(rop.SETFIELD_GC, [frame, history.ConstPtr(llref)],
                            None, descr=descrs.jf_frame_info)
         self.newops.append(op2)
@@ -258,6 +278,18 @@
         self._gen_call_malloc_gc([ConstInt(addr), v_num_elem], v_result,
                                  self.gc_ll_descr.malloc_unicode_descr)
 
+    def gen_malloc_nursery_varsize(self, sizebox, v_result, is_small=False):
+        """ Generate CALL_MALLOC_NURSERY_VARSIZE_SMALL
+        """
+        assert is_small
+        self.emitting_an_operation_that_can_collect()
+        op = ResOperation(rop.CALL_MALLOC_NURSERY_VARSIZE_SMALL,
+                          [sizebox],
+                          v_result)
+
+        self.newops.append(op)
+        self.recent_mallocs[v_result] = None
+
     def gen_malloc_nursery(self, size, v_result):
         """Try to generate or update a CALL_MALLOC_NURSERY.
         If that fails, generate a plain CALL_MALLOC_GC instead.
diff --git a/rpython/jit/backend/llsupport/test/test_rewrite.py 
b/rpython/jit/backend/llsupport/test/test_rewrite.py
--- a/rpython/jit/backend/llsupport/test/test_rewrite.py
+++ b/rpython/jit/backend/llsupport/test/test_rewrite.py
@@ -76,8 +76,11 @@
         ll_frame_info = lltype.cast_opaque_ptr(llmemory.GCREF, frame_info)
         clt.frame_info = frame_info
         frame_info.jfi_frame_depth = 13
+        frame_info.jfi_frame_size = 255
         framedescrs = self.gc_ll_descr.getframedescrs(self.cpu)
+        framelendescr = framedescrs.arraydescr.lendescr
         jfi_frame_depth = framedescrs.jfi_frame_depth
+        jfi_frame_size = framedescrs.jfi_frame_size
         jf_frame_info = framedescrs.jf_frame_info
         signedframedescr = self.cpu.signedframedescr
         floatframedescr = self.cpu.floatframedescr
@@ -737,12 +740,13 @@
         i2 = call_assembler(i0, f0, descr=casmdescr)
         """, """
         [i0, f0]
-        i1 = getfield_gc(ConstPtr(ll_frame_info), descr=jfi_frame_depth)
-        p1 = call_malloc_nursery(13)
+        i1 = getfield_gc(ConstPtr(ll_frame_info), descr=jfi_frame_size)
+        p1 = call_malloc_nursery_varsize_small(i1)
+        setfield_gc(p1, 0, descr=tiddescr)
+        i2 = getfield_gc(ConstPtr(ll_frame_info), descr=jfi_frame_depth)
+        setfield_gc(p1, i2, descr=framelendescr)
         setfield_gc(p1, ConstPtr(ll_frame_info), descr=jf_frame_info)
         setarrayitem_gc(p1, 0, i0, descr=signedframedescr)
         setarrayitem_gc(p1, 1, f0, descr=floatframedescr)
-        i2 = call_assembler(p1, descr=casmdescr)
+        i3 = call_assembler(p1, descr=casmdescr)
         """)
-        # XXX we want call_malloc_nursery actually, but let's not care
-        # for now, the array is a bit non-standard
diff --git a/rpython/jit/backend/x86/assembler.py 
b/rpython/jit/backend/x86/assembler.py
--- a/rpython/jit/backend/x86/assembler.py
+++ b/rpython/jit/backend/x86/assembler.py
@@ -507,7 +507,7 @@
         clt = CompiledLoopToken(self.cpu, looptoken.number)
         clt.frame_info = lltype.malloc(jitframe.JITFRAMEINFO)
         clt.allgcrefs = []
-        clt.frame_info.jfi_frame_depth = 0 # for now
+        clt.frame_info.set_frame_depth(0) # for now
         looptoken.compiled_loop_token = clt
         clt._debug_nbargs = len(inputargs)
         if not we_are_translated():
@@ -666,13 +666,13 @@
                 mc.copy_to_raw_memory(rawstart + pos_after_jz - 4)
 
     def update_frame_depth(self, frame_depth):
-        self.current_clt.frame_info.jfi_frame_depth = frame_depth
+        self.current_clt.frame_info.set_frame_depth(frame_depth)
         new_jumping_to = []
         for wref in self.current_clt.jumping_to:
             clt = wref()
             if clt is not None:
-                clt.frame_info.jfi_frame_depth = max(frame_depth,
-                    clt.frame_info.jfi_frame_depth)
+                clt.frame_info.set_frame_depth(max(frame_depth,
+                    clt.frame_info.jfi_frame_depth))
                 new_jumping_to.append(weakref.ref(clt))
         self.current_clt.jumping_to = new_jumping_to
 
@@ -898,7 +898,7 @@
         # copy frame-info data
         old_fi = oldlooptoken.compiled_loop_token.frame_info
         new_fi = newlooptoken.compiled_loop_token.frame_info
-        old_fi.jfi_frame_depth = new_fi.jfi_frame_depth
+        old_fi.set_frame_depth(new_fi.jfi_frame_depth)
         mc = codebuf.MachineCodeBlockWrapper()
         mc.JMP(imm(target))
         if WORD == 4:         # keep in sync with prepare_loop()
diff --git a/rpython/jit/backend/x86/test/test_gc_integration.py 
b/rpython/jit/backend/x86/test/test_gc_integration.py
--- a/rpython/jit/backend/x86/test/test_gc_integration.py
+++ b/rpython/jit/backend/x86/test/test_gc_integration.py
@@ -451,6 +451,8 @@
             setattr(descrs, name, cpu.fielddescrof(JITFRAME, name))
         descrs.jfi_frame_depth = cpu.fielddescrof(jitframe.JITFRAMEINFO,
                                                   'jfi_frame_depth')
+        descrs.jfi_frame_size = cpu.fielddescrof(jitframe.JITFRAMEINFO,
+                                                  'jfi_frame_size')
         return descrs
 
     def do_write_barrier(self, gcref_struct, gcref_newptr):
diff --git a/rpython/jit/backend/x86/test/test_zrpy_gc.py 
b/rpython/jit/backend/x86/test/test_zrpy_gc.py
--- a/rpython/jit/backend/x86/test/test_zrpy_gc.py
+++ b/rpython/jit/backend/x86/test/test_zrpy_gc.py
@@ -790,5 +790,11 @@
     def test_compile_framework_minimal_size_in_nursery(self):
         self.run('compile_framework_minimal_size_in_nursery')
 
+    #def define_compile_framework_call_assembler(self):
+    #    xxx
+
+    #def test_compile_framework_call_assembler(self):
+    #    self.run('compile_framework_call_assembler')
+
 class TestShadowStack(CompileFrameworkTests):
     gcrootfinder = "shadowstack"
diff --git a/rpython/jit/metainterp/executor.py 
b/rpython/jit/metainterp/executor.py
--- a/rpython/jit/metainterp/executor.py
+++ b/rpython/jit/metainterp/executor.py
@@ -354,6 +354,7 @@
                          rop.QUASIIMMUT_FIELD,
                          rop.CALL_MALLOC_GC,
                          rop.CALL_MALLOC_NURSERY,
+                         rop.CALL_MALLOC_NURSERY_VARSIZE_SMALL,
                          rop.LABEL,
                          ):      # list of opcodes never executed by pyjitpl
                 continue
_______________________________________________
pypy-commit mailing list
pypy-commit@python.org
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to