aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDoug Barton <dougb@FreeBSD.org>2008-09-01 21:43:09 +0000
committerDoug Barton <dougb@FreeBSD.org>2008-09-01 21:43:09 +0000
commit02678434fa2a287b30816759a5c57d562434dc7e (patch)
tree70af4059a455206a137900193794375962a78fdf
parent218ea97b9e01d8e16190789f89493723232ae1f0 (diff)
downloadsrc-02678434fa2a287b30816759a5c57d562434dc7e.tar.gz
src-02678434fa2a287b30816759a5c57d562434dc7e.zip
Vendor import of BIND 9.3.5-P2
Notes
Notes: svn path=/vendor/bind9/dist-9.3/; revision=182639
-rw-r--r--CHANGES45
-rw-r--r--bin/dig/dighost.c12
-rw-r--r--bin/named/client.c46
-rw-r--r--bin/named/config.c13
-rw-r--r--bin/named/controlconf.c6
-rw-r--r--bin/named/interfacemgr.c19
-rw-r--r--bin/named/lwresd.c11
-rw-r--r--bin/named/named.conf.docbook6
-rw-r--r--bin/named/server.c65
-rw-r--r--configure.in4
-rw-r--r--doc/arm/Bv9ARM-book.xml20
-rw-r--r--lib/bind/configure.in4
-rw-r--r--lib/dns/api2
-rw-r--r--lib/dns/dispatch.c48
-rw-r--r--lib/dns/include/dns/dispatch.h14
-rw-r--r--lib/dns/message.c13
-rw-r--r--lib/dns/request.c18
-rw-r--r--lib/dns/resolver.c18
-rw-r--r--lib/dns/xfrin.c25
-rw-r--r--lib/isc/api6
-rw-r--r--lib/isc/include/isc/resource.h19
-rw-r--r--lib/isc/include/isc/socket.h19
-rw-r--r--lib/isc/include/isc/timer.h6
-rw-r--r--lib/isc/timer.c18
-rw-r--r--lib/isc/unix/app.c8
-rw-r--r--lib/isc/unix/resource.c56
-rw-r--r--lib/isc/unix/socket.c246
-rw-r--r--lib/isc/unix/socket_p.h4
-rw-r--r--lib/isccfg/api2
-rw-r--r--lib/isccfg/namedconf.c3
-rw-r--r--version4
31 files changed, 587 insertions, 193 deletions
diff --git a/CHANGES b/CHANGES
index a44e20337bb5..df9ebf1c5eed 100644
--- a/CHANGES
+++ b/CHANGES
@@ -1,3 +1,44 @@
+ --- 9.3.5-P2 released ---
+
+2406. [bug] Some operating systems have FD_SETSIZE set to a
+ low value by default, which can cause resource
+ exhaustion when many simultaneous connections are
+ open. Linux in particular makes it difficult to
+ increase this value. To use more sockets with
+ select(), set ISC_SOCKET_FDSETSIZE. Example:
+ STD_CDEFINES="-DISC_SOCKET_FDSETSIZE=4096" ./configure
+ (This should not be necessary in most cases, and
+ never for an authoritative-only server.) [RT #18328]
+
+2404. [port] hpux: files unlimited support.
+
+2403. [bug] TSIG context leak. [RT #18341]
+
+2402. [port] Support Solaris 2.11 and over. [RT #18362]
+
+2401. [bug] Expect to get E[MN]FILE errno internal_accept()
+ (from accept() or fcntl() system calls). [RT #18358]
+
+2399. [bug] Abort timeout queries to reduce the number of open
+ UDP sockets. [RT #18367]
+
+2398. [bug] Improve file descriptor management. New,
+ temporary, named.conf option reserved-sockets,
+ default 512. [RT #18344]
+
+2396. [bug] Don't set SO_REUSEADDR for randomized ports.
+ [RT #18336]
+
+2395. [port] Avoid warning and no effect from "files unlimited"
+ on Linux when running as root. [RT #18335]
+
+2394. [bug] Default configuration options set the limit for
+ open files to 'unlimited' as described in the
+ documentation. [RT #18331]
+
+2392. [bug] remove 'grep -q' from acl test script, some platforms
+ don't support it. [RT #18253]
+
--- 9.3.5-P1 released ---
2375. [security] Fully randomize UDP query ports to improve
@@ -154,7 +195,7 @@
[RT #17113]
2249. [bug] Only set Authentic Data bit if client requested
- DNSSEC, per RFC 3655 [RT #17175]
+ DNSSEC, per RFC 3655 [RT #17175]
2248. [cleanup] Fix several errors reported by Coverity. [RT #17160]
@@ -817,7 +858,7 @@
query order sensitive. [RT #14933]
1905. [bug] Strings returned from cfg_obj_asstring() should be
- treated as read-only. [RT #15256]
+ treated as read-only. [RT #15256]
1901. [cleanup] Don't add DNSKEY records to the additional section.
diff --git a/bin/dig/dighost.c b/bin/dig/dighost.c
index f3b0d9954b96..efd24030b17f 100644
--- a/bin/dig/dighost.c
+++ b/bin/dig/dighost.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: dighost.c,v 1.221.2.19.2.46 2008/01/17 23:45:26 tbox Exp $ */
+/* $Id: dighost.c,v 1.221.2.19.2.46.4.2 2008/07/23 23:16:25 marka Exp $ */
/*
* Notice to programmers: Do not use this code as an example of how to
@@ -2047,14 +2047,15 @@ send_tcp_connect(dig_query_t *query) {
sockcount++;
debug("sockcount=%d", sockcount);
if (specified_source)
- result = isc_socket_bind(query->sock, &bind_address);
+ result = isc_socket_bind(query->sock, &bind_address,
+ ISC_SOCKET_REUSEADDRESS);
else {
if ((isc_sockaddr_pf(&query->sockaddr) == AF_INET) &&
have_ipv4)
isc_sockaddr_any(&bind_any);
else
isc_sockaddr_any6(&bind_any);
- result = isc_socket_bind(query->sock, &bind_any);
+ result = isc_socket_bind(query->sock, &bind_any, 0);
}
check_result(result, "isc_socket_bind");
bringup_timer(query, TCP_TIMEOUT);
@@ -2101,11 +2102,12 @@ send_udp(dig_query_t *query) {
sockcount++;
debug("sockcount=%d", sockcount);
if (specified_source) {
- result = isc_socket_bind(query->sock, &bind_address);
+ result = isc_socket_bind(query->sock, &bind_address,
+ ISC_SOCKET_REUSEADDRESS);
} else {
isc_sockaddr_anyofpf(&bind_any,
isc_sockaddr_pf(&query->sockaddr));
- result = isc_socket_bind(query->sock, &bind_any);
+ result = isc_socket_bind(query->sock, &bind_any, 0);
}
check_result(result, "isc_socket_bind");
diff --git a/bin/named/client.c b/bin/named/client.c
index 3215c6e63732..fbc3bad18de7 100644
--- a/bin/named/client.c
+++ b/bin/named/client.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: client.c,v 1.176.2.13.4.38.4.1 2008/05/22 21:11:13 each Exp $ */
+/* $Id: client.c,v 1.176.2.13.4.38.4.2 2008/07/23 07:28:11 tbox Exp $ */
#include <config.h>
@@ -256,7 +256,7 @@ exit_check(ns_client_t *client) {
*
* Keep the view attached until any outstanding updates complete.
*/
- if (client->nupdates == 0 &&
+ if (client->nupdates == 0 &&
client->newstate == NS_CLIENTSTATE_FREED && client->view != NULL)
dns_view_detach(&client->view);
@@ -786,7 +786,7 @@ client_sendpkg(ns_client_t *client, isc_buffer_t *buffer) {
isc_netaddr_fromsockaddr(&netaddr, &client->peeraddr);
if (ns_g_server->blackholeacl != NULL &&
dns_acl_match(&netaddr, NULL,
- ns_g_server->blackholeacl,
+ ns_g_server->blackholeacl,
&ns_g_server->aclenv,
&match, NULL) == ISC_R_SUCCESS &&
match > 0)
@@ -803,7 +803,7 @@ client_sendpkg(ns_client_t *client, isc_buffer_t *buffer) {
isc_buffer_usedregion(buffer, &r);
CTRACE("sendto");
-
+
result = isc_socket_sendto2(socket, &r, client->task,
address, pktinfo,
client->sendevent, sockflags);
@@ -1077,8 +1077,8 @@ ns_client_error(ns_client_t *client, isc_result_t result) {
/*
* FORMERR loop avoidance: If we sent a FORMERR message
* with the same ID to the same client less than two
- * seconds ago, assume that we are in an infinite error
- * packet dialog with a server for some protocol whose
+ * seconds ago, assume that we are in an infinite error
+ * packet dialog with a server for some protocol whose
* error responses look enough like DNS queries to
* elicit a FORMERR response. Drop a packet to break
* the loop.
@@ -1443,7 +1443,7 @@ client_request(isc_task_t *task, isc_event_t *event) {
* For IPv6 UDP queries, we get this from the pktinfo structure (if
* supported).
* If all the attempts fail (this can happen due to memory shortage,
- * etc), we regard this as an error for safety.
+ * etc), we regard this as an error for safety.
*/
if ((client->interface->flags & NS_INTERFACEFLAG_ANYADDR) == 0)
isc_netaddr_fromsockaddr(&destaddr, &client->interface->addr);
@@ -1504,7 +1504,7 @@ client_request(isc_task_t *task, isc_event_t *event) {
view);
if (sigresult == ISC_R_SUCCESS)
tsig = client->message->tsigname;
-
+
if (allowed(&netaddr, tsig, view->matchclients) &&
allowed(&destaddr, tsig, view->matchdestinations) &&
!((client->message->flags & DNS_MESSAGEFLAG_RD)
@@ -1635,7 +1635,7 @@ client_request(isc_task_t *task, isc_event_t *event) {
ns_client_log(client, DNS_LOGCATEGORY_SECURITY, NS_LOGMODULE_CLIENT,
ISC_LOG_DEBUG(3), ra ? "recursion available" :
- "recursion not available");
+ "recursion not available");
/*
* Dispatch the request.
@@ -1949,7 +1949,7 @@ client_newconn(isc_task_t *task, isc_event_t *event) {
if (ns_g_server->blackholeacl != NULL &&
dns_acl_match(&netaddr, NULL,
- ns_g_server->blackholeacl,
+ ns_g_server->blackholeacl,
&ns_g_server->aclenv,
&match, NULL) == ISC_R_SUCCESS &&
match > 0)
@@ -2319,7 +2319,7 @@ ns_client_checkacl(ns_client_t *client,
isc_result_t result =
ns_client_checkaclsilent(client, acl, default_allow);
- if (result == ISC_R_SUCCESS)
+ if (result == ISC_R_SUCCESS)
ns_client_log(client, DNS_LOGCATEGORY_SECURITY,
NS_LOGMODULE_CLIENT, ISC_LOG_DEBUG(3),
"%s approved", opname);
@@ -2375,16 +2375,16 @@ ns_client_log(ns_client_t *client, isc_logcategory_t *category,
void
ns_client_aclmsg(const char *msg, dns_name_t *name, dns_rdatatype_t type,
- dns_rdataclass_t rdclass, char *buf, size_t len)
+ dns_rdataclass_t rdclass, char *buf, size_t len)
{
- char namebuf[DNS_NAME_FORMATSIZE];
- char typebuf[DNS_RDATATYPE_FORMATSIZE];
- char classbuf[DNS_RDATACLASS_FORMATSIZE];
-
- dns_name_format(name, namebuf, sizeof(namebuf));
- dns_rdatatype_format(type, typebuf, sizeof(typebuf));
- dns_rdataclass_format(rdclass, classbuf, sizeof(classbuf));
- (void)snprintf(buf, len, "%s '%s/%s/%s'", msg, namebuf, typebuf,
+ char namebuf[DNS_NAME_FORMATSIZE];
+ char typebuf[DNS_RDATATYPE_FORMATSIZE];
+ char classbuf[DNS_RDATACLASS_FORMATSIZE];
+
+ dns_name_format(name, namebuf, sizeof(namebuf));
+ dns_rdatatype_format(type, typebuf, sizeof(typebuf));
+ dns_rdataclass_format(rdclass, classbuf, sizeof(classbuf));
+ (void)snprintf(buf, len, "%s '%s/%s/%s'", msg, namebuf, typebuf,
classbuf);
}
@@ -2412,7 +2412,7 @@ ns_client_dumpmessage(ns_client_t *client, const char *reason) {
isc_mem_put(client->mctx, buf, len);
len += 1024;
} else if (result == ISC_R_SUCCESS)
- ns_client_log(client, NS_LOGCATEGORY_UNMATCHED,
+ ns_client_log(client, NS_LOGCATEGORY_UNMATCHED,
NS_LOGMODULE_CLIENT, ISC_LOG_DEBUG(1),
"%s\n%.*s", reason,
(int)isc_buffer_usedlength(&buffer),
@@ -2432,7 +2432,7 @@ ns_client_dumprecursing(FILE *f, ns_clientmgr_t *manager) {
const char *sep;
REQUIRE(VALID_MANAGER(manager));
-
+
LOCK(&manager->lock);
client = ISC_LIST_HEAD(manager->recursing);
while (client != NULL) {
diff --git a/bin/named/config.c b/bin/named/config.c
index 88e7bc9e3407..dc4d928d4f6e 100644
--- a/bin/named/config.c
+++ b/bin/named/config.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2006, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2006-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 2001-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: config.c,v 1.11.2.4.8.36 2007/09/13 05:18:08 each Exp $ */
+/* $Id: config.c,v 1.11.2.4.8.36.4.3 2008/07/23 23:47:49 tbox Exp $ */
#include <config.h>
@@ -48,7 +48,7 @@ options {\n\
#ifndef WIN32
" coresize default;\n\
datasize default;\n\
- files default;\n\
+ files unlimited;\n\
stacksize default;\n"
#endif
" deallocate-on-exit true;\n\
@@ -94,6 +94,7 @@ options {\n\
use-id-pool true;\n\
use-ixfr true;\n\
edns-udp-size 4096;\n\
+ reserved-sockets 512;\n\
\n\
/* view */\n\
allow-notify {none;};\n\
@@ -501,7 +502,7 @@ ns_config_getipandkeylist(const cfg_obj_t *config, const cfg_obj_t *list,
tresult = get_masters_def(config, listname, &list);
if (tresult == ISC_R_NOTFOUND) {
cfg_obj_log(addr, ns_g_lctx, ISC_LOG_ERROR,
- "masters \"%s\" not found", listname);
+ "masters \"%s\" not found", listname);
result = tresult;
goto cleanup;
@@ -579,7 +580,7 @@ ns_config_getipandkeylist(const cfg_obj_t *config, const cfg_obj_t *list,
if (keys[i] == NULL)
goto cleanup;
dns_name_init(keys[i], NULL);
-
+
keystr = cfg_obj_asstring(key);
isc_buffer_init(&b, keystr, strlen(keystr));
isc_buffer_add(&b, strlen(keystr));
@@ -635,7 +636,7 @@ ns_config_getipandkeylist(const cfg_obj_t *config, const cfg_obj_t *list,
isc_mem_put(mctx, lists, listcount * sizeof(*lists));
if (stack != NULL)
isc_mem_put(mctx, stack, stackcount * sizeof(*stack));
-
+
INSIST(keycount == addrcount);
*addrsp = addrs;
diff --git a/bin/named/controlconf.c b/bin/named/controlconf.c
index d8a7bcf2fcf9..e9c53ec8dd80 100644
--- a/bin/named/controlconf.c
+++ b/bin/named/controlconf.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: controlconf.c,v 1.28.2.9.2.13 2008/01/17 23:45:27 tbox Exp $ */
+/* $Id: controlconf.c,v 1.28.2.9.2.13.4.2 2008/07/23 23:16:25 marka Exp $ */
#include <config.h>
@@ -1106,8 +1106,8 @@ add_listener(ns_controls_t *cp, controllistener_t **listenerp,
&listener->sock);
if (result == ISC_R_SUCCESS)
- result = isc_socket_bind(listener->sock,
- &listener->address);
+ result = isc_socket_bind(listener->sock, &listener->address,
+ ISC_SOCKET_REUSEADDRESS);
if (result == ISC_R_SUCCESS)
result = control_listen(listener);
diff --git a/bin/named/interfacemgr.c b/bin/named/interfacemgr.c
index f3d1d0b88c34..524f47b3387f 100644
--- a/bin/named/interfacemgr.c
+++ b/bin/named/interfacemgr.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2006, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2006-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: interfacemgr.c,v 1.59.2.5.8.21 2007/08/28 07:19:08 tbox Exp $ */
+/* $Id: interfacemgr.c,v 1.59.2.5.8.21.4.3 2008/07/23 23:16:25 marka Exp $ */
#include <config.h>
@@ -83,7 +83,7 @@ ns_interfacemgr_create(isc_mem_t *mctx, isc_taskmgr_t *taskmgr,
mgr->generation = 1;
mgr->listenon4 = NULL;
mgr->listenon6 = NULL;
-
+
ISC_LIST_INIT(mgr->interfaces);
/*
@@ -298,7 +298,8 @@ ns_interface_accepttcp(ns_interface_t *ifp) {
#ifndef ISC_ALLOW_MAPPED
isc_socket_ipv6only(ifp->tcpsocket, ISC_TRUE);
#endif
- result = isc_socket_bind(ifp->tcpsocket, &ifp->addr);
+ result = isc_socket_bind(ifp->tcpsocket, &ifp->addr,
+ ISC_SOCKET_REUSEADDRESS);
if (result != ISC_R_SUCCESS) {
isc_log_write(IFMGR_COMMON_LOGARGS, ISC_LOG_ERROR,
"binding TCP socket: %s",
@@ -313,7 +314,7 @@ ns_interface_accepttcp(ns_interface_t *ifp) {
goto tcp_listen_failure;
}
- /*
+ /*
* If/when there a multiple filters listen to the
* result.
*/
@@ -500,7 +501,7 @@ setup_locals(ns_interfacemgr_t *mgr, isc_interface_t *interface) {
unsigned int prefixlen;
family = interface->address.family;
-
+
elt.type = dns_aclelementtype_ipprefix;
elt.negative = ISC_FALSE;
elt.u.ip_prefix.address = interface->address;
@@ -651,7 +652,7 @@ do_scan(ns_interfacemgr_t *mgr, ns_listenlist_t *ext_listen,
{
isc_interface_t interface;
ns_listenlist_t *ll;
- unsigned int family;
+ unsigned int family;
result = isc_interfaceiter_current(iter, &interface);
if (result != ISC_R_SUCCESS)
@@ -827,7 +828,7 @@ do_scan(ns_interfacemgr_t *mgr, ns_listenlist_t *ext_listen,
UNEXPECTED_ERROR(__FILE__, __LINE__,
"interface iteration failed: %s",
isc_result_totext(result));
- else
+ else
result = ISC_R_SUCCESS;
cleanup_iter:
isc_interfaceiter_destroy(&iter);
@@ -858,7 +859,7 @@ ns_interfacemgr_scan0(ns_interfacemgr_t *mgr, ns_listenlist_t *ext_listen,
/*
* Warn if we are not listening on any interface, unless
- * we're in lwresd-only mode, in which case that is to
+ * we're in lwresd-only mode, in which case that is to
* be expected.
*/
if (ext_listen == NULL &&
diff --git a/bin/named/lwresd.c b/bin/named/lwresd.c
index e48822f71195..7dcdad4d47bb 100644
--- a/bin/named/lwresd.c
+++ b/bin/named/lwresd.c
@@ -1,8 +1,8 @@
/*
- * Copyright (C) 2004, 2006 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2006, 2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 2000-2003 Internet Software Consortium.
*
- * Permission to use, copy, modify, and distribute this software for any
+ * Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: lwresd.c,v 1.37.2.2.2.8 2006/02/28 06:32:53 marka Exp $ */
+/* $Id: lwresd.c,v 1.37.2.2.2.8.14.3 2008/07/23 23:16:26 marka Exp $ */
/*
* Main program for the Lightweight Resolver Daemon.
@@ -223,7 +223,7 @@ ns_lwresd_parseeresolvconf(isc_mem_t *mctx, cfg_parser_t *pctx,
for (i = 0; i < lwc->searchnxt; i++) {
CHECK(buffer_putstr(&b, "\t\t\""));
CHECK(buffer_putstr(&b, lwc->search[i]));
- CHECK(buffer_putstr(&b, "\";\n"));
+ CHECK(buffer_putstr(&b, "\";\n"));
}
CHECK(buffer_putstr(&b, "\t};\n"));
}
@@ -569,7 +569,8 @@ listener_bind(ns_lwreslistener_t *listener, isc_sockaddr_t *address) {
return (result);
}
- result = isc_socket_bind(sock, &listener->address);
+ result = isc_socket_bind(sock, &listener->address,
+ ISC_SOCKET_REUSEADDRESS);
if (result != ISC_R_SUCCESS) {
char socktext[ISC_SOCKADDR_FORMATSIZE];
isc_sockaddr_format(&listener->address, socktext,
diff --git a/bin/named/named.conf.docbook b/bin/named/named.conf.docbook
index ff9ae4bce1a6..0f5676cfdd61 100644
--- a/bin/named/named.conf.docbook
+++ b/bin/named/named.conf.docbook
@@ -2,7 +2,7 @@
"http://www.oasis-open.org/docbook/xml/4.2/docbookx.dtd"
[<!ENTITY mdash "&#8212;">]>
<!--
- - Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC")
+ - Copyright (C) 2004-2008 Internet Systems Consortium, Inc. ("ISC")
-
- Permission to use, copy, modify, and/or distribute this software for any
- purpose with or without fee is hereby granted, provided that the above
@@ -17,7 +17,7 @@
- PERFORMANCE OF THIS SOFTWARE.
-->
-<!-- $Id: named.conf.docbook,v 1.1.4.13 2007/08/28 07:19:08 tbox Exp $ -->
+<!-- $Id: named.conf.docbook,v 1.1.4.13.4.2 2008/07/23 23:47:49 tbox Exp $ -->
<refentry>
<refentryinfo>
@@ -36,6 +36,7 @@
<year>2005</year>
<year>2006</year>
<year>2007</year>
+ <year>2008</year>
<holder>Internet Systems Consortium, Inc. ("ISC")</holder>
</copyright>
</docinfo>
@@ -201,6 +202,7 @@ options {
port <replaceable>integer</replaceable>;
querylog <replaceable>boolean</replaceable>;
recursing-file <replaceable>quoted_string</replaceable>;
+ reserved-sockets <replaceable>integer</replaceable>;
random-device <replaceable>quoted_string</replaceable>;
recursive-clients <replaceable>integer</replaceable>;
serial-query-rate <replaceable>integer</replaceable>;
diff --git a/bin/named/server.c b/bin/named/server.c
index c705af0ddcb1..afbecb8487ef 100644
--- a/bin/named/server.c
+++ b/bin/named/server.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: server.c,v 1.339.2.15.2.78.4.1 2008/05/22 21:11:14 each Exp $ */
+/* $Id: server.c,v 1.339.2.15.2.78.4.3 2008/07/23 23:47:49 tbox Exp $ */
#include <config.h>
@@ -2153,26 +2153,28 @@ static isc_result_t
load_configuration(const char *filename, ns_server_t *server,
isc_boolean_t first_time)
{
- isc_result_t result;
- cfg_parser_t *parser = NULL;
cfg_obj_t *config;
- const cfg_obj_t *options;
- const cfg_obj_t *views;
+ cfg_parser_t *parser = NULL;
+ const cfg_listelt_t *element;
+ const cfg_obj_t *builtin_views;
+ const cfg_obj_t *maps[3];
const cfg_obj_t *obj;
+ const cfg_obj_t *options;
const cfg_obj_t *v4ports, *v6ports;
- const cfg_obj_t *maps[3];
- const cfg_obj_t *builtin_views;
- const cfg_listelt_t *element;
+ const cfg_obj_t *views;
dns_view_t *view = NULL;
dns_view_t *view_next;
- dns_viewlist_t viewlist;
dns_viewlist_t tmpviewlist;
- ns_aclconfctx_t aclconfctx;
- isc_uint32_t interface_interval;
- isc_uint32_t heartbeat_interval;
- isc_uint32_t udpsize;
+ dns_viewlist_t viewlist;
in_port_t listen_port;
int i;
+ isc_resourcevalue_t files;
+ isc_result_t result;
+ isc_uint32_t heartbeat_interval;
+ isc_uint32_t interface_interval;
+ isc_uint32_t reserved;
+ isc_uint32_t udpsize;
+ ns_aclconfctx_t aclconfctx;
ns_aclconfctx_init(&aclconfctx);
ISC_LIST_INIT(viewlist);
@@ -2262,6 +2264,43 @@ load_configuration(const char *filename, ns_server_t *server,
set_limits(maps);
/*
+ * Sanity check on "files" limit.
+ */
+ result = isc_resource_curlimit(isc_resource_openfiles, &files);
+ if (result == ISC_R_SUCCESS && files < FD_SETSIZE) {
+ isc_log_write(ns_g_lctx, NS_LOGCATEGORY_GENERAL,
+ NS_LOGMODULE_SERVER, ISC_LOG_WARNING,
+ "the 'files' limit (%" ISC_PRINT_QUADFORMAT "u) "
+ "is less than FD_SETSIZE (%d), increase "
+ "'files' in named.conf or recompile with a "
+ "smaller FD_SETSIZE.", files, FD_SETSIZE);
+ if (files > FD_SETSIZE)
+ files = FD_SETSIZE;
+ } else
+ files = FD_SETSIZE;
+
+ /*
+ * Set the number of socket reserved for TCP, stdio etc.
+ */
+ obj = NULL;
+ result = ns_config_get(maps, "reserved-sockets", &obj);
+ INSIST(result == ISC_R_SUCCESS);
+ reserved = cfg_obj_asuint32(obj);
+ if (files < 128U) /* Prevent underflow. */
+ reserved = 0;
+ else if (reserved > files - 128U) /* Mimimum UDP space. */
+ reserved = files - 128;
+ if (reserved < 128U) /* Mimimum TCP/stdio space. */
+ reserved = 128;
+ if (reserved + 128U > files) {
+ isc_log_write(ns_g_lctx, NS_LOGCATEGORY_GENERAL,
+ NS_LOGMODULE_SERVER, ISC_LOG_WARNING,
+ "less than 128 UDP sockets available after "
+ "applying 'reserved-sockets' and 'files'");
+ }
+ isc__socketmgr_setreserved(ns_g_socketmgr, reserved);
+
+ /*
* Configure various server options.
*/
configure_server_quota(maps, "transfers-out", &server->xfroutquota);
diff --git a/configure.in b/configure.in
index d4ea2bd2fe90..67ebe68e9a93 100644
--- a/configure.in
+++ b/configure.in
@@ -18,7 +18,7 @@ AC_DIVERT_PUSH(1)dnl
esyscmd([sed "s/^/# /" COPYRIGHT])dnl
AC_DIVERT_POP()dnl
-AC_REVISION($Revision: 1.294.2.23.2.82 $)
+AC_REVISION($Revision: 1.294.2.23.2.82.2.1 $)
AC_INIT(lib/dns/name.c)
AC_PREREQ(2.13)
@@ -1812,7 +1812,7 @@ case "$host" in
[*-solaris2.[89]])
hack_shutup_pthreadonceinit=yes
;;
- *-solaris2.10)
+ *-solaris2.1[0-9])
hack_shutup_pthreadonceinit=yes
;;
esac
diff --git a/doc/arm/Bv9ARM-book.xml b/doc/arm/Bv9ARM-book.xml
index 710cd36c1d1d..41837c6a9a1c 100644
--- a/doc/arm/Bv9ARM-book.xml
+++ b/doc/arm/Bv9ARM-book.xml
@@ -18,7 +18,7 @@
- PERFORMANCE OF THIS SOFTWARE.
-->
-<!-- File: $Id: Bv9ARM-book.xml,v 1.155.2.27.2.88.2.1 2008/05/22 21:11:14 each Exp $ -->
+<!-- File: $Id: Bv9ARM-book.xml,v 1.155.2.27.2.88.2.2 2008/07/23 12:03:52 marka Exp $ -->
<book>
<title>BIND 9 Administrator Reference Manual</title>
@@ -2878,6 +2878,7 @@ statement in the <filename>named.conf</filename> file:</para>
<optional> max-transfer-idle-in <replaceable>number</replaceable>; </optional>
<optional> max-transfer-idle-out <replaceable>number</replaceable>; </optional>
<optional> tcp-clients <replaceable>number</replaceable>; </optional>
+ <optional> reserved-sockets <replaceable>number</replaceable>; </optional>
<optional> recursive-clients <replaceable>number</replaceable>; </optional>
<optional> serial-query-rate <replaceable>number</replaceable>; </optional>
<optional> serial-queries <replaceable>number</replaceable>; </optional>
@@ -4072,6 +4073,23 @@ connections that the server will accept.
The default is <literal>100</literal>.</para>
</listitem></varlistentry>
+ <varlistentry>
+ <term><command>reserved-sockets</command></term>
+ <listitem>
+ <para>
+ The number of file descriptors reserved for TCP, stdio,
+ etc. This needs to be big enough to cover the number of
+ interfaces named listens on, tcp-clients as well as
+ to provide room for outgoing TCP queries and incoming zone
+ transfers. The default is <literal>512</literal>.
+ The minimum value is <literal>128</literal> and the
+ maximum value is <literal>128</literal> less than
+ 'files' or FD_SETSIZE (whichever is smaller). This
+ option may be removed in the future.
+ </para>
+ </listitem>
+ </varlistentry>
+
<varlistentry><term><command>max-cache-size</command></term>
<listitem><para>The maximum amount of memory to use for the
server's cache, in bytes. When the amount of data in the cache
diff --git a/lib/bind/configure.in b/lib/bind/configure.in
index 8cc91e8e8fd5..4b752f93f1e1 100644
--- a/lib/bind/configure.in
+++ b/lib/bind/configure.in
@@ -13,7 +13,7 @@
# OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
# PERFORMANCE OF THIS SOFTWARE.
-AC_REVISION($Revision: 1.83.2.5.2.38 $)
+AC_REVISION($Revision: 1.83.2.5.2.38.2.1 $)
AC_INIT(resolv/herror.c)
AC_PREREQ(2.13)
@@ -2590,7 +2590,7 @@ case "$host" in
*-solaris2.9)
hack_shutup_in6addr_init_macros=yes
;;
- *-solaris2.10)
+ *-solaris2.1[0-9])
hack_shutup_in6addr_init_macros=yes
;;
esac
diff --git a/lib/dns/api b/lib/dns/api
index 1b3fb8d5a269..efe79b507c4a 100644
--- a/lib/dns/api
+++ b/lib/dns/api
@@ -1,3 +1,3 @@
LIBINTERFACE = 25
-LIBREVISION = 0
+LIBREVISION = 1
LIBAGE = 0
diff --git a/lib/dns/dispatch.c b/lib/dns/dispatch.c
index 207432d5f357..02a2f188d08c 100644
--- a/lib/dns/dispatch.c
+++ b/lib/dns/dispatch.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2006, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2006-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: dispatch.c,v 1.101.2.6.2.21.4.1 2008/05/22 21:11:15 each Exp $ */
+/* $Id: dispatch.c,v 1.101.2.6.2.21.4.5 2008/07/23 23:16:26 marka Exp $ */
#include <config.h>
@@ -274,7 +274,26 @@ request_log(dns_dispatch_t *disp, dns_dispentry_t *resp,
}
/*
- * ARC4 random number generator obtained from OpenBSD
+ * ARC4 random number generator derived from OpenBSD.
+ * Only dispatch_arc4random() and dispatch_arc4uniformrandom() are expected
+ * to be called from general dispatch routines; the rest of them are subroutines
+ * for these two.
+ *
+ * The original copyright follows:
+ * Copyright (c) 1996, David Mazieres <dm@uun.org>
+ * Copyright (c) 2008, Damien Miller <djm@openbsd.org>
+ *
+ * Permission to use, copy, modify, and distribute this software for any
+ * purpose with or without fee is hereby granted, provided that the above
+ * copyright notice and this permission notice appear in all copies.
+ *
+ * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
+ * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
+ * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
+ * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
+ * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
+ * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
+ * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
static void
dispatch_arc4init(arc4ctx_t *actx) {
@@ -708,7 +727,7 @@ udp_recv(isc_task_t *task, isc_event_t *ev_in) {
isc_netaddr_fromsockaddr(&netaddr, &ev->address);
if (disp->mgr->blackhole != NULL &&
dns_acl_match(&netaddr, NULL, disp->mgr->blackhole,
- NULL, &match, NULL) == ISC_R_SUCCESS &&
+ NULL, &match, NULL) == ISC_R_SUCCESS &&
match > 0)
{
if (isc_log_wouldlog(dns_lctx, LVL(10))) {
@@ -761,7 +780,7 @@ udp_recv(isc_task_t *task, isc_event_t *ev_in) {
if (resp == NULL) {
free_buffer(disp, ev->region.base, ev->region.length);
goto unlock;
- }
+ }
/*
* Now that we have the original dispatch the query was sent
@@ -771,7 +790,7 @@ udp_recv(isc_task_t *task, isc_event_t *ev_in) {
if (disp != resp->disp) {
isc_sockaddr_t a1;
isc_sockaddr_t a2;
-
+
/*
* Check that the socket types and ports match.
*/
@@ -784,11 +803,11 @@ udp_recv(isc_task_t *task, isc_event_t *ev_in) {
/*
* If both dispatches are bound to an address then fail as
- * the addresses can't be equal (enforced by the IP stack).
+ * the addresses can't be equal (enforced by the IP stack).
*
* Note under Linux a packet can be sent out via IPv4 socket
* and the response be received via a IPv6 socket.
- *
+ *
* Requests sent out via IPv6 should always come back in
* via IPv6.
*/
@@ -909,7 +928,7 @@ tcp_recv(isc_task_t *task, isc_event_t *ev_in) {
switch (tcpmsg->result) {
case ISC_R_CANCELED:
break;
-
+
case ISC_R_EOF:
dispatch_log(disp, LVL(90), "shutting down on EOF");
do_cancel(disp);
@@ -1167,7 +1186,7 @@ destroy_mgr(dns_dispatchmgr_t **mgrp) {
static isc_result_t
create_socket(isc_socketmgr_t *mgr, isc_sockaddr_t *local,
- isc_socket_t **sockp)
+ unsigned int options, isc_socket_t **sockp)
{
isc_socket_t *sock;
isc_result_t result;
@@ -1181,7 +1200,7 @@ create_socket(isc_socketmgr_t *mgr, isc_sockaddr_t *local,
#ifndef ISC_ALLOW_MAPPED
isc_socket_ipv6only(sock, ISC_TRUE);
#endif
- result = isc_socket_bind(sock, local);
+ result = isc_socket_bind(sock, local, options);
if (result != ISC_R_SUCCESS) {
isc_socket_detach(&sock);
return (result);
@@ -1913,7 +1932,7 @@ dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
attributes &= ~DNS_DISPATCHATTR_RANDOMPORT;
goto getsocket;
}
- result = create_socket(sockmgr, &localaddr_bound, &sock);
+ result = create_socket(sockmgr, &localaddr_bound, 0, &sock);
if (result == ISC_R_ADDRINUSE) {
if (++k == 1024)
attributes &= ~DNS_DISPATCHATTR_RANDOMPORT;
@@ -1921,7 +1940,8 @@ dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
}
localport = prt;
} else
- result = create_socket(sockmgr, localaddr, &sock);
+ result = create_socket(sockmgr, localaddr,
+ ISC_SOCKET_REUSEADDRESS, &sock);
if (result != ISC_R_SUCCESS)
goto deallocate_dispatch;
if ((attributes & DNS_DISPATCHATTR_RANDOMPORT) == 0 &&
@@ -2410,7 +2430,7 @@ dns_dispatch_importrecv(dns_dispatch_t *disp, isc_event_t *event) {
newsevent->timestamp = sevent->timestamp;
newsevent->pktinfo = sevent->pktinfo;
newsevent->attributes = sevent->attributes;
-
+
isc_task_send(disp->task, ISC_EVENT_PTR(&newsevent));
}
diff --git a/lib/dns/include/dns/dispatch.h b/lib/dns/include/dns/dispatch.h
index 806ab880f3cc..e3495aaa361f 100644
--- a/lib/dns/include/dns/dispatch.h
+++ b/lib/dns/include/dns/dispatch.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2007, 2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: dispatch.h,v 1.45.2.2.4.5.4.1 2008/05/22 21:11:16 each Exp $ */
+/* $Id: dispatch.h,v 1.45.2.2.4.5.4.2 2008/07/23 07:28:11 tbox Exp $ */
#ifndef DNS_DISPATCH_H
#define DNS_DISPATCH_H 1
@@ -185,7 +185,7 @@ dns_dispatchmgr_getblackhole(dns_dispatchmgr_t *mgr);
void
dns_dispatchmgr_setblackportlist(dns_dispatchmgr_t *mgr,
- dns_portlist_t *portlist);
+ dns_portlist_t *portlist);
/*
* Sets a list of UDP ports that won't be used when creating a udp
* dispatch with a wildcard port.
@@ -365,7 +365,7 @@ dns_dispatch_removeresponse(dns_dispentry_t **resp,
* "resp" != NULL and "*resp" contain a value previously allocated
* by dns_dispatch_addresponse();
*
- * May only be called from within the task given as the 'task'
+ * May only be called from within the task given as the 'task'
* argument to dns_dispatch_addresponse() when allocating '*resp'.
*/
@@ -382,7 +382,7 @@ dns_dispatch_getsocket(dns_dispatch_t *disp);
* The socket the dispatcher is using.
*/
-isc_result_t
+isc_result_t
dns_dispatch_getlocaladdress(dns_dispatch_t *disp, isc_sockaddr_t *addrp);
/*
* Return the local address for this dispatch.
@@ -393,7 +393,7 @@ dns_dispatch_getlocaladdress(dns_dispatch_t *disp, isc_sockaddr_t *addrp);
* addrp to be non null.
*
* Returns:
- * ISC_R_SUCCESS
+ * ISC_R_SUCCESS
* ISC_R_NOTIMPLEMENTED
*/
@@ -417,7 +417,7 @@ dns_dispatch_changeattributes(dns_dispatch_t *disp,
*
* new = (old & ~mask) | (attributes & mask)
*
- * This function has a side effect when DNS_DISPATCHATTR_NOLISTEN changes.
+ * This function has a side effect when DNS_DISPATCHATTR_NOLISTEN changes.
* When the flag becomes off, the dispatch will start receiving on the
* corresponding socket. When the flag becomes on, receive events on the
* corresponding socket will be canceled.
diff --git a/lib/dns/message.c b/lib/dns/message.c
index e16bb385af1f..915f58787154 100644
--- a/lib/dns/message.c
+++ b/lib/dns/message.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: message.c,v 1.194.2.10.2.28 2007/08/28 07:19:13 tbox Exp $ */
+/* $Id: message.c,v 1.194.2.10.2.28.4.2 2008/07/28 23:47:49 tbox Exp $ */
/***
*** Imports
@@ -590,6 +590,9 @@ msgreset(dns_message_t *msg, isc_boolean_t everything) {
msg->tsigkey = NULL;
}
+ if (msg->tsigctx != NULL)
+ dst_context_destroy(&msg->tsigctx);
+
if (msg->query.base != NULL) {
if (msg->free_query != 0)
isc_mem_put(msg->mctx, msg->query.base,
@@ -985,7 +988,7 @@ getquestions(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx,
if (name == NULL)
return (ISC_R_NOMEMORY);
free_name = ISC_TRUE;
-
+
offsets = newoffsets(msg);
if (offsets == NULL) {
result = ISC_R_NOMEMORY;
@@ -1295,7 +1298,7 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx,
}
/*
* When the rdata is empty, the data pointer is
- * never dereferenced, but it must still be non-NULL.
+ * never dereferenced, but it must still be non-NULL.
* Casting 1 rather than "" avoids warnings about
* discarding the const attribute of a string,
* for compilers that would warn about such things.
@@ -1434,7 +1437,7 @@ getsection(isc_buffer_t *source, dns_message_t *msg, dns_decompress_t *dctx,
rdataset)
== ISC_R_SUCCESS);
- if (rdtype != dns_rdatatype_opt &&
+ if (rdtype != dns_rdatatype_opt &&
rdtype != dns_rdatatype_tsig &&
!issigzero)
{
diff --git a/lib/dns/request.c b/lib/dns/request.c
index 69841e5e710c..6fe7b114ab04 100644
--- a/lib/dns/request.c
+++ b/lib/dns/request.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2006, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2006-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 2000-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: request.c,v 1.64.2.1.10.12 2007/08/28 07:19:13 tbox Exp $ */
+/* $Id: request.c,v 1.64.2.1.10.12.4.2 2008/07/23 07:28:11 tbox Exp $ */
#include <config.h>
@@ -516,11 +516,11 @@ create_tcp_dispatch(dns_requestmgr_t *requestmgr, isc_sockaddr_t *srcaddr,
if (srcaddr == NULL) {
isc_sockaddr_anyofpf(&bind_any,
isc_sockaddr_pf(destaddr));
- result = isc_socket_bind(socket, &bind_any);
+ result = isc_socket_bind(socket, &bind_any, 0);
} else {
src = *srcaddr;
isc_sockaddr_setport(&src, 0);
- result = isc_socket_bind(socket, &src);
+ result = isc_socket_bind(socket, &src, 0);
}
if (result != ISC_R_SUCCESS)
goto cleanup;
@@ -683,7 +683,7 @@ dns_request_createraw3(dns_requestmgr_t *requestmgr, isc_buffer_t *msgbuf,
REQUIRE(action != NULL);
REQUIRE(requestp != NULL && *requestp == NULL);
REQUIRE(timeout > 0);
- if (srcaddr != NULL)
+ if (srcaddr != NULL)
REQUIRE(isc_sockaddr_pf(srcaddr) == isc_sockaddr_pf(destaddr));
mctx = requestmgr->mctx;
@@ -731,7 +731,7 @@ dns_request_createraw3(dns_requestmgr_t *requestmgr, isc_buffer_t *msgbuf,
result = DNS_R_FORMERR;
goto cleanup;
}
-
+
if ((options & DNS_REQUESTOPT_TCP) != 0 || r.length > 512)
tcp = ISC_TRUE;
@@ -855,7 +855,7 @@ dns_request_createvia2(dns_requestmgr_t *requestmgr, dns_message_t *message,
udpretries, task, action, arg,
requestp));
}
-
+
isc_result_t
dns_request_createvia3(dns_requestmgr_t *requestmgr, dns_message_t *message,
isc_sockaddr_t *srcaddr, isc_sockaddr_t *destaddr,
@@ -881,7 +881,7 @@ dns_request_createvia3(dns_requestmgr_t *requestmgr, dns_message_t *message,
REQUIRE(action != NULL);
REQUIRE(requestp != NULL && *requestp == NULL);
REQUIRE(timeout > 0);
- if (srcaddr != NULL)
+ if (srcaddr != NULL)
REQUIRE(isc_sockaddr_pf(srcaddr) == isc_sockaddr_pf(destaddr));
mctx = requestmgr->mctx;
@@ -1135,7 +1135,7 @@ do_cancel(isc_task_t *task, isc_event_t *event) {
if (!DNS_REQUEST_CANCELED(request))
req_cancel(request);
send_if_done(request, ISC_R_CANCELED);
- UNLOCK(&request->requestmgr->locks[request->hash]);
+ UNLOCK(&request->requestmgr->locks[request->hash]);
}
void
diff --git a/lib/dns/resolver.c b/lib/dns/resolver.c
index 93f10f5dd3e3..602dcf5f9632 100644
--- a/lib/dns/resolver.c
+++ b/lib/dns/resolver.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: resolver.c,v 1.218.2.18.4.77.2.1 2008/05/22 21:11:15 each Exp $ */
+/* $Id: resolver.c,v 1.218.2.18.4.77.2.3 2008/07/24 05:00:46 jinmei Exp $ */
#include <config.h>
@@ -1061,7 +1061,7 @@ fctx_query(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo,
goto cleanup_query;
#ifndef BROKEN_TCP_BIND_BEFORE_CONNECT
- result = isc_socket_bind(query->tcpsocket, &addr);
+ result = isc_socket_bind(query->tcpsocket, &addr, 0);
if (result != ISC_R_SUCCESS)
goto cleanup_socket;
#endif
@@ -2516,6 +2516,8 @@ fctx_destroy(fetchctx_t *fctx) {
static void
fctx_timeout(isc_task_t *task, isc_event_t *event) {
fetchctx_t *fctx = event->ev_arg;
+ isc_timerevent_t *tevent = (isc_timerevent_t *)event;
+ resquery_t *query;
REQUIRE(VALID_FCTX(fctx));
@@ -2531,8 +2533,18 @@ fctx_timeout(isc_task_t *task, isc_event_t *event) {
fctx->timeouts++;
/*
* We could cancel the running queries here, or we could let
- * them keep going. Right now we choose the latter...
+ * them keep going. Since we normally use separate sockets for
+ * different queries, we adopt the former approach to reduce
+ * the number of open sockets: cancel the oldest query if it
+ * expired after the query had started (this is usually the
+ * case but is not always so, depending on the task schedule
+ * timing).
*/
+ query = ISC_LIST_HEAD(fctx->queries);
+ if (query != NULL &&
+ isc_time_compare(&tevent->due, &query->start) >= 0) {
+ fctx_cancelquery(&query, NULL, NULL, ISC_TRUE);
+ }
fctx->attributes &= ~FCTX_ATTR_ADDRWAIT;
/*
* Our timer has triggered. Reestablish the fctx lifetime
diff --git a/lib/dns/xfrin.c b/lib/dns/xfrin.c
index 432569a4e40d..0e7a487b1057 100644
--- a/lib/dns/xfrin.c
+++ b/lib/dns/xfrin.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1999-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: xfrin.c,v 1.124.2.4.2.21 2007/10/31 01:59:03 marka Exp $ */
+/* $Id: xfrin.c,v 1.124.2.4.2.21.4.5 2008/07/28 23:47:49 tbox Exp $ */
#include <config.h>
@@ -246,7 +246,7 @@ static isc_result_t
axfr_init(dns_xfrin_ctx_t *xfr) {
isc_result_t result;
- xfr->is_ixfr = ISC_FALSE;
+ xfr->is_ixfr = ISC_FALSE;
if (xfr->db != NULL)
dns_db_detach(&xfr->db);
@@ -857,7 +857,8 @@ xfrin_start(dns_xfrin_ctx_t *xfr) {
isc_sockettype_tcp,
&xfr->socket));
#ifndef BROKEN_TCP_BIND_BEFORE_CONNECT
- CHECK(isc_socket_bind(xfr->socket, &xfr->sourceaddr));
+ CHECK(isc_socket_bind(xfr->socket, &xfr->sourceaddr,
+ ISC_SOCKET_REUSEADDRESS));
#endif
CHECK(isc_socket_connect(xfr->socket, &xfr->masteraddr, xfr->task,
xfrin_connect_done, xfr));
@@ -886,8 +887,8 @@ render(dns_message_t *msg, isc_mem_t *mctx, isc_buffer_t *buf) {
CHECK(dns_message_renderend(msg));
result = ISC_R_SUCCESS;
failure:
- if (cleanup_cctx)
- dns_compress_invalidate(&cctx);
+ if (cleanup_cctx)
+ dns_compress_invalidate(&cctx);
return (result);
}
@@ -1045,6 +1046,8 @@ xfrin_send_request(dns_xfrin_ctx_t *xfr) {
xfr->id++;
xfr->nmsg = 0;
msg->id = xfr->id;
+ if (xfr->tsigctx != NULL)
+ dst_context_destroy(&xfr->tsigctx);
CHECK(render(msg, xfr->mctx, &xfr->qbuffer));
@@ -1180,7 +1183,10 @@ xfrin_recv_done(isc_task_t *task, isc_event_t *ev) {
CHECK(dns_message_settsigkey(msg, xfr->tsigkey));
CHECK(dns_message_setquerytsig(msg, xfr->lasttsig));
+
msg->tsigctx = xfr->tsigctx;
+ xfr->tsigctx = NULL;
+
if (xfr->nmsg > 0)
msg->tcp_continuation = 1;
@@ -1293,9 +1299,11 @@ xfrin_recv_done(isc_task_t *task, isc_event_t *ev) {
xfr->nmsg++;
/*
- * Copy the context back.
+ * Take the context back.
*/
+ INSIST(xfr->tsigctx == NULL);
xfr->tsigctx = msg->tsigctx;
+ msg->tsigctx = NULL;
dns_message_destroy(&msg);
@@ -1391,6 +1399,9 @@ maybe_free(dns_xfrin_ctx_t *xfr) {
if (xfr->tcpmsg_valid)
dns_tcpmsg_invalidate(&xfr->tcpmsg);
+ if (xfr->tsigctx != NULL)
+ dst_context_destroy(&xfr->tsigctx);
+
if ((xfr->name.attributes & DNS_NAMEATTR_DYNAMIC) != 0)
dns_name_free(&xfr->name, xfr->mctx);
diff --git a/lib/isc/api b/lib/isc/api
index f94ca40025ec..a8be9070823b 100644
--- a/lib/isc/api
+++ b/lib/isc/api
@@ -1,3 +1,3 @@
-LIBINTERFACE = 12
-LIBREVISION = 3
-LIBAGE = 1
+LIBINTERFACE = 14
+LIBREVISION = 0
+LIBAGE = 0
diff --git a/lib/isc/include/isc/resource.h b/lib/isc/include/isc/resource.h
index 2c2a82981c56..1d4cb3023a4a 100644
--- a/lib/isc/include/isc/resource.h
+++ b/lib/isc/include/isc/resource.h
@@ -1,8 +1,8 @@
/*
- * Copyright (C) 2004 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 2000, 2001 Internet Software Consortium.
*
- * Permission to use, copy, modify, and distribute this software for any
+ * Permission to use, copy, modify, and/or distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: resource.h,v 1.4.206.1 2004/03/06 08:14:47 marka Exp $ */
+/* $Id: resource.h,v 1.4.206.1.34.2 2008/07/23 23:47:49 tbox Exp $ */
#ifndef ISC_RESOURCE_H
#define ISC_RESOURCE_H 1
@@ -79,6 +79,19 @@ isc_resource_getlimit(isc_resource_t resource, isc_resourcevalue_t *value);
* ISC_R_NOTIMPLEMENTED 'resource' is not a type known by the OS.
*/
+isc_result_t
+isc_resource_curlimit(isc_resource_t resource, isc_resourcevalue_t *value);
+/*
+ * Get the current limit on a resource.
+ *
+ * Requires:
+ * 'resource' is a valid member of the isc_resource_t enumeration.
+ *
+ * Returns:
+ * ISC_R_SUCCESS Success.
+ * ISC_R_NOTIMPLEMENTED 'resource' is not a type known by the OS.
+ */
+
ISC_LANG_ENDDECLS
#endif /* ISC_RESOURCE_H */
diff --git a/lib/isc/include/isc/socket.h b/lib/isc/include/isc/socket.h
index 324a61a19e46..0537a0d6693b 100644
--- a/lib/isc/include/isc/socket.h
+++ b/lib/isc/include/isc/socket.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2007, 2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1998-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: socket.h,v 1.54.12.7 2007/08/28 07:19:15 tbox Exp $ */
+/* $Id: socket.h,v 1.54.12.7.4.4 2008/07/23 23:16:27 marka Exp $ */
#ifndef ISC_SOCKET_H
#define ISC_SOCKET_H 1
@@ -81,6 +81,12 @@ ISC_LANG_BEGINDECLS
*/
#define ISC_SOCKET_MAXSCATTERGATHER 8
+/*%
+ * In isc_socket_bind() set socket option SO_REUSEADDR prior to calling
+ * bind() if a non zero port is specified (AF_INET and AF_INET6).
+ */
+#define ISC_SOCKET_REUSEADDRESS 0x01U
+
/***
*** Types
***/
@@ -306,7 +312,8 @@ isc_socket_detach(isc_socket_t **socketp);
*/
isc_result_t
-isc_socket_bind(isc_socket_t *sock, isc_sockaddr_t *addressp);
+isc_socket_bind(isc_socket_t *sock, isc_sockaddr_t *addressp,
+ unsigned int reuseaddr);
/*
* Bind 'socket' to '*addressp'.
*
@@ -699,6 +706,12 @@ isc_socket_ipv6only(isc_socket_t *sock, isc_boolean_t yes);
* 'sock' is a valid socket.
*/
+void
+isc__socketmgr_setreserved(isc_socketmgr_t *mgr, isc_uint32_t);
+/*%<
+ * Temporary. For use by named only.
+ */
+
ISC_LANG_ENDDECLS
#endif /* ISC_SOCKET_H */
diff --git a/lib/isc/include/isc/timer.h b/lib/isc/include/isc/timer.h
index 3e8d3d593524..9d4cc00000a8 100644
--- a/lib/isc/include/isc/timer.h
+++ b/lib/isc/include/isc/timer.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004, 2005, 2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004, 2005, 2007, 2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1998-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: timer.h,v 1.28.12.9 2007/08/28 07:19:15 tbox Exp $ */
+/* $Id: timer.h,v 1.28.12.9.4.2 2008/07/24 23:47:44 tbox Exp $ */
#ifndef ISC_TIMER_H
#define ISC_TIMER_H 1
@@ -80,6 +80,7 @@
#include <isc/event.h>
#include <isc/eventclass.h>
#include <isc/lang.h>
+#include <isc/time.h>
ISC_LANG_BEGINDECLS
@@ -96,6 +97,7 @@ typedef enum {
typedef struct isc_timerevent {
struct isc_event common;
+ isc_time_t due;
} isc_timerevent_t;
#define ISC_TIMEREVENT_FIRSTEVENT (ISC_EVENTCLASS_TIMER + 0)
diff --git a/lib/isc/timer.c b/lib/isc/timer.c
index d002b11722ce..990f2943cd6c 100644
--- a/lib/isc/timer.c
+++ b/lib/isc/timer.c
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2004-2007 Internet Systems Consortium, Inc. ("ISC")
+ * Copyright (C) 2004-2008 Internet Systems Consortium, Inc. ("ISC")
* Copyright (C) 1998-2003 Internet Software Consortium.
*
* Permission to use, copy, modify, and/or distribute this software for any
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: timer.c,v 1.64.12.17 2007/10/24 01:08:01 marka Exp $ */
+/* $Id: timer.c,v 1.64.12.17.4.3 2008/07/29 18:34:29 jinmei Exp $ */
#include <config.h>
@@ -223,7 +223,7 @@ schedule(isc_timer_t *timer, isc_time_t *now, isc_boolean_t signal_ok) {
"*** POKED TIMER ***");
}
}
-
+
if (timer->index == 1 && signal_ok) {
XTRACE(isc_msgcat_get(isc_msgcat, ISC_MSGSET_TIMER,
ISC_MSG_SIGNALSCHED,
@@ -578,7 +578,7 @@ isc_timer_detach(isc_timer_t **timerp) {
static void
dispatch(isc_timermgr_t *manager, isc_time_t *now) {
isc_boolean_t done = ISC_FALSE, post_event, need_schedule;
- isc_event_t *event;
+ isc_timerevent_t *event;
isc_eventtype_t type = 0;
isc_timer_t *timer;
isc_result_t result;
@@ -651,16 +651,18 @@ dispatch(isc_timermgr_t *manager, isc_time_t *now) {
/*
* XXX We could preallocate this event.
*/
- event = isc_event_allocate(manager->mctx,
+ event = (isc_timerevent_t *)isc_event_allocate(manager->mctx,
timer,
type,
timer->action,
timer->arg,
sizeof(*event));
- if (event != NULL)
- isc_task_send(timer->task, &event);
- else
+ if (event != NULL) {
+ event->due = timer->due;
+ isc_task_send(timer->task,
+ ISC_EVENT_PTR(&event));
+ } else
UNEXPECTED_ERROR(__FILE__, __LINE__,
isc_msgcat_get(isc_msgcat,
ISC_MSGSET_TIMER,
diff --git a/lib/isc/unix/app.c b/lib/isc/unix/app.c
index 8e1f0fafd306..382e445ead5c 100644
--- a/lib/isc/unix/app.c
+++ b/lib/isc/unix/app.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: app.c,v 1.43.2.3.8.8 2008/01/17 23:45:28 tbox Exp $ */
+/* $Id: app.c,v 1.43.2.3.8.8.4.1 2008/07/29 04:43:57 each Exp $ */
#include <config.h>
@@ -301,7 +301,7 @@ evloop() {
int n;
isc_time_t when, now;
struct timeval tv, *tvp;
- fd_set readfds, writefds;
+ fd_set *readfds, *writefds;
int maxfd;
isc_boolean_t readytasks;
isc_boolean_t call_timer_dispatch = ISC_FALSE;
@@ -330,7 +330,7 @@ evloop() {
}
isc__socketmgr_getfdsets(&readfds, &writefds, &maxfd);
- n = select(maxfd, &readfds, &writefds, NULL, tvp);
+ n = select(maxfd, readfds, writefds, NULL, tvp);
if (n == 0 || call_timer_dispatch) {
/*
@@ -350,7 +350,7 @@ evloop() {
isc__timermgr_dispatch();
}
if (n > 0)
- (void)isc__socketmgr_dispatch(&readfds, &writefds,
+ (void)isc__socketmgr_dispatch(readfds, writefds,
maxfd);
(void)isc__taskmgr_dispatch();
diff --git a/lib/isc/unix/resource.c b/lib/isc/unix/resource.c
index bfec43d32d45..a6280b7477e8 100644
--- a/lib/isc/unix/resource.c
+++ b/lib/isc/unix/resource.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: resource.c,v 1.11.206.3 2008/01/26 23:45:31 tbox Exp $ */
+/* $Id: resource.c,v 1.11.206.3.4.3 2008/07/28 22:45:53 marka Exp $ */
#include <config.h>
@@ -28,6 +28,14 @@
#include <isc/result.h>
#include <isc/util.h>
+#ifdef __linux__
+#include <linux/fs.h> /* To get the large NR_OPEN. */
+#endif
+
+#ifdef __hpux
+#include <sys/dyntune.h>
+#endif
+
#include "errno2result.h"
static isc_result_t
@@ -151,7 +159,36 @@ isc_resource_setlimit(isc_resource_t resource, isc_resourcevalue_t value) {
if (unixresult == 0)
return (ISC_R_SUCCESS);
}
+#elif defined(NR_OPEN) && defined(__linux__)
+ /*
+ * Some Linux kernels don't accept RLIM_INFINIT; the maximum
+ * possible value is the NR_OPEN defined in linux/fs.h.
+ */
+ if (resource == isc_resource_openfiles && rlim_value == RLIM_INFINITY) {
+ rl.rlim_cur = rl.rlim_max = NR_OPEN;
+ unixresult = setrlimit(unixresource, &rl);
+ if (unixresult == 0)
+ return (ISC_R_SUCCESS);
+ }
+#elif defined(__hpux)
+ if (resource == isc_resource_openfiles && rlim_value == RLIM_INFINITY) {
+ uint64_t maxfiles;
+ if (gettune("maxfiles_lim", &maxfiles) == 0) {
+ rl.rlim_cur = rl.rlim_max = maxfiles;
+ unixresult = setrlimit(unixresource, &rl);
+ if (unixresult == 0)
+ return (ISC_R_SUCCESS);
+ }
+ }
#endif
+ if (resource == isc_resource_openfiles && rlim_value == RLIM_INFINITY) {
+ if (getrlimit(unixresource, &rl) == 0) {
+ rl.rlim_cur = rl.rlim_max;
+ unixresult = setrlimit(unixresource, &rl);
+ if (unixresult == 0)
+ return (ISC_R_SUCCESS);
+ }
+ }
return (isc__errno2result(errno));
}
@@ -171,3 +208,20 @@ isc_resource_getlimit(isc_resource_t resource, isc_resourcevalue_t *value) {
return (result);
}
+
+isc_result_t
+isc_resource_curlimit(isc_resource_t resource, isc_resourcevalue_t *value) {
+ int unixresult;
+ int unixresource;
+ struct rlimit rl;
+ isc_result_t result;
+
+ result = resource2rlim(resource, &unixresource);
+ if (result == ISC_R_SUCCESS) {
+ unixresult = getrlimit(unixresource, &rl);
+ INSIST(unixresult == 0);
+ *value = rl.rlim_cur;
+ }
+
+ return (result);
+}
diff --git a/lib/isc/unix/socket.c b/lib/isc/unix/socket.c
index 7322abc2518e..3ee796c24bba 100644
--- a/lib/isc/unix/socket.c
+++ b/lib/isc/unix/socket.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: socket.c,v 1.207.2.19.2.35 2008/01/27 02:06:07 marka Exp $ */
+/* $Id: socket.c,v 1.207.2.19.2.35.4.6 2008/07/29 04:43:57 each Exp $ */
#include <config.h>
@@ -62,7 +62,35 @@
#include <sys/utsname.h>
#endif
-/*
+/*%
+ * Max number of open sockets. In the vast majority of cases the default size
+ * of FD_SETSIZE should be fine, and this constant should be increased only
+ * when absolutely necessary and possible, i.e., the server is exhausting all
+ * available file descriptors (up to FD_SETSIZE) and the select() function
+ * and FD_xxx macros support larger values than FD_SETSIZE (which may not
+ * always by true, but we keep using some of them to ensure as much
+ * portability as possible). Note also that overall server performance
+ * may be rather worsened with a larger value of this constant due to
+ * inherent scalability problems of select().
+ *
+ * As a special note, this value shouldn't have to be touched if
+ * this is a build for an authoritative only DNS server.
+ */
+
+#ifndef ISC_SOCKET_FDSETSIZE
+#define ISC_SOCKET_FDSETSIZE FD_SETSIZE
+#endif
+
+/*%
+ * Mac OS X needs a special definition to support larger values in select()
+ */
+#if ISC_SOCKET_FDSETSIZE > FD_SETSIZE
+#ifdef __APPLE__
+#define _DARWIN_UNLIMITED_SELECT
+#endif /* __APPLE__ */
+#endif
+
+/*%
* Some systems define the socket length argument as an int, some as size_t,
* some as socklen_t. This is here so it can be easily changed if needed.
*/
@@ -190,13 +218,18 @@ struct isc_socketmgr {
unsigned int magic;
isc_mem_t *mctx;
isc_mutex_t lock;
+ int fd_bufsize;
+ int fdsize;
/* Locked by manager lock. */
ISC_LIST(isc_socket_t) socklist;
- fd_set read_fds;
- fd_set write_fds;
- isc_socket_t *fds[FD_SETSIZE];
- int fdstate[FD_SETSIZE];
+ fd_set *read_fds;
+ fd_set *read_fds_copy;
+ fd_set *write_fds;
+ fd_set *write_fds_copy;
+ isc_socket_t **fds;
+ int *fdstate;
int maxfd;
+ int reserved; /* unlocked */
#ifdef ISC_PLATFORM_USETHREADS
isc_thread_t watcher;
isc_condition_t shutdown_ok;
@@ -239,6 +272,8 @@ static void build_msghdr_send(isc_socket_t *, isc_socketevent_t *,
struct msghdr *, struct iovec *, size_t *);
static void build_msghdr_recv(isc_socket_t *, isc_socketevent_t *,
struct msghdr *, struct iovec *, size_t *);
+static void cleanup_fdsets(isc_socketmgr_t *, isc_mem_t *);
+static isc_result_t create_fdsets(isc_socketmgr_t *, isc_mem_t *);
#define SELECT_POKE_SHUTDOWN (-1)
#define SELECT_POKE_NOTHING (-2)
@@ -317,12 +352,12 @@ wakeup_socket(isc_socketmgr_t *manager, int fd, int msg) {
* or writes.
*/
- INSIST(fd >= 0 && fd < (int)FD_SETSIZE);
+ INSIST(fd >= 0 && fd < manager->fdsize);
if (manager->fdstate[fd] == CLOSE_PENDING) {
manager->fdstate[fd] = CLOSED;
- FD_CLR(fd, &manager->read_fds);
- FD_CLR(fd, &manager->write_fds);
+ FD_CLR(fd, manager->read_fds);
+ FD_CLR(fd, manager->write_fds);
(void)close(fd);
return;
}
@@ -335,9 +370,9 @@ wakeup_socket(isc_socketmgr_t *manager, int fd, int msg) {
* Set requested bit.
*/
if (msg == SELECT_POKE_READ)
- FD_SET(sock->fd, &manager->read_fds);
+ FD_SET(sock->fd, manager->read_fds);
if (msg == SELECT_POKE_WRITE)
- FD_SET(sock->fd, &manager->write_fds);
+ FD_SET(sock->fd, manager->write_fds);
}
#ifdef ISC_PLATFORM_USETHREADS
@@ -1198,7 +1233,7 @@ destroy(isc_socket_t **sockp) {
INSIST(ISC_LIST_EMPTY(sock->recv_list));
INSIST(ISC_LIST_EMPTY(sock->send_list));
INSIST(sock->connect_ev == NULL);
- REQUIRE(sock->fd >= 0 && sock->fd < (int)FD_SETSIZE);
+ REQUIRE(sock->fd >= 0 && sock->fd < (int)manager->fdsize);
LOCK(&manager->lock);
@@ -1452,9 +1487,18 @@ isc_socket_create(isc_socketmgr_t *manager, int pf, isc_sockettype_t type,
#ifdef F_DUPFD
/*
- * Leave a space for stdio to work in.
+ * Leave a space for stdio and TCP to work in.
*/
- if (sock->fd >= 0 && sock->fd < 20) {
+ if (manager->reserved != 0 && type == isc_sockettype_udp &&
+ sock->fd >= 0 && sock->fd < manager->reserved) {
+ int new, tmp;
+ new = fcntl(sock->fd, F_DUPFD, manager->reserved);
+ tmp = errno;
+ (void)close(sock->fd);
+ errno = tmp;
+ sock->fd = new;
+ err = "isc_socket_create: fcntl/reserved";
+ } else if (sock->fd >= 0 && sock->fd < 20) {
int new, tmp;
new = fcntl(sock->fd, F_DUPFD, 20);
tmp = errno;
@@ -1465,7 +1509,7 @@ isc_socket_create(isc_socketmgr_t *manager, int pf, isc_sockettype_t type,
}
#endif
- if (sock->fd >= (int)FD_SETSIZE) {
+ if (sock->fd >= (int)manager->fdsize) {
(void)close(sock->fd);
isc_log_iwrite(isc_lctx, ISC_LOGCATEGORY_GENERAL,
ISC_LOGMODULE_SOCKET, ISC_LOG_ERROR,
@@ -1929,7 +1973,7 @@ internal_accept(isc_task_t *me, isc_event_t *ev) {
(void)close(fd);
errno = tmp;
fd = new;
- err = "fcntl";
+ err = "accept/fcntl";
}
#endif
@@ -1937,8 +1981,17 @@ internal_accept(isc_task_t *me, isc_event_t *ev) {
if (SOFT_ERROR(errno))
goto soft_error;
switch (errno) {
- case ENOBUFS:
case ENFILE:
+ case EMFILE:
+ isc_log_iwrite(isc_lctx, ISC_LOGCATEGORY_GENERAL,
+ ISC_LOGMODULE_SOCKET, ISC_LOG_ERROR,
+ isc_msgcat, ISC_MSGSET_SOCKET,
+ ISC_MSG_TOOMANYFDS,
+ "%s: too many open file descriptors",
+ err);
+ goto soft_error;
+
+ case ENOBUFS:
case ENOMEM:
case ECONNRESET:
case ECONNABORTED:
@@ -1988,7 +2041,7 @@ internal_accept(isc_task_t *me, isc_event_t *ev) {
sock->pf);
(void)close(fd);
goto soft_error;
- } else if (fd >= (int)FD_SETSIZE) {
+ } else if (fd >= (int)manager->fdsize) {
isc_log_iwrite(isc_lctx, ISC_LOGCATEGORY_GENERAL,
ISC_LOGMODULE_SOCKET, ISC_LOG_ERROR,
isc_msgcat, ISC_MSGSET_SOCKET,
@@ -2200,7 +2253,7 @@ process_fds(isc_socketmgr_t *manager, int maxfd,
isc_socket_t *sock;
isc_boolean_t unlock_sock;
- REQUIRE(maxfd <= (int)FD_SETSIZE);
+ REQUIRE(maxfd <= (int)manager->fdsize);
/*
* Process read/writes on other fds here. Avoid locking
@@ -2214,8 +2267,8 @@ process_fds(isc_socketmgr_t *manager, int maxfd,
if (manager->fdstate[i] == CLOSE_PENDING) {
manager->fdstate[i] = CLOSED;
- FD_CLR(i, &manager->read_fds);
- FD_CLR(i, &manager->write_fds);
+ FD_CLR(i, manager->read_fds);
+ FD_CLR(i, manager->write_fds);
(void)close(i);
@@ -2226,7 +2279,7 @@ process_fds(isc_socketmgr_t *manager, int maxfd,
unlock_sock = ISC_FALSE;
if (FD_ISSET(i, readfds)) {
if (sock == NULL) {
- FD_CLR(i, &manager->read_fds);
+ FD_CLR(i, manager->read_fds);
goto check_write;
}
unlock_sock = ISC_TRUE;
@@ -2237,12 +2290,12 @@ process_fds(isc_socketmgr_t *manager, int maxfd,
else
dispatch_recv(sock);
}
- FD_CLR(i, &manager->read_fds);
+ FD_CLR(i, manager->read_fds);
}
check_write:
if (FD_ISSET(i, writefds)) {
if (sock == NULL) {
- FD_CLR(i, &manager->write_fds);
+ FD_CLR(i, manager->write_fds);
continue;
}
if (!unlock_sock) {
@@ -2255,7 +2308,7 @@ process_fds(isc_socketmgr_t *manager, int maxfd,
else
dispatch_send(sock);
}
- FD_CLR(i, &manager->write_fds);
+ FD_CLR(i, manager->write_fds);
}
if (unlock_sock)
UNLOCK(&sock->lock);
@@ -2276,8 +2329,6 @@ watcher(void *uap) {
isc_boolean_t done;
int ctlfd;
int cc;
- fd_set readfds;
- fd_set writefds;
int msg, fd;
int maxfd;
char strbuf[ISC_STRERRORSIZE];
@@ -2291,13 +2342,16 @@ watcher(void *uap) {
done = ISC_FALSE;
while (!done) {
do {
- readfds = manager->read_fds;
- writefds = manager->write_fds;
+ memcpy(manager->read_fds_copy, manager->read_fds,
+ manager->fd_bufsize);
+ memcpy(manager->write_fds_copy, manager->write_fds,
+ manager->fd_bufsize);
maxfd = manager->maxfd + 1;
UNLOCK(&manager->lock);
- cc = select(maxfd, &readfds, &writefds, NULL, NULL);
+ cc = select(maxfd, manager->read_fds_copy,
+ manager->write_fds_copy, NULL, NULL);
if (cc < 0) {
if (!SOFT_ERROR(errno)) {
isc__strerror(errno, strbuf,
@@ -2319,7 +2373,7 @@ watcher(void *uap) {
/*
* Process reads on internal, control fd.
*/
- if (FD_ISSET(ctlfd, &readfds)) {
+ if (FD_ISSET(ctlfd, manager->read_fds_copy)) {
for (;;) {
select_readmsg(manager, &fd, &msg);
@@ -2358,7 +2412,8 @@ watcher(void *uap) {
}
}
- process_fds(manager, maxfd, &readfds, &writefds);
+ process_fds(manager, maxfd, manager->read_fds_copy,
+ manager->write_fds_copy);
}
manager_log(manager, TRACE,
@@ -2370,6 +2425,88 @@ watcher(void *uap) {
}
#endif /* ISC_PLATFORM_USETHREADS */
+void
+isc__socketmgr_setreserved(isc_socketmgr_t *manager, isc_uint32_t reserved) {
+
+ REQUIRE(VALID_MANAGER(manager));
+
+ manager->reserved = reserved;
+}
+
+/*
+ * Initialize fdsets in socketmgr structure.
+ */
+static isc_result_t
+create_fdsets(isc_socketmgr_t *manager, isc_mem_t *mctx) {
+#if ISC_SOCKET_FDSETSIZE > FD_SETSIZE
+ manager->fdsize = ISC_SOCKET_FDSETSIZE;
+ manager->fd_bufsize = howmany(ISC_SOCKET_FDSETSIZE, NFDBITS) *
+ sizeof(fd_mask);
+#else
+ manager->fdsize = FD_SETSIZE;
+ manager->fd_bufsize = sizeof(fd_set);
+#endif
+
+ manager->fds = NULL;
+ manager->fdstate = NULL;
+ manager->read_fds = NULL;
+ manager->read_fds_copy = NULL;
+ manager->write_fds = NULL;
+ manager->write_fds_copy = NULL;
+
+ manager->fds = isc_mem_get(mctx,
+ manager->fdsize * sizeof(manager->fds[0]));
+ if (manager->fds == NULL)
+ goto fail;
+
+ manager->fdstate = isc_mem_get(mctx, manager->fdsize *
+ sizeof(manager->fdstate[0]));
+ if (manager->fdstate == NULL)
+ goto fail;
+
+ manager->read_fds = isc_mem_get(mctx, manager->fd_bufsize);
+ if (manager->read_fds == NULL)
+ goto fail;
+ manager->read_fds_copy = isc_mem_get(mctx, manager->fd_bufsize);
+ if (manager->read_fds_copy == NULL)
+ goto fail;
+ manager->write_fds = isc_mem_get(mctx, manager->fd_bufsize);
+ if (manager->write_fds == NULL)
+ goto fail;
+ manager->write_fds_copy = isc_mem_get(mctx, manager->fd_bufsize);
+ if (manager->write_fds_copy == NULL)
+ goto fail;
+
+ return (ISC_R_SUCCESS);
+
+ fail:
+ cleanup_fdsets(manager, mctx);
+ return (ISC_R_NOMEMORY);
+}
+
+/*
+ * Clean up fdsets in socketmgr structure.
+ */
+static void
+cleanup_fdsets(isc_socketmgr_t *manager, isc_mem_t *mctx) {
+ if (manager->fds != NULL) {
+ isc_mem_put(mctx, manager->fds,
+ manager->fdsize * sizeof(manager->fds[0]));
+ }
+ if (manager->fdstate != NULL) {
+ isc_mem_put(mctx, manager->fdstate,
+ manager->fdsize * sizeof(manager->fdstate[0]));
+ }
+ if (manager->read_fds != NULL)
+ isc_mem_put(mctx, manager->read_fds, manager->fd_bufsize);
+ if (manager->read_fds_copy != NULL)
+ isc_mem_put(mctx, manager->read_fds_copy, manager->fd_bufsize);
+ if (manager->write_fds != NULL)
+ isc_mem_put(mctx, manager->write_fds, manager->fd_bufsize);
+ if (manager->write_fds_copy != NULL)
+ isc_mem_put(mctx, manager->write_fds_copy, manager->fd_bufsize);
+}
+
/*
* Create a new socket manager.
*/
@@ -2379,6 +2516,7 @@ isc_socketmgr_create(isc_mem_t *mctx, isc_socketmgr_t **managerp) {
#ifdef ISC_PLATFORM_USETHREADS
char strbuf[ISC_STRERRORSIZE];
#endif
+ isc_result_t result;
REQUIRE(managerp != NULL && *managerp == NULL);
@@ -2394,11 +2532,19 @@ isc_socketmgr_create(isc_mem_t *mctx, isc_socketmgr_t **managerp) {
if (manager == NULL)
return (ISC_R_NOMEMORY);
+ result = create_fdsets(manager, mctx);
+ if (result != ISC_R_SUCCESS) {
+ cleanup_fdsets(manager, mctx);
+ isc_mem_put(mctx, manager, sizeof(*manager));
+ return (result);
+ }
+
manager->magic = SOCKET_MANAGER_MAGIC;
manager->mctx = NULL;
- memset(manager->fds, 0, sizeof(manager->fds));
ISC_LIST_INIT(manager->socklist);
- if (isc_mutex_init(&manager->lock) != ISC_R_SUCCESS) {
+ result = isc_mutex_init(&manager->lock);
+ if (result != ISC_R_SUCCESS) {
+ cleanup_fdsets(manager, mctx);
isc_mem_put(mctx, manager, sizeof(*manager));
UNEXPECTED_ERROR(__FILE__, __LINE__,
"isc_mutex_init() %s",
@@ -2408,6 +2554,7 @@ isc_socketmgr_create(isc_mem_t *mctx, isc_socketmgr_t **managerp) {
}
#ifdef ISC_PLATFORM_USETHREADS
if (isc_condition_init(&manager->shutdown_ok) != ISC_R_SUCCESS) {
+ cleanup_fdsets(manager, mctx);
DESTROYLOCK(&manager->lock);
isc_mem_put(mctx, manager, sizeof(*manager));
UNEXPECTED_ERROR(__FILE__, __LINE__,
@@ -2422,6 +2569,7 @@ isc_socketmgr_create(isc_mem_t *mctx, isc_socketmgr_t **managerp) {
* select/poll loop when something internal needs to be done.
*/
if (pipe(manager->pipe_fds) != 0) {
+ cleanup_fdsets(manager, mctx);
DESTROYLOCK(&manager->lock);
isc_mem_put(mctx, manager, sizeof(*manager));
isc__strerror(errno, strbuf, sizeof(strbuf));
@@ -2445,15 +2593,17 @@ isc_socketmgr_create(isc_mem_t *mctx, isc_socketmgr_t **managerp) {
/*
* Set up initial state for the select loop
*/
- FD_ZERO(&manager->read_fds);
- FD_ZERO(&manager->write_fds);
+ memset(manager->read_fds, 0, manager->fd_bufsize);
+ memset(manager->write_fds, 0, manager->fd_bufsize);
#ifdef ISC_PLATFORM_USETHREADS
- FD_SET(manager->pipe_fds[0], &manager->read_fds);
+ FD_SET(manager->pipe_fds[0], manager->read_fds);
manager->maxfd = manager->pipe_fds[0];
#else /* ISC_PLATFORM_USETHREADS */
manager->maxfd = 0;
#endif /* ISC_PLATFORM_USETHREADS */
- memset(manager->fdstate, 0, sizeof(manager->fdstate));
+ manager->reserved = 0;
+ memset(manager->fdstate, 0,
+ manager->fdsize * sizeof(manager->fdstate[0]));
#ifdef ISC_PLATFORM_USETHREADS
/*
@@ -2559,11 +2709,12 @@ isc_socketmgr_destroy(isc_socketmgr_t **managerp) {
(void)isc_condition_destroy(&manager->shutdown_ok);
#endif /* ISC_PLATFORM_USETHREADS */
- for (i = 0; i < (int)FD_SETSIZE; i++)
+ for (i = 0; i < (int)manager->fdsize; i++)
if (manager->fdstate[i] == CLOSE_PENDING)
(void)close(i);
DESTROYLOCK(&manager->lock);
+ cleanup_fdsets(manager, manager->mctx);
manager->magic = 0;
mctx= manager->mctx;
isc_mem_put(mctx, manager, sizeof(*manager));
@@ -2948,7 +3099,8 @@ isc_socket_sendto2(isc_socket_t *sock, isc_region_t *region,
}
isc_result_t
-isc_socket_bind(isc_socket_t *sock, isc_sockaddr_t *sockaddr) {
+isc_socket_bind(isc_socket_t *sock, isc_sockaddr_t *sockaddr,
+ unsigned int options) {
char strbuf[ISC_STRERRORSIZE];
int on = 1;
@@ -2963,7 +3115,8 @@ isc_socket_bind(isc_socket_t *sock, isc_sockaddr_t *sockaddr) {
/*
* Only set SO_REUSEADDR when we want a specific port.
*/
- if (isc_sockaddr_getport(sockaddr) != (in_port_t)0 &&
+ if ((options & ISC_SOCKET_REUSEADDRESS) != 0 &&
+ isc_sockaddr_getport(sockaddr) != (in_port_t)0 &&
setsockopt(sock->fd, SOL_SOCKET, SO_REUSEADDR, (void *)&on,
sizeof(on)) < 0) {
UNEXPECTED_ERROR(__FILE__, __LINE__,
@@ -3588,12 +3741,17 @@ isc_socket_ipv6only(isc_socket_t *sock, isc_boolean_t yes) {
#ifndef ISC_PLATFORM_USETHREADS
void
-isc__socketmgr_getfdsets(fd_set *readset, fd_set *writeset, int *maxfd) {
+isc__socketmgr_getfdsets(fd_set **readset, fd_set **writeset, int *maxfd) {
if (socketmgr == NULL)
*maxfd = 0;
else {
- *readset = socketmgr->read_fds;
- *writeset = socketmgr->write_fds;
+ /* Prepare duplicates of fd_sets, as select() will modify */
+ memcpy(socketmgr->read_fds_copy, socketmgr->read_fds,
+ socketmgr->fd_bufsize);
+ memcpy(socketmgr->write_fds_copy, socketmgr->write_fds,
+ socketmgr->fd_bufsize);
+ *readset = socketmgr->read_fds_copy;
+ *writeset = socketmgr->write_fds_copy;
*maxfd = socketmgr->maxfd + 1;
}
}
diff --git a/lib/isc/unix/socket_p.h b/lib/isc/unix/socket_p.h
index f430bf22e1c6..07720eef656c 100644
--- a/lib/isc/unix/socket_p.h
+++ b/lib/isc/unix/socket_p.h
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: socket_p.h,v 1.6.206.1 2004/03/06 08:15:02 marka Exp $ */
+/* $Id: socket_p.h,v 1.6.206.1.34.1 2008/07/29 04:43:57 each Exp $ */
#ifndef ISC_SOCKET_P_H
#define ISC_SOCKET_P_H
@@ -25,7 +25,7 @@
#endif
void
-isc__socketmgr_getfdsets(fd_set *readset, fd_set *writeset, int *maxfd);
+isc__socketmgr_getfdsets(fd_set **readset, fd_set **writeset, int *maxfd);
isc_result_t
isc__socketmgr_dispatch(fd_set *readset, fd_set *writeset, int maxfd);
diff --git a/lib/isccfg/api b/lib/isccfg/api
index d174ce2fc4b1..808217d1f364 100644
--- a/lib/isccfg/api
+++ b/lib/isccfg/api
@@ -1,3 +1,3 @@
LIBINTERFACE = 1
-LIBREVISION = 8
+LIBREVISION = 9
LIBAGE = 0
diff --git a/lib/isccfg/namedconf.c b/lib/isccfg/namedconf.c
index 1943af3dbebf..622d76aef790 100644
--- a/lib/isccfg/namedconf.c
+++ b/lib/isccfg/namedconf.c
@@ -15,7 +15,7 @@
* PERFORMANCE OF THIS SOFTWARE.
*/
-/* $Id: namedconf.c,v 1.21.44.36 2008/01/24 23:45:28 tbox Exp $ */
+/* $Id: namedconf.c,v 1.21.44.36.2.1 2008/07/23 12:03:53 marka Exp $ */
#include <config.h>
@@ -601,6 +601,7 @@ options_clauses[] = {
{ "recursing-file", &cfg_type_qstring, 0 },
{ "random-device", &cfg_type_qstring, 0 },
{ "recursive-clients", &cfg_type_uint32, 0 },
+ { "reserved-sockets", &cfg_type_uint32, 0 },
{ "serial-queries", &cfg_type_uint32, CFG_CLAUSEFLAG_OBSOLETE },
{ "serial-query-rate", &cfg_type_uint32, 0 },
{ "server-id", &cfg_type_serverid, 0 },
diff --git a/version b/version
index 6853a8a6bf39..9a2d587b3d09 100644
--- a/version
+++ b/version
@@ -1,4 +1,4 @@
-# $Id: version,v 1.26.2.17.2.31.4.1 2008/05/22 21:11:13 each Exp $
+# $Id: version,v 1.26.2.17.2.31.4.2 2008/07/29 05:03:50 each Exp $
#
# This file must follow /bin/sh rules. It is imported directly via
# configure.
@@ -7,4 +7,4 @@ MAJORVER=9
MINORVER=3
PATCHVER=5
RELEASETYPE=-P
-RELEASEVER=1
+RELEASEVER=2