Security Misconfiguration in Aspnet with Mutual Tls
Security Misconfiguration in Aspnet with Mutual Tls — how this specific combination creates or exposes the vulnerability
Security misconfiguration around Mutual TLS (mTLS) in ASP.NET applications often arises when transport security is enabled without properly enforcing client certificate validation. This combination can expose the application to authentication bypass or impersonation, even when HTTPS is in place. A typical misconfiguration is enabling RequireHttps and specifying a certificate for the server, but omitting or incorrectly configuring the client certificate validation callback.
In ASP.NET Core, the server can request and optionally require client certificates, but if the application does not explicitly validate the client certificate, the runtime may accept an unverified or missing certificate. For example, using the default development certificate without enforcing chain validation or revocation checks can allow an attacker presenting any certificate (or none in some configurations) to authenticate as an arbitrary client. This misconfiguration is especially risky when combined with overly permissive authorization policies that grant access based solely on the presence of a claim, rather than validating the certificate’s subject, issuer, or thumbprint.
Another common issue is binding the server certificate without specifying the client certificate mode as CertificateRequired, leading to scenarios where mTLS is effectively optional. If the application also does not enforce HTTPS in all environments (e.g., allowing HTTP in staging), the client certificate exchange may be completely skipped, undermining the purpose of mTLS. These misconfigurations violate secure transport best practices and can map to findings in Authentication and Encryption checks within security scans.
Real-world attack patterns include connecting to the endpoint without a client certificate when the server is misconfigured to accept an empty or default certificate. In some cases, weak certificate validation logic (e.g., accepting any certificate with a particular subject name but not validating the full chain) can allow an attacker with a self-signed certificate to impersonate a trusted client. These issues are detectable by scanning tools that inspect both the runtime behavior and the OpenAPI/Swagger specification, especially when the spec describes securitySchemes of type openIdConnect or oauth2 without accurately reflecting the mTLS requirement.
Mutual Tls-Specific Remediation in Aspnet — concrete code fixes
To remediate mTLS misconfiguration in ASP.NET, explicitly configure the server to require and validate client certificates. Below are concrete, syntactically correct examples for both ASP.NET Core 6+ and minimal hosting models.
Example 1: ASP.NET Core with Program.cs (minimal hosting model)
using System.Security.Cryptography.X509Certificates;
var builder = WebApplication.CreateBuilder(args);
// Require HTTPS and configure Kestrel to use server certificate
builder.WebHost.ConfigureKestrel(serverOptions =>
{
serverOptions.ListenAnyIP(5001, listenOptions =>
{
listenOptions.UseHttps("path/to/server.pfx", "serverPassword");
});
});
// Enforce client certificate validation
builder.Services.AddAuthentication("Certificate")
.AddCertificate(options =>
{
options.AllowedCertificateTypes = CertificateTypes.All;
options.RevocationMode = X509RevocationMode.Online;
options.RemoteCertificateValidator = (sender, cert, chain, errors) =>
{
if (cert is null) return false;
// Example: validate thumbprint or issuer
var allowedThumbprint = "A1B2C3D4E5F6...";
if (cert.Thumbprint != allowedThumbprint) return false;
// Optionally validate chain
chain.ChainPolicy.RevocationMode = X509RevocationMode.Online;
chain.ChainPolicy.VerificationFlags = X509VerificationFlags.NoFlag;
return chain.Build((X509Certificate2)cert);
};
});
var app = builder.Build();
app.UseAuthentication();
app.UseAuthorization();
app.MapGet("/", () => "Hello mTLS secured world");
app.Run();
Example 2: Traditional Startup-style ASP.NET Core
using System.Security.Cryptography.X509Certificates;
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddAuthentication(CertificateAuthenticationDefaults.AuthenticationScheme)
.AddCertificate(options =>
{
options.AllowedCertificateTypes = CertificateTypes.All;
options.RevocationMode = X509RevocationMode.Online;
options.RemoteCertificateValidator = ValidateClientCertificate;
});
services.AddAuthorization();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
app.UseHttpsRedirection();
app.UseAuthentication();
app.UseAuthorization();
app.UseEndpoints(endpoints =>
{
endpoints.MapGet("/", async context =>
{
await context.Response.WriteAsync("Hello mTLS secured world");
});
});
}
private bool ValidateClientCertificate(
object sender,
X509Certificate? certificate,
X509Chain? chain,
System.Net.Security.SslPolicyErrors sslPolicyErrors)
{
if (certificate is null) return false;
var cert = new X509Certificate2(certificate);
var allowedThumbprint = "A1B2C3D4E5F6...";
if (cert.Thumbprint != allowedThumbprint) return false;
if (chain is not null)
{
chain.ChainPolicy.RevocationMode = X509RevocationMode.Online;
chain.ChainPolicy.VerificationFlags = X509VerificationFlags.NoFlag;
return chain.Build(cert);
}
return false;
}
}
Key remediation steps include:
- Always set a non-None revocation mode (Online or Offline) when validating client certificates.
- Validate the certificate chain and enforce issuer/thumbprint checks rather than relying on default trust.
- Ensure the server is configured to request and require client certificates (CertificateRequired) and not merely request them.
- Avoid allowing HTTP in any environment where mTLS is intended; enforce HTTPS redirects consistently.
These practices align with secure transport and identity validation controls and reduce the likelihood of authentication bypass. Findings from scans that include Authentication, Encryption, and SSL/TLS checks will reflect improvements when these configurations are applied.