套接字层
操作的对象是socket,在socket进行write的过程中,首先会把要write的字符串缓冲区整理成mgshdr的数据结构形式(linux 2.4),然后调用sock_sendmsg把msghdr的数据传送至inet层,对于msghdr结构中数据区中的每个数据包,创建sk_buff结构,填充数据,挂到发送队列中。一层层往下层协议传递。一下每层协议不再对数据进行拷贝,而只是对sk_buff结构进行操作。
创建socket其实就是创建一个socket实例,然后创建一个文件描述符结构,并且互相建立一些关联,建立互相连接的指针,并且初始化这些对文件的读写操作映射到socket的read,write函数上来。
同时初始化socket的操作函数(proto_ops结构),如果传入的type参数stream类型,那么初始化它的ops
成员为inet_stream_ops,如果是DGRAM类型,则ops为inet_dgram_ops。对于inet_stream_ops其实是一个结构体,包含了stream类型的socket操作的函数集,在这些函数里主要做的是对socket进行的相关操作,同时通过调用下面提到的sock中的相关操作操作完成socket到sock层的传递。
struct socket {
socket_state state;
unsigned long flags;
const struct proto_ops *ops;
struct fasync_struct *fasync_list;
struct file *file;
struct sock *sk;
wait_queue_head_t wait;
short type;
};
创建socket同时还创建了sock数据空间,初始化sock,初始化过程主要做的事情是对receive_queue(接受到的数据包sk_buff链表队列),send_queue,backlog_queue,根据
family,type参数,初始化sock的操作,如,type为stream类型,sock中的proto初始化
tcp_prot,其中包括stream类型的协议sock操作对应的入口函数
struct sock {
struct sock_common __sk_common;
...........
struct {
struct sk_buff *head;
struct sk_buff *tail;
} sk_backlog;
struct sk_buff_head sk_receive_queue;
struct sk_buff_head sk_write_queue;
struct sk_buff_head sk_async_wait_queue;
struct socket *sk_socket;
struct proto *sk_prot_creator;
};
阅读(1711) | 评论(0) | 转发(0) |