Skip to content

Stop setting separate properties for BUNDLE_PROBE, HOSTPOLICY_EMBEDDED, PINVOKE_OVERRIDE #92448

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 2 commits into from
Sep 27, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions docs/design/features/host-runtime-information.md
Original file line number Diff line number Diff line change
Expand Up @@ -84,10 +84,16 @@ List of directory paths corresponding to shared store paths and additional probi

Hex string representation of a function pointer. It is set when running a single-file application. The function is called by the runtime to look for assemblies bundled into the application. The expected signature is defined as `BundleProbeFn` in [`coreclrhost.h`](/src/coreclr/hosts/inc/coreclrhost.h)

**.NET 9 and above** This property is no longer set by the host. `host_runtime_contract.bundle_probe` is set when running a single-file application.

`HOSTPOLICY_EMBEDDED`

Indicates whether or not [`hostpolicy`](./host-components.md#host-policy) is embedded in the host executable. It is set to `true` when running a self-contained single-file application.

**.NET 9 and above** This property is no longer set by the host or read by the runtime. Self-contained single-file includes both host and runtime components in the executable, so the information is known at build-time.

`PINVOKE_OVERRIDE`

Hex string representation of a function pointer. It is set when running a self-contained single-file application. The function is called by the runtime to check for redirected p/invokes. The expected signature is defined as `PInvokeOverrideFn` in [`coreclrhost.h`](/src/coreclr/hosts/inc/coreclrhost.h) and [`mono-private-unstable-types.h`](/src/native/public/mono/metadata/details/mono-private-unstable-types.h).

**.NET 9 and above** This property is no longer set by the host. `host_runtime_contract.pinvoke_override` is set when running a self-contained single-file application.
10 changes: 0 additions & 10 deletions src/coreclr/dlls/mscoree/exports.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -138,7 +138,6 @@ static void ConvertConfigPropertiesToUnicode(
LPCWSTR** propertyValuesWRef,
BundleProbeFn** bundleProbe,
PInvokeOverrideFn** pinvokeOverride,
bool* hostPolicyEmbedded,
host_runtime_contract** hostContract)
{
LPCWSTR* propertyKeysW = new (nothrow) LPCWSTR[propertyCount];
Expand Down Expand Up @@ -170,11 +169,6 @@ static void ConvertConfigPropertiesToUnicode(
if (*pinvokeOverride == nullptr)
*pinvokeOverride = (PInvokeOverrideFn*)u16_strtoui64(propertyValuesW[propertyIndex], nullptr, 0);
}
else if (strcmp(propertyKeys[propertyIndex], HOST_PROPERTY_HOSTPOLICY_EMBEDDED) == 0)
{
// The HOSTPOLICY_EMBEDDED property indicates if the executable has hostpolicy statically linked in
*hostPolicyEmbedded = (u16_strcmp(propertyValuesW[propertyIndex], W("true")) == 0);
}
else if (strcmp(propertyKeys[propertyIndex], HOST_PROPERTY_RUNTIME_CONTRACT) == 0)
{
// Host contract is passed in as the value of HOST_RUNTIME_CONTRACT property (encoded as a string).
Expand Down Expand Up @@ -252,7 +246,6 @@ int coreclr_initialize(
LPCWSTR* propertyKeysW;
LPCWSTR* propertyValuesW;
BundleProbeFn* bundleProbe = nullptr;
bool hostPolicyEmbedded = false;
PInvokeOverrideFn* pinvokeOverride = nullptr;
host_runtime_contract* hostContract = nullptr;

Expand All @@ -268,7 +261,6 @@ int coreclr_initialize(
&propertyValuesW,
&bundleProbe,
&pinvokeOverride,
&hostPolicyEmbedded,
&hostContract);

#ifdef TARGET_UNIX
Expand All @@ -283,8 +275,6 @@ int coreclr_initialize(
}
#endif

g_hostpolicy_embedded = hostPolicyEmbedded;

if (hostContract != nullptr)
{
HostInformation::SetContract(hostContract);
Expand Down
3 changes: 1 addition & 2 deletions src/coreclr/vm/ceemain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -224,13 +224,12 @@ extern "C" HRESULT __cdecl CorDBGetInterface(DebugInterface** rcInterface);

// g_coreclr_embedded indicates that coreclr is linked directly into the program
// g_hostpolicy_embedded indicates that the hostpolicy library is linked directly into the executable
// Note: that it can happen that the hostpolicy is embedded but coreclr isn't (on Windows singlefilehost is built that way)
#ifdef CORECLR_EMBEDDED
bool g_coreclr_embedded = true;
bool g_hostpolicy_embedded = true; // We always embed hostpolicy if coreclr is also embedded
#else
bool g_coreclr_embedded = false;
bool g_hostpolicy_embedded = false; // In this case the value may come from a runtime property and may change
bool g_hostpolicy_embedded = false;
#endif

// Remember how the last startup of EE went.
Expand Down
29 changes: 22 additions & 7 deletions src/mono/mono/mini/monovm.c
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,8 @@

#include <mono/metadata/components.h>

#include <corehost/host_runtime_contract.h>

static MonoCoreTrustedPlatformAssemblies *trusted_platform_assemblies;
static MonoCoreLookupPaths *native_lib_paths;
static MonoCoreLookupPaths *app_paths;
Expand Down Expand Up @@ -187,26 +189,39 @@ parse_properties (int propertyCount, const char **propertyKeys, const char **pro
// A partial list of relevant properties is at:
// https://docs.microsoft.com/en-us/dotnet/core/tutorials/netcore-hosting#step-3---prepare-runtime-properties

PInvokeOverrideFn override_fn = NULL;
for (int i = 0; i < propertyCount; ++i) {
size_t prop_len = strlen (propertyKeys [i]);
if (prop_len == 27 && !strncmp (propertyKeys [i], "TRUSTED_PLATFORM_ASSEMBLIES", 27)) {
if (prop_len == 27 && !strncmp (propertyKeys [i], HOST_PROPERTY_TRUSTED_PLATFORM_ASSEMBLIES, 27)) {
parse_trusted_platform_assemblies (propertyValues[i]);
} else if (prop_len == 9 && !strncmp (propertyKeys [i], "APP_PATHS", 9)) {
} else if (prop_len == 9 && !strncmp (propertyKeys [i], HOST_PROPERTY_APP_PATHS, 9)) {
app_paths = parse_lookup_paths (propertyValues [i]);
} else if (prop_len == 23 && !strncmp (propertyKeys [i], "PLATFORM_RESOURCE_ROOTS", 23)) {
} else if (prop_len == 23 && !strncmp (propertyKeys [i], HOST_PROPERTY_PLATFORM_RESOURCE_ROOTS, 23)) {
platform_resource_roots = parse_lookup_paths (propertyValues [i]);
} else if (prop_len == 29 && !strncmp (propertyKeys [i], "NATIVE_DLL_SEARCH_DIRECTORIES", 29)) {
} else if (prop_len == 29 && !strncmp (propertyKeys [i], HOST_PROPERTY_NATIVE_DLL_SEARCH_DIRECTORIES, 29)) {
native_lib_paths = parse_lookup_paths (propertyValues [i]);
} else if (prop_len == 16 && !strncmp (propertyKeys [i], "PINVOKE_OVERRIDE", 16)) {
PInvokeOverrideFn override_fn = (PInvokeOverrideFn)(uintptr_t)strtoull (propertyValues [i], NULL, 0);
mono_loader_install_pinvoke_override (override_fn);
} else if (prop_len == 16 && !strncmp (propertyKeys [i], HOST_PROPERTY_PINVOKE_OVERRIDE, 16)) {
if (override_fn == NULL) {
override_fn = (PInvokeOverrideFn)(uintptr_t)strtoull (propertyValues [i], NULL, 0);
}
} else if (prop_len == STRING_LENGTH(HOST_PROPERTY_RUNTIME_CONTRACT) && !strncmp (propertyKeys [i], HOST_PROPERTY_RUNTIME_CONTRACT, STRING_LENGTH(HOST_PROPERTY_RUNTIME_CONTRACT))) {
// Functions in HOST_RUNTIME_CONTRACT have priority over the individual properties
// for callbacks, so we set them as long as the contract has a non-null function.
struct host_runtime_contract* contract = (struct host_runtime_contract*)(uintptr_t)strtoull (propertyValues [i], NULL, 0);
if (contract->pinvoke_override != NULL) {
override_fn = (PInvokeOverrideFn)contract->pinvoke_override;
}
} else {
#if 0
// can't use mono logger, it's not initialized yet.
printf ("\t Unprocessed property %03d '%s': <%s>\n", i, propertyKeys[i], propertyValues[i]);
#endif
}
}

if (override_fn != NULL)
mono_loader_install_pinvoke_override (override_fn);

return TRUE;
}

Expand Down
2 changes: 0 additions & 2 deletions src/native/corehost/apphost/static/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -36,10 +36,8 @@ set(HEADERS
add_definitions(-D_NO_ASYNCRTIMP)
add_definitions(-D_NO_PPLXIMP)
remove_definitions(-DEXPORT_SHARED_API)
add_definitions(-DHOSTPOLICY_EMBEDDED)
add_definitions(-DNATIVE_LIBS_EMBEDDED)


include(../../fxr/files.cmake)
include(../../hostpolicy/files.cmake)
include(../../hostcommon/files.cmake)
Expand Down
1 change: 0 additions & 1 deletion src/native/corehost/host_runtime_contract.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@
#define HOST_PROPERTY_APP_PATHS "APP_PATHS"
#define HOST_PROPERTY_BUNDLE_PROBE "BUNDLE_PROBE"
#define HOST_PROPERTY_ENTRY_ASSEMBLY_NAME "ENTRY_ASSEMBLY_NAME"
#define HOST_PROPERTY_HOSTPOLICY_EMBEDDED "HOSTPOLICY_EMBEDDED"
#define HOST_PROPERTY_NATIVE_DLL_SEARCH_DIRECTORIES "NATIVE_DLL_SEARCH_DIRECTORIES"
#define HOST_PROPERTY_PINVOKE_OVERRIDE "PINVOKE_OVERRIDE"
#define HOST_PROPERTY_PLATFORM_RESOURCE_ROOTS "PLATFORM_RESOURCE_ROOTS"
Expand Down
3 changes: 0 additions & 3 deletions src/native/corehost/hostpolicy/coreclr.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -166,9 +166,6 @@ namespace
_X("STARTUP_HOOKS"),
_X("APP_PATHS"),
_X("RUNTIME_IDENTIFIER"),
_X("BUNDLE_PROBE"),
_X("HOSTPOLICY_EMBEDDED"),
_X("PINVOKE_OVERRIDE")
};

static_assert((sizeof(PropertyNameMapping) / sizeof(*PropertyNameMapping)) == static_cast<size_t>(common_property::Last), "Invalid property count");
Expand Down
3 changes: 0 additions & 3 deletions src/native/corehost/hostpolicy/coreclr.h
Original file line number Diff line number Diff line change
Expand Up @@ -64,9 +64,6 @@ enum class common_property
StartUpHooks,
AppPaths,
RuntimeIdentifier,
BundleProbe,
HostPolicyEmbedded,
PInvokeOverride,
// Sentinel value - new values should be defined above
Last
};
Expand Down
38 changes: 0 additions & 38 deletions src/native/corehost/hostpolicy/hostpolicy_context.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -329,44 +329,6 @@ int hostpolicy_context_t::initialize(const hostpolicy_init_t &hostpolicy_init, c
coreclr_properties.add(common_property::StartUpHooks, startup_hooks.c_str());
}

// Single-File Bundle Probe
if (bundle::info_t::is_single_file_bundle())
{
// Encode the bundle_probe function pointer as a string, and pass it to the runtime.
pal::stringstream_t ptr_stream;
ptr_stream << "0x" << std::hex << (size_t)(&bundle_probe);

if (!coreclr_properties.add(common_property::BundleProbe, ptr_stream.str().c_str()))
{
log_duplicate_property_error(coreclr_property_bag_t::common_property_to_string(common_property::BundleProbe));
return StatusCode::LibHostDuplicateProperty;
}
}

#if defined(NATIVE_LIBS_EMBEDDED)
// PInvoke Override
if (bundle::info_t::is_single_file_bundle())
{
// Encode the pinvoke_override function pointer as a string, and pass it to the runtime.
pal::stringstream_t ptr_stream;
ptr_stream << "0x" << std::hex << (size_t)(&pinvoke_override);

if (!coreclr_properties.add(common_property::PInvokeOverride, ptr_stream.str().c_str()))
{
log_duplicate_property_error(coreclr_property_bag_t::common_property_to_string(common_property::PInvokeOverride));
return StatusCode::LibHostDuplicateProperty;
}
}
#endif

#if defined(HOSTPOLICY_EMBEDDED)
if (!coreclr_properties.add(common_property::HostPolicyEmbedded, _X("true")))
{
log_duplicate_property_error(coreclr_property_bag_t::common_property_to_string(common_property::HostPolicyEmbedded));
return StatusCode::LibHostDuplicateProperty;
}
#endif

{
host_contract = { sizeof(host_runtime_contract), this };
if (bundle::info_t::is_single_file_bundle())
Expand Down