From cef0a831b8292f1f2ab52cac779e51ae28a8364f Mon Sep 17 00:00:00 2001 From: Chet Husk Date: Thu, 16 Jul 2026 17:42:09 -0500 Subject: [PATCH 1/6] Enable NativeAOT CLI for source build Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: eaed26de-227d-466f-a063-c09bc7334995 --- src/Layout/Directory.Build.props | 33 +++++++++---------- src/Layout/redist/redist.csproj | 8 ++--- .../redist/targets/GenerateLayout.targets | 24 +++++++------- 3 files changed, 33 insertions(+), 32 deletions(-) diff --git a/src/Layout/Directory.Build.props b/src/Layout/Directory.Build.props index 05792e065bd6..1070e75a763e 100644 --- a/src/Layout/Directory.Build.props +++ b/src/Layout/Directory.Build.props @@ -13,6 +13,8 @@ true + + - <_DotnetAotTargetRidSupported Condition="$(TargetRid.StartsWith('win')) or $(TargetRid.StartsWith('linux')) or $(TargetRid.StartsWith('osx'))">true + <_DotnetAotTargetRidSupported Condition="$(PortableTargetRid.StartsWith('win')) or $(PortableTargetRid.StartsWith('linux')) or $(PortableTargetRid.StartsWith('osx'))">true - - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('WINDOWS')) and $(TargetRid.StartsWith('win'))">true - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('OSX')) and $(TargetRid.StartsWith('osx'))">true - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('LINUX')) and $(TargetRid.StartsWith('linux'))">true + + <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('WINDOWS')) and '$(TargetOS)' == 'windows'">true + <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('OSX')) and '$(TargetOS)' == 'osx'">true + <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('LINUX')) and '$(TargetOS)' == 'linux'">true - <_DotnetAotIsNativeBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' == '$(BuildArchitecture)' and '$(CrossBuild)' != 'true' and '$(DotNetBuildSourceOnly)' != 'true' and !$(TargetRid.StartsWith('linux-musl'))">true + <_DotnetAotIsNativeBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' == '$(BuildArchitecture)' and '$(CrossBuild)' != 'true' and !$(PortableTargetRid.StartsWith('linux-musl'))">true - <_DotnetAotIsCrossBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' != '$(BuildArchitecture)' and '$(DotNetBuildSourceOnly)' != 'true' and !$(TargetRid.StartsWith('linux-musl')) and !($(TargetRid.StartsWith('linux')) and '$(CrossBuild)' != 'true')">true + <_DotnetAotIsCrossBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' != '$(BuildArchitecture)' and !$(PortableTargetRid.StartsWith('linux-musl')) and !($(PortableTargetRid.StartsWith('linux')) and '$(CrossBuild)' != 'true')">true - <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == '' and '$(_DotnetAotTargetRidSupported)' == 'true' and ('$(_DotnetAotIsNativeBuild)' == 'true' or '$(_DotnetAotIsCrossBuild)' == 'true')">true + <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == '' and '$(_DotnetAotTargetRidSupported)' == 'true' and '$(NativeAotSupported)' == 'true' and '$(DotNetBuildUseMonoRuntime)' != 'true' and ('$(_DotnetAotIsNativeBuild)' == 'true' or '$(_DotnetAotIsCrossBuild)' == 'true')">true <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == ''">false @@ -98,8 +99,6 @@ )">true - - true true diff --git a/src/Layout/redist/redist.csproj b/src/Layout/redist/redist.csproj index ead3a742dec4..198344108a59 100644 --- a/src/Layout/redist/redist.csproj +++ b/src/Layout/redist/redist.csproj @@ -88,10 +88,10 @@ race over shared bin\ and obj\ directories. This ProjectReference sequences the outer Build to complete before redist's GenerateSdkLayout target runs. - Conditioned on the same check as the PublishDotnetAot target itself (_ShouldPublishDotnetAot); - when NativeAOT publish doesn't run (e.g. source-build with TargetRid like centos.10-x64), - pulling dotnet-aot.csproj into the restore graph would demand the ILCompiler RID-specific - runtime pack, which isn't available from source-built feeds (NU1100). --> + Conditioned on the same check as the PublishDotnetAot target itself (_ShouldPublishDotnetAot) + so unsupported target platforms don't pull NativeAOT compiler/runtime packs into the restore + graph. Supported Source Build configurations produce these packs from source and retain this + project reference. --> diff --git a/src/Layout/redist/targets/GenerateLayout.targets b/src/Layout/redist/targets/GenerateLayout.targets index 10421dfe99ff..b54cf9fa359c 100644 --- a/src/Layout/redist/targets/GenerateLayout.targets +++ b/src/Layout/redist/targets/GenerateLayout.targets @@ -532,11 +532,11 @@ them entirely in native code, falling back to the managed dotnet.dll for other commands. The output is placed next to dotnet.dll so it's packaged with the SDK. - Runs for native builds (target OS/arch match the build host) on supported platforms, and for - same-OS cross-arch builds where NativeAOT targets a different architecture from the build host - (win-x64 -> win-arm64, osx-x64 -> osx-arm64, and Linux via the azurelinux cross containers that - provide a cross toolchain and target sysroot via ROOTFS_DIR). See the _ShouldPublishDotnetAot - property in src/Layout/Directory.Build.props. + Runs for native builds (target OS/arch match the build host) on supported platforms, including + Source Build with a distro-specific RID, and for same-OS cross-arch builds where NativeAOT targets + a different architecture from the build host (win-x64 -> win-arm64, osx-x64 -> osx-arm64, and + Linux via the azurelinux cross containers that provide a cross toolchain and target sysroot via + ROOTFS_DIR). See the _ShouldPublishDotnetAot property in src/Layout/Directory.Build.props. --> @@ -550,14 +550,16 @@ <_DotnetAotPublishProperties>_IsPublishing=true - <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);CrossBuild=true;TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid) + <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true' or '$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid) + <_DotnetAotPublishProperties Condition="'$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);DotNetBuildSourceOnly=true + <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);CrossBuild=true - $(TargetRid) + $(TargetRid) + $(PortableTargetRid) true + + + + Microsoft.NETCore.App.Runtime.$(TargetRid) + $(PortableTargetRid) + + + Microsoft.NETCore.App.Runtime.NativeAOT.$(TargetRid) + + + diff --git a/src/Layout/redist/targets/GenerateLayout.targets b/src/Layout/redist/targets/GenerateLayout.targets index b54cf9fa359c..5968123354bf 100644 --- a/src/Layout/redist/targets/GenerateLayout.targets +++ b/src/Layout/redist/targets/GenerateLayout.targets @@ -551,10 +551,11 @@ <_DotnetAotPublishProperties>_IsPublishing=true <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true' or '$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid) From c58e79e46aada676585789a9a6aa32e062e2113e Mon Sep 17 00:00:00 2001 From: Chet Husk Date: Thu, 16 Jul 2026 23:11:08 -0500 Subject: [PATCH 3/6] Use exact Source Build pack RIDs Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: eaed26de-227d-466f-a063-c09bc7334995 --- Directory.Build.targets | 12 ++++++++-- src/Cli/dotnet-aot/dotnet-aot.csproj | 22 ++----------------- .../redist/targets/GenerateLayout.targets | 9 ++++---- 3 files changed, 16 insertions(+), 27 deletions(-) diff --git a/Directory.Build.targets b/Directory.Build.targets index dbdfed1de973..2ac6aada836e 100644 --- a/Directory.Build.targets +++ b/Directory.Build.targets @@ -50,8 +50,15 @@ Update="Microsoft.NETCore.App" TargetingPackVersion="$(MicrosoftNETCoreAppRefPackageVersion)" RuntimeFrameworkVersion="$(MicrosoftNETCoreAppRuntimePackageVersion)" /> - + + + %(RuntimePackRuntimeIdentifiers);$(TargetRid) + + + $(MicrosoftNETCoreAppRuntimePackageVersion) + %(ILCompilerRuntimeIdentifiers);$(TargetRid) + $(MicrosoftAspNetCoreAppRefPackageVersion) $(SupportedRuntimeIdentifiers) + %(RuntimePackRuntimeIdentifiers);$(TargetRid) $(MicrosoftAspNetCoreAppRefPackageVersion) $(MicrosoftAspNetCoreAppRefPackageVersion) diff --git a/src/Cli/dotnet-aot/dotnet-aot.csproj b/src/Cli/dotnet-aot/dotnet-aot.csproj index abf23c25f78b..e43693142573 100644 --- a/src/Cli/dotnet-aot/dotnet-aot.csproj +++ b/src/Cli/dotnet-aot/dotnet-aot.csproj @@ -52,30 +52,12 @@ Declare RuntimeIdentifier so that centralized NuGet restore (via sdk.slnx) generates the RID-specific target (e.g. net11.0/win-x64) in project.assets.json. Without this, the assets file only has the TFM target and Publish fails with NETSDK1047. - - Source Build can use a distro-specific TargetRid that isn't in the portable RID graph. - Publish against its portable parent while selecting the distro-specific runtime packs below. + Conditioned to platforms where NativeAOT publish is supported. --> - $(TargetRid) - $(PortableTargetRid) + $(TargetRid) true - - - - Microsoft.NETCore.App.Runtime.$(TargetRid) - $(PortableTargetRid) - - - Microsoft.NETCore.App.Runtime.NativeAOT.$(TargetRid) - - - diff --git a/src/Layout/redist/targets/GenerateLayout.targets b/src/Layout/redist/targets/GenerateLayout.targets index 5968123354bf..b54cf9fa359c 100644 --- a/src/Layout/redist/targets/GenerateLayout.targets +++ b/src/Layout/redist/targets/GenerateLayout.targets @@ -551,11 +551,10 @@ <_DotnetAotPublishProperties>_IsPublishing=true <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true' or '$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid) From ff5d5f6cf6990a104ea41429b2a63d906a2d306b Mon Sep 17 00:00:00 2001 From: Chet Husk Date: Fri, 17 Jul 2026 09:49:29 -0500 Subject: [PATCH 4/6] Simplify NativeAOT Source Build properties Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: eaed26de-227d-466f-a063-c09bc7334995 --- src/Layout/Directory.Build.props | 12 +++++------- src/Layout/redist/targets/GenerateLayout.targets | 13 +++++-------- 2 files changed, 10 insertions(+), 15 deletions(-) diff --git a/src/Layout/Directory.Build.props b/src/Layout/Directory.Build.props index 1070e75a763e..570fd4a7a1c3 100644 --- a/src/Layout/Directory.Build.props +++ b/src/Layout/Directory.Build.props @@ -38,17 +38,15 @@ inputs (CrossBuild/TargetArchitecture/TargetRid) are forwarded to the child dotnet-aot Publish in GenerateLayout.targets; ROOTFS_DIR flows via the environment on Linux. --> - <_DotnetAotTargetRidSupported Condition="$(PortableTargetRid.StartsWith('win')) or $(PortableTargetRid.StartsWith('linux')) or $(PortableTargetRid.StartsWith('osx'))">true + <_DotnetAotTargetOSSupported Condition="'$(TargetOS)' == 'windows' or '$(TargetOS)' == 'linux' or '$(TargetOS)' == 'osx'">true - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('WINDOWS')) and '$(TargetOS)' == 'windows'">true - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('OSX')) and '$(TargetOS)' == 'osx'">true - <_DotnetAotIsSameOSBuild Condition="$([MSBuild]::IsOSPlatform('LINUX')) and '$(TargetOS)' == 'linux'">true + <_DotnetAotIsSameOSBuild Condition="'$(TargetOS)' == '$(HostOS)'">true - <_DotnetAotIsNativeBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' == '$(BuildArchitecture)' and '$(CrossBuild)' != 'true' and !$(PortableTargetRid.StartsWith('linux-musl'))">true + <_DotnetAotIsNativeBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' == '$(BuildArchitecture)' and '$(CrossBuild)' != 'true' and '$(OSName)' != 'linux-musl'">true - <_DotnetAotIsCrossBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' != '$(BuildArchitecture)' and !$(PortableTargetRid.StartsWith('linux-musl')) and !($(PortableTargetRid.StartsWith('linux')) and '$(CrossBuild)' != 'true')">true + <_DotnetAotIsCrossBuild Condition="'$(_DotnetAotIsSameOSBuild)' == 'true' and '$(TargetArchitecture)' != '$(BuildArchitecture)' and '$(OSName)' != 'linux-musl' and !('$(TargetOS)' == 'linux' and '$(CrossBuild)' != 'true')">true - <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == '' and '$(_DotnetAotTargetRidSupported)' == 'true' and '$(NativeAotSupported)' == 'true' and '$(DotNetBuildUseMonoRuntime)' != 'true' and ('$(_DotnetAotIsNativeBuild)' == 'true' or '$(_DotnetAotIsCrossBuild)' == 'true')">true + <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == '' and '$(_DotnetAotTargetOSSupported)' == 'true' and '$(NativeAotSupported)' == 'true' and '$(DotNetBuildUseMonoRuntime)' != 'true' and ('$(_DotnetAotIsNativeBuild)' == 'true' or '$(_DotnetAotIsCrossBuild)' == 'true')">true <_ShouldPublishDotnetAot Condition="'$(_ShouldPublishDotnetAot)' == ''">false diff --git a/src/Layout/redist/targets/GenerateLayout.targets b/src/Layout/redist/targets/GenerateLayout.targets index b54cf9fa359c..740e819d3b34 100644 --- a/src/Layout/redist/targets/GenerateLayout.targets +++ b/src/Layout/redist/targets/GenerateLayout.targets @@ -550,16 +550,13 @@ <_DotnetAotPublishProperties>_IsPublishing=true - <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true' or '$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid) - <_DotnetAotPublishProperties Condition="'$(DotNetBuildSourceOnly)' == 'true'">$(_DotnetAotPublishProperties);DotNetBuildSourceOnly=true - <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);CrossBuild=true + <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid);CrossBuild=true <_DotnetAotPublishProperties>_IsPublishing=true - <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);TargetOS=$(TargetOS);TargetArchitecture=$(TargetArchitecture);TargetRid=$(TargetRid);PortableTargetRid=$(PortableTargetRid);CrossBuild=true + <_DotnetAotPublishProperties Condition="'$(_DotnetAotIsCrossBuild)' == 'true'">$(_DotnetAotPublishProperties);CrossBuild=true <_DotnetAotTargetOSSupported Condition="'$(TargetOS)' == 'windows' or '$(TargetOS)' == 'linux' or '$(TargetOS)' == 'osx'">true