Copying zero-length data to/from unmanaged memory with
Marshal.Copy methods results in the following errors:
** ERROR **: file marshal.c: line 2686 (ves_icall_System_Runtime_InteropServices_Marshal_copy_to_unmanaged): assertion failed: (start_index >= 0 && start_index < mono_array_length (src))
aborting...
or
** ERROR **: file marshal.c: line 2709 (ves_icall_System_Runtime_InteropServices_Marshal_copy_from_unmanaged): assertion failed: (start_index >= 0 && start_index < mono_array_length (dest))
aborting...
The attached files contain a test and a proposed patch for this problem.
Regards,
Aleksey
using System; using System.Runtime.InteropServices; public class TestCopy { public static void Main (string[] args) { IntPtr buffer = Marshal.AllocHGlobal (1024); byte[] bytes = UnmarshalBytes (buffer, 0); MarshalBytes (buffer, bytes); }
private static void MarshalBytes (IntPtr buffer, byte[] bytes) { Marshal.Copy (bytes, 0, buffer, bytes.Length); } private static byte[] UnmarshalBytes (IntPtr buffer, int length) { byte[] bytes = new byte[length]; Marshal.Copy (buffer, bytes, 0, length); return bytes; } }
Index: marshal.c =================================================================== RCS file: /mono/mono/mono/metadata/marshal.c,v retrieving revision 1.67 diff -u -r1.67 marshal.c --- marshal.c 20 Jan 2003 18:06:01 -0000 1.67 +++ marshal.c 21 Jan 2003 10:08:10 -0000 @@ -2683,7 +2683,8 @@ MONO_CHECK_ARG_NULL (dest); g_assert (src->obj.vtable->klass->rank == 1); - g_assert (start_index >= 0 && start_index < mono_array_length (src)); + g_assert (start_index >= 0); + g_assert (length >= 0); g_assert (start_index + length <= mono_array_length (src)); element_size = mono_array_element_size (src->obj.vtable->klass); @@ -2706,7 +2707,8 @@ MONO_CHECK_ARG_NULL (dest); g_assert (dest->obj.vtable->klass->rank == 1); - g_assert (start_index >= 0 && start_index < mono_array_length (dest)); + g_assert (start_index >= 0); + g_assert (length >= 0); g_assert (start_index + length <= mono_array_length (dest)); element_size = mono_array_element_size (dest->obj.vtable->klass);