Linux内核网络协议栈六-socket地址绑定(续)

Linux内核网络协议栈6-socket地址绑定(续)

接上篇《socket地址绑定》

?

?

三、根据不同的协议来完成绑定

上面代码中的第3步是根据应用程序在创建socket时传递到内核的协议域及socket类型来决定调用采用哪个方法,具体可以参考
创建socket

一文,这里不再赘述;下面以AF_IENT及SOCK_STREAM为例来说明绑定的过程;

1、调用链:

net/Socket.c:sys_bind()->net/ipv4/Af_inet.c:inet_bind();

2
、inet_bind()逻辑:

1) 地址类型检查

chk_addr_ret = inet_addr_type(sock_net(sk), addr->sin_addr.s_addr);
if (!sysctl_ip_nonlocal_bind &&
    !inet->freebind &&
    addr->sin_addr.s_addr != htonl(INADDR_ANY) &&
    chk_addr_ret != RTN_LOCAL &&
    chk_addr_ret != RTN_MULTICAST &&
    chk_addr_ret != RTN_BROADCAST)
    goto out;

?


inet_addr_type()函数根据设置的ip地址检查其类型:

static inline unsigned __inet_dev_addr_type(struct net *net,
                               		const struct net_device *dev,
                               		__be32 addr)
{
   	……
 
   	if (ipv4_is_zeronet(addr) || ipv4_is_lbcast(addr))
          	return RTN_BROADCAST;
   	if (ipv4_is_multicast(addr))
          	return RTN_MULTICAST;
   	……
 
   	local_table = fib_get_table(net, RT_TABLE_LOCAL);
   	if (local_table) {
          	ret = RTN_UNICAST;
          	if (!local_table->tb_lookup(local_table, &fl, &res)) {
                 	if (!dev || dev == res.fi->fib_dev)
                        	ret = res.type;
                 	fib_res_put(&res);
          	}
   	}
   	return ret;
}

?


其中:</

Linux内核网络协议栈六-socket地址绑定(续)

相关文章:

你感兴趣的文章:

标签云: