开源项目Tinyhttpd第一篇 详解sockaddr_in,socklen_t,pthread_t

server_sock = startup(&port);
printf("httpd running on port %d\n", port);

while (1)
{
    client_sock = accept(server_sock,
            (struct sockaddr *)&client_name,
            &client_name_len);
    if (client_sock == -1)
        error_die("accept");
    /* accept_request(&client_sock); */
    if (pthread_create(&newthread , NULL, (void *)accept_request, (void *)(intptr_t)client_sock) != 0)
        perror("pthread_create");
}

close(server_sock);

return(0);

}

这里面有很多个函数和字段很不常见,具体如下:<br>
1.sockaddr_in
这个结构体是用来用来处理网路通信的地址,它主要是在头文件<netinet/in.h>或<arpa/inet.h>定义的,这个结构体的内部数据结构主要如下:

struct sockaddr_in { sa_family sin_family; uint16_t sin_port; struct in_addr sin_addr; char sin_zero[8]; } struct in_addr { In_addr_t s_addr; }

* in_family: 地址家族,可以理解为一系列相似的通信协议的族群,占用2字节,一般它的值主要为AF_INET,AF_INET6和AF_UNSPE。其中AF_INET不能返回任何任何IPV6相关的地址信息,AF_INET6不能返回任何IPV4地址信息,AF_UNSPEC则意味着函数返回的是适用于指定主机名和服务名且适合任何协议族的地址。
* sin_port: 端口号
* sin_addr:IPv4/IPv6地址
* sin_zero[8]:这个奇怪的东西。。。。。我们其实是不用管的,但是说到这个东西必须提到下面这个sockaddr结构,下面这个结构是程序员无法编辑的,即在操作系统中使用的一种socket数据结构,sa_family和上面的定义是一样的,而sa_data则包括上面的端口号和ip地址。sockaddr_in的用处本来是便于程序员进行端口和ip地址的编辑,在系统中会被强行转换成sockaddr,他们两个都是占有16个字节,所以。。。sin_zero[8]就是为了让他们两个保持大小相同而保留的空字节。

struct sockaddr { unsigned short sa_family; char sa_data[14]; };

1. socklen_t <br>
这个数据结构在网络上资料很乱,总的来说是哈指的是现在socket数据结构的长度,在当初的时候它并不叫这个名字,而是叫做size_t,而size_t类型在64位的系统上并不能和BSD套接字接口所要求的保持一致,故他们改了个名字叫做socklen_t,然而不管怎么变,他们都是int数据类型的马甲罢了。。。。。。。<br>
2.pthread_t <br>
用来声明Linux中的线程ID,数据结构为:unsigned long int。。。。。