[zeromq-dev] ZMQ occupies random TCP ports on Windows

Michał Sznajder michalsznajder at gmail.com
Wed Sep 28 17:01:02 CEST 2011


On Wed, Sep 28, 2011 at 3:08 PM, Michał Sznajder
<michalsznajder at gmail.com> wrote:
>> 1. Enclose the signaler_t::make_fdpair function in a critical section so
>> that two simulataneous calls don't collide.
>>
>> 2. Use a fixed port number rather than OS-assigned one.
>>
>> Would you give it a try? If not, I'll add it to my TODO list.
>
> Did you mean something like this:
>
> diff --git a/ZeroMQ/zeromq/src/signaler.hpp b/ZeroMQ/zeromq/src/signaler.hpp
> --- a/ZeroMQ/zeromq/src/signaler.hpp
> +++ b/ZeroMQ/zeromq/src/signaler.hpp
> @@ -22,6 +22,7 @@
>  #define __ZMQ_SIGNALER_HPP_INCLUDED__
>
>  #include "fd.hpp"
> +#include "mutex.hpp"
>
>  namespace zmq
>  {
> @@ -45,11 +46,15 @@ namespace zmq
>
>     private:
>
> -        //  Creates a pair of filedescriptors that will be used
> +        //  Creates a pair of file descriptors that will be used
>         //  to pass the signals.
>         static int make_fdpair (fd_t *r_, fd_t *w_);
> +#if defined ZMQ_HAVE_WINDOWS
> +        static mutex_t socket_number_mutex;
> +        static unsigned short socket_number;
> +#endif
>
> -        //  Write & read end of the socketpair.
> +        //  Write & read end of the socket pair.
>         fd_t w;
>         fd_t r;
>
> diff --git a/ZeroMQ/zeromq/src/signaler.cpp b/ZeroMQ/zeromq/src/signaler.cpp
> --- a/ZeroMQ/zeromq/src/signaler.cpp
> +++ b/ZeroMQ/zeromq/src/signaler.cpp
> @@ -63,6 +63,8 @@
>
>  #if defined ZMQ_HAVE_WINDOWS
>  #include "windows.hpp"
> +unsigned short zmq::signaler_t::socket_number(50000);
> +zmq::mutex_t zmq::signaler_t::socket_number_mutex;
>  #else
>  #include <unistd.h>
>  #include <fcntl.h>
> @@ -233,7 +235,12 @@ int zmq::signaler_t::make_fdpair (fd_t *
>     memset (&addr, 0, sizeof (addr));
>     addr.sin_family = AF_INET;
>     addr.sin_addr.s_addr = htonl (INADDR_LOOPBACK);
> -    addr.sin_port = 0;
> +
> +    socket_number_mutex.lock ();
> +    addr.sin_port = htons (socket_number);
> +    socket_number++;
> +    socket_number_mutex.unlock ();
> +
>     rc = bind (listener, (const struct sockaddr*) &addr, sizeof (addr));
>     wsa_assert (rc != SOCKET_ERROR);
>
> This approach has obvious problem that multiple instances will
> collide. Any idea how to get a parameter here? Somehow via a
> zmq_init()?
>
> I also examined bind() documentation
> http://msdn.microsoft.com/en-us/library/windows/desktop/ms737550(v=vs.85).aspx
> . I found this
>
> < quote >
> For TCP/IP, if the port is specified as zero, the service provider
> assigns a unique port to the application from the dynamic client port
> range. On Windows Vista and later, the dynamic client port range is a
> value between 49152 and 65535. This is a change from Windows Server
> 2003 and earlier where the dynamic client port range was a value
> between 1025 and 5000. The maximum value for the client dynamic port
> range can be changed by setting a value under the following registry
> key:
> < /quote >
>
> Maybe I could depend on this and guarantee that "my" ports are outside
> of above "magic" ranges...
>
> Mike
>



More information about the zeromq-dev mailing list