From 80745587da06b0ff0900a788f431fe8496081ad5 Mon Sep 17 00:00:00 2001 From: Marcin Gozdalik Date: Fri, 12 Nov 2021 14:37:26 +0100 Subject: [PATCH 1/2] Allow to bind to IPv6 address specified by name, not address --- gunicorn/sock.py | 60 ++++++++++++++++++++++++++++++++---------------- 1 file changed, 40 insertions(+), 20 deletions(-) diff --git a/gunicorn/sock.py b/gunicorn/sock.py index eb2b6fa9c..fcb58de44 100644 --- a/gunicorn/sock.py +++ b/gunicorn/sock.py @@ -176,30 +176,50 @@ def create_sockets(conf, log, fds=None): return listeners # no sockets is bound, first initialization of gunicorn in this env. + some_sock_succeeded = False for addr in laddr: - sock_type = _sock_type(addr) - sock = None - for i in range(5): - try: - sock = sock_type(addr, conf, log) - except OSError as e: - if e.args[0] == errno.EADDRINUSE: - log.error("Connection in use: %s", str(addr)) - if e.args[0] == errno.EADDRNOTAVAIL: - log.error("Invalid address: %s", str(addr)) - msg = "connection to {addr} failed: {error}" - log.error(msg.format(addr=str(addr), error=str(e))) - if i < 5: - log.debug("Retrying in 1 second.") - time.sleep(1) + try: + if isinstance(addr, tuple): + addrinfos = socket.getaddrinfo(addr[0], addr[1], type=socket.SOCK_STREAM) else: - break + addrinfos = [(socket.AF_UNIX, None, None, None, addr)] + except OSError as e: + log.error("Failed getaddrinfo for %s: %s", str(addr), str(e)) + continue + for sock_family, _, _, _, sock_addr in addrinfos: + if sock_family == socket.AF_INET: + sock_class = TCPSocket + elif sock_family == socket.AF_INET6: + sock_class = TCP6Socket + elif sock_family == socket.AF_UNIX: + sock_class = UnixSocket + else: + log.warning("Ignoring unknown socket family: %s", str(sock_family)) + continue + sock = None + for i in range(5): + try: + sock = sock_class(sock_addr, conf, log) + except OSError as e: + if e.args[0] == errno.EADDRINUSE: + log.error("Connection in use: %s", str(sock_addr)) + if e.args[0] == errno.EADDRNOTAVAIL: + log.error("Invalid address: %s", str(sock_addr)) + msg = "connection to {addr} failed: {error}" + log.error(msg.format(addr=str(sock_addr), error=str(e))) + if i < 5: + log.debug("Retrying in 1 second.") + time.sleep(1) + else: + break - if sock is None: - log.error("Can't connect to %s", str(addr)) - sys.exit(1) + if sock is not None: + listeners.append(sock) + some_sock_succeeded = True - listeners.append(sock) + if not some_sock_succeeded: + log.error("Can't connect to %s", str(addr)) + sys.exit(1) return listeners From 34e862731fd64bd84e1c39862ea97bb69291cc72 Mon Sep 17 00:00:00 2001 From: Marcin Gozdalik Date: Tue, 7 Dec 2021 13:29:04 +0100 Subject: [PATCH 2/2] Exit if any of the addresses fails to bind --- gunicorn/sock.py | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/gunicorn/sock.py b/gunicorn/sock.py index fcb58de44..049fe20ed 100644 --- a/gunicorn/sock.py +++ b/gunicorn/sock.py @@ -176,8 +176,8 @@ def create_sockets(conf, log, fds=None): return listeners # no sockets is bound, first initialization of gunicorn in this env. - some_sock_succeeded = False for addr in laddr: + some_sock_succeeded = False try: if isinstance(addr, tuple): addrinfos = socket.getaddrinfo(addr[0], addr[1], type=socket.SOCK_STREAM) @@ -188,18 +188,18 @@ def create_sockets(conf, log, fds=None): continue for sock_family, _, _, _, sock_addr in addrinfos: if sock_family == socket.AF_INET: - sock_class = TCPSocket + sock_type = TCPSocket elif sock_family == socket.AF_INET6: - sock_class = TCP6Socket + sock_type = TCP6Socket elif sock_family == socket.AF_UNIX: - sock_class = UnixSocket + sock_type = UnixSocket else: log.warning("Ignoring unknown socket family: %s", str(sock_family)) continue sock = None for i in range(5): try: - sock = sock_class(sock_addr, conf, log) + sock = sock_type(sock_addr, conf, log) except OSError as e: if e.args[0] == errno.EADDRINUSE: log.error("Connection in use: %s", str(sock_addr)) @@ -217,9 +217,9 @@ def create_sockets(conf, log, fds=None): listeners.append(sock) some_sock_succeeded = True - if not some_sock_succeeded: - log.error("Can't connect to %s", str(addr)) - sys.exit(1) + if not some_sock_succeeded: + log.error("Can't connect to %s", str(addr)) + sys.exit(1) return listeners