99ee94728a
refer to https://man7.org/linux/man-pages/man7/ip.7.html IP_MULTICAST_IF (since Linux 1.2) Set the local device for a multicast socket. The argument for setsockopt(2) is an ip_mreqn or (since Linux 3.5) ip_mreq structure similar to IP_ADD_MEMBERSHIP, or an in_addr structure. (The kernel determines which structure is being passed based on the size passed in optlen.) For getsockopt(2), the argument is an in_addr structure. refer to https://man7.org/linux/man-pages/man7/ipv6.7.html IPV6_MULTICAST_IF Set the device for outgoing multicast packets on the socket. This is allowed only for SOCK_DGRAM and SOCK_RAW socket. The argument is a pointer to an interface index (see netdevice(7)) in an integer. testcase1: TEST_IMPL(udp_multicast_interface) { /* TODO(gengjiawen): Fix test on QEMU. */ RETURN_SKIP("Test does not currently work in QEMU"); int r; uv_udp_send_t req; uv_buf_t buf; struct sockaddr_in addr; struct sockaddr_in baddr; close_cb_called = 0; sv_send_cb_called = 0; ASSERT(0 == uv_ip4_addr("239.255.0.1", TEST_PORT, &addr)); r = uv_udp_init(uv_default_loop(), &server); ASSERT(r == 0); ASSERT(0 == uv_ip4_addr("0.0.0.0", 0, &baddr)); r = uv_udp_bind(&server, (const struct sockaddr*)&baddr, 0); ASSERT(r == 0); r = uv_udp_set_multicast_interface(&server, "0.0.0.0"); ASSERT(r == 0); /* server sends "PING" */ buf = uv_buf_init("PING", 4); r = uv_udp_send(&req, &server, &buf, 1, (const struct sockaddr*)&addr, sv_send_cb); ASSERT(r == 0); ASSERT(close_cb_called == 0); ASSERT(sv_send_cb_called == 0); /* run the loop till all events are processed */ uv_run(uv_default_loop(), UV_RUN_DEFAULT); ASSERT(sv_send_cb_called == 1); ASSERT(close_cb_called == 1); ASSERT(client.send_queue_size == 0); ASSERT(server.send_queue_size == 0); MAKE_VALGRIND_HAPPY(); return 0; } testcase2: TEST_IMPL(udp_multicast_interface6) { /* TODO(gengjiawen): Fix test on QEMU. */ RETURN_SKIP("Test does not currently work in QEMU"); int r; uv_udp_send_t req; uv_buf_t buf; struct sockaddr_in6 addr; struct sockaddr_in6 baddr; if (!can_ipv6()) RETURN_SKIP("IPv6 not supported"); close_cb_called = 0; sv_send_cb_called = 0; ASSERT(0 == uv_ip6_addr("::1", TEST_PORT, &addr)); r = uv_udp_init(uv_default_loop(), &server); ASSERT(r == 0); ASSERT(0 == uv_ip6_addr("::", 0, &baddr)); r = uv_udp_bind(&server, (const struct sockaddr*)&baddr, 0); ASSERT(r == 0); r = uv_udp_set_multicast_interface(&server, "::1%lo0"); r = uv_udp_set_multicast_interface(&server, NULL); ASSERT(r == 0); /* server sends "PING" */ buf = uv_buf_init("PING", 4); r = uv_udp_send(&req, &server, &buf, 1, (const struct sockaddr*)&addr, sv_send_cb); ASSERT(r == 0); ASSERT(close_cb_called == 0); ASSERT(sv_send_cb_called == 0); /* run the loop till all events are processed */ uv_run(uv_default_loop(), UV_RUN_DEFAULT); ASSERT(sv_send_cb_called == 1); ASSERT(close_cb_called == 1); MAKE_VALGRIND_HAPPY(); return 0; } Signed-off-by: wangchen <wangchen41@xiaomi.com> |
||
---|---|---|
.. | ||
CMakeLists.txt | ||
inet_globals.c | ||
inet_sockif.c | ||
inet_txdrain.c | ||
inet.h | ||
ipv4_build_header.c | ||
ipv4_getpeername.c | ||
ipv4_getsockname.c | ||
ipv4_getsockopt.c | ||
ipv4_setsockopt.c | ||
ipv6_build_header.c | ||
ipv6_getpeername.c | ||
ipv6_getsockname.c | ||
ipv6_getsockopt.c | ||
ipv6_setsockopt.c | ||
Kconfig | ||
Make.defs |