Chinaunix首页 | 论坛 | 博客
  • 博客访问: 348648
  • 博文数量: 18
  • 博客积分: 2049
  • 博客等级: 大尉
  • 技术积分: 664
  • 用 户 组: 普通用户
  • 注册时间: 2007-07-06 17:38
文章分类

全部博文(18)

文章存档

2012年(1)

2011年(8)

2010年(4)

2009年(2)

2008年(3)

分类: LINUX

2011-11-11 20:54:27


继续讲述/proc/net/netstat, /proc/net/snmp中TCP的故事。

TCP Congestion Processing

类别
名称
描述
TcpExtTCPDSACKUndotcp_ack() -> tcp_fastretrans_alert() -> tcp_try_undo_dsack()

Disorder状态下,undo完成(undo_retrans == 0)的次数。

TcpExtTCPFullUndotcp_ack() -> tcp_fastretrans_alert() -> tcp_try_undo_recovery()

Recovery状态时,接收到到全部确认(snd_una >= high_seq)后且已经undo完成(undo_retrans == 0)的次数。

TcpExtTCPPartialUndotcp_ack() -> tcp_fastretrans_alert() -> tcp_undo_partial()

Recovery状态时,接收到到部分确认(snd_una < high_seq)时但已经undo完成(undo_retrans == 0)的次数。

TcpExtTCPLossUndotcp_ack() -> tcp_fastretrans_alert() -> tcp_try_undo_loss()

Loss状态时,接收到到全部确认(snd_una >= high_seq)后且已经undo完成(undo_retrans == 0)的次数。

TcpExtTCPRenoReorder

在tcp_update_reordering()中更新,当metric > tp->reordering并且没有启用SACK,本计数器加1 综合来说,在sacked_out“不可靠”时,tp->reordering被更新为当前窗口中的“已用seg”个数,同时包括未确认(和已确认的?)数据,但不包括lost_out。

A. tcp_ack() -> tcp_fastretrans_alert() -> tcp_add_reno_sack() -> tcp_check_reno_reordering() -> tcp_update_reordering(): 
在Open/Recovery/Disorder/CWR状态下接收到dupACK时:
如果sacked_out + lost_out > packets_out,
用metric( = packets_out)调用tcp_update_reordering()
B. tcp_ack() -> tcp_clean_rtx_queue() -> tcp_remove_reno_sacks() -> tcp_check_reno_reordering() -> tcp_update_reordering() : 
在清理rtx queue时,会从packets_out, lost_out, sacked_out中减去确认了的seg数量,
如果sacked_out + lost_out > packets_out,
用metric( = packets_out + acked_pcount)调用tcp_update_reordering()

注:

  1. sacked_out : 接收到的dupACK数量
  2. lost_out : 限制最小值为1,最大值为packets_out
  3. tp->reordering: 创建socket时,被动建立连接时,进入Loss状态时,初始化为sysctl_tcp_reordering

TcpExtTCPSACKReorder

在tcp_update_reordering()中更新,当metric > tp->reordering并且启用SACK但关闭FACK时,本计数器加1
A. tcp_ack() -> tcp_sacktag_write_queue() -> tcp_update_reordering() 
在tcp_sacktag_walk()中会计算fackets_out(通过累加state.fack_count),这个值即从snd_una开始到已经SACK的最高序号间的seg数量(包括没有被SACK覆盖的)。判断发生乱序的条件是: (1)发现针对重传报文的D-SACK;(2)当前接收到SACK序号比以前接收到的最大SACK序号小。state.reord是发生乱序时的最小fack_count,即在“snd_una + fack_count”处发生了乱序。
metric = tp->fackets_out - state.reord,即可能发生乱序的最多报文数。
B. tcp_ack() -> tcp_clean_rtx_queue() -> tcp_update_reordering() 
与A.类似,tcp_clean_rtx_queue()计算rtx queue中被SACK过的数据(非重传)中空洞,reord保存“最小号”空洞的位置(在重传队列中的“座次”)。而prior_fackets - reord即可能发生乱序的TCP segments数量。如果没有SACK,reorder = prior_fackets = 0
metric = prior_fackets - reord

TcpExtTCPFACKReorder与TCPSACKReorder类似,如果同时启用了SACK和FACK,就增加本计数器。
TcpExtTCPTSReordertcp_ack() -> tcp_fastretrans_alert() -> tcp_undo_partial() -> tcp_update_reordering() 

