static MonoMethodSignature*
signature_dup (MonoImage *image, MonoMethodSignature *sig)
{
- MonoMethodSignature *res;
- int sigsize;
-
- res = mono_metadata_signature_alloc (image, sig->param_count);
- sigsize = MONO_SIZEOF_METHOD_SIGNATURE + sig->param_count * sizeof (MonoType *);
- memcpy (res, sig, sigsize);
-
- return res;
+ return mono_metadata_signature_dup_full (image, sig);
}
MonoMethodSignature*
* Return the hash table pointed to by VAR, lazily creating it if neccesary.
*/
static GHashTable*
-get_cache (GHashTable **var, GHashFunc hash_func, GCompareFunc equal_func)
+get_cache_full (GHashTable **var, GHashFunc hash_func, GCompareFunc equal_func,
+ GDestroyNotify key_destroy_func,
+ GDestroyNotify value_destroy_func)
{
if (!(*var)) {
mono_marshal_lock ();
if (!(*var)) {
GHashTable *cache =
- g_hash_table_new (hash_func, equal_func);
+ g_hash_table_new_full (hash_func, equal_func, key_destroy_func, value_destroy_func);
mono_memory_barrier ();
*var = cache;
}
return *var;
}
+static GHashTable*
+get_cache (GHashTable **var, GHashFunc hash_func, GCompareFunc equal_func)
+{
+ return get_cache_full (var, hash_func, equal_func, NULL, NULL);
+}
+
GHashTable*
mono_marshal_get_cache (GHashTable **var, GHashFunc hash_func, GCompareFunc equal_func)
{
g_free (tmp_sig);
}
+ printf ("D: %s\n", mono_method_full_name (method, TRUE));
+
/* to make it work with our special string constructors */
if (!string_dummy) {
MONO_GC_REGISTER_ROOT (string_dummy);
MonoMethodBuilder *mb;
MonoMethod *res;
int i;
+ GHashTable *cache;
- mb = mono_mb_new_no_dup_name (class, name, MONO_WRAPPER_MANAGED_TO_MANAGED);
+ cache = get_cache_full (&method->klass->image->generic_array_helper_cache, mono_aligned_addr_hash, NULL, NULL, (GDestroyNotify)mono_free_method);
+
+ if ((res = mono_marshal_find_in_cache (cache, method)))
+ return res;
+
+ mb = mono_mb_new (class, name, MONO_WRAPPER_MANAGED_TO_MANAGED);
mb->method->slot = -1;
+ mb->dynamic = TRUE;
mb->method->flags = METHOD_ATTRIBUTE_PRIVATE | METHOD_ATTRIBUTE_VIRTUAL |
METHOD_ATTRIBUTE_NEW_SLOT | METHOD_ATTRIBUTE_HIDE_BY_SIG | METHOD_ATTRIBUTE_FINAL;
sig = mono_method_signature (method);
- csig = signature_dup (method->klass->image, sig);
+ csig = signature_dup (NULL, sig);
csig->generic_param_count = 0;
mono_mb_emit_ldarg (mb, 0);
/* We can corlib internal methods */
mb->skip_visibility = TRUE;
- res = mono_mb_create_method (mb, csig, csig->param_count + 16);
+ res = mono_mb_create_and_cache (cache, method, mb, csig, csig->param_count + 16);
mono_mb_free (mb);
g_hash_table_remove (method->klass->image->cominterop_wrapper_cache, method);
if (method->klass->image->thunk_invoke_cache)
g_hash_table_remove (method->klass->image->thunk_invoke_cache, method);
+ if (method->klass->image->generic_array_helper_cache)
+ g_hash_table_remove (method->klass->image->generic_array_helper_cache, method);
mono_marshal_unlock ();
}