最新消息:雨落星辰是一个专注网站SEO优化、网站SEO诊断、搜索引擎研究、网络营销推广、网站策划运营及站长类的自媒体原创博客

c# - Certificate revocation and CRL with status unknown - Stack Overflow

programmeradmin1浏览0评论

I need help to understand how to configure and how certificate revocations really work in Windows.

I'm testing a scenario where I have a self-signed certificate that will be the one for the root CA, another certificate for Intermediate CA signed by the root CA and then the Server certificate signed by the Intermediate CA.

I built a simple POC application (C#) that will create a TCP Server and a TCP Client, I added all the certificates to the correct stores, root to the trusted, intermediate to the intermediate and then the Server one to the personal.

The certificates look fine, if I select the one in the personal folder, the named Server certificate, I can see that the chain is correctly built up to the root.

The TCP server will use the Server certificate in the AuthenticateAsServer method, then in the client I have a callback method to validate the server certificate and that's where I start to have problems...

I already tested 3 scenarios, all with "different" but similar outcomes:

  1. As is, the method that validates the certificate returns only one status in the chain status property, "Revocation Status Unknown".

  2. If I create a revocation list and added it to the store intermediate\certificate revocation list, the chain status returns 3 status, one saying that the certificate is revoked (so it uses the list installed in the store), another one with the "Revocation Status Unknown" and the third one something related to CRL Offline

  3. If I use a simple endpoint (http://localhost/something.crl) that returns the revocation list (CRL file), and added this information to x509 extensions of the intermediate certificate, it returns 2 status, one with the "Revocation Status Unknown" and other with offline status (the endpoint it's working and I removed the list from the store).

To sum up, I don't know how to configure all of this, so the validate server certificate callback doesn't fail, with (installed or available in one endpoint) and without revocation list.

Thanks

I need help to understand how to configure and how certificate revocations really work in Windows.

I'm testing a scenario where I have a self-signed certificate that will be the one for the root CA, another certificate for Intermediate CA signed by the root CA and then the Server certificate signed by the Intermediate CA.

I built a simple POC application (C#) that will create a TCP Server and a TCP Client, I added all the certificates to the correct stores, root to the trusted, intermediate to the intermediate and then the Server one to the personal.

The certificates look fine, if I select the one in the personal folder, the named Server certificate, I can see that the chain is correctly built up to the root.

The TCP server will use the Server certificate in the AuthenticateAsServer method, then in the client I have a callback method to validate the server certificate and that's where I start to have problems...

I already tested 3 scenarios, all with "different" but similar outcomes:

  1. As is, the method that validates the certificate returns only one status in the chain status property, "Revocation Status Unknown".

  2. If I create a revocation list and added it to the store intermediate\certificate revocation list, the chain status returns 3 status, one saying that the certificate is revoked (so it uses the list installed in the store), another one with the "Revocation Status Unknown" and the third one something related to CRL Offline

  3. If I use a simple endpoint (http://localhost/something.crl) that returns the revocation list (CRL file), and added this information to x509 extensions of the intermediate certificate, it returns 2 status, one with the "Revocation Status Unknown" and other with offline status (the endpoint it's working and I removed the list from the store).

To sum up, I don't know how to configure all of this, so the validate server certificate callback doesn't fail, with (installed or available in one endpoint) and without revocation list.

Thanks

Share Improve this question edited Nov 18, 2024 at 7:50 MckPT asked Nov 16, 2024 at 19:27 MckPTMckPT 352 silver badges8 bronze badges 4
  • For now just the server certificate in the client, only tls, in the future I will do for both sides. – MckPT Commented Nov 16, 2024 at 22:41
  • 1 "it returns 2 status, one with the "Revocation Status Unknown" and other with offline status" can you show the code where you check the status? I can't see how you would get two statuses? – Charlieface Commented Nov 17, 2024 at 17:06
  • learn.microsoft/en-us/dotnet/api/…. the X509Chain object we have the property chain status... That's that one that as the errors/status... The ssl policy also have errors, but right now don't remember what they re. Tomorrow I can put here the code, but it's just the method and checking if the status is empty and if the ssl policy it's equal to none. – MckPT Commented Nov 17, 2024 at 20:23
  • 1 I recommend trying to debug things out with X509Chain directly before using it indirectly with SslStream. Off the top of my head: a) you used https instead of http (CRLs can't be fetched over HTTPS or the cert validation system would need to call itself) or b) you only provided CRLs for the bottom layer, but the X509Chain doing the work is set to do EntireChainExcludeRoot, so you're missing revocation data for the middle layer, or c) you issued both layers to the same file, and it's guaranteed wrong for at least one of them. – bartonjs Commented Nov 18, 2024 at 18:36
Add a comment  | 

1 Answer 1

Reset to default 1

This sounds like a CRL availability issue at some point in the chain. I suggest looking closely at the results of the X509Chain object provided to the RemoteCertificateValidationCallback delegate in either the SslClientAuthenticationOptions() or the SslStream ctor.

The following code will help track down which certificate is causing the issue:

    static bool ValidateRemoteCertificateAsClient(object sender,
        X509Certificate? serverCertificate,
        X509Chain? serverCertificateChain,
        SslPolicyErrors sslPolicyErrors)
    {

        if(sslPolicyErrors == SslPolicyErrors.None)
        {
            Console.WriteLine("No errors found during validation");
            return true;
        }

        if ((sslPolicyErrors & SslPolicyErrors.RemoteCertificateNotAvailable) != 0)
            Console.WriteLine("Validation Error: Remote certificate not available");

        if((sslPolicyErrors & SslPolicyErrors.RemoteCertificateNameMismatch) != 0)
            Console.WriteLine("Validation Error: Remote certificate name mis-match");

        if((sslPolicyErrors & SslPolicyErrors.RemoteCertificateChainErrors) != 0)
        {
            ArgumentNullException.ThrowIfNull(serverCertificateChain, nameof(serverCertificateChain));
            ArgumentOutOfRangeException.ThrowIfZero(serverCertificateChain.ChainElements.Count,nameof(serverCertificateChain.ChainElements));

            Console.WriteLine("Validation Error: One or more chain errors found.");

            foreach (var chainElement in serverCertificateChain.ChainElements) 
            {
                Console.WriteLine("Chain certificate: " + chainElement.Certificate.Subject);

                if (chainElement.ChainElementStatus.Length == 0)
                    Console.WriteLine($"    No validation errors found.");
                else
                {
                    foreach (var chainStatus in chainElement.ChainElementStatus)
                    {
                        Console.WriteLine("     Error: " + chainStatus.StatusInformation);
                        foreach (X509ChainStatusFlags flag in Enum.GetValues(typeof(X509ChainStatusFlags)))
                        {
                            if (flag != X509ChainStatusFlags.NoError && (chainStatus.Status & flag) != 0)
                            {
                                Console.WriteLine($"        Flag: {flag} ({((int)flag)})");
                            }
                        }
                    }
                }
            }
        }

        return false;
    }
发布评论

评论列表(0)

  1. 暂无评论