[pypy-svn] r14965 - in pypy/dist/pypy/translator/llvm2: . test

ericvrp at codespeak.net ericvrp at codespeak.net
Sat Jul 23 23:33:33 CEST 2005


Author: ericvrp
Date: Sat Jul 23 23:33:32 2005
New Revision: 14965

Modified:
   pypy/dist/pypy/translator/llvm2/codewriter.py
   pypy/dist/pypy/translator/llvm2/funcnode.py
   pypy/dist/pypy/translator/llvm2/opwriter.py
   pypy/dist/pypy/translator/llvm2/test/test_exception.py
Log:
Starting to use invoke for last direct_call in 'try' block. Not finished yet.


Modified: pypy/dist/pypy/translator/llvm2/codewriter.py
==============================================================================
--- pypy/dist/pypy/translator/llvm2/codewriter.py	(original)
+++ pypy/dist/pypy/translator/llvm2/codewriter.py	Sat Jul 23 23:33:32 2005
@@ -98,6 +98,15 @@
         arglist = ["%s %s" % item for item in zip(argtypes, argrefs)]
         self.indent("call void %s(%s)" % (functionref, ", ".join(arglist)))
 
+    def invoke(self, targetvar, returntype, functionref, argrefs, argtypes, label, except_label):
+        arglist = ["%s %s" % item for item in zip(argtypes, argrefs)]
+        self.indent("%s = invoke %s %s(%s) to label %s except label %s" % (targetvar, returntype, functionref,
+                                             ", ".join(arglist), label, except_label))
+
+    def invoke_void(self, functionref, argrefs, argtypes, label, except_label):
+        arglist = ["%s %s" % item for item in zip(argtypes, argrefs)]
+        self.indent("invoke void %s(%s) to label %s except label %s" % (functionref, ", ".join(arglist), label, except_label))
+
     def cast(self, targetvar, fromtype, fromvar, targettype):
         self.indent("%(targetvar)s = cast %(fromtype)s "
                         "%(fromvar)s to %(targettype)s" % locals())

Modified: pypy/dist/pypy/translator/llvm2/funcnode.py
==============================================================================
--- pypy/dist/pypy/translator/llvm2/funcnode.py	(original)
+++ pypy/dist/pypy/translator/llvm2/funcnode.py	Sat Jul 23 23:33:32 2005
@@ -1,6 +1,6 @@
 import py
 from pypy.objspace.flow.model import Block, Constant, Variable, Link
-from pypy.objspace.flow.model import flatten, mkentrymap, traverse
+from pypy.objspace.flow.model import flatten, mkentrymap, traverse, last_exception
 from pypy.rpython import lltype
 from pypy.translator.backendoptimization import remove_same_as 
 from pypy.translator.unsimplify import remove_double_links                     
@@ -126,6 +126,12 @@
                 codewriter.phi(arg, type_, names, blocknames) 
 
     def write_block_branches(self, codewriter, block):
+
+        #BLOCK.EXITS[%fn]=3                        ['__class__', '__delattr__', '__doc__', '__getattribute__', '__hash__', '__init__', '__module__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__slots__', '__str__', 'at', 'closeblock', 'dead', 'exc_handler', 'exits', 'exitswitch', 'fillcolor', 'framestate', 'getconstants', 'getvariables', 'inputargs', 'isstartblock', 'operations', 'patchframe', 'recloseblock', 'renamevariables'
+        
+        print 'BLOCK.EXITS[%s], exitswitch=%s' % (self.ref, str(block.exitswitch))
+
+        #assert len(block.exits) <= 2    #more exits are possible (esp. in combination with exceptions)
         if len(block.exits) == 1:
             codewriter.br_uncond(self.block_to_name[block.exits[0].target])
         elif len(block.exits) == 2:
@@ -135,9 +141,18 @@
 
     def write_block_operations(self, codewriter, block):
         opwriter = OpWriter(self.db, codewriter)
-        for op in block.operations:
+        last_direct_call = -1
+        if block.exitswitch == Constant(last_exception):
+            for op_index, op in enumerate(block.operations):
+                if op.opname == 'direct_call':
+                    last_direct_call = op_index
+        for op_index, op in enumerate(block.operations):
             codewriter.comment(str(op), indent=True)
