This issue tracker has been migrated to GitHub, and is currently read-only.
For more information, see the GitHub FAQs in the Python's Developer Guide.

Title: SSL match_hostname does not accept IP Address
Type: enhancement Stage: resolved
Components: Extension Modules, SSL Versions: Python 2.7
Status: closed Resolution: out of date
Dependencies: Superseder:
Assigned To: Nosy List: Alex Gaynor, Marc.Abramowitz, alex, christian.heimes, dstufft, j-harbott, pitrou, python-dev, r.david.murray, Ádám.Zsigmond
Priority: high Keywords: patch

Created on 2015-01-14 09:04 by Ádám.Zsigmond, last changed 2022-04-11 14:58 by admin. This issue is now closed.

File name Uploaded Description Edit
ip_certs.patch pitrou, 2015-01-17 18:54 review
ip_certs_comment.patch Marc.Abramowitz, 2016-03-17 16:38 review
Messages (14)
msg234017 - (view) Author: Ádám Zsigmond (Ádám.Zsigmond) Date: 2015-01-14 09:04
ssl.match_hostname does not accept the ca certificate if the hostname matches the ip address. 

I am trying to connect to a servert with a cacert by IP address but I get an error message like: '' hostname does not match '<hostname_in_cacert>'

The IP Address is in the ca certificate, so it should be accepted.
msg234038 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2015-01-14 17:24
This is a feature request. Not supporting IP addresses is a documented limitation of the current implementation.
msg234190 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2015-01-17 18:54
Here is a patch.
msg236051 - (view) Author: Roundup Robot (python-dev) (Python triager) Date: 2015-02-15 17:13
New changeset b15a5f239e8a by Antoine Pitrou in branch 'default':
Issue #23239: ssl.match_hostname() now supports matching of IP addresses.
msg244665 - (view) Author: Christian Heimes (christian.heimes) * (Python committer) Date: 2015-06-02 11:49
The patch has a couple of issues

1) match_hostname()'s doc string needs to be updated. It still contains "but IP addresses are not accepted for *hostname*"

2) The stdlib uses server_hostname for SNI and matching. An IP address in the SNI TLS extension violates RF 3546

   Literal IPv4 and IPv6 addresses are not permitted in "HostName".

3) The code doesn't match IP addresses in dNSName and DNS names in IP Address fields. Hynek's service identity module and Mozilla's NSS [1] agree with you. As far as I have studied OpenSSL 1.0.2, it has a different opinion. I'm in favor for the current check. I suggest to document the decision in the code and raise a more explicit exception. The current message is a bit confusing:

  ssl.CertificateError: hostname '' doesn't match ''

4) The code doesn't check the CN field for IP address as NSS does. [2]

In order to fix 2) and make the check more explicit I like to suggest an API change. Don't convert the host name to an IP address implicitly. If the user wants to validate an IP address, then she must pass in an ipaddress object as server_hostname. In that case SSLSocket.server_hostname is set to the ipaddress object. socket._wrap_socket() is called with server_hostname=None for ipaddress. That fixes the RFC violation.

[1] cert_VerifySubjectAltName()
[2] CERT_VerifyCertName
msg246327 - (view) Author: Christian Heimes (christian.heimes) * (Python committer) Date: 2015-07-05 17:48
msg246671 - (view) Author: Antoine Pitrou (pitrou) * (Python committer) Date: 2015-07-12 20:39
> ping

Sorry. I do not have time currently to tackle this issue. Feel free to submit and/or commit improvements if you feel like it.
msg261917 - (view) Author: Marc Abramowitz (Marc.Abramowitz) * Date: 2016-03-17 16:38
Patch to update the comment to remove "IP addresses are not accepted for *hostname*", because supported for IP addresses was added earlier by @pitrou in
msg262987 - (view) Author: Marc Abramowitz (Marc.Abramowitz) * Date: 2016-04-07 14:57
`ip_certs_comment.patch` is a simple patch that just removes the verbiage about not supporting IP addresses in hostnames, as that restriction was removed by an earlier commit from Antoine.
msg262988 - (view) Author: Christian Heimes (christian.heimes) * (Python committer) Date: 2016-04-07 15:06
I'm -1 on the patch for a practical reason: The current API is broken and I don't want to have it documented as officially supported.

