From 64ce98d1c69462000a571c1fb35592ded9074511 Mon Sep 17 00:00:00 2001 From: Cosmin Neculcea Date: Tue, 22 Sep 2026 09:41:35 +0300 Subject: [PATCH] fix(tlsutil): avoid nil pointer dereference in ClientConfig When opts.CertFile and opts.KeyFile are empty, cert remains nil. Previously, ClientConfig unconditionally dereferenced cert when constructing tls.Config, causing a runtime panic when only CaCertFile or InsecureSkipVerify was configured. This conditions the assignment of cfg.Certificates on cert != nil and adds a unit test covering the scenario. Fixes #32674 Signed-off-by: Cosmin Neculcea --- internal/tlsutil/cfg.go | 8 +++++++- internal/tlsutil/tlsutil_test.go | 19 +++++++++++++++++++ 2 files changed, 26 insertions(+), 1 deletion(-) diff --git a/internal/tlsutil/cfg.go b/internal/tlsutil/cfg.go index 8b9d4329f..04aa907d3 100644 --- a/internal/tlsutil/cfg.go +++ b/internal/tlsutil/cfg.go @@ -53,6 +53,12 @@ func ClientConfig(opts Options) (cfg *tls.Config, err error) { } } - cfg = &tls.Config{InsecureSkipVerify: opts.InsecureSkipVerify, Certificates: []tls.Certificate{*cert}, RootCAs: pool} + cfg = &tls.Config{ + InsecureSkipVerify: opts.InsecureSkipVerify, + RootCAs: pool, + } + if cert != nil { + cfg.Certificates = []tls.Certificate{*cert} + } return cfg, nil } diff --git a/internal/tlsutil/tlsutil_test.go b/internal/tlsutil/tlsutil_test.go index e31a873d3..7236a6b4e 100644 --- a/internal/tlsutil/tlsutil_test.go +++ b/internal/tlsutil/tlsutil_test.go @@ -112,3 +112,22 @@ func TestNewClientTLS(t *testing.T) { t.Fatalf("mismatch tls RootCAs, expecting nil") } } + +func TestClientConfigWithoutClientCert(t *testing.T) { + opts := Options{ + InsecureSkipVerify: true, + } + + cfg, err := ClientConfig(opts) + if err != nil { + t.Fatalf("unexpected error: %v", err) + } + + if cfg == nil { + t.Fatal("expected non-nil tls.Config") + } + + if len(cfg.Certificates) != 0 { + t.Fatalf("expected empty Certificates slice, got %d", len(cfg.Certificates)) + } +}