diff options
author | Ghanan Gowripalan <ghanan@google.com> | 2021-09-14 17:17:17 -0700 |
---|---|---|
committer | gVisor bot <gvisor-bot@google.com> | 2021-09-14 17:20:30 -0700 |
commit | 39470428dd3c5fef966cee138ae00ab8b9059983 (patch) | |
tree | 98a2c5f1d0a4046ef94e3594c6eb5b9e3c6ff263 /test | |
parent | d6c99694bcb9a5e4ce50ff48d648ba6ada0b9687 (diff) |
Use a shared method to get loopback index
Code to get the loopback interface's index is scattered throughout the
syscall tests. Implement the code once and use that in tests (where
applicable).
While I am here, trim the dependencies/includes for network namespace
tests.
PiperOrigin-RevId: 396718124
Diffstat (limited to 'test')
-rw-r--r-- | test/syscalls/linux/BUILD | 6 | ||||
-rw-r--r-- | test/syscalls/linux/ip_socket_test_util.h | 3 | ||||
-rw-r--r-- | test/syscalls/linux/network_namespace.cc | 19 | ||||
-rw-r--r-- | test/syscalls/linux/packet_socket.cc | 9 | ||||
-rw-r--r-- | test/syscalls/linux/packet_socket_raw.cc | 11 | ||||
-rw-r--r-- | test/syscalls/linux/socket_ipv4_udp_unbound.cc | 61 | ||||
-rw-r--r-- | test/syscalls/linux/socket_ipv6_udp_unbound_external_networking.cc | 2 |
7 files changed, 41 insertions, 70 deletions
diff --git a/test/syscalls/linux/BUILD b/test/syscalls/linux/BUILD index b06b3d233..190135d6c 100644 --- a/test/syscalls/linux/BUILD +++ b/test/syscalls/linux/BUILD @@ -1446,6 +1446,7 @@ cc_binary( defines = select_system(), linkstatic = 1, deps = [ + ":ip_socket_test_util", ":unix_domain_socket_test_util", "//test/util:capability_util", "//test/util:cleanup", @@ -1465,6 +1466,7 @@ cc_binary( srcs = ["packet_socket.cc"], linkstatic = 1, deps = [ + ":ip_socket_test_util", ":unix_domain_socket_test_util", "//test/util:capability_util", "//test/util:cleanup", @@ -4132,12 +4134,10 @@ cc_binary( srcs = ["network_namespace.cc"], linkstatic = 1, deps = [ - "//test/util:socket_util", gtest, + ":ip_socket_test_util", "//test/util:capability_util", - "//test/util:posix_error", "//test/util:test_main", - "//test/util:test_util", "//test/util:thread_util", ], ) diff --git a/test/syscalls/linux/ip_socket_test_util.h b/test/syscalls/linux/ip_socket_test_util.h index 8f26f1cd0..930e26ca5 100644 --- a/test/syscalls/linux/ip_socket_test_util.h +++ b/test/syscalls/linux/ip_socket_test_util.h @@ -35,6 +35,9 @@ uint16_t PortFromInetSockaddr(const struct sockaddr* addr); // InterfaceIndex returns the index of the named interface. PosixErrorOr<int> InterfaceIndex(std::string name); +// GetLoopbackIndex returns the index of the loopback interface. +inline PosixErrorOr<int> GetLoopbackIndex() { return InterfaceIndex("lo"); } + // IPv6TCPAcceptBindSocketPair returns a SocketPairKind that represents // SocketPairs created with bind() and accept() syscalls with AF_INET6 and the // given type bound to the IPv6 loopback. diff --git a/test/syscalls/linux/network_namespace.cc b/test/syscalls/linux/network_namespace.cc index 1984feedd..aa9e1bc04 100644 --- a/test/syscalls/linux/network_namespace.cc +++ b/test/syscalls/linux/network_namespace.cc @@ -12,18 +12,9 @@ // See the License for the specific language governing permissions and // limitations under the License. -#include <net/if.h> -#include <sched.h> -#include <sys/ioctl.h> -#include <sys/socket.h> -#include <sys/types.h> - -#include "gmock/gmock.h" #include "gtest/gtest.h" +#include "test/syscalls/linux/ip_socket_test_util.h" #include "test/util/capability_util.h" -#include "test/util/posix_error.h" -#include "test/util/socket_util.h" -#include "test/util/test_util.h" #include "test/util/thread_util.h" namespace gvisor { @@ -37,13 +28,7 @@ TEST(NetworkNamespaceTest, LoopbackExists) { ASSERT_THAT(unshare(CLONE_NEWNET), SyscallSucceedsWithValue(0)); // TODO(gvisor.dev/issue/1833): Update this to test that only "lo" exists. - // Check loopback device exists. - int sock = socket(AF_INET, SOCK_DGRAM, 0); - ASSERT_THAT(sock, SyscallSucceeds()); - struct ifreq ifr; - strncpy(ifr.ifr_name, "lo", IFNAMSIZ); - EXPECT_THAT(ioctl(sock, SIOCGIFINDEX, &ifr), SyscallSucceeds()) - << "lo cannot be found"; + ASSERT_NE(ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()), 0); }); } diff --git a/test/syscalls/linux/packet_socket.cc b/test/syscalls/linux/packet_socket.cc index bfa5d179a..9515a48f2 100644 --- a/test/syscalls/linux/packet_socket.cc +++ b/test/syscalls/linux/packet_socket.cc @@ -29,6 +29,7 @@ #include "gtest/gtest.h" #include "absl/base/internal/endian.h" +#include "test/syscalls/linux/ip_socket_test_util.h" #include "test/syscalls/linux/unix_domain_socket_test_util.h" #include "test/util/capability_util.h" #include "test/util/cleanup.h" @@ -156,11 +157,9 @@ void CookedPacketTest::TearDown() { } int CookedPacketTest::GetLoopbackIndex() { - struct ifreq ifr; - snprintf(ifr.ifr_name, IFNAMSIZ, "lo"); - EXPECT_THAT(ioctl(socket_, SIOCGIFINDEX, &ifr), SyscallSucceeds()); - EXPECT_NE(ifr.ifr_ifindex, 0); - return ifr.ifr_ifindex; + int v = EXPECT_NO_ERRNO_AND_VALUE(gvisor::testing::GetLoopbackIndex()); + EXPECT_NE(v, 0); + return v; } // Receive and verify the message via packet socket on interface. diff --git a/test/syscalls/linux/packet_socket_raw.cc b/test/syscalls/linux/packet_socket_raw.cc index e57c60ffa..aa7182b01 100644 --- a/test/syscalls/linux/packet_socket_raw.cc +++ b/test/syscalls/linux/packet_socket_raw.cc @@ -14,14 +14,12 @@ #include <arpa/inet.h> #include <net/ethernet.h> -#include <net/if.h> #include <net/if_arp.h> #include <netinet/in.h> #include <netinet/ip.h> #include <netinet/udp.h> #include <netpacket/packet.h> #include <poll.h> -#include <sys/ioctl.h> #include <sys/socket.h> #include <sys/types.h> #include <unistd.h> @@ -29,6 +27,7 @@ #include "gmock/gmock.h" #include "gtest/gtest.h" #include "absl/base/internal/endian.h" +#include "test/syscalls/linux/ip_socket_test_util.h" #include "test/syscalls/linux/unix_domain_socket_test_util.h" #include "test/util/capability_util.h" #include "test/util/cleanup.h" @@ -156,11 +155,9 @@ void RawPacketTest::TearDown() { } int RawPacketTest::GetLoopbackIndex() { - struct ifreq ifr; - snprintf(ifr.ifr_name, IFNAMSIZ, "lo"); - EXPECT_THAT(ioctl(s_, SIOCGIFINDEX, &ifr), SyscallSucceeds()); - EXPECT_NE(ifr.ifr_ifindex, 0); - return ifr.ifr_ifindex; + int v = EXPECT_NO_ERRNO_AND_VALUE(gvisor::testing::GetLoopbackIndex()); + EXPECT_NE(v, 0); + return v; } // Receive via a packet socket. diff --git a/test/syscalls/linux/socket_ipv4_udp_unbound.cc b/test/syscalls/linux/socket_ipv4_udp_unbound.cc index 816d1181c..a4a793c86 100644 --- a/test/syscalls/linux/socket_ipv4_udp_unbound.cc +++ b/test/syscalls/linux/socket_ipv4_udp_unbound.cc @@ -15,8 +15,6 @@ #include "test/syscalls/linux/socket_ipv4_udp_unbound.h" #include <arpa/inet.h> -#include <net/if.h> -#include <sys/ioctl.h> #include <sys/socket.h> #include <sys/types.h> #include <sys/un.h> @@ -140,7 +138,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackNicNoDefaultSendIf) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); EXPECT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -238,7 +236,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackNic) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -326,7 +324,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNic) { // Set the default send interface. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &iface, sizeof(iface)), SyscallSucceeds()); @@ -346,7 +344,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNic) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -437,7 +435,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicConnect) { // Set the default send interface. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &iface, sizeof(iface)), SyscallSucceeds()); @@ -457,7 +455,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicConnect) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -548,7 +546,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelf) { // Set the default send interface. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &iface, sizeof(iface)), SyscallSucceeds()); @@ -568,7 +566,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelf) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -657,7 +655,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelfConnect) { // Set the default send interface. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &iface, sizeof(iface)), SyscallSucceeds()); @@ -677,7 +675,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelfConnect) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -770,7 +768,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelfNoLoop) { // Set the default send interface. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &iface, sizeof(iface)), SyscallSucceeds()); @@ -794,7 +792,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastLoopbackIfNicSelfNoLoop) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); EXPECT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -917,7 +915,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastDropNic) { // Register and unregister to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); EXPECT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -981,7 +979,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastIfSetShort) { // Create a valid full-sized request. ip_mreqn iface = {}; - iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + iface.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); // Send an optlen of 1 to check that optlen is enforced. EXPECT_THAT( @@ -1079,7 +1077,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastIfSetNicGetReqn) { auto socket2 = ASSERT_NO_ERRNO_AND_VALUE(NewSocket()); ip_mreqn set = {}; - set.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + set.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &set, sizeof(set)), SyscallSucceeds()); @@ -1140,7 +1138,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastIfSetNic) { auto socket2 = ASSERT_NO_ERRNO_AND_VALUE(NewSocket()); ip_mreqn set = {}; - set.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + set.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_MULTICAST_IF, &set, sizeof(set)), SyscallSucceeds()); @@ -1186,7 +1184,7 @@ TEST_P(IPv4UDPUnboundSocketTest, TestMultipleJoinsOnSingleSocket) { auto fd = socket1->get(); ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); EXPECT_THAT( setsockopt(fd, IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), @@ -1204,7 +1202,7 @@ TEST_P(IPv4UDPUnboundSocketTest, TestTwoSocketsJoinSameMulticastGroup) { ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); EXPECT_THAT(setsockopt(socket1->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -1419,7 +1417,7 @@ TEST_P(IPv4UDPUnboundSocketTest, TestBindToMcastThenJoinThenReceive) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(socket2->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -2110,16 +2108,11 @@ TEST_P(IPv4UDPUnboundSocketTest, SetAndReceiveIPPKTINFO) { EXPECT_EQ(cmsg->cmsg_level, level); EXPECT_EQ(cmsg->cmsg_type, type); - // Get loopback index. - ifreq ifr = {}; - absl::SNPrintF(ifr.ifr_name, IFNAMSIZ, "lo"); - ASSERT_THAT(ioctl(sender->get(), SIOCGIFINDEX, &ifr), SyscallSucceeds()); - ASSERT_NE(ifr.ifr_ifindex, 0); - // Check the data in_pktinfo received_pktinfo = {}; memcpy(&received_pktinfo, CMSG_DATA(cmsg), sizeof(in_pktinfo)); - EXPECT_EQ(received_pktinfo.ipi_ifindex, ifr.ifr_ifindex); + EXPECT_EQ(received_pktinfo.ipi_ifindex, + ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex())); EXPECT_EQ(received_pktinfo.ipi_spec_dst.s_addr, htonl(INADDR_LOOPBACK)); EXPECT_EQ(received_pktinfo.ipi_addr.s_addr, htonl(INADDR_LOOPBACK)); } @@ -2439,7 +2432,7 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastIPPacketInfo) { // Register to receive multicast packets. ip_mreqn group = {}; group.imr_multiaddr.s_addr = inet_addr(kMulticastAddress); - group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo")); + group.imr_ifindex = ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex()); ASSERT_THAT(setsockopt(receiver_socket->get(), IPPROTO_IP, IP_ADD_MEMBERSHIP, &group, sizeof(group)), SyscallSucceeds()); @@ -2484,16 +2477,10 @@ TEST_P(IPv4UDPUnboundSocketTest, IpMulticastIPPacketInfo) { EXPECT_EQ(cmsg->cmsg_level, IPPROTO_IP); EXPECT_EQ(cmsg->cmsg_type, IP_PKTINFO); - // Get loopback index. - ifreq ifr = {}; - absl::SNPrintF(ifr.ifr_name, IFNAMSIZ, "lo"); - ASSERT_THAT(ioctl(receiver_socket->get(), SIOCGIFINDEX, &ifr), - SyscallSucceeds()); - ASSERT_NE(ifr.ifr_ifindex, 0); - in_pktinfo received_pktinfo = {}; memcpy(&received_pktinfo, CMSG_DATA(cmsg), sizeof(in_pktinfo)); - EXPECT_EQ(received_pktinfo.ipi_ifindex, ifr.ifr_ifindex); + EXPECT_EQ(received_pktinfo.ipi_ifindex, + ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex())); if (IsRunningOnGvisor()) { // This should actually be a unicast address assigned to the interface. // diff --git a/test/syscalls/linux/socket_ipv6_udp_unbound_external_networking.cc b/test/syscalls/linux/socket_ipv6_udp_unbound_external_networking.cc index 09f070797..d72b6b53f 100644 --- a/test/syscalls/linux/socket_ipv6_udp_unbound_external_networking.cc +++ b/test/syscalls/linux/socket_ipv6_udp_unbound_external_networking.cc @@ -39,7 +39,7 @@ TEST_P(IPv6UDPUnboundExternalNetworkingSocketTest, TestJoinLeaveMulticast) { .ipv6mr_multiaddr = reinterpret_cast<sockaddr_in6*>(&multicast_addr.addr)->sin6_addr, .ipv6mr_interface = static_cast<decltype(ipv6_mreq::ipv6mr_interface)>( - ASSERT_NO_ERRNO_AND_VALUE(InterfaceIndex("lo"))), + ASSERT_NO_ERRNO_AND_VALUE(GetLoopbackIndex())), }; ASSERT_THAT(setsockopt(receiver->get(), IPPROTO_IPV6, IPV6_ADD_MEMBERSHIP, &group_req, sizeof(group_req)), |