diff options
Diffstat (limited to 'src/coreclr/hosts/unixcoreconsole/coreconsole.cpp')
-rw-r--r-- | src/coreclr/hosts/unixcoreconsole/coreconsole.cpp | 162 |
1 files changed, 162 insertions, 0 deletions
diff --git a/src/coreclr/hosts/unixcoreconsole/coreconsole.cpp b/src/coreclr/hosts/unixcoreconsole/coreconsole.cpp new file mode 100644 index 0000000000..e43124d0f2 --- /dev/null +++ b/src/coreclr/hosts/unixcoreconsole/coreconsole.cpp @@ -0,0 +1,162 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. +// See the LICENSE file in the project root for more information. + +// +// A simple CoreCLR host that runs a managed binary with the same name as this executable but with the *.dll extension +// The dll binary must contain a main entry point. +// + +#include <coreruncommon.h> +#include <string> +#include <string.h> +#include <sys/stat.h> + +// Display the help text +void DisplayUsage() +{ + fprintf( + stderr, + "Runs executables on CoreCLR\n\n" + "Usage: <program> [OPTIONS] [ARGUMENTS]\n" + "Runs <program>.dll on CoreCLR.\n\n" + "Options:\n" + "-_c path to libcoreclr.so and the managed CLR assemblies.\n" + "-_h show this help message. \n"); +} + +// Parse the command line arguments +bool ParseArguments( + const int argc, + const char* argv[], + const char** clrFilesPath, + int* managedAssemblyArgc, + const char*** managedAssemblyArgv) +{ + bool success = true; + + *clrFilesPath = nullptr; + *managedAssemblyArgv = nullptr; + *managedAssemblyArgc = 0; + + for (int i = 1; i < argc; i++) + { + // Check for options. Options to the Unix coreconsole are prefixed with '-_' to match the convention + // used in the Windows version of coreconsole. + if (strncmp(argv[i], "-_", 2) == 0) + { + // Path to the libcoreclr.so and the managed CLR assemblies + if (strcmp(argv[i], "-_c") == 0) + { + i++; + if (i < argc) + { + *clrFilesPath = argv[i]; + } + else + { + fprintf(stderr, "Option %s: missing path\n", argv[i - 1]); + success = false; + break; + } + } + else if (strcmp(argv[i], "-_h") == 0) + { + DisplayUsage(); + success = false; + break; + } + else + { + fprintf(stderr, "Unknown option %s\n", argv[i]); + success = false; + break; + } + } + else + { + // We treat everything starting from the first non-option argument as arguments + // to the managed assembly. + *managedAssemblyArgc = argc - i; + if (*managedAssemblyArgc != 0) + { + *managedAssemblyArgv = &argv[i]; + } + + break; + } + } + + return success; +} + +int main(const int argc, const char* argv[]) +{ + // Make sure we have a full path for argv[0]. + std::string argv0AbsolutePath; + std::string entryPointExecutablePath; + + if (!GetEntrypointExecutableAbsolutePath(entryPointExecutablePath)) + { + perror("Could not get full path to current executable"); + return -1; + } + + if (!GetAbsolutePath(entryPointExecutablePath.c_str(), argv0AbsolutePath)) + { + perror("Could not normalize full path to current executable"); + return -1; + } + + // We will try to load the managed assembly with the same name as this executable + // but with the .dll extension. + std::string programPath(argv0AbsolutePath); + programPath.append(".dll"); + const char* managedAssemblyAbsolutePath = programPath.c_str(); + + // Check if the specified managed assembly file exists + struct stat sb; + if (stat(managedAssemblyAbsolutePath, &sb) == -1) + { + perror("Managed assembly not found"); + return -1; + } + + // Verify that the managed assembly path points to a file + if (!S_ISREG(sb.st_mode)) + { + fprintf(stderr, "The specified managed assembly is not a file\n"); + return -1; + } + + const char* clrFilesPath; + const char** managedAssemblyArgv; + int managedAssemblyArgc; + + if (!ParseArguments( + argc, + argv, + &clrFilesPath, + &managedAssemblyArgc, + &managedAssemblyArgv + )) + { + // Invalid command line + return -1; + } + + std::string clrFilesAbsolutePath; + if(!GetClrFilesAbsolutePath(argv0AbsolutePath.c_str(), clrFilesPath, clrFilesAbsolutePath)) + { + return -1; + } + + int exitCode = ExecuteManagedAssembly( + argv0AbsolutePath.c_str(), + clrFilesAbsolutePath.c_str(), + managedAssemblyAbsolutePath, + managedAssemblyArgc, + managedAssemblyArgv); + + return exitCode; +} |