16 网络IPC:套接字
16.1 引言
管道、先进先出、消息队列、信号量及共享内存
16.2 套接字描述符
#include <sys/socket.h>
int socket( int domain, int type, int protocol );
domain: AF_INET, AF_INET6, AF_UNIX, AF_UNSPEC AF: address family
type: SOCK_DGRAM, SOCK_RAW, SOCK_SEQPACKET, SOCK_STREAM
protocol: 0
int shutdown( int sockfd, int how );
16.3 寻址
16.3.1 字节序
#include <arpa/inet.h>
uint32_t htonl( uint32_t hostint32 );
uint16_t htons( uint16_t hostint16 );
uint32_t ntohl( uint32_t netint32 );
uint16_t ntohs( uint16_t netint16 );
16.3.2 地址格式
struct sockaddr{
sa_family_t sa_family;
char sa_data[14];
};
struct sockaddr_in{
sa_family_t sin_family;
in_port_t sin_port;
struct in_addr sin_addr;
unsigned char sin_zero[8];
};
#include <arpa/inet.h>const char *inet_ntop( int domain, const void * restrict addr, char *restrict str, socklen_t size );
int *inet_pton( int domain, const char *restrict str, void * restrict addr );
16.3.3 地址查询
#include <netdb.h>
struct hostent *gethostent( void );
void sethostent( int stayopen );
void endhostent( void );
struct hostent{
char *h_name;
char **aliases;
int h_addrtype;
int h_length;
char **h_addr_list;
};
#include <netdb.h>
struct netent *getnetbyaddr( uint32_t net, int type );
struct netent *getnetbyname( const char *name );
struct netent *getnetent( void );
void setnetent( int stayopen );
void endnetent( void );
struct netent{
char *n_name;
char **n_aliases;
int n_addrtype;
uint32_t n_net;
...
};
struct protoent *getprotobyname( const char *name );
struct protoent *getprotobynumber( int proto );
struct protoent *getprotoent( void );
void setprotoent( int stayopen );
void endprotoent( void );
struct protoent{
char *p_name;
char **p_aliases;
int p_proto;
...
};
struct netent *getservbyname( const char *name, const char *proto );
struct netent *getservbyport( int port, const char *proto );
struct netent *getservent( void );
void setservent( int stayopen );
void endservent( void );
struct netent{
char *s_name;
char **s_aliases;
int s_port;
char *s_proto;
...
};
#include <sys/socket.h>
#include <netdb.h>
int getaddrinfo( const char *restrict host, const char *restrict service, const struct addrinfo *restrict hint, struct addrinfo **restrict res );
void freeaddrinfo( struct addrinfo *ai );
struct addrinfo{
int ai_flags;
int ai_family;
int ai_socktype;
int ai_protocol;
socklen_t ai_addrlen;
struct sockaddr *ai_addr;
char *ai_canoname;
struct addrinfo *ai_next;
...
};
#include <netdb.h>const char *gai_strerror( int error );
#include <sys/socket.h>
#include <netdb.h>
int getnameinfo( const struct sockaddr *restrict addr,
socklen_t alen, char *restrict host,
socklen_t hostlen, char (restrict service,
socklen_t servlen, unsigned int flags );
16.3.4 将套接字与地址绑定
#include <sys/socket.h>
int bind( int sockfd, const struct sockaddr *addr, socklen_t len );
int getsockname( int sockfd, struct sockaddr *restrict addr, socklen_t *restrict alenp );
int getpeername( int sockfd, struct sockaddr *restrict addr, socklen_t *restrict alenp );
16.4 建立连接
#include <sys/socket.h>
int connect( int sockfd, const struct sockaddr *addr, socklen_t len );
int listen( int sockfd, int backlog );
int accept( int sockfd, struct sockaddr *restrict addr, socklen_t *restrict len );
16.5 数据传输
#include <sys/socket.h>
ssize_t send( int sockfd, const void *buf, size_t nbytes, int flags );
ssizt_t sendto( int sockfd, const void *buf, size_t nbytes, int flags, const struct sockaddr *destaddr, socklen_t destlen );
ssize_t sendmsg( int sockfd, const struct msgdr *msg, int flags );
ssize_t recvfrom( int sockfd, void *restrict buf, size_t len, int flags, struct sockaddr *restrict addr, socklen_t *restrict addrlen );
ssize_t recvmsg( int sockfd, struct msghdr *msg, int flags );
16.6 套接字选项
#include <sys/socket.h>
int setsockopt( int sockfd, int level, int option, const void *val, socklen_t len );
int getsockopt( int sockfd, int level, int option, void *restrict val, socklen_t *restrict lenp );
16.7 带外数据
#include <sys/socket.h>
int sockatmark( int sockfd );
16.8 非阻塞和异步I/O