Reputation: 24767
I want to find an open local port in some range.
How can I do that in the most efficient way, without connecting to the port.
Upvotes: 8
Views: 8118
Reputation: 311050
Just pass zero as the port number to new ServerSocket(), then it will find one for you. But you can forget about the range, it will choose from the system-defined range.
Upvotes: 0
Reputation: 221
Essentially the same idea as Karaszi, but instead of constructing that many sockets, use the InetSocketAddress and try to bind a ServerSocket to every address in range, until you hit an open one.
If you don't want to bind to that port (although if you don't, the socket may as well be bound the next moment after you check), use a plain Socket Object and try to connect to the ports - if it works, the port is taken, if it doesn't (and you don't have a firewall forbiding the connection), then it's most likely free.
Upvotes: 0
Reputation: 16209
If this is not about port-sniffing, but about service discovery, consider using a rendez-vous server (like an RMI server) or using the UDP protocol. Back in the day we used JXTA for this, but I hope there is a better alternative for this now.
Upvotes: 0
Reputation: 5892
There's a little problem you may face in a multitasking windows/unix environment: if some isPortAvailable(final int port) from any of the answers returns a true for you, that doesn't mean, that at the moment when you will actually bind it it still will be available. The better solution would be create a method
ServerSocket tryBind(int portRangeBegin, int portRangeEnd) throws UnableToBindException;
So that you will just launch it and receive open socket for you, on some available port in the given range.
Upvotes: 3
Reputation: 17923
One way to do is use some native network command and parse the output.
netstat -n
Its output is of following format.
you need to parse the 'Foreign Address column for localhost or 127.0.0.1' and get a list of busy ports. Then see if they are in the range you specified.
Upvotes: 0
Reputation: 31477
If you want to find a local open port to bind a server to, then you can create a ServerSocket
and if it does not throw an Exception, then it's open.
I did the following in one of my projects:
private int getAvailablePort() throws IOException {
int port = 0;
do {
port = RANDOM.get().nextInt(20000) + 10000;
} while (!isPortAvailable(port));
return port;
}
private boolean isPortAvailable(final int port) throws IOException {
ServerSocket ss = null;
try {
ss = new ServerSocket(port);
ss.setReuseAddress(true);
return true;
} catch (final IOException e) {
} finally {
if (ss != null) {
ss.close();
}
}
return false;
}
RANDOM
is a ThreadLocal
here, but of course you can do an incrementing part there.
Upvotes: 6