Kestrel Cannot Generate Certificate Chain Correctly
- Dominant language
- C#
- Stars
- 38.4k
- Forks
- 10.9k
- Avg merge
- 2d 6h
- Merged PRs (30d)
- 290
Description
### Is there an existing issue for this?
- [x] I have searched the existing issues
### Describe the bug
### Problem Description
I have a PEM format certificate with the following structure:
```
-mydomain_bundle.crt
|___ mydomain.crt
|___ intermediate.crt
|___ cross.crt(Sectigo Public Server Authentication Root R46)
|___ root.crt(USERTrust RSA Certification Authority)
```
When this certificate is used on an nginx server and verified using the `openssl s_client -connect` command on a Linux client, the Certificate chain is as follows:
```
-mydomain_bundle.crt
|___ mydomain.crt
|___ intermediate.crt
|___ cross.crt(Sectigo Public Server Authentication Root R46)
```
When these certificates are placed on Kestrel, the Certificate chain seen by the client is as follows:
```
-mydomain_bundle.crt
|___ mydomain.crt
|___ intermediate.crt
```
In other words, when Kestrel builds the certificate chain, it considers cross.crt to be the root certificate. If the client environment lacks the Sectigo Public Server Authentication Root R46 root certificate, it manifests as 'Verify return code: 20 (unable to get local issuer certificate)', failing to achieve the same certificate compatibility as nginx.
### Problem Analysis
It is suspected that [HttpsConnectionMiddleware L112](https://github.com/dotnet/aspnetcore/blob/main/src/Servers/Kestrel/Core/src/Middleware/HttpsConnectionMiddleware.cs#L112) unconditionally constructs the certificate chain from the system when creating SslStreamCertificateContext, without using options.ServerCertificateChain.
### Expected Behavior
_No response_
### Steps To Reproduce
_No response_
### Exceptions (if any)
_No response_
### .NET Version
_No response_
### Anything else?
_No response_
Contributor guide
Assessment
This issue has not been assessed yet.