[runtime] Add support for initializing in an embedder mode.

This commit is contained in:
Rolf Bjarne Kvinge 2017-04-10 06:48:35 +02:00
Родитель 38960a5b9a
Коммит 1afae37c7f
6 изменённых файлов: 53 добавлений и 13 удалений

Просмотреть файл

@ -530,10 +530,12 @@ app_initialize (xamarin_initialize_data *data, bool is_extension)
#define __XAMARIN_MAC_RELAUNCH_APP__ "__XAMARIN_MAC_RELAUNCH_APP__"
int xamarin_main (int argc, char **argv, bool is_extension)
int xamarin_main (int argc, char **argv, enum XamarinLaunchMode launch_mode)
{
xamarin_initialize_data data = { 0 };
bool is_extension = launch_mode == XamarinLaunchModeExtension;
if (getcwd (original_working_directory_path, sizeof (original_working_directory_path)) == NULL)
original_working_directory_path [0] = '\0';
@ -596,7 +598,8 @@ int xamarin_main (int argc, char **argv, bool is_extension)
*ptr++ = argv [i];
*ptr = NULL;
if (is_extension) {
switch (launch_mode) {
case XamarinLaunchModeExtension: {
void * libExtensionHandle = dlopen ("/usr/lib/libextension.dylib", RTLD_LAZY);
if (libExtensionHandle == nil)
exit_with_message ("Unable to load libextension.dylib", data.basename, false);
@ -610,8 +613,17 @@ int xamarin_main (int argc, char **argv, bool is_extension)
rv = (*extensionMain) (new_argc, new_argv);
dlclose (libExtensionHandle);
} else {
break;
}
case XamarinLaunchModeApp:
rv = mono_main (new_argc, new_argv);
break;
case XamarinLaunchModeEmbedded:
// do nothing
break;
default:
xamarin_assertion_message ("Invalid launch mode: %i.", launch_mode);
break;
}
free (new_argv);
@ -622,10 +634,10 @@ int xamarin_main (int argc, char **argv, bool is_extension)
int main (int argc, char **argv)
{
return xamarin_main (argc, argv, false);
return xamarin_main (argc, argv, XamarinLaunchModeApp);
}
int xamarin_mac_extension_main (int argc, char **argv)
{
return xamarin_main (argc, argv, true);
return xamarin_main (argc, argv, XamarinLaunchModeEmbedded);
}

Просмотреть файл

@ -220,7 +220,7 @@ extern void mono_gc_init_finalizer_thread (void);
*/
int
xamarin_main (int argc, char *argv[], bool is_extension)
xamarin_main (int argc, char *argv[], enum XamarinLaunchMode launch_mode)
{
// COOP: ?
// + 1 for the initial "monotouch" +1 for the final NULL = +2.
@ -234,7 +234,7 @@ xamarin_main (int argc, char *argv[], bool is_extension)
patch_sigaction ();
#endif
xamarin_is_extension = is_extension;
xamarin_is_extension = launch_mode == XamarinLaunchModeExtension;
memset (managed_argv, 0, sizeof (char*) * (argc + 2));
managed_argv [0] = "monotouch";
@ -464,7 +464,8 @@ xamarin_main (int argc, char *argv[], bool is_extension)
DEBUG_LAUNCH_TIME_PRINT ("Total initialization time");
int rv = 0;
if (is_extension) {
switch (launch_mode) {
case XamarinLaunchModeExtension:
char base_dir [1024];
char config_file_name [1024];
@ -476,8 +477,16 @@ xamarin_main (int argc, char *argv[], bool is_extension)
MONO_ENTER_GC_SAFE;
rv = xamarin_extension_main (argc, argv);
MONO_EXIT_GC_SAFE;
} else {
break;
case XamarinLaunchModeApp:
mono_jit_exec (mono_domain_get (), assembly, managed_argc, managed_argv);
break;
case XamarinLaunchModeEmbedded:
// do nothing
break;
default:
xamarin_assertion_message ("Invalid launch mode: %i.", launch_mode);
break;
}
return rv;

Просмотреть файл

@ -1099,6 +1099,18 @@ print_callback (const char *string, mono_bool is_stdout)
PRINT ("%s", string);
}
void
xamarin_initialize_embedded ()
{
static bool initialized = false;
if (initialized)
return;
initialized = true;
char *argv[] = { (char *) "embedded" };
xamarin_main (1, argv, XamarinLaunchModeEmbedded);
}
void
xamarin_initialize ()
{

Просмотреть файл

@ -98,6 +98,12 @@ enum NSObjectFlags {
NSObjectFlagsHasManagedRef = 32,
};
enum XamarinLaunchMode {
XamarinLaunchModeApp = 0,
XamarinLaunchModeExtension = 1,
XamarinLaunchModeEmbedded = 2,
};
struct AssemblyLocation {
const char *assembly_name; // base name (without extension) of the assembly
const char *location; // the directory where the assembly is
@ -109,6 +115,7 @@ struct AssemblyLocations {
};
void xamarin_initialize ();
void xamarin_initialize_embedded (); /* STABLE */
void xamarin_assertion_message (const char *msg, ...) __attribute__((__noreturn__));
const char * xamarin_get_bundle_path (); /* Public API */
@ -159,7 +166,7 @@ void xamarin_create_managed_ref (id self, void * managed_object, bool retain);
void xamarin_release_managed_ref (id self, MonoObject *managed_obj);
void xamarin_notify_dealloc (id self, int gchandle);
int xamarin_main (int argc, char *argv[], bool is_extension);
int xamarin_main (int argc, char *argv[], enum XamarinLaunchMode launch_mode);
char * xamarin_type_get_full_name (MonoType *type, guint32 *exception_gchandle); // return value must be freed with 'mono_free'
char * xamarin_class_get_full_name (MonoClass *klass, guint32 *exception_gchandle); // return value must be freed with 'mono_free'

Просмотреть файл

@ -680,9 +680,9 @@ namespace Xamarin.Bundler
// the name of the executable must be the bundle id (reverse dns notation)
// but we do not want to impose that (ugly) restriction to the managed .exe / project name / ...
sw.WriteLine ("\targv [0] = (char *) \"{0}\";", Path.GetFileNameWithoutExtension (app.RootAssemblies [0]));
sw.WriteLine ("\tint rv = xamarin_main (argc, argv, true);");
sw.WriteLine ("\tint rv = xamarin_main (argc, argv, XamarinLaunchModeApp);");
} else {
sw.WriteLine ("\tint rv = xamarin_main (argc, argv, false);");
sw.WriteLine ("\tint rv = xamarin_main (argc, argv, XamarinLaunchModeExtension);");
}
sw.WriteLine ("\t[pool drain];");
sw.WriteLine ("\treturn rv;");

Просмотреть файл

@ -28,7 +28,7 @@ void xamarin_setup_impl ()
int
main (int argc, char** argv)
{
@autoreleasepool { return xamarin_main (argc, argv, false); }
@autoreleasepool { return xamarin_main (argc, argv, XamarinLaunchModeApp); }
}