HP.Firmware.SecurePlatform.psm1
# # Copyright 2018-2024 HP Development Company, L.P. # All Rights Reserved. # # NOTICE: All information contained herein is, and remains the property of HP Inc. # # The intellectual and technical concepts contained herein are proprietary to HP Inc # and may be covered by U.S. and Foreign Patents, patents in process, and are protected by # trade secret or copyright law. Dissemination of this information or reproduction of this material # is strictly forbidden unless prior written permission is obtained from HP Inc. using namespace HP.CMSLHelper Set-StrictMode -Version 3.0 $ErrorActionPreference = "Stop" #requires -Modules "HP.Private" # CMSL is normally installed in C:\Program Files\WindowsPowerShell\Modules # but if installed via PSGallery and via PS7, it is installed in a different location if (Test-Path "$PSScriptRoot\..\HP.Private\HP.CMSLHelper.dll") { Add-Type -Path "$PSScriptRoot\..\HP.Private\HP.CMSLHelper.dll" } else{ Add-Type -Path "$PSScriptRoot\..\..\HP.Private\1.8.0\HP.CMSLHelper.dll" } <# .SYNOPSIS Retrieves the HP Secure Platform Management state .DESCRIPTION This command retrieves the state of the HP Secure Platform Management. .LINK [Blog post: HP Secure Platform Management with the HP Client Management Script Library](https://developers.hp.com/hp-client-management/blog/hp-secure-platform-management-hp-client-management-script-library) .NOTES - Requires HP BIOS with Secure Platform Management support. - This command requires elevated privileges. .EXAMPLE Get-HPSecurePlatformState #> function Get-HPSecurePlatformState { [CmdletBinding(HelpUri = "https://developers.hp.com/hp-client-management/doc/Get-HPSecurePlatformState")] param() $mi_result = 0 $data = New-Object -TypeName provisioning_data_t $c = '[DfmNativeSecurePlatform]::get_secureplatform_provisioning' + (Test-OSBitness) + '([ref]$data,[ref]$mi_result);' $result = Invoke-Expression -Command $c Test-HPPrivateCustomResult -result $result -mi_result $mi_result -Category 0x04 $kek_mod = $data.kek_mod [array]::Reverse($kek_mod) $sk_mod = $data.sk_mod [array]::Reverse($sk_mod) # calculating EndorsementKeyID $kek_encoded = [System.Convert]::ToBase64String($kek_mod) # $kek_decoded = [Convert]::FromBase64String($kek_encoded) # $kek_hash = Get-HPPrivateHash -Data $kek_decoded # $kek_Id = [System.Convert]::ToBase64String($kek_hash) # calculating SigningKeyID $sk_encoded = [System.Convert]::ToBase64String($sk_mod) # $sk_decoded = [Convert]::FromBase64String($sk_encoded) # $sk_hash = Get-HPPrivateHash -Data $sk_decoded # $sk_Id = [System.Convert]::ToBase64String($sk_hash) # get Sure Admin Mode and Local Access values $sure_admin_mode = "" $local_access = "" if ((Get-HPPrivateIsSureAdminSupported) -eq $true) { $sure_admin_state = Get-HPSureAdminState $sure_admin_mode = $sure_admin_state.SureAdminMode $local_access = $sure_admin_state.LocalAccess } # calculate FeaturesInUse $featuresInUse = "" if ($data.features_in_use -eq "SureAdmin") { $featuresInUse = "SureAdmin ($sure_admin_mode, Local Access - $local_access)" } else { $featuresInUse = $data.features_in_use } $obj = [ordered]@{ State = $data.State Version = "$($data.subsystem_version[0]).$($data.subsystem_version[1])" Nonce = $($data.arp_counter) FeaturesInUse = $featuresInUse EndorsementKeyMod = $kek_mod SigningKeyMod = $sk_mod EndorsementKeyID = $kek_encoded SigningKeyID = $sk_encoded } return New-Object -TypeName PSCustomObject -Property $obj } <# .SYNOPSIS Creates an HP Secure Platform Management payload to provision a _Key Endorsement_ key .DESCRIPTION This command creates an HP Secure Platform Management payload to provision a _Key Endorsement_ key. The purpose of the endorsement key is to protect the signing key against unauthorized changes. Only holders of the key endorsement private key may change the signing key. There are three endorsement options to choose from: - Endorsement Key File (and Password) using -EndorsementKeyFile and -EndorsementKeyPassword parameters - Endorsement Key Certificate using -EndorsementKeyCertificate parameter - Remote Endorsement using -RemoteEndorsementKeyID and -RemoteSigningServiceURL parameters Please note that using a Key File with Password in PFX format is recommended over using an X509 Certificate object because a private key in a certificate is not password protected. This command writes the created payload to the pipeline or to the file specified in the OutputFile parameter. This payload can then be passed to the Set-HPSecurePlatformPayload command. Security note: Payloads should only be created on secure servers. Once created, the payload may be transferred to a client and applied via the Set-HPSecurePlatformPayload command. Creating the payload and passing it to the Set-HPSecurePlatformPayload command via the pipeline is not a recommended production pattern. .PARAMETER EndorsementKeyFile Specifies the _Key Endorsement_ key certificate as a PFX (PKCS #12) file .PARAMETER EndorsementKeyPassword Specifies the password for the _Endorsement Key_ PFX file. If no password was used when the PFX was created (not recommended), this parameter may be omitted. .PARAMETER EndorsementKeyCertificate Specifies the endorsement key certificate as an X509Certificate object .PARAMETER BIOSPassword Specifies the BIOS setup password, if any. Note that the password will be in the clear in the generated payload. .PARAMETER OutputFile Specifies the file to write output to instead of writing the output to the pipeline .PARAMETER RemoteEndorsementKeyID Specifies the Endorsement Key ID to be used .PARAMETER RemoteSigningServiceURL Specifies the Key Management Services (KMS) server URL (I.e.: https://<KMSAppName>.azurewebsites.net/). This URL must be HTTPS. .PARAMETER CacheAccessToken If specified, the access token is cached in msalcache.dat file and user credentials will not be asked again until the credentials expire. This parameter should be specified for caching the access token when performing multiple operations on the KMS server. If access token is not cached, the user must re-enter credentials on each call of this command. .LINK [Blog post: HP Secure Platform Management with the HP Client Management Script Library](https://developers.hp.com/hp-client-management/blog/hp-secure-platform-management-hp-client-management-script-library) .NOTES The Key Endorsement private key must never leave a secure server. The payload must be created on a secure server, then may be transferred to a client. - Requires HP BIOS with Secure Platform Management support. .EXAMPLE $payload = New-HPSecurePlatformEndorsementKeyProvisioningPayload -EndorsementKeyFile "$path\endorsement_key.pfx" ... $payload | Set-HPSecurePlatformPayload #> function New-HPSecurePlatformEndorsementKeyProvisioningPayload { [CmdletBinding(DefaultParameterSetName = "EK_FromFile",HelpUri = "https://developers.hp.com/hp-client-management/doc/New-HPSecurePlatformEndorsementKeyProvisioningPayload")] param( [Parameter(ParameterSetName = "EK_FromFile",Mandatory = $true,Position = 0)] [System.IO.FileInfo]$EndorsementKeyFile, [Parameter(ParameterSetName = "EK_FromFile",Mandatory = $false,Position = 1)] [string]$EndorsementKeyPassword, [Parameter(ParameterSetName = "EK_FromBytes",Mandatory = $true,Position = 0)] [System.Security.Cryptography.X509Certificates.X509Certificate2]$EndorsementKeyCertificate, [Parameter(ParameterSetName = "EK_FromFile",Mandatory = $false,Position = 2)] [Parameter(ParameterSetName = "EK_FromBytes",Mandatory = $false,Position = 2)] [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 0)] [string]$BIOSPassword, [Parameter(ParameterSetName = "EK_FromFile",Mandatory = $false,Position = 3)] [Parameter(ParameterSetName = "EK_FromBytes",Mandatory = $false,Position = 3)] [System.IO.FileInfo]$OutputFile, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 1)] [string]$RemoteEndorsementKeyID, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 2)] [string]$RemoteSigningServiceURL, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 3)] [switch]$CacheAccessToken ) # only allow https or file paths with or without file:// URL prefix if ($RemoteSigningServiceURL -and -not ($RemoteSigningServiceURL.StartsWith("https://",$true,$null) -or [System.IO.Directory]::Exists($RemoteSigningServiceURL) -or $RemoteSigningServiceURL.StartsWith("file://",$true,$null))) { throw [System.ArgumentException]"Only HTTPS or valid existing directory paths are supported." } if ($PSCmdlet.ParameterSetName -eq "RemoteSigning") { if (-not $RemoteSigningServiceURL.EndsWith('/')) { $RemoteSigningServiceURL += '/' } $RemoteSigningServiceURL += 'api/commands/p21ekpubliccert' $jsonPayload = New-HPPrivateRemoteSecurePlatformProvisioningJson -EndorsementKeyID $RemoteEndorsementKeyID $accessToken = Get-HPPrivateSureAdminKMSAccessToken -CacheAccessToken:$CacheAccessToken $response,$responseContent = Send-HPPrivateKMSRequest -KMSUri $RemoteSigningServiceURL -JsonPayload $jsonPayload -AccessToken $accessToken -Verbose:$VerbosePreference if ($response -eq "OK") { $crt = [Convert]::FromBase64String($responseContent) } else { Invoke-HPPrivateKMSErrorHandle -ApiResponseContent $responseContent -Status $response } } else { $crt = (Get-HPPrivateX509CertCoalesce -File $EndorsementKeyFile -cert $EndorsementKeyCertificate -password $EndorsementKeyPassword -Verbose:$VerbosePreference).Certificate } Write-Verbose "Creating EK provisioning payload" if ($BIOSPassword) { $passwordLength = $BIOSPassword.Length } else { $passwordLength = 0 } $opaque = New-Object opaque4096_t $opaqueLength = 4096 $mi_result = 0 $cmd = '[DfmNativeSecurePlatform]::get_ek_provisioning_data' + (Test-OSBitness) + '($crt,$($crt.Count),$BIOSPassword, $passwordLength, [ref]$opaque, [ref]$opaqueLength, [ref]$mi_result);' $result = Invoke-Expression -Command $cmd Test-HPPrivateCustomResult -result $result -mi_result $mi_result -Category 0x04 $output = New-Object -TypeName PortableFileFormat $output.Data = $opaque.raw[0..($opaqueLength - 1)] $output.purpose = "hp:provision:endorsementkey" $output.timestamp = Get-Date if ($OutputFile) { Write-Verbose "Will output to file $OutputFile" $f = $ExecutionContext.SessionState.Path.GetUnresolvedProviderPathFromPSPath($OutputFile) $output | ConvertTo-Json -Compress | Out-File $f -Encoding utf8 } else { $output | ConvertTo-Json -Compress } } <# .SYNOPSIS Creates an HP Secure Platform Management payload to provision a _Signing Key_ key .DESCRIPTION This command creates an HP Secure Platform Management payload to provision a _Signing Key_ key. The purpose of the signing key is to sign commands for the Secure Platform Management. The Signing key is protected by the endorsement key. As a result, the endorsement key private key must be available when provisioning or changing the signing key. There are three signing options to choose from: - Signing Key File (and Password) using -SigningKeyFile and -SigningKeyPassword parameters - Signing Key Certificate using -SigningKeyCertificate parameter - Remote Signing using -RemoteSigningServiceKeyID and -RemoteSigningServiceURL parameters There are three endorsement options to choose from: - Endorsement Key File (and Password) using -EndorsementKeyFile and -EndorsementKeyPassword parameters - Endorsement Key Certificate using -EndorsementKeyCertificate parameter - Remote Endorsement using -RemoteEndorsementKeyID and -RemoteSigningServiceURL parameters Please note that using a Key File with Password in PFX format is recommended over using an X509 Certificate object because a private key in a certificate is not password protected. This command writes the created payload to the pipeline or to the file specified in the -OutputFile parameter. This payload can then be passed to the Set-HPSecurePlatformPayload command. Security note: Payloads should only be created on secure servers. Once created, the payload may be transferred to a client and applied via the Set-HPSecurePlatformPayload command. Please note that creating the payload and passing it to the Set-HPSecurePlatformPayload command via the pipeline is not a recommended production pattern. .PARAMETER EndorsementKeyFile Specifies the _Key Endorsement_ key certificate as a PFX (PKCS #12) file .PARAMETER EndorsementKeyPassword Specifies the password for the _Endorsement Key_ PFX file. If no password was used when the PFX was created (which is not recommended), this parameter may be omitted. .PARAMETER EndorsementKeyCertificate Specifies the endorsement key certificate as an X509Certificate object .PARAMETER SigningKeyFile Specifies the path to the Secure Platform Management signing key as a PFX file. If the PFX file is protected by a password (recommended), the SigningKeyPassword parameter should also be provided. .PARAMETER SigningKeyCertificate Specifies the Secure Platform Management signing key certificate as an X509Certificate object .PARAMETER SigningKeyPassword Specifies the Secure Platform Management signing key file password, if required. .PARAMETER Nonce Specifies a Nonce. If nonce is specified, the Secure Platform Management subsystem will only accept commands with a nonce greater or equal to the last nonce sent. This approach helps to prevent replay attacks. If not specified, the nonce is inferred from the current local time. The current local time as the nonce works in most cases. However, this approach has a resolution of seconds, so when performing parallel operations or a high volume of operations, it is possible for the same counter to be interpreted for more than one command. In these cases, the caller should use its own nonce derivation and provide it through this parameter. .PARAMETER OutputFile Specifies the file to write output to instead of writing the output to the pipeline .PARAMETER RemoteEndorsementKeyID Specifies the Endorsement Key ID to be used .PARAMETER RemoteSigningKeyID Specifies the Signing Key ID to be provisioned .PARAMETER RemoteSigningServiceURL Specifies the (Key Management Service) KMS server URL (I.e.: https://<KMSAppName>.azurewebsites.net/). This URL must be HTTPS. .PARAMETER CacheAccessToken If specified, the access token is cached in msalcache.dat file and user credentials will not be asked again until the credentials expire. This parameter should be specified for caching the access token when performing multiple operations on the KMS server. If access token is not cached, the user must re-enter credentials on each call of this command. .LINK [Blog post: HP Secure Platform Management with the HP Client Management Script Library](https://developers.hp.com/hp-client-management/blog/hp-secure-platform-management-hp-client-management-script-library) .NOTES - Requires HP BIOS with Secure Platform Management support. .EXAMPLE $payload = New-HPSecurePlatformSigningKeyProvisioningPayload -EndorsementKeyFile "$path\endorsement_key.pfx" ` -SigningKeyFile "$path\signing_key.pfx" ... $payload | Set-HPSecurePlatformPayload #> function New-HPSecurePlatformSigningKeyProvisioningPayload { [CmdletBinding(DefaultParameterSetName = "EF_SF",HelpUri = "https://developers.hp.com/hp-client-management/doc/New-HPSecurePlatformSigningKeyProvisioningPayload")] param( [Parameter(ParameterSetName = "EF_SF",Mandatory = $true,Position = 0)] [Parameter(ParameterSetName = "EF_SB",Mandatory = $true,Position = 0)] [System.IO.FileInfo]$EndorsementKeyFile, [Parameter(ParameterSetName = "EF_SF",Mandatory = $false,Position = 1)] [Parameter(ParameterSetName = "EF_SB",Mandatory = $false,Position = 1)] [string]$EndorsementKeyPassword, [Parameter(ParameterSetName = "EF_SF",Mandatory = $false,Position = 2)] [Parameter(ParameterSetName = "EB_SF",Mandatory = $false,Position = 2)] [System.IO.FileInfo]$SigningKeyFile, [Parameter(ParameterSetName = "EF_SF",Mandatory = $false,Position = 3)] [Parameter(ParameterSetName = "EB_SF",Mandatory = $false,Position = 3)] [string]$SigningKeyPassword, [Parameter(ParameterSetName = "EB_SF",Mandatory = $true,Position = 0)] [Parameter(ParameterSetName = "EB_SB",Mandatory = $true,Position = 0)] [System.Security.Cryptography.X509Certificates.X509Certificate2]$EndorsementKeyCertificate, [Parameter(ValueFromPipeline = $true,ParameterSetName = "EB_SB",Mandatory = $false,Position = 2)] [Parameter(ValueFromPipeline = $true,ParameterSetName = "EF_SB",Mandatory = $false,Position = 2)] [System.Security.Cryptography.X509Certificates.X509Certificate2]$SigningKeyCertificate, [Parameter(ParameterSetName = "EF_SF",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "EB_SF",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "EF_SB",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "EB_SB",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 1)] [uint32]$Nonce = [math]::Floor([decimal](Get-Date (Get-Date).ToUniversalTime() -UFormat "%s").Replace(',','.')), [Parameter(ParameterSetName = "EF_SF",Mandatory = $false,Position = 5)] [Parameter(ParameterSetName = "EB_SF",Mandatory = $false,Position = 5)] [Parameter(ParameterSetName = "EF_SB",Mandatory = $false,Position = 5)] [Parameter(ParameterSetName = "EB_SB",Mandatory = $false,Position = 5)] [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 2)] [System.IO.FileInfo]$OutputFile, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 3)] [string]$RemoteEndorsementKeyID, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 4)] [string]$RemoteSigningKeyID, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 5)] [string]$RemoteSigningServiceURL, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 6)] [switch]$CacheAccessToken ) # only allow https or file paths with or without file:// URL prefix if ($RemoteSigningServiceURL -and -not ($RemoteSigningServiceURL.StartsWith("https://",$true,$null) -or [System.IO.Directory]::Exists($RemoteSigningServiceURL) -or $RemoteSigningServiceURL.StartsWith("file://",$true,$null))) { throw [System.ArgumentException]"Only HTTPS or valid existing directory paths are supported." } if ($PSCmdlet.ParameterSetName -eq "RemoteSigning") { if (-not $RemoteSigningServiceURL.EndsWith('/')) { $RemoteSigningServiceURL += '/' } $RemoteSigningServiceURL += 'api/commands/p21skprovisioningpayload' $params = @{ EndorsementKeyID = $RemoteEndorsementKeyID Nonce = $Nonce } if ($RemoteSigningKeyID) { $params.SigningKeyID = $RemoteSigningKeyID } $jsonPayload = New-HPPrivateRemoteSecurePlatformProvisioningJson @params $accessToken = Get-HPPrivateSureAdminKMSAccessToken -CacheAccessToken:$CacheAccessToken $response,$responseContent = Send-HPPrivateKMSRequest -KMSUri $RemoteSigningServiceURL -JsonPayload $jsonPayload -AccessToken $accessToken -Verbose:$VerbosePreference if ($response -eq "OK") { return $responseContent } else { Invoke-HPPrivateKMSErrorHandle -ApiResponseContent $responseContent -Status $response } } else { $ek = Get-HPPrivateX509CertCoalesce -File $EndorsementKeyFile -password $EndorsementKeyPassword -cert $EndorsementKeyCertificate -Verbose:$VerbosePreference $sk = $null if ($SigningKeyFile -or $SigningKeyCertificate) { $sk = Get-HPPrivateX509CertCoalesce -File $SigningKeyFile -password $SigningKeyPassword -cert $SigningKeyCertificate -Verbose:$VerbosePreference } Write-Verbose "Creating SK provisioning payload" $payload = New-Object sk_provisioning_t $sub = New-Object sk_provisioning_payload_t $sub.Counter = $nonce if ($sk) { $sub.mod = $Sk.Modulus } else { Write-Verbose "Assuming deprovisioning due to missing signing key update" $sub.mod = New-Object byte[] 256 } $payload.Data = $sub Write-Verbose "Using counter value of $($sub.Counter)" $out = Convert-HPPrivateObjectToBytes -obj $sub -Verbose:$VerbosePreference $payload.sig = Invoke-HPPrivateSignData -Data $out[0] -Certificate $ek.Full -Verbose:$VerbosePreference Write-Verbose "Serializing payload" $out = Convert-HPPrivateObjectToBytes -obj $payload -Verbose:$VerbosePreference $output = New-Object -TypeName PortableFileFormat $output.Data = ($out[0])[0..($out[1] - 1)]; $output.purpose = "hp:provision:signingkey" $output.timestamp = Get-Date if ($OutputFile) { Write-Verbose "Will output to file $OutputFile" $f = $ExecutionContext.SessionState.Path.GetUnresolvedProviderPathFromPSPath($OutputFile) $output | ConvertTo-Json -Compress | Out-File -FilePath $f -Encoding utf8 } else { $output | ConvertTo-Json -Compress } } } function New-HPPrivateRemoteSecurePlatformProvisioningJson { [CmdletBinding()] param( [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 1)] [uint32]$Nonce, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 2)] [string]$EndorsementKeyId, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 3)] [string]$SigningKeyId ) $payload = [ordered]@{ EKId = $EndorsementKeyId } if ($Nonce) { $payload['Nonce'] = $Nonce } if ($SigningKeyId) { $payload['SKId'] = $SigningKeyId } $payload | ConvertTo-Json -Compress } <# .SYNOPSIS Creates a deprovisioning payload .DESCRIPTION This command creates a payload to deprovision the HP Secure Platform Management. The caller must have access to the Endorsement Key private key in order to create this payload. There are three endorsement options to choose from: - Endorsement Key File (and Password) using -EndorsementKeyFile and -EndorsementKeyPassword parameters - Endorsement Key Certificate using -EndorsementKeyCertificate parameter - Remote Endorsement using -RemoteEndorsementKeyID and -RemoteSigningServiceURL parameters Please note that using a Key File with Password in PFX format is recommended over using an X509 Certificate object because a private key in a certificate is not password protected. This command writes the created payload to the pipeline or to the file specified in the -OutputFile parameter. This payload can then be passed to the Set-HPSecurePlatformPayload command. Security note: Payloads should only be created on secure servers. Once created, the payload may be transferred to a client and applied via the Set-HPSecurePlatformPayload command. Creating the payload and passing it to the Set-HPSecurePlatformPayload command via the pipeline is not a recommended production pattern. .PARAMETER EndorsementKeyFile Specifies the _Key Endorsement_ key certificate as a PFX (PKCS #12) file .PARAMETER EndorsementKeyPassword The password for the endorsement key certificate file. If no password was used when the PFX was created (which is not recommended), this parameter may be omitted. .PARAMETER EndorsementKeyCertificate Specifies the endorsement key certificate as an X509Certificate object .PARAMETER Nonce Specifies a Nonce. If nonce is specified, the Secure Platform Management subsystem will only accept commands with a nonce greater or equal to the last nonce sent. This approach helps to prevent replay attacks. If not specified, the nonce is inferred from the current local time. The current local time as the nonce works in most cases. However, this approach has a resolution of seconds, so when performing parallel operations or a high volume of operations, it is possible for the same counter to be interpreted for more than one command. In these cases, the caller should use its own nonce derivation and provide it through this parameter. .PARAMETER RemoteEndorsementKeyID Specifies the Endorsement Key ID to be used .PARAMETER RemoteSigningServiceURL Specifies the (Key Management Service) KMS server URL (I.e.: https://<KMSAppName>.azurewebsites.net/). This URL must be HTTPS. .PARAMETER CacheAccessToken If specified, the access token is cached in msalcache.dat file and user credentials will not be asked again until the credentials expire. This parameter should be specified for caching the access token when performing multiple operations on the KMS server. If access token is not cached, the user must re-enter credentials on each call of this command. .LINK [Blog post: HP Secure Platform Management with the HP Client Management Script Library](https://developers.hp.com/hp-client-management/blog/hp-secure-platform-management-hp-client-management-script-library) .PARAMETER OutputFile Specifies the file to write output to instead of writing the output to the pipeline .NOTES - Requires HP BIOS with Secure Platform Management support. .EXAMPLE New-HPSecurePlatformDeprovisioningPayload -EndorsementKeyFile kek.pfx | Set-HPSecurePlatformPayload .EXAMPLE New-HPSecurePlatformDeprovisioningPayload -EndorsementKeyFile kek.pfx -OutputFile deprovisioning_payload.dat #> function New-HPSecurePlatformDeprovisioningPayload { [CmdletBinding(DefaultParameterSetName = "EF",HelpUri = "https://developers.hp.com/hp-client-management/doc/New-HPSecurePlatformDeprovisioningPayload")] param( [Parameter(ParameterSetName = "EF",Mandatory = $true,Position = 0)] [string]$EndorsementKeyFile, [Parameter(ParameterSetName = "EF",Mandatory = $false,Position = 1)] [string]$EndorsementKeyPassword, [Parameter(ParameterSetName = "EF",Mandatory = $false,Position = 2)] [Parameter(ParameterSetName = "EB",Mandatory = $false,Position = 2)] [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 1)] [uint32]$Nonce = [math]::Floor([decimal](Get-Date (Get-Date).ToUniversalTime() -UFormat "%s").Replace(',','.')), [Parameter(ParameterSetName = "EB",Mandatory = $true,Position = 0)] [System.Security.Cryptography.X509Certificates.X509Certificate2]$EndorsementKeyCertificate, [Parameter(ParameterSetName = "EB",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "EF",Mandatory = $false,Position = 4)] [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 2)] [System.IO.FileInfo]$OutputFile, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 3)] [string]$RemoteEndorsementKeyID, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $true,Position = 4)] [string]$RemoteSigningServiceURL, [Parameter(ParameterSetName = "RemoteSigning",Mandatory = $false,Position = 5)] [switch]$CacheAccessToken ) # only allow https or file paths with or without file:// URL prefix if ($RemoteSigningServiceURL -and -not ($RemoteSigningServiceURL.StartsWith("https://",$true,$null) -or [System.IO.Directory]::Exists($RemoteSigningServiceURL) -or $RemoteSigningServiceURL.StartsWith("file://",$true,$null))) { throw [System.ArgumentException]"Only HTTPS or valid existing directory paths are supported." } New-HPSecurePlatformSigningKeyProvisioningPayload @PSBoundParameters } <# .SYNOPSIS Applies a payload to HP Secure Platform Management .DESCRIPTION This command applies a properly encoded payload created by one of the New-HPSecurePlatform*, New-HPSureRun*, New-HPSureAdmin*, or New-HPSureRecover* commands to the BIOS. Payloads created by means other than the commands mentioned above are not supported. Security note: Payloads should only be created on secure servers. Once created, the payload may be transferred to a client and applied via the Set-HPSecurePlatformPayload command. Creating the payload and passing it to the Set-HPSecurePlatformPayload command via the pipeline is not a recommended production pattern. .PARAMETER Payload Specifies the payload to apply. This parameter can also be specified via the pipeline. .PARAMETER PayloadFile Specifies the payload file to apply. This file must contain a properly encoded payload. .LINK [Blog post: HP Secure Platform Management with the HP Client Management Script Library](https://developers.hp.com/hp-client-management/blog/hp-secure-platform-management-hp-client-management-script-library) .NOTES - Requires HP BIOS with Secure Platform Management support. - This command requires elevated privileges. .EXAMPLE Set-HPSecurePlatformPayload -Payload $payload .EXAMPLE Set-HPSecurePlatformPayload -PayloadFile .\payload.dat .EXAMPLE $payload | Set-HPSecurePlatformPayload #> function Set-HPSecurePlatformPayload { [CmdletBinding(DefaultParameterSetName = "FB",HelpUri = "https://developers.hp.com/hp-client-management/doc/Set-HPSecurePlatformPayload")] param( [Parameter(ParameterSetName = "FB",ValueFromPipeline = $true,Position = 0,Mandatory = $True)] [string]$Payload, [Parameter(ParameterSetName = "FF",ValueFromPipeline = $true,Position = 0,Mandatory = $True)] [System.IO.FileInfo]$PayloadFile ) if ($PSCmdlet.ParameterSetName -eq "FB") { Write-Verbose "Setting payload string" [PortableFileFormat]$type = ConvertFrom-Json -InputObject $Payload } else { Write-Verbose "Setting from file $PayloadFile" $Payload = Get-Content -Path $PayloadFile -Encoding UTF8 [PortableFileFormat]$type = ConvertFrom-Json -InputObject $Payload } $mi_result = 0 $pbytes = $type.Data Write-Verbose "Setting payload from document with type $($type.purpose)" $cmd = $null switch ($type.purpose) { "hp:provision:endorsementkey" { $cmd = '[DfmNativeSecurePlatform]::set_ek_provisioning' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:provision:signingkey" { $cmd = '[DfmNativeSecurePlatform]::set_sk_provisioning' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:provision:os_image" { $cmd = '[DfmNativeSureRecover]::set_surerecover_osr_provisioning' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:provision:recovery_image" { $cmd = '[DfmNativeSureRecover]::set_surerecover_re_provisioning' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:failover:os_image" { if (-not (Get-HPSureRecoverState).ImageIsProvisioned) { throw [System.IO.InvalidDataException]"Custom OS Recovery Image is required to configure failover" } $cmd = '[DfmNativeSureRecover]::set_surerecover_osr_failover' + (Test-OSBitness) + '($pbytes,$pbytes.length,[ref]$mi_result);' } "hp:surerecover:deprovision" { $cmd = '[DfmNativeSureRecover]::set_surerecover_deprovision_opaque' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:scheduler" { $cmd = '[DfmNativeSureRecover]::set_surerecover_schedule' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:configure" { $cmd = '[DfmNativeSureRecover]::set_surerecover_configuration' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:trigger" { $cmd = '[DfmNativeSureRecover]::set_surerecover_trigger' + (Test-OSBitness) + '($pbytes,$pbytes.length, [ref]$mi_result);' } "hp:surerecover:service_event" { $cmd = '[DfmNativeSureRecover]::raise_surerecover_service_event_opaque' + (Test-OSBitness) + '($null,0, [ref]$mi_result);' } "hp:surerrun:manifest" { $mbytes = $type.Meta1 $cmd = '[DfmNativeSureRun]::set_surererun_manifest' + (Test-OSBitness) + '($pbytes,$pbytes.length, $mbytes, $mbytes.length, [ref]$mi_result);' } "hp:sureadmin:biossetting" { $Payload | Set-HPPrivateBIOSSettingValuePayload -Verbose:$VerbosePreference } "hp:sureadmin:biossettingslist" { $Payload | Set-HPPrivateBIOSSettingsListPayload -Verbose:$VerbosePreference } "hp:sureadmin:resetsettings" { $Payload | Set-HPPrivateBIOSSettingDefaultsPayload -Verbose:$VerbosePreference } "hp:sureadmin:firmwareupdate" { $Payload | Set-HPPrivateFirmwareUpdatePayload -Verbose:$VerbosePreference } default { throw [System.IO.InvalidDataException]"Document type $($type.purpose) not recognized" } } if ($cmd) { $result = Invoke-Expression -Command $cmd Test-HPPrivateCustomResult -result $result -mi_result $mi_result -Category 0x04 } } # SIG # Begin signature block # MIIoFwYJKoZIhvcNAQcCoIIoCDCCKAQCAQExDzANBglghkgBZQMEAgEFADB5Bgor # BgEEAYI3AgEEoGswaTA0BgorBgEEAYI3AgEeMCYCAwEAAAQQH8w7YFlLCE63JNLG # KX7zUQIBAAIBAAIBAAIBAAIBADAxMA0GCWCGSAFlAwQCAQUABCDAVYa1oyNOA3A6 # TP74o1ESYLzGbfmoX35udYiye97hdKCCDYowggawMIIEmKADAgECAhAIrUCyYNKc # TJ9ezam9k67ZMA0GCSqGSIb3DQEBDAUAMGIxCzAJBgNVBAYTAlVTMRUwEwYDVQQK # EwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5jb20xITAfBgNV # BAMTGERpZ2lDZXJ0IFRydXN0ZWQgUm9vdCBHNDAeFw0yMTA0MjkwMDAwMDBaFw0z # NjA0MjgyMzU5NTlaMGkxCzAJBgNVBAYTAlVTMRcwFQYDVQQKEw5EaWdpQ2VydCwg # SW5jLjFBMD8GA1UEAxM4RGlnaUNlcnQgVHJ1c3RlZCBHNCBDb2RlIFNpZ25pbmcg # UlNBNDA5NiBTSEEzODQgMjAyMSBDQTEwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAw # ggIKAoICAQDVtC9C0CiteLdd1TlZG7GIQvUzjOs9gZdwxbvEhSYwn6SOaNhc9es0 # JAfhS0/TeEP0F9ce2vnS1WcaUk8OoVf8iJnBkcyBAz5NcCRks43iCH00fUyAVxJr # Q5qZ8sU7H/Lvy0daE6ZMswEgJfMQ04uy+wjwiuCdCcBlp/qYgEk1hz1RGeiQIXhF # LqGfLOEYwhrMxe6TSXBCMo/7xuoc82VokaJNTIIRSFJo3hC9FFdd6BgTZcV/sk+F # LEikVoQ11vkunKoAFdE3/hoGlMJ8yOobMubKwvSnowMOdKWvObarYBLj6Na59zHh # 3K3kGKDYwSNHR7OhD26jq22YBoMbt2pnLdK9RBqSEIGPsDsJ18ebMlrC/2pgVItJ # wZPt4bRc4G/rJvmM1bL5OBDm6s6R9b7T+2+TYTRcvJNFKIM2KmYoX7BzzosmJQay # g9Rc9hUZTO1i4F4z8ujo7AqnsAMrkbI2eb73rQgedaZlzLvjSFDzd5Ea/ttQokbI # YViY9XwCFjyDKK05huzUtw1T0PhH5nUwjewwk3YUpltLXXRhTT8SkXbev1jLchAp # QfDVxW0mdmgRQRNYmtwmKwH0iU1Z23jPgUo+QEdfyYFQc4UQIyFZYIpkVMHMIRro # OBl8ZhzNeDhFMJlP/2NPTLuqDQhTQXxYPUez+rbsjDIJAsxsPAxWEQIDAQABo4IB # WTCCAVUwEgYDVR0TAQH/BAgwBgEB/wIBADAdBgNVHQ4EFgQUaDfg67Y7+F8Rhvv+ # YXsIiGX0TkIwHwYDVR0jBBgwFoAU7NfjgtJxXWRM3y5nP+e6mK4cD08wDgYDVR0P # AQH/BAQDAgGGMBMGA1UdJQQMMAoGCCsGAQUFBwMDMHcGCCsGAQUFBwEBBGswaTAk # BggrBgEFBQcwAYYYaHR0cDovL29jc3AuZGlnaWNlcnQuY29tMEEGCCsGAQUFBzAC # hjVodHRwOi8vY2FjZXJ0cy5kaWdpY2VydC5jb20vRGlnaUNlcnRUcnVzdGVkUm9v # dEc0LmNydDBDBgNVHR8EPDA6MDigNqA0hjJodHRwOi8vY3JsMy5kaWdpY2VydC5j # b20vRGlnaUNlcnRUcnVzdGVkUm9vdEc0LmNybDAcBgNVHSAEFTATMAcGBWeBDAED # MAgGBmeBDAEEATANBgkqhkiG9w0BAQwFAAOCAgEAOiNEPY0Idu6PvDqZ01bgAhql # +Eg08yy25nRm95RysQDKr2wwJxMSnpBEn0v9nqN8JtU3vDpdSG2V1T9J9Ce7FoFF # UP2cvbaF4HZ+N3HLIvdaqpDP9ZNq4+sg0dVQeYiaiorBtr2hSBh+3NiAGhEZGM1h # mYFW9snjdufE5BtfQ/g+lP92OT2e1JnPSt0o618moZVYSNUa/tcnP/2Q0XaG3Ryw # YFzzDaju4ImhvTnhOE7abrs2nfvlIVNaw8rpavGiPttDuDPITzgUkpn13c5Ubdld # AhQfQDN8A+KVssIhdXNSy0bYxDQcoqVLjc1vdjcshT8azibpGL6QB7BDf5WIIIJw # 8MzK7/0pNVwfiThV9zeKiwmhywvpMRr/LhlcOXHhvpynCgbWJme3kuZOX956rEnP # LqR0kq3bPKSchh/jwVYbKyP/j7XqiHtwa+aguv06P0WmxOgWkVKLQcBIhEuWTatE # QOON8BUozu3xGFYHKi8QxAwIZDwzj64ojDzLj4gLDb879M4ee47vtevLt/B3E+bn # KD+sEq6lLyJsQfmCXBVmzGwOysWGw/YmMwwHS6DTBwJqakAwSEs0qFEgu60bhQji # WQ1tygVQK+pKHJ6l/aCnHwZ05/LWUpD9r4VIIflXO7ScA+2GRfS0YW6/aOImYIbq # yK+p/pQd52MbOoZWeE4wggbSMIIEuqADAgECAhAJvPMqSNxAYhV5FFpsbzOhMA0G # CSqGSIb3DQEBCwUAMGkxCzAJBgNVBAYTAlVTMRcwFQYDVQQKEw5EaWdpQ2VydCwg # SW5jLjFBMD8GA1UEAxM4RGlnaUNlcnQgVHJ1c3RlZCBHNCBDb2RlIFNpZ25pbmcg # UlNBNDA5NiBTSEEzODQgMjAyMSBDQTEwHhcNMjQwMjE1MDAwMDAwWhcNMjUwMjE4 # MjM1OTU5WjBaMQswCQYDVQQGEwJVUzETMBEGA1UECBMKQ2FsaWZvcm5pYTESMBAG # A1UEBxMJUGFsbyBBbHRvMRAwDgYDVQQKEwdIUCBJbmMuMRAwDgYDVQQDEwdIUCBJ # bmMuMIIBojANBgkqhkiG9w0BAQEFAAOCAY8AMIIBigKCAYEApbF6fMFy6zhGVra3 # SZN418Cp2O8kjihQCU9tqPO9tkzbMyTsgveLJVnXPJNG9kQPMGUNp+wEHcoUzlRc # YJMEL9fhfzpWPeSIIezGLPCdrkMmS3fdRUwFqEs7z/C6Ui2ZqMaKhKjBJTIWnipe # rRfzGB7RoLepQcgqeF5s0DBy4oG83dqcRHo3IJRTBg39tHe3mD5uoGHn5n366abX # vC+k53BVyD8w8XLppFVH5XuNlXMq/Ohf613i7DRb/+u92ZiAPVPXXnlxUE26cuDb # OfJKN/bXPmvnWcNW3YHVp9ztPTQZhX4yWYXHrAI2Cv6HxUpO6NzhFoRoBTkcYNbA # 91pf1Vagh/MNcA2BfQYT975/Vlvj9cfEZ/NwZthZuHa3rdrvCKhhjw7YU2QUeaTJ # 0uaX4g6B9PFNqAASYLach3CDJiLmYEfus/utPh57mk0q27yL25fXo/PaMDXiDNIi # 7Wuz7A+sPsbtdiY8zvEIRQ+XJXtKAlD4tqG9YzlTO6ZoQX/rAgMBAAGjggIDMIIB # /zAfBgNVHSMEGDAWgBRoN+Drtjv4XxGG+/5hewiIZfROQjAdBgNVHQ4EFgQURH4F # u5yEAuElYWUbyGRYkNLLrA8wPgYDVR0gBDcwNTAzBgZngQwBBAEwKTAnBggrBgEF # BQcCARYbaHR0cDovL3d3dy5kaWdpY2VydC5jb20vQ1BTMA4GA1UdDwEB/wQEAwIH # gDATBgNVHSUEDDAKBggrBgEFBQcDAzCBtQYDVR0fBIGtMIGqMFOgUaBPhk1odHRw # Oi8vY3JsMy5kaWdpY2VydC5jb20vRGlnaUNlcnRUcnVzdGVkRzRDb2RlU2lnbmlu # Z1JTQTQwOTZTSEEzODQyMDIxQ0ExLmNybDBToFGgT4ZNaHR0cDovL2NybDQuZGln # aWNlcnQuY29tL0RpZ2lDZXJ0VHJ1c3RlZEc0Q29kZVNpZ25pbmdSU0E0MDk2U0hB # Mzg0MjAyMUNBMS5jcmwwgZQGCCsGAQUFBwEBBIGHMIGEMCQGCCsGAQUFBzABhhho # dHRwOi8vb2NzcC5kaWdpY2VydC5jb20wXAYIKwYBBQUHMAKGUGh0dHA6Ly9jYWNl # cnRzLmRpZ2ljZXJ0LmNvbS9EaWdpQ2VydFRydXN0ZWRHNENvZGVTaWduaW5nUlNB # NDA5NlNIQTM4NDIwMjFDQTEuY3J0MAkGA1UdEwQCMAAwDQYJKoZIhvcNAQELBQAD # ggIBAFiCyuI6qmaQodDyMNpp0l7eIXFgJ4JI59o59PleFj4rcyd/+F4iI7u5if8G # rV5Kn3s3tK9vfJO8SpqtEh7lL4e69z6v3ohcy4uy2hsjKQ/fFcDo9pQYDGmDVjCa # D5qSVEIBlJHBe5NKEJAgUE0kaMjLzbi2+8DKJlNtvZ+hatuPl9fMnmU+VbQh7JhZ # yJdz8Ay0tcQ9lC8HAX5Ah/pU+Vtv+c8gMSxjS1aWXoGCa1869IVi2O6qx7MuX12U # 1eIpB9XxYr7HSebvg2G7Gz6nCh7u+4k7m3hJu9EStUIN2JII5260+E60uDWoHEhx # tHbdueFQxJrTKnhplOSaaPFCVBDkWG83ZzN9N3z/45w1pBUNBiPJdRQJ58MhBYQe # Zl90heMBL8QNQk2i0E5gHNT9pJiCR9+mvJkRxEVgUn+16ZpVnI6kzhThV9qBaWVF # h83X4UWc/nwHKIuu+4x4fmkYc79A3MrsHflZIO8jOy0GC/xBnZTQ8s5b9Tb2UkHk # w692Ypl7War3W7M37JCAPC/A7M4CwQYjdjG43zs5m36auYVaTvRLKtZVLzcj8oZX # 4vqhlZ8+jCPXFiuDfoBXiTckTLpv/eHQ6q7Aoda+qARWPPE1U2v5r/lpKVqIx7B4 # PdFZAUf5MtG/Bj7LVXvXjW8ABIJv7L4cI2akn6Es0dmvd6PsMYIZ4zCCGd8CAQEw # fTBpMQswCQYDVQQGEwJVUzEXMBUGA1UEChMORGlnaUNlcnQsIEluYy4xQTA/BgNV # BAMTOERpZ2lDZXJ0IFRydXN0ZWQgRzQgQ29kZSBTaWduaW5nIFJTQTQwOTYgU0hB # Mzg0IDIwMjEgQ0ExAhAJvPMqSNxAYhV5FFpsbzOhMA0GCWCGSAFlAwQCAQUAoHww # EAYKKwYBBAGCNwIBDDECMAAwGQYJKoZIhvcNAQkDMQwGCisGAQQBgjcCAQQwHAYK # KwYBBAGCNwIBCzEOMAwGCisGAQQBgjcCARUwLwYJKoZIhvcNAQkEMSIEIK6zUt/4 # Km9Z+E3se4Oot7w5DogOpeyYVl3kBXLUZJJAMA0GCSqGSIb3DQEBAQUABIIBgEyg # R4OZOC3xGtW6p9r5y+Q5PlHtuWnYn60REIB3MM807ZLwjZoxPedvYOxweM/+1cqW # nst2CrSziysAx+rYqmmaKfCREBQsxuet/10bPxwFSA0ZpwL+QXpRt2vKRBNxBNOd # YbssxC/F2dyafgHklrqYSHiUvOrGk+h/P4uwAPhUkh43k3uqETzWPjK6RZtE1oWw # VVyXe3fJe+27Z8VC5emVyma39cFlczQK7Oh8UktkxuJ8PqQ/D+10yz0J03xNTAii # 4AsizJpwrk33Qfh+b3J/LB39anfstSUfLOyYCKG8GtZZB+njtRipNzz2aQ7AU/lS # ZAU5VEjmIjNswciO4NJLR9k2z+7WIe9zWntv2QJih0rxjK+mHEvLA57FgcubzfSl # SxEAHDCII2Nvs0/O+WFjXze0IDgkVW11RDqQmzUYfwubz3EHOeE8Mre5PEE3s2+p # LCmMUdyoPCOPdSjAd0ihsL5pnsR/fZHH0mx2RHwg8M7zpApaki/s96ZMvU34sqGC # Fzkwghc1BgorBgEEAYI3AwMBMYIXJTCCFyEGCSqGSIb3DQEHAqCCFxIwghcOAgED # MQ8wDQYJYIZIAWUDBAIBBQAwdwYLKoZIhvcNAQkQAQSgaARmMGQCAQEGCWCGSAGG # /WwHATAxMA0GCWCGSAFlAwQCAQUABCAvl05CkajcE0m2gpCY7h33bZ75YjOxsK6z # UTd+5kdYcwIQH6wRjItA+fyc1DAC17Z4wxgPMjAyNDExMDYxNzE3MzVaoIITAzCC # BrwwggSkoAMCAQICEAuuZrxaun+Vh8b56QTjMwQwDQYJKoZIhvcNAQELBQAwYzEL # MAkGA1UEBhMCVVMxFzAVBgNVBAoTDkRpZ2lDZXJ0LCBJbmMuMTswOQYDVQQDEzJE # aWdpQ2VydCBUcnVzdGVkIEc0IFJTQTQwOTYgU0hBMjU2IFRpbWVTdGFtcGluZyBD # QTAeFw0yNDA5MjYwMDAwMDBaFw0zNTExMjUyMzU5NTlaMEIxCzAJBgNVBAYTAlVT # MREwDwYDVQQKEwhEaWdpQ2VydDEgMB4GA1UEAxMXRGlnaUNlcnQgVGltZXN0YW1w # IDIwMjQwggIiMA0GCSqGSIb3DQEBAQUAA4ICDwAwggIKAoICAQC+anOf9pUhq5Yw # ultt5lmjtej9kR8YxIg7apnjpcH9CjAgQxK+CMR0Rne/i+utMeV5bUlYYSuuM4vQ # ngvQepVHVzNLO9RDnEXvPghCaft0djvKKO+hDu6ObS7rJcXa/UKvNminKQPTv/1+ # kBPgHGlP28mgmoCw/xi6FG9+Un1h4eN6zh926SxMe6We2r1Z6VFZj75MU/HNmtsg # tFjKfITLutLWUdAoWle+jYZ49+wxGE1/UXjWfISDmHuI5e/6+NfQrxGFSKx+rDdN # MsePW6FLrphfYtk/FLihp/feun0eV+pIF496OVh4R1TvjQYpAztJpVIfdNsEvxHo # fBf1BWkadc+Up0Th8EifkEEWdX4rA/FE1Q0rqViTbLVZIqi6viEk3RIySho1XyHL # IAOJfXG5PEppc3XYeBH7xa6VTZ3rOHNeiYnY+V4j1XbJ+Z9dI8ZhqcaDHOoj5KGg # 4YuiYx3eYm33aebsyF6eD9MF5IDbPgjvwmnAalNEeJPvIeoGJXaeBQjIK13SlnzO # DdLtuThALhGtyconcVuPI8AaiCaiJnfdzUcb3dWnqUnjXkRFwLtsVAxFvGqsxUA2 # Jq/WTjbnNjIUzIs3ITVC6VBKAOlb2u29Vwgfta8b2ypi6n2PzP0nVepsFk8nlcuW # fyZLzBaZ0MucEdeBiXL+nUOGhCjl+QIDAQABo4IBizCCAYcwDgYDVR0PAQH/BAQD # AgeAMAwGA1UdEwEB/wQCMAAwFgYDVR0lAQH/BAwwCgYIKwYBBQUHAwgwIAYDVR0g # BBkwFzAIBgZngQwBBAIwCwYJYIZIAYb9bAcBMB8GA1UdIwQYMBaAFLoW2W1NhS9z # KXaaL3WMaiCPnshvMB0GA1UdDgQWBBSfVywDdw4oFZBmpWNe7k+SH3agWzBaBgNV # HR8EUzBRME+gTaBLhklodHRwOi8vY3JsMy5kaWdpY2VydC5jb20vRGlnaUNlcnRU # cnVzdGVkRzRSU0E0MDk2U0hBMjU2VGltZVN0YW1waW5nQ0EuY3JsMIGQBggrBgEF # BQcBAQSBgzCBgDAkBggrBgEFBQcwAYYYaHR0cDovL29jc3AuZGlnaWNlcnQuY29t # MFgGCCsGAQUFBzAChkxodHRwOi8vY2FjZXJ0cy5kaWdpY2VydC5jb20vRGlnaUNl # cnRUcnVzdGVkRzRSU0E0MDk2U0hBMjU2VGltZVN0YW1waW5nQ0EuY3J0MA0GCSqG # SIb3DQEBCwUAA4ICAQA9rR4fdplb4ziEEkfZQ5H2EdubTggd0ShPz9Pce4FLJl6r # eNKLkZd5Y/vEIqFWKt4oKcKz7wZmXa5VgW9B76k9NJxUl4JlKwyjUkKhk3aYx7D8 # vi2mpU1tKlY71AYXB8wTLrQeh83pXnWwwsxc1Mt+FWqz57yFq6laICtKjPICYYf/ # qgxACHTvypGHrC8k1TqCeHk6u4I/VBQC9VK7iSpU5wlWjNlHlFFv/M93748YTeoX # U/fFa9hWJQkuzG2+B7+bMDvmgF8VlJt1qQcl7YFUMYgZU1WM6nyw23vT6QSgwX5P # q2m0xQ2V6FJHu8z4LXe/371k5QrN9FQBhLLISZi2yemW0P8ZZfx4zvSWzVXpAb9k # 4Hpvpi6bUe8iK6WonUSV6yPlMwerwJZP/Gtbu3CKldMnn+LmmRTkTXpFIEB06nXZ # rDwhCGED+8RsWQSIXZpuG4WLFQOhtloDRWGoCwwc6ZpPddOFkM2LlTbMcqFSzm4c # d0boGhBq7vkqI1uHRz6Fq1IX7TaRQuR+0BGOzISkcqwXu7nMpFu3mgrlgbAW+Bzi # kRVQ3K2YHcGkiKjA4gi4OA/kz1YCsdhIBHXqBzR0/Zd2QwQ/l4Gxftt/8wY3grcc # /nS//TVkej9nmUYu83BDtccHHXKibMs/yXHhDXNkoPIdynhVAku7aRZOwqw6pDCC # Bq4wggSWoAMCAQICEAc2N7ckVHzYR6z9KGYqXlswDQYJKoZIhvcNAQELBQAwYjEL # MAkGA1UEBhMCVVMxFTATBgNVBAoTDERpZ2lDZXJ0IEluYzEZMBcGA1UECxMQd3d3 # LmRpZ2ljZXJ0LmNvbTEhMB8GA1UEAxMYRGlnaUNlcnQgVHJ1c3RlZCBSb290IEc0 # MB4XDTIyMDMyMzAwMDAwMFoXDTM3MDMyMjIzNTk1OVowYzELMAkGA1UEBhMCVVMx # FzAVBgNVBAoTDkRpZ2lDZXJ0LCBJbmMuMTswOQYDVQQDEzJEaWdpQ2VydCBUcnVz # dGVkIEc0IFJTQTQwOTYgU0hBMjU2IFRpbWVTdGFtcGluZyBDQTCCAiIwDQYJKoZI # hvcNAQEBBQADggIPADCCAgoCggIBAMaGNQZJs8E9cklRVcclA8TykTepl1Gh1tKD # 0Z5Mom2gsMyD+Vr2EaFEFUJfpIjzaPp985yJC3+dH54PMx9QEwsmc5Zt+FeoAn39 # Q7SE2hHxc7Gz7iuAhIoiGN/r2j3EF3+rGSs+QtxnjupRPfDWVtTnKC3r07G1decf # BmWNlCnT2exp39mQh0YAe9tEQYncfGpXevA3eZ9drMvohGS0UvJ2R/dhgxndX7RU # CyFobjchu0CsX7LeSn3O9TkSZ+8OpWNs5KbFHc02DVzV5huowWR0QKfAcsW6Th+x # tVhNef7Xj3OTrCw54qVI1vCwMROpVymWJy71h6aPTnYVVSZwmCZ/oBpHIEPjQ2OA # e3VuJyWQmDo4EbP29p7mO1vsgd4iFNmCKseSv6De4z6ic/rnH1pslPJSlRErWHRA # KKtzQ87fSqEcazjFKfPKqpZzQmiftkaznTqj1QPgv/CiPMpC3BhIfxQ0z9JMq++b # Pf4OuGQq+nUoJEHtQr8FnGZJUlD0UfM2SU2LINIsVzV5K6jzRWC8I41Y99xh3pP+ # OcD5sjClTNfpmEpYPtMDiP6zj9NeS3YSUZPJjAw7W4oiqMEmCPkUEBIDfV8ju2Tj # Y+Cm4T72wnSyPx4JduyrXUZ14mCjWAkBKAAOhFTuzuldyF4wEr1GnrXTdrnSDmuZ # DNIztM2xAgMBAAGjggFdMIIBWTASBgNVHRMBAf8ECDAGAQH/AgEAMB0GA1UdDgQW # BBS6FtltTYUvcyl2mi91jGogj57IbzAfBgNVHSMEGDAWgBTs1+OC0nFdZEzfLmc/ # 57qYrhwPTzAOBgNVHQ8BAf8EBAMCAYYwEwYDVR0lBAwwCgYIKwYBBQUHAwgwdwYI # KwYBBQUHAQEEazBpMCQGCCsGAQUFBzABhhhodHRwOi8vb2NzcC5kaWdpY2VydC5j # b20wQQYIKwYBBQUHMAKGNWh0dHA6Ly9jYWNlcnRzLmRpZ2ljZXJ0LmNvbS9EaWdp # Q2VydFRydXN0ZWRSb290RzQuY3J0MEMGA1UdHwQ8MDowOKA2oDSGMmh0dHA6Ly9j # cmwzLmRpZ2ljZXJ0LmNvbS9EaWdpQ2VydFRydXN0ZWRSb290RzQuY3JsMCAGA1Ud # IAQZMBcwCAYGZ4EMAQQCMAsGCWCGSAGG/WwHATANBgkqhkiG9w0BAQsFAAOCAgEA # fVmOwJO2b5ipRCIBfmbW2CFC4bAYLhBNE88wU86/GPvHUF3iSyn7cIoNqilp/GnB # zx0H6T5gyNgL5Vxb122H+oQgJTQxZ822EpZvxFBMYh0MCIKoFr2pVs8Vc40BIiXO # lWk/R3f7cnQU1/+rT4osequFzUNf7WC2qk+RZp4snuCKrOX9jLxkJodskr2dfNBw # CnzvqLx1T7pa96kQsl3p/yhUifDVinF2ZdrM8HKjI/rAJ4JErpknG6skHibBt94q # 6/aesXmZgaNWhqsKRcnfxI2g55j7+6adcq/Ex8HBanHZxhOACcS2n82HhyS7T6NJ # uXdmkfFynOlLAlKnN36TU6w7HQhJD5TNOXrd/yVjmScsPT9rp/Fmw0HNT7ZAmyEh # QNC3EyTN3B14OuSereU0cZLXJmvkOHOrpgFPvT87eK1MrfvElXvtCl8zOYdBeHo4 # 6Zzh3SP9HSjTx/no8Zhf+yvYfvJGnXUsHicsJttvFXseGYs2uJPU5vIXmVnKcPA3 # v5gA3yAWTyf7YGcWoWa63VXAOimGsJigK+2VQbc61RWYMbRiCQ8KvYHZE/6/pNHz # V9m8BPqC3jLfBInwAM1dwvnQI38AC+R2AibZ8GV2QqYphwlHK+Z/GqSFD/yYlvZV # VCsfgPrA8g4r5db7qS9EFUrnEw4d2zc4GqEr9u3WfPwwggWNMIIEdaADAgECAhAO # mxiO+dAt5+/bUOIIQBhaMA0GCSqGSIb3DQEBDAUAMGUxCzAJBgNVBAYTAlVTMRUw # EwYDVQQKEwxEaWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5jb20x # JDAiBgNVBAMTG0RpZ2lDZXJ0IEFzc3VyZWQgSUQgUm9vdCBDQTAeFw0yMjA4MDEw # MDAwMDBaFw0zMTExMDkyMzU5NTlaMGIxCzAJBgNVBAYTAlVTMRUwEwYDVQQKEwxE # aWdpQ2VydCBJbmMxGTAXBgNVBAsTEHd3dy5kaWdpY2VydC5jb20xITAfBgNVBAMT # GERpZ2lDZXJ0IFRydXN0ZWQgUm9vdCBHNDCCAiIwDQYJKoZIhvcNAQEBBQADggIP # ADCCAgoCggIBAL/mkHNo3rvkXUo8MCIwaTPswqclLskhPfKK2FnC4SmnPVirdprN # rnsbhA3EMB/zG6Q4FutWxpdtHauyefLKEdLkX9YFPFIPUh/GnhWlfr6fqVcWWVVy # r2iTcMKyunWZanMylNEQRBAu34LzB4TmdDttceItDBvuINXJIB1jKS3O7F5OyJP4 # IWGbNOsFxl7sWxq868nPzaw0QF+xembud8hIqGZXV59UWI4MK7dPpzDZVu7Ke13j # rclPXuU15zHL2pNe3I6PgNq2kZhAkHnDeMe2scS1ahg4AxCN2NQ3pC4FfYj1gj4Q # kXCrVYJBMtfbBHMqbpEBfCFM1LyuGwN1XXhm2ToxRJozQL8I11pJpMLmqaBn3aQn # vKFPObURWBf3JFxGj2T3wWmIdph2PVldQnaHiZdpekjw4KISG2aadMreSx7nDmOu # 5tTvkpI6nj3cAORFJYm2mkQZK37AlLTSYW3rM9nF30sEAMx9HJXDj/chsrIRt7t/ # 8tWMcCxBYKqxYxhElRp2Yn72gLD76GSmM9GJB+G9t+ZDpBi4pncB4Q+UDCEdslQp # JYls5Q5SUUd0viastkF13nqsX40/ybzTQRESW+UQUOsxxcpyFiIJ33xMdT9j7CFf # xCBRa2+xq4aLT8LWRV+dIPyhHsXAj6KxfgommfXkaS+YHS312amyHeUbAgMBAAGj # ggE6MIIBNjAPBgNVHRMBAf8EBTADAQH/MB0GA1UdDgQWBBTs1+OC0nFdZEzfLmc/ # 57qYrhwPTzAfBgNVHSMEGDAWgBRF66Kv9JLLgjEtUYunpyGd823IDzAOBgNVHQ8B # Af8EBAMCAYYweQYIKwYBBQUHAQEEbTBrMCQGCCsGAQUFBzABhhhodHRwOi8vb2Nz # cC5kaWdpY2VydC5jb20wQwYIKwYBBQUHMAKGN2h0dHA6Ly9jYWNlcnRzLmRpZ2lj # ZXJ0LmNvbS9EaWdpQ2VydEFzc3VyZWRJRFJvb3RDQS5jcnQwRQYDVR0fBD4wPDA6 # oDigNoY0aHR0cDovL2NybDMuZGlnaWNlcnQuY29tL0RpZ2lDZXJ0QXNzdXJlZElE # Um9vdENBLmNybDARBgNVHSAECjAIMAYGBFUdIAAwDQYJKoZIhvcNAQEMBQADggEB # AHCgv0NcVec4X6CjdBs9thbX979XB72arKGHLOyFXqkauyL4hxppVCLtpIh3bb0a # FPQTSnovLbc47/T/gLn4offyct4kvFIDyE7QKt76LVbP+fT3rDB6mouyXtTP0UNE # m0Mh65ZyoUi0mcudT6cGAxN3J0TU53/oWajwvy8LpunyNDzs9wPHh6jSTEAZNUZq # aVSwuKFWjuyk1T3osdz9HNj0d1pcVIxv76FQPfx2CWiEn2/K2yCNNWAcAgPLILCs # WKAOQGPFmCLBsln1VWvPJ6tsds5vIy30fnFqI2si/xK4VC0nftg62fC2h5b9W9Fc # rBjDTZ9ztwGpn1eqXijiuZQxggN2MIIDcgIBATB3MGMxCzAJBgNVBAYTAlVTMRcw # FQYDVQQKEw5EaWdpQ2VydCwgSW5jLjE7MDkGA1UEAxMyRGlnaUNlcnQgVHJ1c3Rl # ZCBHNCBSU0E0MDk2IFNIQTI1NiBUaW1lU3RhbXBpbmcgQ0ECEAuuZrxaun+Vh8b5 # 6QTjMwQwDQYJYIZIAWUDBAIBBQCggdEwGgYJKoZIhvcNAQkDMQ0GCyqGSIb3DQEJ # EAEEMBwGCSqGSIb3DQEJBTEPFw0yNDExMDYxNzE3MzVaMCsGCyqGSIb3DQEJEAIM # MRwwGjAYMBYEFNvThe5i29I+e+T2cUhQhyTVhltFMC8GCSqGSIb3DQEJBDEiBCAz # U3SyDuA19foVLXhpKXUxPirOcYyDZe5wFK0ajHEJUjA3BgsqhkiG9w0BCRACLzEo # MCYwJDAiBCB2dp+o8mMvH0MLOiMwrtZWdf7Xc9sF1mW5BZOYQ4+a2zANBgkqhkiG # 9w0BAQEFAASCAgAdmWTnxrQ3xGxW80YJbSpjnrnJ232sxHQgVLU7GolVXuLUBi3S # YnyejMowlcswmtfuYZv161d5ET6dKBaRPMKNK7E8L2pCirjAy6AzuITIEssT+fSd # A41ioHD7SJW6po+KCkX+LlrV3BacNSlWVooDgHXqdeSv5Ash6eX93qZZivwRBVd7 # zrj2z6kVV/JHfWuwQXx4Bvem7y2/omgvAWdrz7xAA9OS/6TZCkg0EAQzV7Uxu35k # n1yApmlbWnJOCDPD6roNzWmBr/T/NZYHWTqnooitYaCDTKC5T30o/2YGRRrKx39t # Wje/bkGfox113gyYTawZ8gpgL15/2aVU6cM6/eqp1cpzrX77eUJ+c0psgSDNPw4x # RvItcaNurrN1yHuWSALet35RQDyQEOpAaWxxVQ4kHQPH4EzpjKIBU7STjvQ98X+1 # oGFllrNy4uP/izsn3B7oVP6d/bv8BOueFmBC0oQSawb2pjaEgpqYiosZOhgTKtmj # Ac1RT0sli0sACIFr6qlAZZCvSICzIm1yMtsOj1nJMKz75ynsM4tTfb1AsocamLLp # OjQdxbKV9LMCsnF+x0aRMUM15V5X/SgVfvvZEaxNSSQGLmTSEjNHH1tVou//IV42 # ISazeGl2MyUHthCxk17NgaPzCgbk9xNLT/u/fifxVxefONCV8QLVjojdBg== # SIG # End signature block |