2

Another thread in my server process listens on a specific port that my main thread knows the number of. The main thread doesn't have access to the actual Socket object opened by the other thread, it just knows the number of the local port it would be listening on.

Is there a way to find out the state of this socket? I really only care about if it's listening vs. connected/established. But having access to all the states listed here: https://github.com/mss/java-netstat/blob/master/src/main/java/de/msquadrat/netstat/ConnectionState.java would be nice.

Now you might ask why I don't just use that project as it seems to do exactly what I'd want. Well, it only works on linux (or systems exposing the same /proc/net file system). I need something that is cross platform.

Edit: To respond to some of the comments below. I don't have access to any objects from the thread that is either listening or connected. I don't have access to that code, so I can't keep a global table of the connection state myself. And yes, the connection will either be in state LISTEN or ESTABLISHED. There can only be one connected client at a time and while that client is connected, the server code will not still be listening on that port. Here's the output of netstat while no client is connected:

$ netstat -nap | fgrep 10010
tcp        0      0 0.0.0.0:10010               0.0.0.0:*                   LISTEN      20096/java

And the same output when a client is connected:

$ netstat -nap | fgrep 10010
tcp        0      0 192.168.101.94:10010        10.0.42.252:50426           ESTABLISHED 20096/java

And just for completeness, here's an example of a more traditional TCP server when just listening:

$ netstat -nap | fgrep 8080
tcp        0      0 127.0.0.1:8080              0.0.0.0:*                   LISTEN      20096/java

And that same server with one connected client:

$ netstat -nap | fgrep 8080
tcp        0      0 127.0.0.1:8080              0.0.0.0:*                   LISTEN      20096/java          
tcp        0      0 127.0.0.1:8080              10.0.42.252:60660             ESTABLISHED 20096/java

As you can see, this server does what most servers do, it keeps listening after accepting a connection. So in that case there would be two sockets on that single local port, one in LISTEN and one in ESTABLISHED. But this is explicitly not the situation I have.

onlynone
  • 7,602
  • 3
  • 31
  • 50
  • check apache-mina if it suffice your need – Vishrant Jun 02 '16 at 16:19
  • I suggest you have a method available from the thread to pull the socket status using one or more of the various methods available for socket status http://docs.oracle.com/javase/6/docs/api/java/net/Socket.html see also http://stackoverflow.com/questions/969866/java-detect-lost-connection and http://stackoverflow.com/questions/10240694/java-socket-api-how-to-tell-if-a-connection-has-been-closed – Richard Chambers Jun 02 '16 at 16:20
  • Unfortunately I can't modify the code of the other thread. All I have to go on is the port number. – onlynone Jun 02 '16 at 16:27
  • @Vishrant I just looked at mina, but I'm not sure how I would use it. Do you have any pointers? – onlynone Jun 02 '16 at 17:06
  • there are APIs to read/ write data onto socket and there are call back mechanism to get the response – Vishrant Jun 02 '16 at 17:11
  • @Vishrant I'm not trying to read/write data from/to a socket (I don't even have access to the socket). I'm trying to figure out what state a given port is in. – onlynone Jun 02 '16 at 17:14
  • what exactly you mean by state? and what you want to do with that state? – Vishrant Jun 02 '16 at 17:21
  • @Vishrant As I mentioned in my initial question, by state I mean listening vs connected. And what I want to do with it is kind of irrelevant. I just want the main thread to do different things based on the state of the socket connection in the other thread. – onlynone Jun 02 '16 at 17:47
  • A server socket is always listening, there is no connected state. When a connection is made, a new socket is created for the actual communication (there can be many clients connected to the same service). When you say "port" thats only useful as a selection criterion, a connection is only unambigously identified by *IP plus port*. – Durandal Jun 02 '16 at 17:49
  • 1
    About the only thing that you can determine about a particular port in an OS independent way is whether it is in use/blocked or is available. To determine specifics about the connection in an OS independent way requires access to the socket using a port so that you can request information from the socket. `/proc/net` is how Linux exposes specific networking data as pseudo-files which can be looked at. A different OS will expose the data in a different way, perhaps WMI from Windows for instance. see http://www.onlamp.com/pub/a/linux/2000/11/16/LinuxAdmin.html – Richard Chambers Jun 02 '16 at 17:54
  • @RichardChambers: yeah that looks to be what I'm seeing. I sure wish 30 years ago Berkeley sockets included some way to get the state of a socket. – onlynone Jun 02 '16 at 18:20
  • @Durandal: you're being pedantic. Obviously the port is only used as a selection criteria, and that's what I'd be using to find the socket in use by the other thread, and that's all I need. But you're not correct about a socket always listening. Sure that's mostly the case typical servers. But in this case only one client is allowed at a time. So the socket bound to the port I'm interested in will either be in `LISTEN` or `ESTABLISHED` (or one of the intermediate states, or not exist if something has gone wrong) – onlynone Jun 02 '16 at 18:25
  • @Durandal: Oh, and I think an actual connection is only unambiguously identified by the tuple of (local_address, local_port, remote_address, remote_port). – onlynone Jun 02 '16 at 18:28
  • 1
    @onlynone what you seem to actually be asking for is some way to obtain a reference to a socket based on looking up a port and to then be able to query various state and status information from the socket reference. Berkeley sockets provides a way to get state/status information from the socket however what you are saying is that you do not have access to the socket and want to get a reference to any socket using a particular port, if the port is in use, by calling some API and then once you have the socket reference use the standard socket functions to query status/state. – Richard Chambers Jun 02 '16 at 19:15
  • 1
    So you already know that, but *still* asked as if all of that could be ignored and insist that you can want to find *the sockets state* with just *the port number*. You don't see the contradiction in cardinality? Fine, count me out :) – Durandal Jun 02 '16 at 19:17
  • @onlyone check APIs of apache-mina it has all you want. you can also write wrapper for the same. – Vishrant Jun 03 '16 at 08:33
  • @Durandal I didn't know that. That's why I asked the question. But in parallel to posting the question here I was also actively searching various APIs and references and google. My own research seemed to be indicating the same thing @RichardChambers stated. And Richard, yes that would be one way to do it (get a ref to a socket given a port number, then query that socket directly). An API that queries socket state without having to hold a ref to the socket would also work (for example, what `java-netstat` does). But it doesn't seem like that's possible in a platform independent way. – onlynone Jun 03 '16 at 15:07
  • @Vishrant I have checked out the APIs of apache-mina, but it seems like a library for writing networked applications. Would you be able to point me to a specific package or class or doc in that project that might apply to my situation? – onlynone Jun 03 '16 at 15:10
  • @Vishrant There is nothing in Apache Mina of any relevance to this question. If you think otherwise please state what you think it is. Otherwise please stop it. – user207421 Feb 24 '17 at 22:42
  • @EJP statement from apache mina `Apache MINA is a network application framework which helps users develop high performance and high scalability network applications easily. It provides an abstract event-driven asynchronous API over various transports such as TCP/IP and UDP/IP via Java NIO`. Well we used apache mina for Java to C++ asynchronous communication using socket programming and as it as asynchronous we had to maintain the state of communication.It would be an extra overhead of making a system call to get TCP Conn details so as apache mina suffice my need so asked to check if its useful – Vishrant Feb 25 '17 at 05:31
  • @Vishrant There is nothing there that answers the question. Please stop waffling and name the specific feature of MINA that does what the OP is asking, or else stop this now. – user207421 Feb 25 '17 at 07:03

2 Answers2

0

The answer is no. There's no platform independent way to query the connection state of a socket in java if you don't have access to the Socket or ServerSocket object.

onlynone
  • 7,602
  • 3
  • 31
  • 50
-1

The answer is yes. You'll need an SNMP library, and with it you can interrogate the TCP Connection Table to find out everything netstat can tell you, and yes this is platform-independent.

However this is overkill. All you should need to know about the socket is whether it is still connected or not, and only the code that has access to the socket should need to know. That code can maintain state in a global table for the information of the rest of the program if it's really necessary. You don't want to build SNMP into a server application unless it is of a really special kind.

Also your question as actually stated doesn't make sense:

'is there any way to get the state of a socket connection ... given its port number'

This is basically meaningless. A socket connection is ESTABLISHED, period, but any given port can be in multiple states at the same time, because there is a LISTENING socket and any number of accepted sockets all using it, any of which can be in any state. See any netstat display on a server.

Another thread in my server process listens on a specific port that my main thread knows the number of. The main thread doesn't have access to the actual Socket object opened by the other thread, it just knows the number of the local port it would be listening on.

If the other thread is listening it has a ServerSocket, not a Socket.

Is there a way to find out the state of this socket? I really only care about if it's listening vs. connected/established.

If it's a ServerSocket it's listening. If there is a current connection there is also a Socket that is connected, and both these are using the same port.

Re your comments:

by state I mean listening vs connected

Now that doesn't make sense. You're only using one port for all sockets in a server: one of them is listening, and the rest are connected. This information cannot possibly be of any use.

But you're not correct about a socket always listening.

Yes he is.

Sure that's mostly the case typical servers.

All TCP servers.

But in this case only one client is allowed at a time.

Doesn't make any difference. The socket you accept from is listening: the sockets you accept from it are connected. The number of connections allowed at a time is irrelevant.

So the socket bound to the port I'm interested in will either be in LISTEN or ESTABLISHED ...

Or both, as there will be at least two sockets bound to the port when there is a connection.

You're still not making sense.

user207421
  • 305,947
  • 44
  • 307
  • 483