Author: Maciej Fijalkowski <[email protected]>
Branch: fast-slowpath
Changeset: r65370:ac2a867e421e
Date: 2013-07-12 13:30 +0200
http://bitbucket.org/pypy/pypy/changeset/ac2a867e421e/

Log:    Start a branch about conditional calls. implement a basic one-arg
        test and the llgraph backend

diff --git a/rpython/jit/backend/llgraph/runner.py 
b/rpython/jit/backend/llgraph/runner.py
--- a/rpython/jit/backend/llgraph/runner.py
+++ b/rpython/jit/backend/llgraph/runner.py
@@ -286,7 +286,7 @@
     def get_savedata_ref(self, deadframe):
         assert deadframe._saved_data is not None
         return deadframe._saved_data
-    
+
     # ------------------------------------------------------------
 
     def calldescrof(self, FUNC, ARGS, RESULT, effect_info):
@@ -334,7 +334,7 @@
         except KeyError:
             descr = InteriorFieldDescr(A, fieldname)
             self.descrs[key] = descr
-            return descr        
+            return descr
 
     def _calldescr_dynamic_for_tests(self, atypes, rtype,
                                      abiname='FFI_DEFAULT_ABI'):
@@ -802,7 +802,7 @@
         else:
             ovf = False
         self.overflow_flag = ovf
-        return z        
+        return z
 
     def execute_guard_no_overflow(self, descr):
         if self.overflow_flag:
@@ -821,6 +821,11 @@
         x = math.sqrt(y)
         return support.cast_to_floatstorage(x)
 
+    def execute_cond_call(self, calldescr, cond, func, *args):
+        if not cond:
+            return
+        self.execute_call(calldescr, func, *args)
+
     def execute_call(self, calldescr, func, *args):
         effectinfo = calldescr.get_extra_info()
         if effectinfo is not None and hasattr(effectinfo, 'oopspecindex'):
diff --git a/rpython/jit/backend/test/runner_test.py 
b/rpython/jit/backend/test/runner_test.py
--- a/rpython/jit/backend/test/runner_test.py
+++ b/rpython/jit/backend/test/runner_test.py
@@ -2266,6 +2266,40 @@
                     value |= 32768
                 assert s.data.tid == value
 
+    def test_cond_call(self):
+        called = []
+
+        def func_void(arg):
+            called.append(arg)
+
+        FUNC = self.FuncType([lltype.Signed], lltype.Void)
+        func_ptr = llhelper(lltype.Ptr(FUNC), func_void)
+        calldescr = self.cpu.calldescrof(FUNC, FUNC.ARGS, FUNC.RESULT,
+                                         EffectInfo.MOST_GENERAL)
+
+        ops = '''
+        [i0, i1, i2, i3, i4, i5, i6, f0, f1]
+        cond_call(i1, ConstClass(func_ptr), i2, descr=calldescr)
+        guard_false(i0, descr=faildescr) [i1, i2, i3, i4, i5, i6, f0, f1]
+        '''
+        loop = parse(ops, namespace={'faildescr': BasicFailDescr(),
+                                     'func_ptr': func_ptr,
+                                     'calldescr': calldescr})
+        looptoken = JitCellToken()
+        self.cpu.compile_loop(loop.inputargs, loop.operations, looptoken)
+        frame = self.cpu.execute_token(looptoken, 1, 0, 1, 2, 3, 4, 5, 1.2, 
3.4)
+        assert not called
+        for i in range(5):
+            assert self.cpu.get_int_value(frame, i) == i
+        assert self.cpu.get_float_value(frame, 6) == 1.2
+        assert self.cpu.get_float_value(frame, 7) == 3.4
+        frame = self.cpu.execute_token(looptoken, 1, 1, 1, 2, 3, 4, 5, 1.2, 
3.4)
+        assert called == [1]
+        for i in range(4):
+            assert self.cpu.get_int_value(frame, i + 1) == i + 1
+        assert self.cpu.get_float_value(frame, 6) == 1.2
+        assert self.cpu.get_float_value(frame, 7) == 3.4
+
     def test_force_operations_returning_void(self):
         values = []
         def maybe_force(token, flag):
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
@@ -149,6 +149,22 @@
         mc.RET()
         self._frame_realloc_slowpath = mc.materialize(self.cpu.asmmemmgr, [])
 
+    def _build_call_slowpath(self, no_args):
+        """ This builds a general call slowpath, for whatever call happens to
+        come.
+        """
+        mc = codebuf.MachineCodeBlockWrapper()
+        self._push_all_regs_to_frame(mc, [], self.cpu.supports_floats,
+                                     callee_only=False)
+        assert no_args == 1
+        mc.SUB(esp, imm(WORD))
+        # first arg is always in edi
+        mc.CALL()
+        mc.ADD(esp, imm(WORD))
+        self._pop_all_regs_from_frame(mc, [], self.cpu.supports_floats,
+                                      callee_only=False)
+        mc.RET()
+
     def _build_malloc_slowpath(self, kind):
         """ While arriving on slowpath, we have a gcpattern on stack 0.
         The arguments are passed in eax and edi, as follows:
diff --git a/rpython/jit/metainterp/resoperation.py 
b/rpython/jit/metainterp/resoperation.py
--- a/rpython/jit/metainterp/resoperation.py
+++ b/rpython/jit/metainterp/resoperation.py
@@ -518,6 +518,7 @@
     '_CANRAISE_FIRST', # ----- start of can_raise operations -----
     '_CALL_FIRST',
     'CALL/*d',
+    'COND_CALL/*d', # a conditional call, with first argument as a condition
     'CALL_ASSEMBLER/*d',  # call already compiled assembler
     'CALL_MAY_FORCE/*d',
     'CALL_LOOPINVARIANT/*d',
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to