HIGH information disclosureaxummutual tls

Information Disclosure in Axum with Mutual Tls

Information Disclosure in Axum with Mutual Tls

Information disclosure in Axum when using Mutual TLS (mTLS) typically arises from misconfiguration or incomplete verification practices rather than a flaw in Axum itself. When mTLS is enabled, both the client and the server present certificates during the TLS handshake. If the server does not properly validate the client certificate, it may inadvertently accept unauthenticated or spoofed connections, leading to exposure of sensitive data intended for authorized clients only.

In Axum, routing and handler logic are designed to be explicit about authorization, but developers might rely solely on the presence of a client certificate without validating its contents. For example, a handler might assume that because a certificate was presented, the associated identity meets authorization requirements. This assumption can lead to Information Disclosure when sensitive route parameters or query data are returned to a client whose certificate attributes (such as distinguished name or SAN) should restrict access.

Another specific scenario involves logging or error responses that include data derived from request inputs or paths. If an Axum application logs the full request path, including user identifiers, and these logs are accessible to unauthorized parties, the combination of mTLS and verbose logging can amplify the impact of information disclosure. Additionally, if the server does not enforce strict hostname verification and an attacker terminates TLS with a valid but unrelated certificate, the application might process requests and return data that should remain confidential to the intended peer.

Consider an endpoint that returns user-specific profile information based on a path parameter such as /users/{user_id}. If mTLS is enabled but the server does not correlate the client certificate with the requested user_id, a client with a valid certificate could iterate over numeric IDs and retrieve profiles belonging to other users. This is a form of broken access control that manifests through insufficient binding between certificate identity and application-level permissions, resulting in information disclosure.

Furthermore, when integrating mTLS with middleware that inspects connection details, improper handling of certificate extensions or subject alternative names can lead to data exposure. For instance, extracting common name (CN) values without validating the certificate chain may allow a request from a trusted CA but an unintended peer to access sensitive endpoints. Axum applications must ensure that certificate validation includes checking revocation status, proper chain verification, and attribute constraints before granting access to data-heavy routes.

Mutual Tls-Specific Remediation in Axum

Remediation focuses on strict certificate validation and binding identity to authorization checks within Axum handlers and middleware. Developers should configure the TLS acceptor to require and verify client certificates, ensuring that the certificate chain is validated against a trusted CA and that revocation is checked where possible. In practice, this means setting up Rustls with appropriate root store configuration and enforcing client authentication before routing reaches application logic.

In Axum, you can enforce mTLS at the router level by wrapping your routes with a middleware that inspects the peer certificate and aborts the request if validation fails. Below is a concrete example of how to set up a Rustls acceptor with client authentication required, and how to integrate it with an Axum server so that only requests presenting valid certificates are processed.

use axum::Router;
use rustls::{Certificate, PrivateKey, ServerConfig};
use rustls_pemfile::{certs, pkcs8_private_keys};
use std::fs::File;
use std::io::{BufReader, BufWriter};
use std::net::TcpListener;
use std::sync::Arc;

async fn build_server() -> Arc<ServerConfig> {
    let mut cert_reader = BufReader::new(File::open("ca.crt").expect("cannot open CA cert"));
    let mut key_reader = BufReader::new(File::open("server.key").expect("cannot open server key"));
    let ca_certs = certs(&mut cert_reader)
        .unwrap()
        .into_iter()
        .map(Certificate)
        .collect();
    let mut keys = pkcs8_private_keys(&mut key_reader).unwrap();
    let server_key = PrivateKey(keys.remove(0));

    let mut config = ServerConfig::builder()
        .with_safe_defaults()
        .with_client_auth_cert(ca_certs, server_key)
        .expect("invalid client auth setup");
    config.alpn_protocols = vec![b"h2", b"http/1.1"];
    Arc::new(config)
}

#[tokio::main]
async fn main() {
    let tls_config = build_server().await;
    let listener = TcpListener::bind("0.0.0.0:8443").unwrap();
    let acceptor = tokio_rustls::TlsAcceptor::from(tls_config);

    let app = Router::new()
        .route("/health", axum::routing::get(|| async { "ok" }));

    axum::serve(listener, app.into_make_service_with_connect_info::(), acceptor)
        .await
        .unwrap();
}

This example configures the server to require client certificates signed by the CA in ca.crt and uses the server’s private key for its own certificate. Note that this setup does not by itself enforce identity-based access; it only ensures that connecting clients possess a valid certificate chain. To prevent information disclosure, you must add logic that maps certificate fields (such as SAN or extended key usage) to authorization rules within your handlers or middleware.

Additionally, when constructing error responses, avoid including stack traces or internal paths that might reveal system details. Use standardized error types that do not expose sensitive context. For example, returning a generic 403 status when certificate identity does not match required permissions prevents leakage of whether a resource exists or why access was denied.

Finally, verify hostname and certificate extension constraints explicitly if your threat model requires it. While Rustls provides options for server name indication (SNI) verification, you should implement additional checks in application logic to ensure that the presented certificate matches the expected identity for the requested operation, thereby closing the gap that could lead to information disclosure in Axum services using mTLS.

Frequently Asked Questions

How can I ensure my Axum mTLS setup does not leak user-specific data?
Bind certificate identity to authorization checks in handlers or middleware, validate the full certificate chain including revocation, and avoid logging or exposing path parameters that reference user identifiers without verifying the certificate maps to that user.
Is simply enabling mTLS in Axum enough to prevent information disclosure?
No. Enabling mTLS ensures a client presents a certificate, but you must still validate the certificate, map its attributes to permissions, and enforce authorization before accessing or returning sensitive data.