[pypy-svn] r14297 - in pypy/dist/pypy/rpython: . test

pedronis at codespeak.net pedronis at codespeak.net
Tue Jul 5 17:07:03 CEST 2005


Author: pedronis
Date: Tue Jul  5 17:06:59 2005
New Revision: 14297

Modified:
   pypy/dist/pypy/rpython/extfunctable.py
   pypy/dist/pypy/rpython/llinterp.py
   pypy/dist/pypy/rpython/rbuiltin.py
   pypy/dist/pypy/rpython/rtyper.py
   pypy/dist/pypy/rpython/test/test_rbuiltin.py
Log:
implemented rtyping support for external functions with a testing-only ll_function that cannot be annotated.



Modified: pypy/dist/pypy/rpython/extfunctable.py
==============================================================================
--- pypy/dist/pypy/rpython/extfunctable.py	(original)
+++ pypy/dist/pypy/rpython/extfunctable.py	Tue Jul  5 17:06:59 2005
@@ -24,12 +24,16 @@
     table[func] = ExtFuncInfo(func, annotation, ll_function, ll_annotable)
 
 # low-level helpers representing the external functions
+def ll_os_open(fname, mode):
+    return os.open(''.join(fname.chars), mode)
+
 def ll_os_getuid():
-    return 1 #return os.getuid()
+    return os.getuid()
 
 def ll_os_dup(fd):
     return 999
 
 # external function declarations
-declare(os.getuid, int, ll_os_getuid, ll_annotable=True)
+declare(os.open, int, ll_os_open, ll_annotable=False)
+declare(os.getuid, int, ll_os_getuid, ll_annotable=False)
 declare(os.dup, int, ll_os_dup, ll_annotable=True)

Modified: pypy/dist/pypy/rpython/llinterp.py
==============================================================================
--- pypy/dist/pypy/rpython/llinterp.py	(original)
+++ pypy/dist/pypy/rpython/llinterp.py	Tue Jul  5 17:06:59 2005
@@ -169,7 +169,11 @@
         if hasattr(f._obj, 'graph'):
             graph = f._obj.graph
         else:
-            graph = self.llinterpreter.getgraph(f._obj._callable)
+            try:
+                graph = self.llinterpreter.getgraph(f._obj._callable)
+            except KeyError:
+                assert hasattr(f._obj, '_callable'), "don't know how to execute %r" % f
+                return f._obj._callable(*args)
         frame = self.__class__(graph, args, self.llinterpreter)
         return frame.eval()
 

Modified: pypy/dist/pypy/rpython/rbuiltin.py
==============================================================================
--- pypy/dist/pypy/rpython/rbuiltin.py	(original)
+++ pypy/dist/pypy/rpython/rbuiltin.py	Tue Jul  5 17:06:59 2005
@@ -248,9 +248,15 @@
     ll_function = extfuncinfo.ll_function
     if extfuncinfo.ll_annotable:
         def rtype_extfunc(hop):
-            return hop.gendirectcall(ll_function, *hop.args_v)
+            vars = hop.inputargs(*hop.args_r)
+            return hop.gendirectcall(ll_function, *vars)
     else:
-        assert False, "xxx not implemented"
+        def rtype_extfunc(hop):
+            resulttype = hop.r_result
+            vars = hop.inputargs(*hop.args_r)
+            return hop.llops.genexternalcall(ll_function.__name__, vars, resulttype=resulttype,
+                                             _callable = ll_function)
+            
     return sourcetools.func_with_new_name(rtype_extfunc,
                                           "rtype_extfunc_%s" % extfuncinfo.func.__name__)
 

Modified: pypy/dist/pypy/rpython/rtyper.py
==============================================================================
--- pypy/dist/pypy/rpython/rtyper.py	(original)
+++ pypy/dist/pypy/rpython/rtyper.py	Tue Jul  5 17:06:59 2005
@@ -521,15 +521,17 @@
         return self.genop('direct_call', [c]+list(args_v),
                           resulttype = typeOf(f).TO.RESULT)
 
-    def gencapicall(self, cfnname, args_v, resulttype=None, **flags):
+    def genexternalcall(self, fnname, args_v, resulttype=None, **flags):
         if isinstance(resulttype, Repr):
             resulttype = resulttype.lowleveltype
         argtypes = [v.concretetype for v in args_v]
         FUNCTYPE = FuncType(argtypes, resulttype or Void)
-        f = functionptr(FUNCTYPE, cfnname, external="C", **flags)
+        f = functionptr(FUNCTYPE, fnname, **flags)
         cf = inputconst(typeOf(f), f)
         return self.genop('direct_call', [cf]+list(args_v), resulttype)
 
+    def gencapicall(self, cfnname, args_v, resulttype=None, **flags):
+        return genexternalcall(cfname, args_v, resulttype=resulttype, external="C")
 
 # _______________________________________________________________________
 # this has the side-effect of registering the unary and binary operations

Modified: pypy/dist/pypy/rpython/test/test_rbuiltin.py
==============================================================================
--- pypy/dist/pypy/rpython/test/test_rbuiltin.py	(original)
+++ pypy/dist/pypy/rpython/test/test_rbuiltin.py	Tue Jul  5 17:06:59 2005
@@ -1,6 +1,7 @@
 from pypy.rpython.test.test_llinterp import interpret
 from pypy.rpython.test import test_llinterp
 from pypy.objspace.flow import model as flowmodel
+from pypy.tool import udir
 
 from pypy.annotation.builtin import *
 import py
@@ -63,12 +64,24 @@
             ry = 100 * float(i-10) +0.1
             assert fn(rv,ry) == interpret(fn, (rv, ry))
 
-def DONOT_test_os_getuid():
+def enum_direct_calls(translator, func):
+    blocks = []
+    graph = translator.getflowgraph(func)
+    def visit(block):
+        if isinstance(block, flowmodel.Block):
+            blocks.append(block)
+    flowmodel.traverse(visit, graph)
+    for block in blocks:
+        for op in block.operations:
+            if op.opname == 'direct_call':
+                yield op
+
+def test_os_getuid():
     import os
     def fn():
         return os.getuid()
     assert interpret(fn, []) == fn()
-
+        
 def test_os_dup():
     import os
     def fn(fd):
@@ -78,20 +91,31 @@
     #    os.close(res)
     #except OSError:
     #    pass
-    t = test_llinterp.typer.annotator.translator
-    graph = t.getflowgraph(fn)
-    count = [0]
-    def visit(block):
-        from pypy.rpython import extfunctable
-        if isinstance(block, flowmodel.Block):
-            for op in block.operations:
-                if op.opname == 'direct_call':
-                    cfptr = op.args[0]
-                    assert cfptr.value._obj._callable == extfunctable.ll_os_dup
-                    count[0] += 1
-    flowmodel.traverse(visit, graph)
-    assert count[0] == 1
+    count = 0
+    from pypy.rpython import extfunctable
+    for dir_call in enum_direct_calls(test_llinterp.typer.annotator.translator, fn):
+        cfptr = dir_call.args[0]
+        assert cfptr.value._obj._callable == extfunctable.ll_os_dup
+        count += 1
+    assert count == 1
 
+def test_os_open():
+    tmpdir = str(udir.udir.join("os_open_test"))
+    import os
+    def wr_open(fname):
+        return os.open(fname, os.O_WRONLY|os.O_CREAT)
+    def f():
+        return wr_open(tmpdir)
+    res = interpret(f, [])
+    os.close(res)
+    count = 0
+    from pypy.rpython import extfunctable
+    for dir_call in enum_direct_calls(test_llinterp.typer.annotator.translator, wr_open):
+        cfptr = dir_call.args[0]
+        assert cfptr.value._obj._callable == extfunctable.ll_os_open
+        count += 1
+    assert count == 1
+        
 def test_pbc_isTrue():
     class C:
         def f(self):



More information about the Pypy-commit mailing list