From 9eb4f0ee85685afc86f416a7e94b1ff39b05d0a2 Mon Sep 17 00:00:00 2001 From: Chris Vest Date: Wed, 18 Aug 2021 20:43:01 +0200 Subject: [PATCH] Fix a problem with IP protocol version confusion on MacOS when TCP FastOpen is enabled (#11588) Motivation: This fixes a bug that would result in an `io.netty.channel.unix.Errors$NativeIoException: connectx(..) failed: Address family not supported by protocol family` error. This happens when the connecting socket is configured to use IPv6 but the address being connected to is IPv4. This can occur because, for instance, Netty and `InetAddress.getLoopbackAddress()` have different preferences for IPv6 vs. IPv4. Modification: Pass the correct ipv6 or ipv4 flags to connectx, depending on whether the socket was created for AF_INET or AF_INET6, rather than relying on the IP version of the destination address. Result: No more issue with TCP FastOpen on MacOS when using addresses of the "wrong" IP version. --- .../transport/socket/AbstractSocketTest.java | 10 ++--- .../epoll/EpollDomainDatagramPathTest.java | 6 +-- .../epoll/EpollDomainDatagramUnicastTest.java | 2 +- ...lDomainSocketDataReadInitialStateTest.java | 2 +- .../epoll/EpollDomainSocketEchoTest.java | 2 +- .../epoll/EpollDomainSocketFdTest.java | 2 +- .../EpollDomainSocketFileRegionTest.java | 2 +- .../EpollDomainSocketFixedLengthEchoTest.java | 2 +- .../EpollDomainSocketGatheringWriteTest.java | 2 +- .../EpollDomainSocketObjectEchoTest.java | 2 +- .../epoll/EpollDomainSocketReuseFdTest.java | 2 +- ...lDomainSocketShutdownOutputByPeerTest.java | 2 +- ...lDomainSocketSslClientRenegotiateTest.java | 2 +- .../epoll/EpollDomainSocketSslEchoTest.java | 2 +- .../EpollDomainSocketSslGreetingTest.java | 2 +- .../epoll/EpollDomainSocketStartTlsTest.java | 2 +- .../EpollDomainSocketStringEchoTest.java | 2 +- .../EpollJdkLoopbackSocketSslEchoTest.java | 27 ++++++++++++ .../netty/channel/epoll/EpollSocketTest.java | 2 +- .../epoll/EpollSocketTestPermutation.java | 4 +- .../io/netty/channel/kqueue/BsdSocket.java | 8 ++-- .../KQueueJdkLoopbackSocketSslEchoTest.java | 27 ++++++++++++ .../channel/kqueue/KQueueSocketTest.java | 4 +- .../kqueue/KQueueSocketTestPermutation.java | 5 ++- .../channel/unix/tests/UnixTestUtils.java | 42 +++++++++++++++++++ .../java/io/netty/channel/unix/Socket.java | 10 ++++- 26 files changed, 140 insertions(+), 35 deletions(-) create mode 100644 transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollJdkLoopbackSocketSslEchoTest.java create mode 100644 transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueJdkLoopbackSocketSslEchoTest.java diff --git a/testsuite/src/main/java/io/netty/testsuite/transport/socket/AbstractSocketTest.java b/testsuite/src/main/java/io/netty/testsuite/transport/socket/AbstractSocketTest.java index 5c2f41acab..2f32444a8c 100644 --- a/testsuite/src/main/java/io/netty/testsuite/transport/socket/AbstractSocketTest.java +++ b/testsuite/src/main/java/io/netty/testsuite/transport/socket/AbstractSocketTest.java @@ -34,11 +34,11 @@ public abstract class AbstractSocketTest extends AbstractComboTestsuiteTest { try { bootstrap.handler(new ChannelHandlerAdapter() { }) - .connect(EpollSocketTestPermutation.newSocketAddress()).get(); + .connect(EpollSocketTestPermutation.newDomainSocketAddress()).get(); fail("Expected FileNotFoundException"); } catch (Exception e) { assertTrue(e.getCause() instanceof FileNotFoundException); @@ -52,10 +52,10 @@ class EpollDomainDatagramPathTest extends AbstractClientSocketTest { run(testInfo, bootstrap -> { try { Channel ch = bootstrap.handler(new ChannelHandlerAdapter() { }) - .bind(EpollSocketTestPermutation.newSocketAddress()).get(); + .bind(EpollSocketTestPermutation.newDomainSocketAddress()).get(); ch.writeAndFlush(new DomainDatagramPacket( Unpooled.copiedBuffer("test", CharsetUtil.US_ASCII), - EpollSocketTestPermutation.newSocketAddress())).sync(); + EpollSocketTestPermutation.newDomainSocketAddress())).sync(); fail("Expected FileNotFoundException"); } catch (Exception e) { assertTrue(e.getCause() instanceof FileNotFoundException); diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainDatagramUnicastTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainDatagramUnicastTest.java index 95fdd3a4b6..41db896b8e 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainDatagramUnicastTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainDatagramUnicastTest.java @@ -76,7 +76,7 @@ class EpollDomainDatagramUnicastTest extends DatagramUnicastTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketDataReadInitialStateTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketDataReadInitialStateTest.java index edbf17d87d..49b90e4447 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketDataReadInitialStateTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketDataReadInitialStateTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketDataReadInitialStateTest extends SocketDataReadInitialStateTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketEchoTest.java index d8267b5d25..3e8c64233d 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketEchoTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketEchoTest.java @@ -25,7 +25,7 @@ import java.util.List; public class EpollDomainSocketEchoTest extends EpollSocketEchoTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFdTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFdTest.java index 27058f69c4..3b12117bb6 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFdTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFdTest.java @@ -43,7 +43,7 @@ import static org.junit.jupiter.api.Assertions.assertTrue; public class EpollDomainSocketFdTest extends AbstractSocketTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFileRegionTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFileRegionTest.java index fe2b1cc45d..b77f50c6ca 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFileRegionTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFileRegionTest.java @@ -25,7 +25,7 @@ import java.util.List; public class EpollDomainSocketFileRegionTest extends EpollSocketFileRegionTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFixedLengthEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFixedLengthEchoTest.java index 194a45177f..1c343289c7 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFixedLengthEchoTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketFixedLengthEchoTest.java @@ -27,7 +27,7 @@ public class EpollDomainSocketFixedLengthEchoTest extends SocketFixedLengthEchoT @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketGatheringWriteTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketGatheringWriteTest.java index ba0c2cce7c..5e25a9369c 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketGatheringWriteTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketGatheringWriteTest.java @@ -27,7 +27,7 @@ public class EpollDomainSocketGatheringWriteTest extends SocketGatheringWriteTes @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketObjectEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketObjectEchoTest.java index b67b9b91c3..fc7d7ce864 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketObjectEchoTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketObjectEchoTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketObjectEchoTest extends SocketObjectEchoTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketReuseFdTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketReuseFdTest.java index 8360475c55..8a18feb5c5 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketReuseFdTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketReuseFdTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketReuseFdTest extends AbstractSocketReuseFdTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketShutdownOutputByPeerTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketShutdownOutputByPeerTest.java index 9b555cd4d8..8b0077c8c6 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketShutdownOutputByPeerTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketShutdownOutputByPeerTest.java @@ -35,7 +35,7 @@ public class EpollDomainSocketShutdownOutputByPeerTest extends AbstractSocketShu @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslClientRenegotiateTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslClientRenegotiateTest.java index 1d0a6005e6..64858ce921 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslClientRenegotiateTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslClientRenegotiateTest.java @@ -31,6 +31,6 @@ public class EpollDomainSocketSslClientRenegotiateTest extends SocketSslClientRe @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } } diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslEchoTest.java index 69f44138b7..87755ab555 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslEchoTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslEchoTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketSslEchoTest extends SocketSslEchoTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslGreetingTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslGreetingTest.java index 9718c27ab3..9ff9f1591a 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslGreetingTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketSslGreetingTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketSslGreetingTest extends SocketSslGreetingTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStartTlsTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStartTlsTest.java index 88b1285342..dfdf6eded0 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStartTlsTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStartTlsTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketStartTlsTest extends SocketStartTlsTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStringEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStringEchoTest.java index d0c94e21bb..29945edead 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStringEchoTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollDomainSocketStringEchoTest.java @@ -26,7 +26,7 @@ import java.util.List; public class EpollDomainSocketStringEchoTest extends SocketStringEchoTest { @Override protected SocketAddress newSocketAddress() { - return EpollSocketTestPermutation.newSocketAddress(); + return EpollSocketTestPermutation.newDomainSocketAddress(); } @Override diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollJdkLoopbackSocketSslEchoTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollJdkLoopbackSocketSslEchoTest.java new file mode 100644 index 0000000000..3a1c246128 --- /dev/null +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollJdkLoopbackSocketSslEchoTest.java @@ -0,0 +1,27 @@ +/* + * Copyright 2021 The Netty Project + * + * The Netty Project licenses this file to you under the Apache License, + * version 2.0 (the "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at: + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + */ +package io.netty.channel.epoll; + +import io.netty.channel.unix.tests.UnixTestUtils; + +import java.net.SocketAddress; + +public class EpollJdkLoopbackSocketSslEchoTest extends EpollSocketSslEchoTest { + @Override + protected SocketAddress newSocketAddress() { + return UnixTestUtils.newInetLoopbackSocketAddress(); + } +} diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTest.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTest.java index 472f907ff1..6266789457 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTest.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTest.java @@ -47,7 +47,7 @@ public class EpollSocketTest extends SocketTest { LinuxSocket s2 = LinuxSocket.newSocketDomain(); try { - DomainSocketAddress dsa = UnixTestUtils.newSocketAddress(); + DomainSocketAddress dsa = UnixTestUtils.newDomainSocketAddress(); s1.bind(dsa); s1.listen(1); diff --git a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTestPermutation.java b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTestPermutation.java index f54934eb20..1759261f38 100644 --- a/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTestPermutation.java +++ b/transport-native-epoll/src/test/java/io/netty/channel/epoll/EpollSocketTestPermutation.java @@ -184,8 +184,8 @@ class EpollSocketTestPermutation extends SocketTestPermutation { ); } - public static DomainSocketAddress newSocketAddress() { - return UnixTestUtils.newSocketAddress(); + public static DomainSocketAddress newDomainSocketAddress() { + return UnixTestUtils.newDomainSocketAddress(); } public List> domainDatagram() { diff --git a/transport-native-kqueue/src/main/java/io/netty/channel/kqueue/BsdSocket.java b/transport-native-kqueue/src/main/java/io/netty/channel/kqueue/BsdSocket.java index 75a2e92ea1..ab717aeef7 100644 --- a/transport-native-kqueue/src/main/java/io/netty/channel/kqueue/BsdSocket.java +++ b/transport-native-kqueue/src/main/java/io/netty/channel/kqueue/BsdSocket.java @@ -125,8 +125,8 @@ final class BsdSocket extends Socket { sourcePort = 0; } else { InetAddress sourceInetAddress = source.getAddress(); - sourceIPv6 = sourceInetAddress instanceof Inet6Address; - if (sourceIPv6) { + sourceIPv6 = useIpv6(this, sourceInetAddress); + if (sourceInetAddress instanceof Inet6Address) { sourceAddress = sourceInetAddress.getAddress(); sourceScopeId = ((Inet6Address) sourceInetAddress).getScopeId(); } else { @@ -138,10 +138,10 @@ final class BsdSocket extends Socket { } InetAddress destinationInetAddress = destination.getAddress(); - boolean destinationIPv6 = destinationInetAddress instanceof Inet6Address; + boolean destinationIPv6 = useIpv6(this, destinationInetAddress); byte[] destinationAddress; int destinationScopeId; - if (destinationIPv6) { + if (destinationInetAddress instanceof Inet6Address) { destinationAddress = destinationInetAddress.getAddress(); destinationScopeId = ((Inet6Address) destinationInetAddress).getScopeId(); } else { diff --git a/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueJdkLoopbackSocketSslEchoTest.java b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueJdkLoopbackSocketSslEchoTest.java new file mode 100644 index 0000000000..2f966a9f5b --- /dev/null +++ b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueJdkLoopbackSocketSslEchoTest.java @@ -0,0 +1,27 @@ +/* + * Copyright 2021 The Netty Project + * + * The Netty Project licenses this file to you under the Apache License, + * version 2.0 (the "License"); you may not use this file except in compliance + * with the License. You may obtain a copy of the License at: + * + * https://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT + * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the + * License for the specific language governing permissions and limitations + * under the License. + */ +package io.netty.channel.kqueue; + +import io.netty.channel.unix.tests.UnixTestUtils; + +import java.net.SocketAddress; + +public class KQueueJdkLoopbackSocketSslEchoTest extends KQueueSocketSslEchoTest { + @Override + protected SocketAddress newSocketAddress() { + return UnixTestUtils.newInetLoopbackSocketAddress(); + } +} diff --git a/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTest.java b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTest.java index 7cac7ed532..3f44e9f5cb 100644 --- a/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTest.java +++ b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTest.java @@ -40,7 +40,7 @@ public class KQueueSocketTest extends SocketTest { BsdSocket s2 = BsdSocket.newSocketDomain(); try { - DomainSocketAddress dsa = UnixTestUtils.newSocketAddress(); + DomainSocketAddress dsa = UnixTestUtils.newDomainSocketAddress(); s1.bind(dsa); s1.listen(1); @@ -61,7 +61,7 @@ public class KQueueSocketTest extends SocketTest { BsdSocket s2 = BsdSocket.newSocketDomain(); try { - DomainSocketAddress dsa = UnixTestUtils.newSocketAddress(); + DomainSocketAddress dsa = UnixTestUtils.newDomainSocketAddress(); s1.bind(dsa); s1.listen(1); diff --git a/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTestPermutation.java b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTestPermutation.java index 98d13d251f..f70bd88380 100644 --- a/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTestPermutation.java +++ b/transport-native-kqueue/src/test/java/io/netty/channel/kqueue/KQueueSocketTestPermutation.java @@ -54,7 +54,7 @@ class KQueueSocketTestPermutation extends SocketTestPermutation { public List> socket() { List> list = - combo(serverSocket(), clientSocket()); + combo(serverSocket(), clientSocketWithFastOpen()); list.remove(list.size() - 1); // Exclude NIO x NIO test @@ -139,8 +139,9 @@ class KQueueSocketTestPermutation extends SocketTestPermutation { () -> new Bootstrap().group(KQUEUE_WORKER_GROUP).channel(KQueueDatagramChannel.class) ); } + public static DomainSocketAddress newSocketAddress() { - return UnixTestUtils.newSocketAddress(); + return UnixTestUtils.newDomainSocketAddress(); } public List> domainDatagram() { diff --git a/transport-native-unix-common-tests/src/main/java/io/netty/channel/unix/tests/UnixTestUtils.java b/transport-native-unix-common-tests/src/main/java/io/netty/channel/unix/tests/UnixTestUtils.java index 2108dfcc92..3453c236bc 100644 --- a/transport-native-unix-common-tests/src/main/java/io/netty/channel/unix/tests/UnixTestUtils.java +++ b/transport-native-unix-common-tests/src/main/java/io/netty/channel/unix/tests/UnixTestUtils.java @@ -20,9 +20,26 @@ import io.netty.util.internal.PlatformDependent; import java.io.File; import java.io.IOException; +import java.lang.reflect.Method; +import java.net.InetAddress; +import java.net.InetSocketAddress; +import java.net.SocketAddress; + +import static org.junit.jupiter.api.Assumptions.assumeTrue; public final class UnixTestUtils { + private static final Object INET_LOOPBACK_UNAVAILABLE = new Object(); + private static volatile Object inetLoopbackCache; + + /** + * @deprecated Use {@link #newDomainSocketAddress()} instead. + */ + @Deprecated public static DomainSocketAddress newSocketAddress() { + return newDomainSocketAddress(); + } + + public static DomainSocketAddress newDomainSocketAddress() { try { File file; do { @@ -37,5 +54,30 @@ public final class UnixTestUtils { } } + /** + * The JDK method may produce IPv4 loopback addresses where {@link io.netty.util.NetUtil#LOCALHOST} might be an + * IPv6 addresses. + * This difference can stress the system in different ways that are important to test. + */ + public static SocketAddress newInetLoopbackSocketAddress() { + Object loopback = inetLoopbackCache; + + if (loopback == null) { + inetLoopbackCache = loopback = getLoopbackAddress(); + } + + assumeTrue(loopback != INET_LOOPBACK_UNAVAILABLE, "InetAddress.getLoopbackAddress() is not available"); + return new InetSocketAddress((InetAddress) loopback, 0); + } + + private static Object getLoopbackAddress() { + try { + Method method = InetAddress.class.getMethod("getLoopbackAddress"); + return method.invoke(null); + } catch (Exception ignore) { + return INET_LOOPBACK_UNAVAILABLE; + } + } + private UnixTestUtils() { } } diff --git a/transport-native-unix-common/src/main/java/io/netty/channel/unix/Socket.java b/transport-native-unix-common/src/main/java/io/netty/channel/unix/Socket.java index a2cf22e163..ecb3075abb 100644 --- a/transport-native-unix-common/src/main/java/io/netty/channel/unix/Socket.java +++ b/transport-native-unix-common/src/main/java/io/netty/channel/unix/Socket.java @@ -59,7 +59,15 @@ public class Socket extends FileDescriptor { * Returns {@code true} if we should use IPv6 internally, {@code false} otherwise. */ private boolean useIpv6(InetAddress address) { - return ipv6 || address instanceof Inet6Address; + return useIpv6(this, address); + } + + /** + * Returns {@code true} if the given socket and address combination should use IPv6 internally, + * {@code false} otherwise. + */ + protected static boolean useIpv6(Socket socket, InetAddress address) { + return socket.ipv6 || address instanceof Inet6Address; } public final void shutdown() throws IOException {