Author: Greg Price <[email protected]>
Branch: signatures
Changeset: r59320:2fcd49fa43c7
Date: 2012-12-02 23:34 -0800
http://bitbucket.org/pypy/pypy/changeset/2fcd49fa43c7/

Log:    Basic support for instance types in signatures

diff --git a/pypy/annotation/signature.py b/pypy/annotation/signature.py
--- a/pypy/annotation/signature.py
+++ b/pypy/annotation/signature.py
@@ -131,10 +131,15 @@
                                              s_input))
         inputcells[:] = args_s
 
+def apply_bookkeeper(paramtype, bookkeeper):
+    if isinstance(paramtype, SomeObject):
+        return paramtype
+    else:
+        return paramtype(bookkeeper)
 
 def enforce_signature_args(funcdesc, paramtypes, actualtypes):
     assert len(paramtypes) == len(actualtypes)
-    params_s = paramtypes
+    params_s = [apply_bookkeeper(paramtype, funcdesc.bookkeeper) for paramtype 
in paramtypes]
     for i, (s_param, s_actual) in enumerate(zip(params_s, actualtypes)):
         if not s_param.contains(s_actual):
             raise Exception("%r argument %d:\n"
@@ -142,6 +147,5 @@
                             "     got %s" % (funcdesc, i+1, s_param, s_actual))
     actualtypes[:] = params_s
 
-
 def enforce_signature_return(funcdesc, sigtype, inferredtype):
-    return sigtype
+    return apply_bookkeeper(sigtype, funcdesc.bookkeeper)
diff --git a/pypy/annotation/types.py b/pypy/annotation/types.py
--- a/pypy/annotation/types.py
+++ b/pypy/annotation/types.py
@@ -18,3 +18,6 @@
 def array(element):
     listdef = ListDef(None, element, mutated=True, resized=False)
     return model.SomeList(listdef)
+
+def instance(class_):
+    return lambda bookkeeper: 
model.SomeInstance(bookkeeper.getuniqueclassdef(class_))
diff --git a/pypy/rlib/test/test_signature.py b/pypy/rlib/test/test_signature.py
--- a/pypy/rlib/test/test_signature.py
+++ b/pypy/rlib/test/test_signature.py
@@ -126,3 +126,27 @@
         l = f()
         l.append(2)
     check_annotator_fails(try_append)
+
+def test_signature_instance():
+    class C1(object):
+        pass
+    class C2(C1):
+        pass
+    class C3(C2):
+        pass
+    @signature(types.instance(C3), returns=types.instance(C2))
+    def f(x):
+        assert isinstance(x, C2)
+        return x
+    argtype, rettype = getsig(f)
+    assert isinstance(argtype, model.SomeInstance)
+    assert argtype.classdef.classdesc.pyobj == C3
+    assert isinstance(rettype, model.SomeInstance)
+    assert rettype.classdef.classdesc.pyobj == C2
+
+    @check_annotator_fails
+    def ok_for_body():
+        f(C2())
+    @check_annotator_fails
+    def bad_for_body():
+        f(C1())
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to