Recovery状态时,接收到到部分确认(snd_una < high_seq)时但已经undo完成(undo_retrans == 0)的次数。 数量上与TCPPartialUndo相等。




TCP Others

类别
名称
描述
TcpExtTCPRenoRecoveryFailtcp_retransmit_timer(): 在Reovery状态下发生RTO,并且没有启用SACK,加1
TcpExtTCPRenoFailurestcp_retransmit_timer(): 在Reorder状态下,或者sacked_out不为0时,发生RTO,并且没有启用SACK,加1
TcpExtTCPRenoRecoverytcp_fastretrans_alert(): 不使用SACK的TCP进入Reovery状态的次数
TcpExtArpFilterarp_rcv() -> NETFILTER(ARP_IN) -> arp_process()

与TCP无关,接收到ARP packet时做一次输出路由查找(sip, tip),如果找到的路由项的device与输入device的不同,计数器加1

TcpExtEmbryonicRststcp_v4_do_rcv() -> tcp_v4_hnd_req() -> tcp_check_req(): 在三手握手时的SYN_RECV状态中接收到RST或者SYN的次数。
TcpExtLockDroppedIcmpstcp_v4_err(): 接收到ICMP错误报文,但tcp socket被user锁住
TcpExOfoPrunedtcp_data_queue() -> tcp_try_rmem_schedule()

慢速路径中,如果不能将数据直接复制到user space,需要加入到sk_receive_queue前,会检查receiver side memory是否允许,如果rcv_buf不足就可能prune ofo queue。此时计数器加1

TcpExtOutOfWindowIcmpstcp_v4_err(): 接收到的ICMP,但ICMP中的TCP头序号不在接收窗口之内的次数,有两个可能情况:(1)LISTEN状态时,序号不等待ISN;(2)其他状态时,序号不在SND_UNA .. SND_NXT之间
TcpExtPAWSActivetcp_rcv_synsent_state_process(): 在发送SYN后,接收到ACK,但PAWS检查失败的次数。
TcpExtPAWSEstabtcp_validate_incoming()

tcp_timewait_state_process()
tcp_check_req()
输入包PAWS失败次数。

TcpExtPAWSPassivetcp_v4_conn_request(): 三路握手最后一个ACK的PAWS检查失败次数。
TcpExtPruneCalledtcp_data_queue() -> tcp_try_rmem_schedule()

慢速路径中,如果不能将数据直接复制到user space,需要加入到sk_receive_queue前,会检查receiver side memory是否允许,如果rcv_buf不足就可能prune ofo queue。此时计数器加1

TcpExtRcvPrunedtcp_data_queue() -> tcp_try_rmem_schedule()

慢速路径中,如果不能将数据直接复制到user space,需要加入到sk_receive_queue前,会检查receiver side memory是否允许,如果rcv_buf不足就可能prune receive queue,如果prune失败了,此计数器加1。

TcpExtSyncookiesFailedcookie_v4_check(): SYN cookie检查失败次数。
TcpExtSyncookiesRecvcookie_v4_check(): 接收SYN cookie次数。
TcpExtSyncookiesSentcookie_v4_init_sequence(): 生成SYN cookie次数。
TcpExtTCPAbortFailedtcp_send_active_reset(): alloc_skb()或者tcp_transmit_skb()失败。
TcpExtTCPAbortOnClosetcp_close(): sk_receive_queue中仍有数据的次数。
TcpExtTCPAbortOnDatatcp_rcv_state_process(): 在FIN_WAIT_1/FIN_WAIT_2状态下接收到后续数据(序号>RCV_NXT);或者,TCP_LINGER2设置值<0,计数器加1

tcp_close(): 没有未读数据,但设置了SO_LINGER并且linger timeout=0, 计数器加1,此时TCP正常断开连接sk_prot->disconnect()。

TcpExtTCPAbortOnLingertcp_close(): 因TCP_LINGER2设置值<0,FIN_WAIT_2立即切换到CLOSE的次数。
TcpExtTCPAbortOnMemory在执行tcp_close()/probe timer/keepalive timer时,orphan sockets数量和tcp_memory_allocated是否超过最大值的次数。
TcpExtTCPAbortOnSyntcp_validate_incoming(): 出现SYN,并且序号大于RCV_NXT的次数。
TcpExtTCPAbortOnTimeoutRTO/probe/keepalive timer到达最大重试次数或者最长重试时间的次数



阅读(8529) | 评论(0) | 转发(2) |
给主人留下些什么吧!~~