JDK-8233296 : MulticastSocket getOption/setOption inverts the value of IP_MULTICAST_LOOP
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.net
  • Affected Version: 9,14
  • Priority: P4
  • Status: Closed
  • Resolution: Fixed
  • Submitted: 2019-10-31
  • Updated: 2020-04-15
  • Resolved: 2019-11-22
The Version table provides details related to the release that this issue/RFE will be addressed.

Unresolved : Release in which this issue/RFE will be addressed.
Resolved: Release in which this issue/RFE has been resolved.
Fixed : Release in which this issue/RFE has been fixed. The release containing this fix may be available for download as an Early Access Release or a General Availability Release.

To download the current JDK release, click here.
JDK 14
14 b25Fixed
Related Reports
Blocks :  
CSR :  
Sub Tasks
JDK-8234643 :  
MulticastSocket has two ways to report whether loopback of multicast datagrams is enabled or disabled:

1. Legacy getLoopbackMode(), should return true when loopback is disabled.

2. getOption(IP_MULTICAST_LOOP), should return true when loopback is enabled. 

We seem to have a bug with #2 in that it returns true when the loopback is disabled. These methods should always return the inverse of one another. 

The setOption/getOption methods are @since 9 so the compatibility impact of fixing this is probably low.
URL: https://hg.openjdk.java.net/jdk/jdk/rev/55fdee124e89 User: dfuchs Date: 2019-11-22 11:54:35 +0000

`DatagramSocketImpl` implements `java.net.SocketOption`, which defines: public void setOption(int optID, Object value) throws SocketException; public Object getOption(int optID) throws SocketException; The long standing behavior in MulticastSocket has been to call `setOption(SocketOptions.IP_MULTICAST_LOOP, true)` to disable looping, and `setOption(SocketOptions.IP_MULTICAST_LOOP, false)` to enable it, in accordance to the parameter passed to MulticastSocket::setLoopback, and returned by MulticastSocket::getLoopback. For backward compatibility, this fix will not change that. However, since Java 9, DatagramSocket defines: public <T> T getOption(SocketOption<T> name) throws IOException; public <T> DatagramSocket setOption(SocketOption<T> name, T value) throws IOException; where StandardSocketOptions.IP_MULTICAST_LOOP is defined to interpret TRUE has enabled and FALSE as disabled. In the *JDK implementation of the AbstractDatagramSocketImpl subclass* of `DatagramSocketImpl` these latter methods are wired to call the legacy setOption/getOption defined by `java.net.SocketOption`. Unfortunately, the wired implementation passes/returns the value associated with `StandardSocketOptions.IP_MULTICAST_LOOP` unchanged, with the effect that the desired logic is actually inverted. In other words, setOption(StandardSocketOptions.IP_MULTICAST_LOOP, true) should have been wired to call setOption(SocketOptions.IP_MULTICAST_LOOP, false) in order to conform to the `StandardSocketOptions.IP_MULTICAST_LOOP` specification. This is this latter wiring that this change is intending to fix, in order to both: - conform to the specification of `StandardSocketOptions.IP_MULTICAST_LOOP`, and - remain backward compatible with pre-existing implementations of `DatagramSocketImpl` which expect `true` to mean 'disabled'.