--- hosts_ctl.c.orig +++ hosts_ctl.c @@ -29,10 +29,12 @@ char *user; { struct request_info request; - return (hosts_access(request_init(&request, - RQ_DAEMON, daemon, - RQ_CLIENT_NAME, name, - RQ_CLIENT_ADDR, addr, - RQ_USER, user, - 0))); + request_init(&request, RQ_DAEMON, daemon, + RQ_CLIENT_NAME, name, + RQ_CLIENT_ADDR, addr, + RQ_USER, user, + 0); + sock_hostnofd(&request); + + return (hosts_access(&request)); } --- socket.c.orig +++ socket.c @@ -140,6 +140,53 @@ struct request_info *request; #endif } + + +/* sock_hostnofd - look up endpoint addresses and install conversion methods */ + +void sock_hostnofd(request) +struct request_info *request; +{ + static struct sockaddr_storage client; + struct addrinfo hints, *res; + int ret; + char *host; + + /* If the address field is non-empty and non-unknown and if the hostname + * field is empty or unknown, use the address field to get the sockaddr + * and hostname. */ + if (strlen(request->client->addr) && + HOSTNAME_KNOWN(request->client->addr) && + (!strlen(request->client->addr) || + !HOSTNAME_KNOWN(request->client->name))) + host = request->client->addr; + else + return; + + memset(&hints, 0, sizeof(hints)); + hints.ai_family = AF_INET6; + hints.ai_socktype = SOCK_STREAM; + hints.ai_flags = AI_PASSIVE | AI_NUMERICHOST; + + ret = getaddrinfo(host, NULL, &hints, &res); + if (ret != 0) { + hints.ai_family = AF_INET; + ret = getaddrinfo(host, NULL, &hints, &res); + } + + if (ret != 0) { + tcpd_warn("can't resolve hostname (%s): %s", host, gai_strerror(ret)); + } else { + sock_methods(request); + + memcpy(&client, res->ai_addr, res->ai_addrlen); + request->client->sin = (struct sockaddr *)&client; + freeaddrinfo(res); + + request->client->name[0] = 0; + } +} + /* sock_hostaddr - map endpoint address to printable form */ void sock_hostaddr(host) --- tcpd.h.orig +++ tcpd.h @@ -174,10 +174,12 @@ extern char *eval_server(); /* whatever #ifdef __STDC__ extern void sock_host(struct request_info *); +extern void sock_hostnofd(struct request_info *); extern void sock_hostname(struct host_info *); extern void sock_hostaddr(struct host_info *); #else extern void sock_host(); /* look up endpoint addresses */ +extern void sock_hostnofd(); extern void sock_hostname(); /* translate address to hostname */ extern void sock_hostaddr(); /* address to printable address */ #endif