【问题标题】:MulticastSocket join/leave group, send, receive thread-safetyMulticastSocket 加入/离开组,发送,接收线程安全
【发布时间】:2018-01-16 09:31:14
【问题描述】:

我正在推理我的应用程序中的多播套接字线程安全。首先,我有多个线程共享同一个多播套接字实例,这个多播套接字用于加入同一端口上的不同组。以下是我的问题:

  1. 我是否必须同步对 joinGroup()leaveGroup() 方法的调用?
  2. 我是否必须同步调用send()receive() 方法,这些方法总是使用新的数据报包作为参数?

这是第二个问题的代码示例:

/* SEND METHOD EXAMPLE. */
    DatagramPacket sndPckt = new DatagramPacket(buf, buf.length, groupAddr,port);
    try{
        multicastSocket.send(sndPckt);
    } catch (IOException e) {
        /* Error handling. */
    }
/* RECEIVE METHOD EXAMPLE. */
    DatagramPacket recv = new DatagramPacket(buf, buf.length);
        try{
            multicastSocket.receive(recv);
        } catch (IOException e) {
            /* Error handling. */
        }

我找到了this answer,但它谈到使用相同的Datagram Packet。 我还测试了我的应用程序,但没有发现任何竞争条件或不一致,但我不能 100% 确定使用是线程安全的。

【问题讨论】:

  • 文档对这些方法的线程安全有什么看法?
  • @Kayaman 什么都没有?
  • 你说得对,小蚱蜢。
  • 有时文档说明了很多,但它什么也没说。其他时候则相反。
  • 当 EJP 和 Stephen C 都参与其中时,您会得到一些 A 级答案。更不用说他们同意了!

标签: java multithreading thread-safety multicast


【解决方案1】:

javadocs 没有说明MulticastSocket 是否是线程安全的,但阅读源代码表明它是。

  1. joinGroup()leaveGroup() 方法是 native 调用的包装器,它们(反过来)是系统调用的包装器。所有系统调用都是线程安全的,至少就内核空间中保存的数据而言。 (如果不是,那将是一个潜在的安全漏洞。)我对代码的解读是 joinGroup()leaveGroup() 不会更新任何用户空间数据。

  2. send()receive() 方法在它们的DataPacket 参数上同步,以确保使用相同DataPacket 的两个线程可以安全地这样做。除了数据包对象之外,这些方法不会更新用户空间中的任何共享套接字状态,并且(如上所述)我们可以假设内核空间数据是线程安全的。

EJP 理由是这些系统调用是原子的(按设计),因此是线程安全的。这是正确的1。但是,还需要考虑用户空间中的线程安全(即系统调用之前和之后,或者当两个系统调用共享用户空间缓冲区时)。


1 - 至少在我看来。我找不到明确的来源来说明哪些系统调用是原子设计的。

【讨论】:

  • 同意。我更关心的是把我古老的太阳帖子读到这里的记录中。
【解决方案2】:

我是否必须同步对 joinGroup() 和 leaveGroup() 方法的调用?

没有。

我是否必须同步调用 send() 和 receive() 方法,这些方法总是使用新的数据报包作为参数?

没有。

  • DatagramSocket 读写相互独立。
  • DatagramSocket 写入在操作系统级别是原子的,因此它们是线程安全的。
  • DatagramSocket 读取是由 Java 同步的,它们也是 在操作系统级别是原子的,因此它们也是线程安全的。
  • MulticastSocketDatagramSocket 继承其 I/O 方法。
  • joinGroup()/leaveGroup() 在操作系统级别也是原子的。

为了避免我被指控plagiarism,我会声明该链接本身就是我几十年前在 Sun Java 论坛上最初写的材料的未经授权的副本。

【讨论】:

  • 我建议您在发布指向您的内容的链接之前先获得自己的授权。
猜你喜欢
  • 1970-01-01
  • 2011-03-07
  • 2014-04-27
  • 1970-01-01
  • 2015-06-30
  • 2021-06-20
  • 2016-02-22
  • 1970-01-01
  • 2016-01-28
相关资源
最近更新 更多