[pypy-svn] r26001 - in pypy/dist/pypy/translator/cli: . src test

antocuni at codespeak.net antocuni at codespeak.net
Wed Apr 19 21:05:48 CEST 2006


Author: antocuni
Date: Wed Apr 19 21:05:16 2006
New Revision: 26001

Added:
   pypy/dist/pypy/translator/cli/oopspec.py   (contents, props changed)
Modified:
   pypy/dist/pypy/translator/cli/cts.py
   pypy/dist/pypy/translator/cli/metavm.py
   pypy/dist/pypy/translator/cli/src/pypylib.cs
   pypy/dist/pypy/translator/cli/test/compile.py
   pypy/dist/pypy/translator/cli/test/test_list.py
Log:
Added support for target-specific specialization based on the oopspec
attribute. The CLI backend can now decide to call a builtin method
instead of a ll_* helper function, thus bypassing it. As an example
the ll_append function is converted to the List<T>.append method.



Modified: pypy/dist/pypy/translator/cli/cts.py
==============================================================================
--- pypy/dist/pypy/translator/cli/cts.py	(original)
+++ pypy/dist/pypy/translator/cli/cts.py	Wed Apr 19 21:05:16 2006
@@ -8,6 +8,7 @@
 from pypy.rpython.lltypesystem.lltype import SignedLongLong, UnsignedLongLong
 from pypy.rpython.ootypesystem.ootype import Instance, Class, StaticMethod, List
 from pypy.translator.cli.option import getoption
+from pypy.translator.cli import oopspec
 
 from pypy.tool.ansi_print import ansi_log
 import py
@@ -100,7 +101,7 @@
             return self.graph_to_signature(meth.graph, True, full_name), True
 
         elif isinstance(obj, List):
-            meth = obj._GENERIC_METHODS[name]
+            meth = oopspec.get_method(obj, name)
             class_name = self.lltype_to_cts(obj)
             ret_type = self.lltype_to_cts(meth.RESULT)
             arg_types = [self.lltype_to_cts(arg) for arg in meth.ARGS]

Modified: pypy/dist/pypy/translator/cli/metavm.py
==============================================================================
--- pypy/dist/pypy/translator/cli/metavm.py	(original)
+++ pypy/dist/pypy/translator/cli/metavm.py	Wed Apr 19 21:05:16 2006
@@ -1,3 +1,5 @@
+from pypy.translator.cli import oopspec
+
 class Generator(object):
     def function_signature(self, graph):
         pass
@@ -54,9 +56,11 @@
 class _Call(MicroInstruction):
     def render(self, generator, op):
         graph = op.args[0].value.graph
-        cls = getattr(graph.func, 'class_', None)
-
-        self._render_function(generator, graph, op.args)
+        method_name = oopspec.get_method_name(graph, op)
+        if method_name is None:
+            self._render_function(generator, graph, op.args)
+        else:
+            self._render_method(generator, method_name, op.args[1:])
 
     def _render_function(self, generator, graph, args):
         func_sig = generator.function_signature(graph)
@@ -64,6 +68,18 @@
             generator.load(func_arg)
         generator.call(graph, func_sig)
 
+    def _render_method(self, generator, method_name, args):
+        this = args[0]
+        for arg in args: # push parametes
+            generator.load(arg)
+        generator.call_method(this.concretetype, method_name)
+        
+
+class _CallMethod(_Call):
+    def render(self, generator, op):
+        method = op.args[0]
+        self._render_method(generator, method.value, op.args[1:])
+
 class _New(MicroInstruction):
     def render(self, generator, op):
         generator.new(op.args[0].value)
@@ -84,17 +100,6 @@
         generator.load(this)
         generator.get_field(this.concretetype, field.value)
 
-class _CallMethod(MicroInstruction):
-    def render(self, generator, op):
-        method = op.args[0]
-        this = op.args[1]
-
-        # push parameters
-        for func_arg in op.args[1:]:
-            generator.load(func_arg)
-
-        generator.call_method(this.concretetype, method.value)
-
 class _RuntimeNew(MicroInstruction):
     def render(self, generator, op):
         generator.load(op.args[0])

Added: pypy/dist/pypy/translator/cli/oopspec.py
==============================================================================
--- (empty file)
+++ pypy/dist/pypy/translator/cli/oopspec.py	Wed Apr 19 21:05:16 2006
@@ -0,0 +1,41 @@
+from pypy.rpython.ootypesystem.ootype import List, Meth, Void
+
+def get_method_name(graph, op):
+    try:
+        oopspec = graph.func.oopspec
+    except AttributeError:
+        return None
+
+    # TODO: handle parsing of arguments; by now it is assumed that
+    # builtin methods take the same arguments of the corresponding
+    # ll_* function.
+    full_name, _ = oopspec.split('(', 1)
+    type_name, method_name = full_name.split('.')
+
+    try:
+        type_ = BUILTIN_TYPES[type_name]
+    except KeyError:
+        return None
+
+    this = op.args[1]
+    if isinstance(this.concretetype, type_) and method_name in BUILTIN_METHODS[type_]:
+        return method_name
+    else:
+        return None # explicit is better than implicit :-)
+
+def get_method(obj, name):
+    try:
+        return obj._GENERIC_METHODS[name]
+    except KeyError:
+        t = type(obj)
+        return BUILTIN_METHODS[t][name]
+
+BUILTIN_TYPES = {
+    'list': List
+    }
+
+BUILTIN_METHODS = {
+    List : {
+        'append': Meth([List.ITEMTYPE_T], Void)
+        }
+    } 

Modified: pypy/dist/pypy/translator/cli/src/pypylib.cs
==============================================================================
--- pypy/dist/pypy/translator/cli/src/pypylib.cs	(original)
+++ pypy/dist/pypy/translator/cli/src/pypylib.cs	Wed Apr 19 21:05:16 2006
@@ -58,12 +58,12 @@
             }
         }
 
-        /*
         public void append(T item)
         {
             this.Add(item);
         }
 
+        /*
         public void extend(List<T> other)
         {
             this.AddRange(other);

Modified: pypy/dist/pypy/translator/cli/test/compile.py
==============================================================================
--- pypy/dist/pypy/translator/cli/test/compile.py	(original)
+++ pypy/dist/pypy/translator/cli/test/compile.py	Wed Apr 19 21:05:16 2006
@@ -24,20 +24,11 @@
         print 'OK'
 
 
-def sum_(lst):
-    total = 0
-    i = 0
-    while i < len(lst):
-        total += lst[i]
-        i += 1
-    return total    
-
-class A:
-    pass
-
-##def bar(x, y):
-##    lst = [A(), A()]
-##    return lst.pop(1)
+
+def bar(x, y):
+    lst = [1,2]
+    lst.append(x)
+    return lst[2]
 
 
 f = compile_function(bar, [int, int])

Modified: pypy/dist/pypy/translator/cli/test/test_list.py
==============================================================================
--- pypy/dist/pypy/translator/cli/test/test_list.py	(original)
+++ pypy/dist/pypy/translator/cli/test/test_list.py	Wed Apr 19 21:05:16 2006
@@ -23,6 +23,11 @@
 def list_sum(x, y):
     return sum_(create(x, y))
 
+def list_append(x, y):
+    lst = create(x, y)
+    lst.append(x)
+    return sum_(lst)
+
 def list_setitem(x, y):
     lst = create(x, y)
     lst[0] = 0



More information about the Pypy-commit mailing list