Skip to content

Commit

Permalink
Enable dedup optimization in FullAOT mode only (#20687)
Browse files Browse the repository at this point in the history
## Description

This PR enables the dedup optimization in FullAOT mode only. The
optimization can only run in FullAOT mode with complete application
context. Without it, the AOT compiler may fail to collect all generic
instances, and the runtime can't find them as they are searched in the
dedup assembly.

## Changes

This PR updates the SDK targets to enable dedup optimization in FullAOT
mode only. This change doesn't depend on any runtime changes.

## Verification

This PR also introduces partial AOT tests. They inspect the bundle for
`aot-instances.dll`, which shouldn't be generated in a partial AOT
compilation setup. Additionally, basic functionality is tested by
asserting at app startup.

## Additional notes

This change should be backported to .NET 8 as well.

Fixes dotnet/runtime#99248
  • Loading branch information
kotlarmilos authored Jun 7, 2024
1 parent 7a868d4 commit 603781b
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 3 deletions.
7 changes: 4 additions & 3 deletions dotnet/targets/Xamarin.Shared.Sdk.targets
Original file line number Diff line number Diff line change
Expand Up @@ -1096,8 +1096,9 @@

<_AOTInputDirectory>$(_IntermediateNativeLibraryDir)aot-input/</_AOTInputDirectory>
<_AOTOutputDirectory>$(_IntermediateNativeLibraryDir)aot-output/</_AOTOutputDirectory>
<_IsDedupEnabled Condition="'$(_IsDedupEnabled)' == ''">true</_IsDedupEnabled>
<_DedupAssembly Condition="'$(_RunAotCompiler)' == 'true' And '$(IsMacEnabled)' == 'true' And '$(_IsDedupEnabled)' == 'true'">$(IntermediateOutputPath)aot-instances.dll</_DedupAssembly>
<!-- Enable dedup optimization only in FullAOT mode -->
<_IsDedupEnabled Condition="'$(_IsDedupEnabled)' == '' And '$(_RunAotCompiler)' == 'true' And '$(MtouchInterpreter)' == '' And '$(IsMacEnabled)' == 'true'">true</_IsDedupEnabled>
<_DedupAssembly Condition="'$(_IsDedupEnabled)' == 'true'">$(IntermediateOutputPath)aot-instances.dll</_DedupAssembly>

<!-- default to 'static' for Mac Catalyst to work around https://github.com/xamarin/xamarin-macios/issues/14686 -->
<_LibMonoLinkMode Condition="'$(_LibMonoLinkMode)' == '' And '$(_PlatformName)' == 'MacCatalyst'">static</_LibMonoLinkMode>
Expand Down Expand Up @@ -1219,7 +1220,7 @@
</Target>

<Target Name="_CreateAOTDedupAssembly"
Condition="'$(_RunAotCompiler)' == 'true' And '$(IsMacEnabled)' == 'true'"
Condition="'$(_IsDedupEnabled)' == 'true'"
DependsOnTargets="_ComputeManagedAssemblyToLink"
BeforeTargets="PrepareForILLink"
Inputs="$(MSBuildThisFileFullPath)"
Expand Down
40 changes: 40 additions & 0 deletions tests/dotnet/UnitTests/ProjectTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -1917,5 +1917,45 @@ public void RaisesAppDomainUnhandledExceptionEvent (ApplePlatform platform)
var output = ExecuteWithMagicWordAndAssert (appExecutable, env);
}
}

bool FindAssembly (string path, string dllName)
{
foreach (string file in Directory.GetFiles (path, "*.dll", SearchOption.AllDirectories)) {
if (Path.GetFileName (file).Equals (dllName, StringComparison.OrdinalIgnoreCase)) {
return true;
}
}

return false;
}

[Test]
[TestCase (ApplePlatform.iOS, "ios-arm64;", "-all,System.Private.CoreLib")]
[TestCase (ApplePlatform.iOS, "ios-arm64;", "all,-System.Private.CoreLib")]
[TestCase (ApplePlatform.MacCatalyst, "maccatalyst-arm64;maccatalyst-x64", "-all,System.Private.CoreLib")]
[TestCase (ApplePlatform.MacCatalyst, "maccatalyst-arm64;maccatalyst-x64", "all,-System.Private.CoreLib")]
[TestCase (ApplePlatform.TVOS, "tvos-arm64;", "-all,System.Private.CoreLib")]
[TestCase (ApplePlatform.TVOS, "tvos-arm64;", "all,-System.Private.CoreLib")]
public void PartialAOTTest (ApplePlatform platform, string runtimeIdentifiers, string mtouchInterpreter)
{
var project = "MySimpleApp";
Configuration.IgnoreIfIgnoredPlatform (platform);
Configuration.AssertRuntimeIdentifiersAvailable (platform, runtimeIdentifiers);

var project_path = GetProjectPath (project, runtimeIdentifiers: runtimeIdentifiers, platform: platform, out var appPath);
Clean (project_path);
var properties = GetDefaultProperties (runtimeIdentifiers);
properties ["MtouchInterpreter"] = $"\"{mtouchInterpreter}\"";

DotNet.AssertBuild (project_path, properties);

Assert.True (!FindAssembly (appPath, "aot-instances.dll"), "Dedup optimization shouldn't been enabled for partial AOT compilation");

var appExecutable = GetNativeExecutable (platform, appPath);

if (CanExecute (platform, runtimeIdentifiers)) {
ExecuteWithMagicWordAndAssert (appExecutable);
}
}
}
}

0 comments on commit 603781b

Please sign in to comment.