JDK-8242483 : DatagramPacket::getSocketAddress doesn't specify what happens if address or port are not set
  • Type: CSR
  • Component: core-libs
  • Sub-Component: java.net
  • Priority: P4
  • Status: Closed
  • Resolution: Approved
  • Fix Versions: 15
  • Submitted: 2020-04-10
  • Updated: 2020-04-20
  • Resolved: 2020-04-20
Related Reports
CSR :  
Description
Summary
-------
`DatagramPacket::getSocketAddress` throws `IllegalArgumentException` if invoked on a packet whose _address_ or _port_ are not set, even though `IllegalArgumentException` is not specified. 


Problem
-------

The no-arg method `DatagramPacket.getSocketAddress()` is misleading, because it can throw an `IllegalArgumentException` even though it doesn't take any arguments. This can occur if the _port_ of a `DatagramPacket` is not set before a call to `getSocketAddress()` is made.

Solution
--------

In the recent fix for [JDK-8236940][1], additional checks were added to ensure that a `DatagramPacket` cannot be sent to port `0`. Following on from that fix, this issues changes the default port of a `DatagramPacket` from a value of `-1` to `0`. An `IllegalArgumentException` will therefore no longer be thrown from `getSocketAddress()`, when invoked on a packet that has not had its port explicitly set. Instead, an `InetSocketAddress` representing _any local address_ with a port of `0` is returned.

The default values of the packets _address_ and _port_ are also specified.

Specification
-------------

         /**
          * Returns the IP address of the machine to which this datagram is being
    -     * sent or from which the datagram was received.
    +     * sent or from which the datagram was received, or {@code null} if not
    +     * set.
          *
          * @return  the IP address of the machine to which this datagram is being
          *          sent or from which the datagram was received.
          * @see     java.net.InetAddress
          * @see #setAddress(java.net.InetAddress)
          */
         public synchronized InetAddress getAddress() {


         /**
          * Returns the port number on the remote host to which this datagram is
    -     * being sent or from which the datagram was received.
    +     * being sent or from which the datagram was received, or 0 if not set.
          *
          * @return  the port number on the remote host to which this datagram is
          *          being sent or from which the datagram was received.
          * @see #setPort(int)
          */
         public synchronized int getPort() {


         /**
    -     * Gets the the SocketAddress (usually IP address + port number) of the remote
    -     * host that this packet is being sent to or is coming from.
    +     * Returns the {@link InetSocketAddress#InetSocketAddress(InetAddress, int)
    +     * SocketAddress} (usually {@linkplain #getAddress() IP address} +
    +     * {@linkplain #getPort() port number}) of the remote host that this packet
    +     * is being sent to or is coming from.
          *
          * @return  the {@code SocketAddress}
          *
          * @since   1.4
          */
         public synchronized SocketAddress getSocketAddress() {

  [1]: https://bugs.openjdk.java.net/browse/JDK-8236940,

Comments
Moving to Approved.
20-04-2020

I've updated the compatibility section to more clearly describe the two aspects of the change in this CSR. I agree the compatibility impact is low and we'll document the behavior change in a release note. JEP 373 is expected to proposed for JDK 15 so there will be outreach to encourage developers using the legacy DatagramSocket/DatagramPacket APIs to test with the JDK 15 EA builds and the new implementation. That might help identify any cases where legacy code is depending on the undocumented behavior.
16-04-2020