[pypy-svn] r37329 - in pypy/dist/pypy/jit/codegen: . dump i386/test llgraph/test llvm/test ppc/test test

arigo at codespeak.net arigo at codespeak.net
Thu Jan 25 14:26:20 CET 2007


Author: arigo
Date: Thu Jan 25 14:26:17 2007
New Revision: 37329

Modified:
   pypy/dist/pypy/jit/codegen/dump/rgenop.py
   pypy/dist/pypy/jit/codegen/i386/test/test_rgenop.py
   pypy/dist/pypy/jit/codegen/llgraph/test/test_rgenop.py
   pypy/dist/pypy/jit/codegen/llvm/test/test_rgenop.py
   pypy/dist/pypy/jit/codegen/model.py
   pypy/dist/pypy/jit/codegen/ppc/test/test_rgenop.py
   pypy/dist/pypy/jit/codegen/test/rgenop_tests.py
Log:
Made the frame_var part of the interface "official", by moving the tests
to rgenop_tests.  Skipped on real backends for now.


Modified: pypy/dist/pypy/jit/codegen/dump/rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/dump/rgenop.py	(original)
+++ pypy/dist/pypy/jit/codegen/dump/rgenop.py	Thu Jan 25 14:26:17 2007
@@ -240,6 +240,21 @@
     def log(self, msg):
         self.rgenop.dump('# log: %s' % (msg,))
 
+    def genop_get_frame_base(self):
+        v = self.llbuilder.genop_get_frame_base()
+        self.dump("%s = %s.genop_get_frame_base()" % (
+            self.rgenop.vname(v),
+            self.name))
+        return v
+
+    def get_frame_info(self, vars_gv):
+        info = self.llbuilder.get_frame_info(vars_gv)
+        self.dump("%r = %s.get_frame_info([%s])" % (
+            info,
+            self.name,
+            self.rgenop.vlistname(vars_gv)))
+        return info
+
 
 class RDumpGenOp(llrgenop.RGenOp):
 
@@ -355,4 +370,14 @@
             self.kindtokensname(kinds)))
         return b, args_gv
 
+    @staticmethod
+    @specialize.arg(0)
+    def read_frame_var(T, base, info, index):
+        XXX
+
+    @staticmethod
+    @specialize.arg(0)
+    def write_frame_var(T, base, info, index, value):
+        XXX
+
 kindtokennames = {}

Modified: pypy/dist/pypy/jit/codegen/i386/test/test_rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/i386/test/test_rgenop.py	(original)
+++ pypy/dist/pypy/jit/codegen/i386/test/test_rgenop.py	Thu Jan 25 14:26:17 2007
@@ -1,3 +1,4 @@
+import py
 from pypy.rpython.lltypesystem import lltype
 from pypy.jit.codegen.i386.rgenop import RI386GenOp
 from pypy.jit.codegen.test.rgenop_tests import AbstractRGenOpTests
@@ -49,3 +50,8 @@
         fnptr = self.cast(gv_callable, 3)
         res = fnptr(21, -21, 0)
         assert res == 42
+
+    def test_read_frame_var_direct(self):   py.test.skip("in-progress")
+    def test_read_frame_var_compile(self):  py.test.skip("in-progress")
+    def test_write_frame_var_direct(self):  py.test.skip("in-progress")
+    def test_write_frame_var_compile(self): py.test.skip("in-progress")

Modified: pypy/dist/pypy/jit/codegen/llgraph/test/test_rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/llgraph/test/test_rgenop.py	(original)
+++ pypy/dist/pypy/jit/codegen/llgraph/test/test_rgenop.py	Thu Jan 25 14:26:17 2007
@@ -1,5 +1,5 @@
 import py
-from pypy.rpython.lltypesystem import lltype, llmemory
+from pypy.rpython.lltypesystem import lltype
 from pypy.jit.codegen.llgraph.rgenop import RGenOp
 from pypy.jit.codegen.llgraph.llimpl import testgengraph
 from pypy.jit.codegen.test.rgenop_tests import AbstractRGenOpTests
@@ -21,78 +21,16 @@
             return interpret(runner, args, policy=annotatorpolicy)
         return quasi_compiled_runner
 
+    def directtesthelper(self, FUNC, func):
+        from pypy.annotation import model as annmodel
+        argtypes = [annmodel.lltype_to_annotation(T) for T in FUNC.TO.ARGS]
+        t, rtyper, graph = gengraph(func, argtypes)
+        return rtyper.getcallable(graph)
+
     # for the individual tests see
     # ====> ../../test/rgenop_tests.py
 
 
-def test_read_frame_var():
-    from pypy.annotation import model as annmodel
-
-    def reader(base, info):
-        return RGenOp.read_frame_var(lltype.Signed, base, info, 0)
-
-    t, rtyper, reader_graph = gengraph(reader,
-                                       [annmodel.SomeAddress(),
-                                        annmodel.SomePtr(llmemory.GCREF)])
-    reader_ptr = rtyper.getcallable(reader_graph)
-
-    F1 = lltype.FuncType([lltype.Signed], lltype.Signed)
-    rgenop = RGenOp()
-    signed_kind = rgenop.kindToken(lltype.Signed)
-    sigtoken = rgenop.sigToken(F1)
-    gv_reader = RGenOp.constPrebuiltGlobal(reader_ptr)
-    readertoken = rgenop.sigToken(lltype.typeOf(reader_ptr).TO)
-
-    builder, gv_f, [gv_x] = rgenop.newgraph(sigtoken, "f")
-    builder.start_writing()
-
-    gv_y = builder.genop2("int_mul", gv_x, rgenop.genconst(2))
-    gv_base = builder.genop_get_frame_base()
-    info = builder.get_frame_info([gv_y])
-    gv_info = RGenOp.constPrebuiltGlobal(info)
-    gv_z = builder.genop_call(readertoken, gv_reader, [gv_base, gv_info])
-    builder.finish_and_return(sigtoken, gv_z)
-    builder.end()
-
-    ptr = gv_f.revealconst(lltype.Ptr(F1))
-    res = testgengraph(ptr._obj.graph, [21])
-    assert res == 42
-
-def test_write_frame_var():
-    from pypy.annotation import model as annmodel
-
-    def writer(base, info, value):
-        RGenOp.write_frame_var(lltype.Signed, base, info, 0, value)
-
-    t, rtyper, writer_graph = gengraph(writer,
-                                       [annmodel.SomeAddress(),
-                                        annmodel.SomePtr(llmemory.GCREF),
-                                        annmodel.SomeInteger()])
-    writer_ptr = rtyper.getcallable(writer_graph)
-
-    F1 = lltype.FuncType([lltype.Signed], lltype.Signed)
-    rgenop = RGenOp()
-    signed_kind = rgenop.kindToken(lltype.Signed)
-    sigtoken = rgenop.sigToken(F1)
-    gv_writer = RGenOp.constPrebuiltGlobal(writer_ptr)
-    writertoken = rgenop.sigToken(lltype.typeOf(writer_ptr).TO)
-
-    builder, gv_f, [gv_x] = rgenop.newgraph(sigtoken, "f")
-    builder.start_writing()
-
-    gv_y = builder.genop_same_as(signed_kind, rgenop.genconst(0))
-    gv_base = builder.genop_get_frame_base()
-    info = builder.get_frame_info([gv_y])
-    gv_info = RGenOp.constPrebuiltGlobal(info)
-    gv_42 = rgenop.genconst(42)
-    builder.genop_call(writertoken, gv_writer, [gv_base, gv_info, gv_42])
-    builder.finish_and_return(sigtoken, gv_y)
-    builder.end()
-
-    ptr = gv_f.revealconst(lltype.Ptr(F1))
-    res = testgengraph(ptr._obj.graph, [-1])
-    assert res == 42
-
 def test_not_calling_end_explodes():
     F1 = lltype.FuncType([lltype.Signed], lltype.Signed)
     rgenop = RGenOp()

Modified: pypy/dist/pypy/jit/codegen/llvm/test/test_rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/llvm/test/test_rgenop.py	(original)
+++ pypy/dist/pypy/jit/codegen/llvm/test/test_rgenop.py	Thu Jan 25 14:26:17 2007
@@ -24,3 +24,8 @@
         test_goto_compile = skip_too_minimal #segfault
         test_fact_direct = skip_too_minimal #segfault
         test_fact_compile= skip_too_minimal #segfault
+
+    test_read_frame_var_direct   = skip
+    test_read_frame_var_compile  = skip
+    test_write_frame_var_direct  = skip
+    test_write_frame_var_compile = skip

Modified: pypy/dist/pypy/jit/codegen/model.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/model.py	(original)
+++ pypy/dist/pypy/jit/codegen/model.py	Thu Jan 25 14:26:17 2007
@@ -176,11 +176,21 @@
     # read frame var support
     
     def genop_get_frame_base(self):