-            opwriter.write_operation(op)
+            opname = op.opname
+            if op_index == last_direct_call:
+                opname = 'direct_invoke'
+            opwriter.write_operation(op, opname)
+
     def write_startblock(self, codewriter, block):
         self.write_block_operations(codewriter, block)
         self.write_block_branches(codewriter, block)
@@ -162,10 +177,10 @@
         t = 'long'  #void*
         tmpvar = self.db.repr_tmpvar()
         codewriter.cast(tmpvar, inputargtypes[0], inputargs[0], t)
-        codewriter.store(t, tmpvar, 'last_exception_type')
+        codewriter.store(t, tmpvar, '%last_exception_type')
 
         tmpvar = self.db.repr_tmpvar()
         codewriter.cast(tmpvar, inputargtypes[1], inputargs[1], t)
-        codewriter.store(t, tmpvar, 'last_exception_value')
+        codewriter.store(t, tmpvar, '%last_exception_value')
 
         codewriter.unwind()

Modified: pypy/dist/pypy/translator/llvm2/opwriter.py
==============================================================================
--- pypy/dist/pypy/translator/llvm2/opwriter.py	(original)
+++ pypy/dist/pypy/translator/llvm2/opwriter.py	Sat Jul 23 23:33:32 2005
@@ -75,14 +75,16 @@
         self.db = db
         self.codewriter = codewriter
 
-    def write_operation(self, op):
-        if op.opname in self.binary_operations:
+    def write_operation(self, op, opname=None):
+        if not opname:
+            opname = op.opname
+        if opname in self.binary_operations:
             self.binaryop(op)
-        elif op.opname in self.shift_operations:
+        elif opname in self.shift_operations:
             self.shiftop(op)
         else:
-            meth = getattr(self, op.opname, None)
-            assert meth is not None, "operation %r not found" %(op.opname,)
+            meth = getattr(self, opname, None)
+            assert meth is not None, "operation %r not found" %(opname,)
             meth(op)    
 
     def int_neg(self, op): 
@@ -180,6 +182,19 @@
         else:
             self.codewriter.call_void(functionref, argrefs, argtypes)
 
+    def direct_invoke(self, op):
+        assert len(op.args) >= 1
+        targetvar = self.db.repr_arg(op.result)
+        returntype = self.db.repr_arg_type(op.result)
+        functionref = self.db.repr_arg(op.args[0])
+        argrefs = self.db.repr_arg_multi(op.args[1:])
+        argtypes = self.db.repr_arg_type_multi(op.args[1:])
+        if returntype != "void":
+            self.codewriter.invoke(targetvar, returntype, functionref, argrefs,
+                                 argtypes, 'PYPY_LABEL', 'PYPY_EXCEPT_LABEL')
+        else:
+            self.codewriter.invoke_void(functionref, argrefs, argtypes, 'PYPY_LABEL', 'PYPY_EXCEPT_LABEL')
+
     def malloc(self, op): 
         targetvar = self.db.repr_arg(op.result) 
         arg = op.args[0]

Modified: pypy/dist/pypy/translator/llvm2/test/test_exception.py
==============================================================================
--- pypy/dist/pypy/translator/llvm2/test/test_exception.py	(original)
+++ pypy/dist/pypy/translator/llvm2/test/test_exception.py	Sat Jul 23 23:33:32 2005
@@ -9,16 +9,20 @@
         self.n = n
 
 def test_simple1():
+    import time
     def raise_(i):
         if i:
             raise TestException()
         else:
-            return 1
+            return 3
     def fn(i):
         try:
-            return raise_(i)
+            a = time.time() + raise_(i) + 11
+            b = time.time() + raise_(i) + 12
+            c = time.time() + raise_(i) + 13
+            return a+b+c
         except TestException: 
-            return 0
+            return 7
     f = compile_function(fn, [int])
     assert f(0) == fn(0)
     assert f(1) == fn(1)



More information about the Pypy-commit mailing list