网络函数bind源码分析
static int sock_bind(int fd, struct sockaddr *umyaddr, int addrlen)
{struct socket *sock;int i;char address[MAX_SOCK_ADDR];int err;if (fd < 0 || fd >= NR_OPEN || current->files->fd[fd] == NULL)return(-EBADF);// 通过文件描述符找到对应的socket,见socket函数源码分析的视图if (!(sock = sockfd_lookup(fd, NULL))) return(-ENOTSOCK);if((err=move_addr_to_kernel(umyaddr,addrlen,address))<0)return err;if ((i = sock->ops->bind(sock, (struct sockaddr *)address, addrlen)) < 0) {return(i);}return(0);
}
```
可见bind函数是直接调用底层af_inet.c的inet_bind
```c
// 给socket绑定一个地址
static int inet_bind(struct socket *sock, struct sockaddr *uaddr,int addr_len)
{struct sockaddr_in *addr=(struct sockaddr_in *)uaddr;struct sock *sk=(struct sock *)sock->data, *sk2;unsigned short snum = 0 /* Stoopid compiler.. this IS ok */;int chk_addr_ret;/* check this error. */if (sk->state != TCP_CLOSE)return(-EIO);if(addr_len<sizeof(struct sockaddr_in))return -EINVAL;// raw是链路层,不需要端口 if(sock->type != SOCK_RAW){ // 已经绑定了端口if (sk->num != 0) return(-EINVAL);snum = ntohs(addr->sin_port);/** We can't just leave the socket bound wherever it is, it might* be bound to a privileged port. However, since there seems to* be a bug here, we will leave it if the port is not privileged.*/// 端口无效则随机获取一个非root才能使用的端口if (snum == 0) {snum = get_new_socknum(sk->prot, 0);}// 小于1024的端口需要超级用户权限if (snum < PROT_SOCK && !suser()) return(-EACCES);}// 判断ipchk_addr_ret = ip_chk_addr(addr->sin_addr.s_addr);if (addr->sin_addr.s_addr != 0 && chk_addr_ret != IS_MYADDR && chk_addr_ret != IS_MULTICAST)return(-EADDRNOTAVAIL); /* Source address MUST be ours! */if (chk_addr_ret || addr->sin_addr.s_addr == 0)sk->saddr = addr->sin_addr.s_addr;if(sock->type != SOCK_RAW){/* Make sure we are allowed to bind here. */cli();for(sk2 = sk->prot->sock_array[snum & (SOCK_ARRAY_SIZE -1)];sk2 != NULL; sk2 = sk2->next) {/* should be below! */if (sk2->num != snum) continue;// 端口已经被使用,没有设置可重用标记,比如断开了解后在2msl内是否可以重用if (!sk->reuse){sti();return(-EADDRINUSE);}if (sk2->num != snum) continue; /* more than one */if (sk2->saddr != sk->saddr) continue; /* socket per slot ! -FB */// 被监听的端口不能同时被使用if (!sk2->reuse || sk2->state==TCP_LISTEN) {sti();return(-EADDRINUSE);}}sti();// 保证该sk不在sock_array队列里remove_sock(sk);// 挂载到sock_array里put_sock(snum, sk);// tcp头中的源端口sk->dummy_th.source = ntohs(sk->num);sk->daddr = 0;sk->dummy_th.dest = 0;}return(0);
}
复制代码
由代码中可以看到,bind函数主要做的事情是判断一下端口和ip和可用性,然后把sock结构体挂载到协议对应的sock_array哈希列表中。
网络函数bind源码分析相关推荐
- jQuery源码分析-10事件处理-Event-事件绑定与删除-bind/unbind+live/die+delegat/unde
10.4 .bind() .one() 10.4.1 如何使用 .bind( eventType, [eventData], handler(eventObject) ) 在匹配的元素上绑 ...
- jQuery源码分析-10事件处理-Event-事件绑定与删除-bind/unbind+live/die+delegat/undelegate
Js代码 作者:nuysoft/高云 QQ:47214707 EMail:nuysoft@gmail.com 声明:本文为原创文章,如需转载,请注明来源并保留原文链接. 后文预告:封装事件对象 便 ...
- SpringBoot-web开发(二): 页面和图标定制(源码分析)
[SpringBoot-web系列]前文: SpringBoot-web开发(一): 静态资源的导入(源码分析) 目录 一.首页 1. 源码分析 2. 访问首页测试 二.动态页面 1. 动态资源目录t ...
- ceph bluestore源码分析:admin_socket实时获取内存池数据
环境: 版本:ceph 12.2.1 部署完cephfs 使用ceph-fuse挂载,并写入数据 关键参数: debug_mempool = true 将该参数置为true即可查看详细的blustor ...
- koa源码分析-co模块以及thunk
Thunk以及CO模块 co4.0之前都是返回的thunk函数 之后的都是返回promise thunk thunk:在 JavaScript 语言中,Thunk 函数替换的是将多参数函数,替换成单参 ...
- djangorestframework源码分析2:serializer序列化数据的执行流程
djangorestframework源码分析 本文环境python3.5.2,djangorestframework (3.5.1)系列 djangorestframework源码分析-serial ...
- celery源码分析-Task的初始化与发送任务
celery源码分析 本文环境python3.5.2,celery4.0.2,django1.10.x系列 celery的任务发送 在Django项目中使用了装饰器来包装待执行任务, from cel ...
- celery源码分析-wroker初始化分析(上)
celery源码分析 本文环境python3.5.2,celery4.0.2,django1.10.x系列 celery与Django的配合使用 首先,在安装有django的环境中创建一个django ...
- tornado源码分析
tornado源码分析 本源码为tornado1.0版本 源码附带例子helloworld import tornado.httpserver import tornado.ioloop import ...
最新文章
- 阿里云 Redis 开发规范
- iOS开源项目周报0420
- 系统集成项目管理之项目采购管理
- CDN监控系统(一)
- 46.一个例子了解C++中异常处理
- JZOJ__Day 5:【普及模拟】权势二进制
- android上如何写配置文件
- python采用pika库使用rabbitmq总结,多篇笔记和示例
- sourceTree添加git密钥步骤
- 前端学习(2878):原生js模块化+发送弹幕和重置弹幕
- IBM Holosofx 进行业务流程管理
- html 怎么给li空格,html 空格
- tl r402路由器设置_记一次TP-LINK路由器问题排查
- 查看修改oracle数据库字符集
- SQL SERVER 2000安装教程图文详解
- 深入理解Nginx模块开发与架构解析第2版(书签导航正确)
- MATLAB中改变默认工作路径的方法
- 金融数据类——外汇,CFD
- 控件(五)——Gridview控件以SqlDataSource控件为数据源实现换肤功能
- 苹果电脑可以装windows系统吗_苹果电脑MacBook双系统安装好后,如何下载Windows支持组件?...