Skip to content

Conversation

@jonathanpeppers
Copy link
Member

Context: https://github.com/dotnet/runtime/blob/242f7b23752599f22157268de41fee91cb97ef6c/docs/design/features/host-startup-hook.md

.NET has a concept of a "startup hook", which appears to work fine
on Mono if you set:

env.txt
    DOTNET_STARTUP_HOOKS=StartupHook
(MSBuild)
    <StartupHookSupport>true</StartupHookSupport>
    <RuntimeHostConfigurationOption Include="STARTUP_HOOKS" Value="StartupHook" />

The startup hook is a managed assembly with a static method, in the
"global" namespace:

class StartupHook
{
    public static void Initialize()
    {
        // ...
    }
}

When the runtime starts, it will call StartupHook.Initialize() before
any other managed code is executed.

dotnet watch (Hot Reload) relies on this feature.

I added a test to Mono.Android-Tests to verify that the startup hook
was called.

This is not yet working on CoreCLR on Android, investigation ongoing.

@jonathanpeppers
Copy link
Member Author

@rolfbjarne do you know if this works on iOS/Catalyst?

@rolfbjarne
Copy link
Member

@rolfbjarne do you know if this works on iOS/Catalyst?

I did a quick test, and it doesn't seem to work, so I filed an issue: dotnet/macios#24492

Context: https://github.com/dotnet/runtime/blob/242f7b23752599f22157268de41fee91cb97ef6c/docs/design/features/host-startup-hook.md

.NET has a concept of a "startup hook", which appears to work fine
on Mono if you set:

    env.txt
        DOTNET_STARTUP_HOOKS=StartupHook
    (MSBuild)
        <StartupHookSupport>true</StartupHookSupport>
        <RuntimeHostConfigurationOption Include="STARTUP_HOOKS" Value="StartupHook" />

The startup hook is a managed assembly with a static method, in the
"global" namespace:

    class StartupHook
    {
        public static void Initialize()
        {
            // ...
        }
    }

When the runtime starts, it will call `StartupHook.Initialize()` before
any other managed code is executed.

`dotnet watch` (Hot Reload) relies on this feature.

I added a test to `Mono.Android-Tests` to verify that the startup hook
was called.

This is not yet working on CoreCLR on Android, investigation ongoing.
@jonathanpeppers jonathanpeppers force-pushed the dev/peppers/startup-hook branch from a09103f to 17176cd Compare January 8, 2026 23:23
@jonathanpeppers
Copy link
Member Author

The one test failure is a flaky test, we can ignore:

image

@jonathanpeppers jonathanpeppers marked this pull request as ready for review January 12, 2026 15:19
return;
}

var method = type.GetMethod (methodName,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it make sense to use the [UnsafeAccessor] attribute to avoid using reflection here?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like you can only do that if a type is public, and it's internal in System.Private.CoreLib.

}

[RequiresUnreferencedCode ("Uses reflection to access System.StartupHookProvider.")]
static void RunStartupHooks ()
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do you have a test to ensure this method is really trimmed away for a Release build (or when startuphook support is not enabled)?

Copy link
Member Author

@jonathanpeppers jonathanpeppers Jan 12, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, we run the new test in both trimmed, AOT, all runtimes, etc.

They have a line in dotnet/runtime to preserve it, too:

https://github.com/dotnet/runtime/blob/eaf635955da0410b94cb8607f6e598c51245f830/src/mono/System.Private.CoreLib/src/ILLink/ILLink.Descriptors.xml#L656-L663

@jonathanpeppers jonathanpeppers merged commit b2332ca into main Jan 12, 2026
57 of 59 checks passed
@jonathanpeppers jonathanpeppers deleted the dev/peppers/startup-hook branch January 12, 2026 17:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants