[patch] Set SO_REUSEADDR on outgoing TCP connections

Marek Majkowski majek04 at gmail.com
Thu Apr 10 16:04:30 UTC 2014


On Thu, Apr 10, 2014 at 4:40 PM, Maxim Dounin <mdounin at mdounin.ru> wrote:
>> ...
>> The patch will work perfectly well assuming there aren't too many
>> connections to one destination address and port. If that happens the
>> kernel may randomly allocate an outgoing port number that is already
>> used for a given destination and attempt to connect() will fail with
>> EADDRNOTAVAIL. This is fairly easy to detect, and we can just retry
>> connecting again, using another random source port allocated by the
>> kernel.
>
> While it may be interesting approach to overcome the limitation, I
> don't think that this is something that should be done by clients
> in real life.  I think it's something kernel should care about,
> not clients.
>
> From practical point of view, trivial solutions are to avoid
> bind() or use multiple addresses for bind().

May I ask how can you specify multiple outgoing IP addresses for a single proxy?

Indeed, this patch does add complexity to the ngx_event_connect_peer
function. Unfortunately nginx currently supports bind before connect
and in current form it severely reduces the number of possible
outgoing connections. Using proxy_bind in current form is harmful.
This patch fixes that.

In perfect world kernel would be able to reuse ports established with
bind before connect. Actually kernel can do that already - this is
what the SO_REUSADDR flag is for. Unfortunately, due to BSD API
compatibility kernel needs to allocate outgoing port on bind() -
before it is told of the destination address. This inevitably may lead
to conflicts indicated by EADDRNOTAVAIL error on connect(), and
results in complexity in proper implementation of bind before connect.

A reasonable solution to bind before connect limitations is to either
merge this patch or retire proxy_bind option.

Cheers,
    Marek



More information about the nginx-devel mailing list