From b2a98acb49e000d0ab5f48e88800510464cdce69 Mon Sep 17 00:00:00 2001 From: Michael Ruoss Date: Tue, 19 Dec 2023 09:28:55 +0100 Subject: [PATCH 1/2] add `match_fun` clause to deal with ip addresses in TLS handshake --- lib/mint/core/transport/ssl.ex | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/lib/mint/core/transport/ssl.ex b/lib/mint/core/transport/ssl.ex index 8163d1cd..1a31bd91 100644 --- a/lib/mint/core/transport/ssl.ex +++ b/lib/mint/core/transport/ssl.ex @@ -509,6 +509,16 @@ defmodule Mint.Core.Transport.SSL do end end + # In case the hostname is an IP address: + defp match_fun({:dns_id, hostname}, {:iPAddress, ip}) do + with {:ok, ip_tuple} <- :inet.parse_address(hostname), + ^ip <- Tuple.to_list(ip_tuple) do + true + else + _ -> :default + end + end + defp match_fun(_reference, _presented), do: :default defp domain_without_host([]), do: [] From 5dd73bfeec9a709850df463999b8c7753aa0e3f5 Mon Sep 17 00:00:00 2001 From: Michael Ruoss Date: Fri, 12 Jan 2024 13:45:39 +0100 Subject: [PATCH 2/2] add test and comment --- lib/mint/core/transport/ssl.ex | 6 +++++- test/mint/core/transport/ssl_test.exs | 4 ++++ 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/lib/mint/core/transport/ssl.ex b/lib/mint/core/transport/ssl.ex index 1a31bd91..2e1a8c9b 100644 --- a/lib/mint/core/transport/ssl.ex +++ b/lib/mint/core/transport/ssl.ex @@ -509,7 +509,11 @@ defmodule Mint.Core.Transport.SSL do end end - # In case the hostname is an IP address: + # Workaround for a bug that was fixed in OTP 27: + # Before OTP 27 when connecting to an IP address and the server offers a + # certificate with its IP address in the "subject alternate names" extension, + # the TLS handshake fails with a `{:bad_cert, :hostname_check_failed}`. + # This clause can be removed once we depend on OTP 27+. defp match_fun({:dns_id, hostname}, {:iPAddress, ip}) do with {:ok, ip_tuple} <- :inet.parse_address(hostname), ^ip <- Tuple.to_list(ip_tuple) do diff --git a/test/mint/core/transport/ssl_test.exs b/test/mint/core/transport/ssl_test.exs index 27c70f05..3604655d 100644 --- a/test/mint/core/transport/ssl_test.exs +++ b/test/mint/core/transport/ssl_test.exs @@ -148,6 +148,10 @@ defmodule Mint.Core.Transport.SSLTest do refute :mint_shims.pkix_verify_hostname(cert, ip: {1, 2, 3, 4}) refute :mint_shims.pkix_verify_hostname(cert, ip: {10, 11, 12, 13}) end + + test "custom match fun for IP addresses as hostname", %{cert: cert} do + assert {:valid, _} = SSL.verify_fun(cert, :valid_peer, dns_id: ~c"10.67.16.75") + end end # Certificate chain rooted in an expired root CA, and CA store containing