Chinaunix首页 | 论坛 | 博客
  • 博客访问: 301619
  • 博文数量: 94
  • 博客积分: 2163
  • 博客等级: 大尉
  • 技术积分: 932
  • 用 户 组: 普通用户
  • 注册时间: 2010-12-20 09:23
文章存档

2012年(2)

2011年(92)

分类: LINUX

2011-09-09 10:18:57

接:
这里不得不介绍一些概况一些重要数据结构。
struct socket{
short type;  // 如上文。
socket_state state;   //插口的状态:SS_UNCONNECTED,SS_CONNECTED,SS_CONNECTING,SS_DISCONNECTED,第一个未连 接(初始化时的状态),第二个为已经建立连接,第三个为连接正在被处理,最后为取消连接。//
long flags;   // SO_ACCEPTION 用于未连接socket,而且他们的进程在等待一个连接请求。其他SO_NOSPASE,SO_WAITDATA 表示不正常。
struct proto_ops *ops; //如上所示。
void *data;  保存私有数据。对于不同域的该指针指向不同数据结构。UNIX域指向unix_proto_data数据结构,INET指向sock数据结构。
struct socket *conn;  
struct socket *iconn;两个字段仅对UNIX域有意义。
struct socket *next; 构成socket结构链表。
struct wait_queue **wait; 等待队列。
struct inode *inode; 上文中创建的inode结构,在sock_socket->sock_create()->sock_alloc()中。
struct fasync_struct *fasync_list; fasync_struct构成的链表,用于同步文件读写。  
}

                             补充域协议协议初始化
域协议   初始化函数             说明
UNIX” unix_proto_init    本机进程间模拟网络的数据一种交换形式
                                               
"INET” inet_proto_ini     使用TCP/IP 协议族的网络数据包交换协议  
                                          
"802.2” p8022_proto_init 使用 802.2 协议    局域网数据包定义标准。
"SNAP” snap_proto_init 使 用 SNAP ( Subnetwork
                                Access Protocol)协议
"AX.25” ipx_proto_init “IPX” ipx_proto_init 使用 IPX 网络层协议进行数据包交换 Novell 网络协议)
“DDP” atalk_proto_init AppleTalk
使用struct net_proto数据结构
struct net_proto{
char *name //域协议名称。
void (*init_func) (struct net_proto*); /指针
}                                 
                             初始化
struct net_proto protocols[] =
#ifdef CONFIG_UNIX
{"UNIX", unix_proto_init},
#endif
........
};
举例在linux堆栈1.2.13中
inet_proto_init函数定义在/net/inet/af_inet.c中
调用 inet_proto_add; 进行传输层与网络层的连接。具体将inet_proto_base全局变量指向的inet_protocol结构队列中元素散列到struct inet_proto *inet_protos[]中,被网络层调用。inet_protol结构为一个传输层协议,定义了传输层协议号和接受函数。
                 数据包传送通道
                          | 硬件监听物理传输介质  |
                                      |
                                      |完全接受一个数据包
                                      |产生中断
                                      |
                        |系统调用驱动程序中断处理函数处理 |
                                       |
             数据从硬件到内核复制     |  封装为特定数据结构sk_buff,调用链路层函接口函数netif_rx                             | 将数据包暂存到内核维护的一个数据包队列backlog指向。                                  |
                                       |
                            |启动下半部处理函数net_bh|
                                      |从backlog队列中取数据包,进行本层处理后。
                                      |便利ptype_base指向的网络协议层队列,进行协议号匹配。调用接受函数。如ARP协议,调用arp_rcv函数,网络层调用ip_rcv.
                                      |                假设调用的为IP协议。
                                      |
                              | IP_rcv处理函数|
                                      |
                                      |用到inet_protos散列表进行匹配,找到inet_proto结构。                                  |              假设调用的为TCP协议
                              |tcp_rcv 处理函数 |
                                      |    完成从网络层到传输层的传递。
                                      |tcp协议使用的sock结构都在tcp_prot全局变量对应的ptoto结构之sock_array[]数组中。       |采用本地端口号为索引在tcp_prot对应的数组中找到sock结构队列                          |                  进而找到sock结构
                   | 将数据报挂在到sock结果缓冲队列中 (receive_queue)|
                                      |
                                      | 用户读取数据,首先根据文件描述符得到inode,然后得到socket结构,进而得到sock结构,    |       最后到达receive_queue队列。
                                      |
                                      |
                          |将数据包拷贝到用户缓冲区中|

举例: static struct inet_protocol tcp_protol =
{
tcp_rcv,//     处理函数。
NULL,// 初始化没有报文分段处理函数。
tcp_err, //错误控制
NULL,//
IPPROTO_TCP, //协议号
0,   //copy
NULL, //数据
"TCP" // 名字
};
其中 inet_protocol 数据结构
struct inet_protocol {
int (*handler ) (struct sk_buff *skb, struct device *dev, struct opions *opt, unsigned long daddr, unsigned short len, unsigned long saddr, int redo, struct inet_protocol *protocol);
int (*frag_handler)(......);//参数一样
void (*err_hander)(int err, unsigned char *buff, unsigned long daddr, unsigned long saddr, struct inet_protocol *protocol);
struct inet_protocol *next;
unsigned char protocol;
unsigned char copy :1;
void          *data;
char          *name;
};
阅读(1431) | 评论(0) | 转发(0) |
给主人留下些什么吧!~~