up:: 5.7-TCP可靠传输的实现
学习视频
笔记
小结:
需要解决的矛盾
三次握手
注意同步建立的状态和连接建立状态在三次握手里的区分。。。
大写ACK为了确认收到首部SYN,小写确认收到seq
syn是为了区分出传输过程和连接过程,这两个性质不相同。。。
TCP工作模式是全双工的,发送和接收数据序号不一样,两边都有发送和确认,seq表示从哪发送,ack表示确认收到的序号数。。。所以一个seq为x,一个为y,上面也说了只消耗一个字节,ack于是就是seq序号然后加一个数的确认,即ack=x+1,ack=y+1
同理,连接报文段是表示连接过程,而不是传输过程,所以也不能传输数据,也要消耗掉一个报文序号。。。
tcp客户进程收到tcp连接请求确认报文段后,还要向tcp服务器进程发送一个普通的tcp确认报文段 并进入连接已建立状态。。。
tcp规定,普通的tcp确认报文段可以携带数据,但如果不携带数据,则不消耗序号。tcp是通过字节流传输,我们会分组传输,打上序号,按序进行,失序以便得到重传。。。
思考
为什么tcp客户进程最后还要发送一个普通的tcp确认报文段呢,这是否多余
换句话说,能否使用两报文握手建立连接呢
答案是并不多余,不能简化为两报文握手
说明:(细读)
考虑这样一种情况,tcp客户进程发出一个tcp连接请求报文段,但该报文段在某些网络节点长时间滞留了
这必然会造成该报文段的超时重传,假设重传的报文段被tcp服务器进程正常接收
tcp服务器进程给tcp客户进程发送一个tcp连接请求确认报文段
并进入连接已建立状态,请注意,由于我们改为两道文握手,因此tcp服务器进程发送完tcp连接请求确认报文段后,进入的是连接已建立状态,而不像三报文握手那样进入同步已接收状态
并等待tcp客户进程发来针对tcp连接请求确认报文段的普通确认报文段
tcp客户进程收到tcp连接请求确认报文段后,进入tcp连接已建立状态,但不会给tcp服务器进程发送针对该报文段的普通确认报文段
现在tcp双方都处于连接已建立状态,他们可以相互传输数据之后可以通过四报文挥手来释放连接,tcp双方都进入了关闭状态
一段时间后,之前滞留在网络中的那个失效的tcp连接请求,报文段到达了tcp服务器进程,tcp服务器进程会误认为这是tcp客户进程又发起了一个新的tcp连接请求,于是给tcp客户进程发送tcp连接请求,确认报文段并进入连接已建立状态,该报文段到达tcp客户进程,由于tcp客户进程并没有发起新的tcp连接请求,并且处于关闭状态,因此不会理会该报文段,但tcp服务器进程已进入了连接已建立状态,他认为新的tcp连接已建立好了,并一直等待tcp客户进程发来数据,这将白白浪费tcp服务器进程所在主机的很多资源
综上所述,采用三报文握手,而不是两报文握手来建立tcp连接,是为了防止以失效的连接请求报文段突然又传送到了tcp服务器进程,因而导致错误