From 5cea3d67b9b1262a30bcab3851b2f1d97630d6c9 Mon Sep 17 00:00:00 2001 From: Zoltan Varga Date: Fri, 28 Apr 2023 18:22:19 +0200 Subject: [PATCH] [mono] Invoke AssemblyLoad hooks from RuntimeAssemblyBuilder:.ctor () instead from native code. (#85307) The call from native code is made before the manifest module was created, causing errors if the hook tried to access Assembly.ManifestModule. Fixes https://github.com/dotnet/runtime/issues/84771. --- .../src/System/Runtime/Loader/AssemblyLoadContext.cs | 5 +++++ .../System/Reflection/Emit/RuntimeAssemblyBuilder.Mono.cs | 2 ++ src/mono/mono/metadata/appdomain.c | 4 ++++ 3 files changed, 11 insertions(+) diff --git a/src/libraries/System.Private.CoreLib/src/System/Runtime/Loader/AssemblyLoadContext.cs b/src/libraries/System.Private.CoreLib/src/System/Runtime/Loader/AssemblyLoadContext.cs index 53de721a0c458..2e8fcb7d4a0df 100644 --- a/src/libraries/System.Private.CoreLib/src/System/Runtime/Loader/AssemblyLoadContext.cs +++ b/src/libraries/System.Private.CoreLib/src/System/Runtime/Loader/AssemblyLoadContext.cs @@ -722,6 +722,11 @@ private static void OnAssemblyLoad(RuntimeAssembly assembly) return InvokeResolveEvent(AssemblyResolve, assembly, assemblyFullName); } + internal static void InvokeAssemblyLoadEvent(Assembly assembly) + { + AssemblyLoad?.Invoke(AppDomain.CurrentDomain, new AssemblyLoadEventArgs(assembly)); + } + [UnconditionalSuppressMessage("SingleFile", "IL3000: Avoid accessing Assembly file path when publishing as a single file", Justification = "The code handles the Assembly.Location equals null")] private static RuntimeAssembly? InvokeResolveEvent(ResolveEventHandler? eventHandler, RuntimeAssembly? assembly, string name) diff --git a/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/RuntimeAssemblyBuilder.Mono.cs b/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/RuntimeAssemblyBuilder.Mono.cs index 32cbacfc6a4df..929b9c1ec1f59 100644 --- a/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/RuntimeAssemblyBuilder.Mono.cs +++ b/src/mono/System.Private.CoreLib/src/System/Reflection/Emit/RuntimeAssemblyBuilder.Mono.cs @@ -256,6 +256,8 @@ internal RuntimeAssemblyBuilder(AssemblyName n, AssemblyBuilderAccess access) // Netcore only allows one module per assembly manifest_module = new RuntimeModuleBuilder(this, "RefEmit_InMemoryManifestModule"); modules = new RuntimeModuleBuilder[] { manifest_module }; + + AssemblyLoadContext.InvokeAssemblyLoadEvent (this); } public override bool ReflectionOnly diff --git a/src/mono/mono/metadata/appdomain.c b/src/mono/mono/metadata/appdomain.c index 686ec7e0ed593..44c8cf3de8c5b 100644 --- a/src/mono/mono/metadata/appdomain.c +++ b/src/mono/mono/metadata/appdomain.c @@ -571,6 +571,10 @@ mono_domain_fire_assembly_load_event (MonoDomain *domain, MonoAssembly *assembly if (!method) goto exit; + if (assembly->dynamic) + /* Called by RuntimeAssemblyBuilder:.ctor () after the manifest module has been created */ + goto exit; + MonoReflectionAssemblyHandle assembly_handle; assembly_handle = mono_assembly_get_object_handle (assembly, error); goto_if_nok (error, exit);