[Nut-upsdev] [Nut-upsuser] Question on simultaneous IPv4 and IPv6 "any address" listening

Greg Troxel gdt at lexort.com
Sat Aug 5 13:24:50 BST 2023


Jim Klimov via Nut-upsuser <nut-upsuser at alioth-lists.debian.net> writes:

>   I've recently found that at least on my test box the `LISTEN *` line had
> only set up an IPv4 `0.0.0.0` listener but not an IPv6 `::0` listener for
> `upsd`.

Interesting.  On one system I checked, I have 4 explicit directives for
127.0.0.1, ::1, and the LAN on v4/v6.  On another, I have an empty
upsd.conf and it is listening:

nut      upsd        1047    4* internet stream tcp 127.0.0.1:3493
nut      upsd        1047    5* internet6 stream tcp [::1]:3493

> In fact, at least on a "dual-stack" system, it seems impossible to
> bind to both - so depending on binding order I either lose IPv6 or lose
> IPv4 directly (but have it practically as IPv4-over-IPv6).

That is not intrinsic to a system that does v4 and v6.  It is about a
misfeature which if turned on, when one binds to v6 also sets up a
listener on v4 which connects as a mapped address.  These days, I view
it as a bug for a system to be configuret hat way.  On NetBSD, from
ip6(4):

     IPV6_V6ONLY int *
             Get or set whether only IPv6 connections can be made to this
             socket.  For wildcard sockets, this can restrict connections to
             IPv6 only.

which is 1 on my system.

>   Given that `LISTEN *` support is in fact not documented explicitly (I
> think), I am inclined to define it as listening to "any" on whatever
> address families are available and supported by the NUT build, and somehow
> ensuring that to the best of our capability (technical puzzles exist - see
> GitHub issue).

It seems really obvious that * means anything, so agreed.

I think it's important that the default, if there are no LISTEN
directives, be "listen on all localhost addresses of all address
familes".  And probably there should be a way to say that explicitly,
like "LISTEN localhost".

Practically, LISTEN localhost should:

#ifdef v6 at compile time
  open a socket and bind to [::1]:3493
    error log that v6 bind failed
#endif

  open a socket and bind to 127.0.0.1:3493
    if error:
      if there is a v6 socket:
        debug log that v4 bind failed, maybe, or maybe it's a real
        error?  need to figure out if v6only=0 systems some try to map
        this.  The point  being not to fight os/sysadmin choice even if
        misguided :-)
      else:
        error log that v4 bind failed

and LISTEN * should

#ifdef v6 at compile time
  open a socket and bind to INADDR6_ANY:3493
    error log that v6 bind failed
#endif

  open a socket and bind to INADDR_ANY:3493
    if error:
      if there is a v6 socket:
        debug log that v4 bind failed
      else:
        error log that v4 bind failed

    


>   Detailed musing and logs are posted in
> https://github.com/networkupstools/nut/issues/2012
>
>   Pro/Con ideas are welcome :)
>
> Jim
> _______________________________________________
> Nut-upsuser mailing list
> Nut-upsuser at alioth-lists.debian.net
> https://alioth-lists.debian.net/cgi-bin/mailman/listinfo/nut-upsuser



More information about the Nut-upsdev mailing list