getnameinfo()

Выполнить преобразование адреса в имя узла независимо от протокола

Прототип:

#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
int getnameinfo( const struct sockaddr *sa,
socklen_t salen,
char *host,
size_t hostlen,
char *serv,
size_t servlen,
int flags );

Аргументы:

sa
Указывает либо на структуру sockaddr_in (для IPv4) или на структуру sockaddr_in6 (для IPv6), содержащую IP адрес и номер порта.
salen
Размер структуры sockaddr_in или sockaddr_in6.
host
Указатель на буфер хоста.
hostlen
Размер буфера хоста.
serv
Указатель на буфер сервера.
servlen
Размер буфера сервера.
flags
Изменяет поведение по умолчанию для getnameinfo(). По умолчанию, полностью определённое имя домена (FQDN) для хоста ищется в DNS и возвращается из функции. Флаги определены в <netdb.h>:
NI_NOFQDN
Для локальных хостов возвращается только часть полного доменного имени узла.
NI_NUMERICHOST
Если данный флаг установлен, или если имя хоста не может быть обнаружено в DNS, вместо его имени возвращается числовая форма адреса хоста (например, путем вызова inet_ntop() вместо getnodebyaddr()).
NI_NAMEREQD
Если данный флаг установлен, ошибка возвращается, когда имя хоста не может быть найдено в DNS.
NI_NUMERICSERV
Если данный флаг установлен, возвращается числовая форма адреса службы (вместо ее имени), например номер порта. Может потребоваться два флага NI_NUMERICxxx для поддержки флага -n, который предоставляют многие команды.
NI_DGRAM
Указать, что служба является службой датаграмм. Следует вызвать getservbyport() со вторым аргументом udp вместо используемого по умолчанию tcp. Это требуется, поскольку некоторые порты (а именно, 512-514), имеют различные службы для UDP и TCP.

Библиотека:

libsocket

Описание:

Функция getnameinfo() определяет и выполняет протоколо-независимые преобразования "адрес-имя узла". Для простоты, можно думать об этом как о реализации обратной функциональности getaddrinfo() или приблизительной функциональности gethostbyaddr() или getservbyport().

Данная функция ищет IP-адрес и номер порта, предоставленные вызывающей стороной, в DNS и базе данных конкретной системы. Как для IP-адреса, так и для номера порта функция getnameinfo() возвращает текстовые строки в соответствующих буферах, предоставленных вызывающей стороной. Функция указывает на успешное завершение нулевым возвращаемым значением; ненулевое возвращаемое значение указывает на сбой.

Функция getnameinfo() возвращает имя узла, связанное с IP-адресом в буфере, на который указывает аргумент host. Аргумент hostlen указывает длину этого буфера.

Функция getnameinfo() возвращает имя службы, связанное с номером порта в буфере, на который указывает аргумент serv. Аргумент servlen указывает длину этого буфера.

Укажите ноль для hostlen или servlen, когда вызывающая сторона не ожидает ни одну из строк. В противном случае вызывающая сторона должна предоставить буферы, достаточно большие для хранения имени узла и имени службы, включая завершающие нулевые символы.

Большинство систем не предоставляют константы, указывающие максимальный размер FQDN или имени службы. Для помощи в распределении буферов при разработке приложения, в <netdb.h> определены следующие константы:

#define NI_MAXHOST 1025
#define NI_MAXSERV 32

Можно встретить первое значение в виде константы MAXDNAME в последних версиях <arpa/nameser.h> BIND; более поздние версии BIND определяют данную константу значением 256. Второе значение - это предположение, основанное на сервисах, перечисленных в текущем Assigned Numbers RFC. BIND (Berkeley Internet Name Domain) - это набор функций, реализующий протоколы системы доменных имен (DNS).

Расширение

Реализация допускает экспериментальную числовую нотацию IPv6-адресов с идентификатором области действия. Локальный адрес канала IPv6 отображается в виде строки вида fe80::1%ne0, когда в аргументе flags включен бит NI_WITHSCOPEID. Обозначения см. в getaddrinfo().

Возвращаемое значение:

0
Успешное завершение.
Ненулевое
значение

Возникла ошибка.

Коды ошибок:

EAI_AGAIN
Имя не может быть разрешено в настоящий момент. Последующие попытки могут увенчаться успехом.
EAI_BADFLAGS
Флаги имели недопустимые значения.
EAI_FAIL
Произошла неустранимая ошибка.
EAI_FAMILY
Семейство адресов не распознано или длина адреса недопустима для указанного семейства.
EAI_MEMORY
Произошла ошибка выделения памяти.
EAI_NONAME
Имя не разрешается для предоставленных параметров. NI_NAMEREQD установлен, и имя хоста не может быть определено, либо и host и hostname были пустыми.
EAI_SYSTEM
Произошла системная ошибка. Код ошибки можно найти в errno.

Примеры:

Следующий код получает числовое имя хоста и имя службы для данного адреса сокета. Нет жестко заданной ссылки на конкретное семейство адресов.

struct sockaddr *sa; /* input */
char hbuf[NI_MAXHOST], sbuf[NI_MAXSERV];
if ( getnameinfo( sa, sa->sa_len, hbuf, sizeof( hbuf ), sbuf,
sizeof(sbuf), NI_NUMERICHOST | NI_NUMERICSERV ) )
{
errx( 1, "could not get numeric hostname" );
/*NOTREACHED*/
}
printf( "host=%s, serv=%s\n", hbuf, sbuf );

The following version checks if the socket address has reverse address mapping.

struct sockaddr *sa; /* input */
char hbuf[NI_MAXHOST];
if ( getnameinfo( sa, sa->sa_len, hbuf, sizeof( hbuf ), NULL, 0,
NI_NAMEREQD ) )
{
errx( 1, "could not resolve hostname" );
/*NOTREACHED*/
}
printf( "host=%s\n", hbuf );

Классификация:

POSIX 1003.1

Точка остановки потока
Да
Обработчик прерываний
Нет
Обработчик сигналов
Нет
В потоке
Нет

Тематические ссылки:

getaddrinfo(), gethostbyaddr(), getservbyport(), /etc/hosts, /etc/nsswitch.conf, /etc/services, named




Предыдущий раздел: Описание API сетевой библиотеки