[zeromq-dev] IPv6 support (was Re: Leaving my role as maintainer)

Martin Lucina mato at kotelna.sk
Tue Jul 12 15:32:18 CEST 2011

sustrik at 250bpm.com said:
> Btw, one final question. You've explained to me how to design IPv6 
> support so that it plays well with dual-stack boxes. Of course, I forgot 
> what you've said in the meantime, but it seemed to make sense back then. 
> Can you outline how it should work in few sentences?

Hmm, I thought I wrote about this some time ago, but maybe not. Here's my
view on how things should work, anyone else with practical IPv6 experience
please comment/correct. It's been a while since I looked at this so the
actual APIs I talk about might not be entirely correct.

Also, the asynchronous nature of connecting 0MQ sockets might pose problems
I haven't anticipated.

Listening (bind) side

1) If the user has specified an endpoint of '*', INADDR_ANY/AF_UNSPEC(?)
should be used to create a dual-stack listening socket. This is the
simplest case.

2) If the user has specified an endpoint using an interface name, e.g.
'eth0', 0MQ must determine if the interface has an IPv6 or IPv4 address,
and bind two separate listening sockets, one to each address family.

3) If the user specifies a numeric IPv4 or IPv6 address then only that
address shall be used (i.e. existing behaviour with the addition of IPv6).

4) For PGM endpoints, I don't know. To be discussed with Steve.

Connecting (connect) side

1) If the user has specified a host name, and the local machine has IPv6
enabled at all (I forget exactly how to detect that, but it's part of the
getaddrinfo() stuff), then 0MQ must first attempt to resolve an AF_INET6
address for the hostname.

2) If the resolution fails, skip this step. Else, attempt to connect to the
IPv6 address. If that succeeds then we are done.

2a) Not sure how well this is possible with the current codebase, but if
the connection to the IPv6 address fails using a hard error that could be
attributed to faulty IPv6 connectivity, then we should fall back to IPv4.
Such an error could be e.g. "No route to host" or even "Connection refused".

3) Attempt to resolve an AF_INET address for the host. If that succeeds,
connect to it (and assume IPv6 to that endpoint is not functional). If that
fails, then fail.

4) For numeric addresses nothing changes, other than the addition of IPv6
addressing (i.e. no fallback).

As you can see from the above, the general idea is always to bind to all
available address families, and then, provided the box "claims to have"
IPv6, attempt to resolve/connect to IPv6 first, falling back to IPv4 if
that doesn't work. Step 2a) is the complex part for us, since most normal
TCP applications connect synchronously, and for UDP/PGM it's pratically
impossible to tell if there's anyone at the other end so I'm not sure what
to do there (possibly no fallback at all, since that's really only
interesting in the simple case of users using TCP.)

Hope this helps.


More information about the zeromq-dev mailing list