为什么TCP套接字编程需要两个套接字(一个欢迎套接字和一个连接套接字)但UDP只需要一个?

这是因为TCP连接是一个持久连接,所以服务器需要同时处理多个请求,因此需要不同的连接套接字?

但是如果UDP传输完成,下一个连接将启动到同一个服务器套接字,因此UDP只需要一个套接字.

这些是我的推测.
它是否正确?

最佳答案
原因是TCP有两种不同的状态要控制,而UDP只有一种.

在端口上侦听TCP连接时,网络堆栈需要跟踪您使用该套接字监听的端口号和接口,以及该套接字的传入TCP连接请求的积压列表,以及它将该状态保存在与传递给listen()/ bind()/ accept()的套接字关联的内部数据结构中.只要套接字存在,该数据结构将被更新,并且当您关闭()该套接字时将被丢弃.

一旦接受了TCP连接,另一方面,accept()返回的新TCP套接字具有自己的连接特定状态,需要单独跟踪 – 该状态包括客户端的IP地址和源端口,TCP数据包ID序列,TCP窗口大小和发送速率,已为该TCP连接接收的传入数据,已为该TCP连接发送的传出数据(如果数据包被丢弃,可能需要稍后重新发送),等等.所有这些都存储在一个单独的内部数据结构中,该数据结构与新的套接字相关联,该套接字将被更新,直到新的套接字关闭()为止,此时它将被丢弃.

请注意,这两种类型的状态的生命周期非常相互独立 – 例如,您可能决定不再接受任何传入的TCP连接,因此您希望关闭第一个(连接接受) )套接字,同时继续使用第二个(特定于TCP连接)套接字与已连接的客户端进行通信.或者你可能会反过来,并决定你不想继续与该特定客户端的对话,所以你关闭第二个套接字,但你确实想继续接受更多的TCP连接,所以你打开第一个套接字.如果只有一个插槽可以处理所有内容,那么只关闭一个上下文或另一个上下文是不可能的;你唯一的选择就是close()单个套接字,并且它会失去所有状态,甚至是你想要保留的部分.这充其量只是尴尬.

另一方面,UDP没有“接受连接”的概念,因此只有一种状态,即缓冲的发送和/或接收数据包的集合(无论其源和/或目的地如何).因此,通常不需要具有多个UDP套接字.

转载注明原文:为什么TCP套接字编程需要两个套接字(一个欢迎套接字和一个连接套接字)但UDP只需要一个? - 代码日志