-        pass
+        '''Generate an operation that reads the current stack frame pointer.
+        The pointer can later be passed to read_frame_var() and
+        write_frame_var().  This returns a GenVar.
+        '''
+        raise NotImplementedError
+
+    def get_frame_info(self, vars_gv):
+        '''Return a constant object that describes where the variables are
+        inside the stack frame.  The result should be correct for the
+        current basic block.  Clearly, it forces the listed variables to
+        live in the stack instead of being allocated to registers.
+        '''
+        raise NotImplementedError
+
 
-    def get_frame_info(self, vars):
-        pass
-        
 class GenLabel(object):
     '''A "smart" label.  Represents an address of the start of a basic
     block and the location of the inputargs on entry to that block.'''
@@ -285,6 +295,21 @@
     #    """Return a token describing the signature of FUNCTYPE."""
     #    raise NotImplementedError
 
+    #@staticmethod
+    #@specialize.arg(0)
+    #def read_frame_var(T, base, info, index):
+    #    """Read from the stack frame of a caller.  The 'base' is the
+    #    frame stack pointer captured by the operation generated by
+    #    genop_get_frame_base().  The 'info' is the object returned by
+    #    get_frame_info(); we are looking for the index-th variable
+    #    in the list passed to get_frame_info()."""
+
+    #@staticmethod
+    #@specialize.arg(0)
+    #def write_frame_var(T, base, info, index, value):
+    #    """Write into the stack frame of a caller.
+    #    See read_frame_var()."""
+
 
 class CodeGenSwitch(object):
     '''A CodeGenSwitch is a flexible switch on a given GenVar that can have cases added

Modified: pypy/dist/pypy/jit/codegen/ppc/test/test_rgenop.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/ppc/test/test_rgenop.py	(original)
+++ pypy/dist/pypy/jit/codegen/ppc/test/test_rgenop.py	Thu Jan 25 14:26:17 2007
@@ -20,3 +20,8 @@
 
     def compile(self, runner, argtypes):
         py.test.skip("Skip compiled tests w/ restricted register allocator")
+
+    def test_read_frame_var_direct(self):   py.test.skip("in-progress")
+    def test_read_frame_var_compile(self):  py.test.skip("in-progress")
+    def test_write_frame_var_direct(self):  py.test.skip("in-progress")
+    def test_write_frame_var_compile(self): py.test.skip("in-progress")

Modified: pypy/dist/pypy/jit/codegen/test/rgenop_tests.py
==============================================================================
--- pypy/dist/pypy/jit/codegen/test/rgenop_tests.py	(original)
+++ pypy/dist/pypy/jit/codegen/test/rgenop_tests.py	Thu Jan 25 14:26:17 2007
@@ -1,7 +1,7 @@
 import random
-from pypy.rpython.annlowlevel import MixLevelAnnotatorPolicy
+from pypy.rpython.annlowlevel import MixLevelAnnotatorPolicy, llhelper
 from pypy.rlib.objectmodel import keepalive_until_here
-from pypy.rpython.lltypesystem import lltype
+from pypy.rpython.lltypesystem import lltype, llmemory
 from pypy.translator.c.test import test_boehm
 from ctypes import c_void_p, cast, CFUNCTYPE, c_int
 
@@ -617,6 +617,80 @@
 
     return gv_callable
 
+FRAME_VAR_READER = lltype.Ptr(lltype.FuncType([llmemory.Address,
+                                               llmemory.GCREF],
+                                              lltype.Signed))
+FRAME_VAR_WRITER = lltype.Ptr(lltype.FuncType([llmemory.Address,
+                                               llmemory.GCREF,
+                                               lltype.Signed],
+                                              lltype.Void))
+
+def make_read_frame_var(rgenop, reader_ptr):
+    signed_kind = rgenop.kindToken(lltype.Signed)
+    sigtoken = rgenop.sigToken(FUNC)
+    gv_reader = rgenop.constPrebuiltGlobal(reader_ptr)
+    readertoken = rgenop.sigToken(FRAME_VAR_READER.TO)
+
+    builder, gv_f, [gv_x] = rgenop.newgraph(sigtoken, "f")
+    builder.start_writing()
+
+    gv_y = builder.genop2("int_mul", gv_x, rgenop.genconst(2))
+    gv_base = builder.genop_get_frame_base()
+    info = builder.get_frame_info([gv_y])
+    gv_info = rgenop.genconst(info)
+    gv_z = builder.genop_call(readertoken, gv_reader, [gv_base, gv_info])
+    builder.finish_and_return(sigtoken, gv_z)
+    builder.end()
+
+    return gv_f
+
+def get_read_frame_var_runner(RGenOp):
+    def reader(base, info):
+        return RGenOp.read_frame_var(lltype.Signed, base, info, 0) + 2
+
+    def read_frame_var_runner(x):
+        rgenop = RGenOp()
+        gv_f = make_read_frame_var(rgenop, llhelper(FRAME_VAR_READER, reader))
+        fn = gv_f.revealconst(lltype.Ptr(FUNC))
+        res = fn(x)
+        keepalive_until_here(rgenop)    # to keep the code blocks alive
+        return res
+    return read_frame_var_runner
+
+def make_write_frame_var(rgenop, writer_ptr):
+    signed_kind = rgenop.kindToken(lltype.Signed)
+    sigtoken = rgenop.sigToken(FUNC)
+    gv_writer = rgenop.constPrebuiltGlobal(writer_ptr)
+    writertoken = rgenop.sigToken(FRAME_VAR_WRITER.TO)
+
+    builder, gv_f, [gv_x] = rgenop.newgraph(sigtoken, "f")
+    builder.start_writing()
+
+    gv_y = builder.genop_same_as(signed_kind, rgenop.genconst(0))
+    gv_base = builder.genop_get_frame_base()
+    info = builder.get_frame_info([gv_y])
+    gv_info = rgenop.constPrebuiltGlobal(info)
+    gv_42 = rgenop.genconst(42)
+    builder.genop_call(writertoken, gv_writer, [gv_base, gv_info, gv_42])
+    builder.finish_and_return(sigtoken, gv_y)
+    builder.end()
+
+    return gv_f
+
+def get_write_frame_var_runner(RGenOp):
+    def writer(base, info, value):
+        RGenOp.write_frame_var(lltype.Signed, base, info, 0, value)
+
+    def write_frame_var_runner(x):
+        rgenop = RGenOp()
+        gv_f = make_write_frame_var(rgenop, llhelper(FRAME_VAR_WRITER, writer))
+        fn = gv_f.revealconst(lltype.Ptr(FUNC))
+        res = fn(x)
+        keepalive_until_here(rgenop)    # to keep the code blocks alive
+        return res
+    return write_frame_var_runner
+
+
 class AbstractRGenOpTests(test_boehm.AbstractGCTestClass):
     RGenOp = None
 
@@ -628,6 +702,16 @@
         print gv.value
         return cast(c_void_p(gv.value), CFUNCTYPE(c_int, *[c_int]*nb_args))
 
+    def directtesthelper(self, FUNCTYPE, func):
+        # for machine code backends: build a ctypes function pointer
+        # (with a real physical address) that will call back our 'func'
+        nb_args = len(FUNCTYPE.TO.ARGS)
+        callback = CFUNCTYPE(c_int, *[c_int]*nb_args)(func)
+        keepalive = self.__dict__.setdefault('_keepalive', [])
+        keepalive.append((callback, func))
+        return cast(callback, c_void_p).value
+        # NB. returns the address as an integer
+
     def test_adder_direct(self):
         rgenop = self.RGenOp()
         gv_add_5 = make_adder(rgenop, 5)
@@ -1143,3 +1227,39 @@
         assert res == 168
         res = fnptr(7)
         assert res == 111
+
+    def test_read_frame_var_direct(self):
+        RGenOp = self.RGenOp
+
+        def reader(base, info):
+            return RGenOp.read_frame_var(lltype.Signed, base, info, 0) + 2
+        reader_ptr = self.directtesthelper(FRAME_VAR_READER, reader)
+
+        rgenop = self.RGenOp()
+        gv_callable = make_read_frame_var(rgenop, reader_ptr)
+        fnptr = self.cast(gv_callable, 1)
+        res = fnptr(20)
+        assert res == 42
+
+    def test_read_frame_var_compile(self):
+        fn = self.compile(get_read_frame_var_runner(self.RGenOp), [int])
+        res = fn(30)
+        assert res == 62
+
+    def test_write_frame_var_direct(self):
+        RGenOp = self.RGenOp
+
+        def writer(base, info, value):
+            RGenOp.write_frame_var(lltype.Signed, base, info, 0, value)
+        writer_ptr = self.directtesthelper(FRAME_VAR_WRITER, writer)
+
+        rgenop = self.RGenOp()
+        gv_callable = make_write_frame_var(rgenop, writer_ptr)
+        fnptr = self.cast(gv_callable, 1)
+        res = fnptr(-0xfada)
+        assert res == 42
+
+    def test_write_frame_var_compile(self):
+        fn = self.compile(get_write_frame_var_runner(self.RGenOp), [int])
+        res = fn(-1)
+        assert res == 42



More information about the Pypy-commit mailing list