上海网站建设导航,网站301重定向,怎样做一个属于自己的小程序,wordpress前台用户中心注#xff1a;本文为“TCP 连接状态标识”相关文章合辑。 TCP 的状态#xff1a;SYN, FIN, ACK, PSH, RST, URG 简介及 ACK 确认机制
llzhang_fly 于 2020-09-19 05:25:26 发布
1、TCP 的状态 FLAGS 字段状态
在 TCP 层#xff0c;有个 FLAGS 字段#xff0c;这个字段有…注本文为“TCP 连接状态标识”相关文章合辑。 TCP 的状态SYN, FIN, ACK, PSH, RST, URG 简介及 ACK 确认机制
llzhang_fly 于 2020-09-19 05:25:26 发布
1、TCP 的状态 FLAGS 字段状态
在 TCP 层有个 FLAGS 字段这个字段有以下几个标识SYN, FIN, ACK, PSH, RST, URG.
对于我们日常的分析有用的就是前面的五个字段它们的含义是
SYN 表示建立连接
FIN 表示关闭连接
ACK 表示响应
PSH 表示有 DATA 数据传输
RST 表示连接重置。
其中ACK 是可能与 SYNFIN 等同时使用的比如SYN 和 ACK 可能同时为 1它表示的就是建立连接之后的响应 如果只是单个的一个 SYN它表示的只是建立连接。TCP 的几次握手就是通过这样的 ACK 表现出来的。
但 SYN 与 FIN 是不会同时为 1 的因为前者表示的是建立连接而后者表示的是断开连接。
RST 一般是在 FIN 之后才会出现为 1 的情况表示的是连接重置。 一般地当出现 FIN 包或 RST 包时我们便认为客户端与服务器端断开了连接而当出现 SYN 和 SYNACK 包时我们认为客户端与服务器建立了一个连接。
PSH 为 1 的情况一般只出现在 DATA 内容不为 0 的包中也就是说 PSH 为 1 表示的是有真正的 TCP 数据包内容被传递。
TCP 的连接建立和连接关闭都是通过请求响应的模式完成的。
概念补充 - TCP 三次握手
TCP(Transmission Control Protocol) 传输控制协议
TCP 是主机对主机层的传输控制协议提供可靠的连接服务采用三次握手确认建立一个连接
位码即 tcp 标志位有 6 种标示SYN(synchronous 建立联机) ACK(acknowledgement 确认) PSH(push 传送) FIN(finish 结束) RST(reset 重置) URG(urgent 紧急) Sequence number(顺序号码) Acknowledge number(确认号码)
第一次握手主机 A 发送位码为 syn1随机产生 seq number1234567 的数据包到服务器主机 B 由 SYN1 知道A 要求建立联机
第二次握手主机 B 收到请求后要确认联机信息向 A 发送 ack number(主机 A 的 seq1)syn1ack1随机产生 seq7654321 的包
第三次握手主机 A 收到后检查 ack number 是否正确即第一次发送的 seq number1以及位码 ack 是否为 1若正确主机 A 会再发送 ack number(主机 B 的 seq1)ack1主机 B 收到后确认 seq 值与 ack1 则连接建立成功。
完成三次握手主机 A 与主机 B 开始传送数据。
2、Wireshark TCP 报文到达 ACK 确认机制
转载
Wireshark TCP 报文到达 ACK 确认机制_whireshark ack-CSDN 博客 https://blog.csdn.net/chenlycly/article/details/74028616
TCP 数据包中的序列号Sequence Number 不是以报文段来进行编号的而是 将连接生存周期内传输的所有数据当作一个字节流序列号就是整个字节流中每个字节的编号。一个 TCP 数据包中包含多个字节流的数据即数据段而且每个 TCP 数据包中的数据大小不一定相同。在建立 TCP 连接的三次握手过程中通信双方各自已确定了初始的序号 x 和 yTCP 每次传送的报文段中的序号字段值表示所要传送本报文中的第一个字节的序号。
TCP 的报文到达确认ACK是对接收到的数据的最高序列号的确认表示这前面的数据已经接收到并向发送端返回一个下次接收时期望的 TCP 数据包的序列号Ack Number 。例如主机 A 发送的当前数据序号是 400数据长度是 100则接收端收到后会返回一个确认号是 500 的确认号给主机 A。
TCP 提供的确认机制可以在通信过程中可以不对每一个 TCP 数据包发出单独的确认包Delayed ACK 机制而是在传送数据时顺便把确认信息传出这样可以大大提高网络的利用率和传输效率。同时TCP 的确认机制也可以一次确认多个数据报例如接收方收到了 201301401 的数据报则只需要对 401 的数据包进行确认即可对 401 的数据包的确认也意味着 401 之前的所有数据包都已经确认这样也可以提高系统的效率。
若发送方在规定时间内没有收到接收方的确认信息就要将未被确认的数据包重新发送。接收方如果收到一个有差错的报文则丢弃此报文并不向发送方发送确认信息。因此TCP 报文的重传机制是由设置的超时定时器来决定的在定时的时间内没有收到确认信息则进行重传。 这个定时的时间值的设定非常重要太大会使包重传的延时比较大太小则可能没有来得及收到对方的确认包发送方就再次重传会使网络陷入无休止的重传过程中。接收方如果收到了重复的报文将会丢弃重复的报文但是必须发回确认信息否则对方会再次发送。 丢包重传直到收到 ACK 报文或发送方达到配置的最大重传次数最大重传次数取决于发送操作系统的配置值。默认情况下Windows 主机默认重传 5 次。大多数 Linux 系统默认最大 15 次。两种操作系统都可配置。
TCP 协议应当保证数据报按序到达接收方。如果接收方收到的数据报文没有错误只是未按序号这种现象如何处理呢TCP 协议本身没有规定而是由 TCP 协议的实现者自己去确定。通常有两种方法进行处理一是对没有按序号到达的报文直接丢弃二是将未按序号到达的数据包先放于缓冲区内等待它前面的序号包到达后再将它交给应用进程。后一种方法将会提高系统的效率。例如发送方连续发送了每个报文中 100 个字节的 TCP 数据报其序号分别是 1101201…,701。假如其它数据报都收到了而 201 这个数据报没有收到则接收端应当对 1 和 101 这两个数据报进行确认并将数据递交给相关的应用进程301 至 701 这 5 个数据报则应当放于缓冲区等到 201 这个数据报到达后然后按序将 201 至 701 这些数据报递交给相关应用进程并对 701 数据报进行确认确保了应用进程级的 TCP 数据的按序到达。
3、TCP 抓包分析 总结
1、ACK 包可以和其他包合在一起比如 ACK 包可以携带数据
2、可以接收多个数据包后一次性给一个应答不用每个数据包一一对应给应答
3、在通信过程中通过接收到的包的 ack 值可以判断是否是上一个本机发送包的应答包ack 值与上一个本机发送包的 seq 有关seq 值和 ack 值的确定规则如下
三次握手
第一次握手发送seq 为 xx 为任意值无视 ack因为是第一个包不需要给其他包应答
第二次握手发送seq 为 yy 为任意值ack 等于接收包 seq1即 x1
第三次握手发送seq 等于上一个本机发送包 seq1即 x1也就是 1ack 等于接收包 seq1即 y1
数据传输
某主机发送的 seq 和 ack 是根据上一个接收包的 seq、ack 和 len 得到具体为seqackackseqlen
提醒如果某一主机连续发了 4 个包后三个包的 seq 和 ack 和第一个包的一样
提醒seq 会单调增大
特别如果握手完第一个数据包是客户端发送第一个数据包的 seq 和 ack 和第三次握手的一样
四次挥手
如果是服务器发起的挥手挥手前最后一个包是服务器发送
如果是客户端发起的挥手挥手前最后一个包是客户端发送
第一次挥手发送seq 为上一个本机发送包 seqlenack 为上一个本机发送包 ack
第二个挥手发送seq 为本次接收包 ackack 为本次接收包 seq1
第三次挥手发送和第二次挥手一样
第四次挥手发送seq 为本次接收包 ackack 为本次接收包 seq1
如果是服务器发起的挥手挥手前最后一个包是客户端发送
如果是客户端发起的挥手挥手前最后一个包是服务器发送
第一次挥手发送seq 为本次接收包 ackack 为本次接收包 seqlen
第二个挥手发送seq 为本次接收包 ackack 为本次接收包 seq1
第三次挥手发送和第二次挥手一样
第四次挥手发送seq 为本次接收包 ackack 为本次接收包 seq1
4、TCP 包的 seq 和 ack 号计算方法
https://blog.csdn.net/huaishu/article/details/93739446
5、使用 wireshark 出现很多 TCP Retransmission 信息
http://blog.jues.org.cn/post/shi-yong-wireshark-chu-xian-hen-duo-tcp-retransmission-xin-xi.html
出现 TCP Retransmission 多数是因为目标主机的端口没开有开放监听很少出现是网络不好导致的。 如果在某个时间段RTT 的倍数内没有确认发送的数据则将数据重新传输到远程主机。重传超时从 RTT 开始并随着每次重传而增加一倍。 重传超时总是受限于 CFGZ-MNRTO 和 CFGYMax RTO。如果自从第一次传输数据以来CFGY-ReTrExtTMO 时间就过去了连接被关闭即状态被设置为关闭。注意当一个套接字被关闭时将响应于接收到的端口所发送的任何数据包来发送重置。
当超时发生时将重新发送输出窗口中的所有未确认数据。数据被重新打包因此包将不与原始包相同。例如如果以 10 字节的数据发送分组则发送具有 30 字节数据的分组并且第一分组丢失40 字节的未确认数据将在输出窗口中。当超时发生时所有 40 个字节将在一个分组中发送假设 MSS 大于或等于 40。
如果接收到三个重复的确认则快速重传算法无需等待超时即可重传 TCP 数据。RTIP32 还实现了 RFC 2582 中定义的 NeReNeO 快速恢复算法。
转载https://blog.csdn.net/lemontree1945/article/details/88581516
类似场景client 连接服务器时因 TLS 证书设置错误所以会导致连接服务器后没有收到应答即发送 SYN 报文无响应 TCP 的连接状态标识(SYN, FIN, ACK, PSH, RST, URG)
m0_37989944 于 2021-09-03 18:47:59 发布
TCP 层有个 FLAGS 字段这个字段有以下几个标识SYN, FIN, ACK, PSH, RST, URG.
其中对于我们日常的分析有用的就是前面的五个字段。它们的含义是
1SYN 表示建立连接
2FIN 表示关闭连接
3ACK 表示响应
4PSH 表示有 DATA 数据传输
5RST 表示连接重置。
其中ACK 是可能与 SYNFIN 等同时使用的比如 SYN 和 ACK 可能同时为 1它表示的就是建立连接之后的响应
如果只是单个的一个 SYN它表示的只是建立连接。
TCP 的几次握手就是通过这样的 ACK 表现出来的。
但 SYN 与 FIN 是不会同时为 1 的因为前者表示的是建立连接而后者表示的是断开连接。
RST 一般是在 FIN 之后才会出现为 1 的情况表示的是连接重置。
一般地当出现 FIN 包或 RST 包时我们便认为客户端与服务器端断开了连接而当出现 SYN 和 SYNACK 包时我们认为客户端与服务器建立了一个连接。
PSH 为 1 的情况一般只出现在 DATA 内容不为 0 的包中也就是说 PSH 为 1 表示的是有真正的 TCP 数据包内容被传递。
TCP 的连接建立和连接关闭都是通过请求响应的模式完成的。
概念补充 - TCP 三次握手 TCP(Transmission Control Protocol) 传输控制协议
TCP 是主机对主机层的传输控制协议提供可靠的连接服务采用三次握手确认建立一个连接
位码即 tcp 标志位有 6 种标示SYN(synchronous 建立联机) ACK(acknowledgement 确认) PSH(push 传送) FIN(finish 结束) RST(reset 重置) URG(urgent 紧急) Sequence number(顺序号码) Acknowledge number(确认号码)
第一次握手主机 A 发送位码为 syn1随机产生 seq number1234567 的数据包到服务器主机 B 由 SYN1 知道A 要求建立联机
第二次握手主机 B 收到请求后要确认联机信息向 A 发送 ack number(主机 A 的 seq1)syn1ack1随机产生 seq7654321 的包
第三次握手主机 A 收到后检查 ack number 是否正确即第一次发送的 seq number1以及位码 ack 是否为 1若正确主机 A 会再发送 ack number(主机 B 的 seq1)ack1主机 B 收到后确认 seq 值与 ack1 则连接建立成功。
完成三次握手主机 A 与主机 B 开始传送数据。
在 TCP/IP 协议中TCP 协议提供可靠的连接服务采用三次握手建立一个连接。
第一次握手建立连接时客户端发送 syn 包(synj) 到服务器并进入 SYN_SEND 状态等待服务器确认
第二次握手服务器收到 syn 包必须确认客户的 SYNackj1同时自己也发送一个 SYN 包synk即 SYNACK 包此时服务器进入 SYN_RECV 状态
第三次握手客户端收到服务器的 SYNACK 包向服务器发送确认包 ACK(ackk1)此包发送完毕客户端和服务器进入 ESTABLISHED 状态完成三次握手。完成三次握手客户端与服务器开始传送数据。 【注意】中断连接端可以是 Client 端也可以是 Server 端。
假设 Client 端发起中断连接请求也就是发送 FIN 报文。Server 端接到 FIN 报文后意思是说 “我 Client 端没有数据要发给你了”但是如果你还有数据没有发送完成则不必急着关闭 Socket可以继续发送数据。所以你先发送 ACK“告诉 Client 端你的请求我收到了但是我还没准备好请继续你等我的消息”。这个时候 Client 端就进入 FIN_WAIT 状态继续等待 Server 端的 FIN 报文。当 Server 端确定数据已发送完成则向 Client 端发送 FIN 报文“告诉 Client 端好了我这边数据发完了准备好关闭连接了”。Client 端收到 FIN 报文后“就知道可以关闭连接了但是他还是不相信网络怕 Server 端不知道要关闭所以发送 ACK 后进入 TIME_WAIT 状态如果 Server 端没有收到 ACK 则可以重传。“Server 端收到 ACK 后” 就知道可以断开连接了 。Client 端等待了 2MSL后依然没有收到回复则证明 Server 端已正常关闭那好我 Client 端也可以关闭连接了。OkTCP 连接就这样关闭了
整个过程 Client 端所经历的状态如下 而 Server 端所经历的过程如下
【注意】 在 TIME_WAIT 状态中如果 TCP client 端最后一次发送的 ACK 丢失了它将重新发送。TIME_WAIT 状态中所需要的时间是依赖于实现方法的。典型的值为 30 秒、1 分钟和 2 分钟。等待之后连接正式关闭并且所有的资源(包括端口号) 都被释放。
【问题 1】为什么连接的时候是三次握手关闭的时候却是四次握手
答因为当 Server 端收到 Client 端的 SYN 连接请求报文后可以直接发送 SYNACK 报文。其中 ACK 报文是用来应答的SYN 报文是用来同步的。但是关闭连接时当 Server 端收到 FIN 报文时很可能并不会立即关闭 SOCKET所以只能先回复一个 ACK 报文告诉 Client 端“你发的 FIN 报文我收到了”。只有等到我 Server 端所有的报文都发送完了我才能发送 FIN 报文因此不能一起发送。故需要四步握手。
【问题 2】为什么 TIME_WAIT 状态需要经过 2MSL(最大报文段生存时间) 才能返回到 CLOSE 状态
答虽然按道理四个报文都发送完毕我们可以直接进入 CLOSE 状态了但是我们必须假象网络是不可靠的有可以最后一个 ACK 丢失。所以 TIME_WAIT 状态就是用来重发可能丢失的 ACK 报文。 10054 错位码
有人问select 写 socket 时候 建立链接立马发送数据有时候收不到数据 还提示 10054 大多数的况还是能收到的 一般收不到数据的时候 第二次再链接发送数据就能收到 请问是怎么回事呢
对于好奇心极强的我对于这个没遇到的问题我就百度了 10054 错误。网上说
一般来说是连接被对方重设。一个建立的连接被远程主机强行关闭若远程主机上的进程异常终止运行由于内存冲突或硬件故障或者针对套接字执行了一次强行关闭便会产生 10054 错误。针对强行关闭的情况可用 SO_LINGER 套接字选项和 setsockopt 来配置一个套接字。
而对于 群里描述的那个问题我回忆了 TCP/IP 协议我认为会有如下两种情况
1client 在与 server 进行三次握手时client 调用 connect 函数完成了连接的建立客户端自以为建立了而实际 server 那边却没有收到最后一次握手 ack 的回复。这时触发了 server 的 syn 触发器重发 SYNACK 包一般默认是重发 5 次时间分别是 1 秒、2 秒、4 秒、8 秒、16 秒而此时 client 马上发送数据的话server 会发 RST 回复给 client, 那么此时 client 就会提示 10054。
2而另一种情况就是 server 这边的 accept 队列满了一般有 syn_recv 队列accept 队列那么此时 server 会直接回复 RST(最新的 linux 内核是这么实现的)当然也有可能会拒绝 client 的请求让 client 自己自动断开请求。
群里的一位大神冒泡说实现第二种方式也就是拒绝 client 发过来的请求原因如下
第一服务器已经处理不过来了再发 rst 加剧压力
第二客户端如果丢包会等到超时再重试而收到 rst 的话有可能立刻重试服务器压力会更大。
Linux 网络编程中 socket 常见错误码分析
EINTR 4
阻塞的操作被取消阻塞的调用打断。如设置了发送接收超时就会遇到这种错误。
只能针对阻塞模式的 socket。读写阻塞的 socket 时-1 返回错误号为 INTR。另外如果出现 EINTR 即 errno 为 4错误描述 Interrupted system call操作也应该继续。如果 recv 的返回值为 0那表明连接已经断开接收操作也应该结束。
ETIMEOUT110
1、操作超时。一般设置了发送接收超时遇到网络繁忙的情况就会遇到这种错误。
2、服务器做了读数据做了超时限制读时发生了超时。
3、错误被描述为 “connect time out”即 “连接超时”这种情况一般发生在服务器主机崩溃。此时客户 TCP 将在一定时间内依具体实现持续重发数据分节试图从服务 TCP 获得一个 ACK 分节。当最终放弃尝试后此时服务器未重新启动内核将会向客户进程返回 ETIMEDOUT 错误。如果某个中间路由器判定该服务器主机已经不可达则一般会响应 “destination unreachable”“目的地不可达” 的 ICMP 消息相应的客户进程返回的错误是 EHOSTUNREACH 或 ENETUNREACH。当服务器重新启动后由于 TCP 状态丢失之前所有的连接信息也不存在了此时对于客户端发来请求将回应 RST。如果客户进程对检测服务器主机是否崩溃很有必要要求即使客户进程不主动发送数据也能检测出来那么需要使用其它技术如配置 SO_KEEPALIVE Socket 选项或实现某些心跳函数。
EAGAIN
1、Send 返回值小于要发送的数据数目会返回 EAGAIN 和 EINTR。
2、recv 返回值小于请求的长度时说明缓冲区已经没有可读数据但再读不一定会触发 EAGAIN有可能返回 0 表示 TCP 连接已被关闭。
3、当 socket 是非阻塞时如返回此错误表示写缓冲队列已满可以做延时后再重试.
4、在 Linux 进行非阻塞的 socket 接收数据时经常出现 Resource temporarily unavailableerrno 代码为 11(EAGAIN)表明在非阻塞模式下调用了阻塞操作在该操作没有完成就返回这个错误这个错误不会破坏 socket 的同步不用管它下次循环接着 recv 就可以。对非阻塞 socket 而言EAGAIN 不是一种错误。
EPIPE
1、Socket 关闭但是 socket 号并没有置 - 1。继续在此 socket 上进行 send 和 recv就会返回这种错误。这个错误会引发 SIGPIPE 信号系统会将产生此 EPIPE 错误的进程杀死。所以一般在网络程序中首先屏蔽此消息以免发生不及时设置 socket 进程被杀死的情况。
2、write(…) on a socket that has been closed at the other end will cause a SIGPIPE.
3、错误被描述为 “broken pipe”即 “管道破裂”这种情况一般发生在客户进程不理会或未及时处理Socket 错误继续向服务 TCP 写入更多数据时内核将向客户进程发送 SIGPIPE 信号该信号默认会使进程终止此时该前台进程未进行 core dump。结合上边的 ECONNRESET 错误可知向一个 FIN_WAIT2 状态的服务 TCP已 ACK 响应 FIN 分节写入数据不成问题但是写一个已接收了 RST 的 Socket 则是一个错误。
EBADF
read(…) or write(…) on a locally closed socket will return EBADF
EFAULT
地址错误。
EBUSY
ECONNREFUSED
1、拒绝连接。一般发生在连接建立时。
拔服务器端网线测试客户端设置 keep alive 时recv 较快返回 0 先收到 ECONNREFUSED(Connection refused) 错误码其后都是 ETIMEOUT。
2、an error returned from connect(), so it can only occur in a client(if a client is defined as the party that initiates the connection
ECONNRESET
1、在客户端服务器程序中客户端异常退出并没有回收关闭相关的资源服务器端会先收到 ECONNRESET 错误然后收到 EPIPE 错误。
2、连接被远程主机关闭。有以下几种原因远程主机停止服务重新启动当在执行某些操作时遇到失败因为设置了 “keep alive” 选项连接被关闭一般与 ENETRESET 一起出现。
3、远程端执行了一个 “hard” 或者 “abortive” 的关闭。应用程序应该关闭 socket因为它不再可用。当执行在一个 UDP socket 上时这个错误表明前一个 send 操作返回一个 ICMP “port unreachable” 信息。
4、如果 client 关闭连接server 端的 select 并不出错(不返回 - 1, 使用 select 对唯一一个 socket 进行 non- blocking 检测), 但是写该 socket 就会出错用的是 send. 错误号ECONNRESET. 读(recv) socket 并没有返回错误。
5、该错误被描述为 “connection reset by peer”即 “对方复位连接”这种情况一般发生在服务进程较客户进程提前终止。当服务进程终止时会向客户 TCP 发送 FIN 分节客户 TCP 回应 ACK服务 TCP 将转入 FIN_WAIT2 状态。此时如果客户进程没有处理该 FIN 如阻塞在其它调用上而没有关闭 Socket 时则客户 TCP 将处于 CLOSE_WAIT 状态。当客户进程再次向 FIN_WAIT2 状态的服务 TCP 发送数据时则服务 TCP 将立刻响应 RST。一般来说这种情况还可以会引发另外的应用程序异常客户进程在发送完数据后往往会等待从网络 IO 接收数据很典型的如 read 或 readline 调用此时由于执行时序的原因如果该调用发生在 RST 分节收到前执行的话那么结果是客户进程会得到一个非预期的 EOF 错误。此时一般会输出 “server terminated prematurely”“服务器过早终止” 错误。
EINVAL
无效参数。提供的参数非法。有时也会与 socket 的当前状态相关如一个 socket 并没有进入 listening 状态此时调用 accept就会产生 EINVAL 错误。
EMFILE
打开了太多的 socket。对进程或者线程而言每种实现方法都有一个最大的可用 socket 数目处理或者是全局的或者是局部的。
EWOULDBLOCKEAGAIN
资源暂时不可用。这个错误是从对非阻塞 socket 进行的不能立即结束的操作返回的如当没有数据在队列中可以读时调用 recv。并不是 fatal 错误稍后操作可以被重复。调用在一个非阻塞的 SOCK_STREAM socket 上调用 connect 时会产生这个错误因为有时连接建立必须消耗一定的时间。
ENOTCONN
在一个没有建立连接的 socket 上进行 readwrite 操作会返回这个错误。出错的原因是 socket 没有标识地址。Setsoc 也可能会出错。
ECONNRESET
Connection reset by peer.
连接被远程主机关闭。有以下几种原因远程主机停止服务重新启动当在执行某些操作时遇到失败因为设置了 “keep alive” 选项连接被关闭一般与 ENETRESET 一起出现。
ECONNABORTED
1、软件导致的连接取消。一个已经建立的连接被 host 方的软件取消原因可能是数据传输超时或者是协议错误。
2、该错误被描述为 “software caused connection abort”即 “软件引起的连接中止”。原因在于当服务和客户进程在完成用于 TCP 连接的 “三次握手” 后客户 TCP 却发送了一个 RST 复位分节在服务进程看来就在该连接已由 TCP 排队等着服务进程调用 accept 的时候 RST 却到达了。POSIX 规定此时的 errno 值必须 ECONNABORTED。源自 Berkeley 的实现完全在内核中处理中止的连接服务进程将永远不知道该中止的发生。服务器进程一般可以忽略该错误直接再次调用 accept。
当 TCP 协议接收到 RST 数据段表示连接出现了某种错误函数 read 将以错误返回错误类型为 ECONNERESET。并且以后所有在这个套接字上的读操作均返回错误。错误返回时返回值小于 0。
ENETUNREACH
网络不可达。Socket 试图操作一个不可达的网络。这意味着 local 的软件知道没有路由到达远程的 host。
ENETRESET
网络重置时丢失连接。
由于设置了 “keep-alive” 选项探测到一个错误连接被中断。在一个已经失败的连接上试图使用 setsockopt 操作也会返回这个错误。
EINPROGRESS
操作正在进行中。一个阻塞的操作正在执行。
ENOTSOCK
在非 socket 上执行 socket 操作。
EDESTADDRREQ
需要提供目的地址。
在一个 socket 上的操作需要提供地址。如往一个 ADDR_ANY 地址上进行 sendto 操作会返回这个错误。
EMSGSIZE
消息体太长。
发送到 socket 上的一个数据包大小比内部的消息缓冲区大或者超过别的网络限制或是用来接收数据包的缓冲区比数据包本身小。
EPROTOTYPE
协议类型错误。标识了协议的 Socket 函数在不支持的 socket 上进行操作。如 ARPA Internet
UDP 协议不能被标识为 SOCK_STREAM socket 类型。
ENOPROTOOPT
该错误不是一个 Socket 连接相关的错误。errno 给出该值可能由于通过 getsockopt 系统调用来获得一个套接字的当前选项状态时如果发现了系统不支持的选项参数就会引发该错误。
EPROTONOSUPPORT
不支持的协议。系统中没有安装标识的协议或者是没有实现。如函数需要 SOCK_DGRAM socket但是标识了 stream protocol.。
ESOCKTNOSUPPORT
Socket 类型不支持。指定的 socket 类型在其 address family 中不支持。如可选选中选项 SOCK_RAW但实现并不支持 SOCK_RAW sockets。
连接过程可能出现的错误情况有
1 如果客户机 TCP 协议没有接收到对它的 SYN 数据段的确认函数以错误返回错误类型为 ETIMEOUT。通常 TCP 协议在发送 SYN 数据段失败之后会多次发送 SYN 数据段在所有的发送都高中失败之后函数以错误返回。
注SYNsynchronize位请求连接。TCP 用这种数据段向对方 TCP 协议请求建立连接。在这个数据段中TCP 协议将它选择的初始序列号通知对方并且与对方协议协商最大数据段大小。SYN 数据段的序列号为初始序列号这个 SYN 数据段能够被确认。当协议接收到对这个数据段的确认之后建立 TCP 连接。
2 如果远程 TCP 协议返回一个 RST 数据段函数立即以错误返回错误类型为 ECONNREFUSED。当远程机器在 SYN 数据段指定的目的端口号处没有服务进程在等待连接时远程机器的 TCP 协议将发送一个 RST 数据段向客户机报告这个错误。客户机的 TCP 协议在接收到 RST 数据段后不再继续发送 SYN 数据段函数立即以错误返回。
注RSTreset位表示请求重置连接。当 TCP 协议接收到一个不能处理的数据段时向对方 TCP 协议发送这种数据段表示这个数据段所标识的连接出现了某种错误请求 TCP 协议将这个连接清除。 有 3 种情况可能导致 TCP 协议发送 RST 数据段 1SYN 数据段指定的目的端口处没有接收进程在等待 2TCP 协议想放弃一个已经存在的连接 3TCP 接收到一个数据段但是这个数据段所标识的连接不存在。接收到 RST 数据段的 TCP 协议立即将这条连接非正常地断开并向应用程序报告错误。
3 如果客户机的 SYN 数据段导致某个路由器产生 “目的地不可到达” 类型的 ICMP 消息函数以错误返回错误类型为 EHOSTUNREACH 或 ENETUNREACH。通常 TCP 协议在接收到这个 ICMP 消息之后记录这个消息然后继续几次发送 SYN 数据段在所有的发送都告失败之后TCP 协议检查这个 ICMP 消息函数以错误返回。
注ICMPInternet 消息控制协议。Internet 的运行主要是由 Internet 的路由器来控制路由器完成 IP 数据包的发送和接收如果发送数据包时发生错误路由器使用 ICMP 协议来报告这些错误。ICMP 数据包是封装在 IP 数据包的数据部分中进行传输的其格式如下
ICMP 数据包主要有以下类型
1 目的地不可到达A、目的主机未运行B、目的地址不存在C、路由表中没有目的地址对应的条目因而路由器无法找到去往目的主机的路由。
2 超时路由器将接收到的 IP 数据包的生存时间TTL域减 1如果这个域的值变为 0路由器丢弃这个 IP 数据包并且发送这种 ICMP 消息。
3 参数出错当 IP 数据包中有无效域时发送。
4 重定向将一条新的路径通知主机。
5 ECHO 请求、ECHO 回答这两条消息用语测试目的主机是否可以到达。请求者向目的主机发送 ECHO 请求 ICMP 数据包目的主机在接收到这个 ICMP 数据包之后返回 ECHO 回答 ICMP 数据包。
6 时戳请求、时戳回答ICMP 协议使用这两种消息从其他机器处获得其时钟的当前时间。
调用函数 connect 的过程中当客户机 TCP 协议发送了 SYN 数据段的确认之后TCP 状态由 CLOSED 状态转为 SYN_SENT 状态在接收到对 SYN 数据段的确认之后TCP 状态转换成 ESTABLISHED 状态函数成功返回。如果调用函数 connect 失败应该用 close 关闭这个套接字描述符不能再次使用这个套接字描述符来调用函数 connect。
connect 函数的出错处理
1ETIMEOUTconnection timed out 目的主机不存在没有返回任何相应例如主机关闭
2ECONNREFUSEDconnection refused硬错到达目的主机后由于各种原因建立不了连接主机返回 RST复位响应例如主机监听进程未启用tcp 取消连接等
3EHOSTTUNREACHno route to host软错) 路由上引发了一个目的地不可达的 ICMP 错误
其中13客户端会进行定时多次重试一定次数后才返回错误。另外当 connect 连接失败时sockfd 套接口不可用必须关闭后重新 socket 分配才行。 via: TCP 的状态SYN, FIN, ACK, PSH, RST, URG 简介及 ACK 确认机制_psh ack-CSDN 博客 https://blog.csdn.net/llzhang_fly/article/details/108676070 TCP 的连接状态标识(SYN, FIN, ACK, PSH, RST, URG)_fin ack-CSDN 博客 https://blog.csdn.net/m0_37989944/article/details/120086446