[pypy-svn] r34735 - in pypy/dist/pypy: annotation/test rpython

arigo at codespeak.net arigo at codespeak.net
Sat Nov 18 17:43:01 CET 2006


Author: arigo
Date: Sat Nov 18 17:42:59 2006
New Revision: 34735

Modified:
   pypy/dist/pypy/annotation/test/test_annrpython.py
   pypy/dist/pypy/rpython/controllerentry.py
Log:
(pedronis, arigo)

More experimentation...


Modified: pypy/dist/pypy/annotation/test/test_annrpython.py
==============================================================================
--- pypy/dist/pypy/annotation/test/test_annrpython.py	(original)
+++ pypy/dist/pypy/annotation/test/test_annrpython.py	Sat Nov 18 17:42:59 2006
@@ -2403,7 +2403,7 @@
 
 
     def test_simple_controllerentry(self):
-        from pypy.rpython.controllerentry import ControllerEntry
+        from pypy.rpython.controllerentry import Controller, ControllerEntry
 
         class C:
             "Imagine some magic here to have a foo attribute on instances"
@@ -2412,17 +2412,22 @@
             c = C()
             return c.foo
 
-        class MyC:
-            def get_foo(self):
-                return 42
+        class C_Controller(Controller):
+            knowntype = C
+
+            def new(self):
+                return "4"
+
+            def get_foo(self, obj):
+                return obj + "2"
 
         class Entry(ControllerEntry):
             _about_ = C
-            _implementation_ = MyC
+            _controller_ = C_Controller
 
-        a = self.RPythonAnnotator()
+        a = self.RPythonAnnotator(policy=policy.AnnotatorPolicy())
         s = a.build_types(fun, [])
-        assert isinstance(s, annmodel.SomeInteger)
+        assert s.const == "42"
 
 
 def g(n):

Modified: pypy/dist/pypy/rpython/controllerentry.py
==============================================================================
--- pypy/dist/pypy/rpython/controllerentry.py	(original)
+++ pypy/dist/pypy/rpython/controllerentry.py	Sat Nov 18 17:42:59 2006
@@ -1,46 +1,67 @@
 from pypy.annotation import model as annmodel
+from pypy.annotation.pairtype import pairtype
 from pypy.annotation.bookkeeper import getbookkeeper
 from pypy.rpython.extregistry import ExtRegistryEntry
+from pypy.rpython.annlowlevel import cachedtype
 
 
+class ControllerEntry(ExtRegistryEntry):
+
+    def compute_result_annotation(self, *args_s):
+        cls = self.instance
+        controller = self.getcontroller(*args_s)
+        s_real_obj = controller.ctrl_new(*args_s)
+        return SomeControlledInstance(s_real_obj, controller)
+
+    def getcontroller(self, *args_s):
+        return self._controller_()
+
+
+class Controller(object):
+    __metaclass__ = cachedtype
+
+    def _freeze_(self):
+        return True
+
+    def ctrl_new(self, *args_s):
+        return delegate(self.new, *args_s)
+
+    def ctrl_getattr(self, s_obj, s_attr):
+        return delegate(self.getattr, s_obj, s_attr)
+
+    def getattr(self, obj, attr):
+        return getattr(self, 'get_' + attr)(obj)
+    getattr._annspecialcase_ = 'specialize:arg(2)'
+
+
+def delegate(boundmethod, *args_s):
+    bk = getbookkeeper()
+    s_meth = bk.immutablevalue(boundmethod)
+    return bk.emulate_pbc_call(bk.position_key, s_meth, args_s,
+                               callback = bk.position_key)
+
+# ____________________________________________________________
+
 class SomeControlledInstance(annmodel.SomeObject):
 
-    def __init__(self, classdef, originaltype):
-        self.classdef = classdef
-        self.knowntype = originaltype
-
-    def s_implself(self):
-        return annmodel.SomeInstance(self.classdef)
-
-    def delegate(self, methodname, *args_s):
-        bk = getbookkeeper()
-        classdef = self.classdef
-        # emulate a getattr to make sure it's on the classdef
-        classdef.find_attribute(methodname)
-        origindesc = classdef.classdesc.lookup(methodname)
-        s_func = origindesc.s_read_attribute(methodname)
-        funcdesc, = s_func.descriptions
-        methdesc = bk.getmethoddesc(
-            funcdesc,
-            origindesc.getuniqueclassdef(),
-            classdef,
-            methodname)
-        s_meth = annmodel.SomePBC([methdesc])
-        return bk.emulate_pbc_call(bk.position_key, s_meth, args_s,
-                                   callback = bk.position_key)
+    def __init__(self, s_real_obj, controller):
+        self.s_real_obj = s_real_obj
+        self.controller = controller
+        self.knowntype = controller.knowntype
 
 
 class __extend__(SomeControlledInstance):
 
     def getattr(s_cin, s_attr):
         assert s_attr.is_constant()
-        assert isinstance(s_attr.const, str)
-        return s_cin.delegate('get_' + s_attr.const)
+        return s_cin.controller.ctrl_getattr(s_cin.s_real_obj, s_attr)
 
 
-class ControllerEntry(ExtRegistryEntry):
+class __extend__(pairtype(SomeControlledInstance, SomeControlledInstance)):
 
-    def compute_result_annotation(self):
-        cls = self.instance
-        classdef = self.bookkeeper.getuniqueclassdef(self._implementation_)
-        return SomeControlledInstance(classdef, cls)
+    def union((s_cin1, s_cin2)):
+        if s_cin1.controller is not s_cin2.controller:
+            raise annmodel.UnionError("different controller!")
+        return SomeControlledInstance(annmodel.unionof(s_cin1.s_real_obj,
+                                                       s_cin2.s_real_obj),
+                                      s_cin1.controller)



More information about the Pypy-commit mailing list