diff options
Diffstat (limited to 'lib/dns/resolver.c')
-rw-r--r-- | lib/dns/resolver.c | 43 |
1 files changed, 38 insertions, 5 deletions
diff --git a/lib/dns/resolver.c b/lib/dns/resolver.c index 16d22e08b332e..93f10f5dd3e39 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 2008/01/17 23:45:27 tbox Exp $ */ +/* $Id: resolver.c,v 1.218.2.18.4.77.2.1 2008/05/22 21:11:15 each Exp $ */ #include <config.h> @@ -1070,17 +1070,50 @@ fctx_query(fetchctx_t *fctx, dns_adbaddrinfo_t *addrinfo, * A dispatch will be created once the connect succeeds. */ } else { + isc_sockaddr_t localaddr; + unsigned int attrs, attrmask; + dns_dispatch_t *disp_base; + + attrs = 0; + attrs |= DNS_DISPATCHATTR_UDP; + attrs |= DNS_DISPATCHATTR_RANDOMPORT; + + attrmask = 0; + attrmask |= DNS_DISPATCHATTR_UDP; + attrmask |= DNS_DISPATCHATTR_TCP; + attrmask |= DNS_DISPATCHATTR_IPV4; + attrmask |= DNS_DISPATCHATTR_IPV6; + switch (isc_sockaddr_pf(&addrinfo->sockaddr)) { - case PF_INET: - dns_dispatch_attach(res->dispatchv4, &query->dispatch); + case AF_INET: + disp_base = res->dispatchv4; + attrs |= DNS_DISPATCHATTR_IPV4; break; - case PF_INET6: - dns_dispatch_attach(res->dispatchv6, &query->dispatch); + case AF_INET6: + disp_base = res->dispatchv6; + attrs |= DNS_DISPATCHATTR_IPV6; break; default: result = ISC_R_NOTIMPLEMENTED; goto cleanup_query; } + + result = dns_dispatch_getlocaladdress(disp_base, &localaddr); + if (result != ISC_R_SUCCESS) + goto cleanup_query; + if (isc_sockaddr_getport(&localaddr) == 0) { + result = dns_dispatch_getudp(res->dispatchmgr, + res->socketmgr, + res->taskmgr, + &localaddr, + 4096, 1000, 32768, + 16411, 16433, + attrs, attrmask, + &query->dispatch); + if (result != ISC_R_SUCCESS) + goto cleanup_query; + } else + dns_dispatch_attach(disp_base, &query->dispatch); /* * We should always have a valid dispatcher here. If we * don't support a protocol family, then its dispatcher |