From f5510262bcfee430cab7cebf25d48f8367465750 Mon Sep 17 00:00:00 2001 From: Ignacio Etcheverry Date: Thu, 23 Apr 2020 18:55:44 +0200 Subject: [PATCH] Mono/C#: Fix load hook not called for some assemblies on domain reload --- modules/mono/mono_gd/gd_mono_assembly.cpp | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/modules/mono/mono_gd/gd_mono_assembly.cpp b/modules/mono/mono_gd/gd_mono_assembly.cpp index 8439769d845..0f211eebc69 100644 --- a/modules/mono/mono_gd/gd_mono_assembly.cpp +++ b/modules/mono/mono_gd/gd_mono_assembly.cpp @@ -277,12 +277,25 @@ no_pdb: #endif + bool need_manual_load_hook = mono_image_get_assembly(image) != nullptr; // Re-using an existing image with an assembly loaded + status = MONO_IMAGE_OK; MonoAssembly *assembly = mono_assembly_load_from_full(image, image_filename.utf8().get_data(), &status, p_refonly); ERR_FAIL_COND_V_MSG(status != MONO_IMAGE_OK || !assembly, nullptr, "Failed to load assembly for image"); + if (need_manual_load_hook) { + // For some reason if an assembly survived domain reloading (maybe because it's referenced somewhere else), + // the mono internal search hook don't detect it, yet mono_image_open_from_data_with_name re-uses the image + // and assembly, and mono_assembly_load_from_full doesn't call the load hook. We need to call it manually. + String name = String::utf8(mono_assembly_name_get_name(mono_assembly_get_name(assembly))); + bool has_extension = name.ends_with(".dll") || name.ends_with(".exe"); + GDMonoAssembly *loaded_asm = GDMono::get_singleton()->get_loaded_assembly(has_extension ? name.get_basename() : name); + if (!loaded_asm) + assembly_load_hook(assembly, nullptr); + } + // Decrement refcount which was previously incremented by mono_image_open_from_data_with_name mono_image_close(image);