+#ifdef PLATFORM_WIN32
+ /* Load modules using LoadLibrary. */
+ if (!refonly && coree_module_handle) {
+ HMODULE module_handle;
+ guint16 *fname_utf16;
+ DWORD last_error;
+
+ absfname = mono_path_resolve_symlinks (fname);
+ fname_utf16 = NULL;
+
+ /* There is little overhead because the OS loader lock is held by LoadLibrary. */
+ mono_images_lock ();
+ image = g_hash_table_lookup (loaded_images_hash, absfname);
+ if (image) {
+ g_assert (image->is_module_handle);
+ if (image->has_entry_point && image->ref_count == 0) {
+ /* Increment reference count on images loaded outside of the runtime. */
+ fname_utf16 = g_utf8_to_utf16 (absfname, -1, NULL, NULL, NULL);
+ /* The image is already loaded because _CorDllMain removes images from the hash. */
+ module_handle = LoadLibrary (fname_utf16);
+ g_assert (module_handle == (HMODULE) image->raw_data);
+ }
+ mono_image_addref (image);
+ mono_images_unlock ();
+ if (fname_utf16)
+ g_free (fname_utf16);
+ g_free (absfname);
+ return image;
+ }
+
+ fname_utf16 = g_utf8_to_utf16 (absfname, -1, NULL, NULL, NULL);
+ module_handle = MonoLoadImage (fname_utf16);
+ if (status && module_handle == NULL)
+ last_error = GetLastError ();
+
+ /* mono_image_open_from_module_handle is called by _CorDllMain. */
+ image = g_hash_table_lookup (loaded_images_hash, absfname);
+ if (image)
+ mono_image_addref (image);
+ mono_images_unlock ();
+
+ g_free (fname_utf16);
+
+ if (module_handle == NULL) {
+ g_assert (!image);
+ g_free (absfname);
+ if (status) {
+ if (last_error == ERROR_BAD_EXE_FORMAT || last_error == STATUS_INVALID_IMAGE_FORMAT)
+ *status = MONO_IMAGE_IMAGE_INVALID;
+ else
+ *status = MONO_IMAGE_ERROR_ERRNO;
+ }
+ return NULL;
+ }
+
+ if (image) {
+ g_assert (image->is_module_handle);
+ g_assert (image->has_entry_point);
+ g_free (absfname);
+ return image;
+ }
+
+ return mono_image_open_from_module_handle (module_handle, absfname, FALSE, status);
+ }
+#endif
+