Open ThierryPermentier opened 1 year ago
How did you get it to work? We are also struggling a bit after June 1st. Has anyone else done a DigiCert certificate and had success?
Is your code signing certificate on an usb stick?
Hi ThierryPermentier, I work with CodeThumper. No, we got the option to have our private key stored in the Key Locker, but we know that's working because when we run the sign command (with Signtool.exe) without those arguments we get an error that the private key couldn't be accessed. I could go into more detail, but we're curious what you did to get the signing to work for you and where you got your certificate because we're open to doing it the exact same way if it works. We encountered the same problem of not being able to create the complete .pfx file, so what were the steps you took to sign your app given the new regulations? Thanks.
Our certificate is from Sectigo (code signing for 1 year). We have a personal token on an USB stick. We followed the instructions from this post. Because the signtool is used with different parameters than the ones from navcontainerhelper, we wrote our own powershell (call to signtool.exe) to sign our extensions. So we sign our code on the host, not in the container. As we have to use a USB stick, we only can sign on 1 server. (There are solutions to share the USB across the network, but we do not use them)
Ok, thanks for the info. We did get it working with the DigiCert connection to their Key Locker using signtool manually in the command line after referencing their Authenticode setup and fixing the terminal environment variables.
Hi,
We have also get a new Codesigning Certificate from Digicert on a HSM USB-Stick. Is there already a solution to use this E-Token with Containerhelper? We can't use them in our Azure Pipelines. Th only way to sign the App is on a local host, where the USB-Token is connected.
Is "Code signing with Software Trust Manager" from Digicert not an option for you?
Our codesigning certificate that we have been using for the past 3 years has expired. We ordered a new one at ssl.com. But we got a Codesigning Certificate on a yubikey. We can not create a pfx file anymore, and according to SSL.com this is as expected (see below).
I'll expect this problem to grow. Others will be experiencing the new codesigning limitations soon. Will containerhelper provide a solution for this?
"Starting June 1, 2023, SSL.com's Organization Validation (OV) and Individual Validation (IV) Code Signing Certificates have been issued either on Federal Information Processing Standard 140-2 (FIPS 140-2) USB tokens, Cloud HSMs, or through our eSigner cloud code signing service, and are no longer available as downloadable pfx files. This change is in compliance with the Certificate Authority/Browser (CA/B) Forum's new key storage requirements to increase security for code signing keys. The previous rule allowed OV and IV code signing certificates to be issued as downloadable files from the internet. Since the new requirements only allow the use of encrypted USB tokens or cloud-based FIPS compliant hardware appliances to store the certificate and private key, it is expected that instances of code signing keys being stolen and misused by malicious actors will be greatly reduced."
function Add-SignatureHBRD {
[Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSAvoidUsingPlainTextForPassword', 'SslComPassWord',
Justification = 'Password is stored as secure string in Azure DevOps')]
[Diagnostics.CodeAnalysis.SuppressMessageAttribute('PSAvoidUsingCmdletAliases', '',
Justification = 'Echo used in a way that is yet to be translated to powershell')]
[CmdletBinding()]
param(
[Parameter(Mandatory=$true)]
[string] $containerName,
[Parameter(Mandatory=$true)]
[string] $AppFile,
[Parameter(Mandatory=$true)]
[string] $SslComUserName,
[Parameter(Mandatory=$true)]
[string] $SslComPassWord,
[Parameter(Mandatory=$true)]
[string] $SslComSecret,
[Parameter(Mandatory=$true)]
[string] $SslComMode
)
$ErrorActionPreference = 'Stop'
$containerAppFile = Get-BcContainerPath -containerName $containerName -path $AppFile
if ("$containerAppFile" -eq "") {
Write-Error "The app ($appFile)needs to be in a folder, which is shared with the container $containerName"
}
Invoke-ScriptInBcContainer -containerName $containerName -useSession:$false -ScriptBlock { Param($AppFile, $SslComUserName, $SslComPassWord, $SslComSecret, $SslComMode)
$BuildBinariesPath = '.\EsignerBuildBinaries'
if (Test-Path '.\EsignerBuildBinaries\') {
if (!(Test-Path '.\EsignerBuildBinaries\eSigner_CKA_Setup*.exe')) {
Remove-Item -LiteralPath '.\EsignerBuildBinaries' -Force -Recurse
}
}
if (!(Test-Path $BuildBinariesPath)) {
New-Item -Path $BuildBinariesPath -ItemType Directory
if (!(Test-Path "C:\Windows\System32\msvcr120.dll")) {
Write-Host "Downloading vcredist_x86"
(New-Object System.Net.WebClient).DownloadFile('https://bcartifacts.azureedge.net/prerequisites/vcredist_x86.exe','c:\run\install\vcredist_x86.exe')
Write-Host "Installing vcredist_x86"
start-process -Wait -FilePath c:\run\install\vcredist_x86.exe -ArgumentList /q, /norestart
Write-Host "Downloading vcredist_x64"
(New-Object System.Net.WebClient).DownloadFile('https://bcartifacts.azureedge.net/prerequisites/vcredist_x64.exe','c:\run\install\vcredist_x64.exe')
Write-Host "Installing vcredist_x64"
start-process -Wait -FilePath c:\run\install\vcredist_x64.exe -ArgumentList /q, /norestart
}
if (!(Test-Path "C:\Windows\System32\vcruntime140_1.dll")) {
Write-Host "Downloading vcredist_x64 (version 140)"
(New-Object System.Net.WebClient).DownloadFile('https://aka.ms/vs/17/release/vc_redist.x64.exe','c:\run\install\vcredist_x64-140.exe')
Write-Host "Installing vcredist_x64 (version 140)"
start-process -Wait -FilePath c:\run\install\vcredist_x64-140.exe -ArgumentList /q, /norestart
}
if (Test-Path "C:\Program Files (x86)\Windows Kits\10\bin\*\x64\SignTool.exe") {
$signToolExe = (get-item "C:\Program Files (x86)\Windows Kits\10\bin\*\x64\SignTool.exe").FullName
} else {
Write-Host "Downloading Signing Tools"
$winSdkSetupExe = "c:\run\install\winsdksetup.exe"
$winSdkSetupUrl = "https://bcartifacts.azureedge.net/prerequisites/winsdksetup.exe"
(New-Object System.Net.WebClient).DownloadFile($winSdkSetupUrl,$winSdkSetupExe)
Write-Host "Installing Signing Tools"
Start-Process $winSdkSetupExe -ArgumentList "/features OptionId.SigningTools /q" -Wait
if (!(Test-Path "C:\Program Files (x86)\Windows Kits\10\bin\*\x64\SignTool.exe")) {
throw "Cannot locate signtool.exe after installation"
}
$signToolExe = (get-item "C:\Program Files (x86)\Windows Kits\10\bin\*\x64\SignTool.exe").FullName
}
if (!(Test-Path '.\eSigner_CKA_Setup')) {
Write-Host "Download and Unzip eSignerCKA Setup"
Invoke-WebRequest -OutFile eSigner_CKA_Setup.zip "https://www.ssl.com/download/ssl-com-esigner-cka"
Expand-Archive -Force eSigner_CKA_Setup.zip
Remove-Item eSigner_CKA_Setup.zip
$eSigner = (Get-ChildItem -Path '.\eSigner_CKA_Setup' -Filter '*.exe' | Sort-Object | Select-Object -First 1).FullName
Move-Item -Destination "eSigner_CKA_Installer.exe" -Path $eSigner
}
}
Write-Host "Setup eSignerCKA in Silent Mode"
./eSigner_CKA_Installer.exe /CURRENTUSER /VERYSILENT /SUPPRESSMSGBOXES /DIR="$BuildBinariesPath\Desktop\eSignerCKA" | Out-Null
Get-ChildItem -Path $BuildBinariesPath\Desktop\eSignerCKA
write-host "Config Account Information on eSignerCKA"
& "$BuildBinariesPath\Desktop\eSignerCKA\eSignerCKATool.exe" config -mode $SslComMode -user $SslComUserName -pass $SslComPassWord -totp $SslComSecret -key "$BuildBinariesPath\Desktop\eSignerCKA\master.key" -r
write-host "Unload and Load Certificate into Windows Store"
& "$BuildBinariesPath\Desktop\eSignerCKA\eSignerCKATool.exe" unload
& "$BuildBinariesPath\Desktop\eSignerCKA\eSignerCKATool.exe" load
write-host "Sign File with SignTool"
$signToolExe = (get-item "C:\Program Files (x86)\Windows Kits\10\bin\*\x64\SignTool.exe").FullName
$CodeSigningCert = Get-ChildItem Cert:\CurrentUser\My -CodeSigningCert | Select-Object -First 1; echo $CodeSigningCert.Thumbprint > .Thumbprint
Set-Variable -Name Thumbprint -Value (Get-Content .Thumbprint); echo $Thumbprint
& "$signtoolexe" @("sign", "/debug", "/fd", "sha256", "/tr", "http://ts.ssl.com" ,"/td", "sha256", "/sha1", $Thumbprint, $AppFile) | Write-Host
} -ArgumentList $containerAppFile, $SslComUserName, $SslComPassWord, $SslComSecret, $SslComMode
}
Above my powershell code for ssl.com. It could be a nice feature to have this one and maybe others insicde containerhelper.
Hi @mishof ,
I have a question. Is the code snippet you provided in PowerShell for manual signing or through some automation?
We're facing the same issue, and initially, we ordered the Certum SimplySign, which works for manually signing apps, but the token expires after 3 hours, making it impractical for automated signing through, for example, a pipeline. After encountering this problem, SSLPoint support directed us to purchase a token-based certificate, stating: "For automation, you can consider a token-based certificate, e.g., from GlobalSign: https://www.sslpoint.com/eu/code-signing/"
Alright, we have obtained this certificate now, but I still don't see a solution for using this certificate for automatic app signing, considering that our app is built through a pipeline using the Run-AlPipeline function from bccontainerhelper:
Okay, we've resolved the token input issue, meaning the token can only be entered once, and then the app can be signed:
However, this still pertains to manually signing apps on a computer where the certificate is loaded from a USB. Considering we have multiple agents, both self-hosted and Microsoft-hosted, I'm unsure if it's even possible to use this certificate for automated app signing in this manner:
Before certificate expiring, we signed apps using built-in sigining in AL-Pipeline:
Is there anyone else facing the same issue? And is it even possible to use the new HSM format of certificate for automatic app signing?
AL-Go for GitHub handles this by getting the certificate delivered in an Azure KeyVault with HSM support and then using the AzureSignTool to sign the app. This is no longer done inside Run-AlPipeline, but is done after the pipeline - you should do the same. The Run-AlPipeline is only capable of signing in the "old" way.
@KrunoslavPipic This code works flawlessly in our ci/cd pipelines in Azure DevOps that build and release to appsource. I wrote it with support of ssl.com. It will probably only work with certicates provided through the ssl.com service. The method Freddy metions is probably more generic, and thus preferred.
thanks,
it works now as Freddy suggested:
AzureSignTool.exe sign --description-url $env:SIGNINGURL --file-digest sha384 --azure-key-vault-url $env:SIGNINGVAULTURL --azure-key-vault-client-id $env:SIGNINGCLIENTID --azure-key-vault-tenant-id $env:SIGNINGTENANTID --azure-key-vault-client-secret $env:SIGNINGCLIENTSECRET --azure-key-vault-certificate $env:SIGNINGCERTNAME --timestamp-rfc3161 'http://timestamp.digicert.com' --timestamp-digest sha384 -v $appFile.FullName
As of June 1st, code signing certificates are delivered as E-Token (on USB stick), not possible anymore to create a PFX from it. How can we sign the apps using functionality of BcContainerHelper? Any suggestions? Or how can we sign the app files in an automated way?
Thank you