In fact it is not only broken but also incompatible with more modern releases of OpenSSL. Recently OpenSSL got proper implementation of hostname and IP checking. Hostname and IP must be set with different API calls:
msg303155 - (view) Author: (j-harbott) Date: 2017-09-27 15:10
The original issue still exists in py27, is there a chance to get the fix backported? See and for sample issues that arise because we need to work around this one.
msg303156 - (view) Author: Alex Gaynor (Alex Gaynor) Date: 2017-09-27 15:13
I'd be in favor of backporting this to the 2.x - encouraging reliance on the nonsense behaviour of putting IPAddresses in DNS Names or relying on CN over SAN is bad, and we shouldn't encourage it.
msg314190 - (view) Author: Christian Heimes (christian.heimes) * (Python committer) Date: 2018-03-21 11:03
#32819 and #32185 have solved the last outstanding bugs with IP address validation and handling. I'm fine with a backport of the feature to 2.7 now.
msg391301 - (view) Author: Christian Heimes (christian.heimes) * (Python committer) Date: 2021-04-17 18:23
Python 2 is out of support. Python 3 can verify IP addresses in certificates correctly.
Date User Action Args
2022-04-11 14:58:11adminsetgithub: 67428
2021-04-17 18:23:06christian.heimessetstatus: open -> closed
resolution: out of date
messages: + msg391301

stage: needs patch -> resolved
2018-03-21 11:03:48christian.heimessetassignee: christian.heimes ->
messages: + msg314190
versions: - Python 3.5, Python 3.6, Python 3.7
2017-09-27 15:13:41Alex Gaynorsetnosy: + Alex Gaynor
messages: + msg303156
2017-09-27 15:10:04j-harbottsetnosy: + j-harbott

messages: + msg303155
versions: + Python 2.7
2016-09-15 07:49:53christian.heimessetcomponents: + SSL
2016-09-08 23:26:31christian.heimessetpriority: normal -> high
assignee: christian.heimes
versions: + Python 3.7
2016-08-24 15:53:38r.david.murraysetstage: commit review -> needs patch
2016-04-07 15:06:31christian.heimessetstage: resolved -> commit review
messages: + msg262988
versions: + Python 3.6
2016-04-07 14:57:02Marc.Abramowitzsetmessages: + msg262987
2016-03-17 16:38:36Marc.Abramowitzsetfiles: + ip_certs_comment.patch
nosy: + Marc.Abramowitz
messages: + msg261917

2015-07-12 20:39:00pitrousetmessages: + msg246671
2015-07-05 17:48:23christian.heimessetmessages: + msg246327
2015-06-02 11:49:20christian.heimessetstatus: closed -> open
resolution: fixed -> (no value)
messages: + msg244665
2015-02-15 17:15:44pitrousetstatus: open -> closed
resolution: fixed
stage: patch review -> resolved
2015-02-15 17:13:17python-devsetnosy: + python-dev
messages: + msg236051
2015-01-17 18:54:25pitrousetfiles: + ip_certs.patch
keywords: + patch
2015-01-17 18:54:16pitrousetmessages: + msg234190
stage: needs patch -> patch review
2015-01-14 17:24:27pitrousetnosy: + christian.heimes, dstufft
messages: + msg234038
2015-01-14 17:23:28pitrousetstage: needs patch
type: security -> enhancement
versions: - Python 2.7, Python 3.4
2015-01-14 13:37:05r.david.murraysetnosy: + r.david.murray
2015-01-14 09:05:33vstinnersetnosy: + pitrou, alex

versions: + Python 3.4, Python 3.5
2015-01-14 09:04:52Ádám.Zsigmondcreate