Linux – 使用ETIMEDOUT的TCP连接()失败
对于TCP客户端connect()调用TCP服务器..
Richard Stevens撰写的UNIX?网络编程书籍如下…… 如果客户端TCP未收到对其SYN段的响应,则返回ETIMEDOUT. 4.4BSD, 在Linux中我想知道什么是重试机制(多少次和多远).要求因为TCP客户端connect()调用我得到ETIMEDOUT错误.此套接字具有O_NONBLOCK选项,并由epoll()监视事件. 如果有人可以指向我在代码中的哪个位置实现了这个重试逻辑,那么它也会有所帮助.我尝试从net / ipv4 / tcp_ipv4.c开始使用tcp_v4_connect(),但很快就迷失了方向. 解决方法
根据测量的往返时间缩放超时.
tcp_connect()设置一个计时器: /* Timer for repeating the SYN until an answer. */ inet_csk_reset_xmit_timer(sk,ICSK_TIME_RETRANS,inet_csk(sk)->icsk_rto,TCP_RTO_MAX); icsk_rto将使用每个目的地re-transmission timeout;如果来自目的地的先前度量标准可从先前的连接获得,则重新使用它. (有关详细信息,请参阅tcp(7)中的tcp_no_metrics_save讨论.)如果未保存任何度量标准,则内核将回退到默认的RTO值: #define TCP_RTO_MAX ((unsigned)(120*HZ)) #define TCP_RTO_MIN ((unsigned)(HZ/5)) #define TCP_TIMEOUT_INIT ((unsigned)(1*HZ)) /* RFC2988bis initial RTO value */ #define TCP_TIMEOUT_FALLBACK ((unsigned)(3*HZ)) /* RFC 1122 initial RTO value,now * used as a fallback RTO for the * initial data transmission if no * valid RTT sample has been acquired,* most likely due to retrans in 3WHS. */ tcp_retransmit_timer()在底部附近有一些代码用于重新计算延迟: inet_csk_reset_xmit_timer(sk,icsk->icsk_rto,TCP_RTO_MAX); if (retransmits_timed_out(sk,sysctl_tcp_retries1 + 1,0)) __sk_dst_reset(sk); retransmits_timed_out()将首先执行线性退避,然后执行指数退避. 我认为,除非内核有充分的理由怀疑远程对等方应该早点回复,否则你可以合理地期望在从连接(2)获得ETIMEDOUT错误返回之前大约120秒. (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |