patch to apache for IPv6 only httpd

Curtis Villamizar curtis at occnc.com
Mon Aug 13 18:08:59 UTC 2012


In message <CACM2dAaQLa38rLvbOfXJb6wFzrV_E0DUL6cxT9dher6G_6v4bA at mail.gmail.com>
"Philip M. Gollucci" writes:
 
> What happens if you try to bind to an ip address the machine doesn't
> have whether v4 or v6 with this patch ?


In that case there is no change to the behavior although "assert" may
not be the best diagnostic, the same thing happens with or without the
patch if the address is not present.

The code here insures that the server does not start unless it has at
least one valid address.  The hostname is provided as NULL and a
lookup is done.  The old code looks for any valid IPv4 address.  The
code breaks if there are no IPv4 addresses, there are only valid IPv6
addresses.  The patch repeats the check with AF_UNSPEC (accept
anything) and this would pick up a valid IPv6 address and avoid the
assert.  If there were no valid addresses, then prior code that
produced a list of addresses is broken and this code does the same as
before the patch - it asserts.

apr_sockaddr_info_get is in srclib/apr/network_io/unix/sockaddr.c
where it does some checking, calls call_resolver if getaddrinfo
exists, otherwise gethostbyname with the hostname.  In call_resolver
getaddrinfo (see man page) is called which returns a struct addrinfo
which has a list of addresses.  If an address string is provided,
there will be one address in the list.  call_resolver will only return
an AF_INET or AF_INET6 address (it creates a linked list in the
argument p, using calloc to allocate entries).

The assumption in this code is that you can't get here without a valid
address, but then in testing that assumption, only a valid IPv4
address is accepted.

After this test, the result does not appear to be used (otherwise DS
machines wouldn't work).  The addresses from the config file are used
in alloc_listener which calls apr_sockaddr_info_get with APR_UNSPEC
and a port number.  The addresses from the config file may have
absolutely nothing to do with the list of addresses returned by
gethostbyname in the prior check.

Curtis


> On Sun, Aug 12, 2012 at 11:53 PM, Curtis Villamizar <curtis at occnc.com>wrote:
>  
> >
> > In message <50282D58.5070605 at FreeBSD.org>
> > Olli Hauer writes:
> >
> > > On 2012-08-11 23:22, Curtis Villamizar wrote:
> > > > FYI-
> > > >
> > > > This very simple patch prevents an assert when httpd is run on a
> > > > server that has no IPv4 address.  An example is a BSD jail running
> > > > with only an IPv6 address on the interface (no loopback so no
> > > > 127.0.0.1 address to bind to).
> > > >
> > > > Copy the patch below into the files directory as
> > > > /usr/ports/www/apache22/files/patch-server__config.c
> > > >
> > > > The port maintainer is on the Cc.  No bug has been reported.
> > > >
> > > > BTW- I noticed this a long time ago.  I don't remember if I reported
> > > > it or forgot to.  Appologies if this is a duplicate.  It is not in the
> > > > httpd-2.2.22.tar.bz2 tarball, in the distinfo dated 23 July 2012.
> > > >
> > > > Curtis
> > > >
> > > >
> > > > --- ./server/config.c.orig  2010-10-07 09:56:54.000000000 -0700
> > > > +++ ./server/config.c       2011-09-26 21:20:35.000000000 -0700
> > > > @@ -1979,6 +1979,9 @@
> > > >      /* NOT virtual host; don't match any real network interface */
> > > >      rv = apr_sockaddr_info_get(&s->addrs->host_addr,
> > > >                                 NULL, APR_INET, 0, 0, p);
> > > > +    if (rv != APR_SUCCESS)
> > > > +        rv = apr_sockaddr_info_get(&s->addrs->host_addr,
> > > > +                                   NULL, APR_UNSPEC, 0, 0, p);
> > > >      ap_assert(rv == APR_SUCCESS); /* otherwise: bug or no storage */
> > > >
> > > >      s->addrs->host_port = 0; /* matches any port */
> > >
> > > Hi Curtis,
> > >
> > > Is this patch also relevant if apache22 was build with
> > > -DWITH_IPV6_V6ONLY ?
> > >
> > > --
> > > olli
> >
> >
> > No.  Apache was not built with -DWITH_IPV6_V6ONLY.  It is apache built
> > with dual stack support though I don't think the code is any different
> > if built with WITH_IPV6_V6ONLY.  Nothing here is conditionally
> > compiled.  I also checked the .h where APR_INET is defined (in
> > srclib/apr/include/apr_network_io.h).  It is unconditionally defined
> > to AF_INET.
> >
> > The code compiles but the server fails to run, giving an assert when
> > starting up.  Its a simple patch.  APR_INET6 could be used instead of
> > APR_UNSPEC in the patch.
> >
> > Curtis


More information about the freebsd-apache mailing list