Tarantool development patches archive
 help / color / mirror / Atom feed
From: Vladislav Shpilevoy via Tarantool-patches <tarantool-patches@dev.tarantool.org>
To: tarantool-patches@dev.tarantool.org, gorcunov@gmail.com,
	sergepetrenko@tarantool.org
Subject: [Tarantool-patches] [PATCH 1/2] swim: add SO_BROADCAST option
Date: Thu, 18 Mar 2021 01:02:03 +0100	[thread overview]
Message-ID: <f3310c98835788f3d557994eca1e1891d77f7088.1616025567.git.v.shpilevoy@tarantool.org> (raw)
In-Reply-To: <cover.1616025567.git.v.shpilevoy@tarantool.org>

Swim node couldn't talk to broadcast network interfaces because
the option SO_BROADCAST wasn't set.

It worked fine for localhost broadcast, but failed for all the
other IPs. There is no a test, because the tests work for the
localhost only anyway.

It still fails on Mac though in case the swim node was bound to
127.0.0.1. Then somewhy sendto() raises EADDRNOTAVAIL on attempt
to broadcast beyond the local machine. Not present on Linux, where
such an error simply can't be returned from sendto(). This error
is ignored on Mac, because it is not critical.

Part of #5906
---
 src/lib/swim/swim_io.c            | 19 +++++++++++++++++--
 src/lib/swim/swim_transport_udp.c | 23 ++++++++++++++---------
 2 files changed, 31 insertions(+), 11 deletions(-)

diff --git a/src/lib/swim/swim_io.c b/src/lib/swim/swim_io.c
index c8558c43e..45df36ba4 100644
--- a/src/lib/swim/swim_io.c
+++ b/src/lib/swim/swim_io.c
@@ -512,8 +512,23 @@ static inline void
 swim_complete_send(struct swim_scheduler *scheduler, struct swim_task *task,
 		   ssize_t size)
 {
-	if (size < 0)
-		diag_log();
+	if (size < 0) {
+		bool is_critical = false;
+#if TARGET_OS_DARWIN
+		/*
+		 * On Mac this error happens regularly if SWIM is bound to
+		 * the localhost and tries to broadcast out of the machine. This
+		 * is not critical, because will happen in the tests a lot, and
+		 * in prod it simply should not bind to localhost if there are
+		 * multiple machines in the cluster. Besides, Mac as a platform
+		 * is not supposed to be used in prod.
+		 */
+		struct error *last = diag_last_error(diag_get());
+		is_critical = (last->saved_errno == EADDRNOTAVAIL);
+#endif
+		if (is_critical)
+			diag_log();
+	}
 	if (task->complete != NULL)
 		task->complete(task, scheduler, size);
 }
diff --git a/src/lib/swim/swim_transport_udp.c b/src/lib/swim/swim_transport_udp.c
index c0317a20b..12626cc49 100644
--- a/src/lib/swim/swim_transport_udp.c
+++ b/src/lib/swim/swim_transport_udp.c
@@ -80,25 +80,27 @@ swim_transport_bind(struct swim_transport *transport,
 		return 0;
 	}
 
+	int is_on = 1;
+	int real_port = new_addr->sin_port;
 	int fd = sio_socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
 	if (fd < 0)
 		return -1;
-	if (sio_bind(fd, (struct sockaddr *) addr, addr_len) != 0 ||
-	    evio_setsockopt_server(fd, AF_INET, SOCK_DGRAM) != 0) {
+	if (sio_bind(fd, (struct sockaddr *) addr, addr_len) != 0) {
 		if (errno == EADDRINUSE)
 			diag_set(SocketError, sio_socketname(fd), "bind");
-		close(fd);
-		return -1;
+		goto end_error;
 	}
-	int real_port = new_addr->sin_port;
+	if (sio_setsockopt(fd, SOL_SOCKET, SO_BROADCAST, &is_on,
+			   sizeof(is_on)) != 0)
+		goto end_error;
+	if (evio_setsockopt_server(fd, AF_INET, SOCK_DGRAM) != 0)
+		goto end_error;
 	if (is_new_port_any) {
 		struct sockaddr_in real_addr;
 		addr_len = sizeof(real_addr);
 		if (sio_getsockname(fd, (struct sockaddr *) &real_addr,
-				    &addr_len) != 0) {
-			close(fd);
-			return -1;
-		}
+				    &addr_len) != 0)
+			goto end_error;
 		real_port = real_addr.sin_port;
 	}
 	if (transport->fd != -1)
@@ -107,6 +109,9 @@ swim_transport_bind(struct swim_transport *transport,
 	transport->addr = *new_addr;
 	transport->addr.sin_port = real_port;
 	return 0;
+end_error:
+	close(fd);
+	return -1;
 }
 
 void
-- 
2.24.3 (Apple Git-128)


  reply	other threads:[~2021-03-18  0:02 UTC|newest]

Thread overview: 16+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2021-03-18  0:02 [Tarantool-patches] [PATCH 0/2] Swim broadcast errors Vladislav Shpilevoy via Tarantool-patches
2021-03-18  0:02 ` Vladislav Shpilevoy via Tarantool-patches [this message]
2021-03-18  0:49   ` [Tarantool-patches] [PATCH 1/2] swim: add SO_BROADCAST option Vladislav Shpilevoy via Tarantool-patches
2021-03-18 19:37   ` Cyrill Gorcunov via Tarantool-patches
2021-03-18 20:47     ` Vladislav Shpilevoy via Tarantool-patches
2021-03-18 21:27       ` Cyrill Gorcunov via Tarantool-patches
2021-03-18 22:34         ` Vladislav Shpilevoy via Tarantool-patches
2021-03-18 23:18         ` Vladislav Shpilevoy via Tarantool-patches
2021-03-19  6:53           ` Cyrill Gorcunov via Tarantool-patches
2021-03-19 20:18             ` Vladislav Shpilevoy via Tarantool-patches
2021-03-19 20:29               ` Cyrill Gorcunov via Tarantool-patches
2021-03-19 21:46             ` Vladislav Shpilevoy via Tarantool-patches
2021-03-19 22:15               ` Cyrill Gorcunov via Tarantool-patches
2021-03-18  0:02 ` [Tarantool-patches] [PATCH 2/2] lua: separate sched and script diag Vladislav Shpilevoy via Tarantool-patches
2021-03-19 13:17 ` [Tarantool-patches] [PATCH 0/2] Swim broadcast errors Serge Petrenko via Tarantool-patches
2021-03-19 22:37 ` Vladislav Shpilevoy via Tarantool-patches

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=f3310c98835788f3d557994eca1e1891d77f7088.1616025567.git.v.shpilevoy@tarantool.org \
    --to=tarantool-patches@dev.tarantool.org \
    --cc=gorcunov@gmail.com \
    --cc=sergepetrenko@tarantool.org \
    --cc=v.shpilevoy@tarantool.org \
    --subject='Re: [Tarantool-patches] [PATCH 1/2] swim: add SO_BROADCAST option' \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox