diff options
author | Gonzalo Paniagua Javier <gonzalo.mono@gmail.com> | 2005-06-20 22:07:16 +0400 |
---|---|---|
committer | Gonzalo Paniagua Javier <gonzalo.mono@gmail.com> | 2005-06-20 22:07:16 +0400 |
commit | 723e38c82c5b452e355f49f5d5a821160f6179ba (patch) | |
tree | 8bac5364364d576e5b3227f126eedfa18bf61081 | |
parent | 669e1211f916836ed1151d494ef6363f477c6875 (diff) |
2005-06-20 Gonzalo Paniagua Javier <gonzalo@ximian.com>
* domain.c:
* appdomain.c:
* domain-internals.h:
* reflection.c: 'domain_assemblies' field is now protected by its own
lock. Don't call into managed code to run the AssemblyLoad event if we
now there are no registered delegates for it.
svn path=/branches/mono-1-1-7/mono/; revision=46252
-rw-r--r-- | mono/metadata/ChangeLog | 8 | ||||
-rw-r--r-- | mono/metadata/appdomain.c | 46 | ||||
-rw-r--r-- | mono/metadata/domain-internals.h | 4 | ||||
-rw-r--r-- | mono/metadata/domain.c | 8 | ||||
-rw-r--r-- | mono/metadata/reflection.c | 4 |
5 files changed, 48 insertions, 22 deletions
diff --git a/mono/metadata/ChangeLog b/mono/metadata/ChangeLog index eb081b2b460..f32d2c9678c 100644 --- a/mono/metadata/ChangeLog +++ b/mono/metadata/ChangeLog @@ -1,3 +1,11 @@ +2005-06-20 Gonzalo Paniagua Javier <gonzalo@ximian.com> + + * domain.c: + * appdomain.c: + * domain-internals.h: + * reflection.c: 'domain_assemblies' field is now protected by its own + lock. Don't call into managed code to run the AssemblyLoad event if we + now there are no registered delegates for it. Wed Jun 8 19:26:38 CEST 2005 Paolo Molaro <lupus@ximian.com> diff --git a/mono/metadata/appdomain.c b/mono/metadata/appdomain.c index 1e61c04e9eb..b1d41c07169 100644 --- a/mono/metadata/appdomain.c +++ b/mono/metadata/appdomain.c @@ -440,11 +440,11 @@ ves_icall_System_AppDomain_createDomain (MonoString *friendly_name, MonoAppDomai mono_context_init (data); /* The new appdomain should have all assemblies loaded */ - mono_domain_lock (domain); + mono_domain_assemblies_lock (domain); /*g_print ("copy assemblies from domain %p (%s)\n", domain, domain->friendly_name);*/ for (tmp = domain->domain_assemblies; tmp; tmp = tmp->next) add_assemblies_to_domain (data, tmp->data, NULL); - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); return ad; } @@ -467,7 +467,7 @@ ves_icall_System_AppDomain_GetAssemblies (MonoAppDomain *ad, MonoBoolean refonly count = 0; /* Need to skip internal assembly builders created by remoting */ - mono_domain_lock (domain); + mono_domain_assemblies_lock (domain); for (tmp = domain->domain_assemblies; tmp; tmp = tmp->next) { ass = tmp->data; if (refonly && !ass->ref_only) @@ -486,7 +486,7 @@ ves_icall_System_AppDomain_GetAssemblies (MonoAppDomain *ad, MonoBoolean refonly mono_array_set (res, gpointer, i, mono_assembly_get_object (domain, ass)); ++i; } - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); return res; } @@ -517,7 +517,7 @@ try_assembly_resolve (MonoDomain *domain, MonoString *fname, gboolean refonly) } /* - * LOCKING: assumes domain is already locked. + * LOCKING: assumes assemblies_lock in the domain is already locked. */ static void add_assemblies_to_domain (MonoDomain *domain, MonoAssembly *ass, GHashTable *ht) @@ -558,10 +558,12 @@ add_assemblies_to_domain (MonoDomain *domain, MonoAssembly *ass, GHashTable *ht) static void mono_domain_fire_assembly_load (MonoAssembly *assembly, gpointer user_data) { + static MonoClassField *assembly_load_field; + static MonoMethod *assembly_load_method; MonoDomain *domain = mono_domain_get (); MonoReflectionAssembly *ref_assembly; MonoClass *klass; - MonoMethod *method; + gpointer load_value; void *params [1]; if (!domain->domain) @@ -570,21 +572,31 @@ mono_domain_fire_assembly_load (MonoAssembly *assembly, gpointer user_data) klass = domain->domain->mbr.obj.vtable->klass; - method = mono_class_get_method_from_name (klass, "DoAssemblyLoad", -1); - if (method == NULL) { - g_warning ("Method AppDomain.DoAssemblyLoad not found.\n"); - return; + mono_domain_assemblies_lock (domain); + add_assemblies_to_domain (domain, assembly, NULL); + mono_domain_assemblies_unlock (domain); + + if (assembly_load_field == NULL) { + assembly_load_field = mono_class_get_field_from_name (klass, "AssemblyLoad"); + g_assert (assembly_load_field); } - mono_domain_lock (domain); - add_assemblies_to_domain (domain, assembly, NULL); - mono_domain_unlock (domain); + mono_field_get_value (domain->domain, assembly_load_field, &load_value); + if (load_value == NULL) { + /* No events waiting to be triggered */ + return; + } ref_assembly = mono_assembly_get_object (domain, assembly); g_assert (ref_assembly); + if (assembly_load_method == NULL) { + assembly_load_method = mono_class_get_method_from_name (klass, "DoAssemblyLoad", -1); + g_assert (assembly_load_method); + } + *params = ref_assembly; - mono_runtime_invoke (method, domain->domain, params, NULL); + mono_runtime_invoke (assembly_load_method, domain->domain, params, NULL); } static gchar * @@ -852,17 +864,17 @@ mono_domain_assembly_search (MonoAssemblyName *aname, MonoAssembly *ass; gboolean refonly = GPOINTER_TO_UINT (user_data); - mono_domain_lock (domain); + mono_domain_assemblies_lock (domain); for (tmp = domain->domain_assemblies; tmp; tmp = tmp->next) { ass = tmp->data; /* Dynamic assemblies can't match here in MS.NET */ if (ass->dynamic || refonly != ass->ref_only || !mono_assembly_names_equal (aname, &ass->aname)) continue; - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); return ass; } - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); return NULL; } diff --git a/mono/metadata/domain-internals.h b/mono/metadata/domain-internals.h index fbbbda74524..6c115f05469 100644 --- a/mono/metadata/domain-internals.h +++ b/mono/metadata/domain-internals.h @@ -128,6 +128,8 @@ struct _MonoDomain { * if the hashtable contains a GC visible reference to them. */ GHashTable *finalizable_objects_hash; + /* Used when accessing 'domain_assemblies' */ + CRITICAL_SECTION assemblies_lock; }; typedef struct { @@ -143,6 +145,8 @@ typedef struct { #define mono_domain_lock(domain) EnterCriticalSection(&(domain)->lock) #define mono_domain_unlock(domain) LeaveCriticalSection(&(domain)->lock) +#define mono_domain_assemblies_lock(domain) EnterCriticalSection(&(domain)->assemblies_lock) +#define mono_domain_assemblies_unlock(domain) LeaveCriticalSection(&(domain)->assemblies_lock) void mono_jit_info_table_add (MonoDomain *domain, MonoJitInfo *ji); diff --git a/mono/metadata/domain.c b/mono/metadata/domain.c index ad4de0f8b8f..02e1adda4fd 100644 --- a/mono/metadata/domain.c +++ b/mono/metadata/domain.c @@ -312,6 +312,7 @@ mono_domain_create (void) domain->jit_trampoline_hash = g_hash_table_new (mono_aligned_addr_hash, NULL); InitializeCriticalSection (&domain->lock); + InitializeCriticalSection (&domain->assemblies_lock); EnterCriticalSection (&appdomains_mutex); domain_id_alloc (domain); @@ -738,15 +739,15 @@ mono_domain_assembly_open (MonoDomain *domain, const char *name) MonoAssembly *ass; GSList *tmp; - mono_domain_lock (domain); + mono_domain_assemblies_lock (domain); for (tmp = domain->domain_assemblies; tmp; tmp = tmp->next) { ass = tmp->data; if (strcmp (name, ass->aname.name) == 0) { - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); return ass; } } - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); if (!(ass = mono_assembly_open (name, NULL))) return NULL; @@ -856,6 +857,7 @@ mono_domain_free (MonoDomain *domain, gboolean force) g_hash_table_destroy (domain->special_static_fields); domain->special_static_fields = NULL; } + DeleteCriticalSection (&domain->assemblies_lock); DeleteCriticalSection (&domain->lock); domain->setup = NULL; diff --git a/mono/metadata/reflection.c b/mono/metadata/reflection.c index d5617716008..1f97e8648e7 100644 --- a/mono/metadata/reflection.c +++ b/mono/metadata/reflection.c @@ -4338,9 +4338,9 @@ mono_image_basic_init (MonoReflectionAssemblyBuilder *assemblyb) assembly->assembly.aname.name = image->image.name; assembly->assembly.image = &image->image; - mono_domain_lock (domain); + mono_domain_assemblies_lock (domain); domain->domain_assemblies = g_slist_prepend (domain->domain_assemblies, assembly); - mono_domain_unlock (domain); + mono_domain_assemblies_unlock (domain); register_assembly (mono_object_domain (assemblyb), &assemblyb->assembly, &assembly->assembly); mono_assembly_invoke_load_hook ((MonoAssembly*)assembly); |