classification
Title: getaddrinfo returns wrong results if IPv6 is disabled
Type: behavior Stage:
Components: Library (Lib) Versions: Python 2.7
process
Status: closed Resolution: wont fix
Dependencies: Superseder:
Assigned To: Nosy List: giampaolo.rodola, loewis, schlamar, schmir, vstinner
Priority: normal Keywords:

Created on 2012-10-12 08:04 by schmir, last changed 2013-04-03 10:28 by giampaolo.rodola. This issue is now closed.

Messages (12)
msg172730 - (view) Author: Ralf Schmitt (schmir) Date: 2012-10-12 08:08
I'm running the following code on python 2.7.3 on a 64 bit linux.

import socket
print "has_ipv6", socket.has_ipv6

res = socket.getaddrinfo("python.org", 80, socket.AF_INET6, socket.SOCK_STREAM)
print "python.org is", res

With IPv6 enabled, I get the following output:
has_ipv6 True
python.org is [(10, 1, 6, '', ('2001:888:2000:d::a2', 80, 0, 0))]

With IPv6 disabled (i.e I ran ./configure --disable-ipv6), I get:

has_ipv6 False
python.org is [(10, 1, 6, '', (10, '\x00P\x00\x00\x00\x00 \x01\x08\x88 \x00\x00\r'))]
msg172784 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2012-10-12 21:41
> getaddrinfo returns wrong results if IPv6 is disabled

If IPv6 support is disabled, Python is unable to decode an IPv6 address. So don't ask for IPv6 addresses if you disabled IPv6 support.

I don't understand this issue.
msg172786 - (view) Author: Ralf Schmitt (schmir) Date: 2012-10-12 21:58
Thanks for looking at this. loewis told me in  http://bugs.python.org/issue7735#msg172726 the following:

"""The switch --disable-ipv6 is supported and works as intended. It is not the intention of the switch to disable AAAA lookups. Instead, it disables support for IPv6 sockets."""

So, I expected it to work.

Can you please take a look at the issue 7735? loewis closed this as wontfix. And my argumentation actually involves "don't ask for IPv6 addresses if you disabled IPv6 support".

Anyway, I still think those bogus addresses should be filtered from the getaddrinfo result (if they can't be made correct).

Note that you'll also get bogus results from this call when not explicitly asking for IPv6 addresses (e.g. passing socket.AF_UNSPEC as the third argument).
msg178756 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2013-01-01 21:24
"""The switch --disable-ipv6 is supported and works as intended. It is not the intention of the switch to disable AAAA lookups. Instead, it disables support for IPv6 sockets."""

I just think that this definition is not exact. Do you seriously expect IPv6 to work when you explicitly use --disable-ipv6 which *disables* support of IPv6?

If you would like to use IPv6, just forget this old configuration option.

If you would like to disable IPv6, disable it system-wide. See:
http://bugs.python.org/issue7735#msg178634
msg178760 - (view) Author: Ralf Schmitt (schmir) Date: 2013-01-01 21:48
socket getaddrinfo returns garbage:

>>> socket.getaddrinfo("python.org", 80)
[(2, 1, 6, '', ('82.94.164.162', 80)), (2, 2, 17, '', ('82.94.164.162', 80)), (2, 3, 0, '', ('82.94.164.162', 80)), (10, 1, 6, '', (10, '\x00P\x00\x00\x00\x00 \x01\x08\x88 \x00\x00\r')), (10, 2, 17, '', (10, '\x00P\x00\x00\x00\x00 \x01\x08\x88 \x00\x00\r')), (10, 3, 0, '', (10, '\x00P\x00\x00\x00\x00 \x01\x08\x88 \x00\x00\r'))]

yes, I would expect that python didn't give me garbage when calling getaddrinfo. Note that the caller didn't specify AF_INET6 this time!

Do you really think that this is not a bug?
msg178761 - (view) Author: STINNER Victor (vstinner) * (Python committer) Date: 2013-01-01 21:53
> socket.getaddrinfo("python.org", 80)

This is a different issue: it's #7735.

> Do you really think that this is not a bug?

#7735 is a bug but it was decided that it will not be fixed. You may reopen #7735 if you disagree.
msg178764 - (view) Author: Martin v. Löwis (loewis) * (Python committer) Date: 2013-01-01 22:13
The data returned is not bogus; this is the correct result. If the system's getaddrinfo returns an unsupported address family, Python returns a bytes object (the system's sockaddr buffer) to the application. This should be documented, though (either in the introduction to the socket module, or specifically for getaddrinfo).
msg178768 - (view) Author: Ralf Schmitt (schmir) Date: 2013-01-01 22:24
Given the fact that the bytes object is rather surprising and probaby useless for the caller I wouldn't call this a "correct result".

(sorry, I lost too much time on this issue, I had to put another comment here).
msg178772 - (view) Author: Martin v. Löwis (loewis) * (Python committer) Date: 2013-01-01 22:48
It's not at all useless: it enables the application to bypass limitations in Python, i.e. process the sockaddr on its own (very much in the same way as you have to do for ioctl/fcntl).

Whether it's surprising or not depends on what you expected to happen. Python always tries to expose system interfaces unmodified, so one "should" expect something like this to happen when there is a real chance that the system returns data which Python cannot interpret.

What is puzzling is that you (reportedly) get a TypeError when you pass them to the socket creation (or connect); instead, it should tell you that the address family is not supported.
msg178774 - (view) Author: Ralf Schmitt (schmir) Date: 2013-01-01 22:55
The TypeError error happened when using gevent. I've already written in that other issue that this information was wrong and I get a "bad family" error. Sorry, about that.

But this also demonstrates my point here. The Type error was raised exactly because the gevent code didn't expect a string at that point!
msg180372 - (view) Author: Marc Schlaich (schlamar) * Date: 2013-01-22 08:37
I agree with schmir, this is really unexpected behavior. At least it should be fixed in the documentation. The doc currently says you get a 4-tuple for IPv6, which is just wrong in this case.

Prominent library stumbled about this issue is Tornado (https://github.com/facebook/tornado/pull/670) and there are likely more.
msg180517 - (view) Author: Ralf Schmitt (schmir) Date: 2013-01-24 08:52
Marc, I think you'll have to bring this up on the mailing list if you want to have anything changed. The developers on the nosy list have already closed this as "wont fix". They don't care anymore.
History
Date User Action Args
2013-04-03 10:28:17giampaolo.rodolasetnosy: + giampaolo.rodola
2013-01-24 08:52:28schmirsetmessages: + msg180517
2013-01-22 08:37:51schlamarsetnosy: + schlamar
messages: + msg180372
2013-01-01 23:54:04loewissetmessages: - msg178791
2013-01-01 23:53:55loewissetmessages: - msg178789
2013-01-01 23:53:43loewissetmessages: + msg178791
2013-01-01 23:52:29loewissetmessages: + msg178789
2013-01-01 22:55:41schmirsetmessages: + msg178774
2013-01-01 22:48:59loewissetmessages: + msg178772
2013-01-01 22:24:39schmirsetmessages: + msg178768
2013-01-01 22:13:04loewissetmessages: + msg178764
2013-01-01 21:53:19vstinnersetmessages: + msg178761
2013-01-01 21:48:40schmirsetmessages: + msg178760
2013-01-01 21:24:05vstinnersetstatus: open -> closed

nosy: + loewis
messages: + msg178756

resolution: wont fix
2012-10-12 21:58:03schmirsetmessages: + msg172786
2012-10-12 21:42:00vstinnersetnosy: + vstinner
messages: + msg172784
2012-10-12 08:08:37schmirsettype: behavior
messages: + msg172730
components: + Library (Lib)
versions: + Python 2.7
2012-10-12 08:04:15schmircreate