TCP确认中的数据有效负载

TCP确认中的数据有效负载,tcp,Tcp,我在筛选一些网络跟踪,发现在我自己的机器上,当我通过HTTP连接时,数据包看起来像: client --> server: GET server --> client: tcp ack server --> client: HTTP response client --> server: tcp ack 但是,我查看了几年前保存的一些CIFS(SMB)跟踪。我看到的是: client --> server: Create Request server -->

我在筛选一些网络跟踪,发现在我自己的机器上,当我通过HTTP连接时,数据包看起来像:

client --> server: GET
server --> client: tcp ack
server --> client: HTTP response
client --> server: tcp ack
但是,我查看了几年前保存的一些CIFS(SMB)跟踪。我看到的是:

client --> server: Create Request 
server --> client: Create response (This packet also acks the request)

在高层次上,我想知道为什么会有这种差异——是什么导致了不同的行为?是什么控制应用程序响应是放在请求ack上还是放在另一个数据包上:应用程序还是操作系统

此行为取决于操作系统和应用程序。在linux中,内核不直接发送ACK,而是等待固定的毫秒数(大约200毫秒),希望is有一些数据要发送回来,并且可以让ACK携带数据

如果计时器熄灭,则立即发送ACK

例1

Client sends the GET request.

Server tries to create a http response, but before it does that 200ms are gone
and it must send the ACK before the http response.
例2

Client sends the GET request.

Server creates a http response within the timer limit, and the ACK can piggyback
the data.

这意味着,如果您的应用程序在生成响应时变慢,那么将发送ACK,而不需要对数据进行搭载。此外,根据操作系统的不同,延迟计时器可以更高/更低,并再次改变ACK的发送方式。

您可以在任何TCP初始化设置中指定延迟计时器吗?您可以使用IPPROTO_TCP(非便携式btw)下的TCP_QUICKACK选项和setsockopt将其关闭。但是改变这个值可能是不可能的,因为我相信它是硬编码的,除非它有一个新添加的sysctl(或类似的东西)。在我设置TCP套接字选项以禁用TCP快速确认后,我仍然没有得到组合数据包的回复:opt=0;setsockopt(sockfd,IPPROTO_TCP,TCP_QUICKACK,(char*)和opt,sizeof(opt));你也可以通过ip路由来实现