From 10fcc026d3c9d330cc24cfa0b4480ba890dc3a47 Mon Sep 17 00:00:00 2001 From: Jay Krell Date: Mon, 29 Jul 2019 02:30:16 -0700 Subject: [PATCH] [Coop] Convert System.Buffer. (mono/mono#15861) And inline `mono_array_handle_length`. And remove `inline` in .c files a little -- it only belongs in .h. Commit migrated from https://github.com/mono/mono/commit/babcdbdcbd354296a74fa038daf24c38853d9d20 --- src/mono/mono/metadata/handle.c | 8 --- src/mono/mono/metadata/handle.h | 3 -- src/mono/mono/metadata/icall-decl.h | 2 - src/mono/mono/metadata/icall-def-netcore.h | 2 +- src/mono/mono/metadata/icall-def.h | 4 +- src/mono/mono/metadata/icall.c | 62 +++++++++++++----------- src/mono/mono/metadata/object-internals.h | 11 ++++- src/mono/mono/metadata/w32file.c | 4 +- src/mono/mono/utils/mono-threads-state-machine.c | 8 +-- 9 files changed, 53 insertions(+), 51 deletions(-) diff --git a/src/mono/mono/metadata/handle.c b/src/mono/mono/metadata/handle.c index bce1308..eff56a6 100644 --- a/src/mono/mono/metadata/handle.c +++ b/src/mono/mono/metadata/handle.c @@ -399,14 +399,6 @@ mono_array_new_full_handle (MonoDomain *domain, MonoClass *array_class, uintptr_ return MONO_HANDLE_NEW (MonoArray, mono_array_new_full_checked (domain, array_class, lengths, lower_bounds, error)); } -uintptr_t -mono_array_handle_length (MonoArrayHandle arr) -{ - MONO_REQ_GC_UNSAFE_MODE; - - return MONO_HANDLE_RAW (arr)->max_length; -} - uint32_t mono_gchandle_from_handle (MonoObjectHandle handle, mono_bool pinned) { diff --git a/src/mono/mono/metadata/handle.h b/src/mono/mono/metadata/handle.h index d0f345a..7b72082 100644 --- a/src/mono/mono/metadata/handle.h +++ b/src/mono/mono/metadata/handle.h @@ -541,9 +541,6 @@ MonoArrayHandle mono_array_new_handle (MonoDomain *domain, MonoClass *eclass, ui MonoArrayHandle mono_array_new_full_handle (MonoDomain *domain, MonoClass *array_class, uintptr_t *lengths, intptr_t *lower_bounds, MonoError *error); -uintptr_t -mono_array_handle_length (MonoArrayHandle arr); - #define mono_array_handle_setref(array,index,value) MONO_HANDLE_ARRAY_SETREF ((array), (index), (value)) void diff --git a/src/mono/mono/metadata/icall-decl.h b/src/mono/mono/metadata/icall-decl.h index b787c95..8cabf40 100644 --- a/src/mono/mono/metadata/icall-decl.h +++ b/src/mono/mono/metadata/icall-decl.h @@ -76,7 +76,6 @@ typedef enum { // grep ICALL_EXPORT | sort | uniq ICALL_EXPORT MonoAssemblyName* ves_icall_System_Reflection_AssemblyName_GetNativeName (MonoAssembly*); ICALL_EXPORT MonoBoolean ves_icall_RuntimeTypeHandle_is_subclass_of (MonoType*, MonoType*); -ICALL_EXPORT MonoBoolean ves_icall_System_Buffer_BlockCopyInternal (MonoArray*, gint32, MonoArray*, gint32, gint32); ICALL_EXPORT MonoBoolean ves_icall_System_Environment_GetIs64BitOperatingSystem (void); ICALL_EXPORT MonoBoolean ves_icall_System_Environment_get_HasShutdownStarted (void); ICALL_EXPORT MonoBoolean ves_icall_System_GCHandle_CheckCurrentDomain (guint32 gchandle); @@ -154,7 +153,6 @@ ICALL_EXPORT float ves_icall_System_MathF_ScaleB (float, gint32); ICALL_EXPORT float ves_icall_System_MathF_FusedMultiplyAdd (float, float, float); #endif ICALL_EXPORT gint ves_icall_System_Runtime_CompilerServices_RuntimeHelpers_GetOffsetToStringData (void); -ICALL_EXPORT gint32 ves_icall_System_Buffer_ByteLengthInternal (MonoArray*); ICALL_EXPORT gint32 ves_icall_System_Environment_get_ProcessorCount (void); ICALL_EXPORT gint32 ves_icall_System_Environment_get_TickCount (void); #if ENABLE_NETCORE diff --git a/src/mono/mono/metadata/icall-def-netcore.h b/src/mono/mono/metadata/icall-def-netcore.h index 297d786..9e4f302 100644 --- a/src/mono/mono/metadata/icall-def-netcore.h +++ b/src/mono/mono/metadata/icall-def-netcore.h @@ -57,7 +57,7 @@ HANDLES(ARRAY_13, "SetValueImpl", ves_icall_System_Array_SetValueImpl, void, 3, HANDLES(ARRAY_14, "SetValueRelaxedImpl", ves_icall_System_Array_SetValueRelaxedImpl, void, 3, (MonoArray, MonoObject, guint32)) ICALL_TYPE(BUFFER, "System.Buffer", BUFFER_1) -ICALL(BUFFER_1, "_ByteLength", ves_icall_System_Buffer_ByteLengthInternal) +HANDLES(BUFFER_1, "_ByteLength", ves_icall_System_Buffer_ByteLengthInternal, gint32, 1, (MonoArray)) NOHANDLES(ICALL(BUFFER_2, "__Memmove", ves_icall_System_Runtime_RuntimeImports_Memmove)) ICALL_TYPE(DELEGATE, "System.Delegate", DELEGATE_1) diff --git a/src/mono/mono/metadata/icall-def.h b/src/mono/mono/metadata/icall-def.h index f9dd021..045b9cb 100644 --- a/src/mono/mono/metadata/icall-def.h +++ b/src/mono/mono/metadata/icall-def.h @@ -225,9 +225,9 @@ HANDLES(ARRAY_12, "SetValue", ves_icall_System_Array_SetValue, void, 3, HANDLES(ARRAY_13, "SetValueImpl", ves_icall_System_Array_SetValueImpl, void, 3, (MonoArray, MonoObject, guint32)) ICALL_TYPE(BUFFER, "System.Buffer", BUFFER_1) -ICALL(BUFFER_1, "InternalBlockCopy", ves_icall_System_Buffer_BlockCopyInternal) +HANDLES(BUFFER_1, "InternalBlockCopy", ves_icall_System_Buffer_BlockCopyInternal, MonoBoolean, 5, (MonoArray, gint32, MonoArray, gint32, gint32)) NOHANDLES(ICALL(BUFFER_5, "InternalMemcpy", ves_icall_System_Buffer_MemcpyInternal)) -ICALL(BUFFER_2, "_ByteLength", ves_icall_System_Buffer_ByteLengthInternal) +HANDLES(BUFFER_2, "_ByteLength", ves_icall_System_Buffer_ByteLengthInternal, gint32, 1, (MonoArray)) ICALL_TYPE(CLRCONFIG, "System.CLRConfig", CLRCONFIG_1) HANDLES(CLRCONFIG_1, "CheckThrowUnobservedTaskExceptions", ves_icall_System_CLRConfig_CheckThrowUnobservedTaskExceptions, MonoBoolean, 0, ()) diff --git a/src/mono/mono/metadata/icall.c b/src/mono/mono/metadata/icall.c index 4edd598..0e38292 100644 --- a/src/mono/mono/metadata/icall.c +++ b/src/mono/mono/metadata/icall.c @@ -6921,10 +6921,14 @@ ves_icall_System_Reflection_RuntimeModule_ResolveSignature (MonoImage *image, gu MonoArrayHandle res = mono_array_new_handle (mono_domain_get (), mono_defaults.byte_class, len, error); return_val_if_nok (error, NULL_HANDLE_ARRAY); + + // FIXME MONO_ENTER_NO_SAFEPOINTS instead of pin/gchandle. + uint32_t h; gpointer array_base = MONO_ARRAY_HANDLE_PIN (res, guint8, 0, &h); memcpy (array_base, ptr, len); mono_gchandle_free_internal (h); + return res; } @@ -7082,22 +7086,22 @@ ves_icall_System_Delegate_GetVirtualMethod_internal (MonoDelegateHandle delegate /* System.Buffer */ -static inline gint32 -mono_array_get_byte_length (MonoArray *array) +static gint32 +mono_array_get_byte_length (MonoArrayHandle array) { - MonoClass *klass; int length; - int i; - klass = array->obj.vtable->klass; + MonoClass * const klass = mono_handle_class (array); - if (array->bounds == NULL) - length = array->max_length; - else { + // This resembles mono_array_get_length, but adds the loop. + + if (mono_handle_array_has_bounds (array)) { length = 1; - int klass_rank = m_class_get_rank (klass); - for (i = 0; i < klass_rank; ++ i) - length *= array->bounds [i].length; + const int klass_rank = m_class_get_rank (klass); + for (int i = 0; i < klass_rank; ++ i) + length *= MONO_HANDLE_GETVAL (array, bounds [i].length); + } else { + length = mono_array_handle_length (array); } switch (m_class_get_byval_arg (m_class_get_element_class (klass))->type) { @@ -7125,8 +7129,8 @@ mono_array_get_byte_length (MonoArray *array) } } -gint32 -ves_icall_System_Buffer_ByteLengthInternal (MonoArray *array) +gint32 +ves_icall_System_Buffer_ByteLengthInternal (MonoArrayHandle array, MonoError* error) { return mono_array_get_byte_length (array); } @@ -7138,35 +7142,39 @@ ves_icall_System_Buffer_MemcpyInternal (gpointer dest, gconstpointer src, gint32 } MonoBoolean -ves_icall_System_Buffer_BlockCopyInternal (MonoArray *src, gint32 src_offset, MonoArray *dest, gint32 dest_offset, gint32 count) +ves_icall_System_Buffer_BlockCopyInternal (MonoArrayHandle src, gint32 src_offset, MonoArrayHandle dest, gint32 dest_offset, gint32 count, MonoError* error) { - guint8 *src_buf, *dest_buf; - if (count < 0) { - ERROR_DECL (error); mono_error_set_argument (error, "count", "is negative"); - mono_error_set_pending_exception (error); return FALSE; } - g_assert (count >= 0); - /* This is called directly from the class libraries without going through the managed wrapper */ - MONO_CHECK_ARG_NULL (src, FALSE); - MONO_CHECK_ARG_NULL (dest, FALSE); + MONO_CHECK_ARG_NULL_HANDLE (src, FALSE); + MONO_CHECK_ARG_NULL_HANDLE (dest, FALSE); /* watch out for integer overflow */ if ((src_offset > mono_array_get_byte_length (src) - count) || (dest_offset > mono_array_get_byte_length (dest) - count)) return FALSE; - src_buf = (guint8 *)src->vector + src_offset; - dest_buf = (guint8 *)dest->vector + dest_offset; + MONO_ENTER_NO_SAFEPOINTS; + + guint8 const * const src_buf = (guint8*)MONO_HANDLE_RAW (src)->vector + src_offset; + guint8* const dest_buf = (guint8*)MONO_HANDLE_RAW (dest)->vector + dest_offset; - if (src != dest) +#if !HOST_WIN32 + + // Windows memcpy is memmove and checks for overlap anyway, so skip + // the check here that would not help. + + if (MONO_HANDLE_RAW (src) != MONO_HANDLE_RAW (dest)) memcpy (dest_buf, src_buf, count); else +#endif memmove (dest_buf, src_buf, count); /* Source and dest are the same array */ + MONO_EXIT_NO_SAFEPOINTS; + return TRUE; } @@ -7285,7 +7293,7 @@ ves_icall_System_Environment_get_MachineName (MonoError *error) } #ifndef HOST_WIN32 -static inline int +static int mono_icall_get_platform (void) { #if defined(__MACH__) @@ -7312,7 +7320,7 @@ ves_icall_System_Environment_get_Platform (void) } #ifndef HOST_WIN32 -static inline MonoStringHandle +static MonoStringHandle mono_icall_get_new_line (MonoError *error) { error_init (error); diff --git a/src/mono/mono/metadata/object-internals.h b/src/mono/mono/metadata/object-internals.h index 86c74b4..fc9c7a2 100644 --- a/src/mono/mono/metadata/object-internals.h +++ b/src/mono/mono/metadata/object-internals.h @@ -51,9 +51,7 @@ #define MONO_CHECK_ARG_NULL(arg, retval) do { \ if (G_UNLIKELY (!(arg))) \ { \ - ERROR_DECL (error); \ mono_error_set_argument_null (error, #arg, ""); \ - mono_error_set_pending_exception (error); \ return retval; \ } \ } while (0) @@ -186,6 +184,15 @@ struct _MonoString { */ #define mono_array_length_internal(array) ((array)->max_length) +static inline +uintptr_t +mono_array_handle_length (MonoArrayHandle arr) +{ + MONO_REQ_GC_UNSAFE_MODE; + + return mono_array_length_internal (MONO_HANDLE_RAW (arr)); +} + // Equivalent to mono_array_addr_with_size, except: // 1. A macro instead of a function -- the types of size and index are open. // 2. mono_array_addr_with_size could, but does not, do GC mode transitions. diff --git a/src/mono/mono/metadata/w32file.c b/src/mono/mono/metadata/w32file.c index d58a28d..4086e3f 100644 --- a/src/mono/mono/metadata/w32file.c +++ b/src/mono/mono/metadata/w32file.c @@ -518,7 +518,7 @@ ves_icall_System_IO_MonoIO_Read (HANDLE handle, MonoArrayHandle dest, *io_error=ERROR_SUCCESS; - MONO_CHECK_ARG_NULL (MONO_HANDLE_RAW (dest), 0); + MONO_CHECK_ARG_NULL_HANDLE (dest, 0); if (dest_offset > mono_array_handle_length (dest) - count) { mono_error_set_argument (error, "array", "array too small. numBytes/offset wrong."); @@ -548,7 +548,7 @@ ves_icall_System_IO_MonoIO_Write (HANDLE handle, MonoArrayHandle src, *io_error=ERROR_SUCCESS; - MONO_CHECK_ARG_NULL (MONO_HANDLE_RAW (src), 0); + MONO_CHECK_ARG_NULL_HANDLE (src, 0); if (src_offset > mono_array_handle_length (src) - count) { mono_error_set_argument (error, "array", "array too small. numBytes/offset wrong."); diff --git a/src/mono/mono/utils/mono-threads-state-machine.c b/src/mono/mono/utils/mono-threads-state-machine.c index d14879e..f8f043e 100644 --- a/src/mono/mono/utils/mono-threads-state-machine.c +++ b/src/mono/mono/utils/mono-threads-state-machine.c @@ -15,25 +15,25 @@ #include /*thread state helpers*/ -static inline int +static int get_thread_state (int thread_state) { return thread_state & THREAD_STATE_MASK; } -static inline int +static int get_thread_suspend_count (int thread_state) { return (thread_state & THREAD_SUSPEND_COUNT_MASK) >> THREAD_SUSPEND_COUNT_SHIFT; } -static inline gboolean +static gboolean get_thread_no_safepoints (int thread_state) { return (thread_state & THREAD_SUSPEND_NO_SAFEPOINTS_MASK) >> THREAD_SUSPEND_NO_SAFEPOINTS_SHIFT; } -static inline int +static int build_thread_state (int thread_state, int suspend_count, gboolean no_safepoints) { g_assert (suspend_count >= 0 && suspend_count <= THREAD_SUSPEND_COUNT_MAX); -- 2.7.4