Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Why is h_addr_list in struct hostent a char ** instead of struct in_addr **?

I am new to network programming. The following structure definitions are quite confusing to me. Here h_addr_list is a defined as string array, but it is used to store array of in_addr structures. Why didn't it define as struct in_addr **h_addr_list rather than char **h_addr_list?

struct hostent 
{
    char *h_name;       /* Official domain name of host */
    char **h_aliases;   /* Null-terminated array of domain names */
    int h_addrtype;     /* Host address type (AF_INET) */
    int h_length;       /* Length of an address, in bytes */
    char **h_addr_list;     /* Null-terminated array of in_addr structs */
};


struct in_addr 
{
    unsigned int s_addr; /* Network byte order (big-endian) */
};
like image 270
noufal Avatar asked Dec 18 '13 13:12

noufal


1 Answers

The structure definition dates back to the era before C supported void * (or void at all, or prototypes). In those days, char * was the 'universal pointer'. This accounts for some of the weirdnesses of the networking function interfaces.

It also dates back to the era when there were many different networking systems (IPX/SPX, SNA, TCP/IP, …). These days, TCP/IP is dominant, but even now, you could have an array of IPv4 or an array of IPv6 addresses being returned, so specifying either struct in_addr or struct in6_addr would cause problems.

The intention was that you'd have an array of pointers to appropriate structure types. Nowadays, it would be written void **h_addr_list — an array of void *. But this option was not available when the structures were first defined, and the rest is history (you don't change an interface after it is standardized if you can avoid it).

like image 86
Jonathan Leffler Avatar answered Oct 20 '22 20:10

Jonathan Leffler