【问题标题】:What is the size (network footprint) of a socket connection?套接字连接的大小(网络占用空间)是多少?
【发布时间】:2012-06-05 01:09:13
【问题描述】:

出于好奇,在建立与端口的连接(使用 Java 套接字)时实际发送了多少数据。它是 Socket 对象的大小吗? SocketConnection 对象?

【问题讨论】:

  • 在建立连接时没有发送特定于 Java 的数据,因此这是一个与语言无关的问题。你真正想做什么?
  • 这与 Socket 对象无关,因为它们只是 TCP/IP 协议的实现。您正在寻找的是 TCP/IP 开销。 *.com/q/2193321/84378 也有类似的问题。
  • 我想知道是否有一种方法可以简单地通过切换连接来“脉冲”信息位。我不担心创建连接的开销,我更担心带宽..因为它受到严格限制。所以我正在考虑切换到远程服务器的连接以传输数据位。但我假设会有某种开销,只是想知道它是什么。使用 apache 中的 HTTP 类会容易得多,但我担心带宽占用本身......
  • “切换连接”是什么意思?网络开销如何与带宽无关?
  • @EJP,对不起我之前的帖子。看完下一篇文章,我明白了……

标签: sockets language-agnostic tcp


【解决方案1】:

您对 TCP 网络连接的理解似乎将它们与电路混为一谈。 (可以理解,鉴于您的background。)

从物理的角度来看,没有连接这样的东西,只有数据包。通过TCP协议,两台设备同意建立逻辑(即软件)连接。客户端首先向远程主机发送数据(SYN),服务器将数据返回给客户端(SYN-ACK),客户端发送最终确认(ACK)来建立连接。 所有这些协商必然会消耗带宽,当您终止连接时,您必须协商一个全新的连接才能再次开始发送数据。

例如,我将从我的机器连接到本地 Web 服务器 192.168.1.2:80。

首先,我的机器发送一个 TCP SYN。这会通过线路发送 66 个字节:(标头以 | 分隔)

0000  00 24 8c a9 4c b4 00 1e  68 66 20 79 08 00|45 00   .$..L... hf y..E.
0010  00 34 53 98 40 00 80 06  00 00 c0 a8 01 0b c0 a8   .4S.@... ........
0020  01 02|36 0a 00 50 09 ef  3a a7 00 00 00 00 80 02   ..6..P.. :.......
0030  20 00 50 c8 00 00 02 04  05 b4 01 03 03 02 01 01    .P..... ........
0040  04 02                                              ..               

前 14 个字节是 Ethernet frame,指定此数据包的目标 MAC 地址。这通常是上游路由器,但在这种情况下,服务器恰好在同一个交换机上,所以它是机器的MAC 地址,00:24:8c:a9:4c:b4。接下来是源(我的)MAC,以及有效负载类型(IP,0x0800)。接下来的 20 个字节是 IPv4 标头,然后是 32 个字节的 TCP 标头。

服务器以 62 字节的 SYN-ACK 响应:

0000  00 1e 68 66 20 79 00 24  8c a9 4c b4 08 00|45 00   ..hf y.$ ..L...E.
0010  00 30 69 b9 40 00 80 06  0d b1 c0 a8 01 02 c0 a8   .0i.@... ........
0020  01 0b|00 50 36 0a d3 ae  9a 73 09 ef 3a a8 70 12   ...P6... .s..:.p.
0030  20 00 f6 9d 00 00 02 04  05 b4 01 01 04 02          ....... ......  

同样,14 字节的以太网报头、20 字节的 IP 报头和 28 字节的 TCP 报头。我发送一个 ACK​​:

0000  00 24 8c a9 4c b4 00 1e  68 66 20 79 08 00|45 00   .$..L... hf y..E.
0010  00 28 53 9a 40 00 80 06  00 00 c0 a8 01 0b c0 a8   .(S.@... ........
0020  01 02|36 0a 00 50 09 ef  3a a8 d3 ae 9a 74 50 10   ..6..P.. :....tP.
0030  fa f0 83 78 00 00                                  ...x..           

14 + 20 + 20 = 54 字节通过线路(顺便说一句,这是 TCP 数据包可能的最小大小 - SYN 和 SYN-ACK 数据包更大,因为它们包含选项)。

这在线路上增加了 182 个字节来建立连接;现在我可以开始向服务器发送实际数据了:

0000  00 24 8c a9 4c b4 00 1e  68 66 20 79 08 00 45|00   .$..L... hf y..E.
0010  01 9d 53 9d 40 00 80 06  00 00 c0 a8 01 0b c0 a8   ..S.@... ........
0020  01 02|36 0a 00 50 09 ef  3a a8 d3 ae 9a 74 50 18   ..6..P.. :....tP.
0030  fa f0 84 ed 00 00|47 45  54 20 2f 20 48 54 54 50   ......GE T / HTTP
0040  2f 31 2e 31 0d 0a 48 6f  73 74 3a 20 66 73 0d 0a   /1.1..Ho st: fs..
...

14 个以太网 + 20 个 IP + 20 个 TCP + 数据,在本例中为 HTTP。


所以我们可以看到,建立一个 TCP 连接需要大约 182 个字节,而终止一个 TCP 连接需要额外的 162-216 个字节(取决于 4-way FIN ACK FIN ACK或更常见的 3 路 FIN FIN-ACK ACK 终止握手),增加近 400 个字节以通过断开和重新连接来“脉冲”连接。

与通过已建立的连接发送一个字节数据的 55 个字节相比,这显然是浪费。

您要做的是建立一个连接,然后根据需要发送数据。如果您真的带宽受限,您可以使用 UDP(它根本不需要握手,并且每个数据包的开销仅为 14 个以太网 + 20 个 IP + 8 个 UDP 字节),但随后您将面临使用不可靠传输的问题,并且必须自己处理丢失的数据包。

【讨论】:

  • 同意。他似乎正在对不存在的拨号音进行某种调制。
  • 非常感谢!!我很困惑,但你的回答真的让我明白了。 @EJP,是的......我正在考虑某种调制。我的动机是尝试发送数据而实际上不必包含任何数据...我想到的类比是无线电,您可以在其中调制幅度或频率...
【解决方案2】:

TCP 数据包的最小大小为 40 字节。创建一个连接需要三个交换的数据包,两个来自客户端,一个来自服务器,另外四个来关闭它,每个方向两个。连接交换中的最后一个数据包也可以包含数据,每个方向的关闭交换中的第一个数据包也可以包含数据,这可以稍微摊销它,就像下面@josh3736 的评论结合传出的 FIN 和 ACK 一样。

【讨论】:

  • 如果我们谈论的是无线字节,您还需要考虑以太网帧开销,这会为每个数据包增加 14 个字节。此外,您可以通过 3 次 FIN FIN-ACK ACK 握手关闭 TCP 连接。
  • @josh3736 是的,谢谢,已编辑。但是,不确定这种情况到底有多“普遍”。我猜对传出的 ACK 进行 Nagling 会有所帮助。应用程序必须在 Nagle 间隔内获取 EOS 并关闭套接字作为响应,才能搭载它。
最近更新 更多