In short this makes TCP over loopback go wroom wroom.
Delaying ACKs on loopback is the cause that in certain situations no
packets flow until we hit a timeout (around 1 second). This mainly affects
request/respose protocols (like iscsi).
--
:wq Claudio
Index: tcp_input.c
===================================================================
RCS file: /cvs/src/sys/netinet/tcp_input.c,v
retrieving revision 1.235
diff -u -p -r1.235 tcp_input.c
--- tcp_input.c 20 Jul 2010 15:36:03 -0000 1.235
+++ tcp_input.c 23 Sep 2010 14:20:07 -0000
@@ -177,10 +177,12 @@ do { \
* We also ACK immediately if we received a PUSH and the ACK-on-PUSH
* option is enabled.
*/
-#define TCP_SETUP_ACK(tp, tiflags) \
+#define TCP_SETUP_ACK(tp, tiflags, m) \
do { \
if ((tp)->t_flags & TF_DELACK || \
- (tcp_ack_on_push && (tiflags) & TH_PUSH)) \
+ (tcp_ack_on_push && (tiflags) & TH_PUSH) || \
+ (m && (m->m_flags & M_PKTHDR) && m->m_pkthdr.rcvif && \
+ (m->m_pkthdr.rcvif->if_flags & IFF_LOOPBACK))) \
tp->t_flags |= TF_ACKNOW; \
else \
TCP_SET_DELACK(tp); \
@@ -1115,6 +1117,8 @@ after_listen:
tcpstat.tcps_rcvpack++;
tcpstat.tcps_rcvbyte += tlen;
ND6_HINT(tp);
+
+ TCP_SETUP_ACK(tp, tiflags, m);
/*
* Drop TCP, IP headers and TCP options then add data
* to socket buffer.
@@ -1126,7 +1130,6 @@ after_listen:
sbappendstream(&so->so_rcv, m);
}
sorwakeup(so);
- TCP_SETUP_ACK(tp, tiflags);
if (tp->t_flags & TF_ACKNOW)
(void) tcp_output(tp);
return;
@@ -2060,7 +2063,7 @@ dodata: /* XXX */
#endif
if (th->th_seq == tp->rcv_nxt && TAILQ_EMPTY(&tp->t_segq) &&
tp->t_state == TCPS_ESTABLISHED) {
- TCP_SETUP_ACK(tp, tiflags);
+ TCP_SETUP_ACK(tp, tiflags, m);
tp->rcv_nxt += tlen;
tiflags = th->th_flags & TH_FIN;
tcpstat.tcps_rcvpack++;