Fork me on GitHub

socket网络编程笔记 与地址相关的常见struct


struct addrinfo {
    int              ai_flags;     // AI_PASSIVE, AI_CANONNAME, etc.
    int              ai_family;    // AF_INET(ipv4), AF_INET6(ipv6), AF_UNSPEC
    int              ai_socktype;  // SOCK_STREAM, SOCK_DGRAM
    int              ai_protocol;  // use 0 for "any"
    size_t           ai_addrlen;   // size of ai_addr in bytes
    struct sockaddr *ai_addr;      // struct sockaddr_in or _in6
    char            *ai_canonname; // full canonical hostname
    struct addrinfo *ai_next;      // linked list, next node
  • 获取此结构的函数:getaddrinfo()


struct sockaddr {
    unsigned short    sa_family;    // address family, AF_xxx
    char              sa_data[14];  // 14 bytes of protocol address,contains a destination address and port number for the socket. 


// (IPv4 only--see struct sockaddr_in6 for IPv6)
struct sockaddr_in {
    short int          sin_family;  // Address family, AF_INET
    unsigned short int sin_port;    // Port number
    struct in_addr     sin_addr;    // Internet address
    unsigned char      sin_zero[8]; // Same size as struct sockaddr
  • sin_zero(which is included to pad the structure to the length of a struct sockaddr) should be set to all zeros with the function memset()
  • sin_family corresponds to sa_family in a struct sockaddr and should be set to _AF_INET_.
  • the sin_port must be in Network Byte Order (by using htons()!)


// (IPv4 only--see struct in6_addr for IPv6)
// Internet address (a structure for historical reasons)
struct in_addr {
    uint32_t s_addr; // that's a 32-bit int (4 bytes)
  • used to be a union
  • referes to the 4-byte IP address

structs in ipv6(similar)

// (IPv6 only--see struct sockaddr_in and struct in_addr for IPv4)
struct sockaddr_in6 {
    u_int16_t       sin6_family;   // address family, AF_INET6
    u_int16_t       sin6_port;     // port number, Network Byte Order
    u_int32_t       sin6_flowinfo; // IPv6 flow information
    struct in6_addr sin6_addr;     // IPv6 address
    u_int32_t       sin6_scope_id; // Scope ID
struct in6_addr {
    unsigned char   s6_addr[16];   // IPv6 address

sockaddr_storage (a structure large enough to hold both ipv4 and ipv6 structrues)

struct sockaddr_storage {
    sa_family_t  ss_family;     // address family
    // all this is padding, implementation specific, ignore it:
    char      __ss_pad1[_SS_PAD1SIZE];
    int64_t   __ss_align;
    char      __ss_pad2[_SS_PAD2SIZE];
  • you can cast it to a struct sockaddr_in or struct sockaddr_in6 if you wanna

manipulate IP address

inet_pton(): cast string form to binary form

struct sockaddr_in sa; // IPv4
struct sockaddr_in6 sa6; // IPv6
inet_pton(AF_INET, "", &(sa.sin_addr)); // IPv4
inet_pton(AF_INET6, "2001:db8:63b3:1::3490", &(sa6.sin6_addr)); // IPv6
  • old way: _inet_addr()_ _inet_aton()_ (not compatible with IPv6)

inet_ntop(): cast binary from to string from

// IPv4:
struct sockaddr_in sa;
// space to hold the IPv4 string
// pretend this is loaded with something
inet_ntop(AF_INET, &(sa.sin_addr), ip4, INET_ADDRSTRLEN);
printf("The IPv4 address is: %s\n", ip4);
// IPv6:
char ip6[INET6_ADDRSTRLEN]; // space to hold the IPv6 string
struct sockaddr_in6 sa6;
// pretend this is loaded with something
inet_ntop(AF_INET6, &(sa6.sin6_addr), ip6, INET6_ADDRSTRLEN);
printf("The address is: %s\n", ip6);

only work with numeric IP addresses,won’t do any nameserver DNS lookup on a hostname. Use getaddrinfo() to do that.

Other Notes

  • Layered Network Model
    • Seven layers
      1. Application (应用层)
      2. Presentaion (表示层)
      3. Session (会话层)
      4. Transport (传输层)
      5. Network (网络层)
      6. Data Link (数据链路层)
      7. Physical (物理层)
    • Simplified Four Layers
      • Application Layer(应用层:telnet,ftp,etc.)
      • Host-to-Host Layer(传输层:TCP UDP)
      • Internet Layer(网络互连层:IP and routing)
      • Network Access Layer(主机到网络层:Ethernet,wi-fi,whatever)
  • Some common IP addresses
    • 10.x.x.x
      • only be used either of fully disconnected networks or the networks behind firewalls
    • 192.168.x.x x in range(0,256)
    • 172.y.x.x y in rarnge(16,32)