c - understanding the protocol family argument of socket() and result list of getaddrinfo() -
i had started network programming days ago there confusion need clear. have not studied networking or tcp/ip protocol before.
socket function argument:
the protocol family argument socket function denote set of protocols or protocol suite used communication.
is above interpretation correct?
if yes, means pf/af_inet , pf/af_inet6 2 different protocol suites. right? reason creating 2 different protocol suites , not 1 tcp/ip protocol suite 2 address families?
if not, protocol family denote function argument?
edit: don't have enough reputation answer own question editing
from unix network programming vol. 1, 3rd edition - section 4.2 socket function, sub-section - af_xxx verseus pf_xxx
the "
af_
" prefix stands "address family" , "pf_
" prefix stands "protocol family". historically, intent single protocol family might support multiple address families ,pf_
value used create socket ,af_
value used in socket addresses structures. in actually, protocol family supporting multiple address families has never been supported ,sys/socket.h
header definespf_
value given protocol equalaf_
value protocol. while there no guarantee equality between 2 true, should change existing protocols, lots of existing code break.so guess reason not creating 1
pf_inet
protocol family 2 address familiesaf_inet
,af_inet6
backward compatibility.
getaddrinfo:
the following code prints information each ip address returned getaddrinfo.
#define _posix_c_source 201112l #include <stdio.h> #include <string.h> #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <netdb.h> void print_family(struct addrinfo *aip) { printf(" family "); switch (aip->ai_family) { case af_inet: printf("inet"); break; case af_inet6: printf("inet6"); break; } } void print_type(struct addrinfo *aip) { printf(" type "); switch (aip->ai_socktype) { case sock_stream: printf("stream"); break; case sock_dgram: printf("datagram"); break; case sock_seqpacket: printf("seqpacket"); break; case sock_raw: printf("raw"); break; default: printf("unknown %d", aip->ai_socktype); } } void print_protocol(struct addrinfo *aip) { printf(" protocol "); switch (aip->ai_protocol) { case 0: printf("0"); break; case ipproto_tcp: printf("tcp"); break; case ipproto_udp: printf("udp"); break; case ipproto_raw: printf("raw"); case ipproto_sctp: printf("sctp"); break; default: printf("unknown %d", aip->ai_protocol); } } int main(int argc, char **argv) { struct addrinfo *ailist, *aip, hint; int err; if (argc != 3) { printf("usage: %s <hostname> <service>\n", argv[0]); printf("if 1 not applicable, provide null in place.\n"); return 1; } if (strcmp(argv[1], "null") == 0) argv[1] = null; if (strcmp(argv[2], "null") == 0) argv[2] = null; hint.ai_flags = 0; hint.ai_family = 0; hint.ai_socktype = 0; hint.ai_protocol = 0; hint.ai_addrlen = 0; hint.ai_canonname = null; hint.ai_addr = null; hint.ai_next = null; if ((err = getaddrinfo(argv[1], argv[2], &hint, &ailist)) != 0) { printf("getaddrinfo error: %s", gai_strerror(err)); return 2; } (aip = ailist; aip != null; aip = aip->ai_next) { struct sockaddr_in *sinp; struct sockaddr_in6 *sinp6; char buf[inet_addrstrlen]; const char *addr; print_family(aip); print_type(aip); print_protocol(aip); printf("\n\thost %s", aip->ai_canonname ? aip->ai_canonname : "-"); if (aip->ai_family == af_inet) { sinp = (struct sockaddr_in *) aip->ai_addr; addr = inet_ntop(af_inet, &sinp->sin_addr, buf, inet_addrstrlen); printf(" address %s", addr ? addr : "unknown"); printf(" port %d ", ntohs(sinp->sin_port)); } else if (aip->ai_family == af_inet6) { sinp6 = (struct sockaddr_in6 *) aip->ai_addr; addr = inet_ntop(af_inet6, &sinp6->sin6_addr, buf, inet6_addrstrlen); printf(" address %s", addr ? addr : "unknown"); printf(" port %d ", ntohs(sinp6->sin6_port)); } printf("\n"); } return 0; }
compiling , running above program on arch linux 4.4.11-1-lts x86-64.
running program as: ./prg localhost http
gives following result (for ipv4 addresses):-
family inet type stream protocol tcp host - address 127.0.0.1 port 80 family inet type datagram protocol udp host - address 127.0.0.1 port 80 family inet type stream protocol sctp host - address 127.0.0.1 port 80 family inet type seqpacket protocol sctp host - address 127.0.0.1 port 80
and command ./prg localhost null
result is:-
family inet type stream protocol tcp host - address 127.0.0.1 port 0 family inet type datagram protocol udp host - address 127.0.0.1 port 0 family inet type raw protocol 0 host - address 127.0.0.1 port 0
- my question how return result when service null? man page says port left uninitialized there nothing number of structures returned. why give addrinfo structure tcp , udp when service null , not sctp? sctp not in default list of protocols return structures when service null, if there such default?
from unix network programming vol. 1 3rd edition w. richard stevens
it acceptable
getaddrinfo
returnai_protocol
of 0 2sock_stream
structures if sufficient specify tcp (it not sufficient if system implements sctp, example), ,ai_protocol
of 0 2sock_dgram
structures if system doesn't implement othersock_dgram
protocols ip.
- as understood above line,
getaddrinfo
can return 0 protocol if there 1 protocol specified socket type.this acceptable.
system implementssctp
, maybe other protocolssock_dgram
socket types cannot return 0 protocol valuetcp
,udp
? why return protocol value of 0sock_raw
socket type there many protocols supported raw sockets underaf_inet
family?
the man page says
there several reasons why linked list may have more 1 addrinfo structure, including: network host multihomed, accessible on multiple protocols (e.g., both af_inet , af_inet6); or same service available multiple socket types (one sock_stream address , sock_dgram address, example).
- is saying "service available multiple socket types" same saying "service supported or available multiple protocols"?
changing line of code hint.ai_socktype=0
hint.ai_socktype=sock_stream
, running ./prg localhost http
gives following result:
family inet type stream protocol tcp host - address 127.0.0.1 port 80
- why did not give 1 structure
sctp
supportedsock_stream
socket type following result shows.
changing line in modified program hint.ai_protocol=0
tohint.ai_protocol=ipproto_sctp
, running ./prg localhost http
gives following result:
family inet type stream protocol sctp host - address 127.0.0.1 port 80
Comments
Post a Comment