C/C++网络编程2中介绍了套接字,这一节介绍给套接字分配ip和端口号。ip用于标识一台主机,端口号用于标识一个主机中的一个应用程序,端口号占16位,0到65535,其中0到1023是知名端口号。
表示IPv4的结构体:
struct sockaddr_in { sa_family_t sin_family; // 地址族 uint16_t sin_port; // 端口号 struct in_addr sin_addr; // 32位ip地址 char sin_zero[8]; // 不使用 }; struct in_addr { in_addr_t s_addr; // 32位IPv4地址 }; sin_family: AF_INET : IPv4地址族 AF_INET6 : IPv6地址族 AF_LOCAL : 本地通信中采用的UNIX协议的地址族
字节序:
大端序:高位字节存放低位地址。存放0x12345678
小端序 :高位字节存放高位地址。
网络通信中采用大端序。
字节序转换:
unsigned short htons(unsigned short); unsigned short ntohs(unsigned short); unsigned long htonl(unsigned long); unsigned long ntohl(unsigned long); h代表主机字节序 n代表网络字节序
ip地址转32位整型:
#include <arpa/inet.h> // 完成字符串转换及网络字节序转换 in_addr_t inet_addr(const char *string); // 完成字符串转换及网络字节序转换,成功返回1,失败返回0 int inet_aton(const char * string, struct in_addr *addr); // 32位整型ip地址转换为字符串 char *inet_ntoa(struct in_addr adr);
网络地址初始化:
struct sockaddr_in addr; char *serv_ip = "211.217.168.13"; char *serv_port = "9999"; memset(&addr, 0, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_addr.s_addr = inet_addr(serv_ip); addr.sin_port = htons(atoi(serv_port)); // 把ip地址写死,很不灵活,可改为 addr.sin_addr.s_addr = htonl(INADDR_ANY); // 自动获取服务器计算机的ip地址
向套接字分配网络地址:
#include <sys/socket.h> int bind(int sockfd, struct sockaddr * myaddr, socklen_t addrlen); sockfd : 要分配ip和端口号的套接字的文件描述符 myaddr : 存在地址信息的结构体变量地址值 addrlen : 第二个结构体变量的长度