Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Connect to first free port with TCP using 0MQ

I'm writing a distributed search algorithm in which agents need to listen on a TCP socket for incoming connections. At some point, the agent should bind a free TCP port. Port number is not important but agent should send his/her listening port number to other agents.

I guess this is right way of doing:

socket.bind("tcp://*:0");

Socket binds successfully but then, how do I get the port number that socket's bound to? I can't see any option code in zmq_getsockopt man page returning a port number.

like image 797
sorush-r Avatar asked May 22 '13 19:05

sorush-r


1 Answers

With Zeromq you use a string to bind or connect. The it starts with the protecol, tcp:// in your case, this is allright. Then you have a '*' which stand for all available devices. Then you end with the port numer :0 in your case.

socket.bind("tcp://*:2424)

Would try to bind at port 2424. If you run man zmq_tcp they advise the port number to be higher than 1024. Basically you should know your portnumber in advance, not after binding. In newer versions 3.2 it is also possible to specify the port :0 or :* then the os will decide where the port is. This can be retrieved with socket.getsockopt() as seen in the next example:

zmq::context_t context(1);
zmq::socket_t sock(context, ZMQ_REP);
char port[1024]; //make this sufficiently large. 
                 //otherwise an error will be thrown because of invalid argument. 
size_t size = sizeof(port);
try{
    sock.bind("tcp://*:*");
}
catch (zmq::error_t&e ){
    cerr << "couldn't bind to socket: " << e.what();
    return e.num();
}
sock.getsockopt( ZMQ_LAST_ENDPOINT, &port, &size );
cout << "socket is bound at port " << port << endl;

This will give the following output for example:

socket is bound at port tcp://0.0.0:53269

So you still have to parse 53269 from the string "tcp://0.0.0.0:53269" hope this helps

like image 53
hetepeperfan Avatar answered Oct 14 '22 17:10

hetepeperfan