(1) application-limited ：when the sender sends less than is allowed by the congestion or receiver window.
(2) network-limited：when the sender is limited by the TCP window. More precisely, we define a network-limited period as any period when the sender is sending a full window of data.
TCP’s congestion window controls the number of packets a TCP flow may have in the
network at any time. However, long periods when the sender is idle or application-limited
can lead to the invalidation of the congestion window, in that the congestion window no longer
reflects current information about the state of the network.
The congestion window is set using an Additive-Increase, Multiplicative-Decrease(AIMD) mechanism
that probes for available bandwidth, dynamically adapting to changing network conditions. This AIMD
works well when the sender continually has data to send, as is typically the case for TCP used for
bulk-data transfer. In contrast, for TCP used with telnet applications, the data sender often has little
or no data to send, and the sending rate is often determined by the rate at which data is generated
by the user.
An invalid congestion window also results when the congestion window is increased (i.e.,
in TCP’s slow-start or congestion avoidance phases) during application-limited periods, when the
previous value of the congestion window might never have been fully utilized. As far as we know, all
current TCP implementations increase the congestion window when an acknowledgement arrives,
if allowed by the receiver’s advertised window and the slow-start or congestion avoidance window
increase algorithm, without checking to see if the previous value of the congestion window has in
fact been used.
This document proposes that the window increase algorithm not be invoked during application-
limited periods. This restriction prevents the congestion window from growing arbitrarily large,
in the absence of evidence that the congestion window can be supported by the network.
/* Congestion state accounting after a packet has been sent. */
static void tcp_event_data_sent (struct tcp_sock *tp, struct sock *sk)
struct inet_connection_sock *icsk = inet_csk(sk);
const u32 now = tcp_time_stamp;
if (sysctl_tcp_slow_start_after_idle &&
(!tp->packets_out && (s32) (now - tp->lsndtime) > icsk->icsk_rto))
tcp_cwnd_restart(sk, __sk_dst_get(sk)); /* 重置cnwd */
tp->lsndtime = now; /* 更新最近发包的时间*/
/* If it is a reply for ato after last received packets,
* enter pingpong mode. */
if ((u32)(now - icsk->icsk_ack.lrcvtime) < icsk.icsk_ack.ato)
icsk->icsk_ack.pingpong = 1;
一个进程去打开文件，输入一个整数，然后上一把写锁（LOCK＿EX），再输入一个整数将解锁（LOCK＿UN），另一个进程打开同样一个文件，直接向文件中写数据，发现锁不起作用，能正常写入（我此时用的是超级用户）。google了一大圈发现flock不提供锁检查，也就是说在用flock之前需要用户自己去检查一下是否已经上了锁，说明白点就是读写文件之前用一下flock检查一下文件有没有上锁，如果上锁了flock将会阻塞在那里(An attempt to lock the file using one of these file descriptors may be denied by a lock that the calling process has already placed via another descriptor )，除非用了LOCK_NB。一个完整的用于测试的事例代码如下所示：