60

似乎至少有 3 种不同的本地/unix 套接字类型 ( AF_UNIX) SOCK_STREAMSOCK_DGRAMSOCK_SEQPACKET.

虽然我知道 aSOCK_STREAM给你一个双向字节流,比如 TCP 或双向管道,而另外两个给你一个 messge/packet API,但 unix 套接字SOCK_DGRAM和有什么区别SOCK_SEQPACKET

由于这些只是本地的,我想不出有人会SOCK_DGRAM以一种可以重新排序数据包的方式实施的充分理由。

此外,是否SOCK_DGRAM/SOCK_SEQPACKET采用流量控制,或者在阅读速度慢的情况下是否可以丢弃消息?

4

5 回答 5

27

这是一篇关于 的预期用例的好文章SOCK_SEQPACKET,事实上它在 IP 协议系列中并不真正可用,以及如何使用现有的 TCP 语义获得相同的东西:

http://urchin.earth.li/~twic/Sequenced_Packets_Over_Ordinary_TCP.html

请注意,SOCK_SEQPACKET它的行为SOCK_STREAM比更接近SOCK_DGRAM

引用参考网站:

SOCK_SEQPACKET 套接字类型类似于 SOCK_STREAM 类型,也是面向连接的。这些类型之间的唯一区别是使用 SOCK_SEQPACKET 类型维护记录边界。可以使用一个或多个输出操作发送记录并使用一个或多个输入操作接收记录,但单个操作永远不会传输多个记录的部分。通过 recvmsg() 函数返回的接收消息标志中的 MSG_EOR 标志,接收方可以看到记录边界。是否规定最大记录大小是特定于协议的。

于 2012-04-11T13:10:18.593 回答
10

SOCK_SEQPACKET 为您提供 SOCK_STREAM 的保证(即,保留顺序、保证交付、无重复),但与 SOCK_DGRAM 一样具有划定的数据包边界。所以,基本上它是两种协议类型的混合。

在 TCP/IP 系列中,SCTP实现了 SOCK_STREAM(类 TCP)和 SOCK_SEQPACKET。不幸的是,它在 Windows 上没有库存。

于 2012-04-11T15:27:41.170 回答
9

我认为这里的主要区别是SOCK_SEQPACKET面向连接,而SOCK_DGRAM不是。

当有多个客户端进程与之通信时,这在连接的服务器端(侦听 UNIX 套接字的进程)上很重要:

使用SOCK_DGRAM,您将直接在侦听套接字上获得交错的客户端数据报。使用SOCK_SEQPACKET,您将使用 为每个客户端生成一个单独的客户端套接字accept,从而分别从每个客户端接收数据报。

报价man 3 accept

accept() 系统调用与基于连接的套接字类型(SOCK_STREAM、SOCK_SEQPACKET)一起使用。

于 2018-09-08T20:19:36.707 回答
6

socket(2) linux-provided manpage: “DGRAM: datagrams (connectionless, unreliable messages), SEQPACKET: sequenced,可靠, [two-way] connection-based data transmission path for datagrams”。显着区别。

unix(7) linux 提供的联机帮助页说:“SOCK_DGRAM,用于保留消息边界的面向数据报的套接字 [但不一定是顺序] [...] SOCK_SEQPACKET,用于保留消息边界并在中传递消息的面向连接的套接字他们被发送的顺序。”</p>

该标准允许您使用 SOCK_DGRAM 获得重新排序的数据包。(换句话说,如果操作系统按顺序将它们交给您,那是特定于实现的功能。或者只是纯粹的计时运气。)

Linux 中的 af_file/af_unix 实现中有流控制,但这根本不需要与标准指定行为相关联。

于 2012-04-11T13:03:25.997 回答
0

与 TCP 和 UDP 套接字一样,有两种形式的 SCTP(流控制传输协议)套接字,端点之间的(一对一)和(一对多)。一对一使用 SOCK_STREAM,一对多使用 SOCK_SEQPACKET

于 2015-05-15T02:02:10.597 回答