From: Mark Zealey Date: Mon, 9 Dec 2013 12:01:02 +0000 (+0200) Subject: more changes X-Git-Tag: rec-3.6.0-rc1~239^2~4 X-Git-Url: http://git.ipfire.org/gitweb.cgi?a=commitdiff_plain;h=3a56adcc8b9e18aaf56cee75df0eaa15d48a6db4;p=thirdparty%2Fpdns.git more changes --- diff --git a/pdns/common_startup.cc b/pdns/common_startup.cc index af0bd6b521..2294ce6051 100644 --- a/pdns/common_startup.cc +++ b/pdns/common_startup.cc @@ -54,6 +54,7 @@ void declareArguments() ::arg().set("smtpredirector","Our smtpredir MX host")="a.misconfigured.powerdns.smtp.server"; ::arg().set("local-address","Local IP addresses to which we bind")="0.0.0.0"; ::arg().set("local-ipv6","Local IP address to which we bind")=""; + ::arg().setSwitch("reuseport","Enable higher performance on compliant kernels by using SO_REUSEPORT allowing each receiver thread to open its own socket")=""; ::arg().set("query-local-address","Source IP address for sending queries")="0.0.0.0"; ::arg().set("query-local-address6","Source IPv6 address for sending queries")="::"; ::arg().set("overload-queue-length","Maximum queuelength moving to packetcache only")="0"; @@ -247,8 +248,10 @@ void *qthread(void *number) // If we have SO_REUSEPORT then create a new port for all receiver threads // other than the first one. - if( number > 0 && NS->canReusePort() ) - NS = new UDPNameserver(); + if( number > 0 && NS->canReusePort() ) { + L< If this many packets are waiting for database attention, answer any new questions strictly from the packet cache. + reuseport=[yes|no] + + On Linux 3.9 and some BSD kernels the SO_REUSEPORT option allows each + receiver-thread to open a new socket on the same port which allows + for much higher performance on multi-core boxes. Setting this option + will enable use of SO_REUSEPORT when available and seamlessly fall + back to a single socket when it is not available. A side-effect is + that you can start multiple servers on the same IP/port combination + which may or may not be a good idea. You could use this to enable + transparent restarts, but it may also mask configuration issues and + for this reason it is disabled by default. + server-id diff --git a/pdns/nameserver.cc b/pdns/nameserver.cc index 5b99520a1a..75ab1d511c 100644 --- a/pdns/nameserver.cc +++ b/pdns/nameserver.cc @@ -89,7 +89,6 @@ extern StatBag S; #endif vector g_localaddresses; // not static, our unit tests need to poke this -pthread_mutex_t localaddresses_lock=PTHREAD_MUTEX_INITIALIZER; void UDPNameserver::bindIPv4() { @@ -124,17 +123,17 @@ void UDPNameserver::bindIPv4() setsockopt(s, IPPROTO_IP, GEN_IP_PKTINFO, &one, sizeof(one)); #ifdef SO_REUSEPORT - if( setsockopt(s, SOL_SOCKET, SO_REUSEPORT, &one, sizeof(one)) ) - d_can_reuseport = false; + if( d_can_reuseport ) + if( setsockopt(s, SOL_SOCKET, SO_REUSEPORT, &one, sizeof(one)) ) + d_can_reuseport = false; #endif locala=ComboAddress(localname, ::arg().asNum("local-port")); if(locala.sin4.sin_family != AF_INET) throw PDNSException("Attempting to bind IPv4 socket to IPv6 address"); - pthread_mutex_lock(&localaddresses_lock); - g_localaddresses.push_back(locala); - pthread_mutex_unlock(&localaddresses_lock); + if( !d_additional_socket ) + g_localaddresses.push_back(locala); if(::bind(s, (sockaddr*)&locala, locala.getSocklen()) < 0) { L<