summaryrefslogtreecommitdiffstats
path: root/usr.sbin/ypserv
diff options
context:
space:
mode:
authorume <ume@FreeBSD.org>2005-05-02 09:34:07 +0000
committerume <ume@FreeBSD.org>2005-05-02 09:34:07 +0000
commit359f287f5157e24e483c8fdd6b54a0ba7b4701dc (patch)
treeef6b41df762c09c900d402c86a08b493f3f1ebc0 /usr.sbin/ypserv
parentd1bb5343c0ad00dbe06df9eba8310e5c10311aa4 (diff)
downloadFreeBSD-src-359f287f5157e24e483c8fdd6b54a0ba7b4701dc.zip
FreeBSD-src-359f287f5157e24e483c8fdd6b54a0ba7b4701dc.tar.gz
teach IPv6 to async DNS resolver in ypserv:
- query AAAA RR on ipnodes.byname query. - query .ip6.arpa. on ipnodes.byaddr query.
Diffstat (limited to 'usr.sbin/ypserv')
-rw-r--r--usr.sbin/ypserv/yp_dnslookup.c67
-rw-r--r--usr.sbin/ypserv/yp_extern.h4
-rw-r--r--usr.sbin/ypserv/yp_server.c17
3 files changed, 61 insertions, 27 deletions
diff --git a/usr.sbin/ypserv/yp_dnslookup.c b/usr.sbin/ypserv/yp_dnslookup.c
index a5c8eab..75c3820 100644
--- a/usr.sbin/ypserv/yp_dnslookup.c
+++ b/usr.sbin/ypserv/yp_dnslookup.c
@@ -69,12 +69,15 @@ parse(struct hostent *hp)
{
static char result[MAXHOSTNAMELEN * 2];
int len,i;
- struct in_addr addr;
+ char addr[46];
if (hp == NULL)
return(NULL);
- len = 16 + strlen(hp->h_name);
+ if (inet_ntop(hp->h_addrtype, hp->h_addr, addr, sizeof(addr)) == NULL)
+ return(NULL);
+
+ len = strlen(addr) + 1 + strlen(hp->h_name);
for (i = 0; hp->h_aliases[i]; i++)
len += strlen(hp->h_aliases[i]) + 1;
len++;
@@ -83,10 +86,7 @@ parse(struct hostent *hp)
return(NULL);
bzero(result, sizeof(result));
-
- bcopy(hp->h_addr, &addr, sizeof(struct in_addr));
- snprintf(result, sizeof(result), "%s %s", inet_ntoa(addr), hp->h_name);
-
+ snprintf(result, sizeof(result), "%s %s", addr, hp->h_name);
for (i = 0; hp->h_aliases[i]; i++) {
strcat(result, " ");
strcat(result, hp->h_aliases[i]);
@@ -95,7 +95,7 @@ parse(struct hostent *hp)
return ((char *)&result);
}
-#define MAXPACKET 1024
+#define MAXPACKET (64*1024)
#define DEF_TTL 50
#define BY_DNS_ID 1
@@ -116,7 +116,9 @@ struct circleq_dnsentry {
unsigned short prot_type;
char **domain;
char *name;
- struct in_addr addr;
+ int addrtype;
+ int addrlen;
+ uint32_t addr[4]; /* IPv4 or IPv6 */
TAILQ_ENTRY(circleq_dnsentry) links;
};
@@ -386,8 +388,9 @@ yp_run_dnsq(void)
if (hent != NULL) {
if (q->type == T_PTR) {
- hent->h_addr = (char *)&q->addr.s_addr;
- hent->h_length = sizeof(struct in_addr);
+ hent->h_addr = (char *)q->addr;
+ hent->h_addrtype = q->addrtype;
+ hent->h_length = q->addrlen;
}
}
@@ -408,7 +411,7 @@ yp_run_dnsq(void)
* Queue and transmit an asynchronous DNS hostname lookup.
*/
ypstat
-yp_async_lookup_name(struct svc_req *rqstp, char *name)
+yp_async_lookup_name(struct svc_req *rqstp, char *name, int af)
{
register struct circleq_dnsentry *q;
socklen_t len;
@@ -431,7 +434,7 @@ yp_async_lookup_name(struct svc_req *rqstp, char *name)
if ((q = yp_malloc_dnsent()) == NULL)
return(YP_YPERR);
- q->type = T_A;
+ q->type = (af == AF_INET) ? T_A : T_AAAA;
q->ttl = DEF_TTL;
q->xprt = rqstp->rq_xprt;
q->ypvers = rqstp->rq_vers;
@@ -463,13 +466,14 @@ yp_async_lookup_name(struct svc_req *rqstp, char *name)
* Queue and transmit an asynchronous DNS IP address lookup.
*/
ypstat
-yp_async_lookup_addr(struct svc_req *rqstp, char *addr)
+yp_async_lookup_addr(struct svc_req *rqstp, char *addr, int af)
{
register struct circleq_dnsentry *q;
- char buf[MAXHOSTNAMELEN];
+ char buf[MAXHOSTNAMELEN], *qp;
+ uint32_t abuf[4]; /* IPv4 or IPv6 */
+ u_char *uaddr = (u_char *)abuf;
socklen_t len;
- int a, b, c, d;
- int type;
+ int type, n;
/* Check for SOCK_DGRAM or SOCK_STREAM -- we need to know later */
type = -1;
@@ -488,10 +492,29 @@ yp_async_lookup_addr(struct svc_req *rqstp, char *addr)
if ((q = yp_malloc_dnsent()) == NULL)
return(YP_YPERR);
- if (sscanf(addr, "%d.%d.%d.%d", &a, &b, &c, &d) != 4)
- return(YP_NOKEY);
-
- snprintf(buf, sizeof(buf), "%d.%d.%d.%d.in-addr.arpa", d, c, b, a);
+ switch (af) {
+ case AF_INET:
+ if (inet_aton(addr, (struct in_addr *)uaddr) != 1)
+ return(YP_NOKEY);
+ snprintf(buf, sizeof(buf), "%u.%u.%u.%u.in-addr.arpa",
+ (uaddr[3] & 0xff), (uaddr[2] & 0xff),
+ (uaddr[1] & 0xff), (uaddr[0] & 0xff));
+ len = INADDRSZ;
+ break;
+ case AF_INET6:
+ if (inet_pton(af, addr, uaddr) != 1)
+ return(YP_NOKEY);
+ qp = buf;
+ for (n = IN6ADDRSZ - 1; n >= 0; n--) {
+ qp += (size_t)sprintf(qp, "%x.%x.", uaddr[n] & 0xf,
+ (uaddr[n] >> 4) & 0xf);
+ }
+ strlcat(buf, "ip6.arpa", sizeof(buf));
+ len = IN6ADDRSZ;
+ break;
+ default:
+ return(YP_YPERR);
+ }
if (debug)
yp_error("DNS address is: %s", buf);
@@ -513,7 +536,9 @@ yp_async_lookup_addr(struct svc_req *rqstp, char *addr)
return(YP_YPERR);
}
- inet_aton(addr, &q->addr);
+ memcpy(q->addr, uaddr, len);
+ q->addrlen = len;
+ q->addrtype = af;
q->name = strdup(buf);
TAILQ_INSERT_HEAD(&qhead, q, links);
pending++;
diff --git a/usr.sbin/ypserv/yp_extern.h b/usr.sbin/ypserv/yp_extern.h
index 553e296..2e574b6 100644
--- a/usr.sbin/ypserv/yp_extern.h
+++ b/usr.sbin/ypserv/yp_extern.h
@@ -111,5 +111,5 @@ extern unsigned long svcudp_get_xid(SVCXPRT *);
extern int yp_init_resolver(void);
extern void yp_run_dnsq(void);
extern void yp_prune_dnsq(void);
-extern ypstat yp_async_lookup_name(struct svc_req *, char *);
-extern ypstat yp_async_lookup_addr(struct svc_req *, char *);
+extern ypstat yp_async_lookup_name(struct svc_req *, char *, int);
+extern ypstat yp_async_lookup_addr(struct svc_req *, char *, int);
diff --git a/usr.sbin/ypserv/yp_server.c b/usr.sbin/ypserv/yp_server.c
index e6d82d6..8bd658b 100644
--- a/usr.sbin/ypserv/yp_server.c
+++ b/usr.sbin/ypserv/yp_server.c
@@ -166,9 +166,10 @@ ypproc_match_2_svc(ypreq_key *argp, struct svc_req *rqstp)
#ifdef DB_CACHE
if (result.stat != YP_TRUE &&
(yp_testflag(argp->map, argp->domain, YP_INTERDOMAIN) ||
- (strstr(argp->map, "hosts") && do_dns))) {
+ ((strstr(argp->map, "hosts") || strstr(argp->map, "ipnode")) && do_dns))) {
#else
- if (do_dns && result.stat != YP_TRUE && strstr(argp->map, "hosts")) {
+ if (do_dns && result.stat != YP_TRUE &&
+ (strstr(argp->map, "hosts") || strstr(argp->map, "ipnode"))) {
#endif
char nbuf[YPMAXRECORD];
@@ -180,9 +181,17 @@ ypproc_match_2_svc(ypreq_key *argp, struct svc_req *rqstp)
yp_error("doing DNS lookup of %s", nbuf);
if (!strcmp(argp->map, "hosts.byname"))
- result.stat = yp_async_lookup_name(rqstp, nbuf);
+ result.stat = yp_async_lookup_name(rqstp, nbuf,
+ AF_INET);
else if (!strcmp(argp->map, "hosts.byaddr"))
- result.stat = yp_async_lookup_addr(rqstp, nbuf);
+ result.stat = yp_async_lookup_addr(rqstp, nbuf,
+ AF_INET);
+ else if (!strcmp(argp->map, "ipnodes.byname"))
+ result.stat = yp_async_lookup_name(rqstp, nbuf,
+ AF_INET6);
+ else if (!strcmp(argp->map, "ipnodes.byaddr"))
+ result.stat = yp_async_lookup_addr(rqstp, nbuf,
+ AF_INET6);
if (result.stat == YP_TRUE)
return(NULL);
OpenPOWER on IntegriCloud