Skip to content
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
12 changes: 7 additions & 5 deletions .pipelines/templates/mac-package-build.yml
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
parameters:
parentJob: ''
buildArchitecture: x64
OfficialBuild: true

jobs:
- job: package_macOS_${{ parameters.buildArchitecture }}
Expand Down Expand Up @@ -78,12 +79,13 @@ jobs:
continueOnError: true

- pwsh: |
$signedDir = "$(Pipeline.Workspace)/CoOrdinatedBuildPipeline/drop_macos_sign_${{ parameters.buildArchitecture }}/Signed-${{ parameters.buildArchitecture }}"
Get-ChildItem $signedDir -Recurse -Include 'pwsh', '*.dylib' | ForEach-Object {
codesign --verify --deep --strict --verbose=4 $_.FullName
if ($LASTEXITCODE -ne 0) { throw "codesign verification failed for $($_.FullName)" }
$signatureParameters = @{
Path = "$(Pipeline.Workspace)/CoOrdinatedBuildPipeline/drop_macos_sign_${{ parameters.buildArchitecture }}/Signed-${{ parameters.buildArchitecture }}"
OfficialBuild = [System.Convert]::ToBoolean('${{ parameters.OfficialBuild }}')
EntitlementsPath = "$(Build.SourcesDirectory)/assets/macos-entitlements.plist"
}
displayName: 'Verify Apple codesign on signed binaries'
& "$(Build.SourcesDirectory)/tools/packaging/Update-MacOSCodeSignature.ps1" @signatureParameters
displayName: 'Apply and verify Apple codesign on signed binaries'

- pwsh: |
# Add -SkipReleaseChecks as a mitigation to unblock release.
Expand Down
42 changes: 36 additions & 6 deletions .pipelines/templates/mac.yml
Original file line number Diff line number Diff line change
Expand Up @@ -190,21 +190,51 @@ jobs:

- pwsh: |
$signedDir = "$(ob_outputDirectory)/Signed-$(Runtime)"
$expected = 'Developer ID Application: Microsoft Corporation'
$officialBuild = [System.Convert]::ToBoolean('$(ps_official_build)')
$officialSignature = 'Developer ID Application: Microsoft Corporation'
$codeDirectoryMagic = [byte[]](0xfa, 0xde, 0x0c, 0x02)
$missing = @()
Get-ChildItem $signedDir -Recurse -Include 'pwsh', '*.dylib' | ForEach-Object {
$bytes = [System.IO.File]::ReadAllBytes($_.FullName)
$text = [System.Text.Encoding]::Latin1.GetString($bytes)
if (-not $text.Contains($expected)) {
$hasOfficialSignature = $text.Contains($officialSignature)
$hasAdHocSignature = $false

if (-not $officialBuild -and -not $hasOfficialSignature) {
# The package stage runs codesign --verify; here the Windows signing job
# verifies that unofficial output contains an ad-hoc CodeDirectory.
for ($offset = 0; $offset -le $bytes.Length - 16; $offset++) {
if ($bytes[$offset] -eq $codeDirectoryMagic[0] -and
$bytes[$offset + 1] -eq $codeDirectoryMagic[1] -and
$bytes[$offset + 2] -eq $codeDirectoryMagic[2] -and
$bytes[$offset + 3] -eq $codeDirectoryMagic[3] -and
($bytes[$offset + 15] -band 0x02) -ne 0) {
$hasAdHocSignature = $true
break
}
}
}

if (-not $hasOfficialSignature -and ($officialBuild -or -not $hasAdHocSignature)) {
$missing += $_.FullName
Write-Host "##[error]Missing '$expected' signature in $($_.FullName)"
$expectedSignature = if ($officialBuild) {
"'$officialSignature'"
} else {
'a Developer ID signature or ad-hoc CodeDirectory'
}
Write-Host "##[error]Missing $expectedSignature in $($_.FullName)"
} else {
Write-Host "OK: $($_.FullName)"
$signatureDescription = if ($hasOfficialSignature) {
'a Developer ID signature'
} else {
'an ad-hoc CodeDirectory'
}
Write-Host "OK: $($_.FullName) contains $signatureDescription"
}
}
if ($missing.Count -gt 0) {
throw "ESRP did not apply a Developer ID signature to $($missing.Count) file(s): $($missing -join ', ')"
throw "The expected Apple signature was not found in $($missing.Count) file(s): $($missing -join ', ')"
}
displayName: 'Verify Developer ID signature on Mach-O binaries'
displayName: 'Verify Apple signature on Mach-O binaries'

- template: /.pipelines/templates/step/finalize.yml@self
2 changes: 2 additions & 0 deletions .pipelines/templates/stages/PowerShell-Packages-Stages.yml
Original file line number Diff line number Diff line change
Expand Up @@ -50,10 +50,12 @@ stages:
- template: /.pipelines/templates/mac-package-build.yml@self
parameters:
buildArchitecture: x64
OfficialBuild: ${{ parameters.OfficialBuild }}

- template: /.pipelines/templates/mac-package-build.yml@self
parameters:
buildArchitecture: arm64
OfficialBuild: ${{ parameters.OfficialBuild }}

- stage: windows_package_build
displayName: 'Win Pkg (unsigned)'
Expand Down
55 changes: 55 additions & 0 deletions tools/packaging/Update-MacOSCodeSignature.ps1
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
# Copyright (c) Microsoft Corporation.
# Licensed under the MIT License.

[CmdletBinding()]
param(
[Parameter(Mandatory)]
[ValidateScript({ Test-Path -LiteralPath $_ -PathType Container })]
[string] $Path,

[Parameter(Mandatory)]
[bool] $OfficialBuild,

[Parameter(Mandatory)]
[ValidateScript({ Test-Path -LiteralPath $_ -PathType Leaf })]
[string] $EntitlementsPath
)

$binaries = @(
Get-ChildItem -LiteralPath $Path -Recurse -File |
Where-Object { $_.Name -eq 'pwsh' -or $_.Extension -eq '.dylib' }
)

if ($binaries.Count -eq 0) {
throw "No Mach-O binaries were found in '$Path'."
}

foreach ($binary in $binaries) {
& codesign --verify --deep --strict --verbose=4 $binary.FullName
if ($LASTEXITCODE -eq 0) {
Comment on lines +28 to +29
continue
}

if ($OfficialBuild) {
throw "codesign verification failed for '$($binary.FullName)'."
}

# Nonofficial signing can leave only one slice of a universal binary signed.
# Re-signing on macOS applies an ad-hoc signature across every architecture.
Write-Verbose -Message "Applying an ad-hoc signature to '$($binary.FullName)' for the nonofficial package." -Verbose
$signArguments = @('--sign', '-', '--force', '--options', 'runtime')
if ($binary.Name -eq 'pwsh') {
$signArguments += @('--entitlements', $EntitlementsPath)
}
$signArguments += $binary.FullName

& codesign @signArguments
if ($LASTEXITCODE -ne 0) {
throw "Ad-hoc codesign failed for '$($binary.FullName)'."
}

& codesign --verify --deep --strict --verbose=4 $binary.FullName
if ($LASTEXITCODE -ne 0) {
throw "codesign verification failed for '$($binary.FullName)' after applying an ad-hoc signature."
}
}
Loading