MonoClass *socket_class;
MonoClass *ad_unloaded_ex_class;
MonoClass *process_class;
+
+ /* Cache function pointers for architectures */
+ /* that require wrappers */
+#if defined(__ia64__) || defined(__ppc64__) || defined(__powerpc64__)
+ GHashTable *ftnptrs_hash;
+#endif
};
typedef struct {
/* Avoid system error message boxes. */
SetErrorMode (SEM_FAILCRITICALERRORS | SEM_NOOPENFILEERRORBOX);
#endif
+#if defined(__ia64__) || defined(__ppc64__) || defined(__powerpc64__)
+ domain->ftnptrs_hash = g_hash_table_new (mono_aligned_addr_hash, NULL);
+#endif
mono_perfcounters_init ();
g_hash_table_destroy (domain->generic_virtual_thunks);
domain->generic_virtual_thunks = NULL;
}
+#if defined(__ia64__) || defined(__ppc64__) || defined(__powerpc64__)
+ if (domain->ftnptrs_hash) {
+ g_hash_table_destroy (domain->ftnptrs_hash);
+ domain->ftnptrs_hash = NULL;
+ }
+#endif
DeleteCriticalSection (&domain->finalizable_objects_hash_lock);
DeleteCriticalSection (&domain->assemblies_lock);
static gpointer
mini_create_ftnptr (MonoDomain *domain, gpointer addr)
{
-#ifdef __ia64__
- gpointer *desc;
+#if !defined(__ia64__) && !defined(__ppc64__) && !defined(__powerpc64__)
+ return addr;
+#else
+ gpointer* desc = NULL;
+
+ if ((desc = g_hash_table_lookup (domain->ftnptrs_hash, addr)))
+ return desc;
+# ifdef __ia64__
desc = mono_domain_code_reserve (domain, 2 * sizeof (gpointer));
desc [0] = addr;
desc [1] = NULL;
-
- return desc;
-#elif defined(__ppc64__) || defined(__powerpc64__)
+# elif defined(__ppc64__) || defined(__powerpc64__)
gpointer *desc;
desc = mono_domain_alloc0 (domain, 3 * sizeof (gpointer));
desc [0] = addr;
desc [1] = NULL;
desc [2] = NULL;
-
+# endif
+ g_hash_table_insert (domain->ftnptrs_hash, addr, desc);
return desc;
-#else
- return addr;
#endif
}