From: Chuck Lever Date: Tue, 24 Aug 2010 11:13:54 +0000 (-0400) Subject: libexport: Fix IP address check in check_netgroup() X-Git-Tag: nfs-utils-1-2-3-rc6~32 X-Git-Url: https://git.decadent.org.uk/gitweb/?a=commitdiff_plain;h=1bb84a09ff58d1314826945db2f3f1f63015e263;p=nfs-utils.git libexport: Fix IP address check in check_netgroup() Neil Brown reports that recent changes to replace gethostby{addr,name}(3) with get{addr,info}name(3) may have inadvertently broken netgroup support. There used to be a gethostbyaddr(3) call in the third paragraph in check_netgroup(). The reason for that gethostbyaddr(3) call was that the first innetgr(3) call has already confirmed that hname is not a member of the netgroup. We also need to confirm that, if hname happens to be an IP address, the hostname bound to that IP address is not a member of the netgroup, either. Fix this by restoring appropriate address to hostname mapping of hname before retrying the innetgr(3) call. See http://marc.info/?l=linux-nfs&m=128084830214653&w=2 . Introduced by commit 0509d3428f523776ddd9d6e9fa318587d3ec7d84. Reviewed-by: Neil Brown Signed-off-by: Chuck Lever Signed-off-by: Steve Dickson --- diff --git a/support/export/client.c b/support/export/client.c index b1a3a09..21001ce 100644 --- a/support/export/client.c +++ b/support/export/client.c @@ -490,14 +490,19 @@ static int check_netgroup(const nfs_client *clp, const struct addrinfo *ai) { const char *netgroup = clp->m_hostname + 1; - const char *hname = ai->ai_canonname; struct addrinfo *tmp = NULL; struct hostent *hp; + char *dot, *hname; int i, match; - char *dot; match = 0; + hname = strdup(ai->ai_canonname); + if (hname == NULL) { + xlog(D_GENERAL, "%s: no memory for strdup", __func__); + goto out; + } + /* First, try to match the hostname without * splitting off the domain */ if (innetgr(netgroup, hname, NULL, NULL)) { @@ -516,13 +521,21 @@ check_netgroup(const nfs_client *clp, const struct addrinfo *ai) } } - /* If hname is ip address convert to FQDN */ + /* If hname happens to be an IP address, convert it + * to a the canonical DNS name bound to this address. */ tmp = host_pton(hname); if (tmp != NULL) { + char *cname = host_canonname(tmp->ai_addr); freeaddrinfo(tmp); - if (innetgr(netgroup, hname, NULL, NULL)) { - match = 1; - goto out; + + /* The resulting FQDN may be in our netgroup. */ + if (cname != NULL) { + free(hname); + hname = cname; + if (innetgr(netgroup, hname, NULL, NULL)) { + match = 1; + goto out; + } } } @@ -533,9 +546,9 @@ check_netgroup(const nfs_client *clp, const struct addrinfo *ai) *dot = '\0'; match = innetgr(netgroup, hname, NULL, NULL); - *dot = '.'; out: + free(hname); return match; } #else /* !HAVE_INNETGR */