#ifdef TUNE_LARGE
#define RESOLVER_NTASKS_PERCPU 32
#define UDPBUFFERS 32768
-#define EXCLBUFFERS 32768
#else
#define RESOLVER_NTASKS_PERCPU 8
-#define UDPBUFFERS 1000
-#define EXCLBUFFERS 4096
+#define UDPBUFFERS 4096
#endif /* TUNE_LARGE */
/* RFC7828 defines timeout as 16-bit value specified in units of 100
dns_dispatch_t **dispatchp, isc_dscp_t *dscpp,
bool is_firstview) {
isc_result_t result = ISC_R_FAILURE;
- dns_dispatch_t *disp;
+ dns_dispatch_t *disp = NULL;
isc_sockaddr_t sa;
unsigned int attrs;
const cfg_obj_t *obj = NULL;
/*
* Try to find a dispatcher that we can share.
*/
- attrs = 0;
- attrs |= DNS_DISPATCHATTR_UDP;
+ attrs = DNS_DISPATCHATTR_UDP;
switch (af) {
case AF_INET:
attrs |= DNS_DISPATCHATTR_IPV4;
attrs |= DNS_DISPATCHATTR_IPV6;
break;
}
- if (isc_sockaddr_getport(&sa) == 0) {
- attrs |= DNS_DISPATCHATTR_EXCLUSIVE;
- maxdispatchbuffers = EXCLBUFFERS;
- } else {
+ if (isc_sockaddr_getport(&sa) != 0) {
INSIST(obj != NULL);
if (is_firstview) {
cfg_obj_log(obj, named_g_lctx, ISC_LOG_INFO,
}
}
- disp = NULL;
- result = dns_dispatch_getudp(named_g_dispatchmgr, named_g_socketmgr,
- named_g_taskmgr, &sa, maxdispatchbuffers,
- 32768, 16411, 16433, attrs, &disp);
+ result = dns_dispatch_createudp(
+ named_g_dispatchmgr, named_g_socketmgr, named_g_taskmgr, &sa,
+ maxdispatchbuffers, 32768, 16411, 16433, attrs, &disp);
if (result != ISC_R_SUCCESS) {
isc_sockaddr_t any;
char buf[ISC_SOCKADDR_FORMATSIZE];
dispatch->dispatchgen = server->dispatchgen;
dispatch->dispatch = NULL;
- attrs = 0;
- attrs |= DNS_DISPATCHATTR_UDP;
+ attrs = DNS_DISPATCHATTR_UDP;
switch (isc_sockaddr_pf(addr)) {
case AF_INET:
attrs |= DNS_DISPATCHATTR_IPV4;
goto cleanup;
}
- result = dns_dispatch_getudp(named_g_dispatchmgr, named_g_socketmgr,
- named_g_taskmgr, &dispatch->addr,
- UDPBUFFERS, 32768, 16411, 16433, attrs,
- &dispatch->dispatch);
+ result = dns_dispatch_createudp(named_g_dispatchmgr, named_g_socketmgr,
+ named_g_taskmgr, &dispatch->addr,
+ UDPBUFFERS, 32768, 16411, 16433, attrs,
+ &dispatch->dispatch);
if (result != ISC_R_SUCCESS) {
goto cleanup;
}
set_source_ports(dispatchmgr);
if (have_ipv6) {
- attrs = DNS_DISPATCHATTR_UDP;
- attrs |= DNS_DISPATCHATTR_MAKEQUERY;
- attrs |= DNS_DISPATCHATTR_IPV6;
+ attrs = (DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY |
+ DNS_DISPATCHATTR_IPV6);
isc_sockaddr_any6(&bind_any6);
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr,
- &bind_any6, 4, 2, 3, 5, attrs,
- &dispatchv6);
- check_result(result, "dns_dispatch_getudp (v6)");
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ &bind_any6, 4, 2, 3, 5, attrs,
+ &dispatchv6);
+ check_result(result, "dns_dispatch_createudp (v6)");
}
if (have_ipv4) {
- attrs = DNS_DISPATCHATTR_UDP;
- attrs |= DNS_DISPATCHATTR_MAKEQUERY;
- attrs |= DNS_DISPATCHATTR_IPV4;
+ attrs = (DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY |
+ DNS_DISPATCHATTR_IPV4);
isc_sockaddr_any(&bind_any);
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr,
- &bind_any, 4, 2, 3, 5, attrs,
- &dispatchv4);
- check_result(result, "dns_dispatch_getudp (v4)");
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ &bind_any, 4, 2, 3, 5, attrs,
+ &dispatchv4);
+ check_result(result, "dns_dispatch_createudp (v4)");
}
result = dns_requestmgr_create(gmctx, timermgr, socketmgr, taskmgr,
#define PORT 5300
#define TIMEOUT 30
-static isc_mem_t *mctx;
-static dns_requestmgr_t *requestmgr;
+static isc_mem_t *mctx = NULL;
+static dns_requestmgr_t *requestmgr = NULL;
static bool have_src = false;
static isc_sockaddr_t srcaddr;
static isc_sockaddr_t dstaddr;
static isc_result_t
sendquery(isc_task_t *task) {
- dns_request_t *request;
- dns_message_t *message;
- dns_name_t *qname;
- dns_rdataset_t *qrdataset;
+ dns_request_t *request = NULL;
+ dns_message_t *message = NULL;
+ dns_name_t *qname = NULL;
+ dns_rdataset_t *qrdataset = NULL;
isc_result_t result;
dns_fixedname_t queryname;
isc_buffer_t buf;
dns_rootname, 0, NULL);
CHECK("dns_name_fromtext", result);
- message = NULL;
dns_message_create(mctx, DNS_MESSAGE_INTENTRENDER, &message);
message->opcode = dns_opcode_query;
message->rdclass = dns_rdataclass_in;
message->id = (unsigned short)(random() & 0xFFFF);
- qname = NULL;
result = dns_message_gettempname(message, &qname);
CHECK("dns_message_gettempname", result);
- qrdataset = NULL;
result = dns_message_gettemprdataset(message, &qrdataset);
CHECK("dns_message_gettemprdataset", result);
ISC_LIST_APPEND(qname->list, qrdataset, link);
dns_message_addname(message, qname, DNS_SECTION_QUESTION);
- request = NULL;
result = dns_request_createvia(requestmgr, message,
have_src ? &srcaddr : NULL, &dstaddr, -1,
DNS_REQUESTOPT_TCP, NULL, TIMEOUT, 0, 0,
isc_sockaddr_t bind_any;
struct in_addr inaddr;
isc_result_t result;
- isc_log_t *lctx;
- isc_logconfig_t *lcfg;
+ isc_log_t *lctx = NULL;
+ isc_logconfig_t *lcfg = NULL;
isc_nm_t *netmgr = NULL;
isc_taskmgr_t *taskmgr = NULL;
isc_task_t *task = NULL;
isc_socketmgr_t *socketmgr = NULL;
dns_dispatchmgr_t *dispatchmgr = NULL;
unsigned int attrs;
- dns_dispatch_t *dispatchv4;
- dns_view_t *view;
+ dns_dispatch_t *dispatchv4 = NULL;
+ dns_view_t *view = NULL;
uint16_t port = PORT;
int c;
}
isc_sockaddr_fromin(&dstaddr, &inaddr, port);
- mctx = NULL;
isc_mem_create(&mctx);
- lctx = NULL;
- lcfg = NULL;
isc_log_create(mctx, &lctx, &lcfg);
RUNCHECK(dst_lib_init(mctx, NULL));
attrs = DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY |
DNS_DISPATCHATTR_IPV4;
- dispatchv4 = NULL;
- RUNCHECK(dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr,
- have_src ? &srcaddr : &bind_any, 4, 2, 3,
- 5, attrs, &dispatchv4));
- requestmgr = NULL;
+
+ RUNCHECK(dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ have_src ? &srcaddr : &bind_any, 4, 2,
+ 3, 5, attrs, &dispatchv4));
RUNCHECK(dns_requestmgr_create(mctx, timermgr, socketmgr, taskmgr,
dispatchmgr, dispatchv4, NULL,
&requestmgr));
- view = NULL;
RUNCHECK(dns_view_create(mctx, 0, "_test", &view));
-
RUNCHECK(isc_app_onrun(mctx, task, sendqueries, NULL));
(void)isc_app_run();
isc_sockaddr_any(&bind_any);
attrs = DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY |
DNS_DISPATCHATTR_IPV4;
- dispatchv4 = NULL;
- RUNCHECK(dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, &bind_any,
- 4, 2, 3, 5, attrs, &dispatchv4));
+ RUNCHECK(dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ &bind_any, 4, 2, 3, 5, attrs,
+ &dispatchv4));
requestmgr = NULL;
RUNCHECK(dns_requestmgr_create(mctx, timermgr, socketmgr, taskmgr,
dispatchmgr, dispatchv4, NULL,
isc_sockaddr_any(&bind_any);
attrs = DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY |
DNS_DISPATCHATTR_IPV4;
- dispatchv4 = NULL;
- RUNCHECK(dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, &bind_any,
- 4, 2, 3, 5, attrs, &dispatchv4));
+ RUNCHECK(dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ &bind_any, 4, 2, 3, 5, attrs,
+ &dispatchv4));
requestmgr = NULL;
RUNCHECK(dns_requestmgr_create(mctx, timermgr, socketmgr, taskmgr,
dispatchmgr, dispatchv4, NULL,
isc_timermgr_t *timermgr = NULL;
isc_socketmgr_t *socketmgr = NULL;
dns_dispatchmgr_t *dispatchmgr = NULL;
- unsigned int attrs;
dns_dispatch_t *dispatchvx = NULL;
dns_view_t *view = NULL;
+ unsigned int attrs, i;
int ns;
- unsigned int i;
RUNCHECK(isc_app_start());
preparse_args(argc, argv);
isc_mem_create(&mctx);
-
isc_log_create(mctx, &lctx, &lcfg);
RUNCHECK(dst_lib_init(mctx, NULL));
&socketmgr);
RUNCHECK(isc_task_create(taskmgr, 0, &task));
-
RUNCHECK(dns_dispatchmgr_create(mctx, &dispatchmgr));
attrs = DNS_DISPATCHATTR_UDP | DNS_DISPATCHATTR_MAKEQUERY;
isc_sockaddr_any6(&bind_any);
attrs |= DNS_DISPATCHATTR_IPV6;
}
- dispatchvx = NULL;
- RUNCHECK(dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr,
- have_src ? &srcaddr : &bind_any, 100, 100,
- 17, 19, attrs, &dispatchvx));
+ RUNCHECK(dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ have_src ? &srcaddr : &bind_any, 100,
+ 100, 17, 19, attrs, &dispatchvx));
+
RUNCHECK(dns_requestmgr_create(
mctx, timermgr, socketmgr, taskmgr, dispatchmgr,
have_ipv4 ? dispatchvx : NULL, have_ipv6 ? dispatchvx : NULL,
bool is_shared, dns_dispatch_t **dispp,
const isc_sockaddr_t *localaddr) {
unsigned int attrs;
- dns_dispatch_t *disp;
+ dns_dispatch_t *disp = NULL;
unsigned maxbuffers, maxrequests, buckets, increment;
isc_result_t result;
isc_sockaddr_t anyaddr;
- attrs = 0;
- attrs |= DNS_DISPATCHATTR_UDP;
+ attrs = DNS_DISPATCHATTR_UDP;
switch (family) {
case AF_INET:
attrs |= DNS_DISPATCHATTR_IPV4;
buckets = is_shared ? 16411 : 3;
increment = is_shared ? 16433 : 5;
- disp = NULL;
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, localaddr,
- maxbuffers, maxrequests, buckets,
- increment, attrs, &disp);
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr,
+ localaddr, maxbuffers, maxrequests,
+ buckets, increment, attrs, &disp);
if (result == ISC_R_SUCCESS) {
*dispp = disp;
}
static void
deactivate_dispsocket(dns_dispatch_t *, dispsocket_t *);
static void
-udp_exrecv(isc_task_t *, isc_event_t *);
-static void
-udp_shrecv(isc_task_t *, isc_event_t *);
-static void
-udp_recv(isc_event_t *, dns_dispatch_t *, dispsocket_t *);
+udp_recv(isc_task_t *, isc_event_t *);
static void
tcp_recv(isc_task_t *, isc_event_t *);
static isc_result_t
static void
dispatch_free(dns_dispatch_t **dispp);
static isc_result_t
-get_udpsocket(dns_dispatchmgr_t *mgr, dns_dispatch_t *disp,
- isc_socketmgr_t *sockmgr, const isc_sockaddr_t *localaddr,
- isc_socket_t **sockp, isc_socket_t *dup_socket);
-static isc_result_t
dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
unsigned int maxrequests, unsigned int attributes,
- dns_dispatch_t **dispp, isc_socket_t *dup_socket);
+ dns_dispatch_t **dispp);
static bool
destroy_mgr_ok(dns_dispatchmgr_t *mgr);
static void
open_socket(isc_socketmgr_t *mgr, const isc_sockaddr_t *local,
unsigned int options, isc_socket_t **sockp,
isc_socket_t *dup_socket);
-static bool
-portavailable(dns_dispatchmgr_t *mgr, isc_socket_t *sock,
- isc_sockaddr_t *sockaddrp);
#define LVL(x) ISC_LOG_DEBUG(x)
LOCK(&mgr->lock);
ISC_LIST_UNLINK(mgr->list, disp, link);
- dispatch_log(disp, LVL(90),
- "shutting down; detaching from sock %p, task %p",
- disp->socket, disp->task[0]); /* XXXX */
+ dispatch_log(disp, LVL(90), "shutting down; detaching from sock %p",
+ disp->socket);
if (disp->sepool != NULL) {
isc_mem_destroy(&disp->sepool);
}
}
- if (result == ISC_R_SUCCESS) {
- dispsock->socket = sock;
- dispsock->host = *dest;
- dispsock->bucket = bucket;
- LOCK(&qid->lock);
- dispsock->portentry = portentry;
- ISC_LIST_APPEND(qid->sock_table[bucket], dispsock, blink);
- UNLOCK(&qid->lock);
- *dispsockp = dispsock;
- *portp = port;
- } else {
- /*
- * We could keep it in the inactive list, but since this should
- * be an exceptional case and might be resource shortage, we'd
- * rather destroy it.
- */
+ if (result != ISC_R_SUCCESS) {
if (sock != NULL) {
isc_socket_detach(&sock);
}
destroy_dispsocket(disp, &dispsock);
+ return (result);
}
- return (result);
+ dispsock->socket = sock;
+ dispsock->host = *dest;
+ dispsock->bucket = bucket;
+ LOCK(&qid->lock);
+ dispsock->portentry = portentry;
+ ISC_LIST_APPEND(qid->sock_table[bucket], dispsock, blink);
+ UNLOCK(&qid->lock);
+ *dispsockp = dispsock;
+ *portp = port;
+
+ return (ISC_R_SUCCESS);
}
/*%
return (ev);
}
-static void
-udp_exrecv(isc_task_t *task, isc_event_t *ev) {
- dispsocket_t *dispsock = ev->ev_arg;
-
- UNUSED(task);
-
- REQUIRE(VALID_DISPSOCK(dispsock));
- udp_recv(ev, dispsock->disp, dispsock);
-}
-
-static void
-udp_shrecv(isc_task_t *task, isc_event_t *ev) {
- dns_dispatch_t *disp = ev->ev_arg;
-
- UNUSED(task);
-
- REQUIRE(VALID_DISPATCH(disp));
- udp_recv(ev, disp, NULL);
-}
-
/*
* General flow:
*
* restart.
*/
static void
-udp_recv(isc_event_t *ev_in, dns_dispatch_t *disp, dispsocket_t *dispsock) {
+udp_recv(isc_task_t *task, isc_event_t *ev_in) {
isc_socketevent_t *ev = (isc_socketevent_t *)ev_in;
+ dispsocket_t *dispsock = NULL;
+ dns_dispatch_t *disp = NULL;
dns_messageid_t id;
isc_result_t dres;
isc_buffer_t source;
unsigned int flags;
dns_dispentry_t *resp = NULL;
dns_dispatchevent_t *rev = NULL;
- unsigned int bucket;
bool killit;
bool queue_response;
dns_dispatchmgr_t *mgr = NULL;
- dns_qid_t *qid = NULL;
isc_netaddr_t netaddr;
int match;
int result;
- bool qidlocked = false;
+
+ UNUSED(task);
+
+ REQUIRE(ev->ev_type == ISC_SOCKEVENT_RECVDONE);
+
+ dispsock = ev_in->ev_arg;
+
+ REQUIRE(VALID_DISPSOCK(dispsock));
+
+ disp = dispsock->disp;
LOCK(&disp->lock);
mgr = disp->mgr;
- qid = mgr->qid;
LOCK(&disp->mgr->buffer_lock);
dispatch_log(disp, LVL(90),
disp->requests, disp->mgr->buffers, disp->recv_pending);
UNLOCK(&disp->mgr->buffer_lock);
- if (dispsock == NULL && ev->ev_type == ISC_SOCKEVENT_RECVDONE) {
- /*
- * Unless the receive event was imported from a listening
- * interface, in which case the event type is
- * DNS_EVENT_IMPORTRECVDONE, receive operation must be pending.
- */
- INSIST(disp->recv_pending != 0);
- disp->recv_pending = 0;
- }
-
- if (dispsock != NULL &&
- (ev->result == ISC_R_CANCELED || dispsock->resp == NULL))
- {
+ if (ev->result == ISC_R_CANCELED || dispsock->resp == NULL) {
/*
* dispsock->resp can be NULL if this transaction was canceled
* just after receiving a response. Since this socket is
* exclusively used and there should be at most one receive
- * event the canceled event should have been no effect. So
+ * event the canceled event should have no effect. So
* we can (and should) deactivate the socket right now.
*/
deactivate_dispsocket(disp, dispsock);
return;
}
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- if (dispsock == NULL) {
- free_buffer(disp, ev->region.base, ev->region.length);
-
- isc_event_free(&ev_in);
- UNLOCK(&disp->lock);
- return;
- }
-
- resp = dispsock->resp;
- id = resp->id;
- if (ev->result != ISC_R_SUCCESS) {
- /*
- * This is most likely a network error on a
- * connected socket. It makes no sense to
- * check the address or parse the packet, but it
- * will help to return the error to the caller.
- */
- goto sendresponse;
- }
- } else if (ev->result != ISC_R_SUCCESS) {
+ if (dispsock == NULL) {
free_buffer(disp, ev->region.base, ev->region.length);
-
- if (ev->result != ISC_R_CANCELED) {
- dispatch_log(disp, ISC_LOG_ERROR,
- "odd socket result in udp_recv(): %s",
- isc_result_totext(ev->result));
- }
-
isc_event_free(&ev_in);
UNLOCK(&disp->lock);
return;
}
+ resp = dispsock->resp;
+ id = resp->id;
+
+ if (ev->result != ISC_R_SUCCESS) {
+ /*
+ * This is most likely a network error on a
+ * connected socket. It makes no sense to
+ * check the address or parse the packet, but it
+ * will help to return the error to the caller.
+ */
+ goto sendresponse;
+ }
+
/*
* If this is from a blackholed address, drop it.
*/
}
/*
- * Search for the corresponding response. If we are using an exclusive
- * socket, we've already identified it and we can skip the search; but
- * the ID and the address must match the expected ones.
+ * The QID and the address must match the expected ones.
*/
- if (resp == NULL) {
- bucket = dns_hash(qid, &ev->address, id, disp->localport);
- LOCK(&qid->lock);
- qidlocked = true;
- resp = entry_search(qid, &ev->address, id, disp->localport,
- bucket);
- dispatch_log(disp, LVL(90),
- "search for response in bucket %d: %s", bucket,
- (resp == NULL ? "not found" : "found"));
-
- } else if (resp->id != id ||
- !isc_sockaddr_equal(&ev->address, &resp->host)) {
- dispatch_log(disp, LVL(90),
- "response to an exclusive socket doesn't match");
- inc_stats(mgr, dns_resstatscounter_mismatch);
- free_buffer(disp, ev->region.base, ev->region.length);
- goto unlock;
- }
-
- if (resp == NULL) {
+ if (resp->id != id || !isc_sockaddr_equal(&ev->address, &resp->host)) {
+ dispatch_log(disp, LVL(90), "response doesn't match");
inc_stats(mgr, dns_resstatscounter_mismatch);
free_buffer(disp, ev->region.base, ev->region.length);
- goto unlock;
+ goto restart;
}
/*
isc_sockaddr_getport(&resp->disp->local))
{
free_buffer(disp, ev->region.base, ev->region.length);
- goto unlock;
+ goto restart;
}
/*
isc_sockaddr_pf(&disp->local) != PF_INET6)
{
free_buffer(disp, ev->region.base, ev->region.length);
- goto unlock;
+ goto restart;
}
isc_sockaddr_anyofpf(&a1, isc_sockaddr_pf(&resp->disp->local));
isc_sockaddr_anyofpf(&a2, isc_sockaddr_pf(&disp->local));
!isc_sockaddr_eqaddr(&a2, &disp->local))
{
free_buffer(disp, ev->region.base, ev->region.length);
- goto unlock;
+ goto restart;
}
}
resp->item_out = true;
isc_task_send(resp->task, ISC_EVENT_PTR(&rev));
}
-unlock:
- if (qidlocked) {
- UNLOCK(&qid->lock);
- }
/*
* Restart recv() to get the next packet.
*/
restart:
result = startrecv(disp, dispsock);
- if (result != ISC_R_SUCCESS && dispsock != NULL) {
- /*
- * XXX: wired. There seems to be no recovery process other than
- * deactivate this socket anyway (since we cannot start
- * receiving, we won't be able to receive a cancel event
- * from the user).
- */
+ if (result != ISC_R_SUCCESS) {
deactivate_dispsocket(disp, dispsock);
}
isc_event_free(&ev_in);
isc_result_t res;
isc_region_t region;
isc_socket_t *sock = NULL;
+ isc_socketevent_t *sev = NULL;
if (disp->shutting_down == 1) {
return (ISC_R_SUCCESS);
}
- if (disp->recv_pending != 0 && dispsock == NULL) {
- return (ISC_R_SUCCESS);
- }
-
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0 &&
- dispsock == NULL) {
- return (ISC_R_SUCCESS);
- }
-
- if (dispsock != NULL) {
- sock = dispsock->socket;
- } else {
+ if (dispsock == NULL) {
+ if (disp->socktype == isc_sockettype_udp ||
+ disp->recv_pending != 0) {
+ return (ISC_R_SUCCESS);
+ }
sock = disp->socket;
+ } else {
+ sock = dispsock->socket;
}
- INSIST(sock != NULL);
switch (disp->socktype) {
/*
if (region.base == NULL) {
return (ISC_R_NOMEMORY);
}
- if (dispsock != NULL) {
- isc_task_t *dt = dispsock->task;
- isc_socketevent_t *sev = allocate_sevent(
- disp, sock, ISC_SOCKEVENT_RECVDONE, udp_exrecv,
- dispsock);
-
- res = isc_socket_recv2(sock, ®ion, 1, dt, sev, 0);
- if (res != ISC_R_SUCCESS) {
- free_buffer(disp, region.base, region.length);
- return (res);
- }
- } else {
- isc_task_t *dt = disp->task[0];
- isc_socketevent_t *sev = allocate_sevent(
- disp, sock, ISC_SOCKEVENT_RECVDONE, udp_shrecv,
- disp);
-
- res = isc_socket_recv2(sock, ®ion, 1, dt, sev, 0);
- if (res != ISC_R_SUCCESS) {
- free_buffer(disp, region.base, region.length);
- disp->shutdown_why = res;
- disp->shutting_down = 1;
- do_cancel(disp);
- return (ISC_R_SUCCESS); /* recover by cancel */
- }
- INSIST(disp->recv_pending == 0);
- disp->recv_pending = 1;
+ sev = allocate_sevent(disp, sock, ISC_SOCKEVENT_RECVDONE,
+ udp_recv, dispsock);
+ res = isc_socket_recv2(sock, ®ion, 1, dispsock->task, sev,
+ 0);
+ if (res != ISC_R_SUCCESS) {
+ free_buffer(disp, region.base, region.length);
+ return (res);
}
break;
isc_stats_attach(stats, &mgr->stats);
}
-static int
-port_cmp(const void *key, const void *ent) {
- in_port_t p1 = *(const in_port_t *)key;
- in_port_t p2 = *(const in_port_t *)ent;
-
- if (p1 < p2) {
- return (-1);
- } else if (p1 == p2) {
- return (0);
- } else {
- return (1);
- }
-}
-
-static bool
-portavailable(dns_dispatchmgr_t *mgr, isc_socket_t *sock,
- isc_sockaddr_t *sockaddrp) {
- isc_sockaddr_t sockaddr;
- isc_result_t result;
- in_port_t *ports, port;
- unsigned int nports;
- bool available = false;
-
- REQUIRE(sock != NULL || sockaddrp != NULL);
-
- PORTBUFLOCK(mgr);
- if (sock != NULL) {
- sockaddrp = &sockaddr;
- result = isc_socket_getsockname(sock, sockaddrp);
- if (result != ISC_R_SUCCESS) {
- goto unlock;
- }
- }
-
- if (isc_sockaddr_pf(sockaddrp) == AF_INET) {
- ports = mgr->v4ports;
- nports = mgr->nv4ports;
- } else {
- ports = mgr->v6ports;
- nports = mgr->nv6ports;
- }
- if (ports == NULL) {
- goto unlock;
- }
-
- port = isc_sockaddr_getport(sockaddrp);
- if (bsearch(&port, ports, nports, sizeof(in_port_t), port_cmp) != NULL)
- {
- available = true;
- }
-
-unlock:
- PORTBUFUNLOCK(mgr);
- return (available);
-}
-
static isc_result_t
qid_allocate(dns_dispatchmgr_t *mgr, unsigned int buckets,
unsigned int increment, dns_qid_t **qidp, bool needsocktable) {
disp->socket = NULL;
isc_socket_attach(sock, &disp->socket);
- disp->sepool = NULL;
-
disp->ntasks = 1;
disp->task[0] = NULL;
result = isc_task_create(taskmgr, 50, &disp->task[0]);
disp->attributes = attributes;
+ if (destaddr == NULL) {
+ (void)isc_socket_getpeername(sock, &disp->peer);
+ } else {
+ disp->peer = *destaddr;
+ }
+
if (localaddr == NULL) {
if (destaddr != NULL) {
switch (isc_sockaddr_pf(destaddr)) {
isc_sockaddr_any6(&disp->local);
break;
}
+ } else {
+ (void)isc_socket_getsockname(sock, &disp->local);
}
} else {
disp->local = *localaddr;
}
- if (destaddr != NULL) {
- disp->peer = *destaddr;
- }
-
/*
* Append it to the dispatcher list.
*/
/* First pass */
attributes = DNS_DISPATCHATTR_TCP | DNS_DISPATCHATTR_CONNECTED;
mask = DNS_DISPATCHATTR_TCP | DNS_DISPATCHATTR_PRIVATE |
- DNS_DISPATCHATTR_EXCLUSIVE | DNS_DISPATCHATTR_CONNECTED;
+ DNS_DISPATCHATTR_CONNECTED;
LOCK(&mgr->lock);
disp = ISC_LIST_HEAD(mgr->list);
}
isc_result_t
-dns_dispatch_getudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
- isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
- unsigned int maxbuffers, unsigned int maxrequests,
- unsigned int buckets, unsigned int increment,
- unsigned int attributes, dns_dispatch_t **dispp) {
+dns_dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
+ isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
+ unsigned int maxbuffers, unsigned int maxrequests,
+ unsigned int buckets, unsigned int increment,
+ unsigned int attributes, dns_dispatch_t **dispp) {
isc_result_t result;
dns_dispatch_t *disp = NULL;
}
LOCK(&mgr->lock);
-
- if ((attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- REQUIRE(isc_sockaddr_getport(localaddr) == 0);
- }
-
- /*
- * We need an exclusive-socket dispatch, or else we didn't
- * find a suitable shared one and need to create it.
- */
result = dispatch_createudp(mgr, sockmgr, taskmgr, localaddr,
- maxrequests, attributes, &disp, NULL);
- if (result != ISC_R_SUCCESS) {
- UNLOCK(&mgr->lock);
- return (result);
+ maxrequests, attributes, &disp);
+
+ if (result == ISC_R_SUCCESS) {
+ *dispp = disp;
}
UNLOCK(&mgr->lock);
- *dispp = disp;
-
return (ISC_R_SUCCESS);
}
-/*
- * mgr should be locked.
- */
-
-#ifndef DNS_DISPATCH_HELD
-#define DNS_DISPATCH_HELD 20U
-#endif /* ifndef DNS_DISPATCH_HELD */
-
-static isc_result_t
-get_udpsocket(dns_dispatchmgr_t *mgr, dns_dispatch_t *disp,
- isc_socketmgr_t *sockmgr, const isc_sockaddr_t *localaddr,
- isc_socket_t **sockp, isc_socket_t *dup_socket) {
- unsigned int i, j;
- isc_socket_t *held[DNS_DISPATCH_HELD];
- isc_sockaddr_t localaddr_bound;
- isc_socket_t *sock = NULL;
- isc_result_t result = ISC_R_SUCCESS;
- unsigned int nports;
- in_port_t *ports = NULL;
-
- REQUIRE(sockp != NULL && *sockp == NULL);
-
- if (isc_sockaddr_getport(localaddr) != 0) {
- /* Allow to reuse address for non-random ports. */
- result = open_socket(sockmgr, localaddr,
- ISC_SOCKET_REUSEADDRESS, &sock,
- dup_socket);
- if (result == ISC_R_SUCCESS) {
- *sockp = sock;
- }
-
- return (result);
- }
-
- /*
- * If no port is specified, we first try to pick up a random
- * port by ourselves.
- */
- if (isc_sockaddr_pf(localaddr) == AF_INET) {
- nports = mgr->nv4ports;
- ports = mgr->v4ports;
- } else {
- nports = mgr->nv6ports;
- ports = mgr->v6ports;
- }
- if (nports == 0) {
- return (ISC_R_ADDRNOTAVAIL);
- }
-
- localaddr_bound = *localaddr;
-
- for (i = 0; i < 1024; i++) {
- in_port_t prt;
-
- prt = ports[isc_random_uniform(nports)];
- isc_sockaddr_setport(&localaddr_bound, prt);
- result = open_socket(sockmgr, &localaddr_bound, 0, &sock, NULL);
- /*
- * If the port chosen is already in use or the OS has
- * reserved it, try again.
- */
- if (result == ISC_R_NOPERM || result == ISC_R_ADDRINUSE) {
- continue;
- }
- disp->localport = prt;
- *sockp = sock;
- return (result);
- }
-
- /*
- * If this fails 1024 times, we then ask the kernel for
- * help choosing one.
- */
- memset(held, 0, sizeof(held));
- i = 0;
-
- for (j = 0; j < 0xffffU; j++) {
- result = open_socket(sockmgr, localaddr, 0, &sock, NULL);
- if (result != ISC_R_SUCCESS) {
- goto end;
- } else if (portavailable(mgr, sock, NULL)) {
- break;
- }
- if (held[i] != NULL) {
- isc_socket_detach(&held[i]);
- }
- held[i++] = sock;
- sock = NULL;
- if (i == DNS_DISPATCH_HELD) {
- i = 0;
- }
- }
-
- if (j == 0xffffU) {
- mgr_log(mgr, ISC_LOG_ERROR,
- "avoid-v%s-udp-ports: unable to allocate "
- "an available port",
- isc_sockaddr_pf(localaddr) == AF_INET ? "4" : "6");
- result = ISC_R_FAILURE;
- goto end;
- }
- *sockp = sock;
-
-end:
- for (i = 0; i < DNS_DISPATCH_HELD; i++) {
- if (held[i] != NULL) {
- isc_socket_detach(&held[i]);
- }
- }
-
- return (result);
-}
-
static isc_result_t
dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
unsigned int maxrequests, unsigned int attributes,
- dns_dispatch_t **dispp, isc_socket_t *dup_socket) {
+ dns_dispatch_t **dispp) {
isc_result_t result;
dns_dispatch_t *disp = NULL;
isc_socket_t *sock = NULL;
+ isc_sockaddr_t sa_any;
int i = 0;
/*
disp->socktype = isc_sockettype_udp;
- if ((attributes & DNS_DISPATCHATTR_EXCLUSIVE) == 0) {
- result = get_udpsocket(mgr, disp, sockmgr, localaddr, &sock,
- dup_socket);
+ /*
+ * For dispatches with a specified source address, we open a
+ * socket to make sure that address is available on the system,
+ * but we don't keep it open; sockets used for sending requests
+ * will be created later on demand.
+ */
+ isc_sockaddr_anyofpf(&sa_any, isc_sockaddr_pf(localaddr));
+ if (!isc_sockaddr_eqaddr(&sa_any, localaddr)) {
+ result = open_socket(sockmgr, localaddr, 0, &sock, NULL);
+ if (sock != NULL) {
+ isc_socket_detach(&sock);
+ }
if (result != ISC_R_SUCCESS) {
goto deallocate_dispatch;
}
+ }
- if (isc_log_wouldlog(dns_lctx, 90)) {
- char addrbuf[ISC_SOCKADDR_FORMATSIZE];
-
- isc_sockaddr_format(localaddr, addrbuf,
- ISC_SOCKADDR_FORMATSIZE);
- mgr_log(mgr, LVL(90),
- "dispatch_createudp: created shared "
- "UDP dispatch for %s with socket fd %d",
- addrbuf, isc_socket_getfd(sock));
- }
- } else {
- isc_sockaddr_t sa_any;
+ disp->port_table = isc_mem_get(mgr->mctx,
+ sizeof(disp->port_table[0]) *
+ DNS_DISPATCH_PORTTABLESIZE);
+ for (i = 0; i < DNS_DISPATCH_PORTTABLESIZE; i++) {
+ ISC_LIST_INIT(disp->port_table[i]);
+ }
- /*
- * For dispatches using exclusive sockets with a specific
- * source address, we only check if the specified address is
- * available on the system. Query sockets will be created later
- * on demand.
- */
- isc_sockaddr_anyofpf(&sa_any, isc_sockaddr_pf(localaddr));
- if (!isc_sockaddr_eqaddr(&sa_any, localaddr)) {
- result = open_socket(sockmgr, localaddr, 0, &sock,
- NULL);
- if (sock != NULL) {
- isc_socket_detach(&sock);
- }
- if (result != ISC_R_SUCCESS) {
- goto deallocate_dispatch;
- }
- }
+ if (isc_log_wouldlog(dns_lctx, 90)) {
+ char addrbuf[ISC_SOCKADDR_FORMATSIZE];
- disp->port_table = isc_mem_get(
- mgr->mctx, sizeof(disp->port_table[0]) *
- DNS_DISPATCH_PORTTABLESIZE);
- for (i = 0; i < DNS_DISPATCH_PORTTABLESIZE; i++) {
- ISC_LIST_INIT(disp->port_table[i]);
- }
+ isc_sockaddr_format(localaddr, addrbuf,
+ ISC_SOCKADDR_FORMATSIZE);
+ mgr_log(mgr, LVL(90),
+ "dispatch_createudp: created UDP dispatch for %s",
+ addrbuf);
}
+
disp->socket = sock;
disp->local = *localaddr;
+ disp->ntasks = MAX_INTERNAL_TASKS;
- if ((attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- disp->ntasks = MAX_INTERNAL_TASKS;
- } else {
- disp->ntasks = 1;
- }
for (i = 0; i < disp->ntasks; i++) {
disp->task[i] = NULL;
result = isc_task_create(taskmgr, 0, &disp->task[i]);
*dispp = disp;
}
-/*
- * It is important to lock the manager while we are deleting the dispatch,
- * since dns_dispatch_getudp will call dispatch_find, which returns to
- * the caller a dispatch but does not attach to it until later. _getudp
- * locks the manager, however, so locking it here will keep us from attaching
- * to a dispatcher that is in the process of going away.
- */
void
dns_dispatch_detach(dns_dispatch_t **dispp) {
dns_dispatch_t *disp = NULL;
REQUIRE(dest != NULL);
REQUIRE(resp != NULL && *resp == NULL);
REQUIRE(idp != NULL);
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- REQUIRE(sockmgr != NULL);
- }
+ REQUIRE(disp->socktype == isc_sockettype_tcp || sockmgr != NULL);
LOCK(&disp->lock);
return (ISC_R_QUOTA);
}
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0 &&
+ if (disp->socktype == isc_sockettype_udp &&
disp->nsockets > DNS_DISPATCH_SOCKSQUOTA)
{
dispsocket_t *oldestsocket = NULL;
qid = DNS_QID(disp);
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
+ if (disp->socktype == isc_sockettype_udp) {
/*
* Get a separate UDP socket with a random port number.
*/
inc_stats(disp->mgr, dns_resstatscounter_dispsockfail);
return (result);
}
- } else {
- localport = disp->localport;
}
/*
UNLOCK(&disp->lock);
+ INSIST(disp->socktype == isc_sockettype_tcp || res->dispsocket != NULL);
+
*idp = id;
*resp = res;
- if ((disp->attributes & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- INSIST(res->dispsocket != NULL);
- }
-
return (ISC_R_SUCCESS);
}
dns_dispatch_getentrysocket(dns_dispentry_t *resp) {
REQUIRE(VALID_RESPONSE(resp));
- if (resp->dispsocket != NULL) {
+ if (resp->disp->socktype == isc_sockettype_tcp) {
+ return (resp->disp->socket);
+ } else if (resp->dispsocket != NULL) {
return (resp->dispsocket->socket);
} else {
return (NULL);
dns_dispatch_changeattributes(dns_dispatch_t *disp, unsigned int attributes,
unsigned int mask) {
REQUIRE(VALID_DISPATCH(disp));
- /* Exclusive attribute can only be set on creation */
- REQUIRE((attributes & DNS_DISPATCHATTR_EXCLUSIVE) == 0);
LOCK(&disp->lock);
LOCK(&mgr->lock);
for (i = 1; i < n; i++) {
dset->dispatches[i] = NULL;
- result = dispatch_createudp(
- mgr, sockmgr, taskmgr, &source->local,
- source->maxrequests, source->attributes,
- &dset->dispatches[i], source->socket);
+ result = dispatch_createudp(mgr, sockmgr, taskmgr,
+ &source->local, source->maxrequests,
+ source->attributes,
+ &dset->dispatches[i]);
if (result != ISC_R_SUCCESS) {
goto fail;
}
return (result);
}
-void
-dns_dispatchset_cancelall(dns_dispatchset_t *dset, isc_task_t *task) {
- int i;
-
- REQUIRE(dset != NULL);
-
- for (i = 0; i < dset->ndisp; i++) {
- isc_socket_t *sock = NULL;
- sock = dns_dispatch_getsocket(dset->dispatches[i]);
- isc_socket_cancel(sock, task, ISC_SOCKCANCEL_ALL);
- }
-}
-
void
dns_dispatchset_destroy(dns_dispatchset_t **dsetp) {
dns_dispatchset_t *dset = NULL;
* _MAKEQUERY
* The dispatcher can be used to issue queries to other servers, and
* accept replies from them.
- *
- * _EXCLUSIVE
- * A separate socket will be used on-demand for each transaction.
*/
#define DNS_DISPATCHATTR_PRIVATE 0x00000001U
#define DNS_DISPATCHATTR_TCP 0x00000002U
#define DNS_DISPATCHATTR_IPV6 0x00000010U
#define DNS_DISPATCHATTR_MAKEQUERY 0x00000040U
#define DNS_DISPATCHATTR_CONNECTED 0x00000080U
-#define DNS_DISPATCHATTR_EXCLUSIVE 0x00000200U
/*@}*/
/*
*/
isc_result_t
-dns_dispatch_getudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
- isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
- unsigned int maxbuffers, unsigned int maxrequests,
- unsigned int buckets, unsigned int increment,
- unsigned int attributes, dns_dispatch_t **dispp);
+dns_dispatch_createudp(dns_dispatchmgr_t *mgr, isc_socketmgr_t *sockmgr,
+ isc_taskmgr_t *taskmgr, const isc_sockaddr_t *localaddr,
+ unsigned int maxbuffers, unsigned int maxrequests,
+ unsigned int buckets, unsigned int increment,
+ unsigned int attributes, dns_dispatch_t **dispp);
/*%<
- * Attach to existing dns_dispatch_t if one is found with dns_dispatchmgr_find,
- * otherwise create a new UDP dispatch.
+ * Create a new UDP dispatch.
*
* Requires:
*\li All pointer parameters be valid for their respective types.
isc_socket_t *
dns_dispatch_getsocket(dns_dispatch_t *disp);
/*%<
- * Return the socket associated with this dispatcher.
+ * Return the socket associated with dispatcher or dispatch entry.
*
* Requires:
*\li disp is valid.
*\li dsetp != NULL, *dsetp == NULL
*/
-void
-dns_dispatchset_cancelall(dns_dispatchset_t *dset, isc_task_t *task);
-/*%<
- * Cancel socket operations for the dispatches in 'dset'.
- */
-
void
dns_dispatchset_destroy(dns_dispatchset_t **dsetp);
/*%<
req_send(dns_request_t *request, isc_task_t *task,
const isc_sockaddr_t *address) {
isc_region_t r;
- isc_socket_t *sock;
- isc_socketevent_t *sendevent;
+ isc_socket_t *sock = NULL;
+ isc_socketevent_t *sendevent = NULL;
isc_result_t result;
req_log(ISC_LOG_DEBUG(3), "req_send: request %p", request);
REQUIRE(VALID_REQUEST(request));
+
sock = req_getsocket(request);
isc_buffer_usedregion(request->query, &r);
/*
dns_dispatch_attach(disp, dispatchp);
return (ISC_R_SUCCESS);
}
- attrs = 0;
- attrs |= DNS_DISPATCHATTR_UDP;
+ attrs = DNS_DISPATCHATTR_UDP;
switch (isc_sockaddr_pf(srcaddr)) {
case PF_INET:
attrs |= DNS_DISPATCHATTR_IPV4;
default:
return (ISC_R_NOTIMPLEMENTED);
}
- return (dns_dispatch_getudp(requestmgr->dispatchmgr,
- requestmgr->socketmgr, requestmgr->taskmgr,
- srcaddr, 32768, 32768, 16411, 16433, attrs,
- dispatchp));
+
+ return (dns_dispatch_createudp(requestmgr->dispatchmgr,
+ requestmgr->socketmgr,
+ requestmgr->taskmgr, srcaddr, 32768,
+ 32768, 16411, 16433, attrs, dispatchp));
}
static isc_result_t
static isc_socket_t *
req_getsocket(dns_request_t *request) {
- unsigned int dispattr;
- isc_socket_t *sock;
-
- dispattr = dns_dispatch_getattributes(request->dispatch);
- if ((dispattr & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- INSIST(request->dispentry != NULL);
- sock = dns_dispatch_getentrysocket(request->dispentry);
- } else {
- sock = dns_dispatch_getsocket(request->dispatch);
- }
-
- return (sock);
+ return (dns_dispatch_getentrysocket(request->dispentry));
}
static void
*/
static void
req_cancel(dns_request_t *request) {
- isc_socket_t *sock;
- unsigned int dispattr;
+ isc_socket_t *sock = NULL;
REQUIRE(VALID_REQUEST(request));
if (request->timer != NULL) {
isc_timer_detach(&request->timer);
}
- dispattr = dns_dispatch_getattributes(request->dispatch);
- sock = NULL;
+
if (DNS_REQUEST_CONNECTING(request) || DNS_REQUEST_SENDING(request)) {
- if ((dispattr & DNS_DISPATCHATTR_EXCLUSIVE) != 0) {
- if (request->dispentry != NULL) {
- sock = dns_dispatch_getentrysocket(
- request->dispentry);
- }
- } else {
- sock = dns_dispatch_getsocket(request->dispatch);
+ if (request->dispentry != NULL) {
+ sock = dns_dispatch_getentrysocket(request->dispentry);
}
if (DNS_REQUEST_CONNECTING(request) && sock != NULL) {
isc_socket_cancel(sock, NULL, ISC_SOCKCANCEL_CONNECT);
isc_mem_t *mctx;
dns_dispatchmgr_t *dispatchmgr;
dns_dispatch_t *dispatch;
- bool exclusivesocket;
dns_adbaddrinfo_t *addrinfo;
isc_socket_t *tcpsocket;
isc_time_t start;
unsigned int options;
dns_dispatchmgr_t *dispatchmgr;
dns_dispatchset_t *dispatches4;
- bool exclusivev4;
dns_dispatchset_t *dispatches6;
isc_dscp_t querydscp4;
isc_dscp_t querydscp6;
- bool exclusivev6;
unsigned int nbuckets;
fctxbucket_t *buckets;
zonebucket_t *dbuckets;
isc_socket_cancel(query->tcpsocket, NULL,
ISC_SOCKCANCEL_CONNECT);
} else if (query->dispentry != NULL) {
- INSIST(query->exclusivesocket);
sock = dns_dispatch_getentrysocket(query->dispentry);
if (sock != NULL) {
isc_socket_cancel(sock, NULL,
/*
* Cancel the pending send.
*/
- if (query->exclusivesocket && query->dispentry != NULL) {
+ if (query->dispentry != NULL) {
sock = dns_dispatch_getentrysocket(query->dispentry);
} else {
sock = dns_dispatch_getsocket(query->dispatch);
* a dispatch for it here. Otherwise we use the resolver's
* shared dispatch.
*/
- query->dispatchmgr = res->dispatchmgr;
if (res->view->peers != NULL) {
dns_peer_t *peer = NULL;
isc_netaddr_t dstip;
result = ISC_R_NOTIMPLEMENTED;
goto cleanup_query;
}
- result = dns_dispatch_getudp(
+ result = dns_dispatch_createudp(
res->dispatchmgr, res->socketmgr, res->taskmgr,
&addr, 20000, 32768, 16411, 16433, attrs,
&query->dispatch);
dns_dispatch_attach(
dns_resolver_dispatchv4(res),
&query->dispatch);
- query->exclusivesocket = res->exclusivev4;
dscp = dns_resolver_getquerydscp4(fctx->res);
break;
case PF_INET6:
dns_dispatch_attach(
dns_resolver_dispatchv6(res),
&query->dispatch);
- query->exclusivesocket = res->exclusivev6;
dscp = dns_resolver_getquerydscp6(fctx->res);
break;
default:
static inline isc_socket_t *
query2sock(const resquery_t *query) {
- if (query->exclusivesocket) {
- return (dns_dispatch_getentrysocket(query->dispentry));
- } else {
- return (dns_dispatch_getsocket(query->dispatch));
- }
+ return (dns_dispatch_getentrysocket(query->dispentry));
}
static inline size_t
*/
if (!tcp) {
address = &query->addrinfo->sockaddr;
- if (query->exclusivesocket) {
- result = isc_socket_connect(sock, address, task,
- resquery_udpconnected,
- query);
- if (result != ISC_R_SUCCESS) {
- goto cleanup_message;
- }
- query->connects++;
+ result = isc_socket_connect(sock, address, task,
+ resquery_udpconnected, query);
+ if (result != ISC_R_SUCCESS) {
+ goto cleanup_message;
}
+ query->connects++;
}
isc_buffer_usedregion(buffer, &r);
* We are connected. Create a dispatcher and
* send the query.
*/
- attrs = 0;
- attrs |= DNS_DISPATCHATTR_TCP;
- attrs |= DNS_DISPATCHATTR_PRIVATE;
- attrs |= DNS_DISPATCHATTR_CONNECTED;
+ attrs = DNS_DISPATCHATTR_TCP |
+ DNS_DISPATCHATTR_PRIVATE |
+ DNS_DISPATCHATTR_CONNECTED |
+ DNS_DISPATCHATTR_MAKEQUERY;
if (isc_sockaddr_pf(&query->addrinfo->sockaddr) ==
AF_INET) {
attrs |= DNS_DISPATCHATTR_IPV4;
} else {
attrs |= DNS_DISPATCHATTR_IPV6;
}
- attrs |= DNS_DISPATCHATTR_MAKEQUERY;
result = dns_dispatch_createtcp(
query->dispatchmgr, query->tcpsocket,
rctx->next_server = true;
/*
- * If this is a network error on an exclusive query
- * socket, mark the server as bad so that we won't try
- * it for this fetch again. Also adjust finish and
- * no_response so that we penalize this address in SRTT
- * adjustment later.
+ * If this is a network error, mark the server as bad so
+ * that we won't try it for this fetch again. Also adjust
+ * finish and no_response so that we penalize this address
+ * in SRTT adjustment later.
*/
- if (query->exclusivesocket &&
- (devent->result == ISC_R_HOSTUNREACH ||
- devent->result == ISC_R_NETUNREACH ||
- devent->result == ISC_R_CONNREFUSED ||
- devent->result == ISC_R_CANCELED))
+ if (devent->result == ISC_R_HOSTUNREACH ||
+ devent->result == ISC_R_NETUNREACH ||
+ devent->result == ISC_R_CONNREFUSED ||
+ devent->result == ISC_R_CANCELED)
{
rctx->broken_server = devent->result;
rctx->broken_type = badns_unreachable;
unsigned int i, buckets_created = 0, dbuckets_created = 0;
isc_task_t *task = NULL;
char name[16];
- unsigned dispattr;
/*
* Create a resolver.
if (dispatchv4 != NULL) {
dns_dispatchset_create(view->mctx, socketmgr, taskmgr,
dispatchv4, &res->dispatches4, ndisp);
- dispattr = dns_dispatch_getattributes(dispatchv4);
- res->exclusivev4 = (dispattr & DNS_DISPATCHATTR_EXCLUSIVE);
}
if (dispatchv6 != NULL) {
dns_dispatchset_create(view->mctx, socketmgr, taskmgr,
dispatchv6, &res->dispatches6, ndisp);
- dispattr = dns_dispatch_getattributes(dispatchv6);
- res->exclusivev6 = (dispattr & DNS_DISPATCHATTR_EXCLUSIVE);
}
isc_mutex_init(&res->lock);
{
fctx_shutdown(fctx);
}
- if (res->dispatches4 != NULL && !res->exclusivev4) {
- dns_dispatchset_cancelall(res->dispatches4,
- res->buckets[i].task);
- }
- if (res->dispatches6 != NULL && !res->exclusivev6) {
- dns_dispatchset_cancelall(res->dispatches6,
- res->buckets[i].task);
- }
atomic_store(&res->buckets[i].exiting, true);
if (ISC_LIST_EMPTY(res->buckets[i].fctxs)) {
INSIST(res->activebuckets > 0);
isc_sockaddr_any(&any);
attrs = DNS_DISPATCHATTR_IPV4 | DNS_DISPATCHATTR_UDP;
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, &any, 6,
- 1024, 17, 19, attrs, &disp);
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr, &any,
+ 6, 1024, 17, 19, attrs, &disp);
if (result != ISC_R_SUCCESS) {
return (result);
}
isc_result_t result;
isc_socket_t *sock = NULL;
- isc_socket_attach(dns_dispatch_getsocket(dispatch), &sock);
+ isc_socket_attach(dns_dispatch_getentrysocket(dispentry), &sock);
result = isc_socket_sendto(sock, event->ev_arg, task, senddone, sock,
&local, NULL);
assert_int_equal(result, ISC_R_SUCCESS);
ina.s_addr = htonl(INADDR_LOOPBACK);
isc_sockaddr_fromin(&local, &ina, 0);
attrs = DNS_DISPATCHATTR_IPV4 | DNS_DISPATCHATTR_UDP;
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, &local, 6,
- 1024, 17, 19, attrs, &dispatch);
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr, &local,
+ 6, 1024, 17, 19, attrs, &dispatch);
assert_int_equal(result, ISC_R_SUCCESS);
/*
assert_int_equal(result, ISC_R_SUCCESS);
result = dns_dispatch_addresponse(dispatch, 0, &local, task, response,
- NULL, &id, &dispentry, NULL);
+ NULL, &id, &dispentry, socketmgr);
assert_int_equal(result, ISC_R_SUCCESS);
memset(message, 0, sizeof(message));
assert_int_equal(result, ISC_R_SUCCESS);
isc_sockaddr_any(&local);
- result = dns_dispatch_getudp(dispatchmgr, socketmgr, taskmgr, &local,
- 100, 100, 100, 500, 0, &dispatch);
+ result = dns_dispatch_createudp(dispatchmgr, socketmgr, taskmgr, &local,
+ 100, 100, 100, 500, 0, &dispatch);
assert_int_equal(result, ISC_R_SUCCESS);
return (0);