X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=mono%2Ftests%2Fpinvoke3.cs;h=c1354ce9b544dc34baea80b26e75b16fa20e156b;hb=012f8610237dfe44034c9d8daea0b90fac75ca9f;hp=ae64d16e090d7af29dd027197a083e92bb2d7845;hpb=3fd4901a235bda0019f03317f4ee083744195758;p=mono.git diff --git a/mono/tests/pinvoke3.cs b/mono/tests/pinvoke3.cs index ae64d16e090..c1354ce9b54 100644 --- a/mono/tests/pinvoke3.cs +++ b/mono/tests/pinvoke3.cs @@ -188,6 +188,17 @@ public class Tests { [DllImport ("libtest", EntryPoint="mono_test_marshal_return_delegate_delegate")] public static extern int mono_test_marshal_return_delegate_delegate (ReturnDelegateDelegate d); + [DllImport ("libtest", EntryPoint="mono_test_marshal_delegate_ref_delegate")] + public static extern int mono_test_marshal_delegate_ref_delegate (DelegateByrefDelegate del); + + [DllImport ("libtest", EntryPoint="mono_test_marshal_virtual_delegate")] + public static extern int mono_test_marshal_virtual_delegate (VirtualDelegate del); + + [DllImport ("libtest", EntryPoint="mono_test_marshal_icall_delegate")] + public static extern int mono_test_marshal_icall_delegate (IcallDelegate del); + + public delegate string IcallDelegate (IntPtr p); + public delegate int TestDelegate (int a, ref SimpleStruct ss, int b); public delegate SimpleStruct SimpleDelegate2 (SimpleStruct ss); @@ -210,6 +221,10 @@ public class Tests { public delegate return_int_delegate ReturnDelegateDelegate (); + public delegate int DelegateByrefDelegate (ref return_int_delegate del); + + public delegate int VirtualDelegate (int i); + public static int Main () { return TestDriver.RunTests (typeof (Tests)); } @@ -333,6 +348,20 @@ public class Tests { return mono_test_marshal_return_delegate_delegate (new ReturnDelegateDelegate (return_delegate)); } + public static int return_plus_1 (int i) { + return i + 1; + } + + public static int ref_delegate_delegate (ref return_int_delegate del) { + del = return_plus_1; + return 0; + } + + public static int test_55_marshal_delegate_ref_delegate () { + var del = new DelegateByrefDelegate (ref_delegate_delegate); + return mono_test_marshal_delegate_ref_delegate (del); + } + /* Passing and returning strings */ public delegate String ReturnStringDelegate (String s); @@ -717,6 +746,21 @@ public class Tests { return mono_test_marshal_array_delegate1 (null, 0, new ArrayDelegate1 (array_delegate2)); } + public delegate int ArrayDelegateBlittable (int i, string j, + [In, MarshalAs(UnmanagedType.LPArray, + ArraySubType=UnmanagedType.LPStr, SizeParamIndex=0)] int[] arr); + + [DllImport ("libtest", EntryPoint="mono_test_marshal_array_delegate")] + public static extern int mono_test_marshal_array_delegate1 (string[] arr, int len, ArrayDelegateBlittable d); + + public static int array_delegate_null_blittable (int i, string j, int[] arr) { + return (arr == null) ? 0 : 1; + } + + public static int test_0_marshal_array_delegate_null_blittable () { + return mono_test_marshal_array_delegate1 (null, 0, new ArrayDelegateBlittable (array_delegate_null_blittable)); + } + public delegate int ArrayDelegate3 (int i, string j, [In, MarshalAs(UnmanagedType.LPArray, @@ -1076,6 +1120,87 @@ public class Tests { return res; } + public struct LargeStruct { + public Int16 s; + public Int16 v; + public UInt32 p; + public UInt32 e; + public Int32 l; + public Int32 ll; + public UInt16 h; + public Int16 r; + public Int16 pp; + public Int32 hh; + public Int32 bn; + public Int32 dn; + public Int32 dr; + public Int32 sh; + public Int32 ra; + [MarshalAs(UnmanagedType.ByValArray, SizeConst = 3)] + public Int32[] angle; + [MarshalAs(UnmanagedType.ByValArray, SizeConst = 3)] + public Int32[] width; + [MarshalAs(UnmanagedType.ByValArray, SizeConst = 3)] + public Int32[] edge; + [MarshalAs(UnmanagedType.ByValArray, SizeConst = 3 * 1024)] + public byte[] echo; + } + + public delegate int LargeStructDelegate (ref LargeStruct s); + + [DllImport ("libtest", EntryPoint="mono_test_marshal_thread_attach_large_vt")] + public static extern int mono_test_marshal_thread_attach_large_vt (LargeStructDelegate d); + + public static int test_43_thread_attach_large_vt () { + int res = mono_test_marshal_thread_attach_large_vt (delegate (ref LargeStruct s) { + return 43; + }); + return res; + } + + class Worker { + volatile bool stop = false; + public void Stop () { + stop = true; + } + + public void Work () { + while (!stop) { + for (int i = 0; i < 100; i++) { + var a = new double[80000]; + Thread.Sleep (0); + } + GC.Collect (); + } + } + } + + public static int test_43_thread_attach_detach_contested () { + // Test plan: we want to create a race between the GC + // and native threads detaching. When a native thread + // calls a managed delegate, it's attached to the + // runtime by the wrapper. It is detached when the + // thread is destroyed and the TLS key destructor for + // MonoThreadInfo runs. That destructor wants to take + // the GC lock. So we create a lot of native threads + // while at the same time running a worker that + // allocates garbage and invokes the collector. + var w = new Worker (); + Thread t = new Thread(new ThreadStart (w.Work)); + t.Start (); + + for (int count = 0; count < 500; count++) { + int res = mono_test_marshal_thread_attach (delegate (int i) { + Thread.Sleep (0); + return i + 1; + }); + } + Thread.Sleep (1000); + w.Stop (); + t.Join (); + return 43; + + } /* * Appdomain save/restore */ @@ -1115,4 +1240,32 @@ public class Tests { return 0; } } + + class Base { + public VirtualDelegate get_del () { + return delegate_test; + } + + public virtual int delegate_test (int i) { + return i; + } + } + + class Derived : Base { + public override int delegate_test (int i) { + return i + 1; + } + } + + public static int test_43_virtual () { + Base b = new Derived (); + + return mono_test_marshal_virtual_delegate (b.get_del ()); + } + + public static int test_0_icall_delegate () { + var m = typeof (Marshal).GetMethod ("PtrToStringAnsi", new Type[] { typeof (IntPtr) }); + + return mono_test_marshal_icall_delegate ((IcallDelegate)Delegate.CreateDelegate (typeof (IcallDelegate), m)); + } }