mirror of
https://github.com/openjdk/jdk.git
synced 2025-09-20 11:04:34 +02:00
8231260: (dc) DatagramChannel::disconnect changes the port of the local address to 0 (lnx)
DatagramChannel::disconnect will attempt to rebind to the original port if the local port switches back to 0 after the association is disolved by the system. Reviewed-by: alanb, chegar, fweimer
This commit is contained in:
parent
fddd963cec
commit
a690af3832
3 changed files with 134 additions and 3 deletions
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2000, 2018, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 2000, 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
|
@ -328,6 +328,10 @@ public abstract class DatagramChannel
|
|||
* <p> If this channel's socket is not connected, or if the channel is
|
||||
* closed, then invoking this method has no effect. </p>
|
||||
*
|
||||
* @apiNote If this method throws an IOException, the channel's socket
|
||||
* may be left in an unspecified state. It is strongly recommended that
|
||||
* the channel be closed when disconnect fails.
|
||||
*
|
||||
* @return This datagram channel
|
||||
*
|
||||
* @throws IOException
|
||||
|
|
|
@ -875,6 +875,11 @@ class DatagramChannelImpl
|
|||
if (state == ST_CONNECTED)
|
||||
throw new AlreadyConnectedException();
|
||||
|
||||
// ensure that the socket is bound
|
||||
if (localAddress == null) {
|
||||
bindInternal(null);
|
||||
}
|
||||
|
||||
int n = Net.connect(family,
|
||||
fd,
|
||||
isa.getAddress(),
|
||||
|
@ -932,8 +937,21 @@ class DatagramChannelImpl
|
|||
remoteAddress = null;
|
||||
state = ST_UNCONNECTED;
|
||||
|
||||
// refresh local address
|
||||
localAddress = Net.localAddress(fd);
|
||||
// check whether rebind is needed
|
||||
InetSocketAddress isa = Net.localAddress(fd);
|
||||
if (isa.getPort() == 0) {
|
||||
// On Linux, if bound to ephemeral port,
|
||||
// disconnect does not preserve that port.
|
||||
// In this case, try to rebind to the previous port.
|
||||
int port = localAddress.getPort();
|
||||
localAddress = isa; // in case Net.bind fails
|
||||
Net.bind(family, fd, isa.getAddress(), port);
|
||||
isa = Net.localAddress(fd); // refresh address
|
||||
assert isa.getPort() == port;
|
||||
}
|
||||
|
||||
// refresh localAddress
|
||||
localAddress = isa;
|
||||
}
|
||||
} finally {
|
||||
writeLock.unlock();
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue