现在业界感觉从协议到socket中间这环是欠缺的,导致很多同学并不能融会贯通。计算机学生在学校学习网络的时候,讲的的分层协议,arp ip tcp 三次握手 四次挥手 流量控制 等等基础概念。但是等到了网络编程的时候,突然就跳跃到socket了。这个跳跃幅度着实有点大,导致很多人无法理解。 其实我觉得在计算机课程教学中缺少了一环,那就是介绍一下socket编程是如何和网络中的各种概念联系起来的,只有这样这样才能融会贯通。 比如,socket中的listen到底是干了啥?很多人只知道大家都是这么用,却不明白它的底层原理。实际上服务器在准备接受客户端的握手请求之前,需要准备半连接队列和全连接队列,准备好之后才能接收握手请求。 再比如connect是干了啥?同样没人讲过。实际上connect是客户端选择了一个可用端口,然后向服务器发起握手请求了。同时自己还开了个定时器,如果逾期收不到反馈会重试。 客户端发起连接请求之后,三次握手的工作就由双方的内核完成了。三次握手成功之后,服务器端会创建一个sock对象,在它上面保存好tcp连接的四元组信息,然后放在接收队列中。 你调用accept的时候就是从这个接收队列中获取一个握手就绪连接来用。 再后面就是在这个连接之上的读和写了。用户流程只需要发起读写请求就好了,放到接收缓存或者发送缓存中。真正的读写,重试都由内核从缓存中取数据,或者写入。 当然了,用户进程在发送或者接收数据的时候如果发送缓存区不够用,或者接收的数据并未到达,那该有可能会被阻塞。会导致一次进程上下文切换的开销。放内核ready的时候,再把该进程切换回来,又来一次切换开销。 如果嫌弃阻塞带来的各种额外的cpu开销,也不想创建那么多进程,那就来试试epoll 如果你想用多进程的方式来使用epoll,哪个进程来处理事件等待,哪个进程真正发送,由于分工的不同,又涉及到Reactor,Proactor等模式。 如果你嫌弃手写epoll以及各种复杂的进程协作模式太麻烦,那就选一些成熟的网络库来用就行了。它们都替你封装好了,例如java里的netty,golang里的net包,C++里的Sogou Workflow。 我想我这一篇把整个socket编程的来龙去脉都讲清楚了。现在业界感觉从协议到socket中间这环是欠缺的,导致很多同学并不能融会贯通。我的公众号【开发内功修炼】就是帮大家打通这个任督二脉的。 而且这些内容马上就要出版了,希望大家都能真正理解技术,而不是只会用。 所谓套接字(Socket),就是对网络中不同主机上的应用进程之间进行双向通信的端点的抽象。一个套接字就是网络上进程通信的一端,提供了应用层进程利用网络协议交换数据的机制。从所处的地位来讲,套接字上联应用进程,下联网络协议栈,是应用程序通过网络协议进行通信的接口,是应用程序与网络协议栈进行交互的接口 [1] 。 中文名 套接字 [1] 外文名 socket [1] 实 质 两个网络各自通信连接中的端点 [2] 类 型 流式套接字、数据报套接字和原始套接字 [3] 作 用 完成两个应用程序之间的数据传输 [3] 学 科 计算机网络 [1] 套接字是通信的基石,是支持TCP/IP协议的路通信的基本操作单元。可以将套接字看作不同主机间的进程进行双间通信的端点,它构成了单个主机内及整个网络间的编程界面。套接字存在于通信域中,通信域是为了处理一般的线程通过套接字通信而引进的一种抽象概念。套接字通常和同一个域中的套接字交换数据(数据交换也可能穿越域的界限,但这时一定要执行某种解释程序),各种进程使用这个相同的域互相之间用Internet协议簇来进行通信 [3] 。 Socket(套接字)可以看成是两个网络应用程序进行通信时,各自通信连接中的端点,这是一个逻辑上的概念。它是网络环境中进程间通信的API(应用程序编程接口),也是可以被命名和寻址的通信端点,使用中的每一个套接字都有其类型和一个与之相连进程。通信时其中一个网络应用程序将要传输的一段信息写入它所在主机的 Socket中,该 Socket通过与网络接口卡(NIC)相连的传输介质将这段信息送到另外一台主机的 Socket中,使对方能够接收到这段信息。 Socket是由IP地址和端口结合的,提供向应用层进程传送数据包的机制 [2] 。 套接字Socket=(IP地址:端口号),套接字的表示方法是点分十进制的lP地址后面写上端口号,中间用冒号或逗号隔开。每一个传输层连接唯一地被通信两端的两个端点(即两个套接字)所确定。例如:如果IP地址是210.37.145.1,而端口号是23,那么得到套接字就是(210.37.145.1:23) [4] 。 1.流套接字(SOCK_STREAM) 流套接字用于提供面向连接、可靠的数据传输服务。该服务将保证数据能够实现无差错、无重复送,并按顺序接收。流套接字之所以能够实现可靠的数据服务,原因在于其使用了传输控制协议,即TCP(The Transmission Control Protocol)协议 [3] 。 2.数据报套接字(SOCK_DGRAM) 数据报套接字提供一种无连接的服务。该服务并不能保证数据传输的可靠性,数据有可能在传输过程中丢失或出现数据重复,且无法保证顺序地接收到数据。数据报套接字使用UDP( User DatagramProtocol)协议进行数据的传输。由于数据报套接字不能保证数据传输的可靠性,对于有可能出现的数据丢失情况,需要在程序中做相应的处理 [3] 。 3.原始套接字(SOCK_RAW) 原始套接字与标准套接字(标准套接字指的是前面介绍的流套接字和数据报套接字)的区别在于:原始套接字可以读写内核没有处理的IP数据包,而流套接字只能读取TCP协议的数据,数据报套接字只能读取UDP协议的数据。因此,如果要访问其他协议发送的数据必须使用原始套接 [3] 。 要通过互联网进行通信,至少需要一对套接字,其中一个运行于客户端,我们称之为 Client Socket,另一个运行于服务器端,我们称之为 Server Socket [3] 。 根据连接启动的方式以及本地套接字要连接的目标,套接字之间的连接过程可以分为三个步骤 [3] : (1)服务器监听。 (2)客户端请求。 (3)连接确认 [3] 。 1.服务器监听 所谓服务器监听,是指服务器端套接字并不定位具体的客户端套接字,而是处于等待连接的状态,实时监控网络状态 [3] 。 2.客户端请求 所谓客户端请求,是指由客户端的套接字提出连接请求,要连接的目标是服务器端的套接字。为此,客户端的套接字必须首先描述它要连接的服务器的套接字,指出服务器端套接字的地址和端口号,然后就向服务器端接字提出连接请求 [3] 。 3.连接确认 所谓连接确认,是指当服务器端套接字监听到或者说接收到客户端套接字的连接请求,就会响应客户端套接字的请求,建立一个新的线程,并把服务器端套接字的描述发送给客户端。一旦客户端确认了此描述,连接就建立好了。而服务器端套接字继续处于监听状态,接收其他客户端套接字的连接请求 [3] 。 根据套接字的不同类型,可以将套接字调用分为面向连接服务和无连接服务 [5] 。 面向连接服务的主要特点如下: (1)数据传输过程必须经过建立连接、维护连接和释放连接3个阶段 [5] ; (2)在传输过程中,各分组不需要携带目的主机的地址 [5] ; (3)可靠性好,但由于协议复杂,通信效率不高 [5] 。 面向无连接服务的主要特点如下: (1)不需要连接的各个阶段 [5] ; (2)每个分组都携带完整的目的主机地址,在系统中独立传送 [5] ; (3)由于没有顺序控制,所以接收方的分组可能出现乱序、重复和丢失现象 [5] ; (4)通信效率高,但可靠性不能确保 [5] 。 为了更方便地开发网络应用程序,美国伯克利大学在UNIX上推出了一种应用程序访问通信协议的操作系统调用接字(Socket)。 Socket的出现,使得程序员可以很方便地访问 TCPIP,从而开发各种网络应用程序。后来套接字被引进到 Windows等操作系统,成为开发网络应用程序的有效工具 [3] 。 套接字存在于通信区域,通信区域也被称为地址族,主要用于将通过套接字通信的进程的公有特性综合在一起。套接字通常只与同一区域的套接字交换数据。Windows Socket只支持一个通信区域——AF_INET国际网区域,使用网际协议族通信的进程使用该域 [3] 。 参考资料
Socket是什么意思?所谓套接字(Socket),就是对网络中不同主机上的应用进程之间进行双向通信的端点的抽象。 一个套接字就是网络上进程通信的一端,提供了应用层进程利用网络协议交换数据的机制。 从所处的地位来讲,套接字上联应用进程,下联网络协议栈,是应用程序通过网络协议进行通信的接口,是应用程序与网络协议栈进行交互的接口 。
Socket究竟是什么?socket: 百度百科上:套接字是双端通讯的端点抽象(网络中不同主机上应用进程之间)。 它上联应用进程,下联网络协议,是应用进程和网络进行交换的接口。 通俗的讲:socket就是对TCP/IP协议的一个封装,它使用设计模式中的门面模式,让程序员更好理解、使用的方式,使用TCP/IP协议栈。
Socket编程有什么用?Socket主要类型
流套接字用于提供面向连接、可靠的数据传输服务。 该服务将保证数据能够实现无差错、无重复送,并按顺序接收。 流套接字之所以能够实现可靠的数据服务,原因在于其使用了传输控制协议,即TCP(The Transmission Control Protocol)协议。
什么是Socket编程?简称套接字,是进程间通信的一种方式,它与其他进程间通信的一个主要不同是:它能实现不同主机间的进程间通信,我们网络上各种各样的服务大多数是基于socket来完成通信的。 socket是基于C/S架构的,也就是说socket网络编程,通常需要写两个文件,一个服务端,一个客户端。
|