From 7605d2e9f5d12b2f9fc291c4f5fc66bafb5e63df Mon Sep 17 00:00:00 2001 From: Oliver Kieselbach Date: Tue, 8 Sep 2026 20:49:38 +0200 Subject: [PATCH] fix(loader): log the signer CN instead of the whole EV subject The full subject of an EV certificate is a line of street address and registration numbers and pushed the useful part of the log line off the screen. The CN answers the question the log has to answer. The full subject is still logged in the one case where it is the finding itself: a valid signature from a publisher that is not us. Loader 1.1 -> 1.2; a Pester case pins the short form. Suite on PS 5.1: 45/45. Co-Authored-By: Claude Opus 5 (1M context) --- scripts/Bootstrap/Start-AutopilotMonitor.Tests.ps1 | 9 +++++++++ scripts/Bootstrap/Start-AutopilotMonitor.ps1 | 12 +++++++++--- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/scripts/Bootstrap/Start-AutopilotMonitor.Tests.ps1 b/scripts/Bootstrap/Start-AutopilotMonitor.Tests.ps1 index fb6e8cce..1dbfc0c5 100644 --- a/scripts/Bootstrap/Start-AutopilotMonitor.Tests.ps1 +++ b/scripts/Bootstrap/Start-AutopilotMonitor.Tests.ps1 @@ -32,6 +32,15 @@ Describe 'Test-BootstrapSignature' { Test-BootstrapSignature -Path 'TestDrive:\x.ps1' | Should -BeTrue } + # An EV subject is a line of street address and registration numbers; the log gets the CN. + It 'logs the signer CN, not the whole subject' { + Mock Get-AuthenticodeSignature { + New-FakeSignature -Status 'Valid' -Subject 'CN=glueckkanja AG, O=glueckkanja AG, L=Offenbach am Main, C=DE, SERIALNUMBER=HRB 12381' + } + Test-BootstrapSignature -Path 'TestDrive:\x.ps1' | Should -BeTrue + Should -Invoke Write-Log -ParameterFilter { $Message -eq 'Signature status: Valid. Signer: glueckkanja AG' } + } + It 'refuses an unsigned script' { Mock Get-AuthenticodeSignature { New-FakeSignature -Status 'NotSigned' -Subject $null } Test-BootstrapSignature -Path 'TestDrive:\x.ps1' | Should -BeFalse diff --git a/scripts/Bootstrap/Start-AutopilotMonitor.ps1 b/scripts/Bootstrap/Start-AutopilotMonitor.ps1 index bf474431..589056da 100644 --- a/scripts/Bootstrap/Start-AutopilotMonitor.ps1 +++ b/scripts/Bootstrap/Start-AutopilotMonitor.ps1 @@ -54,6 +54,8 @@ Runtime : Windows PowerShell 5.1, SYSTEM context, during Autopilot enrollment .CHANGELOG + 2026-09-08 v1.2 Log the signer CN instead of the full EV subject; the full subject is + logged only when the publisher is why a script was rejected. 2026-09-08 v1.1 Also used by the bootstrap MSI, which replaced its own copy of this logic; -LogFileName keeps the channel visible in diagnostics. 2026-09-08 v1.0 Initial version: two-stage bootstrap, publisher-pinned verification. @@ -73,7 +75,7 @@ param( ) # Script version (bump on meaningful changes; see .CHANGELOG above) -$ScriptVersion = "1.1" +$ScriptVersion = "1.2" # The publisher every downloaded stage-2 script must carry. A -like pattern on the subject, # NOT a thumbprint: certificates are renewed, deployed loaders are not. @@ -116,15 +118,19 @@ function Test-BootstrapSignature { return $false } + # The full subject of an EV certificate is a line of street address and registration + # numbers. The CN answers the only question the log has to answer; the full subject is + # logged when it is the reason for a rejection. $subject = if ($sig.SignerCertificate) { $sig.SignerCertificate.Subject } else { "" } - Write-Log "Signature status: $($sig.Status). Signer: $subject" + $signer = if ($subject -match 'CN=([^,]+)') { $Matches[1] } else { $subject } + Write-Log "Signature status: $($sig.Status). Signer: $signer" if ($sig.Status -ne 'Valid') { Write-Log "REJECTED: expected signature status 'Valid'." return $false } if ($subject -notlike $ExpectedPublisher) { - Write-Log "REJECTED: signer does not match the expected publisher." + Write-Log "REJECTED: signer does not match the expected publisher. Full subject: $subject" return $false }