gpointer mono_w32mutex_open (const gchar* utf8_name, gint32 right G_GNUC_UNUSED, gint32 *error) { gpointer handle; *error = ERROR_SUCCESS; /* w32 seems to guarantee that opening named objects can't race each other */ mono_w32handle_namespace_lock (); mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER_MUTEX, "%s: Opening named mutex [%s]", __func__, utf8_name); handle = mono_w32handle_namespace_search_handle (MONO_W32TYPE_NAMEDMUTEX, utf8_name); if (handle == INVALID_HANDLE_VALUE) { /* The name has already been used for a different object. */ *error = ERROR_INVALID_HANDLE; goto cleanup; } else if (!handle) { /* This name doesn't exist */ *error = ERROR_FILE_NOT_FOUND; goto cleanup; } mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER_MUTEX, "%s: returning named mutex handle %p", __func__, handle); cleanup: mono_w32handle_namespace_unlock (); return handle; }
gpointer ves_icall_System_Threading_Semaphore_OpenSemaphore_internal (MonoString *name, gint32 rights, gint32 *error) { gpointer handle; gchar *utf8_name; *error = ERROR_SUCCESS; /* w32 seems to guarantee that opening named objects can't race each other */ mono_w32handle_namespace_lock (); utf8_name = g_utf16_to_utf8 (mono_string_chars (name), -1, NULL, NULL, NULL); mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: Opening named sem [%s]", __func__, utf8_name); handle = mono_w32handle_namespace_search_handle (MONO_W32HANDLE_NAMEDSEM, utf8_name); if (handle == INVALID_HANDLE_VALUE) { /* The name has already been used for a different object. */ *error = ERROR_INVALID_HANDLE; goto cleanup; } else if (!handle) { /* This name doesn't exist */ *error = ERROR_FILE_NOT_FOUND; goto cleanup; } mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: returning named sem handle %p", __func__, handle); cleanup: g_free (utf8_name); mono_w32handle_namespace_unlock (); return handle; }
static gpointer namedsem_create (gint32 initial, gint32 max, const gunichar2 *name) { gpointer handle; gchar *utf8_name; mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: creating %s handle, initial %d max %d name \"%s\"", __func__, mono_w32handle_ops_typename (MONO_W32HANDLE_NAMEDSEM), initial, max, name); /* w32 seems to guarantee that opening named objects can't race each other */ mono_w32handle_namespace_lock (); utf8_name = g_utf16_to_utf8 (name, -1, NULL, NULL, NULL); mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: Creating named sem name [%s] initial %d max %d", __func__, utf8_name, initial, max); handle = mono_w32handle_namespace_search_handle (MONO_W32HANDLE_NAMEDSEM, utf8_name); if (handle == INVALID_HANDLE_VALUE) { /* The name has already been used for a different object. */ handle = NULL; SetLastError (ERROR_INVALID_HANDLE); } else if (handle) { /* Not an error, but this is how the caller is informed that the semaphore wasn't freshly created */ SetLastError (ERROR_ALREADY_EXISTS); /* mono_w32handle_namespace_search_handle already adds a ref to the handle */ } else { /* A new named semaphore */ MonoW32HandleNamedSemaphore namedsem_handle; strncpy (&namedsem_handle.sharedns.name [0], utf8_name, MAX_PATH); namedsem_handle.sharedns.name [MAX_PATH] = '\0'; handle = sem_handle_create ((MonoW32HandleSemaphore*) &namedsem_handle, MONO_W32HANDLE_NAMEDSEM, initial, max); } g_free (utf8_name); mono_w32handle_namespace_unlock (); return handle; }
static gpointer namedmutex_create (gboolean owned, const gunichar2 *name) { gpointer handle; gchar *utf8_name; mono_trace (G_LOG_LEVEL_DEBUG, MONO_TRACE_IO_LAYER, "%s: creating %s handle", __func__, mono_w32handle_get_typename (MONO_W32HANDLE_NAMEDMUTEX)); /* w32 seems to guarantee that opening named objects can't race each other */ mono_w32handle_namespace_lock (); glong utf8_len = 0; utf8_name = g_utf16_to_utf8 (name, -1, NULL, &utf8_len, NULL); handle = mono_w32handle_namespace_search_handle (MONO_W32HANDLE_NAMEDMUTEX, utf8_name); if (handle == INVALID_HANDLE_VALUE) { /* The name has already been used for a different object. */ handle = NULL; mono_w32error_set_last (ERROR_INVALID_HANDLE); } else if (handle) { /* Not an error, but this is how the caller is informed that the mutex wasn't freshly created */ mono_w32error_set_last (ERROR_ALREADY_EXISTS); /* mono_w32handle_namespace_search_handle already adds a ref to the handle */ } else { /* A new named mutex */ MonoW32HandleNamedMutex namedmutex_handle; size_t len = utf8_len < MAX_PATH ? utf8_len : MAX_PATH; memcpy (&namedmutex_handle.sharedns.name [0], utf8_name, len); namedmutex_handle.sharedns.name [len] = '\0'; handle = mutex_handle_create ((MonoW32HandleMutex*) &namedmutex_handle, MONO_W32HANDLE_NAMEDMUTEX, owned); } g_free (utf8_name); mono_w32handle_namespace_unlock (); return handle; }