From 9f3a75bb9063cd29d4589c564d798daad0112c7a Mon Sep 17 00:00:00 2001 From: Otto Moerbeek Date: Tue, 3 Jun 2025 16:56:38 +0200 Subject: [PATCH] rec: start to listen on ::1 by default, but don't consider it an error if it fails --- pdns/recursordist/pdns_recursor.cc | 10 ++++++++-- pdns/recursordist/rec-rust-lib/table.py | 3 ++- pdns/recursordist/rec-tcp.cc | 9 +++++++-- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/pdns/recursordist/pdns_recursor.cc b/pdns/recursordist/pdns_recursor.cc index 8df1a3bf47..22607c192d 100644 --- a/pdns/recursordist/pdns_recursor.cc +++ b/pdns/recursordist/pdns_recursor.cc @@ -2710,7 +2710,7 @@ unsigned int makeUDPServerSockets(deferredAdd_t& deferredAdds, Logr::log_t log, if (socketFd < 0) { throw PDNSException("Making a UDP server socket for resolver: " + stringerror()); } - logVec.emplace_back(address.toStringWithPort()); + if (!setSocketTimestamps(socketFd)) { SLOG(g_log << Logger::Warning << "Unable to enable timestamp reporting for socket" << endl, log->info(Logr::Warning, "Unable to enable timestamp reporting for socket")); @@ -2776,13 +2776,19 @@ unsigned int makeUDPServerSockets(deferredAdd_t& deferredAdds, Logr::log_t log, socklen_t socklen = address.getSocklen(); if (::bind(socketFd, reinterpret_cast(&address), socklen) < 0) { // NOLINT(cppcoreguidelines-pro-type-reinterpret-cast) - throw PDNSException("Resolver binding to server socket on " + address.toStringWithPort() + ": " + stringerror()); + int err = errno; + if (address != ComboAddress{"::1", defaultLocalPort}) { + throw PDNSException("Resolver binding to server socket on " + address.toStringWithPort() + ": " + stringerror(err)); + } + log->info(Logr::Warning, "Cannot listen on this address, skipping", "proto", Logging::Loggable("UDP"), "address", Logging::Loggable(address), "error", Logging::Loggable(stringerror(err))); + continue; } setNonBlocking(socketFd); deferredAdds.emplace_back(socketFd, handleNewUDPQuestion); g_listenSocketsAddresses[socketFd] = address; // this is written to only from the startup thread, not from the workers + logVec.emplace_back(address.toStringWithPort()); } if (doLog) { log->info(Logr::Info, "Listening for queries", "proto", Logging::Loggable("UDP"), "addresses", Logging::IterLoggable(logVec.cbegin(), logVec.cend()), "socketInstances", Logging::Loggable(instances), "reuseport", Logging::Loggable(g_reusePort)); diff --git a/pdns/recursordist/rec-rust-lib/table.py b/pdns/recursordist/rec-rust-lib/table.py index 3dc1ee2730..71f67bde9b 100644 --- a/pdns/recursordist/rec-rust-lib/table.py +++ b/pdns/recursordist/rec-rust-lib/table.py @@ -1265,8 +1265,9 @@ Indication of how many queries will be averaged to get the average latency repor 'section' : 'incoming', 'oldname' : 'local-address', 'type' : LType.ListSocketAddresses, - 'default' : '127.0.0.1', + 'default' : '127.0.0.1, ::1', 'help' : 'IP addresses to listen on, separated by spaces or commas. Also accepts ports.', + 'versionchanged': ('5.3.0', '::1 was added to the list'), 'doc' : ''' Local IP addresses to which we bind. Each address specified can include a port number; if no port is included then the diff --git a/pdns/recursordist/rec-tcp.cc b/pdns/recursordist/rec-tcp.cc index 2b164c21e1..6ea1bc7401 100644 --- a/pdns/recursordist/rec-tcp.cc +++ b/pdns/recursordist/rec-tcp.cc @@ -1115,7 +1115,6 @@ unsigned int makeTCPServerSockets(deferredAdd_t& deferredAdds, std::set& tc if (socketFd < 0) { throw PDNSException("Making a TCP server socket for resolver: " + stringerror()); } - logVec.emplace_back(address.toStringWithPort()); setCloseOnExec(socketFd); int tmp = 1; @@ -1178,7 +1177,12 @@ unsigned int makeTCPServerSockets(deferredAdd_t& deferredAdds, std::set& tc socklen_t socklen = address.sin4.sin_family == AF_INET ? sizeof(address.sin4) : sizeof(address.sin6); if (::bind(socketFd, reinterpret_cast(&address), socklen) < 0) { // NOLINT(cppcoreguidelines-pro-type-reinterpret-cast) - throw PDNSException("Binding TCP server socket for " + address.toStringWithPort() + ": " + stringerror()); + int err = errno; + if (address != ComboAddress{"::1", defaultLocalPort}) { + throw PDNSException("Binding TCP server socket for " + address.toStringWithPort() + ": " + stringerror(err)); + } + log->info(Logr::Warning, "Cannot listen on this address, skipping", "proto", Logging::Loggable("TCP"), "address", Logging::Loggable(address), "error", Logging::Loggable(stringerror(err))); + continue; } setNonBlocking(socketFd); @@ -1193,6 +1197,7 @@ unsigned int makeTCPServerSockets(deferredAdd_t& deferredAdds, std::set& tc listen(socketFd, 128); deferredAdds.emplace_back(socketFd, handleNewTCPQuestion); tcpSockets.insert(socketFd); + logVec.emplace_back(address.toStringWithPort()); // we don't need to update g_listenSocketsAddresses since it doesn't work for TCP/IP: // - fd is not that which we know here, but returned from accept() -- 2.47.3