You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
it's confusing that open_tcp_listeners(0) by default gives you different ports on ipv4 and ipv6. there aren't great options here though. The only way to ask the kernel for a single port that works on all protocols and interfaces is to make a IPV6ONLY=False socket, bind to ("::", 0), and see what port you get. Actually using such a socket seems too messy to be workable – there's address translation issues in and out, and Linux getaddrinfo acts weird (getaddrinfo("google.com", 80, family=AF_INET6, flags=AI_V4MAPPED | AI_ALL)only returns v4 addresses? wtf that's not what the docs say), and what do you do anyway if they don't want the wildcard address. Which means that once you have the port you have to close it and bind new sockets, and now there's a race condition b/c someone else could steal one, which means you need to retry, but this seems kinda messy. (Plus can we really distinguish reliably between an error that means we should retry and one that means we should bail out?) And what if they want to bind to several v4 addresses, should we then only probe the v4 wildcard? And what if we have a busy server where one interface has run out of ephemeral ports but another hasn't?
I guess it is possible to know that you should retry in the specific case where bind gives EADDRINUSE and you already made sure it was free a moment ago.
I also guess it's very rare to use ephemeral ports on real busy servers? I dunno.
The text was updated successfully, but these errors were encountered:
it's confusing that
open_tcp_listeners(0)
by default gives you different ports on ipv4 and ipv6. there aren't great options here though. The only way to ask the kernel for a single port that works on all protocols and interfaces is to make a IPV6ONLY=False socket, bind to("::", 0)
, and see what port you get. Actually using such a socket seems too messy to be workable – there's address translation issues in and out, and Linuxgetaddrinfo
acts weird (getaddrinfo("google.com", 80, family=AF_INET6, flags=AI_V4MAPPED | AI_ALL)
only returns v4 addresses? wtf that's not what the docs say), and what do you do anyway if they don't want the wildcard address. Which means that once you have the port you have to close it and bind new sockets, and now there's a race condition b/c someone else could steal one, which means you need to retry, but this seems kinda messy. (Plus can we really distinguish reliably between an error that means we should retry and one that means we should bail out?) And what if they want to bind to several v4 addresses, should we then only probe the v4 wildcard? And what if we have a busy server where one interface has run out of ephemeral ports but another hasn't?it looks like tornado does this, just ignoring the race condition like my original implementation: https://github.com/tornadoweb/tornado/blob/d4094a0c2a7cddc654381c162ee7786d4bf8453b/tornado/netutil.py#L190-L194
I guess it is possible to know that you should retry in the specific case where
bind
givesEADDRINUSE
and you already made sure it was free a moment ago.I also guess it's very rare to use ephemeral ports on real busy servers? I dunno.
The text was updated successfully, but these errors were encountered: