freebsd-skq/contrib/ntp/libntp/socktohost.c
glebius 9163b6ba3b MFV ntp-4.2.8p4 (r289715)
Security:       VuXML: c4a18a12-77fc-11e5-a687-206a8a720317
Security:	CVE-2015-7871
Security:	CVE-2015-7855
Security:	CVE-2015-7854
Security:	CVE-2015-7853
Security:	CVE-2015-7852
Security:	CVE-2015-7851
Security:	CVE-2015-7850
Security:	CVE-2015-7849
Security:	CVE-2015-7848
Security:	CVE-2015-7701
Security:	CVE-2015-7703
Security:	CVE-2015-7704, CVE-2015-7705
Security:	CVE-2015-7691, CVE-2015-7692, CVE-2015-7702
Security:	http://support.ntp.org/bin/view/Main/SecurityNotice#October_2015_NTP_Security_Vulner
Sponsored by:	Nginx, Inc.
2015-10-22 19:42:57 +00:00

111 lines
2.4 KiB
C

/*
* socktoa - return a numeric host name from a sockaddr_storage structure
*/
#include <config.h>
#include <sys/types.h>
#ifdef HAVE_SYS_SOCKET_H
#include <sys/socket.h>
#endif
#ifdef HAVE_NETINET_IN_H
#include <netinet/in.h>
#endif
#include <arpa/inet.h>
#include <stdio.h>
#include "ntp_fp.h"
#include "lib_strbuf.h"
#include "ntp_stdlib.h"
#include "ntp.h"
#include "ntp_debug.h"
const char *
socktohost(
const sockaddr_u *sock
)
{
const char svc[] = "ntp";
char * pbuf;
char * pliar;
int gni_flags;
struct addrinfo hints;
struct addrinfo * alist;
struct addrinfo * ai;
sockaddr_u addr;
size_t octets;
int a_info;
/* reverse the address to purported DNS name */
LIB_GETBUF(pbuf);
gni_flags = NI_DGRAM | NI_NAMEREQD;
if (getnameinfo(&sock->sa, SOCKLEN(sock), pbuf, LIB_BUFLENGTH,
NULL, 0, gni_flags))
return stoa(sock); /* use address */
TRACE(1, ("%s reversed to %s\n", stoa(sock), pbuf));
/*
* Resolve the reversed name and make sure the reversed address
* is among the results.
*/
ZERO(hints);
hints.ai_family = AF(sock);
hints.ai_protocol = IPPROTO_UDP;
hints.ai_socktype = SOCK_DGRAM;
hints.ai_flags = 0;
alist = NULL;
a_info = getaddrinfo(pbuf, svc, &hints, &alist);
if (a_info == EAI_NONAME
#ifdef EAI_NODATA
|| a_info == EAI_NODATA
#endif
) {
hints.ai_flags = AI_CANONNAME;
#ifdef AI_ADDRCONFIG
hints.ai_flags |= AI_ADDRCONFIG;
#endif
a_info = getaddrinfo(pbuf, svc, &hints, &alist);
}
#ifdef AI_ADDRCONFIG
/* Some older implementations don't like AI_ADDRCONFIG. */
if (a_info == EAI_BADFLAGS) {
hints.ai_flags &= ~AI_ADDRCONFIG;
a_info = getaddrinfo(pbuf, svc, &hints, &alist);
}
#endif
if (a_info)
goto forward_fail;
INSIST(alist != NULL);
for (ai = alist; ai != NULL; ai = ai->ai_next) {
/*
* Make a convenience sockaddr_u copy from ai->ai_addr
* because casting from sockaddr * to sockaddr_u * is
* risking alignment problems on platforms where
* sockaddr_u has stricter alignment than sockaddr,
* such as sparc.
*/
ZERO_SOCK(&addr);
octets = min(sizeof(addr), ai->ai_addrlen);
memcpy(&addr, ai->ai_addr, octets);
if (SOCK_EQ(sock, &addr))
break;
}
freeaddrinfo(alist);
if (ai != NULL)
return pbuf; /* forward check passed */
forward_fail:
TRACE(1, ("%s forward check lookup fail: %s\n", pbuf,
gai_strerror(a_info)));
LIB_GETBUF(pliar);
snprintf(pliar, LIB_BUFLENGTH, "%s (%s)", stoa(sock), pbuf);
return pliar;
}