I am trying to implement client certificate authentication on IIS 8. I have deployed my configuration on a development machine and verified it working as expected there. However after setting up on the server, whenever I navigate to the site and am prompted for the client cert, I select it and immediately get the 403.16 error. The failed requests log gives the error code 2148204809 and message "A certificate chain processed, but terminated in a root certificate which is not trusted by the trust provider."
I have a valid client cert and also a valid CA cert. The CA cert is installed in Trusted Root Authorities on the computer account on both the server and the client machine, and the client cert is installed in the Personal area of the Current User account on the client machine.
The client cert is signed directly by the root CA and as I said, both are valid. There are no other certs in the chain and there are no intermediate certs in the Trusted Root Authorities area.
The IIS configuration has sslFlags = SslNegotiateCert and iisClientCertificateMappingAuthentication is enabled.
The server is not configured to send a CTL and we have SendTrustedIssuerList = 0.
I cannot see why the client cert should not be trusted.
Windows 2012 introduced stricter certificate store validations. According to KB 2795828: Lync Server 2013 Front-End service cannot start in Windows Server 2012, the Trusted Root Certification Authorities (i.e. Root) store can only have certificates that are self-signed. If that store contains non-self-signed certificates, client certificate authentication under IIS returns with a 403.16 error code.
To solve the problem, you have to remove all non-self-signed certificates from the root store. This PowerShell command will identify non-self-signed certificates:
Get-Childitem cert:\LocalMachine\root -Recurse |
Where-Object {$_.Issuer -ne $_.Subject}
In my situation, we moved these non-self-signed certificates into the Intermediate Certification Authorities (i.e. CA) store:
Get-Childitem cert:\LocalMachine\root -Recurse |
Where-Object {$_.Issuer -ne $_.Subject} |
Move-Item -Destination Cert:\LocalMachine\CA
According to KB 2801679: SSL/TLS communication problems after you install KB 931125, you might also have too many trusted certificates.
[T]he maximum size of the trusted certificate authorities list that the Schannel security package supports is 16 kilobytes (KB). Having a large amount of Third-party Root Certication Authorities will go over the 16k limit, and you will experience TLS/SSL communication problems.
The solution in this situation is to remove any certification authority certificates you don't trust, or to stop sending the list of trusted certifiation authorities by setting the HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\SecurityProviders\SCHANNEL\#SendTrustedIssuerList registry entry to 0 (the default, if not present, is 1).
If the issue continues to persist after the above steps, restart the machine.
In my case I'd been adding the root cert into the 'current user' certificate store on the server and was getting the 403.16 error.
Adding my root cert to the Trusted Root Authorities store for the local machine resolved the issue.
Follow the steps below on the server running IIS.
For Windows Server 2008 R2:
Right click on the certificate file and select 'Install Certificate'. Click next.
Select 'Place all certificates in the following store' and click 'Browse...'
Check 'Show physical stores'
Expand 'Trusted Root Certification Authorities' and select 'Local Computer'. Click OK.
Click Next/Click Finish.
For Windows Server 2012 R2:
Right click on the certificate file and select 'Install
Certificate'.
Select 'Local Machine'. Click Next.
Select 'Place all certificates in the following store' and click 'Browse...'
Select 'Trusted Root Certification Authorities'. Click OK.
Click Next/Click Finish.
For Windows 7:
Start -> Run -> mmc.exe
File -> 'Add or Remove Snap-ins'. Select 'Certificates', click 'Add >' and select 'Computer account' and then 'Local computer'. Click Finish/OK
Expand Certificates (Local Computer) -> Trusted Root Certification Authorities -> Certificates. Right click on Certificates and select All Tasks -> Import.
Select the certificate file and click next.
Select 'Place all certificates in the following store' and click 'Browse...'
Check 'Show physical stores'
Expand 'Trusted Root Certification Authorities' and select 'Local Computer'. Click OK.
Click Next/Click Finish.
I got this error in IIS Express:
HTTP Error 403.16 - Forbidden
Your client certificate is either not trusted or is invalid.
Looking at the TraceLogFiles I saw the following error:
<RenderingInfo Culture="en-US">
<Opcode>MODULE_SET_RESPONSE_ERROR_STATUS</Opcode>
<Keywords>
<Keyword>RequestNotifications</Keyword>
</Keywords>
<freb:Description Data="Notification">BEGIN_REQUEST</freb:Description>
<freb:Description Data="ErrorCode">A certificate chain processed, but terminated in a root certificate which is not trusted by the trust provider.
(0x800b0109)</freb:Description>
</RenderingInfo>
Turned out when I installed Razer Synapse the installation also put a certificate for chromasdk.io in Trusted Root Certification Authorities under Computer Account -> Local computer. I removed this and then everything worked.
Just sharing my experience with Windows 2019 server and IISExpress in combination with a self-signed certificate. I couldn't get it working with editing the registry and in the end I didn't need to.
The following three steps got me there:
Generate a root certificate for the localmachine cert store with powershell:
$cert = New-SelfSignedCertificate -Type Custom -KeySpec Signature -Subject "CN=TestRootCert" -KeyExportPolicy Exportable -HashAlgorithm sha256 -KeyLength 2048 -CertStoreLocation "Cert:\LocalMachine\My" -KeyUsageProperty Sign -KeyUsage CertSign
Generate a client certificate for the localuser cert store, based on the root cert with powershell:
New-SelfSignedCertificate -Type Custom -Subject "CN=TestChildCert" -Signer $cert -TextExtension #("2.5.29.37={text}1.3.6.1.5.5.7.3.2","2.5.29.17={text}upn=test#local") -KeyUsage DigitalSignature -KeyAlgorithm RSA -KeyLength 2048 -CertStoreLocation "Cert:\CurrentUser\My"
Move the root cert from Personal\Certificates to Trusted Root Certification\Certificates
After this I could select the TestChildCert and it was accepted just fine.
Related
I use the below script to import a certificate in a pipeline build process,
Powershell script:
param($PfxFilePath, $Password)
$absolutePfxFilePath = Resolve-Path -Path $PfxFilePath
Write-Output "Importing store certificate '$absolutePfxFilePath'..."
Add-Type -AssemblyName System.Security
$cert = New-Object System.Security.Cryptography.X509Certificates.X509Certificate2
$cert.Import($absolutePfxFilePath, $Password, [System.Security.Cryptography.X509Certificates.X509KeyStorageFlags]"PersistKeySet")
$store = new-object system.security.cryptography.X509Certificates.X509Store -argumentlist "MY", CurrentUser
$store.Open([System.Security.Cryptography.X509Certificates.OpenFlags]::"ReadWrite")
$store.Add($cert)
$store.Close()
Get below error:
. 'C:\JobAppAgent_work\1\s\JobApp\DevOps\Build\Import-PfxCertificate.ps1' -PfxFilePath $env:DOWNLOADSECUREFILE1_SECUREFILEPATH -Password ****
Importing store certificate 'C:\JobAppAgent_work_temp\DD.Job.Desktop_TemporaryKey.pfx'...
##[error]Exception calling "Import" with "3" argument(s): "The specified network password is not correct.
This script was running fine when build was running on Azrure PipeLines. Now I create a private Agent pool that runs on a Window 10 VM.
Make sure that the certificate is valid and has not expired. You can check the expiration date of the certificate by double-clicking on it and viewing the details.
Check that the certificate is properly installed on the machine where the build is being performed. If the certificate is not installed, it will not be available for use in the build process.
Make sure that the certificate is correctly referenced in the build pipeline. This may involve specifying the path to the certificate file or the thumbprint of the certificate.
If you are using a self-signed certificate, make sure that it is trusted by the machine where the build is being performed. To do this, you will need to install the certificate in the trusted root certification authorities store on the machine.
If you are using a certificate from a certificate authority (CA), make sure that the CA is trusted by the machine where the build is being performed. This may involve installing the root certificate of the CA on the machine.
This is a PowerShell script that imports a certificate from a file with a given password into the "MY" store in the current user's certificate store. The certificate is imported using the Import method of the X509Certificate2 class, which takes as input the path to the certificate file, the password, and a set of key storage flags. The script then creates an X509Store object representing the "MY" store in the current user's certificate store, opens the store in read-write mode, adds the imported certificate to the store, and closes the store.
This script assumes that the certificate file is in the Personal Information Exchange (PFX) format, which is a common format for storing certificates and their private keys. PFX files are often used to export or import certificates, and they can be password-protected for added security.
Verify that the password you are using to import the certificate is correct. It's possible that the password has been changed or entered incorrectly.
Check that the certificate file has not been damaged or modified in any way. If the file has been altered, it may be causing the import to fail.
Make sure that the certificate file is accessible to the machine where the script is being run. If the file is on a network share or another machine, check that the machine has the necessary permissions to read the file.
If the certificate file is password-protected, make sure that the password has not expired or been revoked.
Try running the script with different key storage flags to see if that has any effect on the error. For example, you could try using "Exportable" instead of "PersistKeySet" as the key storage flag.
I set http.sslbackend=schannel and imported my self-signed certificate into windows 10 (Personal | Certificates) pane in MMC. Now, I'm trying to clone a repository hosted on a server configured with the self-signed certificate.
As far as I understood as long as having the certificate in windows (explained above) git should not complain about the certificate. This is not the case. whenever I try to clone I'm getting:
unable to access https://server.com/project.git : schannel: SEC_E_UNTRUSTED_ROOT (0X80090325) - THE CERTIFICATE CHAIN WAS ISSUED BY AN AUTHORITY THAT IS NOT TRUSTED.
What am I missing here?
I have installed SSL successful in my azure server but it's not binding with domain. I am getting following error message.
It is not clear on what certificate you are using. To use a certificate in App Service, the certificate must meet all the following requirements:
Signed by a trusted certificate authority
Exported as a password-protected PFX file
Contains private key at least 2048 bits long
Contains all intermediate certificates in the certificate chain
As highlighted by Snobu you may regenerate the certificate (for Self-Signed) with: extendedKeyUsage = critical,codeSigning,1.3.6.1.5.5.7.3.1 in the x509_extensions in the file. Refer this document for the step-step instructions on uploading a certificate.
I have an externally hosted iis webserver where i run my website. I would like to add a self signed certificate to this website and trust it on my local client, to remove "Insecure Connection" from the browser.
What i have done so far is the following
Created a self signed certificate in IIS: Server Certificates -> Create self signed Certificate. The cert is issued to the servername e.g "ABCD01"
Created a website with a https binding using the self signed certificate.
Exported the self signed certificate from IIS using: Server Certificates -> Export. This resulted in an .pfx file
Imported the .pfx cert file on the local client: manage computer certificates -> Trusted Root certification authorities -> import
Added the hostname (ABCD01) and ip of the host to the hosts file: C:\Windows\System32\drivers\etc\hosts
When i try to open the website in firefox (using https://ABCD01), i still get the "Your connection is not secure". What am i missing?
There are multiple issues:
IIS certificate generator creates self-signed certificates with SHA1 signature algorithm which is obsolete in modern browsers. You have to use different tools to create test certificates. For example, use PowerShell New-SelfSignedCertificate cmdlet where you can specify signature algorithm. Look at this post to get an example: https://stackoverflow.com/a/45284368/3997611
New-SelfSignedCertificate `
-DnsName "ABCD01" `
-CertStoreLocation "cert:\LocalMachine\My" `
-FriendlyName "test dev cert" `
-TextExtension "2.5.29.37={text}1.3.6.1.5.5.7.3.1" `
-KeyUsage DigitalSignature,KeyEncipherment,DataEncipherment `
-Provider "Microsoft RSA SChannel Cryptographic Provider" `
-HashAlgorithm "SHA256"
IIS certificate generator cannot build certificate with SAN (Subject Alternative Names) certificate extension which is required in Google Chrome. You have to use different tools to create test certificates. Look at the example above for reference.
Google Chrome uses built-in Windows Certificate store to establish a trust, while FireFox uses its own certificate store. Therefore, after adding the certificate to Windows certificate store, you have to import your test certificate to FireFox manually.
I need to authenticate requests to Azure Cloud Service Web Role using client certificates. How to put the Certification Authority (CA) root certificate in a right trusted store?
I tried to upload it in Management Portal and then defining it in service definition file with AuthRoot store name:
<Certificate name="RootCA" storeLocation="LocalMachine" storeName="AuthRoot" />
What's really strange is that it works... but only sometimes. It may work after an instance reboot, but may not work after a service update or another instance reboot. It seems like a bug in Azure.
When I say "works" I mean server successfully accepts the client certificate and processes the request.
When I say "doesn't work" I mean server doesn't negotiate a connection after certificate checks and "The request was aborted: Could not create SSL/TLS secure channel." exception is thrown on a client side.
How to make it working stable?
UPD:
Found this record in System Windows Event Log (source is Schannel):
When asking for client authentication, this server sends a list of
trusted certificate authorities to the client. The client uses this
list to choose a client certificate that is trusted by the server.
Currently, this server trusts so many certificate authorities that the
list has grown too long. This list has thus been truncated. The
administrator of this machine should review the certificate
authorities trusted for client authentication and remove those that do
not really need to be trusted.
The exact problem is described here: http://support.microsoft.com/kb/2801679.
After December 2012 Windows update a lot of certificates were added to AuthRoot store. So we have to remove them to solve the problem.
To make it I use PowerShell startup task:
Get-ChildItem -Path Registry::HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\SystemCertificates\AuthRoot\Certificates | Where-Object {$_.Name -notlike "*\<YOUR_CERTIFICATE_THUMBPRINT>"} | Remove-Item
To run it from CMD startup task:
PowerShell -ExecutionPolicy Unrestricted .\Startup.ps1
exit /b %errorlevel%
And in ServiceDefinition.csdef:
<WebRole name="Web">
<Startup>
<Task commandLine="Startup.cmd" executionContext="elevated" taskType="simple" />
</Startup>
<!-- ... ->
</WebRole>