Skip to content
Open
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
2 changes: 1 addition & 1 deletion .github/workflows/build-deps-ci-action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -250,7 +250,7 @@ jobs:

windows-dependencies:
name: Windows
runs-on: windows-latest
runs-on: ${{ matrix.arch == 'arm64' && 'windows-11-arm' || 'windows-latest' }}
if: ${{ toJSON(fromJSON(inputs.matrix)['windows']) != '[]' }}
env:
USE_S3_CACHE: 'false'
Expand Down
6 changes: 5 additions & 1 deletion .github/workflows/build-packages.yml
Original file line number Diff line number Diff line change
Expand Up @@ -482,7 +482,7 @@ jobs:
matrix:
include: ${{ fromJSON(inputs.matrix)['windows'] }}
runs-on:
- windows-latest
- ${{ matrix.arch == 'arm64' && 'windows-11-arm' || 'windows-latest' }}
env:
SM_HOST: "${{ secrets.WIN_SIGN_HOST_PROD }}"
SM_API_KEY: "${{ secrets.WIN_SIGN_API_KEY }}"
Expand Down Expand Up @@ -585,6 +585,10 @@ jobs:
fi

- name: Upload ${{ matrix.arch }} NSIS Packages
# TEMPORARY: build.ps1 skips NSIS for arm64 (installer.nsi's own
# architecture detection doesn't support it yet, and NSIS was
# never actually requested for this target) - see build.ps1.
if: ${{ matrix.arch != 'arm64' }}
uses: actions/upload-artifact@ea165f8d65b6e75b540449e92b4886f43607fa02 # v4
with:
name: ${{ steps.set-artifact-name.outputs.artifact-name-nsis }}
Expand Down
24 changes: 23 additions & 1 deletion .github/workflows/build-salt-onedir.yml
Original file line number Diff line number Diff line change
Expand Up @@ -167,7 +167,7 @@ jobs:
max-parallel: 2
matrix:
include: ${{ fromJSON(inputs.matrix)['windows'] }}
runs-on: windows-latest
runs-on: ${{ matrix.arch == 'arm64' && 'windows-11-arm' || 'windows-latest' }}
env:
PIP_INDEX_URL: https://pypi.org/simple
USE_S3_CACHE: 'false'
Expand Down Expand Up @@ -196,6 +196,28 @@ jobs:
with:
salt-version: "${{ inputs.salt-version }}"

# TEMPORARY: arm64 has no released relenv build to fetch yet (see
# setup-relenv), so this job compiles CPython from source here
# instead, which needs the VC++ toolchain present. Remove alongside
# the setup-relenv arm64 branch once a real release exists.
- name: Install VS Build Tools
if: ${{ matrix.arch == 'arm64' }}
shell: pwsh
run: |
pkg\windows\install_vs_buildtools.ps1 -CICD

- name: Install ARM64 VC++ Tools
if: ${{ matrix.arch == 'arm64' }}
shell: pwsh
run: |
$vswhere = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\Installer\vswhere.exe"
$vsPath = & $vswhere -latest -products * -property installationPath
$installer = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\Installer\vs_installer.exe"
& $installer modify --installPath "$vsPath" `
--add Microsoft.VisualStudio.Component.VC.Tools.ARM64 `
--quiet --norestart --nocache
if ($LASTEXITCODE -ne 0) { exit $LASTEXITCODE }

- name: Setup Relenv
id: setup-relenv
uses: ./.github/actions/setup-relenv
Expand Down
26 changes: 19 additions & 7 deletions pkg/windows/build.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -30,10 +30,11 @@ param(
[String] $Version,

[Parameter(Mandatory=$false)]
[ValidateSet("x86", "x64", "amd64")]
[ValidateSet("x86", "x64", "amd64", "arm64")]
[Alias("a")]
# The System Architecture to build. "x86" will build a 32-bit installer.
# "x64" will build a 64-bit installer. Default is: x64
# "x64" will build a 64-bit installer. "arm64" will build a native
# ARM64 installer. Default is: x64
$Architecture = "x64",

[Parameter(Mandatory=$false)]
Expand Down Expand Up @@ -250,11 +251,22 @@ if ( $CICD ) {
$KeywordArguments["CICD"] = $true
}

& "$SCRIPT_DIR\nsis\build_pkg.ps1" @KeywordArguments

if ( ! $? ) {
Write-Host "Failed to build NSIS package"
exit 1
# TEMPORARY: the .nsi script's own architecture detection (CPUARCH,
# separate from this script's) only recognizes x64/AMD64/x86 and
# silently falls back to x86 for anything else, producing an installer
# whose filename build_pkg.ps1 then can't find. NSIS was never actually
# requested for arm64 - skip it there rather than widen scope into
# auditing/fixing the .nsi script for a component nobody asked for.
# $KeywordArguments is reused below for the MSI build either way.
if ( $Architecture -eq "arm64" ) {
Write-Host "Skipping NSIS package for arm64 (not yet supported by installer.nsi)"
} else {
& "$SCRIPT_DIR\nsis\build_pkg.ps1" @KeywordArguments

if ( ! $? ) {
Write-Host "Failed to build NSIS package"
exit 1
}
}

#-------------------------------------------------------------------------------
Expand Down
7 changes: 5 additions & 2 deletions pkg/windows/build_python.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,11 @@ param(
[String] $RelenvVersion,

[Parameter(Mandatory=$false)]
[ValidateSet("x64", "x86", "amd64")]
[ValidateSet("x64", "x86", "amd64", "arm64")]
[Alias("a")]
# The System Architecture to build. "x86" will build a 32-bit installer.
# "x64" will build a 64-bit installer. Default is: x64
# "x64" will build a 64-bit installer. "arm64" will build a native
# ARM64 installer. Default is: x64
[String] $Architecture = "x64",

[Parameter(Mandatory=$false)]
Expand Down Expand Up @@ -175,6 +176,8 @@ $BLD_PY_BIN = "$BUILD_DIR\Scripts\python.exe"

if ( $Architecture -eq "x64" ) {
$ARCH = "amd64"
} elseif ( $Architecture -eq "arm64" ) {
$ARCH = "arm64"
} else {
$ARCH = "x86"
}
Expand Down
17 changes: 13 additions & 4 deletions pkg/windows/install_salt.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -257,14 +257,23 @@ if ( ! $SkipInstall ) {
New-Item -Path .\doc\man\salt-cp.1 -Type File -Force | Out-Null
New-Item -Path .\doc\man\salt-minion.1 -Type File -Force | Out-Null
}
# Start-Process -WindowStyle Hidden discards pip's output entirely, so a
# failure here used to show only "Failed" with no indication of why.
# Push-Location/call-operator streams pip's real output to the log
# instead, and $LASTEXITCODE lets us fail on the actual pip error
# rather than only inferring failure from a missing salt-minion.exe.
Push-Location "$PROJECT_DIR"
try {
$env:RELENV_PIP_DIR = "yes"
Start-Process -FilePath $SCRIPTS_DIR\pip3.exe `
-ArgumentList "install", $InstallPath `
-WorkingDirectory "$PROJECT_DIR" `
-Wait -WindowStyle Hidden
& "$SCRIPTS_DIR\pip3.exe" install $InstallPath
$pipExitCode = $LASTEXITCODE
} finally {
Remove-Item env:\RELENV_PIP_DIR
Pop-Location
}
if ( $pipExitCode -ne 0 ) {
Write-Result "Failed" -ForegroundColor Red
exit 1
}
if ( Test-Path -Path "$BUILD_DIR\salt-minion.exe" ) {
Write-Result "Success" -ForegroundColor Green
Expand Down
19 changes: 17 additions & 2 deletions pkg/windows/install_vs_buildtools.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -97,8 +97,23 @@ try {
$VS_INST_LOC = $(Get-CimInstance MSFT_VSInstance -Namespace root/cimv2/vs).InstallLocation
$MSBUILD_BIN = $(Get-ChildItem "$VS_INST_LOC\MSBuild\*\Bin\msbuild.exe").FullName
} catch {
# If VS is not installed, this is the fallback for this installation
$MSBUILD_BIN = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\2017\BuildTools\MSBuild\15.0\Bin\msbuild.exe"
# The MSFT_VSInstance CIM class isn't registered on every runner image
# (confirmed absent on windows-11-arm even though VS 2022 ships
# pre-installed there) -- before assuming VS needs to be installed
# from scratch, fall back to vswhere.exe, which is present on every
# GitHub-hosted Windows image regardless of CIM provider support.
$vswhere = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\Installer\vswhere.exe"
$VS_INST_LOC = $null
if ( Test-Path -Path $vswhere ) {
$VS_INST_LOC = & $vswhere -latest -products * -property installationPath
}
if ( $VS_INST_LOC ) {
$MSBUILD_BIN = $(Get-ChildItem "$VS_INST_LOC\MSBuild\*\Bin\msbuild.exe").FullName
} else {
# Genuinely no VS install found by either method - this is the
# fallback for a from-scratch installation.
$MSBUILD_BIN = "${env:ProgramFiles(x86)}\Microsoft Visual Studio\2017\BuildTools\MSBuild\15.0\Bin\msbuild.exe"
}
}

#-------------------------------------------------------------------------------
Expand Down
42 changes: 41 additions & 1 deletion pkg/windows/msi/Product.wxs
Original file line number Diff line number Diff line change
Expand Up @@ -22,11 +22,20 @@ IMCAC - Immediate Custom Action - It's immediate
Language = "1033">

<!-- Install per Machine -->
<!-- Platform defaults to x86 when omitted, regardless of the -arch
switch passed to candle.exe - without it explicitly here,
light.exe rejects the 64-bit VC++ CRT merge module with "is a
64-bit merge module but the product consuming it is 32-bit."
sys.BUILDARCH did NOT fix this in practice (confirmed live -
same failure, same value) for reasons undetermined; use the
ARCHITECTURE define build_pkg.ps1 passes explicitly instead,
which is exactly the string passed to candle's own -arch. -->
<Package
InstallScope = "perMachine"
InstallerVersion = "500"
Compressed = "yes"
InstallPrivileges = "elevated"
Platform = "$(var.ARCHITECTURE)"
/>

<!-- Prevent downgrade -->
Expand Down Expand Up @@ -246,6 +255,11 @@ IMCAC - Immediate Custom Action - It's immediate
<Custom Action="PreserveRootDirVarCache_IMCAC" Before="RemoveExistingProducts" >WIX_UPGRADE_DETECTED</Custom>
<Custom Action="RestoreRootDirVarCache_IMCAC" After="CreateFolders" >WIX_UPGRADE_DETECTED</Custom>

<?if $(var.ARCHITECTURE) = "arm64" ?>
<!-- Replaces the VC143 MergeRef feature's install for arm64 - see the CustomAction declaration. -->
<Custom Action="InstallVCRedist" After="InstallFiles" >(NOT VCREDIST_INSTALLED) AND (NOT Installed)</Custom>
<?endif ?>

</InstallExecuteSequence>

<!-- Declare Immediate (*_IMCAC) and Deferred (*_DECAC) Custom Actions. -->
Expand All @@ -271,30 +285,56 @@ IMCAC - Immediate Custom Action - It's immediate
<CustomAction Id="MoveInsecureConfig_CADH" Property="MoveInsecureConfig_DECAC" Value="INSECURE_CONFIG_FOUND=[INSECURE_CONFIG_FOUND];" />

<!-- Install VC++ runtime -->
<!-- Visual C++ runtimes depend on the target platform. Merge modules
enforce exact architecture matching at build time (a Windows
Installer rule, not a WiX limitation) - an x64 merge module
cannot be merged into an arm64-declared product even though
the resulting DLLs run fine under Windows 11 on Arm's x64
emulation (confirmed live: WiX's own binder rejects it with
LGHT0345). No native arm64 merge module is published anywhere
yet, so arm64 instead launches the standalone vcredist
installer EXE via a CustomAction below rather than merging an
.msm. Replace with a native Microsoft_VC143_CRT_arm64.msm
(reverting to the merge-module approach) once one exists. -->
<?if $(var.ARCHITECTURE) != "arm64" ?>
<DirectoryRef Id="TARGETDIR">
<!-- Visual C++ runtimes depend on the target platform -->
<?if $(var.WIN64)=yes ?>
<Merge Id="MSM_VC143_CRT" SourceFile="$(var.WEBCACHE_DIR)\Microsoft_VC143_CRT_x64.msm" DiskId="1" Language="0" />
<?else ?>
<Merge Id="MSM_VC143_CRT" SourceFile="$(var.WEBCACHE_DIR)\Microsoft_VC143_CRT_x86.msm" DiskId="1" Language="0" />
<?endif ?>
</DirectoryRef>
<?endif ?>
<!-- Add INSTALLDIR to the system Path -->
<DirectoryRef Id="TARGETDIR">
<Component Id="INSTALLDIR_System_Path" Guid="A9F54641-91F8-4AFB-B812-9409E6EA0192">
<Environment Id="Env_PATH" Name="PATH" Value="[INSTALLDIR]" Permanent="no" Part="last" Action="set" System="yes" />
</Component>
</DirectoryRef>

<?if $(var.ARCHITECTURE) = "arm64" ?>
<!-- vcredist_x64_2022.exe embedded as Binary data rather than a
merge module - see the comment above the (skipped) Merge
block. Deferred + Impersonate=no runs it elevated; Return=
ignore because vcredist installers commonly exit non-zero for
soft conditions (3010 reboot-required, 1638 already installed
at a different version) that shouldn't fail the whole Salt
install. -->
<Binary Id="VCRedistExe" SourceFile="$(var.WEBCACHE_DIR)\vcredist_x64_2022.exe" />
<CustomAction Id="InstallVCRedist" BinaryKey="VCRedistExe" ExeCommand="/install /quiet /norestart" Execute="deferred" Impersonate="no" Return="ignore" />
<?endif ?>

<!-- Assemble fixed and conditional features -->
<!-- Conditional features need attention for install and uninstall -->
<!-- Leaving registry keys would mean the product is still installed -->
<Feature Id="ProductFeature" Title="Minion" Level="1">
<ComponentGroupRef Id="ProductComponents" />
<?if $(var.ARCHITECTURE) != "arm64" ?>
<Feature Id="VC143" Title="VC++ 2022" AllowAdvertise="no" Display="hidden">
<MergeRef Id="MSM_VC143_CRT" />
<Condition Level="0"><![CDATA[VCREDIST_INSTALLED = "#1"]]></Condition>
</Feature>
<?endif ?>
</Feature>

<!-- Get the config file template from the msi store only if no config is present -->
Expand Down
40 changes: 31 additions & 9 deletions pkg/windows/msi/build_pkg.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -82,12 +82,18 @@ $SCRIPTS_DIR = "$BUILDENV_DIR\Scripts"
$SITE_PKGS_DIR = "$BUILDENV_DIR\Lib\site-packages"
$BUILD_SALT_DIR = "$SITE_PKGS_DIR\salt"
$PYTHON_BIN = "$SCRIPTS_DIR\python.exe"
$BUILD_ARCH = $(. $PYTHON_BIN -c "import platform; print(platform.architecture()[0])")
# platform.architecture()[0] only reports pointer width (64bit/32bit),
# which can't distinguish arm64 from amd64 - both are "64bit". Use
# platform.machine() instead, which reports the actual ISA the running
# interpreter was built for.
$BUILD_ARCH = $(. $PYTHON_BIN -c "import platform; print(platform.machine())")
$SCRIPT_DIR = (Get-ChildItem "$($myInvocation.MyCommand.Definition)").DirectoryName
$RUNTIME_DIR = [System.Runtime.InteropServices.RuntimeEnvironment]::GetRuntimeDirectory()
$CSC_BIN = "$RUNTIME_DIR\csc.exe"

if ( $BUILD_ARCH -eq "64bit" ) {
if ( $BUILD_ARCH -eq "ARM64" ) {
$BUILD_ARCH = "ARM64"
} elseif ( $BUILD_ARCH -eq "AMD64" ) {
$BUILD_ARCH = "AMD64"
} else {
$BUILD_ARCH = "x86"
Expand Down Expand Up @@ -169,6 +175,17 @@ $RUNTIMES | ForEach-Object {
VerifyOrDownload "$WEBCACHE_DIR\$name" "$DEPS_URL/$name" "$hash"
}

if ( $BUILD_ARCH -eq "ARM64" ) {
# Merge modules enforce exact architecture matching at build time
# (a Windows Installer rule, not a WiX limitation) - an x64 merge
# module cannot be merged into an arm64-declared product even
# though the resulting DLLs run fine under Windows 11 on Arm's x64
# emulation. No native arm64 merge module is published anywhere
# yet, so arm64 launches the standalone installer EXE via a
# CustomAction (see Product.wxs) instead of merging an .msm.
VerifyOrDownload "$WEBCACHE_DIR\vcredist_x64_2022.exe" "$DEPS_URL/vcredist_x64_2022.exe" "1AD7988C17663CC742B01BEF1A6DF2ED1741173009579AD50A94434E54F56073"
}

#-------------------------------------------------------------------------------
# Converting to MSI Version
#-------------------------------------------------------------------------------
Expand All @@ -195,15 +212,19 @@ $MANUFACTURER = "Salt Project"
$PRODUCT = "Salt Minion"
$PRODUCTFILE = "Salt-Minion-$Version"
$PRODUCTDIR = "Salt"
$DISCOVER_INSTALLDIR = "$BUILDENV_DIR", "$BUILDENV_DIR"
$DISCOVER_INSTALLDIR = "$BUILDENV_DIR", "$BUILDENV_DIR", "$BUILDENV_DIR"
$DISCOVER_CONFDIR = Get-Item "$BUILDENV_DIR\configs"

# MSI related arrays for 64 and 32 bit values, selected by BUILD_ARCH
if ($BUILD_ARCH -eq "AMD64") {$i = 0} else {$i = 1}
$WIN64 = "yes", "no" # Used in wxs
$ARCHITECTURE = "x64", "x86" # WiX dictionary values
$ARCH_AKA = "AMD64", "x86" # For filename
$PROGRAMFILES = "ProgramFiles64Folder", "ProgramFilesFolder" # msi dictionary values
# MSI related arrays for 64, 32, and arm64 bit values, selected by BUILD_ARCH.
# arm64 reuses the amd64 WIN64/PROGRAMFILES values (it's still a native
# 64-bit package installing under the 64-bit Program Files) but needs its
# own WiX -arch tag and filename tag so the resulting MSI is correctly
# identified as ARM64 rather than mislabeled as AMD64.
if ($BUILD_ARCH -eq "ARM64") {$i = 2} elseif ($BUILD_ARCH -eq "AMD64") {$i = 0} else {$i = 1}
$WIN64 = "yes", "no", "yes" # Used in wxs
$ARCHITECTURE = "x64", "x86", "arm64" # WiX dictionary values
$ARCH_AKA = "AMD64", "x86", "ARM64" # For filename
$PROGRAMFILES = "ProgramFiles64Folder", "ProgramFilesFolder", "ProgramFiles64Folder" # msi dictionary values

function CheckExitCode() { # Exit on failure
if ($LastExitCode -ne 0) {
Expand Down Expand Up @@ -521,6 +542,7 @@ Write-Host "Compiling *.wxs to $($ARCHITECTURE[$i]) *.wixobj: " -NoNewline
Push-Location $SCRIPT_DIR
& "$($ENV:WIX)bin\candle.exe" -nologo -sw1150 `
-arch $ARCHITECTURE[$i] `
-dARCHITECTURE="$($ARCHITECTURE[$i])" `
-dWIN64="$($WIN64[$i])" `
-dPROGRAMFILES="$($PROGRAMFILES[$i])" `
-dMANUFACTURER="$MANUFACTURER" `
Expand Down
12 changes: 9 additions & 3 deletions pkg/windows/nsis/build_pkg.ps1
Original file line number Diff line number Diff line change
Expand Up @@ -63,9 +63,15 @@ $PYTHON_BIN = "$SCRIPTS_DIR\python.exe"
$PY_VERSION = [Version]((Get-Command $PYTHON_BIN).FileVersionInfo.ProductVersion)
$PY_VERSION = "$($PY_VERSION.Major).$($PY_VERSION.Minor)"
$NSIS_BIN = "$( ${env:ProgramFiles(x86)} )\NSIS\makensis.exe"
$ARCH = $(. $PYTHON_BIN -c "import platform; print(platform.architecture()[0])")

if ( $ARCH -eq "64bit" ) {
# platform.architecture()[0] only reports pointer width (64bit/32bit),
# which can't distinguish arm64 from amd64 - both are "64bit". Use
# platform.machine() instead, which reports the actual ISA the running
# interpreter was built for.
$ARCH = $(. $PYTHON_BIN -c "import platform; print(platform.machine())")

if ( $ARCH -eq "ARM64" ) {
$ARCH = "ARM64"
} elseif ( $ARCH -eq "AMD64" ) {
$ARCH = "AMD64"
} else {
$ARCH = "x86"
Expand Down
Loading