4.1主机字节序列和网络字节序列
主机字节序列分为:大端字节序和小端字节序
大端:高位字节存储在内存的低地址处,低位字节存储在内存的高地址处。
小端:高位字节存储在内存的高地址处,低位字节存储在内存的低地址处。
在两台使用不同字节序的主机间传递数据时,会存在冲突。所以,在将数据发送到网络时规定整形数据使用大端字节序,所以也把大端字节序成为网络字节序列。
4.2主机和网络字节序之间的转换
Linux系统提供的4个函数:
#include <netinet/in.h>//头文件
uint32_t htonl(uint32_t hostlong); // 长整型的主机字节序转网络字节序
uint32_t ntohl(uint32_t netlong); // 长整型的网络字节序转主机字节序
uint16_t htons(uint16_t hostshort); // 短整形的主机字节序转网络字节序
uint16_t ntohs(uint16_t netshort); // 短整型的网络字节序转主机字节序
4.3 通用 套接字地址结构
相当于指针中的 void* 指针一样可以接收任何类型的指针
socket 网络编程接口中表示 socket 地址的是结构体 sockaddr
#include <bits/socket.h>
struct sockaddr
{
sa_family_t sa_family;//sa_family 成员是地址族类型(sa_family_t)的变量。地址族类型通常与协议族类型对应
char sa_data[14];
};
常见的协议族和对应的地址族:
4.4 专用 套接字地址结构
TCP/IP 协议族有 sockaddr_in 和 sockaddr_in6 两个专用套接字地址结构体,它们分别用于 IPV4 和 IPV6
/*
sin_family: 地址族 AF_INET
sin_port: 端口号,需要用网络字节序表示
sin_addr: IPV4 地址结构:s_addr 以网络字节序表示 IPV4 地址
*/
//ipv4
struct in_addr
{
u_int32_t s_addr;
};
struct sockaddr_in
{
sa_family_t sin_family;
u_int16_t sin_port;
struct in_addr sin_addr;
};
//ipv6
struct in6_addr
{
unsigned char sa_addr[16]; // IPV6 地址,要用网络字节序表示
};
struct sockaddr_in6
{
sa_family_t sin6_family; // 地址族:AF_INET6
u_inet16_t sin6_port; // 端口号:用网络字节序表示
u_int32_t sin6_flowinfo; // 流信息,应设置为 0
struct in6_addr sin6_addr; // IPV6 地址结构体
u_int32_t sin6_scope_id; // scope ID,尚处于试验阶段
};
4.5ip地址转换函数
十进制字符串表示的 IPV4 地址和网络字节序整数表示的 IPV4 地址之间的转换:
#include <arpa/inet.h>
in_addr_t inet_addr(const char *cp); //字符串表示的 IPV4 地址转化为网络字节序
char* inet_ntoa(struct in_addr in); // IPV4 地址的网络字节序转化为字符串表示