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

antocuni at codespeak.net antocuni at codespeak.net
Mon Feb 4 10:45:09 CET 2008


Author: antocuni
Date: Mon Feb  4 10:45:09 2008
New Revision: 51238

Modified:
   pypy/dist/pypy/translator/cli/dotnet.py
   pypy/dist/pypy/translator/cli/test/test_dotnet.py
Log:
add the ability to call a delegate object with the usual () notation



Modified: pypy/dist/pypy/translator/cli/dotnet.py
==============================================================================
--- pypy/dist/pypy/translator/cli/dotnet.py	(original)
+++ pypy/dist/pypy/translator/cli/dotnet.py	Mon Feb  4 10:45:09 2008
@@ -3,6 +3,7 @@
 from pypy.tool.pairtype import pair, pairtype
 from pypy.annotation.model import SomeObject, SomeInstance, SomeOOInstance, SomeInteger, s_None,\
      s_ImpossibleValue, lltype_to_annotation, annotation_to_lltype, SomeChar, SomeString, SomePBC
+from pypy.annotation.unaryop import immutablevalue
 from pypy.annotation.binaryop import _make_none_union
 from pypy.annotation import model as annmodel
 from pypy.rlib.rarithmetic import r_uint, r_longlong, r_ulonglong
@@ -56,6 +57,17 @@
     def rtyper_makekey(self):
         return self.__class__, self.cli_class, self.meth_name
 
+class __extend__(SomeOOInstance):
+
+    def simple_call(self, *s_args):
+        from pypy.translator.cli.query import get_cli_class
+        DELEGATE = get_cli_class('System.Delegate')._INSTANCE
+        if ootype.isSubclass(self.ootype, DELEGATE):
+            s_invoke = self.getattr(immutablevalue('Invoke'))
+            return s_invoke.simple_call(*s_args)
+        else:
+            # cannot call a non-delegate
+            return SomeObject.simple_call(self, *s_args)
 
 class __extend__(pairtype(SomeOOInstance, SomeInteger)):
     def getitem((ooinst, index)):
@@ -148,6 +160,19 @@
         hop.exception_cannot_occur()
         return hop.genop('cli_arraylength', vlist, hop.r_result.lowleveltype)
 
+    def rtype_simple_call(self, hop):
+        TYPE = self.lowleveltype
+        _, meth = TYPE._lookup('Invoke')
+        assert isinstance(meth, ootype._overloaded_meth)
+        ARGS = tuple([repr.lowleveltype for repr in hop.args_r[1:]])
+        desc = meth._get_desc('Invoke', ARGS)
+        cname = hop.inputconst(ootype.Void, desc)
+        vlist = hop.inputargs(self, *hop.args_r[1:])
+        hop.exception_is_here()
+        return hop.genop("oosend", [cname]+vlist,
+                         resulttype = hop.r_result.lowleveltype)
+
+
 ## OOType model
 
 class OverloadingResolver(ootype.OverloadingResolver):

Modified: pypy/dist/pypy/translator/cli/test/test_dotnet.py
==============================================================================
--- pypy/dist/pypy/translator/cli/test/test_dotnet.py	(original)
+++ pypy/dist/pypy/translator/cli/test/test_dotnet.py	Mon Feb  4 10:45:09 2008
@@ -13,6 +13,21 @@
 ArrayList = CLR.System.Collections.ArrayList
 OpCodes = System.Reflection.Emit.OpCodes
 DynamicMethod = System.Reflection.Emit.DynamicMethod
+DelegateType = CLR.pypy.runtime.DelegateType_int__int_int
+Utils = CLR.pypy.runtime.Utils
+
+# RPython function, used by test_dynamic_method and test_call_delegate
+def build_fn():
+    tInt = typeof(System.Int32)
+    args = init_array(System.Type, tInt, tInt)
+    meth = Utils.CreateDynamicMethod("add", tInt, args)
+    il = meth.GetILGenerator()
+    il.Emit(OpCodes.Ldarg_0)
+    il.Emit(OpCodes.Ldarg_1)
+    il.Emit(OpCodes.Add)
+    il.Emit(OpCodes.Ret)
+    myfunc = meth.CreateDelegate(typeof(DelegateType))
+    return clidowncast(DelegateType, myfunc)
 
 class TestDotnetAnnotation(object):
 
@@ -468,24 +483,19 @@
         assert self.ll_to_string(res) == '42'
 
     def test_dynamic_method(self):
-        from pypy.rpython.ootypesystem import ootype
-        DelegateType = CLR.pypy.runtime.DelegateType_int__int_int
-        Utils = CLR.pypy.runtime.Utils
         def fn():
-            tInt = typeof(System.Int32)
-            args = init_array(System.Type, tInt, tInt)
-            meth = Utils.CreateDynamicMethod("add", tInt, args)
-            il = meth.GetILGenerator()
-            il.Emit(OpCodes.Ldarg_0)
-            il.Emit(OpCodes.Ldarg_1)
-            il.Emit(OpCodes.Add)
-            il.Emit(OpCodes.Ret)
-            myfunc = meth.CreateDelegate(typeof(DelegateType))
-            myfunc = clidowncast(DelegateType, myfunc)
+            myfunc = build_fn()
             return myfunc.Invoke(30, 12)
         res = self.interpret(fn, [])
         assert res == 42
 
+    def test_call_delegate(self):
+        def fn():
+            myfunc = build_fn()
+            return myfunc(30, 12)
+        res = self.interpret(fn, [])
+        assert res == 42
+
 
 class TestPythonnet(TestDotnetRtyping):
     # don't interpreter functions but execute them directly through pythonnet



More information about the Pypy-commit mailing list