summaryrefslogtreecommitdiffhomepage
path: root/test/syscalls/linux
diff options
context:
space:
mode:
authorAndrei Vagin <avagin@google.com>2020-10-31 01:17:29 -0700
committergVisor bot <gvisor-bot@google.com>2020-10-31 01:19:40 -0700
commitdf88f223bb5474a462da65ede6f266eb52f1b2ef (patch)
treee01ce7b4c4a27ff498f8b5ce96bf30d0ee2b3bee /test/syscalls/linux
parent4eb1c87e8033520981cce19dea7cde5f85f07737 (diff)
net/tcpip: connect to unset loopback address has to return EADDRNOTAVAIL
In the docker container, the ipv6 loopback address is not set, and connect("::1") has to return ENEADDRNOTAVAIL in this case. Without this fix, it returns EHOSTUNREACH. PiperOrigin-RevId: 340002915
Diffstat (limited to 'test/syscalls/linux')
-rw-r--r--test/syscalls/linux/BUILD18
-rw-r--r--test/syscalls/linux/socket_ip_unbound.cc18
-rw-r--r--test/syscalls/linux/socket_ip_unbound_netlink.cc104
3 files changed, 127 insertions, 13 deletions
diff --git a/test/syscalls/linux/BUILD b/test/syscalls/linux/BUILD
index 88899589d..99f286bfc 100644
--- a/test/syscalls/linux/BUILD
+++ b/test/syscalls/linux/BUILD
@@ -2884,6 +2884,24 @@ cc_binary(
)
cc_binary(
+ name = "socket_ip_unbound_netlink_test",
+ testonly = 1,
+ srcs = [
+ "socket_ip_unbound_netlink.cc",
+ ],
+ linkstatic = 1,
+ deps = [
+ ":ip_socket_test_util",
+ ":socket_netlink_route_util",
+ ":socket_test_util",
+ "//test/util:capability_util",
+ gtest,
+ "//test/util:test_main",
+ "//test/util:test_util",
+ ],
+)
+
+cc_binary(
name = "socket_domain_test",
testonly = 1,
srcs = [
diff --git a/test/syscalls/linux/socket_ip_unbound.cc b/test/syscalls/linux/socket_ip_unbound.cc
index 8f7ccc868..029f1e872 100644
--- a/test/syscalls/linux/socket_ip_unbound.cc
+++ b/test/syscalls/linux/socket_ip_unbound.cc
@@ -454,23 +454,15 @@ TEST_P(IPUnboundSocketTest, SetReuseAddr) {
INSTANTIATE_TEST_SUITE_P(
IPUnboundSockets, IPUnboundSocketTest,
- ::testing::ValuesIn(VecCat<SocketKind>(VecCat<SocketKind>(
+ ::testing::ValuesIn(VecCat<SocketKind>(
ApplyVec<SocketKind>(IPv4UDPUnboundSocket,
- AllBitwiseCombinations(List<int>{SOCK_DGRAM},
- List<int>{0,
- SOCK_NONBLOCK})),
+ std::vector<int>{0, SOCK_NONBLOCK}),
ApplyVec<SocketKind>(IPv6UDPUnboundSocket,
- AllBitwiseCombinations(List<int>{SOCK_DGRAM},
- List<int>{0,
- SOCK_NONBLOCK})),
+ std::vector<int>{0, SOCK_NONBLOCK}),
ApplyVec<SocketKind>(IPv4TCPUnboundSocket,
- AllBitwiseCombinations(List<int>{SOCK_STREAM},
- List<int>{0,
- SOCK_NONBLOCK})),
+ std::vector{0, SOCK_NONBLOCK}),
ApplyVec<SocketKind>(IPv6TCPUnboundSocket,
- AllBitwiseCombinations(List<int>{SOCK_STREAM},
- List<int>{
- 0, SOCK_NONBLOCK}))))));
+ std::vector{0, SOCK_NONBLOCK}))));
} // namespace testing
} // namespace gvisor
diff --git a/test/syscalls/linux/socket_ip_unbound_netlink.cc b/test/syscalls/linux/socket_ip_unbound_netlink.cc
new file mode 100644
index 000000000..6036bfcaf
--- /dev/null
+++ b/test/syscalls/linux/socket_ip_unbound_netlink.cc
@@ -0,0 +1,104 @@
+// Copyright 2019 The gVisor Authors.
+//
+// Licensed 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
+//
+// http://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.
+
+#include <arpa/inet.h>
+#include <netinet/in.h>
+#include <sys/socket.h>
+#include <sys/types.h>
+#include <sys/un.h>
+
+#include <cstdio>
+#include <cstring>
+
+#include "gmock/gmock.h"
+#include "gtest/gtest.h"
+#include "test/syscalls/linux/ip_socket_test_util.h"
+#include "test/syscalls/linux/socket_netlink_route_util.h"
+#include "test/syscalls/linux/socket_test_util.h"
+#include "test/util/capability_util.h"
+#include "test/util/test_util.h"
+
+namespace gvisor {
+namespace testing {
+
+// Test fixture for tests that apply to pairs of IP sockets.
+using IPv6UnboundSocketTest = SimpleSocketTest;
+
+TEST_P(IPv6UnboundSocketTest, ConnectToBadLocalAddress_NoRandomSave) {
+ SKIP_IF(!ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_NET_ADMIN)));
+
+ // TODO(gvisor.dev/issue/4595): Addresses on net devices are not saved
+ // across save/restore.
+ DisableSave ds;
+
+ // Delete the loopback address from the loopback interface.
+ Link loopback_link = ASSERT_NO_ERRNO_AND_VALUE(LoopbackLink());
+ EXPECT_NO_ERRNO(LinkDelLocalAddr(loopback_link.index, AF_INET6,
+ /*prefixlen=*/128, &in6addr_loopback,
+ sizeof(in6addr_loopback)));
+ Cleanup defer_addr_removal =
+ Cleanup([loopback_link = std::move(loopback_link)] {
+ EXPECT_NO_ERRNO(LinkAddLocalAddr(loopback_link.index, AF_INET6,
+ /*prefixlen=*/128, &in6addr_loopback,
+ sizeof(in6addr_loopback)));
+ });
+
+ TestAddress addr = V6Loopback();
+ reinterpret_cast<sockaddr_in6*>(&addr.addr)->sin6_port = 65535;
+ auto sock = ASSERT_NO_ERRNO_AND_VALUE(NewSocket());
+ EXPECT_THAT(connect(sock->get(), reinterpret_cast<sockaddr*>(&addr.addr),
+ addr.addr_len),
+ SyscallFailsWithErrno(EADDRNOTAVAIL));
+}
+
+INSTANTIATE_TEST_SUITE_P(IPUnboundSockets, IPv6UnboundSocketTest,
+ ::testing::ValuesIn(std::vector<SocketKind>{
+ IPv6UDPUnboundSocket(0),
+ IPv6TCPUnboundSocket(0)}));
+
+using IPv4UnboundSocketTest = SimpleSocketTest;
+
+TEST_P(IPv4UnboundSocketTest, ConnectToBadLocalAddress_NoRandomSave) {
+ SKIP_IF(!ASSERT_NO_ERRNO_AND_VALUE(HaveCapability(CAP_NET_ADMIN)));
+
+ // TODO(gvisor.dev/issue/4595): Addresses on net devices are not saved
+ // across save/restore.
+ DisableSave ds;
+
+ // Delete the loopback address from the loopback interface.
+ Link loopback_link = ASSERT_NO_ERRNO_AND_VALUE(LoopbackLink());
+ struct in_addr laddr;
+ laddr.s_addr = htonl(INADDR_LOOPBACK);
+ EXPECT_NO_ERRNO(LinkDelLocalAddr(loopback_link.index, AF_INET,
+ /*prefixlen=*/8, &laddr, sizeof(laddr)));
+ Cleanup defer_addr_removal = Cleanup(
+ [loopback_link = std::move(loopback_link), addr = std::move(laddr)] {
+ EXPECT_NO_ERRNO(LinkAddLocalAddr(loopback_link.index, AF_INET,
+ /*prefixlen=*/8, &addr, sizeof(addr)));
+ });
+ TestAddress addr = V4Loopback();
+ reinterpret_cast<sockaddr_in*>(&addr.addr)->sin_port = 65535;
+ auto sock = ASSERT_NO_ERRNO_AND_VALUE(NewSocket());
+ EXPECT_THAT(connect(sock->get(), reinterpret_cast<sockaddr*>(&addr.addr),
+ addr.addr_len),
+ SyscallFailsWithErrno(EADDRNOTAVAIL));
+}
+
+INSTANTIATE_TEST_SUITE_P(IPUnboundSockets, IPv4UnboundSocketTest,
+ ::testing::ValuesIn(std::vector<SocketKind>{
+ IPv4UDPUnboundSocket(0),
+ IPv4TCPUnboundSocket(0)}));
+
+} // namespace testing
+} // namespace gvisor