笔者这次就从linux源码的角度来阐述socket阻塞(block)和非阻塞(non_block)的区别。 本文源码均来自采用Linux-2.6.24内核版本。...(进程结构体)->files_struct->fd_array中找到对应的socket的file描述符,再修改file->flags 在调用socket.recv的时候 我们跟踪源码调用: socket.recv...|->sys_recv |->sys_recvfrom |->sock_recvmsg |->__sock_recvmsg |->sock->ops->recvmsg 由上文可知...: sock->ops->recvmsg = sock_common_recvmsg; sock 值得注意的是,在sock_recmsg中,有对标识O_NONBLOCK的处理 if (sock->file..., 上面的代码可以看出,如果fcntl(O_NONBLOCK)=>MSG_DONTWAIT置位=>(flags & MSG_DONTWAIT)>0, 再结合tcp_recvmsg的函数签名,即如果设置了
在网络开发模型中,有一种非常易于开发同学使用的方式,那就是同步阻塞的网络 IO(在 Java 中习惯叫 BIO)。...recv(sk, ...) } 但是在高并发的服务器开发中,这种网络 IO 的性能奇差。...在上面的 demo 中虽然只是简单的两三行代码,但实际上用户进程和内核配合做了非常多的工作。先是用户进程发起创建 socket 的指令,然后切换到内核态完成了内核对象的初始化。...首先通过 strace 命令跟踪,可以看到 clib 库函数 recv 会执行到 recvfrom 系统调用。...对象图,从图中可以看到 recvmsg 指向的是 inet_recvmsg 方法。
在本文中,我们首先会简单介绍下TCP中发送缓冲区和接收缓冲区的作用(对于后面理解send和recv非常重要),然后讲解Linux系统下,TCP发送和接收数据是如何实现的。...;否则,send向网络发送缓存中不能容纳的那部分数据,并等待对端确认后再返回(接收端只要将数据收到接收缓存中,就会确认,并不一定要等待应用程序调用recv) 在非阻塞模式下,send函数的过程仅仅是将数据拷贝到协议栈的缓存区而已...在Linux内核中,有两种方式可以查看tcp缓冲区buffer大小。...tcp_sendmsg()的主要工作是传输用户层的数据,将数据放入skb中。...应用层 应用程序调用读取或者 recv 的时候,该调用被映射到 /net/socket.c 中的sys_recv系统调用,然后调用 sock_recvmsg 函数。
关闭连接 当数据量比较大的时候我们可以用stream方式分批次传输数据。...对于客户端还是服务端没有限制,我们可以根据自己的需要使用stream方式,使用方式也非常的简单,在定义接口的时候在参数或者返回值前面加上stream然后就可以多次进行传输了,使用的代码还是之前写的例子,...代码都在github上: 比如我的例子中定义了两个使用stream的接口,一个只在返回值使用stream,另一个是在参数和返回值前都加上了stream,最终的使用方式没有区别 rpc...,如果有发送就会有Send(你的参数),如果有接收会生成Rev() (你的参数, error),但这两个方法只是为了让你使用时方便,里面调用的还是SendMsg(interface)和RecvMsg(interface...)方法,但是他们是怎么工作的,如何多次发送和接收传输的数据,是不是感觉很神奇。
RT,Linux下使用c实现的多线程服务器。这个真是简单的不能再简单的了,有写的不好的地方,还希望大神轻拍。(>﹏<) 本学期Linux、unix网络编程的第四个作业。...主线程循环接收客户连接请求,在ent中查询状态为0的元素, 如果不存在状态为0的元素(即连接数超过最大连接数),向客户发送EXIT标志; 否则,修改客户信息表中该元素的socket描述符...好啦,现在可以开始撸代码了。...,sizeof(recvMsg)); 126 int len =recv(ent[index].sockfd,&recvMsg,sizeof(recvMsg),0); 127...下面上一下演示过程:(测试环境,Red Hat Enterprise Linux 6 + centos系Linux,ubuntu下可能会有些问题。)
UDP不提供可靠性,它只是把应用程序传给IP层的数据报发送出去,但是并不能保证它们能到达目的地。由于UDP在传输数据报前不用在客户和服务器之间建立一个连接,且没有超时重发等机制,故而传输速度很快。...UDP是一种面向无连接的协议,每个数据报都是一个独立的信息,包括完整的源地址或目的地址,它在网络上以任何可能的路径传往目的地,因此能否到达目的地,到达目的地的时间以及内容的正确性都是不能被保证的。...通信协议族在文件sys/socket.h中定义。 ?...要查看当前广播位置有3种方法 广播的计算方法 在线网络计算器 直接用 表示当前所在的广播地址 用代码给飞秋发信息 ''' 应用程序可以在通用的tcp/ip协议基础上,加上自己的判断...例如,Windows使用'\r\n',Linux使用'\n'而Mac使用'\r'。 \r 默认表示将输出的内容返回到第一个指针,这样的话,后面的内容会覆盖前面的内容
如果函数成功,则返回0,创建好的套接字分别是sv[0]和sv[1];否则返回-1,错误码保存于errno中。 基本用法: 1. 这对套接字可以用于全双工通信,每一个套接字既可以读也可以写。...例如,可以往sv[0]中写,从sv[1]中读;或者从sv[1]中写,从sv[0]中读; 2....如果往一个套接字(如sv[0])中写入后,再从该套接字读时会阻塞,只能在另一个套接字中(sv[1])上读成功; 3. 读、写操作可以位于同一个进程,也可以分别位于不同的进程,如父子进程。...处理代码. 2、EFAULT 参数中有一指针指向无法存取的内存空间 3、ENOTSOCK 参数s 为一文件描述词, 非socket. 4、EINTR 被信号所中断. 5、EAGAIN 此操作会令进程阻断, 但参数...:~/Linux/217/pro_pool/socketpair$ .
为了快速掌握本文所要表达的思想,我们可以带着以下问题阅读: 1、应用程序调用read、recv等方法时,socket套接字可以设置为阻塞或者非阻塞,这两种方式是如何工作的?...4、recv这样的接收方法还可以传入各种flags,例如MSG_WAITALL、MSG_PEEK、MSG_TRUNK等等。它们是如何工作的?...在第1步结束后,这时我们需要收到的是S2序号,但到来的报文却是S3打头的,怎么办呢?进入out_of_order队列!从这个队列名称就可以看出来,所有乱序的报文都会暂时放在这。...服务器先是收到了S1-S2这个报文,但S2-S1的长度是小于SO_RCVLOWAT的,用户进程调用recv方法读套接字时,虽然读到了一些,但没有达到最小阀值,所以进程睡眠了,与此同时,在睡眠前收到的乱序的...3、通过tcp_recvmsg方法来完成接收工作。先锁住socket,避免并发进程读取同一socket的同时,也在告诉内核网络软中断处理到这一socket时要有不同行为,如第6步。
在前面我们介绍了UNIX域套接字编程,更重要的一点是UNIX域套接字可以在同一台主机上各进程之间传递文件描述符。...之前打开的文件描述符,子进程是可以共享的,但是子进程打开的文件描述符,父进程是不能共享的,上述程序就是举例在子 进程中打开了一个文件描述符,然后通过send_fd 函数将文件描述符传递给父进程,父进程可以通过...先建立一个 文件test.txt 后输入几个字符,然后运行程序,输出如下: simba@ubuntu:~/Documents/code/linux_programming/UNP/socket$ ....最后提醒一点,只有unix域协议才能在本机进程间传递文件描述符,如果想要在没有亲缘关系的进程间传递,则不能用socketpair函数,要用socket()函 数 才行。...参考: 《Linux C 编程一站式学习》 《TCP/IP详解 卷一》 《UNP》
在选择操作系统的时候由于VMware没有Kali给我们选,但Kali和Ubuntu一样,都是基于Debian的,故在此选择Debian Linux 10.x 64bit 磁盘类型的话sata和nvme...两个随便选一个 图片 这里是较为关键的一步,选择”使用物理磁盘“ 然后选择移动硬盘,使用整个磁盘 在选择完成之后进到虚拟机的设置里面,在”高级“里面将固件类型改为uefi(注:此处如果是打算让移动硬盘同时可以启动...Windows的情况下安装原生Debian组双系统》中类似,但比那个简单,因为这是单Linux系统,那个是Windows & Linux双系统 等待安装程序准备 主机名,随便设置一个就好 用户名,...,这个时候这块硬盘还是不能引导我电脑启动的,得做一些小改动,使用diskgenius进到esp分区中,将文件夹改名为“boot” 然后将里面的文件改名为“bootx64.efi” 现在它能启动我电脑了...登录 进去安装一下软件,让它成为一个完整的Kali Linux 安装Kali-Linux-everything需要十几g的空间 目前算是完事了,成功拥有一个可以随身携带的Kali Linux环境了
管道只能在具有共同祖先的两个进程之间使用,通常一个管道由一个进程创建,在进程调用fork之后,这个管道就你能在父进程和子进程之间使用了。...如果函数成功,则返回0,创建好的套接字分别是sv[0]和sv[1];否则返回-1,错误码保存于errno中。 基本用法: 1. 这对套接字可以用于全双工通信,每一个套接字既可以读也可以写。...例如,可以往sockfd[0]中写,从sockfd[1]中读;或者从sockfd[1]中写,从sockfd[0]中读; 2....2、EFAULT 参数中有一指针指向无法存取的内存空间 3、ENOTSOCK 参数s 为一文件描述词, 非socket. 4、EINTR 被信号所中断. 5、EAGAIN 此操作会令进程阻断, 但参数...yu@ubuntu:~/Linux/217/pro_pool/socketpair .
一、内核网络结构 在Linux内核中,对网络部分按照网络协议层、网络设备层、设备驱动功能层和网络媒介层的分层体系设计。 网络驱动功能层主要通过网络驱动程序实现。 ...在Linux内核,所有的网络设备都被抽象为一个接口处理,该接口提供了所有的网络操作。 net_device结构表示网络设备在内核中的情况,也就是网络设备接口。...网络协议栈中各层协议都可以通过对该结构的操作实现本层协议数据的添加或者删除。使用sk_buff结构避免了网络协议栈各层来回复制数据导致的效率低下。...图片 sk_buff结构可以分为两个部分,一部分是存储数据包缓存,在图中表示为PackertData,另一部分是由一组用于内核管理的指针组成。 ...设备名称总线参数协议参数链接层变量接口标志 四、数据包接收流程 在Linux内核中,一个网络数据包从网卡接收到用户空间需要经过链路层、传输层和socket的处理,最终到达用户空间。
send_msg(): print('------sendmsg方法被调用了-------') recvmsg.py文件里的内容如下: def recv_msg(): print('-----recvmsg...可以在newmsg里创建__init__.py文件,在该文件里导入指定的内容。 在__init__.py文件里编写代码: from . import sendmsg # 导入指定的模块 ....代表的是当前文件夹 test.py文件里的代码: import newmsg newmsg.sendmsg.send_msg() # 可以直接调用对应的方法 # newmsg.recvmsg.recv_msg...init.py为空仅仅是把这个包导入,不会导入包中的模块。可以在__init__.py文件中编写内容。...3. all 在__init__.py文件中,定义一个__all__变量,它控制着 from 包名 import * 时导入的模块。
关于什么是UNIX域套接字可以参考:https://cloud.tencent.com/developer/article/1018893 这里主要介绍非命名的UNIX域套接字的用法。...可以是SOCK_STREAM或者SOCK_DGRAM。这两种都是可靠的 protocol:协议类型。为0 sv:返回套接字对,这个是输出参数。返回的两个描述符都是可读可写的。...Sending data: 13 Recv data: 14 3.UNIX域传递文件描述符 需要用到sendmsg和recvmsg函数: #include <sys/types.h...(fd < 0) ERR_EXIT("open"); send_fd(sockfds[1], fd); } return 0; } 分析:子进程中打开一个文件描述符...2)普通的TCP UDP套接字是不能传递文件描述符的
:它是按值传递的,而不是值-结果参数,因此它只能从进程向内核传递标志,内核不能向进程传递标志。...4.recvmsg和sendmsg函数 这两个函数是最通用的I/O函数,实际上,可以用recvmsg代替read, readv, recv, recvfrom....() */ }; 5.辅助数据 辅助数据(ancillary data)可以通过sendmsg和recvmsg这两个函数,使用msghdr结构中的msg_contorl和msg_controllen成员发送和接收...有三种方法: 如果在没有数据可读时还有其他事情要做,为了不阻塞在内核中,可以使用非阻塞I/O 如果想检查一下数据而使数据仍留在接收队列中,可以使用MSG_PEEK标志。...如果想这样做,但又不能肯定是否有数据可读,可以把这个标志和非阻塞套接口相结合,或与MSG_DONTWAIT标志结合使用。
本学期Linux、unix网络编程的第三个作业。...从命名管道CLIENT中读取通信子进程发来的消息,消息类型为:用户名、退出及一般信息; 若为用户名,依据消息队列在更新客户信息表,状态为可用; 若为一般信息,将信息转换后写入可用客户的消息队列,等待其他通信子进程读取...; 若为退出,在客户信息表中状态设为不可用,执行信号量V操作,并将可用客户的消息队列标识符写入到命名管道SERVER; 2、客户端: 根据用户从终端输入的服务器IP地址及端口号连接到相应的服务器; 连接成功后...架构看起来很复杂,我们可以绘制一下流程图方便理清思路。 ? ? 在word里面截图不是很清晰啊。。。...,sizeof(recvMsg)); 213 int len =recv(connetfd,&recvMsg,sizeof(recvMsg),0); 214
是否可以让服务器和客户端约定一个代表文件尾的字符? 这种方式也有问题,因为这意味这文件中不能有与约定字符相同的内容。为了解决该问题,服务端应最后向客户端传递 EOF 表示文件传输结束。...msg_ fags成员无须设定,它会复制recvmsg/sendmsg的flags参数的内容以影响数据读写过程。recvmsg 还会在调用结束前,将某些更新后的标志设置到msg. flags 中。...recvmsg/sendmsg的flags 参数以及返回值的含义均与send/recv的flags参数及返回值相同。 外带标记 在实际应用中,我们通常无法预期带外数据何时到来。...h_name:该变量中存有官方域名(Official domain name)。官方域名代表某一主页,但实际上,一些著名公司的域名并没有用官方域名注册。...该函数的定义getnameinfo将返回的主机名存储在host参数指向的缓存中,将服务名存储在serv参数指向的缓存中,hostlen和servlen参数分别指定这两块缓存的长度。
领取专属 10元无门槛券
手把手带您无忧上云